我正在尝试使用该功能
int rand(void)
在集会中。
我该如何使用它?我希望得到0到20之间的随机数。
我该怎么做?
我正在使用Ubuntu 32位操作系统并使用at& t汇编语法。 这是我的代码示例,我希望它在%edx注册表中添加0到20之间的随机数。
编辑:
mov $APPLES_X, %ebx
mov $0, %ecx
mov $20, %edx
loop_ax:
call rand
idiv %edx
mov %edx, (%ebx)
add $4, %ebx
inc %ecx
cmp NAPPLES, %ecx
jne loop_ax
答案 0 :(得分:6)
对于这类问题,最好的办法是让编译器为您完成大部分工作。例如。使用gcc,你可以使用gcc -S
为一个小样本C程序生成汇编程序源代码,该程序已经完成了你想做的事情:
#include <stdio.h>
#include <stdlib.h>
int main(void)
{
int x = rand();
printf("x = %d\n", x);
return 0;
}
生成程序集:
$ gcc -Wall -S -O3 -m32 rand.c -o rand.S
你得到:
.file "rand.c"
.section .rodata.str1.1,"aMS",@progbits,1
.LC0:
.string "x = %d\n"
.text
.p2align 4,,15
.globl main
.type main, @function
main:
leal 4(%esp), %ecx
andl $-16, %esp
pushl -4(%ecx)
pushl %ebp
movl %esp, %ebp
pushl %ecx
subl $20, %esp
call rand
movl $.LC0, (%esp)
movl %eax, 4(%esp)
call printf
addl $20, %esp
xorl %eax, %eax
popl %ecx
popl %ebp
leal -4(%ecx), %esp
ret
.size main, .-main
.ident "GCC: (SUSE Linux) 4.3.4 [gcc-4_3-branch revision 152973]"
.section .comment.SUSE.OPTs,"MS",@progbits,1
.string "OspWg"
.section .note.GNU-stack,"",@progbits
所以看起来你只需要:
call rand
,结果将在EAX
。
如果要将随机数的范围限制为0..20,请在上面的C程序中实现,彻底测试,然后重复上述过程以生成具有此附加功能的汇编源。
答案 1 :(得分:3)
您的原始代码并不遥远。请记住以下事项:
rand()
是标准的库函数,因此您需要将程序链接到该程序,否则找不到函数/可执行文件无法运行。gcc
将程序集文件“编译”为可执行文件,和/或使用gcc
将汇编程序生成的*.o
文件链接到可执行文件中,则所有必需的依赖库将是必要时添加。ld ...
进行手动链接,则需要了解所有这些内容并手动指定。%edx
是暂存寄存器(保留调用者),当您进行函数调用时会被覆盖。所以你必须向下移动mov $20, %edx
两行,在<{em> call rand
后执行。%ecx
,因此您无法将循环计数器保留在%ecx
中,除非您在{{之前/之后/之后将其保存/恢复到堆栈中1}}。call rand
,%esi
,%edi
或%ebp
。当然,如果您选择在函数中使用这些寄存器,则还必须添加代码以保存/恢复然后在函数的进入/退出时。除此之外,正如Paul所提到的,从编译器输出中学习总是一个好主意,特别是在汇编的情况下从优化的编译器输出中学习。你不需要编译为asm,只需编译成可执行文件,然后运行%ebx
来反汇编整个东西。