Extern в си: Программирование на C и C++

Что такое Extern в C?

Термин «extern» использовался для определения глобальных переменных в языке C. Слово «внешний» означает, что оно сокращено от слова «внешний», что означает «снаружи». Следовательно, эти переменные доступны во всем коде C. Эти переменные всегда инициализируются и определяются вне основного метода. Это руководство предназначено для пользователей, которые хотят изучить работу переменной extern с помощью языка C. Итак, вперед.

Содержание

  1. Пример 1:
  2. Пример 2:
  3. Пример 3:
  4. Заключение

Пример 1:

После запуска терминала по «Ctrl + Alt + T» вам необходимо создать C-файл. Команда «touch» широко используется для создания любого файла. Итак, мы создали файл «test.c» с инструкцией «touch», как показано ниже.

$ touch test.c

Откройте файл, чтобы добавить код C, используя инструкцию «nano». Слово «нано» используется для обозначения редактора GNU, используемого для обновления и редактирования файлов.

$ nano test.c

Внутри файла мы написали код, показанный на снимке. Включен файл заголовка потока ввода-вывода. После этого объявите внешнюю переменную «z». Мы не присвоили никакого значения переменной «z». В этом коде нет функции или основного метода. Оператор печати использовался для отображения значения внешней переменной «z».

Сохраните этот файл кода с помощью «Ctrl + S» и вернитесь в терминал с помощью «Ctrl + X». Компиляция этого файла C «test.c» была выполнена компилятором «gcc», поддерживаемым системой Ubuntu 20.04 Linux. Ошибка компиляции указывает на то, что внешняя переменная должна быть определена с некоторым значением.

$ gcc test.c

Пример 2:

Давайте снова откроем тот же файл, чтобы немного обновить его. На этот раз мы будем использовать в нашем коде «основной» метод. Мы объявили переменную «z» вне основного метода.

Компиляция файла «test.c» вызывает исключение, что переменная «z» не определена в основном методе. Это потому, что переменной «z» не было присвоено значение; следовательно, нет выделения памяти.

$ gcc test.c

Пожалуйста, откройте файл еще раз и обновите его, как показано на снимке. Мы объявили внешнюю переменную «z» вне основного метода, а затем изменили ее значение на «13» в основном методе. Оператор печати использовался для отображения значения.

После компиляции файла «test.c» мы получили ту же предыдущую ошибку и еще одну ошибку. Мы не присвоили значение внешней переменной «z»; следовательно, для «z» не выделена память. Кроме того, мы хотели изменить значение переменной «z» на «13», пока у нее еще нет выделенной памяти для сохранения значения.

$ gcc test.c

Пример 3:

Давайте еще раз немного обновим файл. На этот раз мы объявили и определили внешнюю переменную «z» вне основного метода со значением «13». В основном методе для печати и отображения значения внешней переменной «z» использовался оператор печати.

Как видно из выходных данных, компиляция файла «test.c» прошла успешно.

$ gcc test.c

При успешном выполнении файла отображается сообщение об успешном выполнении и значение переменной «z». Это потому, что переменная «z» была определена и объявлена ​​одновременно.

$ ./a.out

Поскольку значение по умолчанию для внешней переменной всегда равно 0, вы можете использовать это для ее определения. Определив его как 0, вы можете легко изменить его значение любым методом, как показано ниже.

Компиляция будет успешной.

$ gcc test.c

Оператор печати также будет работать правильно после этого обновления.

$ ./a.out

Вы также можете присвоить значение переменной вне функции, а затем определить его в методе для тех же результатов.

Компиляция и исполнение показаны на изображении. В выходных данных было продемонстрировано внешнее значение.

$ gcc test.c

$ ./a.out

Заключение

Эта статья содержит ключевые слова extern на языке C, используя несколько простых и легких примеров. Реализация содержит объявление внешней переменной внутри и вне основного метода и поможет вам в лучшем случае.

c++ — c extern при множественном объявлении

Подскажите, как ведет себя extern в следующей ситуации:

extern int a,
           b,
           c;

Все три переменные a, b и c являются внешними, так ведь?

5

Да, все 3 являются внешними.

Кстати, чтобы это проверить, достаточно их объявить и использовать с наблюдаемым поведением (это важно!). В таком случае линкер сообщит о попытках использовать несуществующие переменные: https://ideone.com/rgf40P

extern int a, b, c;
int main()
{
  return a + b + c;
}
/home/CPCz1j/ccrst43X. o: In function `main':
prog.cpp:(.text.startup+0x2): undefined reference to `b'
prog.cpp:(.text.startup+0x8): undefined reference to `a'
prog.cpp:(.text.startup+0xe): undefined reference to `c'
collect2: error: ld returned 1 exit status
4

В синтаксисе объявления спецификатор класса хранения extern входит в «общую» часть объявления (declaration-specifiers в С, decl-specifier-seq в С++), то есть относится ко всем деклараторам в объявлении, а не к какому-то одному. В вашем примере все три переменные объявлены с внешним связыванием.

Отдельный вопрос — что вы имеете в виду под «являются внешними». Спецификатор extern просто придает идентификатору внешнее связывание. Но он совсем не говорит, что данная переменная определена где-то в другом месте.

Например, объявление

extern int a,
           b = 42,
           c;

говорит о том, что переменные a и c имеют внешнее связывание и определены где-то в другом месте, а вот переменная b имеет внешнее связывание и определена здесь (и доступна из других мест).

Другими словами, спецификатор extern может иметь как семантику «импорта», так и семантику «экспорта», в зависимости от того, является ли объявление переменной или функции еще и определением.

8

Зарегистрируйтесь или войдите

Регистрация через Google

Регистрация через Facebook

Регистрация через почту

Отправить без регистрации

Почта

Необходима, но никому не показывается

Отправить без регистрации

Почта

Необходима, но никому не показывается

By clicking “Отправить ответ”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

С++ — Действительно ли необходимо ключевое слово extern?

спросил

Изменено 10 лет назад

Просмотрено 4к раз

 ...
#include "test1.h"
инт основной(..)
{
    количество << ааа <

aaa определяется в test1.h , и я не использовал ключевое слово extern, но все же могу сослаться на aaa .

Так что я сомневаюсь, что extern действительно необходим?

  • С++
  • внешний
1

extern имеет свои применения. Но в основном это касается «глобальных переменных», которые не одобряются. Основная идея extern состоит в том, чтобы объявить вещи с внешней связью. Таким образом, это своего рода противоположность статический . Но внешняя связь во многих случаях является связью по умолчанию, поэтому в этих случаях вам не нужен extern . Другое использование extern : Он может превращать определения в объявления. Примеры:

 внешний интервал i; // Объявление i с внешней связью
               // (только сообщает компилятору о существовании i)
инт я; // Определение i с внешней связью
               // (фактически резервирует память, не должно быть в заголовочном файле)
константа int f = 3; // Определение f с внутренней связью (из-за константы)
                 // (Это относится только к C++, а не к C. В C f имело бы
                 // внешняя ссылка.) В C++ совершенно нормально поместить
                 // что-то вроде этого в заголовочный файл.
внешняя константа int g; // Объявление g с внешней связью
                    // можно поместить в заголовочный файл
extern const int g = 3; // Определение g с внешней связью
                        // Не должно быть в заголовочном файле
статический интервал т; // Определение t с внутренней связью.
// может появиться где угодно. Каждая единица перевода, которая // у такой строки есть свой собственный объект t.

Видите ли, это довольно сложно. Есть две ортогональные концепции: связь (внешняя и внутренняя) и вопрос объявления и определения. Ключевое слово

extern может влиять на оба. Что касается связи, это противоположность static . Но значение static также перегружено и — в зависимости от контекста — управляет или не управляет связью. Еще одна вещь, которую он делает, - это контроль времени жизни объектов («статическое время жизни»). Но в глобальном масштабе все переменные уже имеют статическое время жизни, и некоторые люди подумали, что было бы неплохо переработать ключевое слово для управления связью (это я просто догадываюсь).

Связывание в основном является свойством объекта или функции, объявленной/определенной в "пространстве имен". Если у него есть внутренняя связь, он не будет напрямую доступен по имени из других единиц перевода. Если он имеет внешнюю связь, должно быть только одно определение для всех единиц перевода (с исключениями, см. правило одного определения).

2

Я обнаружил, что лучший способ организовать ваши данные — это следовать двум простым правилам:

  • Объявлять вещи только в заголовочных файлах.
  • Определяйте вещи в файлах C (или cpp, но я буду использовать C здесь для простоты).

Под объявлением я подразумеваю уведомление компилятора о том, что вещи существуют, но не выделяет для них память. Сюда входят typedef , struct , extern и так далее.

По определению, я обычно означает «выделить пространство для», например int и так далее.

Если у вас есть строка вида:

 инт ааа;
 

в заголовочном файле, каждая единица компиляции (в основном определяемая как входной поток для компилятора - файл C вместе со всем, что он приносит с #include , рекурсивно) получит свою собственную копию.

Это вызовет проблемы, если вы свяжете вместе два объектных файла, для которых определен один и тот же символ (за исключением некоторых ограниченных обстоятельств, таких как const ).

Лучший способ сделать это — определить эту переменную aaa в одном из ваших файлов C, а затем поместить:

 внешний внутренний ааа;
 

в вашем заголовочном файле.

Обратите внимание, что если ваш заголовочный файл включен только в один файл C, это не проблема. Но в этом случае у меня, вероятно, даже не было бы заголовочного файла. Заголовочные файлы, на мой взгляд, предназначены только для обмена вещами между модулями компиляции.

10

Если ваш test1.h имеет определение aaa и вы хотите включить файл заголовка в более чем одну единицу перевода, вы столкнетесь с ошибкой множественного определения, если только aaa не является постоянным. Лучше определить aaa в файле cpp и добавить определение extern в файл заголовка, который можно добавить в другие файлы в качестве заголовка.

Правило большого пальца для наличия переменной и константы в заголовочном файле

 extern int a ;//Объявления данных
 const float pi = 3.141593 ;//Определение констант
 

Поскольку константа имеет внутреннюю связь в С++, любая константа, определенная в единице перевода, не будет видна другой единице перевода, но это не относится к переменной, у которой есть внешняя связь, т. Е. Они видны для другой единицы перевода. Помещение определения переменной в заголовок, который используется в другой единице перевода, приведет к многократному определению переменной, что приведет к ошибке множественного определения.

В этом случае внешний не нужен. Extern необходим, когда символ объявлен в другой единице компиляции.

При использовании директивы предварительной обработки #include включаемый файл копируется вместо директивы. В этом случае вам не нужен extern , потому что компилятор уже знает aaa .

1

Если aaa не определен в другой единице компиляции, вам не нужен extern, в противном случае он вам нужен.

Зарегистрируйтесь или войдите в систему

Зарегистрируйтесь с помощью Google

Зарегистрироваться через Facebook

Зарегистрируйтесь, используя электронную почту и пароль

Опубликовать как гость

Электронная почта

Обязательно, но не отображается

Опубликовать как гость

Электронная почта

Требуется, но не отображается

Нажимая «Опубликовать свой ответ», вы соглашаетесь с нашими условиями обслуживания и подтверждаете, что прочитали и поняли нашу политику конфиденциальности и кодекс поведения.

Руководство по NASM

Руководство по NASM

Следующая глава | Предыдущая глава | Содержание | Индекс

NASM, хотя он пытается избежать бюрократии ассемблеров, таких как MASM и TASM, тем не менее, вынуждены поддерживать и несколько директив. Они описаны в этой главе.

Директивы NASM бывают двух типов: директивы уровня пользователя и примитивных директив. Как правило, каждая директива имеет уровень пользователя. форма и примитивная форма. Почти во всех случаях мы рекомендуем пользователям использовать пользовательские формы директив, реализованные в виде макросов которые называют примитивными формами.

Примитивные директивы заключаются в квадратные скобки; уровень пользователя директивы нет.

В дополнение к универсальным директивам, описанным в этой главе, каждая Формат объектного файла может опционально содержать дополнительные директивы для контролировать определенные функции этого формата файла. Эти Директивы , специфичные для формата, задокументированы вместе с форматами которые их реализуют, в главе 7.

6.1

БИТЫ : Указание режима целевого процессора

Директива BITS указывает, будет ли NASM должен генерировать код, предназначенный для работы на процессоре, работающем в 16-битном режим, 32-битный режим или 64-битный режим. Синтаксис БИТ XX , где ХХ равно 16, 32 или 64.

В большинстве случаев вам не нужно использовать BITS явно. из , кофф , эльф , мачо , win32 и форматы объектов win64 , предназначенные для использования в 32-разрядных или 64-разрядных операционных системах все заставляют NASM выбирать 32-разрядную или 64-битный режим соответственно по умолчанию. объект Формат объекта позволяет указать каждый сегмент, который вы определяете, как USE16 или USE32 и NASM соответствующим образом установит свой режим работы, поэтому использование BITS Директива снова не нужна.

Наиболее вероятная причина использования BITS директива заключается в написании 32-битного или 64-битного кода в плоском двоичном файле; Это потому что выходной формат bin по умолчанию 16-битный режим в ожидании того, что он будет чаще всего использоваться для написания DOS . COM программы, DOS .SYS драйверы устройств и программное обеспечение загрузчика.

Вы делаете не нужно указать БИТ 32 просто для того, чтобы использовать 32-битные инструкции в 16-битной программе DOS; если вы сделать, ассемблер сгенерирует неправильный код, потому что он будет писать код, ориентированный на 32-битную платформу, для запуска на 16-битной.

Когда NASM находится в режиме BITS 16 , инструкции которые используют 32-битные данные, имеют префикс 0x66 байт, а те, которые ссылаются на 32-битные адреса имеют префикс 0x67. В BITS 32 режим, верно обратное: 32-битный инструкции не требуют префиксов, тогда как инструкции, использующие 16-битные данные нужен 0x66, а тем, кто работает с 16-битными адресами, нужен 0x67.

Когда NASM находится в режиме BITS 64 , большинство инструкции работают так же, как и для БИТ 32 режим. Однако есть еще 8 общих и регистры SSE, а 16-битная адресация больше не поддерживается.

Размер адреса по умолчанию — 64 бита; можно выбрать 32-битную адресацию с префиксом 0x67. Однако размер операнда по умолчанию по-прежнему составляет 32 бита. а префикс 0x66 выбирает 16-битный размер операнда. Префикс REX используется как для выбора 64-битного операнда размера и для доступа к новым регистрам. NASM автоматически вставляет REX префиксы, когда это необходимо.

При использовании префикса REX процессор не знает, как адресовать AH, BH, CH или DH (высокий 8-битный устаревший) регистры. Вместо этого можно получить доступ к младшим 8 битам SP, BP SI и DI регистрируются как SPL, BPL, SIL и DIL соответственно; но только когда используется префикс REX.

БИТ 9Директива 0014 имеет точно эквивалентную примитивная форма, [БИТЫ 16] , [БИТЫ 32] и [БИТЫ 64] . Форма уровня пользователя представляет собой макрос, который не имеет никакой функции, кроме вызова примитивной формы.

Обратите внимание, что место необходимо, т. е. БИТС32 будет ли работать , а не !

6.1.1
USE16 и USE32 : Псевдонимы для BITS

" USE16 " и ` USE32 ' директивы могут быть использованы вместо ` БИТ 16 'и ` BITS 32 ', для совместимости с другими монтажники.

6.2

ПО УМОЛЧАНИЮ : изменить настройки ассемблера по умолчанию

Директива DEFAULT изменяет ассемблер значения по умолчанию. Обычно NASM по умолчанию работает в режиме, в котором программист ожидается, что большинство функций будет явно указано напрямую. Однако это иногда неприятный, так как явная форма почти единственная человек хочет использовать.

В настоящее время ПО УМОЛЧАНИЮ можно установить REL и АБС и БНД и НОБНД .

6.2.1
REL и ABS : RIP-относительная адресация

Устанавливает, будут ли выполняться безрегистровые инструкции в 64-битном режиме. RIP - относительный или нет. По умолчанию они абсолютное значение, если оно не переопределено спецификатором REL . (см. раздел 3.3). Однако, если УСТАНОВЛЕН ОТНОСИТЕЛЬ ПО УМОЛЧАНИЮ , REL используется по умолчанию, если не Спецификатор ABS , , за исключением случаев, когда используется с FS или Переопределение сегмента GS .

Особое обращение с FS и Коррекция GS связана с тем, что эти регистры обычно используются в качестве указателей потоков или других специальных функций. в 64-битном режиме и генерирует RIP -относительный адреса будут очень запутанными.

СТАНДАРТ ПО УМОЛЧАНИЮ отключен с АБС ПО УМОЛЧАНИЮ .

6.2.2
БНД и НОБНД : БНД префикс

Если установлено DEFAULT BND , все префиксы bnd доступные инструкции, следующие за этой директивой, имеют префикс bnd. К отменить его, можно использовать префикс NOBND .

 ПО УМОЛЧАНИЮ BND
     вызовите Фу; BND будет иметь префикс
     вызов nobnd foo ; BND НЕ будет иметь префикс
 

ПО УМОЛЧАНИЮ NOBND можно отключить ПО УМОЛЧАНИЮ BND и затем Префикс BND будет добавлен только тогда, когда явно указано в коде.

ПО УМОЛЧАНИЮ BND считается нормальным конфигурация для написания кода с поддержкой MPX.

6.3

РАЗДЕЛ или СЕГМЕНТ : изменение и определение разделов

Директива РАЗДЕЛ ( СЕГМЕНТ является точно эквивалентным синонимом) изменяет, в каком разделе выходного файла будет код, который вы пишете собран в. В некоторых форматах объектных файлов количество и имена секции фиксируются; в других пользователь может составить столько, сколько пожелает. Отсюда РАЗДЕЛ иногда может выдавать ошибку сообщение или может определить новый раздел, если вы попытаетесь переключиться на раздел которого (пока) нет.

Форматы объектов Unix и объект bin формат (но см. раздел 7.1.3), все поддерживают стандартизированные имена разделов .text , .data и .bss для разделы кода, данных и неинициализированных данных. Формат obj , напротив, не распознает эти имена разделов как специальные, и действительно удалит начальные период любого имени раздела, в котором он есть.

6.3.1 Макрос
__SECT__

Директива SECTION необычна тем, что ее форма пользовательского уровня функционирует иначе, чем его примитивная форма. примитивная форма, [РАЗДЕЛ xyz] , просто переключает текущий целевой раздел на заданный. Форма уровня пользователя, SECTION xyz , однако, сначала определяет однострочный макрос __SECT__ в качестве примитива [РАЗДЕЛ] директива, которую он собирается издать, а потом выдает. Таким образом, директива уровня пользователя

        РАЗДЕЛ . text
 

расширяется до двух строк

%define __SECT__ [РАЗДЕЛ .текст]
        [РАЗДЕЛ .текст]
 

Пользователи могут счесть полезным использовать это в своих макросах. Для Например, макрос writefile , определенный в раздел 4.3.3 может быть полезен переписан в следующей более сложной форме:

%макрос записи в файл 2+
        [раздел .данные]
  %%стр: дб %2
  %%endstr:
        __SECT__
        мов дх,%%стр
        mov cx,%%endstr-%%str
        мов бх,%1
        мов ах, 0x40
        интервал 0x21
%endmacro
 

Эта форма макроса, после передачи строки на вывод, сначала переключается временно в раздел данных файла, используя примитивную форму директиву SECTION , чтобы не изменять __SECT__ . Затем он объявляет свою строку в данных раздел, а затем вызывает __SECT__ для обратного переключения на в зависимости от того, в каком разделе ранее работал пользователь. позволяет избежать необходимости в предыдущей версии макроса включать JMP инструкция для перехода по данным, а также не выходит из строя, если в сложном Формат OBJ модуль, пользователь потенциально может собирать код в любом из нескольких отдельные разделы кода.

6.4

ABSOLUTE : Определение абсолютных меток

Директиву ABSOLUTE можно рассматривать как альтернативная форма РАЗДЕЛ : вызывает последующий код должен быть направлен не на физический раздел, а на гипотетический раздел, начинающийся с заданного абсолютного адреса. Единственный инструкции, которые вы можете использовать в этом режиме, Семейство РЭСБ .

АБСОЛЮТ используется следующим образом:

абсолютный 0x1A
    kbuf_chr resw 1
    kbuf_free resw 1
    кбуф резв 16
 

В этом примере описывается раздел области данных BIOS ПК в сегменте адрес 0x40: приведенный выше код определяет kbuf_chr как быть 0x1A, kbuf_free быть 0x1C и kbuf на 0x1E.

Пользовательская форма ABSOLUTE , как и у РАЗДЕЛ , переопределяет __SECT__ макрос при его вызове.

STRUC и ENDSTRUC определяются как макросы, использующие ABSOLUTE (и также __SECT__ ).

АБСОЛЮТНЫЙ не обязательно должен быть абсолютным константа в качестве аргумента: она может принимать выражение (на самом деле критическое выражение: см. раздел 3.8), и оно может быть значением в сегменте. Например, TSR может повторно использовать свой код установки. как BSS во время выполнения, например:

        орг 100ч ; это программа .COM
        установка джмп; код установки идет последним
        ; здесь проходит жилая часть ТСР
настраивать:
        ; теперь напишите код, который устанавливает TSR здесь
абсолютная установка
runtimevar1 resw 1
runtimevar2 резд 20
tsr_end:
 

Это определяет некоторые переменные «поверх» кода установки, так что после установка завершена, пространство, которое она заняла, может быть повторно использовано в качестве данных хранилище для работающего TSR. Символ `tsr_end' можно использовать для вычисления общий размер части ТСР, которую необходимо сделать резидентной.

6.5

ВНЕШНИЙ : Импорт символов из других модулей

EXTERN аналогичен директиве MASM EXTRN и ключевое слово C extern : используется для объявления символа, который нигде в собираемом модуле не определено, но предполагается определен в каком-то другом модуле, и на него должен ссылаться этот модуль. Нет каждый формат объектного файла может поддерживать внешние переменные: бин формат не может.

EXTERN директива принимает столько аргументов как вам нравится. Каждый аргумент является именем символа:

внешний _printf
внешний _sscanf,_fscanf
 

Некоторые форматы объектных файлов предоставляют дополнительные возможности для ВНЕШНЯЯ директива . Во всех случаях доп. функции используются путем добавления двоеточия к имени символа, за которым следует объектно-форматный текст. Например, obj формат позволяет объявить, что база сегментов по умолчанию внешнего должна быть группа dgroup с помощью директива

extern _variable:wrt dgroup
 

Примитивная форма EXTERN отличается от пользовательского уровня только тем, что может принимать только один аргумент за раз: поддержка нескольких аргументов реализована на уровне препроцессора.

Вы можете объявить ту же переменную, что и EXTERN более одного раза: NASM спокойно проигнорирует второй и последующие передекларации. Вы не можете объявить переменную как ВНЕШНИЙ , а также что-то еще.

6.6

GLOBAL : Экспорт символов в другие модули

ГЛОБАЛЬНЫЙ это другой конец EXTERN : если один модуль объявляет символ как EXTERN и ссылается на него, то во избежание ошибки компоновщика, какой-то другой модуль должен на самом деле определять символ и объявите его как GLOBAL . Некоторые ассемблеры используют имя PUBLIC для этой цели.

ГЛОБАЛЬНЫЙ 9Директива 0014, применяемая к символу, должна появляются до определения символа.

GLOBAL использует тот же синтаксис, что и EXTERN , за исключением того, что он должен относиться к символам которые являются определенными в том же модуле, что и ГЛОБАЛЬНАЯ директива . Например:

глобальный _main
_основной:
        ; какой-то код
 

ГЛОБАЛЬНЫЙ , как ВНЕШНИЙ , позволяет форматам объектов определять частные расширения с помощью двоеточия. 9Например, формат объекта 0013 elf позволяет указать являются ли глобальные элементы данных функциями или данными:

глобальный хэш-поиск:функция, хеш-таблица:данные
 

Как и EXTERN , примитивная форма GLOBAL отличается от пользовательской формы только тем, что что он может принимать только один аргумент за раз.

6.7

ОБЩИЙ : Определение областей общих данных

Директива COMMON используется для объявления общих переменных . Общая переменная очень похожа на глобальную переменную объявлен в секции неинициализированных данных, так что

общий инвар 4
 

аналогичен по функциям

глобальная переменная
раздел .bss
интвар резд 1
 

Разница в том, что если несколько модулей определяют один и тот же общий переменная, то во время компоновки эти переменные будут объединены и ссылки на intvar во всех модулях будут указывать на тот же кусок памяти.

Аналогично ГЛОБАЛЬНЫЙ и ВНЕШНИЙ , ОБЩИЙ поддерживает расширения, специфичные для формата объекта. Например, Формат obj позволяет использовать общие переменные NEAR или FAR, а формат elf позволяет указать требования выравнивания общей переменной:

общий commvar 4:рядом ; работает в ОБЖ
общий интрарей 100:4 ; работает в ELF: выравнивание по 4 байтам
 

Еще раз, как ВНЕШНИЙ и ГЛОБАЛЬНЫЙ , примитивная форма COMMON отличается от пользовательской формы только что он может принимать только один аргумент за раз.

6.8

ЦП : определение зависимостей ЦП

Директива CPU ограничивает сборку теми инструкции, которые доступны на указанном ЦП.

Опции:

  • ЦП 8086 Сборка только набора инструкций 8086
  • CPU 186 Инструкции по сборке до 80186 Набор инструкций
  • CPU 286 Инструкции по сборке до 286 Набор инструкций
  • CPU 386 Инструкции по сборке до 386 Набор инструкций
  • ЦП 486 486 набор инструкций
  • ЦП 586 Набор инструкций Pentium
  • ЦП PENTIUM То же, что и 586
  • CPU 686 Набор инструкций P6
  • ЦП PPRO То же, что и 686
  • ЦП P2 То же, что и 686
  • CPU P3 Pentium III (Katmai) наборы инструкций
  • ЦП KATMAI То же, что и P3
  • ЦП P4 Pentium 4 (Willamette) набор инструкций
  • ЦП WILLAMETTE То же, что и P4
  • CPU PRESCOTT Набор инструкций Prescott
  • Процессор X64 x86-64 (x64/AMD64/Intel 64) Набор инструкций
  • CPU IA64 IA64 CPU (в режиме x86) инструкция набор

Все параметры нечувствительны к регистру. Все инструкции будут выбраны только если они применимы к выбранному процессору или ниже. По умолчанию все инструкции доступны.

6.9

FLOAT : Обработка констант с плавающей запятой

По умолчанию константы с плавающей запятой округляются до ближайшего, а IEEE денормалы поддерживаются. Следующие параметры могут быть установлены, чтобы изменить это поведение:

  • FLOAT DAZ Флеш денормализует до нуля
  • FLOAT NODAZ Не сбрасывать денормали до нуля (по умолчанию)
  • FLOAT NEAR Округление до ближайшего (по умолчанию)
  • FLOAT UP Округление вверх (в сторону +бесконечности)
  • FLOAT DOWN Округление в меньшую сторону (в сторону -бесконечности)
  • FLOAT ZERO Округление до нуля
  • FLOAT DEFAULT Восстановить настройки по умолчанию

Стандартные макросы __FLOAT_DAZ__ , __FLOAT_ROUND__ и __FLOAT__ содержат текущее состояние, если программист избегал использования примитивной формы в скобках, ( [ПЛАВАЮЩАЯ] ).

Оставить комментарий

Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *