比较得到数组最大数
写一个比较得到最大数的汇编, 注意:
- long是4字节
- movl, mov运用在不同范围的数字, mov会搬运64位数字(超过了long的长度), movl会搬运32位(刚好是long的长度)
- rdx, edx是同一寄存器上的不同范围, rdx是64位, edx是32位
- 立即数寻址要加
$
真是耗费了我好些经历, 写了一整天, 每次都报错
segment fault
(其实是因为对数的范围和寻址不敏感, 导致访问了非法内存).
为此还学习了一番gdb调试, 真不戳!
.section .data
data_items:
.long 3, 74, 34, 222, 34, 75, 54, 34, 44, 33, 22, 11, 66
len = . - data_items
.section .text
.globl _start
_start:
mov $-4, %rdi
movl data_items(,1), %ebx
start_loop:
add $4, %rdi
# 比较是否到最后一个元素
cmp $len, %rdi
jae exit_loop
# 取元素比较大小
movl data_items(, %rdi), %eax
cmp %rax, %rbx
jle assign_max
jmp start_loop
assign_max:
mov %rax, %rbx
jmp start_loop
exit_loop:
mov $1, %rax
int $0x80
rasak@515jzl:~/Programs$ as -o demo.o demo.s
rasak@515jzl:~/Programs$ ld -d demo.o -o demo
rasak@515jzl:~/Programs$ ./demo
rasak@515jzl:~/Programs$ echo $?
222
各类寄存器用途
耶鲁x86汇编教程, 很不错的教程, 很清晰.
文中提到, 大部分寄存器都没有特殊用途, 除了rbp
和rsp
是用作栈的(64位系统). rip
指向当前执行的指令.
我们以一个简单例子说明:
.section .text
.globl _start
_start:
push $3
push $5
pop %rax
pop %rbx
gdb调试一下, 先运行两次nexti
, 也就是执行两次push
, 然后查看寄存器情况:
rip
指向当前的指令, rsp
指向的位置保存了5. rbp
为0(为什么呢?)