Доброго времени суток, это снова канал Old Programmer и снова о программировании и только о программировании. Сегодня опять ассемблер, а здесь обзор материалов только по языку ассемблер
- Язык ассемблера (x86-64, Linux). Путеводитель по ресурсам канала Old Programmer
См. также
- И снова ассемблер (GAS x86-64) для Linux. Продолжаем работать со стеком, локальные переменные
Некоторые "фишки" ассемблера x86-64
У меня была статья на канале на Old Programmer:
- Программирование. Некоторые "фишки" языка C
Ну вот сегодня, несколько "фишек" языка ассемблер. Разумеется речь идет об x86-64. Сегодня, как и следует из названия, фишки касаются стека. Эти фишки я еще помню с тех времен, когда в 80-е годы я анализировал тексты компьютерных вирусов. Вот некоторые такие штуки использовались для того, чтобы затруднить анализ кода.
Вызов функции при помощи команды jmp
Поскольку мы теперь знаем. как устроен стек, то легко заменим команду call, вызова подпрограммы, на команду jmp, при условии, что в стеке будет лежать адрес возврата:
...
push $l2
jmp l1
l2:
...
l1:
...
ret
Возврат из функции с помощью команды jmp
Аналогично вызову и возврат из функции можно осуществить с помощью jmp, для это нужно только знать адрес возврата. Но мы же знаем, что он лежит в стеке.
...
pop %rax
jmp *%rax
...
Обратим внимание на команду jmp *%rax. Это косвенный переход по адресу, который лежит в регистре rax. Символ '*' обязателен.
Еще один вызов функции с помощью команды jmp
Вызов функции с помощью команды jmp возможен с помощью еще одного способа косвенного перехода. Если адрес лежит в памяти, а rax содержит адрес области памяти, где лежит адрес функции, то jmp *(%rax) это переход по адресу, который лежит в памяти
...
push $l2
mov $l1, %rax
mov %rax, addr
mov $addr, %rax
jmp *(%rax)
l2:
...
l1:
...
ret
Использование команды ret вместо jmp
Мы использовали jmp вместо call и ret, можно и наоборот, например ret использовать вместо jmp.
...
mov $10, %r15
l1:
# что-то делаем
...
dec %r15
jz l2
push $l1
ret # т.е. на самом деле просто jmp
l2:
...
Ну вот пока все. Таких интересных разностей на ассемблере довольно много и мы еще будем о них говорить.
Заканчиваем, но ассемблер на нашем канале Old Programmer продолжается. Подписывайтесь на мой канал, ставьте лайки и комментируйте.