games-request@tekred.UUCP (05/21/87)
Submitted by: jhs@hpltca.HP.COM (John Stanback) Comp.sources.games: Volume 1, Issue 23 Archive-name: chess [This game was posted to net.sources.games just as that newsgroup was disappearing, so many of you may not have seen it. This has fixes for BSD Unix by Rich Salz and the index variable name conflict fixed. It compiles and runs on our 4.3bsd Vax. Other postings have indicated it plays a decent game. -br] #! /bin/sh # This is a shell archive. Remove anything before this line, then unpack # it by saving it into a file and typing "sh file". To overwrite existing # files, type "sh file -c". You can also feed this as standard input via # unshar, or by typing "sh <file", e.g.. If this archive is complete, you # will see the following message at the end: # "End of shell archive." # Contents: README Makefile patchlevel.h chess.c chess.opn chess.001 # Wrapped by billr@tekred on Wed May 20 17:15:52 1987 PATH=/bin:/usr/bin:/usr/ucb ; export PATH if test -f README -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"README\" else echo shar: Extracting \"README\" \(2865 characters\) sed "s/^X//" >README <<'END_OF_README' X XC source for CHESS X XHere is a shar script containing source code in 'C' for a chess Xprogram I've written. The following files are included: X 1. chess.c : C source for CHESS X 2. chess.opn : Opening Library X 3. chess.001 : Sample problem X XThe file chess.c must be compiled with the -lcurses option. The Xcode is pretty generic (I think) and hopefully will run on a wide Xvariety of machines. The help command gives a list of the options Xavailable. To test out the program, enter 'get' and respond to Xthe file name prompt with 'chess.001'. Type 'switch' and the Xcomputer should find mate in 4 with Nf7. This takes a few seconds Xon an HP350 computer. X XThe program plays a fairly respectable game of chess, although it Xis not competetive with a state-of-the art commercial program. The Xsearch rate is typically 100-300 nodes/sec. on an HP Vectra (8 Mhz. X286) and about 300-900 nodes/sec. on an HP 350 (25 Mhz. 68020). I Xam interested to find out what is achieved on other machines. I Xwould also be interested in any comments on playing strength, Xweaknesses or bugs in the program, and suggested improvements in Xthe algorithm. X XHere are a few comments on the program: X X1. Opening Library X I'm a terrible chess player and don't know anything about X openings. I copied 70-80 random lines of play from MCO into X the file chess.opn. I think there are a few mistakes in the X translation. If anyone generates a better library please let X me know. X X2. Positional Heuristics X I think that improvement in this area would help the program X quite a bit. In most situations the computer cannot do X anything forceful and the choice of a move is based on X positional aspects. I haven't spent a lot of time on the X heuristics and many times the program has no idea of what is X happening and how to proceed. Perhaps optimizing the values of X the existing heuristics would help, but to get a major X improvement I think more chess knowledge will be necessary. X X3. Search Algorithm X This program uses a full-width alpha-beta searching technique X with depth extensions on checks, check evasions, pawn promotion X threats and threats to multiple pieces. Capture sequences are X handled by a separate search routine. I imagine that much more X efficient search routines exist, and would be interested to hear X of any. Refinements of the search extension heuristics (similar X to the extensions for pawn promotion threats) could have a major X effect on the programs ability. X X4. Move Generation X There are probably better ways to do this, but they would X likely change the data structure drastically and necessitate X a complete re-write. Maybe some good hacks would speed things X up, the ataks function would be the best place to start. X END_OF_README if test 2865 -ne `wc -c <README`; then echo shar: \"README\" unpacked with wrong size! fi # end of overwriting check fi if test -f Makefile -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"Makefile\" else echo shar: Extracting \"Makefile\" \(152 characters\) sed "s/^X//" >Makefile <<'END_OF_Makefile' X# Makefile for chess program X X# comment out -DBSD for SYSV machines XCFLAGS = -O -DBSD X Xchess: chess.c X cc $(CFLAGS) -o chess chess.c -lcurses -ltermlib END_OF_Makefile if test 152 -ne `wc -c <Makefile`; then echo shar: \"Makefile\" unpacked with wrong size! fi # end of overwriting check fi if test -f patchlevel.h -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"patchlevel.h\" else echo shar: Extracting \"patchlevel.h\" \(21 characters\) sed "s/^X//" >patchlevel.h <<'END_OF_patchlevel.h' X#define PATCHLEVEL 1 END_OF_patchlevel.h if test 21 -ne `wc -c <patchlevel.h`; then echo shar: \"patchlevel.h\" unpacked with wrong size! fi # end of overwriting check fi if test -f chess.c -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"chess.c\" else echo shar: Extracting \"chess.c\" \(47675 characters\) sed "s/^X//" >chess.c <<'END_OF_chess.c' X/* X C source for CHESS Rev. 3-10-87 X X Written by John Stanback (hplabs!hpfcla!hpisla!hpltca!jhs) X X Patches for BSD Unix by Rich Salz (rs@mirror.TMC.COM) - 5/3/87 X X*/ X X#include <stdio.h> X#include <curses.h> X X#define DEF_TIME 400 X#define neutral 0 X#define white 1 X#define black 2 X#define no_piece 0 X#define pawn 1 X#define knight 2 X#define bishop 3 X#define rook 4 X#define queen 5 X#define king 6 X#define px " PNBRQK" X#define qx " pnbrqk" X#define rx "12345678" X#define cx "abcdefgh" X#define check 0x0001 X#define capture 0x0002 X#define draw 0x0004 X#define promote 0x0010 X#define incheck 0x0020 X#define epmask 0x0040 X#define exact 0x0100 X#define pwnthrt 0x0200 X#define true 1 X#define false 0 X Xstruct leaf X { X short f,t,score,reply; X unsigned short flags; X }; X Xchar mvstr1[5],mvstr2[5]; Xstruct leaf Tree[2000],*root; Xshort TrPnt[30]; Xshort row[64],col[64],locn[8][8],Index[64],svalue[64]; Xshort PieceList[3][16],PieceCnt[3]; Xshort castld[3],kingmoved[3],mtl[3],pmtl[3],emtl[3],hung[3]; Xshort mate,post,xkillr,ykillr,opponent,computer,Sdepth; Xlong time0; Xint response_time,extra_time,timeout,et,et0; Xshort quit,reverse,bothsides,InChk,player; Xint NodeCnt,srate; Xshort atak[3][64],PawnCnt[3][8]; Xshort ChkFlag[30],CptrFlag[30],PawnThreat[30],PPscore[30]; Xshort BookSize,BookDepth; Xshort GameCnt,Game50,epsquare,lpost; Xunsigned short GameList[240],Book[80][24]; Xshort GameScore[240],GamePc[240],GameClr[240]; Xshort value[8]={0,100,330,330,500,950,999}; Xshort otherside[3]={0,2,1}; Xshort passed_pawn1[8]={0,3,4,8,14,24,40,80}; Xshort passed_pawn2[8]={0,2,3,4,6,9,13,80}; Xshort passed_pawn3[8]={0,1,2,3,4,5,6,80}; Xshort map[64]= X {26,27,28,29,30,31,32,33,38,39,40,41,42,43,44,45, X 50,51,52,53,54,55,56,57,62,63,64,65,66,67,68,69, X 74,75,76,77,78,79,80,81,86,87,88,89,90,91,92,93, X 98,99,100,101,102,103,104,105,110,111,112,113,114,115,116,117}; Xshort unmap[144]= X {-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1, X -1,-1,0,1,2,3,4,5,6,7,-1,-1,-1,-1,8,9,10,11,12,13,14,15,-1,-1, X -1,-1,16,17,18,19,20,21,22,23,-1,-1,-1,-1,24,25,26,27,28,29,30,31,-1,-1, X -1,-1,32,33,34,35,36,37,38,39,-1,-1,-1,-1,40,41,42,43,44,45,46,47,-1,-1, X -1,-1,48,49,50,51,52,53,54,55,-1,-1,-1,-1,56,57,58,59,60,61,62,63,-1,-1, X -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1}; Xshort edge[64]= X {0,1,2,3,3,2,1,0,1,2,3,4,4,3,2,1,2,3,4,5,5,4,3,2,3,4,5,6,6,5,4,3, X 3,4,5,6,6,5,4,3,2,3,4,5,5,4,3,2,1,2,3,4,4,3,2,1,0,1,2,3,3,2,1,0}; Xshort pknight[64]= X {0,6,11,14,14,11,6,0,6,12,22,25,25,22,12,6, X 11,20,30,36,36,30,20,11,14,25,36,44,44,36,25,14, X 14,25,36,44,44,36,25,14,11,20,30,36,36,30,20,11, X 6,12,22,25,25,22,12,6,0,6,11,14,14,11,6,0}; Xshort pbishop[64]= X {14,14,14,14,14,14,14,14,14,18,18,18,18,18,18,14, X 14,18,22,22,22,22,18,14,14,18,22,22,22,22,18,14, X 14,18,22,22,22,22,18,14,14,18,22,22,22,22,18,14, X 14,18,18,18,18,18,18,14,14,14,14,14,14,14,14,14}; Xshort board[64]= X {rook,knight,bishop,queen,king,bishop,knight,rook, X pawn,pawn,pawn,pawn,pawn,pawn,pawn,pawn, X 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, X pawn,pawn,pawn,pawn,pawn,pawn,pawn,pawn, X rook,knight,bishop,queen,king,bishop,knight,rook}; Xshort color[64]= X {white,white,white,white,white,white,white,white, X white,white,white,white,white,white,white,white, X 0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0, X black,black,black,black,black,black,black,black, X black,black,black,black,black,black,black,black}; Xshort sweep[7]= {false,false,false,true,true,true,false}; Xshort Dstpwn[3]={0,4,6}; Xshort Dstart[7]={6,4,8,4,0,0,0}; Xshort Dstop[7]={7,5,15,7,3,7,7}; Xshort Dir[16]={1,12,-1,-12,11,13,-11,-13,10,-10,14,-14,23,-23,25,-25}; Xunsigned short PV,Swag1,Swag2,killr1[30],killr2[30],killr3[30],Qkillr[30]; Xunsigned short Ckillr[3],prvar[30]; X Xreadline(x, y, prompt, p) X int x, y; X char *prompt, *p; X{ X char *q; X X standout(); X mvprintw(y-1,x-1, "%s", prompt); X standend(); X ClrEoln(); X getyx(stdscr, y, x); X for (q = p; (*p = getchar()) !=EOF; ) { X switch (*p) { X default: X p++; X x++; X break; X case 'L' & 037: X touchwin(stdscr); X refresh(); X break; X case '\n': case '\r': X move(y, x); X *p = '\0'; X return; X case '\b': X if (p > q) { X p--; X x--; X } X break; X case 'U' & 037: case '\007': case '\033': X p = q; X x = 0; X break; X } X move(y, x); X ClrEoln(); X } X *p = '\0'; X} X Xmain() X{ X initscr(); X NewGame(); X while (!(quit)) X { X if (bothsides && !mate) select_move(opponent); else input_command(); X if (!quit && !mate) select_move(computer); X } X endwin(); X} X X XOpeningBook(side) Xshort side; X{ Xshort i,j,r0,pnt; Xunsigned m,r; X srand(time(0)); X r0 = m = 0; X for (i = 0; i < BookSize; i++) X { X for (j = 0; j <= GameCnt; j++) X if (GameList[j] != Book[i][j]) break; X if (j > GameCnt) X if ((r=rand()) > r0) X { X r0 = r; m = Book[i][GameCnt+1]; X } X } X for (pnt = TrPnt[1]; pnt < TrPnt[2]; pnt++) X if ((Tree[pnt].f<<8) + Tree[pnt].t == m) Tree[pnt].score = 0; X sort(TrPnt[1],TrPnt[2]-1); X if (Tree[TrPnt[1]].score < 0) BookDepth = -1; X} X X Xselect_move(side) Xshort side; X X/* X Select a move by calling function search() at progressively deeper X ply until time is up or a mate or draw is reached. An alpha-beta X window of -0, +75 points is set around the score returned from the X previous iteration. X*/ X X{ Xshort i,alpha,beta,tempb,tempc; X X timeout = false; player = side; X for (i = 0; i < 30; i++) X prvar[i] = killr1[i] = killr2[i] = killr3[i] = 0; X PPscore[0] = -5000; X alpha = -9999; beta = 9999; X NodeCnt = Sdepth = extra_time = 0; X ataks(white,atak[white]); ataks(black,atak[black]); X TrPnt[1] = 0; root = &Tree[0]; X MoveList(side,1); X if (GameCnt < BookDepth) OpeningBook(side); else BookDepth = -1; X if (BookDepth > 0) timeout = true; X while (!timeout && Sdepth<30) X { X Sdepth++; X gotoXY(70,1); printw("%d ",Sdepth); ClrEoln(); X search(side,1,Sdepth,alpha,beta,prvar); X if (root->score < alpha) X search(side,1,Sdepth,-12000,alpha,prvar); X if (root->score > beta && !(root->flags & exact)) X { X gotoXY(70,1); printw("%d+",Sdepth); ClrEoln(); X search(side,1,Sdepth,beta,12000,prvar); X } X beta = root->score+75; X if (root->flags & exact) timeout = true; X } X if (root->score > -9999) X { X MakeMove(side,root,&tempb,&tempc); X algbrnot(root->f,root->t); X PrintBoard(side,root->f,root->t,0); X gotoXY(50,16); printw("My move is: %s",mvstr1); ClrEoln(); X } X ElapsedTime(1); X gotoXY(18,23); printw("Nodes= %d",NodeCnt); ClrEoln(); X gotoXY(18,24); printw("Nodes/Sec= %d",srate); ClrEoln(); X gotoXY(50,13); X if (root->flags & draw) printw("draw game!"); X if (root->score < -9000) printw("opponent will soon mate!"); X if (root->score > 9000) printw("computer will soon mate!"); X if (root->score == -9999) X { X gotoXY(50,13); X printw("opponent mates!!"); mate = true; X } X if (root->score == 9998) X { X gotoXY(50,13); X printw("computer mates!!"); mate = true; X } X ClrEoln(); X if (post) post_move(root); X if (root->f == 255 || root->t == 255) Game50 = GameCnt; X else if (board[root->t] == pawn || (root->flags & capture)) X Game50 = GameCnt; X GameScore[GameCnt] = root->score; X if (GameCnt > 238) quit = true; X player = otherside[side]; X} X X XVerifyMove(s,ok) Xchar s[]; Xshort *ok; X X/* X See if the opponents move is legal, if so, make it. X*/ X X{ Xshort x,pnt,cnt,tempb,tempc; Xunsigned short nxtline[30]; Xstruct leaf *node,*xnode; X X *ok = false; cnt = 0; X MoveList(opponent,2); X pnt = TrPnt[2]; X while (pnt < TrPnt[3]) X { X node = &Tree[pnt]; pnt++; X algbrnot(node->f,node->t); X if (strcmp(s,mvstr1) == 0 || strcmp(s,mvstr2) == 0) X { X xnode = node; cnt++; X } X } X if (cnt == 1) X { X MakeMove(opponent,xnode,&tempb,&tempc); X CaptureSearch(computer,opponent,3,1,-9999,9999,0,&x,nxtline); X if (x == 10000) UnmakeMove(opponent,xnode,&tempb,&tempc); X else X { X *ok = true; PrintBoard(opponent,xnode->f,xnode->t,0); X if (xnode->f == 255 || xnode->t == 255) Game50 = GameCnt; X else if (board[xnode->t] == pawn || (xnode->flags & capture)) X Game50 = GameCnt; X } X } X} X X Xinput_command() X{ Xshort ok,i,f,t; Xchar s[20],fname[20]; XFILE *fd; X X ok=quit=false; X while (!(ok || quit)) X { X readline(50,21,"Your move is? ", s); X player = opponent; X VerifyMove(s,&ok); X if (strcmp(s,"prt") == 0) X { X ClrScreen(); PrintBoard(white,0,0,1); X } X if (strcmp(s,"quit") == 0) quit = true; X if (strcmp(s,"post") == 0) post = !post; X if (strcmp(s,"set") == 0) SetBoard(); X if (strcmp(s,"go") == 0) ok = true; X if (strcmp(s,"help") == 0) help(); X if (strcmp(s, "redraw") == 0) X { X ClrScreen(); X PrintBoard(white,0,0,1); X } X if (strcmp(s,"hint") == 0) X { X algbrnot(prvar[2]>>8,prvar[2] & 0xFF); X gotoXY(50,13); printw("try %5s",mvstr1); ClrEoln(); X } X if (strcmp(s,"both") == 0) X { X bothsides = !bothsides; X select_move(opponent); X ok = true; X } X if (strcmp(s,"reverse") == 0) X { X reverse = !reverse; X ClrScreen(); X PrintBoard(white,0,0,1); X } X if (strcmp(s,"switch") == 0) X { X computer = otherside[computer]; X opponent = otherside[opponent]; X ok = true; X } X if (strcmp(s,"save") == 0) X { X readline(50, 21, "file name? ", fname); X SaveGame(fname); X } X if (strcmp(s,"get") == 0) X { X readline(50, 21, "file name? ", fname); X GetGame(fname); X InitializeStats(); X PrintBoard(white,0,0,1); X } X if (strcmp(s,"time") == 0) X { X readline(50, 21, "enter time: ", fname); X response_time = atoi(fname); X } X if (strcmp(s,"undo") == 0 && GameCnt > 0) X { X f = GameList[GameCnt]>>8; t = GameList[GameCnt] & 0xFF; X board[f] = board[t]; color[f] = color[t]; X board[t] = GamePc[GameCnt]; color[t] = GameClr[GameCnt]; X GameCnt--; X PrintBoard(white,0,0,1); X InitializeStats(); X } X if (strcmp(s,"list") == 0) X { X fd = fopen("chess.lst","w"); X for (i = 0; i <= GameCnt; i++) X { X f = GameList[i]>>8; t = (GameList[i] & 0xFF); X algbrnot(f,t); X if ((i % 2) == 0) fprintf(fd,"\n"); X fprintf(fd," %5s %6d ",mvstr1,GameScore[i]); X } X fprintf(fd,"\n"); X fclose(fd); X } X } X ElapsedTime(1); X} X X XgotoXY(x,y) Xshort x,y; X{ X move(y-1,x-1); X} X X XClrScreen() X{ X clear(); refresh(); X} X X XClrEoln() X{ X clrtoeol(); refresh(); X} X X Xalgbrnot(f,t) Xshort f,t; X{ X if (f == 255) X { strcpy(mvstr1,"o-o"); strcpy(mvstr2,"o-o"); } X else if (t == 255) X { strcpy(mvstr1,"o-o-o"); strcpy(mvstr2,"o-o"); } X else X { X mvstr1[0] = cx[col[f]]; mvstr1[1] = rx[row[f]]; X mvstr1[2] = cx[col[t]]; mvstr1[3] = rx[row[t]]; X mvstr2[0] = qx[board[f]]; X mvstr2[1] = mvstr1[2]; mvstr2[2] = mvstr1[3]; X mvstr1[4] = '\0'; mvstr2[3] = '\0'; X } X} X X Xparse(s,m) Xunsigned short *m; char s[]; X{ Xshort r1,r2,c1,c2; X if (s[4] == 'o') *m = 0x00FF; X else if (s[0] == 'o') *m = 0xFF00; X else X { X c1 = s[0] - 'a'; r1 = s[1] - '1'; X c2 = s[2] - 'a'; r2 = s[3] - '1'; X *m = (locn[r1][c1]<<8) + locn[r2][c2]; X } X} X X XGetOpenings() X{ XFILE *fd; Xint c,j; Xchar s[80],*p; X fd = fopen("chess.opn","r"); X BookSize = 0; BookDepth = 24; j = -1; c = '?'; X while (c != EOF) X { X p = s; X while ((c=getc(fd)) != EOF) X if (c == '\n') break; else *(p++) = c; X *p = '\0'; X if (c != EOF) X if (s[0] == '!') X { X while (j < BookDepth) Book[BookSize][j++] = 0; X BookSize++; j = -1; X } X else if (j < 0) j++; X else X { X parse(&s[0],&Book[BookSize][j]); j++; X parse(&s[6],&Book[BookSize][j]); j++; X } X } X fclose(fd); X} X X XGetGame(fname) Xchar fname[20]; X{ XFILE *fd; Xint c; Xshort loc; Xunsigned short m; X X if (fname[0] == '\0') strcpy(fname,"chess.000"); X if ((fd = fopen(fname,"r")) != NULL) X { X fscanf(fd,"%hd%hd",&castld[white],&castld[black]); X fscanf(fd,"%hd%hd",&kingmoved[white],&kingmoved[black]); X for (loc = 0; loc < 64; loc++) X { X fscanf(fd,"%hd",&m); board[loc] = (m >> 8); color[loc] = (m & 0xFF); X } X GameCnt = -1; c = '?'; X while (c != EOF) X c = fscanf(fd,"%hd%hd%hd%hd",&GameList[++GameCnt],&GameScore[GameCnt], X &GamePc[GameCnt],&GameClr[GameCnt]); X fclose(fd); X } X} X X XSaveGame(fname) Xchar fname[20]; X{ XFILE *fd; Xshort loc,i; X X if (fname[0] == '\0') strcpy(fname,"chess.000"); X fd = fopen(fname,"w"); X fprintf(fd,"%d %d\n",castld[white],castld[black]); X fprintf(fd,"%d %d\n",kingmoved[white],kingmoved[black]); X for (loc = 0; loc < 64; loc++) X fprintf(fd,"%d\n",256*board[loc] + color[loc]); X for (i = 0; i <= GameCnt; i++) X fprintf(fd,"%d %d %d %d\n",GameList[i],GameScore[i],GamePc[i],GameClr[i]); X fclose(fd); X} X X XElapsedTime(iop) Xshort iop; X{ Xint minute,second; X et = time(0) - time0; X if (et < et0) et0 = 0; X if (et > et0 || iop == 1) X { X if (et > response_time+extra_time) timeout = true; X et0 = et; X if (iop == 1) X { X et0 = 0; time0 = time(0); X } X minute = et/60; second = (et - 60*minute); X if (player == computer) gotoXY(50,18); else gotoXY(50,23); X printw("%d:%d",minute,second); ClrEoln(); X if (et > 0) srate = NodeCnt/et; else srate = 0; X if (post) X { X gotoXY(18,24); printw("Nodes/Sec= %d",srate); ClrEoln(); X } X } X} X X Xpost_move(node) Xstruct leaf *node; X{ Xshort d,e,ply; X d = 4; ply = 1; X gotoXY(60,d); printw("%6d ",node->score); X while (prvar[ply] > 0) X { X algbrnot(prvar[ply]>>8,prvar[ply] & 0x00FF); X gotoXY(50,d); printw("%5s",mvstr1); X ply++; d++; X } X e = d; X while (d < lpost) X { X gotoXY(50,d++); ClrEoln(); X } X lpost = e; X refresh(); X} X X XDrawPiece(loc) Xshort loc; X{ Xshort r,c; char x; X if (reverse) r = 7-row[loc]; else r = row[loc]; X if (reverse) c = 7-col[loc]; else c = col[loc]; X if (color[loc] == black) x = '*'; else x = ' '; X gotoXY(5+5*c,4+2*(7-r)); printw("%c%c",x,px[board[loc]]," "); X} X X XPrintBoard(side,f,t,flag) Xshort side,f,t,flag; X{ Xshort i,l,c,z; X X if (side == white) c = 0; else c = 56; X if (flag) X { X i = 2; X gotoXY(3,++i); X printw("|----|----|----|----|----|----|----|----|"); X while (i<19) X { X gotoXY(1,++i); X if (reverse) z = (i/2)-1; else z = 10-(i/2); X printw("%d | | | | | | | | |",z); X gotoXY(3,++i); X printw("|----|----|----|----|----|----|----|----|"); X } X gotoXY(3,20); X if (reverse) printw(" h g f e d c b a"); X else printw(" a b c d e f g h"); X for (l = 0; l < 64; l++) DrawPiece(l); X } X else if (f == 255) X { X DrawPiece(c+4); DrawPiece(c+6); X DrawPiece(c+7); DrawPiece(c+5); X } X else if (t == 255) X { X DrawPiece(c+4); DrawPiece(c+2); X DrawPiece(c); DrawPiece(c+3); X } X else X { X DrawPiece(f); DrawPiece(t); X } X refresh(); X} X X XSetBoard() X{ Xshort a,r,c,loc; Xchar s[20]; X X ClrScreen(); PrintBoard(white,0,0,1); X a = white; X do X { X gotoXY(50,2); printw(". Exit to Main"); X gotoXY(50,3); printw("# Clear Board"); X readline(49,5, "Enter piece & location: ", s); X if (s[0] == '#') X { X for (loc = 0; loc < 64; loc++) X { board[loc] = no_piece; color[loc] = neutral; } X PrintBoard(white,0,0,1); X } X if (s[0] == 'c' || s[0] == 'C') a = otherside[a]; X c = s[1]-'a'; r = s[2]-'1'; X if ((c >= 0) && (c < 8) && (r >= 0) && (r < 8)) X { X loc = locn[r][c]; X color[loc] = a; X if (s[0] == 'p') board[loc] = pawn; X else if (s[0] == 'n') board[loc] = knight; X else if (s[0] == 'b') board[loc] = bishop; X else if (s[0] == 'r') board[loc] = rook; X else if (s[0] == 'q') board[loc] = queen; X else if (s[0] == 'k') board[loc] = king; X else { board[loc] = no_piece; color[loc] = neutral; } X DrawPiece(loc); refresh(); X } X } X while (s[0] != '.'); X if (board[4] != king) kingmoved[white] = 10; X if (board[61] != king) kingmoved[black] = 10; X GameCnt = -1; Game50 = -1; BookDepth = 0; X InitializeStats(); ClrScreen(); PrintBoard(white,0,0,1); X} X X XNewGame() X{ Xshort l,r,c; Xchar buff[20]; X X mate = quit = reverse = bothsides = post = false; X lpost = NodeCnt = epsquare = xkillr = 0; X GameCnt = Game50 = -1; X castld[white] = castld[black] = false; X kingmoved[white] = kingmoved[black] = 0; X opponent = white; computer = black; X for (r = 0; r < 8; r++) X for (c = 0; c < 8; c++) X { X l = 8*r+c; locn[r][c] = l; X row[l] = r; col[l] = c; X } X ClrScreen(); X readline(1, 20, "enter response time (or RETURN for default): ", buff); X response_time = buff[0] ? atoi(buff) : DEF_TIME; X ClrScreen(); PrintBoard(white,0,0,1); X InitializeStats(); X ElapsedTime(1); X GetOpenings(); X} X X Xhelp() X{ Xchar c; Xchar buff[10]; X XClrScreen(); Xprintw("\n"); Xprintw("This program attempts to play CHESS\n\n"); Xprintw("To make a move, enter the column (labelled 'a' - 'h') and\n"); Xprintw("row (labelled '1' - '8') of the 'from' and 'to' squares.\n"); Xprintw("For example, to move the kings pawn forward 2 squares, type e2e4.\n"); Xprintw("Other commands are:\n\n"); Xprintw("o-o castle king side\n"); Xprintw("o-o-o castle queen side\n"); Xprintw("set set up a board position\n"); Xprintw("switch switch sides with computer\n"); Xprintw("go skip your move\n"); Xprintw("reverse reverse board display\n"); Xprintw("redraw re-paint display\n"); Xprintw("both computer plays both sides\n"); Xprintw("time change response time\n"); Xprintw("post post best line of play\n"); Xprintw("hint computer suggests your move\n"); Xprintw("list list moves to file chess.lst\n"); Xprintw("save save game to disk\n"); Xprintw("get get game from disk\n"); Xprintw("quit exit CHESS\n"); Xrefresh(); Xreadline(10, 24, "Type return:", buff); XClrScreen(); XPrintBoard(white,0,0,1); X} X X XUpdatePieceList(side,loc,iop) Xshort side,loc,iop; X X/* X Array PieceList[side][indx] contains the location of all the pieces of X either side. Array Index[loc] contains the indx into PieceList for a X given square. X*/ X X{ Xregister short i; X if (iop == 1) X { X PieceCnt[side]--; X for (i = Index[loc]; i <= PieceCnt[side]; i++) X { X PieceList[side][i] = PieceList[side][i+1]; X Index[PieceList[side][i]] = i; X } X } X else X { X PieceCnt[side]++; X PieceList[side][PieceCnt[side]] = loc; X Index[loc] = PieceCnt[side]; X } X} X X XInitializeStats() X{ Xregister short i,loc; X for (i = 0; i < 8; i++) X PawnCnt[white][i] = PawnCnt[black][i] = 0; X mtl[white] = mtl[black] = pmtl[white] = pmtl[black]=0; X PieceCnt[white] = PieceCnt[black] = 0; X for (loc = 0; loc < 64; loc++) X if (color[loc] != neutral) X { X mtl[color[loc]] += value[board[loc]]; X if (board[loc] == pawn) X { X pmtl[color[loc]] += value[pawn]; X ++PawnCnt[color[loc]][col[loc]]; X } X if (board[loc] == king) Index[loc] = 0; X else Index[loc] = ++PieceCnt[color[loc]]; X PieceList[color[loc]][Index[loc]] = loc; X } X} X X Xsort(p1,p2) Xshort p1,p2; X{ Xregister short p,p0,s; Xstruct leaf temp; X X s = 32000; X while (p1 < p2) X if (Tree[p1].score >= s) p1++; X else X { X s = Tree[p1].score; p0 = p1; X for (p = p1+1; p <= p2; p++) X if (Tree[p].score > s) X { X s = Tree[p].score; p0 = p; X } X temp = Tree[p1]; Tree[p1] = Tree[p0]; Tree[p0] = temp; X p1++; X } X} X X Xrepetition(node) Xstruct leaf *node; X X/* X Check for draw by threefold repetition or 50 move rule. X*/ X X{ Xregister short i,f,t,c; Xshort r,b[64]; Xunsigned short m; X r = c = 0; X#ifdef BSD X bzero((char *)b, sizeof b); X#else X memset(b,0,64*sizeof(short)); X#endif /* BSD */ X for (i = GameCnt; i > Game50; i--) X { X m = GameList[i]; f = m>>8; t = m & 0xFF; X if (t != 255 && f != 255) X { X b[f]++; b[t]--; X if (b[f] == 0) c--; else c++; X if (b[t] == 0) c--; else c++; X if (c == 0) r++; X } X } X if (r == 1) X if (node->score > 0) node->score -= 20; X else node->score += 20; X if (GameCnt-Game50 > 99 || r == 2) X { X node->score = 0; X node->flags |= exact; X node->flags |= draw; X } X} X X Xataks(side,a) Xshort side,a[]; X X/* X Place the lowest value piece attacking a square into array atak[][]. X*/ X X{ Xregister short m,u,d,j; Xshort piece,i,m0,*aloc,*s; X X#ifdef BSD X bzero((char *)a, sizeof a); X#else X a = (short *)memset(a,0,64*sizeof(short)); X#endif /* BSD */ X Dstart[pawn] = Dstpwn[side]; Dstop[pawn] = Dstart[pawn] + 1; X aloc = &PieceList[side][0]; X for (i = 0; i <= PieceCnt[side]; i++) X { X piece = board[*aloc]; m0 = map[*aloc]; X s = &svalue[*aloc]; *s = 0; X aloc++; X if (sweep[piece]) X for (j = Dstart[piece]; j <= Dstop[piece]; j++) X { X d = Dir[j]; m = m0+d; u = unmap[m]; X while (u >= 0) X { X *s += 2; X if (a[u] == 0 || piece < a[u]) a[u] = piece; X if (color[u] == neutral) X { X m += d; u = unmap[m]; X } X else u = -1; X } X } X else X { X for (j = Dstart[piece]; j <= Dstop[piece]; j++) X if ((u = unmap[m0+Dir[j]]) >= 0) X if (a[u] == 0 || piece < a[u]) a[u] = piece; X } X } X} X X Xcastle(side,f,t,iop,ok) Xshort side,f,t,iop,*ok; X{ Xshort i,e,k1,k2,r1,r2,c1,c2,t0,xside; X X xside = otherside[side]; X if (side == white) e = 0; else e = 56; X if (f == 255) X { X k1 = e+4; k2 = e+6; r1 = e+7; r2 = e+5; c1 = k1; c2 = r1; X } X else X { X k1 = e+4; k2 = e+2; r1 = e; r2 = e+3; c1 = r1; c2 = k1; X } X if (iop == 0) X { X *ok = false; X if (board[k1] == king && board[r1] == rook) *ok = true; X for (i = c1; i <= c2; i++) X if (atak[xside][i] > 0) *ok = false; X for (i = c1+1; i < c2; i++) X if (color[i] != neutral) *ok = false; X } X else X { X if (iop == 1) castld[side] = true; else castld[side] = false; X if (iop == 2) X { X t0 = k1; k1 = k2; k2 = t0; X t0 = r1; r1 = r2; r2 = t0; X } X board[k2] = king; color[k2] = side; Index[k2] = 0; X board[k1] = no_piece; color[k1] = neutral; X board[r2] = rook; color[r2] = side; Index[r2] = Index[r1]; X board[r1] = no_piece; color[r1] = neutral; X PieceList[side][Index[k2]] = k2; X PieceList[side][Index[r2]] = r2; X } X} X X Xen_passant(side,xside,f,t,iop) Xshort side,f,t,iop; X{ Xshort l; X if (t > f) l = t-8; else l = t+8; X if (iop == 1) X { X board[l] = no_piece; color[l] = neutral; X } X else X { X board[l] = pawn; color[l] = xside; X } X InitializeStats(); X} X X XLinkMove(ply,f,t,side,xside) Xshort ply,f,t,side,xside; X{ X X/* X Add a move to the tree. Assign a bonus (in an attempt to X improve move ordering) if move is a X principle variation, "killer", or capturing move. X*/ X Xregister short s; Xunsigned short mv; Xstruct leaf *node; X X node = &Tree[TrPnt[ply+1]]; X ++TrPnt[ply+1]; X node->flags = node->reply = 0; X node->f = f; node->t = t; mv = (f<<8) + t; X if (f == 255 || t == 255) s = 100; X else X { X s = 0; X if (mv == PV) s = 150; X else if (mv == killr1[ply]) s = 90; X else if (mv == killr2[ply]) s = 70; X else if (mv == killr3[ply]) s = 50; X else if (mv == Swag1) s = 30; X else if (mv == Swag2) s = 20; X if (color[t] != neutral) X { X node->flags |= capture; X if (t == xkillr) s += 400; X if (atak[xside][t] == 0) s += value[board[t]]-board[f]; X else if (board[t] > board[f]) s += value[board[t]]-value[board[f]]; X else s += 15; X } X if (board[f] == pawn) X { X if (row[t] == 0 || row[t] == 7) node->flags |= promote; X else if (row[t] == 1 || row[t] == 6) node->flags |= pwnthrt; X else if (t == epsquare) node->flags |= epmask; X } X if (atak[xside][f] > 0) s += 15; X if (atak[xside][t] > 0) s -= 20; X if (InChk) X { X if (board[f] == king && atak[xside][t] == 0) s += 600; X if (mv == Qkillr[ply]) s += 100; X } X } X node->score = s-20000; X} X X XGenMoves(ply,loc,side,xside) Xshort ply,loc,side,xside; X X/* X Generate moves for a piece. The from square is mapped onto a 12 by X 12 board and offsets (taken from array Dir[]) are added to the X mapped location. Array unmap[] maps the move back onto array X board[] (yielding a value of -1 if the to square is off the board). X This process is repeated for bishops, rooks, and queens until a X piece is encountered or the the move falls off the board. Legal X moves are then linked into the tree. X*/ X X{ Xregister short m,u,d; Xshort i,m0,piece; X X piece = board[loc]; m0 = map[loc]; X if (sweep[piece]) X { X for (i = Dstart[piece]; i <= Dstop[piece]; i++) X { X d = Dir[i]; m = m0+d; u = unmap[m]; X while (u >= 0) X if (color[u] == neutral) X { X LinkMove(ply,loc,u,side,xside); X m += d; u = unmap[m]; X } X else if (color[u] == xside) X { X LinkMove(ply,loc,u,side,xside); X u = -1; X } X else u = -1; X } X } X else if (piece == pawn) X { X if (side == white && color[loc+8] == neutral) X { X LinkMove(ply,loc,loc+8,side,xside); X if (row[loc] == 1) X if (color[loc+16] == neutral) X LinkMove(ply,loc,loc+16,side,xside); X } X else if (side == black && color[loc-8] == neutral) X { X LinkMove(ply,loc,loc-8,side,xside); X if (row[loc] == 6) X if (color[loc-16] == neutral) X LinkMove(ply,loc,loc-16,side,xside); X } X for (i = Dstart[piece]; i <= Dstop[piece]; i++) X if ((u = unmap[m0+Dir[i]]) >= 0) X if (color[u] == xside || u == epsquare) X LinkMove(ply,loc,u,side,xside); X } X else X { X for (i = Dstart[piece]; i <= Dstop[piece]; i++) X if ((u = unmap[m0+Dir[i]]) >= 0) X if (color[u] != side) X LinkMove(ply,loc,u,side,xside); X } X} X X X XMoveList(side,ply) Xshort side,ply; X X/* X Fill the array Tree[] with all available moves for side to X play. Array TrPnt[ply] contains the index into Tree[] X of the first move at a ply. X*/ X X{ Xregister short i; Xshort ok,xside; X X xside = otherside[side]; X TrPnt[ply+1] = TrPnt[ply]; X Dstart[pawn] = Dstpwn[side]; Dstop[pawn] = Dstart[pawn] + 1; X for (i = 0; i <= PieceCnt[side]; i++) X GenMoves(ply,PieceList[side][i],side,xside); X if (kingmoved[side] == 0) X { X castle(side,255,0,0,&ok); X if (ok) LinkMove(ply,255,0,side,xside); X castle(side,0,255,0,&ok); X if (ok) LinkMove(ply,0,255,side,xside); X } X sort(TrPnt[ply],TrPnt[ply+1]-1); X} X X XMakeMove(side,node,tempb,tempc) Xshort side,*tempc,*tempb; Xstruct leaf *node; X X/* X Update Arrays board[], color[], and Index[] to reflect the new X board position obtained after making the move pointed to by X node. Also update miscellaneous stuff that changes when a move X is made. X*/ X X{ Xregister short f,t; Xshort ok,xside; X X xside = otherside[side]; X f = node->f; t = node->t; epsquare = -1; xkillr = t; X GameList[++GameCnt] = (f<<8) + t; X if (f == 255 || t == 255) X { X GamePc[GameCnt] = no_piece; GameClr[GameCnt] = neutral; X castle(side,f,t,1,&ok); X } X else X { X *tempc = color[t]; *tempb = board[t]; X GamePc[GameCnt] = *tempb; GameClr[GameCnt] = *tempc; X if (*tempc != neutral) X { X UpdatePieceList(*tempc,t,1); X if (*tempb == pawn) --PawnCnt[*tempc][col[t]]; X if (board[f] == pawn) X { X --PawnCnt[side][col[f]]; X ++PawnCnt[side][col[t]]; X } X mtl[xside] -= value[*tempb]; X if (*tempb == pawn) pmtl[xside] -= value[pawn]; X } X color[t] = color[f]; board[t] = board[f]; X Index[t] = Index[f]; PieceList[side][Index[t]] = t; X color[f] = neutral; board[f] = no_piece; X if (board[t] == pawn) X if (t-f == 16) epsquare = f+8; X else if (f-t == 16) epsquare = f-8; X if (node->flags & promote) X { X board[t] = queen; X mtl[side] += value[queen] - value[pawn]; X pmtl[side] -= value[pawn]; X } X if (board[t] == king) ++kingmoved[side]; X if (node->flags & epmask) en_passant(side,xside,f,t,1); X } X} X X XUnmakeMove(side,node,tempb,tempc) Xshort side,*tempc,*tempb; Xstruct leaf *node; X X/* X Take back the move pointed to by node. X*/ X X{ Xregister short f,t; Xshort ok,xside; X X xside = otherside[side]; X f = node->f; t = node->t; epsquare = -1; X GameCnt--; X if (f == 255 || t == 255) castle(side,f,t,2,&ok); X else X { X color[f] = color[t]; board[f] = board[t]; X Index[f] = Index[t]; PieceList[side][Index[f]] = f; X color[t] = *tempc; board[t] = *tempb; X if (*tempc != neutral) X { X UpdatePieceList(*tempc,t,2); X if (*tempb == pawn) ++PawnCnt[*tempc][col[t]]; X if (board[f] == pawn) X { X --PawnCnt[side][col[t]]; X ++PawnCnt[side][col[f]]; X } X mtl[xside] += value[*tempb]; X if (*tempb == pawn) pmtl[xside] += value[pawn]; X } X if (node->flags & promote) X { X board[f] = pawn; X mtl[side] += value[pawn] - value[queen]; X pmtl[side] += value[pawn]; X } X if (board[f] == king) --kingmoved[side]; X if (node->flags & epmask) en_passant(side,xside,f,t,2); X } X} X X XLinkCapture(ply,f,t,ck) Xshort ply,f,t,ck; X{ Xstruct leaf *node; X X node = &Tree[TrPnt[ply+1]]; X ++TrPnt[ply+1]; X node->flags = node->reply = 0; X node->f = f; node->t = t; X if (t == ykillr || t == ck) node->score = value[board[t]]-board[f]; X else node->score = value[board[t]]-value[board[f]]; X} X X XCaptureList(side,xside,ply) Xshort side,xside,ply; X X/* X Generate a list of captures similiarly to GenMoves. X*/ X X{ Xregister short m,u,d; Xshort i,j,m0,piece,ck,*aloc; X X ck = Ckillr[side] & 0x00FF; X TrPnt[ply+1] = TrPnt[ply]; X Dstart[pawn] = Dstpwn[side]; Dstop[pawn] = Dstart[pawn] + 1; X aloc = &PieceList[side][0]; X for (i = 0; i <= PieceCnt[side]; i++) X { X piece = board[*aloc]; m0 = map[*aloc]; X if (sweep[piece]) X for (j = Dstart[piece]; j <= Dstop[piece]; j++) X { X d = Dir[j]; m = m0+d; u = unmap[m]; X while (u >= 0) X if (color[u] == neutral) X { X m += d; u = unmap[m]; X } X else X { X if (color[u] == xside) LinkCapture(ply,*aloc,u,ck); X u = -1; X } X } X else X for (j = Dstart[piece]; j <= Dstop[piece]; j++) X if ((u = unmap[m0+Dir[j]]) >= 0) X if (color[u] == xside) LinkCapture(ply,*aloc,u,ck); X aloc++; X } X sort(TrPnt[ply],TrPnt[ply+1]-1); X} X X Xdistance(a,b) Xshort a,b; X{ Xshort d1,d2; X X d1 = col[a]-col[b]; if (d1 < 0) d1 = -d1; X d2 = row[a]-row[b]; if (d2 < 0) d2 = -d2; X if (d1 > d2) return(d1); else return(d2); X} X X XScorePosition(side,score) Xshort side,*score; X X/* X Calculate a positional score for each piece as follows: X pawns: X material value : 100 pts X d,e file, not moved: -10 pts X & also blocked: -10 pts X doubled : -12 pts (each pawn) X isolated : -24 pts X backward : -8 pts X & attacked : -6 pts X passed : depends on rank, material balance, X position of opponents king, blocked X knights: X material value : 330 pts X centre proximity : array pknight X bishops: X material value : 330 pts X discourage edges : array pbishop X mobility : +2 pts per move X rooks: X material value : 500 pts X mobility : +2 pts per move X open file : +12 pts X half open : +6 pts X queen: X material value : 950 pts X king: X castled : ~ +10 pts (depends on material) X king moved : ~ -15 pts (depends on material) X adjacent pawn : +5 pts before endgame X attacks to : -5 pts each if more than 1 attack X adjacent square before endgame X pawn missing from : -10 pts before endgame X adjacent column X centre proximity : -2 pts before endgame, during endgame X switches to a bonus for center proximity X dependent on opponents control of adjacent X squares X X "hung" pieces : -8 (1 hung piece) X -24 (more than 1) X*/ X X{ Xregister short i,j,a; Xshort loc,e,m0,u,piece,wking,bking,cwking,cbking; Xshort r,db,dw,s,stage1,stage2,c1,c2,a1,a2; Xshort pscore[3],xside,rank,column,in_square; X X xside = otherside[side]; X pscore[white] = pscore[black] = 0; X emtl[white] = mtl[white] - pmtl[white] - value[king]; X emtl[black] = mtl[black] - pmtl[black] - value[king]; X wking = PieceList[white][0]; bking = PieceList[black][0]; X cwking = col[wking]; cbking = col[bking]; X stage1 = 10 - (emtl[white]+emtl[black]) / 670; X stage2 = (stage1*stage1) / 10; X X for (c1 = white; c1 <= black; c1++) X { X c2 = otherside[c1]; X for (i = 0; i <= PieceCnt[c1]; i++) X { X loc = PieceList[c1][i]; piece = board[loc]; X a1 = atak[c1][loc]; a2 = atak[c2][loc]; X rank = row[loc]; column = col[loc]; X s = svalue[loc]; X X if (piece == pawn && c1 == white) X { X if (column == 3 || column == 4) X if (rank == 1) X { X s -= 10; X if (color[loc+8] == white) s -=10; X } X else if (rank == 4 && a1 == pawn) s += 8; X if (column-cwking > 1 || cwking-column > 1) s += stage1*rank; X if (PawnCnt[white][column] > 1) s -= 12; X if (column > 0 && PawnCnt[white][column-1] == 0 && X column < 7 && PawnCnt[white][column+1] == 0) s -= 24; X if (a1 != pawn && atak[c1][loc+8] != pawn) X { X s -= 8; X if (a2 > 0) s -= 6; X } X if (PawnCnt[black][column] == 0) X { X dw = distance(loc,wking); X db = distance(loc,bking); X s += stage2*(db-dw); X if (side == white) r = rank-1; else r = rank; X if (row[bking] >= r && db < 8-r) in_square = true; X else in_square = false; X e = 0; X for (a = loc+8; a < 64; a += 8) X if (atak[black][a] == pawn) a = 99; X else if (atak[black][a] > 0 || color[a] != neutral) e = 1; X if (a == 99) s += stage1*passed_pawn3[rank]; X else if (in_square || e == 1) s += stage1*passed_pawn2[rank]; X else s += stage1*passed_pawn1[rank]; X } X } X else if (piece == pawn && c1 == black) X { X if (column == 3 || column == 4) X if (rank == 6) X { X s -= 10; X if (color[loc-8] == black) s -= 10; X } X else if (rank == 3 && a1 == pawn) s += 8; X if (column-cbking > 1 || cbking-column > 1) s += stage1*(7-rank); X if (PawnCnt[black][column] > 1) s -= 12; X if (column > 0 && PawnCnt[black][column-1] == 0 && X column < 7 && PawnCnt[black][column+1] == 0) s -= 24; X if (a1 != pawn && atak[c1][loc-8] != pawn) X { X s -= 8; X if (a2 > 0) s -= 6; X } X if (PawnCnt[white][column] == 0) X { X dw = distance(loc,wking); X db = distance(loc,bking); X s += stage2*(dw-db); X if (side == black) r = rank+1; else r = rank; X if (row[wking] <= r && dw < r+1) in_square = true; X else in_square = false; X e = 0; X for (a = loc-8; a >= 0 ; a -= 8) X if (atak[white][a] == pawn) a = -99; X else if (atak[white][a] > 0 || color[a] != neutral) e = 1; X if (a == -99) s += stage1*passed_pawn3[7-rank]; X else if (in_square || e == 1) s += stage1*passed_pawn2[7-rank]; X else s += stage1*passed_pawn1[7-rank]; X } X } X else if (piece == knight) X { X s = pknight[loc]; X } X else if (piece == bishop) X { X s += pbishop[loc]; X } X else if (piece == rook) X { X if (PawnCnt[white][column] == 0) s += 6; X if (PawnCnt[black][column] == 0) s += 6; X } X else if (piece == queen) X { X s = s/3; X } X else if (piece == king) X { X m0 = map[loc]; X if (castld[c1]) s += (20/(stage1+1)); X else if (kingmoved[c1] > 0) s -= (30/(stage1+1)); X if (emtl[c1] > 1300) X { X s -= 2*edge[loc]; a = 0; X for (j = Dstart[king]; j <= Dstop[king]; j++) X if ((u = unmap[m0+Dir[j]]) >= 0) X { X if (atak[c2][u] > 0) a++; X if (board[u] == pawn) s += 5; X } X if (a > 1) s -= 5*a; X if (column > 0 && PawnCnt[c1][column-1] == 0) s -= 10; X if (column < 7 && PawnCnt[c1][column+1] == 0) s -= 10; X if (PawnCnt[c1][column] == 0) s -= 12; X } X else X { X e = edge[loc]; X for (j = Dstart[king]; j <= Dstop[king]; j++) X if ((u=unmap[m0+Dir[j]]) >= 0) X if (atak[c2][u] == 0) e += edge[u]; X s += (e*((1300-emtl[c1])/100))/8; X } X if (mtl[c1]<1000 && mtl[c2]<1990 && distance(wking,bking)==2 X && e<12) s -= 30; X } X if (a2 > 0 && (a1 == 0 || a2 < piece)) ++hung[c1]; X if (a2 > 0) s -= 3; X pscore[c1] += s; svalue[loc] = s; X } X } X if (hung[side] > 1) pscore[side] -= 12; X if (hung[xside] == 1) pscore[xside] -= 8; X if (hung[xside] > 1) pscore[xside] -= 24; X *score = mtl[side] - mtl[xside] + pscore[side] - pscore[xside] - 5; X if (*score > 0 && pmtl[side] == 0 && emtl[side] <= value[bishop]) X *score = 0; X if (*score < 0 && pmtl[xside] == 0 && emtl[xside] <= value[bishop]) X *score = 0; X} X X XCaptureSearch(side,xside,ply,depth,alpha,beta,qscore,best,bstline) Xshort side,xside,ply,depth,alpha,beta,qscore,*best; Xunsigned short bstline[]; X X/* X Perform alpha-beta search on captures up to 9 ply past X nominal search depth. X*/ X X{ Xregister short j,f,t; Xshort v,q,pnt,tempb,tempc,pbst,sv; Xunsigned short nxtline[30]; Xstruct leaf *node; X X *best = -qscore; bstline[ply] = 0; X CaptureList(side,xside,ply); X pnt = TrPnt[ply]; pbst = 0; X while (pnt < TrPnt[ply+1] && *best <= beta) X { X node = &Tree[pnt]; pnt++; X f = node->f; t = node->t; X v = value[board[t]]-qscore+svalue[t]; X if (v > alpha) X { X if (board[t] == king) node->score = 10000; X else if (depth == 1) node->score = v; X else X { X ykillr = t; NodeCnt++; X sv = svalue[t]; svalue[t] = svalue[f]; X tempb = board[t]; tempc = color[t]; X UpdatePieceList(tempc,t,1); X board[t] = board[f]; color[t] = color[f]; X Index[t] = Index[f]; PieceList[side][Index[t]] = t; X board[f] = no_piece; color[f] = neutral; X CaptureSearch(xside,side,ply+1,depth-1,-beta,-alpha,v, X &q,nxtline); X node->score = -q; X board[f] = board[t]; color[f] = color[t]; X Index[f] = Index[t]; PieceList[side][Index[f]] = f; X board[t] = tempb; color[t] = tempc; X UpdatePieceList(xside,t,2); X svalue[f] = svalue[t]; svalue[t] = sv; X } X if (node->score > *best) X { X pbst = pnt; X *best = node->score; X if (*best > alpha) alpha = *best; X for (j = ply; j < 30; j++) bstline[j] = nxtline[j]; X bstline[ply] = (f<<8) + t; X } X } X } X if (pbst == 0) Ckillr[side] = -1; X else Ckillr[side] = (Tree[pbst].f<<8) + Tree[pbst].t; X} X X Xexpand(side,node,depth,ply,alpha,beta,nxtline) Xshort side,depth,alpha,beta,ply; Xunsigned short nxtline[]; Xstruct leaf *node; X X/* X Generate a score for current position by calling search routine X to generate opponents best response. X*/ X X{ Xshort s,xside; Xstruct leaf *reply; X X xside = otherside[side]; X nxtline[ply] = (node->f<<8) + node->t; X nxtline[ply+1] = node->reply; X search(xside,ply+1,depth-1,-beta,-alpha,nxtline); X if (!timeout) X { X reply = &Tree[TrPnt[ply+1]]; X s = -reply->score; X if (s >= alpha && s <= beta) node->score = s; X else if (s < alpha && s < node->score) node->score = s; X else if (s > beta && s > node->score) node->score = s; X if ((reply->flags & incheck) && !(node->flags & check)) X { X node->flags |= draw; node->score = 0; X } X if ((node->flags & draw) || (node->score <= -9000) || X (node->score >= 9000)) node->flags |= exact; X node->reply = nxtline[ply+1]; X } X} X X Xevaluate(side,node,ply,depth,alpha,beta,nxtline) Xshort side,ply,alpha,beta; Xunsigned short nxtline[]; Xstruct leaf *node; X X/* X See if either king is in check. If positional score estimate X passed forward from previous ply warrants, score the position. X If positional score is greater than alpha, perform CaptureSearch X to modify score based on ensuing capture sequence. X*/ X X{ Xshort xside,s,x,t; X X hung[white] = hung[black] = 0; X xside = otherside[side]; X ataks(xside,atak[xside]); X if (atak[xside][PieceList[side][0]] > 0) X { X node->score = ply-10000; X node->flags |= incheck; X node->flags |= exact; X } X else X { X ataks(side,atak[side]); X if (atak[side][PieceList[xside][0]]) node->flags |= check; X if (ply > Sdepth) t = 0; else t = 90; X s = -PPscore[ply-1]+mtl[side]-mtl[xside]; X if (s+t > alpha || (node->flags & check) || X (node->flags & pwnthrt)) ScorePosition(side,&s); X PPscore[ply] = s-mtl[side]+mtl[xside]; X if (s < alpha || depth > 1) X { X if (node->score < -12000) node->score = s; X } X else X { X ykillr = xkillr; X CaptureSearch(xside,side,ply+1,9,-s-1,-alpha,s,&x,nxtline); X node->score = -x; X node->reply = nxtline[ply+1]; X } X repetition(node); X } X} X X Xsearch(side,ply,depth,alpha,beta,bstline) Xshort side,ply,depth,alpha,beta; Xunsigned short bstline[]; X X/* X Perform the main alpha-beta search. Extensions up to 3 ply X beyond the nominal iterative search depth MAY occur for checks, X check evasions, pawn promotion threats, and threats to multiple X pieces. X*/ X X{ Xregister short j; Xshort best,tempb,tempc,xside,pnt,pbst,hhh,d; Xunsigned short mv,nxtline[30]; Xstruct leaf *node; X X xside = otherside[side]; X if (ply == 1) InChk = false; else InChk = ChkFlag[ply-1]; X PV = bstline[ply]; X if (ply < 3) X { X Swag1 = Swag2 = 0; X } X else X { X Swag1 = (Tree[TrPnt[ply-2]].f<<8) + Tree[TrPnt[ply-2]].t; X Swag2 = (Tree[TrPnt[ply-2]+1].f<<8) + Tree[TrPnt[ply-2]+1].t; X } X if (ply > 1) MoveList(side,ply); X best = -12000; PPscore[ply] = -PPscore[ply-1]; X pnt = TrPnt[ply]; pbst = pnt; X while (pnt < TrPnt[ply+1] && best<=beta && !timeout) X { X node = &Tree[pnt]; NodeCnt++; X nxtline[ply+1] = 0; X if (ply == 1) X { X d = node->score-best; X if (pnt == TrPnt[ply]) extra_time = 0; X else if (d < -50) extra_time = -response_time/3; X else if (d < 20) extra_time = 0; X else if (d < 60) extra_time = response_time/3; X else if (d < 200) extra_time = response_time; X else extra_time = 2*response_time; X } X if (node->flags & capture) CptrFlag[ply] = true; X else CptrFlag[ply] = false; X if (node->flags & pwnthrt) PawnThreat[ply] = true; X else PawnThreat[ply] = false; X if (ply == 1 && post) X { X algbrnot(node->f,node->t); X gotoXY(50,2); printw("%5s",mvstr1,' '); ClrEoln(); X } X if ((node->flags & exact) == 0) X { X MakeMove(side,node,&tempb,&tempc); X evaluate(side,node,ply,depth,alpha,beta,nxtline); X if (hung[xside] > 1 && ply <= Sdepth) hhh = true; X else hhh = false; X if (node->flags & check) ChkFlag[ply] = true; X else ChkFlag[ply] = false; X if ((node->flags & exact) == 0) X { X if (depth > 1) expand(side,node,depth,ply,alpha,beta,nxtline); X if (node->score <= beta && (PawnThreat[ply] || X ((ChkFlag[ply] || hhh) && depth == 1))) X expand(side,node,depth+1,ply,alpha,beta,nxtline); X else if ((ChkFlag[ply-1] || PawnThreat[ply-1]) && X ply<=Sdepth+2 && Sdepth>1 && X (ply>Sdepth || CptrFlag[ply-1] || X (ply>3 && (ChkFlag[ply-3] || CptrFlag[ply-3])) || X (hung[side] > 1))) X expand(side,node,depth+1,ply,alpha,beta,nxtline); X } X UnmakeMove(side,node,&tempb,&tempc); X } X if (node->score > best && !timeout) X { X if (ply == 1 && depth > 1 && node->score>alpha && X (node->flags & exact) == 0) node->score += 5; X best = node->score; pbst = pnt; X if (best > alpha) alpha = best; X for (j = ply; j < 30; j++) bstline[j] = nxtline[j]; X bstline[ply] = (node->f<<8) + node->t; X if (ply == 1 && post) post_move(node); X } X if ((pnt % 5) == 0) ElapsedTime(0); X pnt++; X if (best > 9000) beta = 0; X } X if (timeout) pnt--; X if (ply == 1) sort(TrPnt[ply],pnt-1); X else Tree[TrPnt[ply]] = Tree[pbst]; X node = &Tree[TrPnt[ply]]; X mv = (node->f<<8) + node->t; X if (node->t != (GameList[GameCnt] & 0x00FF)) X if (best > beta) killr1[ply] = mv; X else if (mv != killr2[ply]) X { X killr3[ply] = killr2[ply]; X killr2[ply] = mv; X } X if (InChk && best > -9000) Qkillr[ply] = mv; X} X END_OF_chess.c if test 47675 -ne `wc -c <chess.c`; then echo shar: \"chess.c\" unpacked with wrong size! fi # end of overwriting check fi if test -f chess.opn -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"chess.opn\" else echo shar: Extracting \"chess.opn\" \(9500 characters\) sed "s/^X//" >chess.opn <<'END_OF_chess.opn' XFour Knight's Game Xe2e4 e7e5 Xg1f3 b8c6 Xb1c3 g8f6 Xf1b5 f8b4 Xo-o o-o Xd2d3 b4c3 Xb2c3 d7d6 Xc1g5 d8e7 Xf1e1 c6d8 Xd3d4 d8e6 X! XGiuoco Piano Xe2e4 e7e5 Xg1f3 b8c6 Xf1c4 f8c5 Xc2c3 g8f6 Xd2d4 e5d4 Xc3d4 c5b4 Xb1c3 f6e4 Xo-o b4c3 X! XGiuoco Piano Xe2e4 e7e5 Xg1f3 b8c6 Xf1c4 f8c5 Xd2d3 g8f6 Xb1c3 d7d6 Xc1g5 h7h6 Xg5f6 d8f6 Xc3d5 f6d8 X! XTwo Knights Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1c4 g8f6 Xf3g5 d7d5 Xe4d5 c6a5 Xc4b5 c7c6 Xd5c6 b7c6 Xb5e2 h7h6 X! XTwo Knights Defence -- Max Lange Attack Xe2e4 e7e5 Xg1f3 b8c6 Xf1c4 g8f6 Xd2d4 e5d4 Xo-o f8c5 Xe4e5 d7d5 Xe5f6 d5c4 Xf6g7 h8g8 X! XPetrov's Defence Xe2e4 e7e5 Xg1f3 g8f6 Xf3e5 d7d6 Xe5f3 f6e4 Xd2d4 d6d5 Xf1d3 f8d6 Xo-o o-o Xc2c4 c8g4 Xc4d5 f7f5 Xb1c3 b8d7 X! XPetrov's Defence Xe2e4 e7e5 Xg1f3 g8f6 Xd2d4 e5d4 Xe4e5 f6e4 Xd1d4 d7d5 X! XVienna Game Xe2e4 e7e5 Xb1c3 g8f6 Xf1c4 b8c6 Xd2d3 f8b4 Xc1g5 h7h6 Xg5f6 b4c3 Xb2c3 d8f6 Xg1e2 d7d6 X! XVienna Game Xe2e4 e7e5 Xb1c3 f8c5 Xg1f3 d7d6 Xd2d4 e5d4 Xf3d4 g8f6 Xc1g5 h7h6 Xg5h4 b1c3 X! XThree Knights Game Xe2e4 e7e5 Xb1c3 b8c6 Xg1f3 g7g6 Xd2d4 e5d4 Xc3d5 f8g7 Xc1g5 c6e7 Xf3d4 c7c6 Xd5c3 h7h6 X! XBishop's Opening Xe2e4 e7e5 Xf1c4 g8f6 Xd2d4 e5d4 Xg1f3 f6e4 Xd1d4 e4c5 Xo-o c5e6 Xf1e1 c7c6 Xb1c3 d7d5 Xc4d3 f8e7 X! XRuy Lopez -- Classical Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 f8c5 Xc2c3 g8f6 Xd2d4 e5d4 Xe4e5 f6e4 Xo-o d7d5 X! XRuy Lopez -- Birds Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 c6d4 Xb5a4 f8c5 Xo-o d4f3 Xd1f3 g8e7 Xd2d3 o-o Xc1e3 c5b6 Xb1c3 d7d6 X! XRuy Lopez -- Schliemann Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 f7f5 Xb1c3 f5e4 Xc3e4 d7d5 Xf3e5 d5e4 Xe5c6 d8d5 Xc2c4 d5d6 Xc6a7 c8d7 X! XRuy Lopez -- Old Steinitz Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 d7d6 Xd2d4 c8d7 Xb1c3 g8f6 Xo-o f8e7 Xf1e1 e5d4 Xf3d4 o-o Xd4f5 f8e8 X! XRuy Lopez -- Old Steinitz Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 d7d6 Xd2d4 c8d7 Xb1c3 g8f6 Xb5c6 d7c6 Xd1d3 e5d4 Xf3d4 f8e7 Xc1g5 c6d7 X! XRuy Lopez -- Modern Steinitz Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 a7a6 Xb5a4 d7d6 Xd2d4 b7b5 Xa4b3 c6d4 Xf3d4 e5d4 Xc2c3 d4c3 Xb1c3 c8b7 X! XRuy Lopez -- Open Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 a7a6 Xb5a4 g8f6 Xo-o f6e4 Xd2d4 b7b5 Xa4b3 d7d5 Xd4e5 c8e6 Xc2c3 f8c5 Xb1d2 o-o X! XRuy Lopez -- Open Defence Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 a7a6 Xb5a4 g8f6 Xo-o f8e7 Xf1e1 b7b5 Xa4b3 d7d6 Xc2c3 o-o Xh2h3 c6a5 Xb3c2 c2c4 Xd2d4 d8c7 X! XRuy Lopez Xe2e4 e7e5 Xg1f3 b8c6 Xf1b5 a7a6 Xb5c6 d7c6 Xd2d4 e5d4 Xd1d4 d8d4 Xf3d4 c8d7 Xc1e3 o-o-o Xb1d2 g8e7 X! XScotch Game Xe2e4 e7e5 Xg1f3 b8c6 Xd2d4 e5d4 Xf3d4 f8c5 Xc1e3 d8f6 Xc2c3 g8e7 Xb1d2 d7d6 Xe3c5 d6c5 X! XPhilidor's Defence Xe2e4 e7e5 Xg1f3 d7d6 Xd2d4 g8f6 Xb8c6 b1d2 Xf8c5 f1e2 Xo-o o-o Xd1e2 c7c6 X! XAlekhine's Defence Xe2e4 g8f6 Xe4e5 f6d5 Xc2c4 d5b6 Xd2d4 d7d6 Xf2f4 d6e5 Xf4e5 b8c6 Xc1e3 c8f5 Xb1c3 e7e6 Xg1f3 f8e7 X! XAlekhine's Defence Xe2e4 g8f6 Xe4e5 f6d5 Xd2d4 d7d6 Xg1f3 c8g4 Xf1e2 e7e6 Xo-o f8e7 Xh2h3 g4h5 Xc2c4 d5b6 X! XKings Gambit Accepted Xe2e4 e7e5 Xf2f4 e5f4 Xg1f3 d7d6 Xf1c4 h7h6 Xd2d4 g7g5 Xo-o f8g7 Xc2c3 b8c6 Xd1b3 d8e7 X! XPonziani's Opening Xe2e4 e7e5 Xg1f3 b8c6 Xc2c3 d7d5 Xd1a4 g8f6 Xf3e5 f8d6 Xe5c6 b7c6 Xd2d3 o-o Xc1g5 h7h6 X! XCaro-Kann Defence Xe2e4 c7c6 Xd2d4 d7d5 Xe4d5 c6d5 Xc2c4 g8f6 Xb1c3 b8c6 Xc1g5 e7e6 Xc4c5 f8e7 Xf1b5 o-o Xg1f3 f6e4 X! XCaro-Kann Defence Xe2e4 c7c6 Xd2d4 d7d5 Xe4e5 c8f5 Xf1d3 f5d3 Xd1d3 e7e6 Xb1c3 d8b6 Xb1d2 c6c5 Xd4c5 f8c5 X! XCaro-Kann Defence Xe2e4 c7c6 Xb1c3 d7d5 Xg1f3 c8g4 Xh2h3 g4f3 Xd1f3 e7e6 Xd2d4 g8f6 Xf1d3 d5e4 Xc3e4 d8d4 Xc2c3 d4d8 X! XFrench Defence -- Classical Xe2e4 e7e6 Xd2d4 d7d5 Xb1c3 g8f6 Xc1g5 f8e7 Xe4e5 f6d7 Xg5e7 d8e7 Xd1d2 o-o Xf2f4 c7c5 Xg1f3 b8c6 Xo-o-o c5c4 X! XFrench Defence -- MacCutcheon Xe2e4 e7e6 Xd2d4 d7d5 Xb1c3 g8f6 Xc1g5 c8g4 Xe4e5 h7h6 Xg5d2 g4f3 Xg2f3 f6e4 Xd1g4 e8f8 Xh2h4 c7c5 X! XFrench Defence -- Rubenstein Xe2e4 e7e6 Xd2d4 d7d5 Xb1c3 d5e4 Xc3e4 b8d7 Xg1f3 g8f6 Xe4f6 d7f6 Xf1d3 b7b6 Xd1e2 c8b7 Xc1g5 f8e7 X! XFrench Defence -- Winawer Xe2e4 e7e6 Xd2d4 d7d5 Xb1c3 f8b4 Xe4e5 c7c5 Xa2a3 b4c3 Xb2c3 b8d7 Xd1g4 o-o Xg1f3 b8c6 Xf1e3 f7f5 X! XFrench Defence -- Tarrasch Xe2e4 e7e6 Xd2d4 d7d5 Xb1d2 b8c6 Xg1f3 g8f6 Xe4e5 f6d7 Xd2b3 f7f6 Xf1b5 f8e7 Xc1f4 o-o X! XSicilian Defence -- Dragon Variation Xe2e4 c7c5 Xg1f3 b8c6 Xd2d4 c5d4 Xf3d4 g8f6 Xb1c3 d7d6 Xf1e2 g7g6 Xc1e3 f8g7 Xo-o o-o Xd4b3 c8e6 Xf2f4 c6a5 Xf4f5 e6c4 X! XSicilian Defence -- Dragon Variation Xe2e4 c7c5 Xg1f3 b8c6 Xd2d4 c5d4 Xf3d4 g7g6 Xb1c3 f8g7 Xc1e3 g8f6 Xf1c4 o-o X! XSicilian Defence -- Boleslavsky Variation Xe2e4 c7c5 Xg1f3 b8c6 Xd2d4 c5d4 Xf3d4 g8f6 Xb1c3 d7d6 Xf1e2 e7e5 Xd4b3 f8e7 Xo-o o-o Xc1e3 c8e6 X! XSicilian Defence -- Najdorf Xe2e4 c7c5 Xg1f3 d7d6 Xd2d4 c5d4 Xf3d4 g8f6 Xb1c3 a7a6 Xc1g5 e7e6 Xd1d2 f8e7 Xo-o-o o-o X! XSicilian Defence -- Najdorf Xe2e4 c7c5 Xg1f3 d7d6 Xd2d4 c5d4 Xf3d4 g8f6 Xb1c3 a7a6 Xf1e2 e7e5 Xd4b3 f8e7 Xo-o o-o Xf2f4 b7b5 Xa2a3 c8b7 X! XSicilian Defence -- Najdorf Xe2e4 c7c5 Xg1f3 d7d6 Xd2d4 c5d4 Xf3d4 g8f6 Xb1c3 a7a6 Xg2g3 e7e5 Xd4e2 c8e6 Xf1g2 b7b5 Xo-o b8d7 X! XSicilian Defence -- Closed Xe2e4 c7c5 Xb1c3 b8c6 Xg2g3 g7g6 Xf1g2 f8g7 Xd2d3 e7e6 Xc1e3 d7d6 Xg1e2 c6d4 Xd1d2 d8h4 Xo-o g8d7 X! XNimzowitsch Defence Xe2e4 b8c6 Xd2d4 d7d5 Xe4e5 f7f6 Xg1f3 c1g4 Xf1e2 e7e6 Xe5f6 g8f6 Xc2c3 f8d6 Xc1g5 d8d7 X! XQueens Gambit Accepted Xd2d4 d7d5 Xc2c4 d5c4 Xg1f3 g8f6 Xe2e3 e7e6 Xf1c4 c7c5 Xo-o a7a6 Xd1e2 b7b5 Xc4d3 c5d4 Xe3d4 b8c6 X! XQueens Gambit -- Catalan Xd2d4 d7d5 Xc2c4 e7e6 Xg2g3 g8f6 Xg1f3 f8e7 Xf1g2 o-o Xo-o f6d7 Xd1c2 c7c6 Xb1d2 b7b6 Xe2e4 c8b7 Xb2b3 a8c8 X! XQueens Gambit Declined -- Orthodox Xd2d4 d7d5 Xc2c4 e7e6 Xb1c3 g8f6 Xc1g5 f8e7 Xe2e3 o-o Xg1f3 b8d7 Xa1c1 c7c6 Xf8d3 d5c4 Xf1c4 f6d5 X! XQueens Gambit Declined -- Cambridge Springs Xd2d4 d7d5 Xc2c4 e7e6 Xb1c3 g8f6 Xc1g5 b8d7 Xe2e3 c7c6 Xg1f3 d8a5 Xf3d2 f8b4 Xd1c2 o-o Xg5h4 c6c5 X! XQueens Gambit Declined -- Exchange Var. Xd2d4 d7d5 Xc2c4 e7e6 Xb1c3 g8f6 Xc1g5 b8d7 Xc4d5 e6d5 Xe2e3 c7c6 Xf1d3 f8e7 Xd1c2 o-o Xg1e2 f8e8 X! XQueens Gambit Declined -- Semi-Tarrasch Xd2d4 d7d5 Xc2c4 e7e6 Xb1c3 g8f6 Xg1f3 c7c5 Xc4d5 c5d4 Xd1d4 e6d5 Xe2e4 b8c6 Xf1b5 f6e4 X! XQueens Gambit Declined -- Tarrasch Xd2d4 d7d5 Xc2c4 e7e6 Xb1c3 c7c5 Xc4d5 e6d5 Xg1f3 b8c6 Xg2g3 g8f6 Xf1g2 f8e7 Xo-o o-o X! XQueens Gambit Declined -- Vienna Xd2d4 d7d5 Xc2c4 e7e6 Xg1f3 g8f6 Xf1b5 f8b4 Xb1c3 d5c4 Xe2e4 c7c5 Xe4e5 c5d4 Xd1a4 b8c6 Xo-o-o c1d2 X! XQueens Gambit Declined -- Slav (Marshall Gambit) Xd2d4 d7d5 Xc2c4 c7c6 Xb1c3 e7e6 Xe2e4 d4e4 Xc3e4 f8b4 Xc1d2 d8d4 Xd2b4 d4e4 Xf1e2 b8a6 Xb4d6 b7b6 X! XQueens Gambit --Slav (Krause) Xd2d4 d7d5 Xc2c4 c7c6 Xg1f3 g8f6 Xb1c3 d5c4 Xa2a4 c8f5 Xf3e5 e7e6 Xf2f3 f8b4 Xc1g5 h7h6 Xg5f6 d8f6 Xe2e4 f5h7 X! XModern Benoni Counter Gambit Xd2d4 g8f6 Xc2c4 c7c5 Xd4d5 e7e6 Xb1c3 e6d5 Xc4d5 d7d6 Xe2e4 g7g6 Xf1d3 f8g7 Xg1e2 o-o Xo-o a7a6 Xa2a4 d8c7 X! XQueens Pawn Game Xd2d4 d7d5 Xg1f3 g8f6 Xc1f4 c7c5 Xe2e3 b8c6 Xc2c3 d8b6 Xd1c1 c8f5 Xd4c5 b6c5 Xb1d2 a8c8 Xf3d4 c6d4 Xe3d4 c5b6 X! XPirc-Robatsch Defence Xd2d4 d7d6 Xe2e4 g8f6 Xb1c3 g7g6 Xc1g5 f8g7 Xd1d2 b8d7 Xo-o-o e7e5 Xd4e5 d6e5 Xg1f3 h7h6 Xg5h4 g6g5 Xh4g3 d8e7 X! XPirc-Robatsch Defence Xd2d4 d7d6 Xe2e4 g8f6 Xb1c3 g7g6 Xf1c4 c7c6 Xd1e2 f8g7 Xg1f3 o-o Xc1g5 b7b5 Xc4d3 d8c7 X! XQueens Indian Defence Xd2d4 g8f6 Xc2c4 e7e6 Xg1f3 b7b6 Xg2g3 c8b7 Xf1g2 f8e7 Xo-o o-o Xb1c3 f6e4 Xd1c2 e4c3 Xc2c3 d7d6 Xc3c2 f7f5 X! XQueens Indian Defence Xd2d4 g8f6 Xc2c4 e7e6 Xg1f3 b7b6 Xe2e3 c8b7 Xf1d3 f8e7 Xb1c3 d7d5 Xo-o o-o Xd1e2 b8d7 X! XNimzo-Indian Defence Xd2d4 g8f6 Xc2c4 e7e6 Xb1c3 f8b4 Xd1c2 d7d5 Xa2a3 b4c3 Xc2c3 b8c6 Xg1f3 f6e4 Xc3b3 c6a5 Xb3a4 c7c6 X! XNimzo-Indian Defence (Rubenstein) Xd2d4 g8f6 Xc2c4 e7e6 Xb1c3 f8b4 Xe2e3 o-o Xf1d3 d7d5 Xg1f3 c7c5 Xo-o b8c6 Xa2a3 b4c3 Xb2c3 d5c4 Xd3c4 d8c7 X! XNimzo-Indian Defence -- Samisch Xd2d4 g8f6 Xc2c4 e7e6 Xb1c3 f8b4 Xa2a3 b4c3 Xb2c3 o-o Xf2f3 d7d5 Xc4d5 e6d5 Xe2e3 c8f5 Xg1e2 b8d7 Xe2g3 f5g6 X! XNimzo-Indian Defence Xd2d4 g8f6 Xc2c4 e7e6 Xb1c3 f8b4 Xc1d2 o-o Xe2e3 d7d5 Xg1f3 c7c5 Xa2a3 b4c3 Xd2c3 f6e4 Xa1c1 e4c3 Xc1c3 c5d4 X! XGrunfeld Defence Xd2d4 g8f6 Xc2c4 g7g6 Xb1c3 d7d5 Xc4d5 f6d5 Xe2e4 d5c3 Xb2c3 c7c5 Xf1c4 f8g7 Xg1e2 o-o Xo-o c5d4 Xc3d4 b8c6 X! XGrunfeld Defence -- Smyslov Xd2d4 g8f6 Xc2c4 g7g6 Xb1c3 d7d5 Xg1f3 f8g7 Xd1b3 d5c4 Xb3c4 o-o Xe2e4 c8g4 Xc1e3 f6d7 Xo-o-o b8c6 X! XGrunfeld Defence Xd2d4 g8f6 Xc2c4 g7g6 Xb1c3 d7d5 Xc1f4 f8g7 Xd2d3 o-o Xc4d5 f6d5 Xc3d5 d8d5 Xf4c7 b8c6 X! XKings Indian Defence -- Classical Xd2d4 g8f6 Xc2c4 g7g6 Xb1c3 f8g7 Xe2e4 d7d6 Xg1f3 o-o Xf1e2 e7e5 Xo-o b8c6 Xc1e3 f8e8 Xd4e5 d6e5 X! XKings Indian Defence -- 4 pawns attack Xd2d4 g8f6 Xc2c4 g7g6 Xb1c3 f8g7 Xe2e4 d7d6 Xf2f4 c7c5 Xg1f3 o-o Xd4d5 e7e6 Xf1d3 e6d5 Xc4d5 d8b6 X! XKings Indian Defence -- Samisch Xd2d4 g8f6 Xc2c4 g7g6 Xb1c3 f8g7 Xe2e4 d7d6 Xf2f3 o-o Xc1e3 e7e5 Xd4d5 c7c6 Xg1e2 c6d5 Xc3d5 f6d5 X! XKings Indian Defence -- Main Line Xd2d4 g8f6 Xc2c4 g7g6 Xg2g3 f8g7 Xf1g2 o-o Xb1c3 d7d6 Xg1f3 b8d7 Xo-o e7e5 Xe2e4 c7c6 Xh2h3 d8b6 X! XKings Indian Defence Xd2d4 g8f6 Xc2c4 g7g6 Xb1c3 f8g7 Xg1f3 o-o Xc1f4 d7d6 Xh2h3 b8d7 Xe2e3 c7c6 X! XDutch Defence Xd2d4 f7f5 Xg2g3 e7e6 Xf1g2 g8f6 Xg1f3 f8e7 Xo-o o-o Xc2c4 d7d6 Xb1c3 d8e8 Xd1c2 e8h5 Xb2b3 b8c6 Xc1a3 a7a5 X! XEnglish Opening Xc2c4 e7e5 Xb1c3 g8f6 Xg1f3 b8c6 Xe2e4 f8b4 Xd2d3 d7d6 Xf1e2 o-o Xo-o b4c3 Xb2c3 d8e7 X! XEnglish Opening Xc2c4 g8f6 Xb1c3 d7d5 Xc4d5 f6d5 Xe2e4 d5f4 Xf1c4 c8e6 Xc4e6 f7e6 X! XEnglish Opening Xc2c4 e7e5 Xb1c3 g8f6 Xg1f3 b8c6 Xg2g3 d7d5 Xc4d5 f6d5 Xf1g2 d5b6 Xo-o f8e7 Xd2d3 o-o Xc1e3 f7f5 X! XReti -- Accepted Xg1f3 d7d5 Xc2c4 d5c4 Xe2e3 c7c5 Xf1c4 e7e6 Xo-o g8f6 Xb2b3 b8c6 Xc1b2 a7a6 Xa2a4 f8e7 X! XReti -- Neo Catalan Xg1f3 d7d5 Xc2c4 e7e6 Xg2g3 g8f6 Xf1g2 f8e7 Xo-o o-o Xb2b3 c7c5 Xc4d5 f6d5 Xc1b2 b8c6 Xd2d4 b7b6 Xb1c3 d5c3 X! XReti -- Barcza Xg1f3 d7d5 Xg2g3 g8f6 Xf1g2 g7g6 Xo-o f8g7 Xd2d3 o-o Xb1d2 b8c6 Xe2e4 e7e5 Xc2c3 a7a5 Xf1e1 d5e4 Xd3e4 f6d7 X! END_OF_chess.opn if test 9500 -ne `wc -c <chess.opn`; then echo shar: \"chess.opn\" unpacked with wrong size! fi # end of overwriting check fi if test -f chess.001 -a "${1}" != "-c" ; then echo shar: Will not over-write existing file \"chess.001\" else echo shar: Extracting \"chess.001\" \(163 characters\) sed "s/^X//" >chess.001 <<'END_OF_chess.001' X0 0 X10 10 X0 X0 X0 X0 X0 X0 X0 X1537 X0 X0 X0 X0 X0 X0 X257 X257 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X1281 X0 X0 X513 X0 X0 X0 X1026 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X0 X258 X258 X0 X0 X1026 X0 X0 X0 X0 X1538 END_OF_chess.001 if test 163 -ne `wc -c <chess.001`; then echo shar: \"chess.001\" unpacked with wrong size! fi # end of overwriting check fi echo shar: End of shell archive. exit 0