Skip to content

Instantly share code, notes, and snippets.

@kspalaiologos
Created March 8, 2018 15:57
Show Gist options
  • Save kspalaiologos/9389712d1f0a1d9dfd045ee0995017f8 to your computer and use it in GitHub Desktop.
Save kspalaiologos/9389712d1f0a1d9dfd045ee0995017f8 to your computer and use it in GitHub Desktop.
TicTacToe game in Assembly. Intel syntax. License: MIT
square:
.byte 48 ;0
.byte 49 ;1
.byte 50 ;2
.byte 51 ;3
.byte 52 ;4
.byte 53 ;5
.byte 54 ;6
.byte 55 ;7
.byte 56 ;8
.byte 57 ;9
.PytanieOPole:
.string "Gracz %d, wpisz numer pola: "
.FormatLiczby:
.string "%d"
.BladRuchu:
.string "Niewlasciwy ruch."
.Wygrana:
.string " > \007 Gracz %d wygrywa! "
.Remis:
.string " > \007 Remis!"
main:
push rbp
mov rbp, rsp
sub rsp, 16
mov DWORD PTR [rbp-4], 1 ;Gracz 1 rozpoczyna
.PetlaGlownaStart: ;Start petli
call board ;Rysuj plansze
mov eax, DWORD PTR [rbp-4] ;Oblicz gracza
and eax, 1
test eax, eax
je .CzyGracz2
mov eax, 1
jmp .GraczDalej
.CzyGracz2:
mov eax, 2
.GraczDalej:
mov DWORD PTR [rbp-4], eax
mov eax, DWORD PTR [rbp-4]
mov esi, eax
mov edi, OFFSET FLAT:.PytanieOPole
mov eax, 0
call printf ;Wyswietl zapytanie o pole
lea rax, [rbp-16]
mov rsi, rax
mov edi, OFFSET FLAT:.FormatLiczby
mov eax, 0
call scanf ;Wczytaj # pola
cmp DWORD PTR [rbp-4], 1
jne .ZnakX ;Jaki bedzie znak gracza?
mov eax, 88
jmp .PoSprawdzeniuZnaku
.ZnakX:
mov eax, 79
.PoSprawdzeniuZnaku:
mov BYTE PTR [rbp-5], al
mov eax, DWORD PTR [rbp-16]
cmp eax, 1
jne .JakNie1
movzx eax, BYTE PTR square[rip+1]
cmp al, 49
jne .JakNie1
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+1], al
jmp .Dalej
.JakNie1: ;Ten fragment powtarza
mov eax, DWORD PTR [rbp-16] ;sie w nastepnych sekcjach
cmp eax, 2 ;pliku, spokojnie mozesz
jne .JakNie2 ;go pominac, jesli go
movzx eax, BYTE PTR square[rip+2] ;rozumiesz.
cmp al, 50
jne .JakNie2
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+2], al
jmp .Dalej
.JakNie2:
mov eax, DWORD PTR [rbp-16]
cmp eax, 3
jne .JakNie3
movzx eax, BYTE PTR square[rip+3]
cmp al, 51
jne .JakNie3
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+3], al
jmp .Dalej
.JakNie3:
mov eax, DWORD PTR [rbp-16]
cmp eax, 4
jne .JakNie4
movzx eax, BYTE PTR square[rip+4]
cmp al, 52
jne .JakNie4
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+4], al
jmp .Dalej
.JakNie4:
mov eax, DWORD PTR [rbp-16]
cmp eax, 5
jne .JakNie5
movzx eax, BYTE PTR square[rip+5]
cmp al, 53
jne .JakNie5
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+5], al
jmp .Dalej
.JakNie5:
mov eax, DWORD PTR [rbp-16]
cmp eax, 6
jne .JakNie6
movzx eax, BYTE PTR square[rip+6]
cmp al, 54
jne .JakNie6
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+6], al
jmp .Dalej
.JakNie6:
mov eax, DWORD PTR [rbp-16]
cmp eax, 7
jne .JakNie7
movzx eax, BYTE PTR square[rip+7]
cmp al, 55
jne .JakNie7
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+7], al
jmp .Dalej
.JakNie7:
mov eax, DWORD PTR [rbp-16]
cmp eax, 8
jne .JakNie8
movzx eax, BYTE PTR square[rip+8]
cmp al, 56
jne .JakNie8
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+8], al
jmp .Dalej
.JakNie8:
mov eax, DWORD PTR [rbp-16]
cmp eax, 9
jne .JakNie9
movzx eax, BYTE PTR square[rip+9]
cmp al, 57
jne .JakNie9
movzx eax, BYTE PTR [rbp-5]
mov BYTE PTR square[rip+9], al
jmp .Dalej
.JakNie9:
mov edi, OFFSET FLAT:.BladRuchu
mov eax, 0
call printf ;Zly ruch podany
sub DWORD PTR [rbp-4], 1
call getchar ;Zaczekaj
.Dalej:
call checkwin ;Czy wygrano?
mov DWORD PTR [rbp-12], eax
add DWORD PTR [rbp-4], 1
cmp DWORD PTR [rbp-12], -1
jne .Koniec
jmp .PetlaGlownaStart
.Koniec
call board ;Rysuj jeszcze raz
cmp DWORD PTR [rbp-12], 1
jne .KoniecRemis
sub DWORD PTR [rbp-4], 1 ;Odejmij od # gracza 1
mov eax, DWORD PTR [rbp-4]
mov esi, eax
mov edi, OFFSET FLAT:.Wygrana ;Gracz wygral
mov eax, 0
call printf ;Wyswietl tekst
jmp .Zaczekaj
.KoniecRemis:
mov edi, OFFSET FLAT:.Remis ;Remis, nie ma potrzeby
mov eax, 0 ;zadnych obliczen
call printf
.Zaczekaj:
call getchar ;Uruchom getchar dla spowolnienia
mov eax, 0 ;eax = 0
leave ;return eax;
ret
checkwin: ;Czy wygrano
push rbp
mov rbp, rsp
movzx edx, BYTE PTR square[rip+1] ;#1 warunek
movzx eax, BYTE PTR square[rip+2]
cmp dl, al ;Jesli #1 kombinacja ok,
jne .CheckwinJesliNie1
movzx edx, BYTE PTR square[rip+2]
movzx eax, BYTE PTR square[rip+3]
cmp dl, al
jne .CheckwinJesliNie1 ;Ten kod bedzie bardzo repetytywny
mov eax, 1 ;wiec nie bede go komentowal
jmp .Zwracaj1
.CheckwinJesliNie1:
movzx edx, BYTE PTR square[rip+4]
movzx eax, BYTE PTR square[rip+5]
cmp dl, al
jne .CheckwinJesliNie2
movzx edx, BYTE PTR square[rip+5]
movzx eax, BYTE PTR square[rip+6]
cmp dl, al
jne .CheckwinJesliNie2
mov eax, 1
jmp .Zwracaj1
.CheckwinJesliNie2:
movzx edx, BYTE PTR square[rip+7]
movzx eax, BYTE PTR square[rip+8]
cmp dl, al
jne .CheckwinJesliNie3
movzx edx, BYTE PTR square[rip+8]
movzx eax, BYTE PTR square[rip+9]
cmp dl, al
jne .CheckwinJesliNie3
mov eax, 1
jmp .Zwracaj1
.CheckwinJesliNie3:
movzx edx, BYTE PTR square[rip+1]
movzx eax, BYTE PTR square[rip+4]
cmp dl, al
jne .CheckwinJesliNie4
movzx edx, BYTE PTR square[rip+4]
movzx eax, BYTE PTR square[rip+7]
cmp dl, al
jne .CheckwinJesliNie4
mov eax, 1
jmp .Zwracaj1
.CheckwinJesliNie4:
movzx edx, BYTE PTR square[rip+2]
movzx eax, BYTE PTR square[rip+5]
cmp dl, al
jne .CheckwinJesliNie5
movzx edx, BYTE PTR square[rip+5]
movzx eax, BYTE PTR square[rip+8]
cmp dl, al
jne .CheckwinJesliNie5
mov eax, 1
jmp .Zwracaj1
.CheckwinJesliNie5:
movzx edx, BYTE PTR square[rip+3]
movzx eax, BYTE PTR square[rip+6]
cmp dl, al
jne .CheckwinJesliNie6
movzx edx, BYTE PTR square[rip+6]
movzx eax, BYTE PTR square[rip+9]
cmp dl, al
jne .CheckwinJesliNie6
mov eax, 1
jmp .Zwracaj1
.CheckwinJesliNie6:
movzx edx, BYTE PTR square[rip+1]
movzx eax, BYTE PTR square[rip+5]
cmp dl, al
jne .CheckwinJesliNie7
movzx edx, BYTE PTR square[rip+5]
movzx eax, BYTE PTR square[rip+9]
cmp dl, al
jne .CheckwinJesliNie7
mov eax, 1
jmp .Zwracaj1
.CheckwinJesliNie7:
movzx edx, BYTE PTR square[rip+3]
movzx eax, BYTE PTR square[rip+5]
cmp dl, al
jne .CheckwinJesliNie8
movzx edx, BYTE PTR square[rip+5]
movzx eax, BYTE PTR square[rip+7]
cmp dl, al
jne .CheckwinJesliNie8
mov eax, 1
jmp .Zwracaj1
.CheckwinJesliNie8: ;Ciekawszy fragment
movzx eax, BYTE PTR square[rip+1] ;sprawdzanie czy zawartosc
cmp al, 49 ;komorki to liczba
je .ZwracajMinus1 ;(tak jak jest na starcie)
movzx eax, BYTE PTR square[rip+2]
cmp al, 50
je .ZwracajMinus1
movzx eax, BYTE PTR square[rip+3]
cmp al, 51
je .ZwracajMinus1
movzx eax, BYTE PTR square[rip+4]
cmp al, 52
je .ZwracajMinus1
movzx eax, BYTE PTR square[rip+5]
cmp al, 53
je .ZwracajMinus1
movzx eax, BYTE PTR square[rip+6]
cmp al, 54
je .ZwracajMinus1
movzx eax, BYTE PTR square[rip+7]
cmp al, 55
je .ZwracajMinus1
movzx eax, BYTE PTR square[rip+8]
cmp al, 56
je .ZwracajMinus1
movzx eax, BYTE PTR square[rip+9]
cmp al, 57
je .ZwracajMinus1
mov eax, 0
jmp .Zwracaj1
.ZwracajMinus1:
mov eax, -1
.Zwracaj1:
pop rbp
ret
.NazwaGry:
.string "\n\tKolko i krzyzyk (by Krzysztof Szewczyk, Copyright (C) 2018)"
.KtoGra:
.string "Gracz 1 (X) - Gracz 2 (O)\n"
.DoRysowaniaPlanszy1:
.string " | | "
.DoRysowaniaPlanszy2:
.string " %c | %c | %c \n"
.DoRysowaniaPlanszy3:
.string "_____|_____|_____"
.FormatLiczby0:
.string " | | \n"
board: ;Rysuj plansze
push rbp
mov rbp, rsp
mov edi, OFFSET FLAT:.NazwaGry
call puts
mov edi, OFFSET FLAT:.KtoGra
call puts
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy1
call puts ;Wyswietlaj wszystkie stringi po kolei
movzx eax, BYTE PTR square[rip+3]
movsx ecx, al ;Kod stanie sie nieco repetytywny (obsluga bardzo prostej grafiki)
movzx eax, BYTE PTR square[rip+2]
movsx edx, al
movzx eax, BYTE PTR square[rip+1]
movsx eax, al
mov esi, eax
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy2
mov eax, 0
call printf
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy3
call puts
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy1
call puts
movzx eax, BYTE PTR square[rip+6]
movsx ecx, al
movzx eax, BYTE PTR square[rip+5]
movsx edx, al
movzx eax, BYTE PTR square[rip+4]
movsx eax, al
mov esi, eax
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy2
mov eax, 0
call printf
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy3
call puts
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy1
call puts
movzx eax, BYTE PTR square[rip+9]
movsx ecx, al
movzx eax, BYTE PTR square[rip+8]
movsx edx, al
movzx eax, BYTE PTR square[rip+7]
movsx eax, al
mov esi, eax
mov edi, OFFSET FLAT:.DoRysowaniaPlanszy2
mov eax, 0
call printf
mov edi, OFFSET FLAT:.FormatLiczby0
call puts ;Rysowanie ZAKONCZONO
nop
pop rbp
ret
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment