-
-
Save root42/1da0be15cfd7c0edb302e52d107ba3ff to your computer and use it in GitHub Desktop.
Game of Life x86
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
.8086 | |
.MODEL tiny | |
.CODE | |
org 100h | |
start: | |
mov ax,0013h | |
int 10h | |
mov al,MEMORY_MODE | |
mov ah,06h | |
mov dx,SC_INDEX | |
out dx,ax | |
mov al,UNDERLINE_LOCATION | |
mov ah,00h | |
mov dx,CRTC_INDEX | |
out dx,ax | |
mov al,MODE_CONTROL | |
mov ah,0e3h | |
out dx,ax | |
mov ax,01h ; c | |
push ax | |
mov ax,64h ; y | |
push ax | |
mov ax,100h ; x | |
push ax | |
mov ax,0h ; page | |
push ax | |
call set_pixel | |
mov ax,01h ; c | |
push ax | |
mov ax,64h ; y | |
push ax | |
mov ax,101h ; x | |
push ax | |
mov ax,0h ; page | |
push ax | |
call set_pixel | |
mov ax,01h ; c | |
push ax | |
mov ax,64h ; y | |
push ax | |
mov ax,102h ; x | |
push ax | |
mov ax,0h ; page | |
push ax | |
call set_pixel | |
mainloop: | |
; set vga page | |
mov dx,CRTC_INDEX | |
mov ax,vgapage1 | |
mov al,START_REG_HIGH | |
out dx,ax | |
mov dx,CRTC_INDEX | |
mov ax,vgapage1 | |
mov cl,8 | |
shl ax,cl | |
mov al,START_REG_LOW | |
out dx,ax | |
; do vsync | |
loop1: | |
mov dx,INPUT_STATUS | |
in al,dx | |
and al,08h | |
jnz loop1 | |
loop2: | |
mov dx,INPUT_STATUS | |
in al,dx | |
and al,08h | |
jz loop2 | |
; update game state | |
call update_game | |
mov ax,vgapage1 | |
mov bx,vgapage2 | |
mov vgapage2,ax | |
mov vgapage1,bx | |
mov ah,01h | |
dec frames | |
jz exit | |
int 16h | |
jz mainloop | |
exit: | |
mov ax,0003h | |
int 10h | |
mov ax,4c00h | |
int 21h | |
update_game proc | |
push bp | |
mov bp,sp | |
mov ax,max_y | |
mov line,ax | |
loop_lines: | |
mov ax,max_x | |
mov column,ax | |
loop_columns: | |
call acc_neighbors | |
dec column | |
jnz loop_columns | |
dec line | |
jnz loop_lines | |
pop bp | |
ret | |
endp update_game | |
acc_neighbors proc | |
push bp | |
mov bp,sp | |
; read current pixel (alive or dead) | |
mov ax,line | |
mov pixel_y,ax | |
mov ax,column | |
mov pixel_x,ax | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
mov current_pixel,al | |
; accumulate all 8 neighbors | |
mov neighbors,0 | |
; -1,-1 | |
mov ax,line | |
mov pixel_y,ax | |
mov ax,column | |
mov pixel_x,ax | |
dec pixel_y | |
dec pixel_x | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
; 0,-1 | |
inc pixel_x | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
; 1,-1 | |
inc pixel_x | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
; 1,0 | |
inc pixel_y | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
; -1,0 | |
dec pixel_x | |
dec pixel_x | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
; -1,1 | |
inc pixel_y | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
; 0,1 | |
inc pixel_x | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
; 1,1 | |
inc pixel_x | |
push pixel_y | |
push pixel_x | |
push vgapage1 | |
call get_pixel | |
add neighbors,al | |
pop bp | |
ret | |
endp acc_neighbors | |
set_pixel proc | |
arg vgapage:word, x:word, y:word, c:byte | |
push bp | |
mov bp,sp | |
push ds | |
;select VGA plane | |
mov cx,x | |
and cl,3 | |
mov ah,1 | |
shl ah,cl | |
mov al,MAP_MASK | |
mov dx,SC_INDEX | |
out dx,ax | |
;compute vga offset | |
mov ax,y | |
mov bx,ax | |
mov cl,8 | |
shl ax,cl | |
mov cl,6 | |
shl bx,cl | |
add ax,bx | |
mov cl,2 | |
shr ax,cl | |
mov bx,x | |
shr bx,cl | |
add ax,bx | |
add ax,vgapage | |
mov dx,VGA_MEM | |
mov ds,dx | |
mov di,ax | |
mov al,c | |
mov ds:[di],al | |
pop ds | |
pop bp | |
ret | |
set_pixel endp | |
get_pixel proc | |
arg vgapage:word, x:word, y:word | |
push bp | |
mov bp,sp | |
push ds | |
;select VGA plane | |
mov cx,x | |
and cl,3 | |
mov ah,1 | |
shl ah,cl | |
mov al,MAP_MASK | |
mov dx,SC_INDEX | |
out dx,ax | |
;compute vga offset | |
mov ax,y | |
mov bx,ax | |
mov cl,8 | |
shl ax,cl | |
mov cl,6 | |
shl bx,cl | |
add ax,bx | |
mov cl,2 | |
shr ax,cl | |
mov bx,x | |
shr bx,cl | |
add ax,bx | |
add ax,vgapage | |
mov dx,VGA_MEM | |
mov ds,dx | |
mov di,ax | |
mov al,ds:[di] | |
pop ds | |
pop bp | |
ret | |
get_pixel endp | |
neighbors db 0 | |
current_pixel db 0 | |
column dw 0 | |
line dw 0 | |
pixel_x dw 0 | |
pixel_y dw 0 | |
frames dw 1000 | |
vgapage1 dw 0 | |
vgapage2 dw 16000 | |
max_x dw 319 | |
max_y dw 199 | |
SC_INDEX equ 03c4h | |
SC_DATA equ 03c5h | |
CRTC_INDEX equ 03d4h | |
CRTC_DATA equ 03d5h | |
MEMORY_MODE equ 04h | |
UNDERLINE_LOCATION equ 014h | |
CRTC_INDEX equ 03d4h | |
INPUT_STATUS equ 03dah | |
MODE_CONTROL equ 017h | |
MAP_MASK equ 02h | |
VGA_MEM equ 0A000h | |
START_REG_HIGH equ 0ch | |
START_REG_LOW equ 0dh | |
end start |
Yes, indeed. We established that in the YouTube comments as well. :)
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
I think you need to pop the function parameters than you are pushing. Apparently ret can take a number of bytes to pop off the stack