Untitled

править

Насчет race-condition - "memory" гарантирует приавльный порядок ассемблерных инструкций. Это, конечно, уменьшает риск race-condition но не до нуля. Грабли заключаются в том что процессор может выполнить инструкции в другом порядке. И это может повлиять на второе ядро процессора. Пример: thread() {

 while (!shared_var1)
   /* nothing */;
 printf("%d\n", sharedvar2);

} main() {

sharedvar1=saredvar2=0;
start_thread(thread);
sleep(1);
sharedvar2=100;
sharedvar1=1;

} Идея: поток крутится в вечном цикле (spinlock) пока главный поток не разблокирует его. потом печатает занчение общей переменной (должно быть 100). Однако, может случиться так что процессор (а не компилятор!) переставит команды приравнивания в main() и цикл разблокируется перед(!) тем как запишется занчение в sharedvar2. Поэтому для самых хитрых есть настоящий memory barrier который заключается в специальных командах которые CPU не имеет права перставить местами. 94.230.134.146 14:43, 6 мая 2010 (UTC)Ответить

Например такая вещь думаю должа быть(доработайте что-ли): "

 asm (
 "                                         \
  <Инструкция> <источник>, <назначение>   ;\
  <Инструкция> <источник>, <назначение>   ;\
  ........, ..........                    ;\
 "
 :"=<Принадлежность>"(<Выходной операнд>), ...
 :"<Принадлежность>" (<Входной>), ...
 :<я незнаю>
 );
 Последние записи не обязательны, но если например нужно использовать <пренодлежность> то обязательна пустая <:> до.
 То есть в итоге
 :
 :"<пренодлежность>" (<Входной>), ...
 И так далие.
 --Принадлежности:
 (взято с http://dllpiton.net.ru/index.php?option=com_content&task=view&id=41&Itemid=112)
 Другие случаи применения constraints:
 "m" : memory operand
 "o" : memory operand с адресом , к которому прибавляется смещение из таблицы
 "V" : противовес предыдущему варианту
 "i" : immediate integer operand с заранее неизвестным значением
 "n" : immediate integer operand с заданным значением
 "g" : любой регистр , память или переменная
 Следующие констрэйнты специфичны только для x86 .
 "r" : Register operand constraint, look table given above.
 "q" : Registers a, b, c or d.
 "I" : Constant in range 0 to 31 (for 32-bit shifts).
 "J" : Constant in range 0 to 63 (for 64-bit shifts).
 "K" : 0xff.
 "L" : 0xffff.
 "M" : 0, 1, 2, or 3 (shifts for lea instruction).
 "N" : Constant in range 0 to 255 (for out instruction).
 "f" : Floating point register
 "t" : First (top of stack) floating point register
 "u" : Second floating point register
 "A" : Specifies the `a’ or `d’ registers. This is primarily useful for 64-bit integer values intended to be returned with the `d’ register holding the most significant bits and the `a’ register holding the least significant bits.
 "

В ассемблерных вставках нельзя использовать названия переменных

править

Данные примеры синтаксиса являются неверными

movl var,%eax — записать в %eax значение переменной var,
movl $var,%eax — загрузить адрес переменной var

В частности для следующего кода

int x=1;

__asm("mov x,%eax");

__asm("mov $x,%eax");

для 2ой и 3ей строки пишет,

undefined reference to `x'

Voproshatel (обс.) 16:07, 4 ноября 2018 (UTC)Ответить

Укажите строки документации gcc / gas в которых есть такой запрет. (https://gcc.gnu.org/onlinedocs/gcc/Using-Assembly-Language-with-C.html#Using-Assembly-Language-with-C) У вас может быть что-то странное вместо компилятора или вместо исходника. Что такое __asm и почему вы решили что это GNU Inl Asm (gcc имеет asm и __asm__; тогда как __asm - это какая-то проприетарщина из категории верблюжего синтаксиса). `a5b (обс.) 04:34, 5 ноября 2018 (UTC)Ответить