Annotation of 43BSDReno/games/chess/move.c, revision 1.1

1.1     ! root        1: /* move generator [email protected] 890318
        !             2:    Modified: 890606 NEWMOVE Levels 1-6 for easier debugging */
        !             3: #include "move.h"
        !             4: #include "gnuchess.h"
        !             5: 
        !             6: short distdata[64][64];
        !             7: short taxidata[64][64];
        !             8: 
        !             9: void Initialize_dist() {
        !            10: register short a,b,d,di;
        !            11: 
        !            12:   /* init taxi and dist data */
        !            13:   for(a=0;a<64;a++)
        !            14:     for(b=0;b<64;b++) {
        !            15:       d = abs(column[a]-column[b]);
        !            16:       di = abs(row[a]-row[b]);
        !            17:       taxidata[a][b] = d + di;
        !            18:       distdata[a][b] = (d > di ? d : di);
        !            19:     };
        !            20: }
        !            21: 
        !            22: #if (NEWMOVE > 1)
        !            23: struct sqdata posdata[3][8][64][64];
        !            24: 
        !            25: static short direc[8][8] = {
        !            26:     0,  0,  0,  0,  0,  0,  0,  0, /* no_piece = 0 */
        !            27:   -10,-11, -9,  0,  0,  0,  0,  0, /* wpawn    = 1 */
        !            28:   -21,-19,-12, -8, 21, 19, 12,  8, /* knight   = 2 */
        !            29:   -11, -9, 11,  9,  0,  0,  0,  0, /* bishop   = 3 */
        !            30:   -10, -1, 10,  1,  0,  0,  0,  0, /* rook     = 4 */
        !            31:   -11, -9,-10, -1, 11,  9, 10,  1, /* queen    = 5 */
        !            32:   -11, -9,-10, -1, 11,  9, 10,  1, /* king     = 6 */
        !            33:     0,  0,  0,  0,  0,  0,  0,  0};/* no_piece = 7 */
        !            34: 
        !            35: static short dc[3] = {-1,1,0};
        !            36: 
        !            37: static short max_steps [8] = {0,2,1,7,7,7,1,0};
        !            38: 
        !            39: static short unmap[120] = {
        !            40:   -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
        !            41:   -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
        !            42:   -1, 0, 1, 2, 3, 4, 5, 6, 7,-1,
        !            43:   -1, 8, 9,10,11,12,13,14,15,-1,
        !            44:   -1,16,17,18,19,20,21,22,23,-1,
        !            45:   -1,24,25,26,27,28,29,30,31,-1,
        !            46:   -1,32,33,34,35,36,37,38,39,-1,
        !            47:   -1,40,41,42,43,44,45,46,47,-1,
        !            48:   -1,48,49,50,51,52,53,54,55,-1,
        !            49:   -1,56,57,58,59,60,61,62,63,-1,
        !            50:   -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
        !            51:   -1,-1,-1,-1,-1,-1,-1,-1,-1,-1};
        !            52: 
        !            53: void Initialize_moves() {
        !            54:   short c,ptyp,po,p0,d,di,s;
        !            55:   struct sqdata *p;
        !            56:   short dest[8][8];
        !            57:   short steps[8];
        !            58:   short sorted[8];
        !            59: 
        !            60:   /* init posdata */
        !            61:   for(c=0;c<3;c++)
        !            62:     for(ptyp=0;ptyp<8;ptyp++)
        !            63:       for(po=0;po<64;po++)
        !            64:        for(p0=0;p0<64;p0++) {
        !            65:          posdata[c][ptyp][po][p0].nextpos = po;
        !            66:          posdata[c][ptyp][po][p0].nextdir = po;
        !            67:        };
        !            68:   /* dest is a function of dir and step */
        !            69:   for(c=0;c<2;c++)
        !            70:     for(ptyp=1;ptyp<7;ptyp++)
        !            71:       for(po=21;po<99;po++)
        !            72:        if (unmap[po] >= 0) {
        !            73:           p = posdata[c][ptyp][unmap[po]];
        !            74:          for(d=0;d<8;d++) {
        !            75:            dest[d][0] = unmap[po];
        !            76:            if (dc[c]*direc[ptyp][d] != 0) {
        !            77:              p0=po;
        !            78:              for(s=0;s<max_steps[ptyp];s++) {
        !            79:                p0 = p0 + dc[c]*direc[ptyp][d];
        !            80:                /* break if (off board) or
        !            81:                   (pawns move two steps from home square) */
        !            82:                if (unmap[p0] < 0 ||
        !            83:                    (ptyp == pawn && s>0 && (d>0 || Stboard[unmap[po]] != ptyp)))
        !            84:                  break;
        !            85:                else
        !            86:                  dest[d][s] = unmap[p0];
        !            87:              }
        !            88:            }
        !            89:            else s=0;
        !            90:            /* sort dest in number of steps order */
        !            91:            steps[d] = s;
        !            92:            for(di=d;di>0;di--)
        !            93:              if (steps[sorted[di-1]] < s)
        !            94:                sorted[di] = sorted[di-1];
        !            95:              else
        !            96:                break;
        !            97:            sorted[di] = d;
        !            98:          }
        !            99:          /* update posdata, pawns have two threads (capture and no capture) */
        !           100:          p0=unmap[po];
        !           101:          if (ptyp == pawn) {
        !           102:            for(s=0;s<steps[0];s++) {
        !           103:              p[p0].nextpos = dest[0][s];
        !           104:              p0 = dest[0][s];
        !           105:            }
        !           106:            p0=unmap[po];
        !           107:            for(d=1;d<3;d++) {
        !           108:              p[p0].nextdir = dest[d][0];
        !           109:              p0 = dest[d][0];
        !           110:            }
        !           111:          }
        !           112:          else {
        !           113:            p[p0].nextdir = dest[sorted[0]][0];
        !           114:            for(d=0;d<8;d++)
        !           115:              for(s=0;s<steps[sorted[d]];s++) {
        !           116:                p[p0].nextpos = dest[sorted[d]][s];
        !           117:                p0 = dest[sorted[d]][s];
        !           118:                if (d < 7)
        !           119:                  p[p0].nextdir = dest[sorted[d+1]][0];
        !           120:                /* else is already initialised */
        !           121:              }
        !           122:          }
        !           123: #ifdef DEBUG
        !           124:          printf("Ptyp:%d Position:%d\n{",ptyp,unmap[po]);
        !           125:          for(p0=0;p0<63;p0++) printf("%d,",p[p0].nextpos);
        !           126:          printf("%d};\n",p[63].nextpos);
        !           127:          for(p0=0;p0<63;p0++) printf("%d,",p[p0].nextdir);
        !           128:          printf("%d};\n",p[63].nextdir);
        !           129: #endif DEBUG
        !           130:        }
        !           131: }
        !           132: #endif
        !           133: 
        !           134: 
        !           135: #if (NEWMOVE > 2)
        !           136: int SqAtakd(sq,side)
        !           137: short sq,side;
        !           138: 
        !           139: /*
        !           140:   See if any piece with color 'side' ataks sq. First check pawns
        !           141:   Then Queen, Bishop, Rook and King and last Knight.
        !           142: */
        !           143: 
        !           144: {
        !           145:   register short u;
        !           146:   register struct sqdata *p;
        !           147: 
        !           148:   p = posdata[1-side][pawn][sq];
        !           149:   u = p[sq].nextdir; /* follow captures thread */
        !           150:   while (u != sq) {
        !           151:     if (board[u] == pawn && color[u] == side) return(true);
        !           152:     u = p[u].nextdir;
        !           153:   }
        !           154:   /* king capture */
        !           155:   if (distance(sq,PieceList[side][0]) == 1) return(true);
        !           156:   /* try a queen bishop capture */
        !           157:   p = posdata[side][bishop][sq];
        !           158:   u = p[sq].nextpos;
        !           159:   while (u != sq) {
        !           160:     if (color[u] == neutral) {
        !           161:       u = p[u].nextpos;
        !           162:     }
        !           163:     else {
        !           164:       if (color[u] == side && 
        !           165:          (board[u] == queen || board[u] == bishop))
        !           166:        return(true);
        !           167:       u = p[u].nextdir;
        !           168:     }
        !           169:   }
        !           170:   /* try a queen rook capture */
        !           171:   p = posdata[side][rook][sq];
        !           172:   u = p[sq].nextpos;
        !           173:   while (u != sq) {
        !           174:     if (color[u] == neutral) {
        !           175:       u = p[u].nextpos;
        !           176:     }
        !           177:     else {
        !           178:       if (color[u] == side && 
        !           179:          (board[u] == queen || board[u] == rook))
        !           180:        return(true);
        !           181:       u = p[u].nextdir;
        !           182:     }
        !           183:   }
        !           184:   /* try a knight capture */
        !           185:   p = posdata[side][knight][sq];
        !           186:   u = p[sq].nextpos;
        !           187:   while (u != sq) {
        !           188:     if (color[u] == neutral) {
        !           189:       u = p[u].nextpos;
        !           190:     }
        !           191:     else {
        !           192:       if (color[u] == side && board[u] == knight) return(true);
        !           193:       u = p[u].nextdir;
        !           194:     }
        !           195:   }
        !           196:   return(false);
        !           197: }
        !           198: #endif
        !           199: 
        !           200: #if (NEWMOVE > 3)
        !           201: BRscan(sq,s,mob)
        !           202: short sq,*s,*mob;
        !           203: /*
        !           204:    Find Bishop and Rook mobility, XRAY attacks, and pins. Increment the 
        !           205:    hung[] array if a pin is found. 
        !           206: */
        !           207: {
        !           208:   register short u,piece,pin;
        !           209:   register struct sqdata *p;
        !           210:   short *Kf;
        !           211: 
        !           212:   Kf = Kfield[c1];
        !           213:   *mob = 0;
        !           214:   piece = board[sq];
        !           215:   p = posdata[color[sq]][piece][sq];
        !           216:   u = p[sq].nextpos;
        !           217:   pin = -1; /* start new direction */
        !           218:   while (u != sq) {
        !           219:     *s += Kf[u];
        !           220:     if (color[u] == neutral) {
        !           221:       (*mob)++;
        !           222:       if (p[u].nextpos == p[u].nextdir) pin = -1; /* oops new direction */
        !           223:       u = p[u].nextpos;
        !           224:     }
        !           225:     else if (pin < 0) {
        !           226:       if (board[u] == pawn || board[u] == king)
        !           227:        u = p[u].nextdir;
        !           228:       else {
        !           229:        if (p[u].nextpos != p[u].nextdir)
        !           230:          pin = u; /* not on the edge and on to find a pin */
        !           231:        u = p[u].nextpos;
        !           232:       }
        !           233:     }
        !           234:     else if (color[u] == c2 && (board[u] > piece || atk2[u] == 0))
        !           235:       {
        !           236:        if (color[pin] == c2)
        !           237:          {
        !           238:            *s += PINVAL;
        !           239:            if (atk2[pin] == 0 ||
        !           240:                atk1[pin] > control[board[pin]]+1)
        !           241:              ++hung[c2];
        !           242:          }
        !           243:        else *s += XRAY;
        !           244:        pin = -1; /* new direction */
        !           245:        u = p[u].nextdir;
        !           246:       }
        !           247:     else {
        !           248:       pin = -1; /* new direction */
        !           249:       u = p[u].nextdir;
        !           250:     }
        !           251:   }
        !           252: }
        !           253: #endif
        !           254: 
        !           255: #if (NEWMOVE >= 5)
        !           256: CaptureList(side,xside,ply)
        !           257: short side,xside,ply;
        !           258: {
        !           259:   register short u,sq;
        !           260:   register struct sqdata *p;
        !           261:   short i,piece,*PL;
        !           262:   struct leaf *node;
        !           263:   
        !           264:   TrPnt[ply+1] = TrPnt[ply];
        !           265:   node = &Tree[TrPnt[ply]];
        !           266:   PL = PieceList[side];
        !           267:   for (i = 0; i <= PieceCnt[side]; i++)
        !           268:     {
        !           269:       sq = PL[i];
        !           270:       piece = board[sq];
        !           271:       p = posdata[side][piece][sq];
        !           272:       if (piece == pawn) {
        !           273:        u = p[sq].nextdir; /* follow captures thread */
        !           274:        while (u != sq) {
        !           275:          if (color[u] == xside) {
        !           276:             node->f = sq; node->t = u;
        !           277:             node->flags = capture;
        !           278:             if (u < 8 || u > 55)
        !           279:               {
        !           280:                 node->flags |= promote;
        !           281:                 node->score = valueQ;
        !           282:               }
        !           283:            else
        !           284:               node->score = value[board[u]] + svalue[board[u]] - piece;
        !           285:             ++node;
        !           286:             ++TrPnt[ply+1];
        !           287:            }
        !           288:          u = p[u].nextdir;
        !           289:        }
        !           290:       }
        !           291:       else {
        !           292:        u = p[sq].nextpos;
        !           293:        while (u != sq) {
        !           294:           if (color[u] == neutral)
        !           295:           u = p[u].nextpos;
        !           296:           else {
        !           297:           if (color[u] == xside) {
        !           298:               node->f = sq; node->t = u;
        !           299:               node->flags = capture;
        !           300:               node->score = value[board[u]] + svalue[board[u]] - piece;
        !           301:               ++node;
        !           302:               ++TrPnt[ply+1];
        !           303:              }
        !           304:           u = p[u].nextdir;
        !           305:         }
        !           306:        }
        !           307:      }
        !           308:    }
        !           309: }
        !           310: #endif
        !           311: 
        !           312: #if (NEWMOVE > 5)
        !           313: GenMoves(ply,sq,side,xside)
        !           314:      short ply,sq,side,xside;
        !           315:  
        !           316: /*
        !           317:   Generate moves for a piece. The moves are taken from the
        !           318:   precalulated array posdata. If the board is free, next move
        !           319:   is choosen from nextpos else from nextdir.
        !           320: */
        !           321:  
        !           322: {
        !           323:   register short u,piece;
        !           324:   register struct sqdata *p;
        !           325:         
        !           326:   piece = board[sq];
        !           327:   p = posdata[side][piece][sq];
        !           328:   if (piece == pawn) {
        !           329:     u = p[sq].nextdir; /* follow captures thread */
        !           330:     while (u != sq) {
        !           331:       if (color[u] == xside) LinkMove(ply,sq,u,xside);
        !           332:       u = p[u].nextdir;
        !           333:     }
        !           334:     u = p[sq].nextpos; /* and follow no captures thread */
        !           335:     while (u != sq) {
        !           336:       if (color[u] == neutral && (u != sq+16 || color[u-8] == neutral)
        !           337:           && (u != sq-16 || color[u+8] == neutral)) {
        !           338:         LinkMove(ply,sq,u,xside);
        !           339:       }
        !           340:       u = p[u].nextpos;
        !           341:     }
        !           342:   }  
        !           343:   else {
        !           344:     u = p[sq].nextpos;
        !           345:     while (u != sq) {
        !           346:       if (color[u] == neutral) {
        !           347:         LinkMove(ply,sq,u,xside);
        !           348:         u = p[u].nextpos;
        !           349:       }
        !           350:       else {
        !           351:         if (color[u] == xside) LinkMove(ply,sq,u,xside);
        !           352:        u = p[u].nextdir;
        !           353:       }
        !           354:     }
        !           355:   }    
        !           356: } 
        !           357: #endif

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.