Здесь на форуме читал про простую задачу: инверсия битов числа из биг-ендиан в литле-ендиан и наоборот. Там писалось, что обычный программист напишет цикл, продвинутый - использует апи из вс2-32, а тот кто пишет на асме использует bswap. Мне хотелось бы узнать, знает ли кто-нибудь как использовать эту команду в ассемблерной вставке для синтаксиса AT&T, чтобы написать примерно такую функцию на Си++: void InvertBits (int& num) { asm ("bswap ???,???"); } или, того лучше оформить это макросом...
я вам сказал как будет правильнее с точки зрения с++ а дальге под свой компилятор/ассемблер сами уже... вот и пишите
ADD(редактирование верните) 4 работает с любым регистром (а не только с eax, куда возвращается результат) 5 если не изменяет память, то bswap появилась раньше чем написали API функцию, хотя скорее всего память мне изменяет.
Млин, стока ответов и ни одного толкового. Ну хоть кто нибудь напишите как использовать эту команду в инлайн варианте, или в асм варианте синтаксиса AT&T. Тут вообще есть те, кто эту команду хоть раз использовал?)
ОО спасибо тебе im1111, а теперь можешь тоже самое только в синтаксисе AT&T)) Как переобозначить регистр я знаю (добавлением %) а вот переменную он не хочет признавать!
Не на чем проверить ( Смотря какой компиль, он может и не позволит такой трюк. Вот 2 варианта: __inline VOID BSWAP(PDWORD x) { __asm { mov ecx, x mov eax, dword[ecx] bswap eax mov dword[ecx], eax } } __inline DWORD BSWAP(DWORD x) { __asm { mov eax, x bswap eax } } Первый создает довольно избыточный код в MSVC 9, а второй компиль инлайнит очень хорошо, но использовать не удобно -> x=BSWAP(x);
Попытался перевести на этот долбанутый синтаксис, вот что вышло: Код (Text): #define BSWAP(x) asm ("movl x, %eax"); asm ("bswap %eax"); asm("movl %eax, x"); Но при попытке использования так: int x = 5; int y = BSWAP (x); получаю собщение от линкера, что символ x - undefined reference. (( Блин осталось чуть-чуть..кто силен в асме американской телефонной компании.
Если компиль совсем тупой, то лучше вообще так: __inline DWORD BSWAP(DWORD x) { __asm { mov eax, x bswap eax mov x, eax } return x; }
Мой компиль от gcc вообще не понимает адекватный асм. Ругаеца на то что вы предлагаете в каждой строчке(( На тот код что мне удалось перевести ругаецо только в том что там переменная, если подставляю число ($0x4) допустим, то все компилится... И нигде пока не могу найти как работать с переменной ...Уже подумываю об htons, правда мне надо 4-х байтное число перевернуть...
Воть, попробуйте вкусненького: Код (Text): #include <stdio.h> #define _BSWAP(x) asm ("movl %%eax, %1\n\t" \ "bswap %%eax\n\t" \ "movl %0, %%eax\n\t" \ :"=r"(x) \ :"r"(x) \ :"%ecx") int main() { printf("hello asm!\n"); unsigned long var_dword = 0x000099BB; printf("var = 0x%X\n",var_dword); _BSWAP(var_dword); printf("result = 0x%X\n",var_dword); return 0; }
Praetor11 Как я понял ты компилишь gcc, в нем есть интринзик на эту инструкцию, лучше использовать его. Если gcc новый, то можно писать совместимо с msvc - интринзик _byteswap_ulong.
Термосинтез, огромное вам спасибо за хороший пример, он отлично компилируется и линкуется с одной только маленькой проблемой - не работает (, т.е. число не меняется... Не могли бы вы мне также объяснить почему перед именами регистров ставится два знака % и что означают магические строки: :"=r"(x) \ :"r"(x) \ :"%ecx") Я конечно понимаю что это глупые вопросы об асме, но найти ответы на них в гугле крайне сложно, потому как данный синтаксис плохо описан (полно по обычному асму). Код (Text): Как я понял ты компилишь gcc, в нем есть интринзик на эту инструкцию, лучше использовать его. Если gcc новый, то можно писать совместимо с msvc - интринзик _byteswap_ulong Да у меня гсс, правда не самый последний (хотя могу скачать и новее, но ради одной команды думаю глупо). Проверил: мой компиль ругаецо на это инструкцию, но это неудивительно в силу его возраста.
Praetor11 Как собирать: gcc -g MyProgBswap.c -o MyProgBswap Обрати внимание что исходник должен быть с расширением ".с" Про магические строки - приложу статью маленькую на интересную вам тему. Статья моя, но недописанная, и сейчас некогда дописывать.
Вообще бсвап юзается для скорости обычно, а это значит лишние movl там никчему, аналогом интринзика будет: asm ("bswap %1" : "=r" (i) : "0" (i)); если не ошибся нигде.