Assembly 在汇编中使用/dev/uradom生成256个数字;
我想知道如何使用/dev/uradom生成32位汇编中的数字。 我知道我应该在内存中有文件“/dev/uradom”的名称:Assembly 在汇编中使用/dev/uradom生成256个数字;,assembly,x86,32-bit,Assembly,X86,32 Bit,我想知道如何使用/dev/uradom生成32位汇编中的数字。 我知道我应该在内存中有文件“/dev/uradom”的名称: segment.data : file : db "/dev/random",10 len : equ $-file index : db "1",10 lenindex : equ $-index 然后我应该读取循环中的文件以生成一个数字,并在生成的数字的索引中写入1,这是我的循环 loop1 : xor ecx,ecx cmp ecx,256
segment.data :
file : db "/dev/random",10
len : equ $-file
index : db "1",10
lenindex : equ $-index
然后我应该读取循环中的文件以生成一个数字,并在生成的数字的索引中写入1,这是我的循环
loop1 : xor ecx,ecx
cmp ecx,256
je end_loop1
mov EAX, 5
mov ebx, file
mov ecx, 0; o for octal // I guess this is how i generate a number (by reading it)
mov edx, 0001o;o for octal // Permission on file.
inc ecx
int 0x80;
mov ebx,eax
mov eax,4
mov ecx,index
mov edx,lenindex
int 0x80
jmp loop1
正如你所说,我是32位汇编的初学者,如果有人解释如何使用/dev/uradom生成数字,并在生成的数字的索引中指示1,我会很高兴的。一次获取256个随机字节并打印它们(NASM assembler): 获得另一个范围,例如
mov edx, 2 ; Max. count of bytes to read
对于字范围(0..65535)。@IMSoP:
int 0x80
陷阱到操作系统,这是在32位x86手写asm中进行Linux系统调用的标准方法。(为了获得高性能,您可以调用
进入VDSO页面,该页面将使用sysenter
,但是int 0x80
更简单。)EAX=5/int 0x80是系统打开的(不属于循环内部)。EAX=4/int 0x80是sys\u write,但循环中没有sys\u read
。@N\u Craft:这是一个无限循环。为循环计数器使用不同的寄存器,系统调用输入需要ECXxor ecx,ecx
做ecx=0,所以你基本上是在(0!=256){write(open(“/dev/uradom”,0),index,lenidenx);}的时候做。i、 e.在以只读方式打开/dev/uradom后尝试写入它。(如果O_RDONLY=0,我就忘了。)我建议从C开始编写一个sane循环,然后在asm中实现它。@PeterCordes:谢谢你的帮助。然而,我对32汇编有一点了解,并且有很多困惑。我不知道如何使用循环,否则;如果我不能使用ecx,我可以使用哪个寄存器来递增和比较?ecx不是特别的,除非您使用循环
指令(您不应该使用它,因为它很慢)<代码>cmp
适用于任何寄存器。ESI或EDI在这里是很好的选择,因为int 0x80 ABI不涉及它们。32位x86只有8个通用寄存器。如果您不知道所有这些,以及如何使用dec reg
/jnz.top\u of_loop
循环等超基础知识,那么在开始编写进行系统调用的程序之前,您需要回到基础知识,阅读介绍体系结构基础知识的教程/指南。感谢您的澄清,我还是不明白你为什么要用字符串?@N\u Craft:随机数是来自/dev/uradom
的整数。Linux内核中没有像C:printf(“%u\n”,i)中那样直接打印它们的函数代码>。因此,我必须将它们转换为字符串,并使用SYS_WRITE函数。我明白了!事实上,我不想打印它们,但要确保它们生成成功,但谢谢分享!
SECTION .data ; Section containing initialised data
file db "/dev/urandom",0 ; NUL terminated (ASCIZ)!
loopcount dd 256
SECTION .bss ; Section containing uninitialised data
decstr resb 40 ; 40 Bytes for an ASCII string
decstr_len resd 1
filedescriptor resd 1
number resd 1
SECTION .text ; Section containing code
global _start ; Linker needs this to find the entry point!
_start:
; http://www.lxhp.in-berlin.de/lhpsysc1.html#open
mov eax, 5 ; SYSCALL open
mov ebx, file ; File descriptor
mov ecx, 0 ; Access: read only
mov edx, 0x00004 ; Mode: read by others
int 0x80 ; Call Linux kernel
mov [filedescriptor], eax ; Store the resulting fd
L1: ; Loop to print <loopcount> numbers
; http://www.lxhp.in-berlin.de/lhpsysc1.html#read
mov eax, 3 ; SYSCALL read
mov ebx, [filedescriptor] ; File descriptor
mov ecx, number ; Pointer to input buffer
mov edx, 4 ; Max. count of bytes to read
int 0x80 ; Call Linux kernel
; Print the number
mov eax, [number] ; Argument: Integer to convert
mov edi, decstr ; Argument: Address of the target string
call int2str ; Get the digits of EAX and store it as ASCII & LF & NUL
sub edi, decstr ; EDI (pointer to the terminating NULL) - pointer to decstr = length of the string
mov [decstr_len], edi ; Store the resulting length of the string
; http://www.lxhp.in-berlin.de/lhpsysc1.html#write
mov eax, 4 ; SYSCALL write
mov ebx, 1 ; File descriptor: STDOUT
mov ecx, decstr ; Pointer to output buffer
mov edx, [decstr_len] ; count of bytes to send
int 0x80
sub dword [loopcount], 1
jnz L1 ; Do it again
; http://www.lxhp.in-berlin.de/lhpsysc1.html#close
mov eax, 6 ; SYSCALL close
mov ebx, [filedescriptor] ; File descriptor
int 0x80 ; Call Linux kernel
; http://www.lxhp.in-berlin.de/lhpsysc1.html#exit
mov eax, 1 ; SYSCALL exit
mov ebx, 0 ; Exit Code
int 80h ; Call Linux kernel
int2str: ; Converts an positive integer in EAX to a string pointed to by EDI
xor ecx, ecx
mov ebx, 10
.LL1: ; First loop: Collect the remainders
xor edx, edx ; Clear EDX for div
div ebx ; EDX:EAX/EBX -> EAX Remainder EDX
push dx ; Save remainder
inc ecx ; Increment push counter
test eax, eax ; Anything left to divide?
jnz .LL1 ; Yes: loop once more
.LL2: ; Second loop: Retrieve the remainders
pop dx ; In DL is the value
or dl, '0' ; To ASCII
mov [edi], dl ; Save it to the string
inc edi ; Increment the pointer to the string
loop .LL2 ; Loop ECX times
mov word [edi], 0x0A ; Last characters: LF, NUL
inc edi
ret ; RET: EDI points to the terminating NULL
mov edx, 4 ; Max. count of bytes to read
mov edx, 2 ; Max. count of bytes to read