1 /* 2 * Copyright (c) 1994 3 * The Regents of the University of California. All rights reserved. 4 * 5 * This code is derived from software contributed to Berkeley by 6 * Ralph Campbell. 7 * 8 * %sccs.include.redist.c% 9 */ 10 11 #ifndef lint 12 static char sccsid[] = "@(#)bdinit.c 8.2 (Berkeley) 05/03/95"; 13 #endif /* not lint */ 14 15 #include <string.h> 16 #include "gomoku.h" 17 18 bdinit(bp) 19 struct spotstr *bp; 20 { 21 register int i, j, r; 22 register struct spotstr *sp; 23 register struct combostr *cbp; 24 25 movenum = 1; 26 27 /* mark the borders as such */ 28 sp = bp; 29 for (i = BSZ2; --i >= 0; sp++) { 30 sp->s_occ = BORDER; /* top border */ 31 sp->s_flg = BFLAGALL; 32 } 33 34 /* fill entire board with EMPTY spots */ 35 memset(frames, 0, sizeof(frames)); 36 cbp = frames; 37 for (j = 0; ++j < BSZ1; sp++) { /* for each row */ 38 for (i = 0; ++i < BSZ1; sp++) { /* for each column */ 39 sp->s_occ = EMPTY; 40 sp->s_flg = 0; 41 sp->s_wval = 0; 42 if (j < 5) { 43 /* directions 1, 2, 3 are blocked */ 44 sp->s_flg |= (BFLAG << 1) | (BFLAG << 2) | 45 (BFLAG << 3); 46 sp->s_fval[BLACK][1].s = MAXCOMBO; 47 sp->s_fval[BLACK][2].s = MAXCOMBO; 48 sp->s_fval[BLACK][3].s = MAXCOMBO; 49 sp->s_fval[WHITE][1].s = MAXCOMBO; 50 sp->s_fval[WHITE][2].s = MAXCOMBO; 51 sp->s_fval[WHITE][3].s = MAXCOMBO; 52 } else if (j == 5) { 53 /* five spaces, blocked on one side */ 54 sp->s_fval[BLACK][1].s = 0x500; 55 sp->s_fval[BLACK][2].s = 0x500; 56 sp->s_fval[BLACK][3].s = 0x500; 57 sp->s_fval[WHITE][1].s = 0x500; 58 sp->s_fval[WHITE][2].s = 0x500; 59 sp->s_fval[WHITE][3].s = 0x500; 60 } else { 61 /* six spaces, not blocked */ 62 sp->s_fval[BLACK][1].s = 0x401; 63 sp->s_fval[BLACK][2].s = 0x401; 64 sp->s_fval[BLACK][3].s = 0x401; 65 sp->s_fval[WHITE][1].s = 0x401; 66 sp->s_fval[WHITE][2].s = 0x401; 67 sp->s_fval[WHITE][3].s = 0x401; 68 } 69 if (i > (BSZ - 4)) { 70 /* directions 0, 1 are blocked */ 71 sp->s_flg |= BFLAG | (BFLAG << 1); 72 sp->s_fval[BLACK][0].s = MAXCOMBO; 73 sp->s_fval[BLACK][1].s = MAXCOMBO; 74 sp->s_fval[WHITE][0].s = MAXCOMBO; 75 sp->s_fval[WHITE][1].s = MAXCOMBO; 76 } else if (i == (BSZ - 4)) { 77 sp->s_fval[BLACK][0].s = 0x500; 78 sp->s_fval[WHITE][0].s = 0x500; 79 /* if direction 1 is not blocked */ 80 if (!(sp->s_flg & (BFLAG << 1))) { 81 sp->s_fval[BLACK][1].s = 0x500; 82 sp->s_fval[WHITE][1].s = 0x500; 83 } 84 } else { 85 sp->s_fval[BLACK][0].s = 0x401; 86 sp->s_fval[WHITE][0].s = 0x401; 87 if (i < 5) { 88 /* direction 3 is blocked */ 89 sp->s_flg |= (BFLAG << 3); 90 sp->s_fval[BLACK][3].s = MAXCOMBO; 91 sp->s_fval[WHITE][3].s = MAXCOMBO; 92 } else if (i == 5 && 93 !(sp->s_flg & (BFLAG << 3))) { 94 sp->s_fval[BLACK][3].s = 0x500; 95 sp->s_fval[WHITE][3].s = 0x500; 96 } 97 } 98 /* 99 * Allocate a frame structure for non blocked frames. 100 */ 101 for (r = 4; --r >= 0; ) { 102 if (sp->s_flg & (BFLAG << r)) 103 continue; 104 cbp->c_combo.s = sp->s_fval[BLACK][r].s; 105 cbp->c_vertex = sp - board; 106 cbp->c_nframes = 1; 107 cbp->c_dir = r; 108 sp->s_frame[r] = cbp; 109 cbp++; 110 } 111 } 112 sp->s_occ = BORDER; /* left & right border */ 113 sp->s_flg = BFLAGALL; 114 } 115 116 /* mark the borders as such */ 117 for (i = BSZ1; --i >= 0; sp++) { 118 sp->s_occ = BORDER; /* bottom border */ 119 sp->s_flg = BFLAGALL; 120 } 121 122 sortframes[BLACK] = (struct combostr *)0; 123 sortframes[WHITE] = (struct combostr *)0; 124 init_overlap(); 125 } 126 127 /* 128 * Initialize the overlap array. 129 * Each entry in the array is a bit mask with eight bits corresponding 130 * to whether frame B overlaps frame A (as indexed by overlap[A * FAREA + B]). 131 * The eight bits coorespond to whether A and B are open ended (length 6) or 132 * closed (length 5). 133 * 0 A closed and B closed 134 * 1 A closed and B open 135 * 2 A open and B closed 136 * 3 A open and B open 137 * 4 A closed and B closed and overlaps in more than one spot 138 * 5 A closed and B open and overlaps in more than one spot 139 * 6 A open and B closed and overlaps in more than one spot 140 * 7 A open and B open and overlaps in more than one spot 141 * As pieces are played, it can make frames not overlap if there are no 142 * common open spaces shared between the two frames. 143 */ 144 init_overlap() 145 { 146 register struct spotstr *sp1, *sp2; 147 register struct combostr *cbp; 148 register int i, f, r, n, d1, d2; 149 int mask, bmask, vertex, s; 150 u_char *str; 151 short *ip; 152 153 memset(overlap, 0, sizeof(overlap)); 154 memset(intersect, 0, sizeof(intersect)); 155 str = &overlap[FAREA * FAREA]; 156 ip = &intersect[FAREA * FAREA]; 157 for (cbp = frames + FAREA; --cbp >= frames; ) { /* each frame */ 158 str -= FAREA; 159 ip -= FAREA; 160 sp1 = &board[vertex = cbp->c_vertex]; 161 d1 = dd[r = cbp->c_dir]; 162 /* 163 * s = 5 if closed, 6 if open. 164 * At this point black & white are the same. 165 */ 166 s = 5 + sp1->s_fval[BLACK][r].c.b; 167 /* for each spot in frame A */ 168 for (i = 0; i < s; i++, sp1 += d1, vertex += d1) { 169 /* the sixth spot in frame A only overlaps if it is open */ 170 mask = (i == 5) ? 0xC : 0xF; 171 /* for each direction */ 172 for (r = 4; --r >= 0; ) { 173 bmask = BFLAG << r; 174 sp2 = sp1; 175 d2 = dd[r]; 176 /* for each frame that intersects at spot sp1 */ 177 for (f = 0; f < 6; f++, sp2 -= d2) { 178 if (sp2->s_occ == BORDER) 179 break; 180 if (sp2->s_flg & bmask) 181 continue; 182 n = sp2->s_frame[r] - frames; 183 ip[n] = vertex; 184 str[n] |= (f == 5) ? mask & 0xA : mask; 185 if (r == cbp->c_dir) { 186 /* compute the multiple spot overlap values */ 187 switch (i) { 188 case 0: /* sp1 is the first spot in A */ 189 if (f == 4) 190 str[n] |= 0xA0; 191 else if (f != 5) 192 str[n] |= 0xF0; 193 break; 194 case 1: /* sp1 is the second spot in A */ 195 if (f == 5) 196 str[n] |= 0xA0; 197 else 198 str[n] |= 0xF0; 199 break; 200 case 4: /* sp1 is the penultimate spot in A */ 201 if (f == 0) 202 str[n] |= 0xC0; 203 else 204 str[n] |= 0xF0; 205 break; 206 case 5: /* sp1 is the last spot in A */ 207 if (f == 1) 208 str[n] |= 0xC0; 209 else if (f != 0) 210 str[n] |= 0xF0; 211 break; 212 default: 213 str[n] |= 0xF0; 214 } 215 } 216 } 217 } 218 } 219 } 220 } 221