source: buchla-68k/lib700/rand24.s@ 109c83b

Last change on this file since 109c83b was 109c83b, checked in by Thomas Lopatic <thomas@…>, 7 years ago

Compiled full ROM in Hatari.

  • Property mode set to 100644
File size: 3.3 KB
Line 
1* ------------------------------------------------------------------------------
2* rand24.s -- generate a 24 bit random number
3* Version 3 -- 1988-04-29 -- D.N. Lynx Crowe
4* ------------------------------------------------------------------------------
5* Synopsis:
6* long
7* rand24()
8*
9* Based on:
10* Knuth, Donald E.
11* The Art of Computer Programming,
12* Volume 2: Semi-Numerical Algorithms
13*
14* Computes:
15* S = [S * C] + K
16*
17* Where:
18* K = 1
19* C = 3141592621
20* S = the seed (if zero, it gets set from the 200 Hz clock)
21*
22* Returns:
23* S >> 8 (a 24 bit pseudo-random number)
24*
25* Note: this function has an LSB with an exactly 50% distribution, so using
26* individual bits is probably not a good idea. Using more bits makes things
27* appear more random.
28* ------------------------------------------------------------------------------
29 .text
30*
31 .xdef _rand24
32*
33 .xdef _rseed
34*
35* equates for things in the BIOS
36*
37RCLOCK .equ $49E * LONG - 200 Hz clock
38*
39* equates for stack offsets
40*
41ARG1 .equ 8 * LONG / WORD - arg1 / MS bits
42ARG1L .equ 10 * WORD - arg1 LS bits
43ARG2 .equ 12 * LONG / WORD - arg2 / MS bits
44ARG2L .equ 14 * WORD - arg2 LS bits
45*
46PART .equ -4 * LONG - partial product
47*
48PI .equ $BB40E62D * LONG - PI as a hex value
49*
50 .page
51*
52* mult32 -- 32 bit signed multiply
53* ------ ----------------------
54mult32: link a6,#-4 * link stack frames
55 clr.w d2 * clear sign flags
56 tst.l ARG1(a6) * check sign of 1st argument
57 bge mult32a * ...
58*
59 neg.l ARG1(a6) * make 1st argument positive
60 addq.w #1,d2 * log its sign as negative
61*
62mult32a: tst.l ARG2(a6) * check sign of 2nd argument
63 bge mult32b * ...
64*
65 neg.l ARG2(a6) * make 2nd argument positive
66 addq.w #1,d2 * log its sign as negative
67*
68mult32b: move.w ARG1L(a6),d0 * generate 1st partial product
69 mulu ARG2L(a6),d0 * ...
70 move.l d0,PART(a6) * ...
71 move.w ARG1(a6),d0 * generate 2nd partial product
72 mulu ARG2L(a6),d0 * ...
73 move.w ARG2(a6),d1 * generate 3rd partial product
74 mulu ARG1L(a6),d1 * ...
75 add.w d1,d0 * add partial products
76 add.w PART(a6),d0 * ...
77 move.w d0,PART(a6) * ...
78 move.l PART(a6),d0 * ...
79 btst #0,d2 * adjust sign of result
80 beq mult32c * ...
81*
82 neg.l d0 * ...
83*
84mult32c: unlk a6 * unlink stack frames
85 rts * return
86*
87 .page
88*
89* _rand24 -- Generate a random number
90* ------- ------------------------
91_rand24: link a6,#0 * Link stack frames
92 tst.l _rseed * See if the seed is zero
93 bne rand01 * Jump if not
94*
95 move.l RCLOCK,d0 * Pick up the 200 Hz clock
96 moveq.l #16,d1 * Shift it left
97 asl.l d1,d0 * ...
98 or.l RCLOCK,d0 * OR in current 200 Hz clock
99 move.l d0,_rseed * Use that as the seed
100*
101rand01: move.l #PI,-(a7) * Put PI on the stack
102 move.l _rseed,-(a7) * ... and _rseed, too
103 bsr mult32 * Multiply them
104 addq.l #8,a7 * Cleanup stack
105 addq.l #1,d0 * Add 1 to the result
106 move.l d0,_rseed * Save as new seed
107 asr.l #8,d0 * Make it a 24 bit number
108 and.l #$00FFFFFF,d0 * ...
109 unlk a6 * Unlink stack frames
110 rts * Return to caller
111*
112* ------------------------------------------------------------------------------
113 .bss
114* ------------------------------------------------------------------------------
115*
116_rseed: .ds.l 1 * random number seed
117*
118 .end
Note: See TracBrowser for help on using the repository browser.