Subversion Repositories Kolibri OS

Rev

Go to most recent revision | Blame | Last modification | View Log | Download | RSS feed

  1. ; C4
  2. ; Copyright (c) 2002 Thomas Mathys
  3. ; killer@vantage.ch
  4. ;
  5. ; This file is part of C4.
  6. ;
  7. ; C4 is free software; you can redistribute it and/or modify
  8. ; it under the terms of the GNU General Public License as published by
  9. ; the Free Software Foundation; either version 2 of the License, or
  10. ; (at your option) any later version.
  11. ;
  12. ; C4 is distributed in the hope that it will be useful,
  13. ; but WITHOUT ANY WARRANTY; without even the implied warranty of
  14. ; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  15. ; GNU General Public License for more details.
  16. ;
  17. ; You should have received a copy of the GNU General Public License
  18. ; along with C4; if not, write to the Free Software
  19. ; Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  20.  
  21. %ifndef _BOARD_INC
  22. %define _BOARD_INC
  23.  
  24.  
  25. ;**********************************************************
  26. ; magic numbers
  27. ;**********************************************************
  28.  
  29. EMPTY           equ     0
  30. PLAYER1         equ     1
  31. PLAYER2         equ     2
  32.  
  33. ; board dimensions (+2 for border)
  34. BWIDTH          equ     9
  35. BHEIGHT         equ     8
  36.  
  37.  
  38.  
  39. ;**********************************************************
  40. ; uninitialized data
  41. ;**********************************************************
  42.  
  43.         section .bss
  44.        
  45. board           resd    BHEIGHT*BWIDTH          ; the board
  46. free            resd    BWIDTH                  ; # of free fields for each column
  47. totalfree       resd    1                       ; total # of free fields
  48. currentplayer   resd    1                       ; player to make next move
  49. lastmove        resd    1                       ; last move done on the board
  50.                                                 ; (0 if no last move available)
  51.  
  52.  
  53.  
  54. ;**********************************************************
  55. ; code
  56. ;**********************************************************
  57.        
  58.         section .text
  59.        
  60.  
  61. ;**********************************************************
  62. ; boardReset
  63. ; reset board for new game
  64. ;
  65. ; input         :       nothing
  66. ; output        :       nothing
  67. ; destroys      :       nothing
  68. ;**********************************************************
  69. boardReset:
  70.         pushfd
  71.         pushad
  72.        
  73.         ; clear all fields
  74.         mov edi,board
  75.         mov ecx,BHEIGHT * BWIDTH
  76.         mov eax,EMPTY
  77.         rep stosd
  78.                
  79.         ; init free array
  80.         mov edi,free
  81.         mov ecx,BWIDTH
  82.         mov eax,BHEIGHT - 2
  83.         rep stosd
  84.        
  85.         mov dword [totalfree],(BWIDTH-2)*(BHEIGHT-2)
  86.         mov dword [currentplayer],PLAYER1
  87.         mov dword [lastmove],0
  88.        
  89.         popad
  90.         popfd
  91.         ret
  92.  
  93.  
  94.  
  95. ;**********************************************************
  96. ; BOARDISVALIDMOVE
  97. ; checks wether a move is valid
  98. ;
  99. ; input         :       32 bit register containing a move
  100. ;                       number (1..7)
  101. ; output        :       zero flag set -> move is invalid
  102. ;                       zero flag clear -> move is valid
  103. ; destroys      :       nothing
  104. ;**********************************************************
  105. %macro BOARDISVALIDMOVE 1
  106.         cmp dword [free+%1*4],0
  107. %endmacro
  108.  
  109.  
  110.  
  111. ;**********************************************************
  112. ; boardMakeMove
  113. ; make a move
  114. ;
  115. ; input         :       eax = move number (1..7)
  116. ;                       ebx = PLAYER1/PLAYER2
  117. ; output        :       nothing
  118. ; destroys      :       edi, flags
  119. ;**********************************************************
  120.  
  121. boardMakeMove:
  122.         mov edi,[free+eax*4]            ; place stone
  123.         imul edi,BWIDTH
  124.         add edi,eax
  125.         mov [board+edi*4],ebx
  126.        
  127.         dec dword [free+eax*4]          ; one stone more in this column
  128.         dec dword [totalfree]           ; one stone more on the board
  129.         mov [lastmove],eax              ; store move for undo
  130.         ret
  131.  
  132.  
  133.  
  134. ;**********************************************************
  135. ; boardUndoMove
  136. ; undo a move
  137. ;
  138. ; input         :       eax = move number to undo (1..7)
  139. ; output        :       move is undone
  140. ; destroys      :       edi, flags
  141. ;**********************************************************
  142. boardUndoMove:
  143.         inc dword [free+eax*4]          ; one stone less in this column
  144.         inc dword [totalfree]           ; one stone less on the board
  145.         mov dword [lastmove],0          ; no last move available
  146.        
  147.         mov edi,[free+eax*4]            ; remove stone from board
  148.         imul edi,BWIDTH
  149.         add edi,eax
  150.         mov dword [board+edi*4],EMPTY
  151.         ret
  152.  
  153.  
  154.  
  155. ;**********************************************************
  156. ; BOARDSWITCHPLAYERS
  157. ; switch current player
  158. ;
  159. ; input         :       nothing
  160. ; output        :       current player is switched
  161. ; destroys      :       flags
  162. ;**********************************************************
  163. %macro BOARDSWITCHPLAYERS 0
  164.         xor dword [currentplayer],(PLAYER1 ^ PLAYER2)
  165. %endmacro
  166.  
  167.  
  168.  
  169. ;**********************************************************
  170. ; BOARDGETOTHERPLAYER
  171. ; get other player =)
  172. ;
  173. ; input         :       32 bit register or variable
  174. ; output        :       player changed
  175. ; destroys      :       flags
  176. ;**********************************************************
  177. %macro BOARDGETOTHERPLAYER 1
  178.         xor %1,(PLAYER1 ^ PLAYER2)
  179. %endmacro
  180.  
  181.  
  182.  
  183. ;**********************************************************
  184. ; BOARDISFULL
  185. ; check wether board is full
  186. ;
  187. ; input         :       nothing
  188. ; output        :       zero flag set -> board is full
  189. ;                       zero flag clear -> board isn't full
  190. ;**********************************************************
  191. %macro BOARDISFULL 0
  192.         cmp dword [totalfree],0
  193. %endmacro
  194.  
  195.  
  196.  
  197. ;**********************************************************
  198. ; boardIsWin
  199. ; check wether the current board state is a win for the
  200. ; given player
  201. ;
  202. ; input         :       eax = player
  203. ; output        :       eax = nonzero -> win for player
  204. ; destroys      :       everything
  205. ;**********************************************************
  206.  
  207. boardIsWin:
  208.  
  209.         ; check wether last move is available
  210.         cmp dword [lastmove],0
  211.         jne .lastmoveok
  212.         xor eax,eax
  213.         ret
  214. .lastmoveok:
  215.  
  216.         ; calculate the address of the most recently placed stone (edi)
  217.         mov edi,[lastmove]
  218.         mov esi,[free + edi*4]
  219.         inc esi
  220.         imul esi,BWIDTH
  221.         add edi,esi
  222.         shl edi,2
  223.         add edi,board
  224.        
  225.         ; check vertically
  226.         xor ecx,ecx                     ; reset counter
  227.         mov esi,edi                     ; start at last stone
  228. .vertical:
  229.         cmp [esi],eax                   ; loop as long the stone [esi] belongs to player
  230.         jne .verticalend
  231.         add esi,BWIDTH*4                ; move to next stone
  232.         inc ecx                         ; one stone more in row
  233.         jmp short .vertical
  234. .verticalend:
  235.         cmp ecx,4                       ; 4 or more stones ?
  236.         jl .nope1                       ; nope -> continue
  237.         mov eax,1                       ; yeah -> tell caller =)
  238.         ret
  239. .nope1:
  240.  
  241.         ; check horizontally
  242.         xor ecx,ecx
  243.         mov esi,edi
  244. .horizontal1:                           ; left
  245.         cmp [esi],eax
  246.         jne .horizontalend1
  247.         sub esi,4
  248.         inc ecx
  249.         jmp short .horizontal1
  250. .horizontalend1:
  251.         lea esi,[edi+4]                 ; right
  252. .horizontal2:
  253.         cmp [esi],eax
  254.         jne .horizontalend2
  255.         add esi,4
  256.         inc ecx
  257.         jmp short .horizontal2
  258. .horizontalend2:
  259.         cmp ecx,4
  260.         jl .nope2
  261.         mov eax,1
  262.         ret
  263. .nope2:
  264.  
  265.         ; diagonally forward
  266.         xor ecx,ecx
  267.         mov esi,edi
  268. .forward1:
  269.         cmp [esi],eax
  270.         jne .forwardend1
  271.         sub esi,(1+BWIDTH)*4
  272.         inc ecx
  273.         jmp short .forward1
  274. .forwardend1:
  275.         lea esi,[edi+(1+BWIDTH)*4]
  276. .forward2:
  277.         cmp [esi],eax
  278.         jne .forwardend2
  279.         add esi,(1+BWIDTH)*4
  280.         inc ecx
  281.         jmp short .forward2
  282. .forwardend2:  
  283.         cmp ecx,4
  284.         jl .nope3
  285.         mov eax,1
  286.         ret
  287. .nope3:
  288.  
  289.         ; diagonally backward
  290.         xor ecx,ecx
  291.         mov esi,edi
  292. .backward1:
  293.         cmp [esi],eax
  294.         jne .backwardend1
  295.         add esi,(1-BWIDTH)*4
  296.         inc ecx
  297.         jmp short .backward1
  298. .backwardend1:
  299.         lea esi,[edi+(BWIDTH-1)*4]
  300. .backward2:
  301.         cmp [esi],eax
  302.         jne .backwardend2
  303.         add esi,(BWIDTH-1)*4
  304.         inc ecx
  305.         jmp short .backward2
  306. .backwardend2:
  307.         cmp ecx,4
  308.         jl .nope4
  309.         mov eax,1
  310.         ret
  311. .nope4:
  312.  
  313.         ; no win for this player
  314.         xor eax,eax
  315.         ret
  316.  
  317.  
  318. %endif