Skip to content

Commit

Permalink
Added random number generator via a modified LFSR
Browse files Browse the repository at this point in the history
  • Loading branch information
jeremyherbert committed Jan 10, 2011
1 parent 45c0744 commit fa4d831
Show file tree
Hide file tree
Showing 3 changed files with 95 additions and 38 deletions.
72 changes: 37 additions & 35 deletions map
Original file line number Diff line number Diff line change
Expand Up @@ -4,53 +4,55 @@ Bank #0 (HOME):
SECTION: $0050-$0052 ($0003 bytes)
SECTION: $0058-$0058 ($0001 bytes)
SECTION: $0060-$0060 ($0001 bytes)
SECTION: $0100-$0D36 ($0C37 bytes)
$0A89 = timer_interrupt
SECTION: $0100-$0D66 ($0C67 bytes)
$0AB9 = timer_interrupt
$0952 = init
$0D1E = setup_dma
$0CFD = stoplcd
$0D4E = setup_dma
$0D2D = stoplcd
$0150 = TileData
$0C61 = clear_bg
$0C73 = splash_text
$0CF3 = splash_text_end
$0C0E = draw_snake
$0AA4 = read_joypad
$0B23 = move_snake
$0A16 = main
$0B10 = draw_gameover
$0A80 = subtract_16bit
$0AA2 = timer_interrupt_end
$0ACB = read_joypad_up_return
$0ABD = read_joypad_right_return
$0AD2 = read_joypad_down_return
$0AC4 = read_joypad_left_return
$0CF3 = gameover_text
$0CFD = gameover_text_end
$0C07 = move_snake_die
$0B73 = move_snake_write
$0B86 = move_snake_continue
$0A3B = tail_collision_scan
$0C0C = move_snake_end
$0BD6 = move_snake_cut_tail_continue
$0C51 = convert_xy_to_screen_addr
$0C32 = draw_snake_continue
$0D0E = multiply_to_hl
$0D2B = dma_copy
$0D37 = dma_copy_end
$0C91 = clear_bg
$0CA3 = splash_text
$0D23 = splash_text_end
$0C3E = draw_snake
$0A47 = lfsr_generate
$0AD4 = read_joypad
$0B53 = move_snake
$0A1F = main
$0B40 = draw_gameover
$0AB0 = subtract_16bit
$0AD2 = timer_interrupt_end
$0AFB = read_joypad_up_return
$0AED = read_joypad_right_return
$0B02 = read_joypad_down_return
$0AF4 = read_joypad_left_return
$0D23 = gameover_text
$0D2D = gameover_text_end
$0C37 = move_snake_die
$0BA3 = move_snake_write
$0BB6 = move_snake_continue
$0A6B = tail_collision_scan
$0C3C = move_snake_end
$0C06 = move_snake_cut_tail_continue
$0C81 = convert_xy_to_screen_addr
$0C62 = draw_snake_continue
$0D3E = multiply_to_hl
$0D5B = dma_copy
$0D67 = dma_copy_end
SECTION: $0061-$00B6 ($0056 bytes)
$007B = mem_CopyMono
$0061 = mem_Set
$00A1 = mem_CopyVRAM
$008B = mem_SetVRAM
$006D = mem_Copy
SLACK: $336A bytes
SLACK: $333A bytes

BSS:
SECTION: $C000-$C179 ($017A bytes)
SECTION: $C000-$C17A ($017B bytes)
$C000 = variables_start
$C17A = variables_end
$C17B = variables_end
$C0A3 = SnakePieces
$C16B = SnakePiecesEnd
$C175 = LFSRSeed
$C0A0 = GameState
$C16D = SnakeTail
$C16B = SnakeHead
Expand All @@ -60,7 +62,7 @@ BSS:
$C174 = TimerTicks
$C16F = SnakeDirection
$C170 = SnakeNextDirection
SLACK: $1E86 bytes
SLACK: $1E85 bytes

VRAM:
EMPTY
Expand Down
61 changes: 58 additions & 3 deletions snake.asm
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ NumberOfFoods: ds 1 ; number of food objects that exist (as sprites)

TimerTicks: ds 1 ; count the number of ticks in the timer (to slow down the movement speed)

LFSRSeed: ds 1 ; seed value for our lfsr

DEBUG_BLANK_DONT_TOUCH: ds 5 ; this gets allocated to zeroes, makes it easier to see our ram block in the debugger
variables_end:

Expand Down Expand Up @@ -146,6 +148,11 @@ init_variables:

; this code displays the splash screen
splash:
; turn on the timer, we need to use its value for our LFSR seed
ld a, TACF_START | TACF_262KHZ ; make it super fast to stop people gaming it
ld [rTAC], a

; we are going to copy across the background tiles from the splash_text label
; using: mem_copyVRAM (hl->pSource, de->pDest, bc->byte count)
ld hl, splash_text
Expand All @@ -169,6 +176,10 @@ splash_wait_for_press:
cp 1
jr z, splash_wait_for_press ; if the a key has not been pressed, the instruction above will set the zero flag and we will jump back

; save our LFSR seed
ld a, [rTIMA] ; counter value into a
ld [LFSRSeed], a ; save it!

;------------------------------------------------------------------------

; ok, time to play the game!
Expand Down Expand Up @@ -218,15 +229,16 @@ init_snake:
ld a, 8 ; piece 2, y
ld [hl+], a

; draw our initial snake
call draw_snake

; now we start the timer interrupts (ll. 828-852)
; start the timer, we need this for our LIFR
ld a, TACF_START | TACF_4KHZ ; turn on, set to 4khz (timer will interrupt every [255 * 1/4000] = 63.75ms)
ld [rTAC], a

ld a, IEF_VBLANK | IEF_TIMER | IEF_HILO ; enable vblank, timer, joypad interrupts
ld [rIE], a ; save the register
; draw our initial snake
call draw_snake

;;;;;;;;;;;;;;;;;; DEBUG (make the snake grow by default)
ld a, 10
Expand All @@ -239,6 +251,8 @@ main:
; nop ; a bug in the cpu means that the instruction after a halt might get skipped
ei

call lfsr_generate ; so we get nice random numbers

ld a, [GameState]
cp 2 ; does GameState == 2? (the gameover state)
jr z, gameover ; show a nice message
Expand All @@ -265,6 +279,47 @@ gameover:
; jr main

;------------------------------------------------------------------------
;---------------
; lfsr_generate
; generate a random number and put it in LFSRSeed
; see http://en.wikipedia.org/wiki/Linear_feedback_shift_register for info on how this works
; uses taps at 8, 6, 5, 4
;---------------
lfsr_generate:
ld a, [LFSRSeed] ; load up the seed
ld e, a ; e will store our seed value

lfsr_generate_loop:
ld d, a

rr d ; roll four times
rr d
rr d
rr d
xor d ; xor it

rr d ; five rolls in total
xor d

rr d ; up to 6 rolls
xor d ; xor it in

rr d
rr d ; 8 rolls, this is our fourth and last tap
xor d
; not really sure if secure crypto allows me to do this, but frankly if you would like to game my system then go for it
ld b, a
ld a, [rDIV] ; source of some more random
xor b ; add it in

cp e
jr z, lfsr_generate_loop ; make sure it is different

; save it
ld [LFSRSeed], a

ret

;---------------
; tail_collision_scan
Expand Down
Binary file modified snake.gb
Binary file not shown.

0 comments on commit fa4d831

Please sign in to comment.