nasm随机数生成器函数

时间:2010-10-15 11:27:10

标签: assembly nasm

我需要一个用nasm编写的随机数生成器函数。 我很抱歉,但我找不到任何东西!

5 个答案:

答案 0 :(得分:1)

在许多情况下,拨打rdtsc就足够了。无论如何,这取决于您的需求。当你很少需要一个小的随机数时,它是完美的:rdtsc % N,或者作为其他情况的更复杂算法的种子。

答案 1 :(得分:1)

除其他外,Agner Fog有一个用汇编编写的随机数生成器,见here

答案 2 :(得分:0)

我不了解NASM,我不习惯按需编写代码,除非他们付钱给我。

但是,这里有你可以调查的算法:

答案 3 :(得分:0)

; in case you still are looking or for the ones who do look around nowadays, here is my
; experiment on random number generation.
; I hope it will be usefull.

STRUC TIMESPEC
    .tv_sec:    resq    1
    .tv_nsec:   resq    1
ENDSTRUC

STRUC TIMEVAL
    .tv_sec:    resq    1
    .tv_usec:   resq    1
ENDSTRUC

%define tv.tv_sec tv+TIMEVAL.tv_sec
%define tv.tv_usec tv+TIMEVAL.tv_usec
%define ts.tv_sec ts+TIMESPEC.tv_sec
%define ts.tv_nsec ts+TIMESPEC.tv_nsec

    NUMBERCOUNT equ 50
    MAXNUMBER   equ 7
    NUMBERLOOPS equ 50

section .bss

    array   resw    NUMBERCOUNT ; 20 64 bit words to store the numbers
    buffer  resb    1

section .data

ts: ISTRUC TIMESPEC
    at  TIMESPEC.tv_sec,    dq 0
    at  TIMESPEC.tv_nsec,   dq 0
IEND

tv: ISTRUC TIMEVAL
    at  TIMEVAL.tv_sec,     dq 0
    at  TIMEVAL.tv_usec,    dq 0
IEND

section .text

global _start
_start:

; start generating 20 random numbers between 0 and 20 both values included
; we will use the computers timer to obtain a seed and a pseudo random value 

;   call syscall clock_gettime for the seed

    xor r8,r8           ; loops
    inc     r8
repeatLoop:
    inc     r8
    push    r8
    xor rcx, rcx
    mov rdi, array
repeat:
    push    rcx
    push    rdi
    mov rsi, ts
    mov rdi, 0
    mov rax, SYS_CLOCK_GETTIME
    syscall

    mov rsi, 0
    mov rdi, tv
    mov rax, SYS_GETTIMEOFDAY
    syscall

    mov rax,[ts.tv_nsec]
    mov rbx,[tv.tv_usec]

    xor rdx, rdx
    add     rax, rbx
    mov rbx, MAXNUMBER+1
    div rbx

    mov rax, rdx
    xor rdx, rdx
    mov rbx, 10
    div rbx
    add     al,30h
    shl rax, 8
    mov al, dl
    add     al,30h
    pop rdi
    stosw

    pop rcx
    inc rcx
    cmp rcx, NUMBERCOUNT
    jl  repeat

    xor rcx, rcx
    mov rsi, array
repeatGet:  
    xor rax, rax
    lodsw
    push    rcx
    push    rsi
    call    WriteValue
    pop rsi
    pop rcx
    inc rcx
    cmp rcx, NUMBERCOUNT
    jl  repeatGet

    pop r8
    cmp r8,NUMBERLOOPS
    jg  Exit
    call    writeEOL
    jmp repeatLoop

Exit:   
    call    writeEOL
    xor rdi, rdi
    mov rax, SYS_EXIT
    syscall

writeEOL:
    mov al,ASCII_LF
    mov byte[buffer],al
    mov rsi,buffer
    mov rdi,STDOUT
    mov rdx, 1
    mov rax,SYS_WRITE
    syscall
    ret

WriteValue:
    cmp ah,"0"
    jne writeDecimal
    mov ah," "
writeDecimal:   
    mov byte[buffer],ah
    push    rax
    mov rsi,buffer
    mov rdi,STDOUT
    mov rdx, 1
    mov rax,SYS_WRITE
    syscall
    pop rax
writeUnit:
    mov byte[buffer],al
    mov rsi,buffer
    mov rdi,STDOUT
    mov rdx, 1
    mov rax,SYS_WRITE
    syscall
writeSpace:
    mov al," "
    mov byte[buffer],al
    mov rsi,buffer
    mov rdi,STDOUT
    mov rdx, 1
    mov rax,SYS_WRITE
    syscall

    ret

答案 4 :(得分:0)

嗨,这个函数正在使用所谓的线性同余 生成器(LCG)算法,参数是那些 GCC使用。

section .bss
next: resd 1 ; 32 bits
section .text
_rand:
    mov eax, [next]       ; pass next to eax for multiplication 
    mov ebx, 1103515245   ; the multiplier
    mul ebx               ; eax = eax * ebx
    add eax, 12345        ; the increment 
    mov dword [next], eax ; update next value
    mov ebx, 32768        ; the modulus 
    xor edx, edx          ; avoid Floating point exception
    div ebx               ; edx now holds the random number
    ret                   ; bye
_srand:
    mov eax, 0x0d         ; sys_time
    mov ebx, 0x0          ; NULL
    int 0x80              ; syscall
    mov dword [next], eax ; initialize next
    ret                   ; bye 

_rand的C模拟类似于

static unsigned long int next = 1;
int _rand( void )
{
    next = 1103515245 * next + 12345;
    return next % 32768;
}

并且调用_srand的结果是相同的 好像你会打电话

srand( time( NULL ));
C中的

。生成的数字范围是[0,32767]。