Search     or:     and:
 LINUX 
 Language 
 Kernel 
 Package 
 Book 
 Test 
 OS 
 Forum 
iakovlev.org
Напишем простую программу , которая просто заносит число 20 в регистр eax , назовем ее first.s и откомрилируем ее командой
        cc first.s       
 .globl main
 main:
   movl $20, %eax
   ret    
Следующая программа вычисляет факториал числа, находящегося в регистре eax. Результат вычислений сохраняется в регистре ebx.
 .globl main
 main: 
     movl $5, %eax
     movl $1, %ebx
 L1:     cmpl $0, %eax           // сравнить содержимое регистра eax с 0
     je L2                   
    // переход на L2 если 0==eax (je - jump if equal, перейти если равно)
     imull %eax, %ebx        // ebx = ebx*eax
     decl %eax               // decrement eax (уменьшить на 1)
     jmp L1                  // безусловный переход на L1
 L2:     ret
 Здесь L1 и L2 -- это метки. 
Напишем программу , создающую и вызывающую другую подпрограмму .
 .globl main
 main:
     movl $10, %eax
     call foo
     ret
 foo:
     addl $5, %eax
     ret
Для работы со стеком используются 2 регистра - esp/ebp Адрес вершины стека хранится в esp . Стек растет от старших адресов к младшим . Следующий пример показывает работу со стеком :
 .globl main
 main:
   call foo
   ret
 foo:
   pushl %ebp
   movl %esp, %ebp
   subl $4, %esp
   movl $10, -4(%ebp)
   movl %ebp, %esp
   popl %ebp
   ret
 
Напишем комбинированный пример из 2-х исходников - один main.c и другой sqr.s и откомпилируем результат командой сс main.c sqr.s
 
 //main.c
 main()
 {
     int i = sqr(11);
     printf("%d\n",i);
 }
 //sqr.s
 .globl sqr
 sqr:
     movl 4(%esp), %eax
     imull %eax, %eax
     ret
 
Обратный вариант (вызов C-шной функции из ассемблера):
 
 //print.c
 print(int i)
 {
   printf("%d\n",i);
 }
 //main.s
 .globl main
 main:
   movl $123, %eax
   pushl %eax
   call print
   addl $4, %esp
   ret
 
Наберем простую программу add.c
 void main()
 {
  add(10,20);
 }
 
 int add(int i,int j)
 {
   int p = i + j;
  return p;
 }
 
 После команды gcc -S add.c получим asm-вариант:
 	.file	"add.c"
 	.text
 .globl main
 	.type	main, @function
 main:
 	pushl	%ebp
 	movl	%esp, %ebp
 	subl	$8, %esp
 	andl	$-16, %esp
 	movl	$0, %eax
 	subl	%eax, %esp
 	subl	$8, %esp
 	pushl	$20
 	pushl	$10
 	call	add
 	addl	$16, %esp
 	leave
 	ret
 	.size	main, .-main
 .globl add
 	.type	add, @function
 add:
 	pushl	%ebp
 	movl	%esp, %ebp
 	subl	$4, %esp
 	movl	12(%ebp), %eax
 	addl	8(%ebp), %eax
 	movl	%eax, -4(%ebp)
 	movl	-4(%ebp), %eax
 	leave
 	ret
 
Если обьявить глобальную переменную , то она будет оттранслирована с префиксом
          .globl
Можно дизассемблировать си-шные программы с помощью gdb . Компилировать нужно с опциями :
 cc -o myprogram -g myprogram.c -static
После этого запускаем gdb и говорим :
 file myprogram
 disassemble myprogram .
Оставьте свой комментарий !

Ваше имя:
Комментарий:
Оба поля являются обязательными

 Автор  Комментарий к данной статье