home *** CD-ROM | disk | FTP | other *** search
/ Usenet 1994 January / usenetsourcesnewsgroupsinfomagicjanuary1994.iso / sources / games / volume13 / gnuchess4 / part05 < prev    next >
Internet Message Format  |  1992-08-03  |  56KB

  1. Path: uunet!zephyr.ens.tek.com!master!saab!billr
  2. From: billr@saab.CNA.TEK.COM (Bill Randle)
  3. Newsgroups: comp.sources.games
  4. Subject: v13i093:  gnuchess4 - GNU Chess 4.0, Part05/12
  5. Message-ID: <3060@master.CNA.TEK.COM>
  6. Date: 19 Jun 92 15:54:13 GMT
  7. Sender: news@master.CNA.TEK.COM
  8. Lines: 2302
  9. Approved: billr@saab.CNA.TEK.COM
  10.  
  11. Submitted-by: cracraft@rice-chex.ai.mit.edu (Stuart Cracraft)
  12. Posting-number: Volume 13, Issue 93
  13. Archive-name: gnuchess4/Part05
  14. Supersedes: gnuchess2: Volume 4, Issue 37-40
  15. Environment: 
  16.  
  17.  
  18.  
  19. #! /bin/sh
  20. # This is a shell archive.  Remove anything before this line, then unpack
  21. # it by saving it into a file and typing "sh file".  To overwrite existing
  22. # files, type "sh file -c".  You can also feed this as standard input via
  23. # unshar, or by typing "sh <file", e.g..  If this archive is complete, you
  24. # will see the following message at the end:
  25. #        "End of archive 5 (of 12)."
  26. # Contents:  src/eval.c src/uxdsp.c test/test-mchess
  27. # Wrapped by billr@saab on Fri Jun 19 08:36:01 1992
  28. PATH=/bin:/usr/bin:/usr/ucb ; export PATH
  29. if test -f 'src/eval.c' -a "${1}" != "-c" ; then 
  30.   echo shar: Will not clobber existing file \"'src/eval.c'\"
  31. else
  32. echo shar: Extracting \"'src/eval.c'\" \(32715 characters\)
  33. sed "s/^X//" >'src/eval.c' <<'END_OF_FILE'
  34. X/*
  35. X * eval.c - C source for GNU CHESS
  36. X *
  37. X * Copyright (c) 1988,1989,1990 John Stanback
  38. X * Copyright (c) 1992 Free Software Foundation
  39. X *
  40. X * This file is part of GNU CHESS.
  41. X *
  42. X * GNU Chess is free software; you can redistribute it and/or modify
  43. X * it under the terms of the GNU General Public License as published by
  44. X * the Free Software Foundation; either version 2, or (at your option)
  45. X * any later version.
  46. X *
  47. X * GNU Chess is distributed in the hope that it will be useful,
  48. X * but WITHOUT ANY WARRANTY; without even the implied warranty of
  49. X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  50. X * GNU General Public License for more details.
  51. X *
  52. X * You should have received a copy of the GNU General Public License
  53. X * along with GNU Chess; see the file COPYING.  If not, write to
  54. X * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
  55. X */
  56. X#include "gnuchess.h"
  57. X#include "ataks.h"
  58. Xshort int sscore[2];
  59. X/* Backward pawn bonus indexed by # of attackers on the square */
  60. Xstatic const short BACKWARD[16] =
  61. X{-6, -10, -15, -21, -28, -28, -28, -28, -28, -28, -28, -28, -28, -28, -28, -28};
  62. X
  63. X/* Bishop mobility bonus indexed by # reachable squares */
  64. Xstatic const short BMBLTY[14] =
  65. X{-2, 0, 2, 4, 6, 8, 10, 12, 13, 14, 15, 16, 16, 16};
  66. X
  67. X/* Rook mobility bonus indexed by # reachable squares */
  68. Xstatic const short RMBLTY[15] =
  69. X{0, 2, 4, 6, 8, 10, 11, 12, 13, 14, 14, 14, 14, 14, 14};
  70. X
  71. X/* Positional values for a dying king */
  72. Xstatic const short DyingKing[64] =
  73. X{0, 8, 16, 24, 24, 16, 8, 0,
  74. X 8, 32, 40, 48, 48, 40, 32, 8,
  75. X 16, 40, 56, 64, 64, 56, 40, 16,
  76. X 24, 48, 64, 72, 72, 64, 48, 24,
  77. X 24, 48, 64, 72, 72, 64, 48, 24,
  78. X 16, 40, 56, 64, 64, 56, 40, 16,
  79. X 8, 32, 40, 48, 48, 40, 32, 8,
  80. X 0, 8, 16, 24, 24, 16, 8, 0};
  81. X
  82. X/* Isoloted pawn penalty by rank */
  83. Xstatic const short ISOLANI[8] =
  84. X{-12, -16, -20, -24, -24, -20, -16, -12};
  85. X
  86. X/* table for King Bishop Knight endings */
  87. Xstatic const short KBNK[64] =
  88. X{99, 90, 80, 70, 60, 50, 40, 40,
  89. X 90, 80, 60, 50, 40, 30, 20, 40,
  90. X 80, 60, 40, 30, 20, 10, 30, 50,
  91. X 70, 50, 30, 10, 0, 20, 40, 60,
  92. X 60, 40, 20, 0, 10, 30, 50, 70,
  93. X 50, 30, 10, 20, 30, 40, 60, 80,
  94. X 40, 20, 30, 40, 50, 60, 80, 90,
  95. X 40, 40, 50, 60, 70, 80, 90, 99};
  96. X
  97. X/* penalty for threats to king, indexed by number of such threats */
  98. Xstatic const short KTHRT[36] =
  99. X{0, -8, -20, -36, -52, -68, -80, -80, -80, -80, -80, -80,
  100. X -80, -80, -80, -80, -80, -80, -80, -80, -80, -80, -80, -80,
  101. X -80, -80, -80, -80, -80, -80, -80, -80, -80, -80, -80, -80};
  102. X
  103. X/* King positional bonus inopening stage */
  104. Xstatic const short KingOpening[64] =
  105. X{0, 0, -4, -10, -10, -4, 0, 0,
  106. X -4, -4, -8, -12, -12, -8, -4, -4,
  107. X -12, -16, -20, -20, -20, -20, -16, -12,
  108. X -16, -20, -24, -24, -24, -24, -20, -16,
  109. X -16, -20, -24, -24, -24, -24, -20, -16,
  110. X -12, -16, -20, -20, -20, -20, -16, -12,
  111. X -4, -4, -8, -12, -12, -8, -4, -4,
  112. X 0, 0, -4, -10, -10, -4, 0, 0};
  113. X
  114. X/* King positional bonus in end stage */
  115. Xstatic const short KingEnding[64] =
  116. X{0, 6, 12, 18, 18, 12, 6, 0,
  117. X 6, 12, 18, 24, 24, 18, 12, 6,
  118. X 12, 18, 24, 30, 30, 24, 18, 12,
  119. X 18, 24, 30, 36, 36, 30, 24, 18,
  120. X 18, 24, 30, 36, 36, 30, 24, 18,
  121. X 12, 18, 24, 30, 30, 24, 18, 12,
  122. X 6, 12, 18, 24, 24, 18, 12, 6,
  123. X 0, 6, 12, 18, 18, 12, 6, 0};
  124. X
  125. X/* Passed pawn positional bonus */
  126. Xstatic const short PassedPawn0[8] =
  127. X{0, 60, 80, 120, 200, 360, 600, 800};
  128. Xstatic const short PassedPawn1[8] =
  129. X{0, 30, 40, 60, 100, 180, 300, 800};
  130. Xstatic const short PassedPawn2[8] =
  131. X{0, 15, 25, 35, 50, 90, 140, 800};
  132. Xstatic const short PassedPawn3[8] =
  133. X{0, 5, 10, 15, 20, 30, 140, 800};
  134. X
  135. X/* Knight positional bonus */
  136. Xstatic const short pknight[64] =
  137. X{0, 4, 8, 10, 10, 8, 4, 0,
  138. X 4, 8, 16, 20, 20, 16, 8, 4,
  139. X 8, 16, 24, 28, 28, 24, 16, 8,
  140. X 10, 20, 28, 32, 32, 28, 20, 10,
  141. X 10, 20, 28, 32, 32, 28, 20, 10,
  142. X 8, 16, 24, 28, 28, 24, 16, 8,
  143. X 4, 8, 16, 20, 20, 16, 8, 4,
  144. X 0, 4, 8, 10, 10, 8, 4, 0};
  145. X
  146. X/* Bishop positional bonus */
  147. Xstatic const short pbishop[64] =
  148. X{14, 14, 14, 14, 14, 14, 14, 14,
  149. X 14, 22, 18, 18, 18, 18, 22, 14,
  150. X 14, 18, 22, 22, 22, 22, 18, 14,
  151. X 14, 18, 22, 22, 22, 22, 18, 14,
  152. X 14, 18, 22, 22, 22, 22, 18, 14,
  153. X 14, 18, 22, 22, 22, 22, 18, 14,
  154. X 14, 22, 18, 18, 18, 18, 22, 14,
  155. X 14, 14, 14, 14, 14, 14, 14, 14};
  156. X
  157. X/* Pawn positional bonus */
  158. Xstatic const short PawnAdvance[64] =
  159. X{0, 0, 0, 0, 0, 0, 0, 0,
  160. X 4, 4, 4, 0, 0, 4, 4, 4,
  161. X 6, 8, 2, 10, 10, 2, 8, 6,
  162. X 6, 8, 12, 16, 16, 12, 8, 6,
  163. X 8, 12, 16, 24, 24, 16, 12, 8,
  164. X 12, 16, 24, 32, 32, 24, 16, 12,
  165. X 12, 16, 24, 32, 32, 24, 16, 12,
  166. X 0, 0, 0, 0, 0, 0, 0, 0};
  167. X#if !defined NOSCORESPACE
  168. X#ifdef BLACKAG0
  169. X/* Space positional bonus */
  170. Xstatic const short SpaceBonusB[64] =
  171. X{0, 0, 0, 0, 0, 0, 0, 0,
  172. X 0, 0, 2, 2, 2, 2, 0, 0,
  173. X 1, 1, 2, 4, 4, 2, 1, 1,
  174. X 0, 0, 3, 4, 4, 3, 0, 0,
  175. X 0, 0, 5, 5, 5, 5, 0, 0,
  176. X 0, 0, 4, 4, 7, 7, 0, 0,
  177. X 0, 0, 0, 0, 0, 0, 0, 0,
  178. X 0, 0, 0, 0, 0, 0, 0, 0};
  179. X#elif defined BLACKAG1
  180. X/* Space positional bonus */
  181. Xstatic const short SpaceBonusB[64] =
  182. X{1, 1, 1, 1, 1, 1, 1, 1,
  183. X 1, 1, 2, 2, 2, 2, 1, 1,
  184. X 1, 1, 2, 3, 3, 2, 1, 1,
  185. X 1, 1, 2, 4, 4, 2, 1, 1,
  186. X 1, 1, 3, 5, 5, 3, 1, 1,
  187. X 1, 1, 3, 6, 6, 3, 1, 1,
  188. X 1, 1, 3, 7, 7, 3, 1, 1,
  189. X 1, 1, 1, 1, 1, 1, 1, 1};
  190. X#elif defined BLACKAG2
  191. X/* Space positional bonus */
  192. Xstatic const short SpaceBonusB[64] =
  193. X{1, 1, 1, 1, 1, 1, 1, 1,
  194. X 1, 1, 2, 2, 2, 2, 1, 1,
  195. X 1, 1, 3, 3, 3, 3, 1, 1,
  196. X 1, 1, 4, 4, 4, 4, 1, 1,
  197. X 1, 1, 5, 6, 6, 5, 1, 1,
  198. X 1, 1, 6, 7, 7, 6, 1, 1,
  199. X 1, 1, 7, 8, 8, 7, 1, 1,
  200. X 1, 1, 1, 1, 1, 1, 1, 1};
  201. X#elif defined BLACKAG3
  202. X/* Space positional bonus */
  203. Xstatic const short SpaceBonusB[64] =
  204. X{0, 0, 0, 0, 0, 0, 0, 0,
  205. X 0, 0, 2, 2, 2, 2, 0, 0,
  206. X 0, 0, 3, 3, 3, 3, 0, 0,
  207. X 0, 0, 4, 4, 4, 3, 0, 0,
  208. X 0, 0, 6, 6, 4, 4, 0, 0,
  209. X 0, 0, 7, 7, 5, 5, 0, 0,
  210. X 0, 0, 8, 8, 7, 7, 0, 0,
  211. X 0, 0, 0, 0, 0, 0, 0, 0};
  212. X#elif defined BLACKAG4
  213. X/* Space positional bonus */
  214. Xstatic const short SpaceBonusB[64] =
  215. X{1, 1, 1, 1, 1, 1, 1, 1,
  216. X 1, 1, 2, 4, 4, 2, 1, 1,
  217. X 1, 1, 2, 4, 4, 2, 1, 1,
  218. X 1, 1, 2, 4, 4, 2, 1, 1,
  219. X 1, 1, 2, 4, 4, 2, 1, 1,
  220. X 1, 1, 2, 4, 4, 2, 1, 1,
  221. X 1, 1, 2, 4, 4, 2, 1, 1,
  222. X 1, 1, 1, 1, 1, 1, 1, 1};
  223. X#endif
  224. X
  225. X#ifdef WHITEAG0
  226. X/* Space positional bonus */
  227. Xstatic const short SpaceBonusW[64] =
  228. X{0, 0, 0, 0, 0, 0, 0, 0,
  229. X 0, 0, 5, 5, 5, 5, 0, 0,
  230. X 0, 0, 3, 4, 4, 3, 0, 0,
  231. X 0, 0, 2, 4, 4, 2, 0, 0,
  232. X 0, 0, 1, 4, 4, 1, 0, 0,
  233. X 0, 0, 1, 4, 4, 1, 0, 0,
  234. X 0, 0, 1, 2, 2, 1, 0, 0,
  235. X 0, 0, 0, 0, 0, 0, 0, 0};
  236. X#elif defined WHITEAG1
  237. X/* Space positional bonus */
  238. Xstatic const short SpaceBonusW[64] =
  239. X{1, 1, 1, 1, 1, 1, 1, 1,
  240. X 1, 1, 3, 7, 7, 3, 1, 1,
  241. X 1, 1, 3, 6, 6, 3, 1, 1,
  242. X 1, 1, 3, 5, 5, 3, 1, 1,
  243. X 1, 1, 2, 4, 4, 2, 1, 1,
  244. X 1, 1, 2, 3, 3, 2, 1, 1,
  245. X 1, 1, 2, 2, 2, 2, 1, 1,
  246. X 1, 1, 1, 1, 1, 1, 1, 1};
  247. X#elif defined WHITEAG2
  248. X/* Space positional bonus */
  249. Xstatic const short SpaceBonusW[64] =
  250. X{1, 1, 1, 1, 1, 1, 1, 1,
  251. X 1, 1, 7, 8, 8, 7, 1, 1,
  252. X 1, 1, 6, 7, 7, 6, 1, 1,
  253. X 1, 1, 5, 6, 6, 5, 1, 1,
  254. X 1, 1, 4, 4, 4, 4, 1, 1,
  255. X 1, 1, 3, 3, 3, 3, 1, 1,
  256. X 1, 1, 2, 2, 2, 2, 1, 1,
  257. X 1, 1, 1, 1, 1, 1, 1, 1};
  258. X#elif defined WHITEAG3
  259. X/* Space positional bonus */
  260. Xstatic const short SpaceBonusW[64] =
  261. X{0, 0, 0, 0, 0, 0, 0, 0,
  262. X 0, 0, 8, 8, 7, 7, 0, 0,
  263. X 0, 0, 7, 7, 5, 5, 0, 0,
  264. X 0, 0, 6, 6, 4, 4, 0, 0,
  265. X 0, 0, 4, 4, 4, 3, 0, 0,
  266. X 0, 0, 3, 3, 3, 3, 0, 0,
  267. X 0, 0, 2, 2, 2, 2, 0, 0,
  268. X 0, 0, 0, 0, 0, 0, 0, 0};
  269. X#elif defined WHITEAG4
  270. X/* Space positional bonus */
  271. Xstatic const short SpaceBonusW[64] =
  272. X{1, 1, 1, 1, 1, 1, 1, 1,
  273. X 1, 1, 2, 4, 4, 2, 1, 1,
  274. X 1, 1, 2, 4, 4, 2, 1, 1,
  275. X 1, 1, 2, 4, 4, 2, 1, 1,
  276. X 1, 1, 2, 4, 4, 2, 1, 1,
  277. X 1, 1, 2, 4, 4, 2, 1, 1,
  278. X 1, 1, 2, 4, 4, 2, 1, 1,
  279. X 1, 1, 1, 1, 1, 1, 1, 1};
  280. X#endif
  281. X#endif
  282. X
  283. Xstatic short Mwpawn[64], Mbpawn[64], Mknight[2][64], Mbishop[2][64];
  284. Xstatic short Mking[2][64], Kfield[2][64];
  285. Xstatic short c1, c2, *atk1, *atk2, *PC1, *PC2, atak[2][64];
  286. Xshort emtl[2];
  287. Xstatic short PawnBonus, BishopBonus, RookBonus;
  288. Xstatic short KNIGHTPOST, KNIGHTSTRONG, BISHOPSTRONG, KATAK;
  289. Xstatic short PEDRNK2B, PWEAKH, PADVNCM, PADVNCI, PAWNSHIELD, PDOUBLED,
  290. X PBLOK;
  291. Xstatic short RHOPN, RHOPNX, KHOPN, KHOPNX, KSFTY;
  292. Xstatic short ATAKD, HUNGP, HUNGX, KCASTLD, KMOVD, XRAY, PINVAL;
  293. Xshort pscore[2];
  294. Xshort tmtl;
  295. X
  296. X/* ............    POSITIONAL EVALUATION ROUTINES    ............ */
  297. X
  298. X/*
  299. X * Inputs are:
  300. X * pmtl[side] - value of pawns
  301. X * mtl[side]  - value of all material
  302. X * emtl[side] - vaule of all material - value of pawns - value of king
  303. X * hung[side] - count of hung pieces
  304. X * Tscore[ply] - search tree score for ply
  305. X * ply
  306. X * Pscore[ply] - positional score for ply ply
  307. X * INCscore    - bonus score or penalty for certain positions
  308. X * slk - single lone king flag
  309. X * Sdepth - search goal depth
  310. X * xwndw - evaluation window about alpha/beta
  311. X * EWNDW - second evaluation window about alpha/beta
  312. X * ChkFlag[ply]- checking piece at level ply or 0 if no check
  313. X */
  314. Xinline
  315. Xint
  316. XScoreKPK (short int side,
  317. X      short int winner,
  318. X      short int loser,
  319. X      short int king1,
  320. X      register short int king2,
  321. X      register short int sq)
  322. X
  323. X/*
  324. X * Score King and Pawns versus King endings.
  325. X */
  326. X
  327. X{
  328. X  register short s, r;
  329. X
  330. X  s = ((PieceCnt[winner] == 1) ? 50 : 120);
  331. X  if (winner == white)
  332. X    {
  333. X      r = row (sq) - ((side == loser) ? 1 : 0);
  334. X      if (row (king2) >= r && distance (sq, king2) < 8 - r)
  335. X    s += 10 * row (sq);
  336. X      else
  337. X    s = 500 + 50 * row (sq);
  338. X      if (row (sq) < 6)
  339. X    sq += 16;
  340. X      else if (row (sq) == 6)
  341. X    sq += 8;
  342. X    }
  343. X  else
  344. X    {
  345. X      r = row (sq) + ((side == loser) ? 1 : 0);
  346. X      if (row (king2) <= r && distance (sq, king2) < r + 1)
  347. X    s += 10 * (7 - row (sq));
  348. X      else
  349. X    s = 500 + 50 * (7 - row (sq));
  350. X      if (row (sq) > 1)
  351. X    sq -= 16;
  352. X      else if (row (sq) == 1)
  353. X    sq -= 8;
  354. X    }
  355. X  s += 8 * (taxicab (king2, sq) - taxicab (king1, sq));
  356. X  return (s);
  357. X}
  358. X
  359. X
  360. Xinline
  361. Xint
  362. XScoreKBNK (short int winner, short int king1, short int king2)
  363. X
  364. X
  365. X/*
  366. X * Score King+Bishop+Knight versus King endings. This doesn't work all that
  367. X * well but it's better than nothing.
  368. X */
  369. X
  370. X{
  371. X  register short s, sq, KBNKsq = 0;
  372. X
  373. X  for (sq = 0; sq < 64; sq++)
  374. X    if (board[sq] == bishop)
  375. X      KBNKsq = (((row (sq) % 2) == (column (sq) % 2)) ? 0 : 7);
  376. X
  377. X  s = emtl[winner] - 300;
  378. X  s += ((KBNKsq == 0) ? KBNK[king2] : KBNK[locn (row (king2), 7 - column (king2))]);
  379. X  s -= ((taxicab (king1, king2) + distance (PieceList[winner][1], king2) + distance (PieceList[winner][2], king2)));
  380. X  return (s);
  381. X}
  382. X
  383. Xinline
  384. Xshort int
  385. XScoreLoneKing (short int side)
  386. X
  387. X/*
  388. X * Static evaluation when loser has only a king and winner has no pawns or no
  389. X * pieces.
  390. X */
  391. X
  392. X{
  393. X  register short winner, loser, king1, king2, s, i;
  394. X
  395. X  UpdateWeights ();
  396. X  winner = ((mtl[white] > mtl[black]) ? white : black);
  397. X  loser = winner ^ 1;
  398. X  king1 = PieceList[winner][0];
  399. X  king2 = PieceList[loser][0];
  400. X
  401. X  s = 0;
  402. X
  403. X  if (pmtl[winner] > 0)
  404. X    for (i = 1; i <= PieceCnt[winner]; i++)
  405. X      s += ScoreKPK (side, winner, loser, king1, king2, PieceList[winner][i]);
  406. X
  407. X  else if (emtl[winner] == valueB + valueN)
  408. X    s = ScoreKBNK (winner, king1, king2);
  409. X
  410. X  else if (emtl[winner] > valueB)
  411. X    s = 500 + emtl[winner] - DyingKing[king2] - 2 * distance (king1, king2);
  412. X
  413. X  return ((side == winner) ? s : -s);
  414. X}
  415. X
  416. Xint
  417. Xevaluate (register short int side,
  418. X      register short int ply,
  419. X      register short int alpha,
  420. X      register short int beta,
  421. X      short int INCscore,
  422. X      short int *slk,    /* output single lone king */
  423. X      short int *InChk)    /* output Check flag */
  424. X
  425. X/*
  426. X * Compute an estimate of the score by adding the positional score from the
  427. X * previous ply to the material difference. If this score falls inside a
  428. X * window which is 180 points wider than the alpha-beta window (or within a
  429. X * 50 point window during quiescence search) call ScorePosition() to
  430. X * determine a score, otherwise return the estimated score. If one side has
  431. X * only a king and the other either has no pawns or no pieces then the
  432. X * function ScoreLoneKing() is called.
  433. X */
  434. X
  435. X{
  436. X  register short evflag, xside;
  437. X  short s;
  438. X
  439. X  xside = side ^ 1;
  440. X  s = -Pscore[ply - 1] + mtl[side] - mtl[xside] - INCscore;
  441. X  hung[white] = hung[black] = 0;
  442. X  *slk = ((mtl[white] == valueK && (pmtl[black] == 0 || emtl[black] == 0)) ||
  443. X      (mtl[black] == valueK && (pmtl[white] == 0 || emtl[white] == 0)));
  444. X
  445. X  if (*slk)
  446. X    evflag = false;
  447. X  else
  448. X    /* should we use the estimete or score the position */
  449. X    evflag = (ply == 1 ||
  450. X          ((ply <= Sdepth)) ||
  451. X          ((ply == Sdepth + 1 || ply == (Sdepth + 2)) && (s > (alpha - xwndw) && s < (beta + xwndw))) ||
  452. X       (ply > (Sdepth + 2) && s >= (alpha - EWNDW) && s <= (beta + EWNDW)));
  453. X#ifdef DEBUG4
  454. X  if (debuglevel & 1)
  455. X    evflag = true;
  456. X#endif
  457. X  if (evflag)
  458. X    {
  459. X      /* score the position */
  460. X      ataks (side, atak[side]);
  461. X      if (Anyatak (side, PieceList[xside][0]))
  462. X    return (10001 - ply);
  463. X      ataks (xside, atak[xside]);
  464. X      *InChk = Anyatak (xside, PieceList[side][0]);
  465. X      EvalNodes++;
  466. X      s = ScorePosition (side);
  467. X    }
  468. X  else
  469. X    {
  470. X      /* use the estimate but look at check and slk */
  471. X      if (SqAtakd (PieceList[xside][0], side))
  472. X    return (10001 - ply);
  473. X      *InChk = SqAtakd (PieceList[side][0], xside);
  474. X      if (*slk)
  475. X    s = ScoreLoneKing (side);
  476. X    }
  477. X
  478. X  Pscore[ply] = s - mtl[side] + mtl[xside];
  479. X  ChkFlag[ply - 1] = ((*InChk) ? Pindex[TOsquare] : 0);
  480. X  return (s);
  481. X}
  482. X
  483. Xinline
  484. Xvoid
  485. XBRscan (short int sq, register short int *s, short int *mob)
  486. X
  487. X/*
  488. X * Find Bishop and Rook mobility, XRAY attacks, and pins. Increment the
  489. X * hung[] array if a pin is found.
  490. X */
  491. X{
  492. X  register short u, pin;
  493. X  register unsigned char *ppos, *pdir;
  494. X  short piece, *Kf;
  495. X
  496. X  Kf = Kfield[c1];
  497. X  *mob = 0;
  498. X  piece = board[sq];
  499. X  ppos = nextpos[piece][sq];
  500. X  pdir = nextdir[piece][sq];
  501. X  u = ppos[sq];
  502. X  pin = -1;            /* start new direction */
  503. X  do
  504. X    {
  505. X      *s += Kf[u];
  506. X      if (color[u] == neutral)
  507. X    {
  508. X      (*mob)++;
  509. X      if (ppos[u] == pdir[u])
  510. X        pin = -1;        /* oops new direction */
  511. X      u = ppos[u];
  512. X    }
  513. X      else if (pin < 0)
  514. X    {
  515. X      if (board[u] == pawn || board[u] == king)
  516. X        u = pdir[u];
  517. X      else
  518. X        {
  519. X          if (ppos[u] != pdir[u])
  520. X        pin = u;    /* not on the edge and on to find a pin */
  521. X          u = ppos[u];
  522. X        }
  523. X    }
  524. X      else
  525. X    {
  526. X      if (color[u] == c2 && (board[u] > piece || atk2[u] == 0))
  527. X        {
  528. X          if (color[pin] == c2)
  529. X        {
  530. X          *s += PINVAL;
  531. X          if (atk2[pin] == 0 || atk1[pin] > control[board[pin]] + 1)
  532. X            ++hung[c2];
  533. X        }
  534. X          else
  535. X        *s += XRAY;
  536. X        }
  537. X      pin = -1;        /* new direction */
  538. X      u = pdir[u];
  539. X    }
  540. X  } while (u != sq);
  541. X}
  542. X
  543. Xinline
  544. Xshort int
  545. XKingScan (register short int sq)
  546. X
  547. X/*
  548. X * Assign penalties if king can be threatened by checks, if squares near the
  549. X * king are controlled by the enemy (especially the queen), or if there are
  550. X * no pawns near the king. The following must be true: board[sq] == king c1
  551. X * == color[sq] c2 == otherside[c1]
  552. X */
  553. X
  554. X#define ScoreThreat \
  555. X    if (color[u] != c2)\
  556. X      if (atk1[u] == 0 || (atk2[u] & 0xFF) > 1) ++cnt;\
  557. X      else s -= 3
  558. X
  559. X{
  560. X  register short int s;
  561. X  register short u;
  562. X  register unsigned char *ppos, *pdir;
  563. X  register short cnt, ok;
  564. X
  565. X  s = 0;
  566. X  cnt = 0;
  567. X  if (HasBishop[c2] || HasQueen[c2])
  568. X    {
  569. X      ppos = nextpos[bishop][sq];
  570. X      pdir = nextdir[bishop][sq];
  571. X      u = ppos[sq];
  572. X      do
  573. X    {
  574. X      if (atk2[u] & ctlBQ)
  575. X        ScoreThreat;
  576. X      u = ((color[u] == neutral) ? ppos[u] : pdir[u]);
  577. X      } while (u != sq);
  578. X    }
  579. X  if (HasRook[c2] || HasQueen[c2])
  580. X    {
  581. X      ppos = nextpos[rook][sq];
  582. X      pdir = nextdir[rook][sq];
  583. X      u = ppos[sq];
  584. X      do
  585. X    {
  586. X      if (atk2[u] & ctlRQ)
  587. X        ScoreThreat;
  588. X      u = ((color[u] == neutral) ? ppos[u] : pdir[u]);
  589. X      } while (u != sq);
  590. X    }
  591. X  if (HasKnight[c2])
  592. X    {
  593. X      pdir = nextdir[knight][sq];
  594. X      u = pdir[sq];
  595. X      do
  596. X    {
  597. X      if (atk2[u] & ctlNN)
  598. X        ScoreThreat;
  599. X      u = pdir[u];
  600. X      } while (u != sq);
  601. X    }
  602. X  s += (KSFTY * KTHRT[cnt]) / 16;
  603. X
  604. X  cnt = 0;
  605. X  ok = false;
  606. X  pdir = nextpos[king][sq];
  607. X  u = pdir[sq];
  608. X  do
  609. X    {
  610. X      if (board[u] == pawn)
  611. X    ok = true;
  612. X      if (atk2[u] > atk1[u])
  613. X    {
  614. X      ++cnt;
  615. X      if (atk2[u] & ctlQ)
  616. X        if (atk2[u] > ctlQ + 1 && atk1[u] < ctlQ)
  617. X          s -= 4 * KSFTY;
  618. X    }
  619. X      u = pdir[u];
  620. X  } while (u != sq);
  621. X  if (!ok)
  622. X    s -= KSFTY;
  623. X  if (cnt > 1)
  624. X    s -= (KSFTY);
  625. X  return (s);
  626. X}
  627. X
  628. Xinline
  629. Xint
  630. Xtrapped (register short int sq)
  631. X
  632. X/*
  633. X * See if the attacked piece has unattacked squares to move to. The following
  634. X * must be true: c1 == color[sq] c2 == otherside[c1]
  635. X */
  636. X
  637. X{
  638. X  register short u, piece;
  639. X  register unsigned char *ppos, *pdir;
  640. X
  641. X  piece = board[sq];
  642. X  ppos = nextpos[ptype[c1][piece]][sq];
  643. X  pdir = nextdir[ptype[c1][piece]][sq];
  644. X  if (piece == pawn)
  645. X    {
  646. X      u = ppos[sq];        /* follow no captures thread */
  647. X      if (color[u] == neutral)
  648. X    {
  649. X      if (atk1[u] >= atk2[u])
  650. X        return (false);
  651. X      if (atk2[u] < ctlP)
  652. X        {
  653. X          u = ppos[u];
  654. X          if (color[u] == neutral && atk1[u] >= atk2[u])
  655. X        return (false);
  656. X        }
  657. X    }
  658. X      u = pdir[sq];        /* follow captures thread */
  659. X      if (color[u] == c2)
  660. X    return (false);
  661. X      u = pdir[u];
  662. X      if (color[u] == c2)
  663. X    return (false);
  664. X    }
  665. X  else
  666. X    {
  667. X      u = ppos[sq];
  668. X      do
  669. X    {
  670. X      if (color[u] != c1)
  671. X        if (atk2[u] == 0 || board[u] >= piece)
  672. X          return (false);
  673. X      u = ((color[u] == neutral) ? ppos[u] : pdir[u]);
  674. X      } while (u != sq);
  675. X    }
  676. X  return (true);
  677. X}
  678. X
  679. Xinline
  680. Xint
  681. XPawnValue (register short int sqx, short int side)
  682. X
  683. X/*
  684. X * Calculate the positional value for a pawn on 'sq'.
  685. X */
  686. X
  687. X{
  688. X  register short s, fyle, rank;
  689. X  register short j, a1, a2, in_square, r, e;
  690. X
  691. X  a1 = (atk1[sqx] & 0x4FFF);
  692. X  a2 = (atk2[sqx] & 0x4FFF);
  693. X  rank = row (sqx);
  694. X  fyle = column (sqx);
  695. X  s = 0;
  696. X  if (c1 == white)
  697. X    {
  698. X      s = Mwpawn[sqx];
  699. X      if ((sqx == 11 && color[19] != neutral) || (sqx == 12 && color[20] != neutral))
  700. X    s += PEDRNK2B;
  701. X      if ((fyle == 0 || PC1[fyle - 1] == 0) && (fyle == 7 || PC1[fyle + 1] == 0))
  702. X    s += ISOLANI[fyle];
  703. X      else if (PC1[fyle] > 1)
  704. X    s += PDOUBLED;
  705. X      if (a1 < ctlP && atk1[sqx + 8] < ctlP)
  706. X    {
  707. X      s += BACKWARD[a2 & 0xFF];
  708. X      if (PC2[fyle] == 0)
  709. X        s += PWEAKH;
  710. X      if (color[sqx + 8] != neutral)
  711. X        s += PBLOK;
  712. X    }
  713. X      if (PC2[fyle] == 0)
  714. X    {
  715. X      r = rank - ((side == black) ? 1 : 0);
  716. X      in_square = (row (bking) >= r && distance (sqx, bking) < 8 - r);
  717. X      e = ((a2 == 0 || side == white) ? 0 : 1);
  718. X      for (j = sqx + 8; j < 64; j += 8)
  719. X        if (atk2[j] >= ctlP)
  720. X          {
  721. X        e = 2;
  722. X        break;
  723. X          }
  724. X        else if (atk2[j] > 0 || color[j] != neutral)
  725. X          e = 1;
  726. X      if (e == 2)
  727. X        s += (stage * PassedPawn3[rank]) / 10;
  728. X      else if (in_square || e == 1)
  729. X        s += (stage * PassedPawn2[rank]) / 10;
  730. X      else if (emtl[black] > 0)
  731. X        s += (stage * PassedPawn1[rank]) / 10;
  732. X      else
  733. X        s += PassedPawn0[rank];
  734. X    }
  735. X    }
  736. X  else if (c1 == black)
  737. X    {
  738. X      s = Mbpawn[sqx];
  739. X      if ((sqx == 51 && color[43] != neutral) || (sqx == 52 && color[44] != neutral))
  740. X    s += PEDRNK2B;
  741. X      if ((fyle == 0 || PC1[fyle - 1] == 0) && (fyle == 7 || PC1[fyle + 1] == 0))
  742. X    s += ISOLANI[fyle];
  743. X      else if (PC1[fyle] > 1)
  744. X    s += PDOUBLED;
  745. X      if (a1 < ctlP && atk1[sqx - 8] < ctlP)
  746. X    {
  747. X      s += BACKWARD[a2 & 0xFF];
  748. X      if (PC2[fyle] == 0)
  749. X        s += PWEAKH;
  750. X      if (color[sqx - 8] != neutral)
  751. X        s += PBLOK;
  752. X    }
  753. X      if (PC2[fyle] == 0)
  754. X    {
  755. X      r = rank + ((side == white) ? 1 : 0);
  756. X      in_square = (row (wking) <= r && distance (sqx, wking) < r + 1);
  757. X      e = ((a2 == 0 || side == black) ? 0 : 1);
  758. X      for (j = sqx - 8; j >= 0; j -= 8)
  759. X        if (atk2[j] >= ctlP)
  760. X          {
  761. X        e = 2;
  762. X        break;
  763. X          }
  764. X        else if (atk2[j] > 0 || color[j] != neutral)
  765. X          e = 1;
  766. X      if (e == 2)
  767. X        s += (stage * PassedPawn3[7 - rank]) / 10;
  768. X      else if (in_square || e == 1)
  769. X        s += (stage * PassedPawn2[7 - rank]) / 10;
  770. X      else if (emtl[white] > 0)
  771. X        s += (stage * PassedPawn1[7 - rank]) / 10;
  772. X      else
  773. X        s += PassedPawn0[7 - rank];
  774. X    }
  775. X    }
  776. X  if (a2 > 0)
  777. X    {
  778. X      if (a1 == 0 || a2 > ctlP + 1)
  779. X    {
  780. X      s += HUNGP;
  781. X      ++hung[c1];
  782. X      if (trapped (sqx))
  783. X        ++hung[c1];
  784. X    }
  785. X      else if (a2 > a1)
  786. X    s += ATAKD;
  787. X    }
  788. X  return (s);
  789. X}
  790. X
  791. Xinline
  792. Xint
  793. XKnightValue (short int sq, short int side)
  794. X
  795. X/*
  796. X * Calculate the positional value for a knight on 'sq'.
  797. X */
  798. X
  799. X{
  800. X  register short s, a2, a1;
  801. X
  802. X  s = Mknight[c1][sq];
  803. X  a2 = (atk2[sq] & 0x4FFF);
  804. X  if (a2 > 0)
  805. X    {
  806. X      a1 = (atk1[sq] & 0x4FFF);
  807. X      if (a1 == 0 || a2 > ctlBN + 1)
  808. X    {
  809. X      s += HUNGP;
  810. X      ++hung[c1];
  811. X      if (trapped (sq))
  812. X        ++hung[c1];
  813. X    }
  814. X      else if (a2 >= ctlBN || a1 < ctlP)
  815. X    s += ATAKD;
  816. X    }
  817. X  return (s);
  818. X}
  819. X
  820. Xinline
  821. Xint
  822. XBishopValue (short int sq, short int side)
  823. X
  824. X/*
  825. X * Calculate the positional value for a bishop on 'sq'.
  826. X */
  827. X
  828. X{
  829. X  register short a2, a1;
  830. X  short s, mob;
  831. X
  832. X  s = Mbishop[c1][sq];
  833. X  BRscan (sq, &s, &mob);
  834. X  s += BMBLTY[mob];
  835. X  a2 = (atk2[sq] & 0x4FFF);
  836. X  if (a2 > 0)
  837. X    {
  838. X      a1 = (atk1[sq] & 0x4FFF);
  839. X      if (a1 == 0 || a2 > ctlBN + 1)
  840. X    {
  841. X      s += HUNGP;
  842. X      ++hung[c1];
  843. X      if (trapped (sq))
  844. X        ++hung[c1];
  845. X    }
  846. X      else if (a2 >= ctlBN || a1 < ctlP)
  847. X    s += ATAKD;
  848. X    }
  849. X  return (s);
  850. X}
  851. X
  852. Xinline
  853. Xint
  854. XRookValue (register short int sq, short int side)
  855. X
  856. X/*
  857. X * Calculate the positional value for a rook on 'sq'.
  858. X */
  859. X
  860. X{
  861. X  register short fyle, a2, a1;
  862. X  short s, mob;
  863. X
  864. X  s = RookBonus;
  865. X  BRscan (sq, &s, &mob);
  866. X  s += RMBLTY[mob];
  867. X  fyle = column (sq);
  868. X  if (PC1[fyle] == 0)
  869. X    s += RHOPN;
  870. X  if (PC2[fyle] == 0)
  871. X    s += RHOPNX;
  872. X  if (pmtl[c2] > 100 && row (sq) == rank7[c1])
  873. X    s += 10;
  874. X  if (stage > 2)
  875. X    s += 14 - taxicab (sq, EnemyKing);
  876. X  a2 = (atk2[sq] & 0x4FFF);
  877. X  if (a2 > 0)
  878. X    {
  879. X      a1 = (atk1[sq] & 0x4FFF);
  880. X      if (a1 == 0 || a2 > ctlR + 1)
  881. X    {
  882. X      s += HUNGP;
  883. X      ++hung[c1];
  884. X
  885. X      if (trapped (sq))
  886. X        ++hung[c1];
  887. X    }
  888. X      else if (a2 >= ctlR || a1 < ctlP)
  889. X    s += ATAKD;
  890. X    }
  891. X  return (s);
  892. X}
  893. X
  894. Xinline
  895. Xint
  896. XQueenValue (register short int sq, short int side)
  897. X
  898. X/*
  899. X * Calculate the positional value for a queen on 'sq'.
  900. X */
  901. X
  902. X{
  903. X  register short s, a2, a1;
  904. X
  905. X  s = ((distance (sq, EnemyKing) < 3) ? 12 : 0);
  906. X  if (stage > 2)
  907. X    s += 14 - taxicab (sq, EnemyKing);
  908. X  a2 = (atk2[sq] & 0x4FFF);
  909. X  if (a2 > 0)
  910. X    {
  911. X      a1 = (atk1[sq] & 0x4FFF);
  912. X      if (a1 == 0 || a2 > ctlQ + 1)
  913. X    {
  914. X      s += HUNGP;
  915. X      ++hung[c1];
  916. X      if (trapped (sq))
  917. X        ++hung[c1];
  918. X    }
  919. X      else if (a2 >= ctlQ || a1 < ctlP)
  920. X    s += ATAKD;
  921. X    }
  922. X  return (s);
  923. X}
  924. X
  925. Xinline
  926. Xint
  927. XKingValue (short int sq, short int side)
  928. X
  929. X/*
  930. X * Calculate the positional value for a king on 'sq'.
  931. X */
  932. X
  933. X{
  934. X  register short fyle, a2, a1;
  935. X  short s;
  936. X  s = (emtl[side ^ 1] > KINGPOSLIMIT) ? Mking[c1][sq] : Mking[c1][sq] / 2;
  937. X  if (KSFTY > 0)
  938. X    if (Developed[c2] || stage > 0)
  939. X      s += KingScan (sq);
  940. X  if (castld[c1])
  941. X    s += KCASTLD;
  942. X  else if (Mvboard[kingP[c1]])
  943. X    s += KMOVD;
  944. X
  945. X  fyle = column (sq);
  946. X  if (PC1[fyle] == 0)
  947. X    s += KHOPN;
  948. X  if (PC2[fyle] == 0)
  949. X    s += KHOPNX;
  950. X  switch (fyle)
  951. X    {
  952. X    case 5:
  953. X      if (PC1[7] == 0)
  954. X    s += KHOPN;
  955. X      if (PC2[7] == 0)
  956. X    s += KHOPNX;
  957. X      /* Fall through */
  958. X    case 4:
  959. X    case 6:
  960. X    case 0:
  961. X      if (PC1[fyle + 1] == 0)
  962. X    s += KHOPN;
  963. X      if (PC2[fyle + 1] == 0)
  964. X    s += KHOPNX;
  965. X      break;
  966. X    case 2:
  967. X      if (PC1[0] == 0)
  968. X    s += KHOPN;
  969. X      if (PC2[0] == 0)
  970. X    s += KHOPNX;
  971. X      /* Fall through */
  972. X    case 3:
  973. X    case 1:
  974. X    case 7:
  975. X      if (PC1[fyle - 1] == 0)
  976. X    s += KHOPN;
  977. X      if (PC2[fyle - 1] == 0)
  978. X    s += KHOPNX;
  979. X      break;
  980. X    default:
  981. X      /* Impossible! */
  982. X      break;
  983. X    }
  984. X
  985. X  a2 = (atk2[sq] & 0x4FFF);
  986. X  if (a2 > 0)
  987. X    {
  988. X      a1 = (atk1[sq] & 0x4FFF);
  989. X      if (a1 == 0 || a2 > ctlK + 1)
  990. X    {
  991. X      s += HUNGP;
  992. X      ++hung[c1];
  993. X    }
  994. X      else
  995. X    s += ATAKD;
  996. X    }
  997. X  return (s);
  998. X}
  999. X
  1000. X#if !defined NOSCORESPACE
  1001. Xinline
  1002. Xvoid
  1003. XScoreSpace (void)
  1004. X{
  1005. X  register short *b, *w, *sw, *sb;
  1006. X  register short sBl, sWh;
  1007. X  sBl = sWh = 0;
  1008. X  for (b = &atak[black][63], w = &atak[white][63], sw = &SpaceBonusW[63], sb = &SpaceBonusB[63];
  1009. X       sw > &SpaceBonusW[0];
  1010. X       b--, w--, sw--, sb--)
  1011. X    {
  1012. X      if (*b > *w)
  1013. X    {
  1014. X      if (*b > ctlR)
  1015. X        sBl += *sb;
  1016. X    }
  1017. X      else if (*b < *w)
  1018. X    if (*w > ctlR)
  1019. X      sWh += *sw;
  1020. X    }
  1021. X  pscore[white] += (sWh);
  1022. X  pscore[black] += (sBl);
  1023. X  sscore[white] = sWh;
  1024. X  sscore[black] = sBl;
  1025. X}
  1026. X
  1027. X#endif
  1028. X
  1029. X
  1030. X
  1031. Xshort int
  1032. XScorePosition (register short int side)
  1033. X
  1034. X/*
  1035. X * Perform normal static evaluation of board position. A score is generated
  1036. X * for each piece and these are summed to get a score for each side.
  1037. X */
  1038. X
  1039. X{
  1040. X  register short int score;
  1041. X  register short sq, s, i, xside;
  1042. X
  1043. X  UpdateWeights ();
  1044. X  xside = side ^ 1;
  1045. X  pscore[white] = pscore[black] = 0;
  1046. X#if !defined NOSCORESPACE
  1047. X  if (stage < SCORESPLIM)
  1048. X    ScoreSpace ();
  1049. X#endif
  1050. X  for (c1 = white; c1 <= black; c1++)
  1051. X    {
  1052. X      c2 = c1 ^ 1;
  1053. X      /* atk1 is array of atacks on squares by my side */
  1054. X      atk1 = atak[c1];
  1055. X      /* atk2 is array of atacks on squares by other side */
  1056. X      atk2 = atak[c2];
  1057. X      /* same for PC1 and PC2 */
  1058. X      PC1 = PawnCnt[c1];
  1059. X      PC2 = PawnCnt[c2];
  1060. X      for (i = PieceCnt[c1]; i >= 0; i--)
  1061. X    {
  1062. X      sq = PieceList[c1][i];
  1063. X      switch (board[sq])
  1064. X        {
  1065. X        case pawn:
  1066. X          s = PawnValue (sq, side);
  1067. X          break;
  1068. X        case knight:
  1069. X          s = KnightValue (sq, side);
  1070. X          break;
  1071. X        case bishop:
  1072. X          s = BishopValue (sq, side);
  1073. X          break;
  1074. X        case rook:
  1075. X          s = RookValue (sq, side);
  1076. X          break;
  1077. X        case queen:
  1078. X          s = QueenValue (sq, side);
  1079. X          break;
  1080. X        case king:
  1081. X          s = KingValue (sq, side);
  1082. X          break;
  1083. X        default:
  1084. X          s = 0;
  1085. X          break;
  1086. X        }
  1087. X      pscore[c1] += s;
  1088. X      svalue[sq] = s;
  1089. X    }
  1090. X    }
  1091. X  if (hung[side] > 1)
  1092. X    pscore[side] += HUNGX;
  1093. X  if (hung[xside] > 1)
  1094. X    pscore[xside] += HUNGX;
  1095. X
  1096. X  score = mtl[side] - mtl[xside] + pscore[side] - pscore[xside] + 10;
  1097. X  if (dither)
  1098. X    {
  1099. X      if (flag.hash)
  1100. X    srand (starttime + (unsigned int) hashbd);
  1101. X      score += urand () % dither;
  1102. X    }
  1103. X
  1104. X  if (score > 0 && pmtl[side] == 0)
  1105. X    if (emtl[side] < valueR)
  1106. X      score = 0;
  1107. X    else if (score < valueR)
  1108. X      score /= 2;
  1109. X  if (score < 0 && pmtl[xside] == 0)
  1110. X    if (emtl[xside] < valueR)
  1111. X      score = 0;
  1112. X    else if (-score < valueR)
  1113. X      score /= 2;
  1114. X
  1115. X  if (mtl[xside] == valueK && emtl[side] > valueB)
  1116. X    score += 200;
  1117. X  if (mtl[side] == valueK && emtl[xside] > valueB)
  1118. X    score -= 200;
  1119. X  return (score);
  1120. X}
  1121. Xstatic inline void
  1122. XBlendBoard (const short int a[64], const short int b[64], short int c[64])
  1123. X{
  1124. X  register int sq, s;
  1125. X  s = 10 - stage;
  1126. X  for (sq = 0; sq < 64; sq++)
  1127. X    c[sq] = ((a[sq] * s) + (b[sq] * stage)) / 10;
  1128. X}
  1129. X
  1130. X
  1131. Xstatic inline void
  1132. XCopyBoard (const short int a[64], short int b[64])
  1133. X{
  1134. X  register short *sqa, *sqb;
  1135. X  for (sqa = a, sqb = b; sqa < a + 64;)
  1136. X    *sqb++ = *sqa++;
  1137. X}
  1138. X
  1139. X
  1140. Xvoid
  1141. XExaminePosition (void)
  1142. X
  1143. X/*
  1144. X * This is done one time before the search is started. Set up arrays Mwpawn,
  1145. X * Mbpawn, Mknight, Mbishop, Mking which are used in the SqValue() function
  1146. X * to determine the positional value of each piece.
  1147. X */
  1148. X
  1149. X{
  1150. X  register short i, sq;
  1151. X  short wpadv, bpadv, wstrong, bstrong, z, side, pp, j, k, val, Pd, fyle,
  1152. X   rank;
  1153. X  static short PawnStorm = false;
  1154. X
  1155. X  ataks (white, atak[white]);
  1156. X  ataks (black, atak[black]);
  1157. X  UpdateWeights ();
  1158. X  HasKnight[white] = HasKnight[black] = 0;
  1159. X  HasBishop[white] = HasBishop[black] = 0;
  1160. X  HasRook[white] = HasRook[black] = 0;
  1161. X  HasQueen[white] = HasQueen[black] = 0;
  1162. X  for (side = white; side <= black; side++)
  1163. X    for (i = PieceCnt[side]; i >= 0; i--)
  1164. X      switch (board[PieceList[side][i]])
  1165. X    {
  1166. X    case knight:
  1167. X      ++HasKnight[side];
  1168. X      break;
  1169. X    case bishop:
  1170. X      ++HasBishop[side];
  1171. X      break;
  1172. X    case rook:
  1173. X      ++HasRook[side];
  1174. X      break;
  1175. X    case queen:
  1176. X      ++HasQueen[side];
  1177. X      break;
  1178. X    }
  1179. X  if (!Developed[white])
  1180. X    Developed[white] = (board[1] != knight && board[2] != bishop &&
  1181. X            board[5] != bishop && board[6] != knight);
  1182. X  if (!Developed[black])
  1183. X    Developed[black] = (board[57] != knight && board[58] != bishop &&
  1184. X            board[61] != bishop && board[62] != knight);
  1185. X  if (!PawnStorm && stage < 5)
  1186. X    PawnStorm = ((column (wking) < 3 && column (bking) > 4) ||
  1187. X         (column (wking) > 4 && column (bking) < 3));
  1188. X
  1189. X  CopyBoard (pknight, Mknight[white]);
  1190. X  CopyBoard (pknight, Mknight[black]);
  1191. X  CopyBoard (pbishop, Mbishop[white]);
  1192. X  CopyBoard (pbishop, Mbishop[black]);
  1193. X  BlendBoard (KingOpening, KingEnding, Mking[white]);
  1194. X  BlendBoard (KingOpening, KingEnding, Mking[black]);
  1195. X
  1196. X  for (sq = 0; sq < 64; sq++)
  1197. X    {
  1198. X      fyle = column (sq);
  1199. X      rank = row (sq);
  1200. X      wstrong = bstrong = true;
  1201. X      for (i = sq; i < 64; i += 8)
  1202. X    if (Patak (black, i))
  1203. X      {
  1204. X        wstrong = false;
  1205. X        break;
  1206. X      }
  1207. X      for (i = sq; i >= 0; i -= 8)
  1208. X    if (Patak (white, i))
  1209. X      {
  1210. X        bstrong = false;
  1211. X        break;
  1212. X      }
  1213. X      wpadv = bpadv = PADVNCM;
  1214. X      if ((fyle == 0 || PawnCnt[white][fyle - 1] == 0) && (fyle == 7 || PawnCnt[white][fyle + 1] == 0))
  1215. X    wpadv = PADVNCI;
  1216. X      if ((fyle == 0 || PawnCnt[black][fyle - 1] == 0) && (fyle == 7 || PawnCnt[black][fyle + 1] == 0))
  1217. X    bpadv = PADVNCI;
  1218. X      Mwpawn[sq] = (wpadv * PawnAdvance[sq]) / 10;
  1219. X      Mbpawn[sq] = (bpadv * PawnAdvance[63 - sq]) / 10;
  1220. X      Mwpawn[sq] += PawnBonus;
  1221. X      Mbpawn[sq] += PawnBonus;
  1222. X      if (Mvboard[kingP[white]])
  1223. X    {
  1224. X      if ((fyle < 3 || fyle > 4) && distance (sq, wking) < 3)
  1225. X        Mwpawn[sq] += PAWNSHIELD;
  1226. X    }
  1227. X      else if (rank < 3 && (fyle < 2 || fyle > 5))
  1228. X    Mwpawn[sq] += PAWNSHIELD / 2;
  1229. X      if (Mvboard[kingP[black]])
  1230. X    {
  1231. X      if ((fyle < 3 || fyle > 4) && distance (sq, bking) < 3)
  1232. X        Mbpawn[sq] += PAWNSHIELD;
  1233. X    }
  1234. X      else if (rank > 4 && (fyle < 2 || fyle > 5))
  1235. X    Mbpawn[sq] += PAWNSHIELD / 2;
  1236. X      if (PawnStorm)
  1237. X    {
  1238. X      if ((column (wking) < 4 && fyle > 4) || (column (wking) > 3 && fyle < 3))
  1239. X        Mwpawn[sq] += 3 * rank - 21;
  1240. X      if ((column (bking) < 4 && fyle > 4) || (column (bking) > 3 && fyle < 3))
  1241. X        Mbpawn[sq] -= 3 * rank;
  1242. X    }
  1243. X      Mknight[white][sq] += 5 - distance (sq, bking);
  1244. X      Mknight[white][sq] += 5 - distance (sq, wking);
  1245. X      Mknight[black][sq] += 5 - distance (sq, wking);
  1246. X      Mknight[black][sq] += 5 - distance (sq, bking);
  1247. X      Mbishop[white][sq] += BishopBonus;
  1248. X      Mbishop[black][sq] += BishopBonus;
  1249. X      for (i = PieceCnt[black]; i >= 0; i--)
  1250. X    if (distance (sq, PieceList[black][i]) < 3)
  1251. X      Mknight[white][sq] += KNIGHTPOST;
  1252. X      for (i = PieceCnt[white]; i >= 0; i--)
  1253. X    if (distance (sq, PieceList[white][i]) < 3)
  1254. X      Mknight[black][sq] += KNIGHTPOST;
  1255. X      if (wstrong)
  1256. X    Mknight[white][sq] += KNIGHTSTRONG;
  1257. X      if (bstrong)
  1258. X    Mknight[black][sq] += KNIGHTSTRONG;
  1259. X      if (wstrong)
  1260. X    Mbishop[white][sq] += BISHOPSTRONG;
  1261. X      if (bstrong)
  1262. X    Mbishop[black][sq] += BISHOPSTRONG;
  1263. X
  1264. X      if (HasBishop[white] == 2)
  1265. X    Mbishop[white][sq] += 8;
  1266. X      if (HasBishop[black] == 2)
  1267. X    Mbishop[black][sq] += 8;
  1268. X      if (HasKnight[white] == 2)
  1269. X    Mknight[white][sq] += 5;
  1270. X      if (HasKnight[black] == 2)
  1271. X    Mknight[black][sq] += 5;
  1272. X
  1273. X      Kfield[white][sq] = Kfield[black][sq] = 0;
  1274. X      if (distance (sq, wking) == 1)
  1275. X    Kfield[black][sq] = KATAK;
  1276. X      if (distance (sq, bking) == 1)
  1277. X    Kfield[white][sq] = KATAK;
  1278. X      Pd = 0;
  1279. X      for (k = 0; k <= PieceCnt[white]; k++)
  1280. X    {
  1281. X      i = PieceList[white][k];
  1282. X      if (board[i] == pawn)
  1283. X        {
  1284. X          pp = true;
  1285. X          z = i + ((row (i) == 6) ? 8 : 16);
  1286. X          for (j = i + 8; j < 64; j += 8)
  1287. X        if (Patak (black, j) || board[j] == pawn)
  1288. X          {
  1289. X            pp = false;
  1290. X            break;
  1291. X          }
  1292. X          Pd += ((pp) ? 5 * taxicab (sq, z) : taxicab (sq, z));
  1293. X        }
  1294. X    }
  1295. X      for (k = 0; k <= PieceCnt[black]; k++)
  1296. X    {
  1297. X      i = PieceList[black][k];
  1298. X      if (board[i] == pawn)
  1299. X        {
  1300. X          pp = true;
  1301. X          z = i - ((row (i) == 1) ? 8 : 16);
  1302. X          for (j = i - 8; j >= 0; j -= 8)
  1303. X        if (Patak (white, j) || board[j] == pawn)
  1304. X          {
  1305. X            pp = false;
  1306. X            break;
  1307. X          }
  1308. X          Pd += ((pp) ? 5 * taxicab (sq, z) : taxicab (sq, z));
  1309. X        }
  1310. X    }
  1311. X      if (Pd != 0)
  1312. X    {
  1313. X      val = (Pd * stage2) / 10;
  1314. X      Mking[white][sq] -= val;
  1315. X      Mking[black][sq] -= val;
  1316. X    }
  1317. X    }
  1318. X}
  1319. X
  1320. Xvoid
  1321. XUpdateWeights (void)
  1322. X
  1323. X/*
  1324. X * If material balance has changed, determine the values for the positional
  1325. X * evaluation terms.
  1326. X */
  1327. X
  1328. X{
  1329. X  register short s1;
  1330. X
  1331. X  emtl[white] = mtl[white] - pmtl[white] - valueK;
  1332. X  emtl[black] = mtl[black] - pmtl[black] - valueK;
  1333. X  tmtl = emtl[white] + emtl[black];
  1334. X  s1 = ((tmtl > 6600) ? 0 : ((tmtl < 1400) ? 10 : (6600 - tmtl) / 520));
  1335. X  if (s1 != stage)
  1336. X    {
  1337. X      stage = s1;
  1338. X      stage2 = ((tmtl > 3600) ? 0 : ((tmtl < 1400) ? 10 : (3600 - tmtl) / 220));
  1339. X      PEDRNK2B = -15;        /* centre pawn on 2nd rank & blocked */
  1340. X      PBLOK = -4;        /* blocked backward pawn */
  1341. X      PDOUBLED = -14;        /* doubled pawn */
  1342. X      PWEAKH = -4;        /* weak pawn on half open file */
  1343. X      PAWNSHIELD = 10 - stage;    /* pawn near friendly king */
  1344. X      PADVNCM = 10;        /* advanced pawn multiplier */
  1345. X      PADVNCI = 7;        /* muliplier for isolated pawn */
  1346. X      PawnBonus = stage;
  1347. X
  1348. X      KNIGHTPOST = (stage + 2) / 3;    /* knight near enemy pieces */
  1349. X      KNIGHTSTRONG = (stage + 6) / 2;    /* occupies pawn hole */
  1350. X
  1351. X      BISHOPSTRONG = (stage + 6) / 2;    /* occupies pawn hole */
  1352. X      BishopBonus = BBONUS * stage;
  1353. X
  1354. X      RHOPN = 10;        /* rook on half open file */
  1355. X      RHOPNX = 4;
  1356. X      RookBonus = RBONUS * stage;
  1357. X
  1358. X      XRAY = 8;            /* Xray attack on piece */
  1359. X      PINVAL = 10;        /* Pin */
  1360. X
  1361. X      KHOPN = (3 * stage - 30) / 2;    /* king on half open file */
  1362. X      KHOPNX = KHOPN / 2;
  1363. X      KCASTLD = 10 - stage;
  1364. X      KMOVD = -40 / (stage + 1);/* king moved before castling */
  1365. X      KATAK = (10 - stage) / 2;    /* B,R attacks near enemy king */
  1366. X      KSFTY = ((stage < 8) ? KINGSAFETY - 2 * stage : 0);
  1367. X
  1368. X      ATAKD = -6;        /* defender > attacker */
  1369. X      HUNGP = -16;        /* each hung piece */
  1370. X      HUNGX = -22;        /* extra for >1 hung piece */
  1371. X    }
  1372. X}
  1373. END_OF_FILE
  1374. if test 32715 -ne `wc -c <'src/eval.c'`; then
  1375.     echo shar: \"'src/eval.c'\" unpacked with wrong size!
  1376. fi
  1377. # end of 'src/eval.c'
  1378. fi
  1379. if test -f 'src/uxdsp.c' -a "${1}" != "-c" ; then 
  1380.   echo shar: Will not clobber existing file \"'src/uxdsp.c'\"
  1381. else
  1382. echo shar: Extracting \"'src/uxdsp.c'\" \(17782 characters\)
  1383. sed "s/^X//" >'src/uxdsp.c' <<'END_OF_FILE'
  1384. X/*
  1385. X * uxdsp.c - ALPHA interface for CHESS
  1386. X *
  1387. X * Copyright (c) 1988,1989,1990 John Stanback
  1388. X * Copyright (c) 1992 Free Software Foundation
  1389. X *
  1390. X * This file is part of GNU CHESS.
  1391. X *
  1392. X * GNU Chess is free software; you can redistribute it and/or modify
  1393. X * it under the terms of the GNU General Public License as published by
  1394. X * the Free Software Foundation; either version 2, or (at your option)
  1395. X * any later version.
  1396. X *
  1397. X * GNU Chess is distributed in the hope that it will be useful,
  1398. X * but WITHOUT ANY WARRANTY; without even the implied warranty of
  1399. X * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  1400. X * GNU General Public License for more details.
  1401. X *
  1402. X * You should have received a copy of the GNU General Public License
  1403. X * along with GNU Chess; see the file COPYING.  If not, write to
  1404. X * the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.
  1405. X */
  1406. X#include <ctype.h>
  1407. X#include <signal.h>
  1408. X#ifdef MSDOS
  1409. X#include <dos.h>
  1410. X#include <conio.h>
  1411. X#include <stdlib.h>
  1412. X#include <string.h>
  1413. X#include <time.h>
  1414. X
  1415. X#define ESC 0x1B
  1416. X#define refresh() fflush(stdout)
  1417. X
  1418. Xint mycntl1, mycntl2;
  1419. Xstatic void param (short n);
  1420. X
  1421. X#else
  1422. X#include <sys/param.h>
  1423. X#include <sys/types.h>
  1424. X#include <sys/file.h>
  1425. X#include <curses.h>
  1426. X
  1427. X
  1428. X/* <stdlib.h> */
  1429. Xextern void *malloc (size_t);
  1430. Xextern void exit (int);
  1431. X
  1432. X/* <string.h> */
  1433. Xextern char *strcat (char *, const char *);
  1434. Xextern int strcmp (const char *, const char *);
  1435. Xextern char *strcpy (char *, const char *);
  1436. X
  1437. X/* <time.h> */
  1438. Xextern long int time (long int *);
  1439. X
  1440. X#endif /* MSDOS */
  1441. X
  1442. X#include "gnuchess.h"
  1443. X
  1444. Xextern short int pscore[2];
  1445. X
  1446. X#define TAB (46)
  1447. X#define VIR_C(s)  ((flag.reverse) ? 7-column(s) : column(s))
  1448. X#define VIR_R(s)  ((flag.reverse) ? 7-row(s) : row(s))
  1449. X
  1450. Xunsigned short int MV[MAXDEPTH];
  1451. Xint MSCORE;
  1452. Xchar *DRAW;
  1453. Xchar mvstr[4][6];
  1454. X
  1455. Xextern char *getenv (const char *);
  1456. Xvoid TerminateSearch (int), Die (int);
  1457. X
  1458. Xvoid
  1459. XInitialize (void)
  1460. X{
  1461. X  signal (SIGINT, Die);
  1462. X#ifndef MSDOS
  1463. X  signal (SIGQUIT, Die);
  1464. X  initscr ();
  1465. X  crmode ();
  1466. X#else
  1467. X  mycntl1 = mycntl2 = 0;
  1468. X#endif /* MSDOS */
  1469. X}
  1470. X
  1471. Xvoid
  1472. XExitChess (void)
  1473. X{
  1474. X  ListGame ();
  1475. X  gotoXY (1, 24);
  1476. X#ifndef MSDOS
  1477. X  nocrmode ();
  1478. X  endwin ();
  1479. X#endif /* MSDOS */
  1480. X  exit (0);
  1481. X}
  1482. X
  1483. Xvoid
  1484. XDie (int Sig)
  1485. X{
  1486. X  char s[80];
  1487. X
  1488. X  signal (SIGINT, SIG_IGN);
  1489. X#ifdef MSDOS
  1490. X  Sig++;            /* shut up the compiler */
  1491. X#else
  1492. X  signal (SIGQUIT, SIG_IGN);
  1493. X#endif /* MSDOS */
  1494. X  ShowMessage (CP[31]);        /*Abort?*/
  1495. X  scanz ("%s", s);
  1496. X  if (strcmp (s, CP[210]) == 0)    /*yes*/
  1497. X    ExitChess ();
  1498. X  signal (SIGINT, Die);
  1499. X#ifndef MSDOS
  1500. X  signal (SIGQUIT, Die);
  1501. X#endif /* MSDOS */
  1502. X}
  1503. X
  1504. Xvoid
  1505. XTerminateSearch (int Sig)
  1506. X{
  1507. X  signal (SIGINT, SIG_IGN);
  1508. X#ifdef MSDOS
  1509. X  Sig++;            /* shut up the compiler */
  1510. X#else
  1511. X  signal (SIGQUIT, SIG_IGN);
  1512. X#endif /* MSDOS */
  1513. X  if (!flag.timeout)
  1514. X    flag.musttimeout = true;
  1515. X  flag.bothsides = false;
  1516. X  signal (SIGINT, Die);
  1517. X#ifndef MSDOS
  1518. X  signal (SIGQUIT, Die);
  1519. X#endif /* MSDOS */
  1520. X}
  1521. Xvoid
  1522. XShowLine (short unsigned int *bstline)
  1523. X{
  1524. X}
  1525. X
  1526. Xvoid
  1527. Xhelp (void)
  1528. X{
  1529. X  ClrScreen ();
  1530. X  /*printz ("CHESS command summary\n");*/
  1531. X  printz (CP[40]);
  1532. X  printz ("----------------------------------------------------------------\n");
  1533. X  /*printz ("g1f3      move from g1 to f3      quit      Exit Chess\n");*/
  1534. X  printz (CP[158]);
  1535. X  /*printz ("Nf3       move knight to f3       beep      turn %s\n", (flag.beep) ? "off" : "on");*/
  1536. X  printz (CP[86], (flag.beep) ? CP[92] : CP[93]);
  1537. X  /*printz ("a7a8q     promote pawn to queen\n");*/
  1538. X  printz (CP[128], (flag.material) ? CP[92] : CP[93]);
  1539. X  /*printz ("o-o       castle king side        easy      turn %s\n", (flag.easy) ? "off" : "on");*/
  1540. X  printz (CP[173], (flag.easy) ? CP[92] : CP[93]);
  1541. X  /*printz ("o-o-o     castle queen side       hash      turn %s\n", (flag.hash) ? "off" : "on");*/
  1542. X  printz (CP[174], (flag.hash) ? CP[92] : CP[93]);
  1543. X  /*printz ("bd        redraw board            reverse   board display\n");*/
  1544. X  printz (CP[130]);
  1545. X  /*printz ("list      game to chess.lst       book      turn %s used %d of %d\n", (Book) ? "off" : "on", book
  1546. Xcount, BOOKSIZE);*/
  1547. X  printz (CP[170], (Book) ? CP[92] : CP[93], bookcount, BOOKSIZE);
  1548. X  /*printz ("undo      undo last ply           remove    take back a move\n");*/
  1549. X  printz (CP[200]);
  1550. X  /*printz ("edit      edit board              force     enter game moves\n");*/
  1551. X  printz (CP[153]);
  1552. X  /*printz ("switch    sides with computer     both      computer match\n");*/
  1553. X  printz (CP[194]);
  1554. X  /*printz ("white     computer plays white    black     computer plays black\n");*/
  1555. X  printz (CP[202]);
  1556. X  /*printz ("depth     set search depth        clock     set time control\n");*/
  1557. X  printz (CP[149]);
  1558. X  /*printz ("hint      suggest a move         post      turn %s principle variation\n", (flag.post) ? "off" :
  1559. X"on");*/
  1560. X  printz (CP[177], (flag.post) ? CP[92] : CP[93]);
  1561. X  /*printz ("save      game to file            get       game from file\n");*/
  1562. X  printz (CP[188]);
  1563. X  /*printz ("random    randomize play          new       start new game\n");*/
  1564. X  printz (CP[181]);
  1565. X  gotoXY (10, 20);
  1566. X  printz (CP[47], ColorStr[computer]);
  1567. X  gotoXY (10, 21);
  1568. X  printz (CP[97], ColorStr[opponent]);
  1569. X  gotoXY (10, 22);
  1570. X  printz (CP[79], Level);
  1571. X  gotoXY (10, 23);
  1572. X  printz (CP[59], (flag.easy) ? CP[93] : CP[92]);
  1573. X  gotoXY (40, 20);
  1574. X  printz (CP[52], MaxSearchDepth);
  1575. X  gotoXY (40, 21);
  1576. X  printz (CP[100], (dither) ? CP[93] : CP[92]);
  1577. X  gotoXY (40, 22);
  1578. X  printz (CP[112], (flag.hash) ? CP[93] : CP[92]);
  1579. X  gotoXY (40, 23);
  1580. X  printz (CP[73]);
  1581. X  gotoXY (10, 24);
  1582. X  printz (CP[110], (TCflag) ? CP[93] : CP[92],
  1583. X      TimeControl.moves[white], TimeControl.clock[white] / 100, OperatorTime, MaxSearchDepth);
  1584. X  refresh ();
  1585. X  fflush (stdin);
  1586. X  getchar ();
  1587. X  ClrScreen ();
  1588. X  UpdateDisplay (0, 0, 1, 0);
  1589. X}
  1590. X
  1591. X
  1592. Xvoid
  1593. XEditBoard (void)
  1594. X
  1595. X/*
  1596. X * Set up a board position. Pieces are entered by typing the piece followed
  1597. X * by the location. For example, Nf3 will place a knight on square f3.
  1598. X */
  1599. X
  1600. X{
  1601. X  short a, r, c, sq, i;
  1602. X  char s[80];
  1603. X
  1604. X  flag.regularstart = false;
  1605. X  Book = false;
  1606. X  ClrScreen ();
  1607. X  UpdateDisplay (0, 0, 1, 0);
  1608. X  gotoXY (TAB, 3);
  1609. X  printz (CP[29]);
  1610. X  gotoXY (TAB, 4);
  1611. X  printz (CP[28]);
  1612. X  gotoXY (TAB, 5);
  1613. X  printz (CP[136]);
  1614. X  gotoXY (TAB, 7);
  1615. X  printz (CP[64]);
  1616. X  a = white;
  1617. X  do
  1618. X    {
  1619. X      gotoXY (TAB, 6);
  1620. X      printz (CP[60], ColorStr[a]);    /*Editing %s*/
  1621. X      gotoXY (TAB + 24, 7);
  1622. X      ClrEoln ();
  1623. X      scanz ("%s", s);
  1624. X      if (s[0] == CP[28][0])    /*#*/
  1625. X    {
  1626. X      for (sq = 0; sq < 64; sq++)
  1627. X        {
  1628. X          board[sq] = no_piece;
  1629. X          color[sq] = neutral;
  1630. X          DrawPiece (sq);
  1631. X        }
  1632. X    }
  1633. X      if (s[0] == CP[136][0])    /*c*/
  1634. X    a = otherside[a];
  1635. X      c = s[1] - 'a';
  1636. X      r = s[2] - '1';
  1637. X      if ((c >= 0) && (c < 8) && (r >= 0) && (r < 8))
  1638. X    {
  1639. X      sq = locn (r, c);
  1640. X      for (i = king; i > no_piece; i--)
  1641. X        if ((s[0] == pxx[i]) || (s[0] == qxx[i]))
  1642. X          break;
  1643. X      board[sq] = i;
  1644. X      color[sq] = ((board[sq] == no_piece) ? neutral : a);
  1645. X      DrawPiece (sq);
  1646. X    }
  1647. X  } while (s[0] != CP[29][0]);    /*.*/
  1648. X
  1649. X  for (sq = 0; sq < 64; sq++)
  1650. X    Mvboard[sq] = ((board[sq] != Stboard[sq]) ? 10 : 0);
  1651. X  GameCnt = 0;
  1652. X  Game50 = 1;
  1653. X  ZeroRPT ();
  1654. X  Sdepth = 0;
  1655. X  InitializeStats ();
  1656. X  ClrScreen ();
  1657. X  UpdateDisplay (0, 0, 1, 0);
  1658. X}
  1659. X
  1660. Xvoid
  1661. XShowPlayers (void)
  1662. X{
  1663. X  gotoXY (5, ((flag.reverse) ? 23 : 2));
  1664. X  printz ("%s", (computer == black) ? CP[218] : CP[74]);
  1665. X  gotoXY (5, ((flag.reverse) ? 2 : 23));
  1666. X  printz ("%s", (computer == white) ? CP[218] : CP[74]);
  1667. X}
  1668. X
  1669. Xvoid
  1670. XShowDepth (char ch)
  1671. X{
  1672. X  gotoXY (TAB, 4);
  1673. X  printz (CP[53], Sdepth, ch);    /*Depth= %d%c*/
  1674. X  ClrEoln ();
  1675. X}
  1676. X
  1677. Xvoid
  1678. XShowScore (short score)
  1679. X{
  1680. X  gotoXY (TAB, 5);
  1681. X  printz (CP[104], score);
  1682. X  ClrEoln ();
  1683. X}
  1684. X
  1685. Xvoid
  1686. XShowMessage (char *s)
  1687. X{
  1688. X  gotoXY (TAB, 6);
  1689. X  printz ("%s", s);
  1690. X  ClrEoln ();
  1691. X}
  1692. X
  1693. Xvoid
  1694. XClearMessage (void)
  1695. X{
  1696. X  gotoXY (TAB, 6);
  1697. X  ClrEoln ();
  1698. X}
  1699. X
  1700. Xvoid
  1701. XShowCurrentMove (short int pnt, short int f, short int t)
  1702. X{
  1703. X  algbr (f, t, false);
  1704. X  gotoXY (TAB, 7);
  1705. X  printz ("(%2d) %4s", pnt, mvstr[0]);
  1706. X}
  1707. X
  1708. Xvoid
  1709. XShowHeader (void)
  1710. X{
  1711. X  gotoXY (TAB, 2);
  1712. X  printz (CP[69]);
  1713. X}
  1714. X
  1715. Xvoid
  1716. XShowSidetoMove (void)
  1717. X{
  1718. X  gotoXY (TAB, 14);
  1719. X  printz ("%2d:   %s", 1 + GameCnt / 2, ColorStr[player]);
  1720. X  ClrEoln ();
  1721. X}
  1722. X
  1723. Xvoid
  1724. XShowPrompt (void)
  1725. X{
  1726. X  gotoXY (TAB, 19);
  1727. X  printz (CP[121]);        /*Your movwe is?*/
  1728. X  ClrEoln ();
  1729. X}
  1730. X
  1731. Xvoid
  1732. XShowNodeCnt (long int NodeCnt)
  1733. X{
  1734. X  gotoXY (TAB, 21);
  1735. X  printz (CP[90], NodeCnt, (et > 100) ? NodeCnt / (et / 100) : 0);
  1736. X  ClrEoln ();
  1737. X}
  1738. X
  1739. Xvoid
  1740. XShowResults (short int score, short unsigned int *bstline, char ch)
  1741. X{
  1742. X  unsigned char d, ply;
  1743. X
  1744. X  if (flag.post)
  1745. X    {
  1746. X      ShowDepth (ch);
  1747. X      ShowScore (score);
  1748. X      d = 7;
  1749. X      for (ply = 1; bstline[ply] > 0; ply++)
  1750. X    {
  1751. X      if (ply % 4 == 1)
  1752. X        {
  1753. X          gotoXY (TAB, ++d);
  1754. X          ClrEoln ();
  1755. X        }
  1756. X      algbr ((short) bstline[ply] >> 8, (short) bstline[ply] & 0xFF, false);
  1757. X      printz ("%5s ", mvstr[0]);
  1758. X    }
  1759. X      ClrEoln ();
  1760. X      while (d < 13)
  1761. X    {
  1762. X      gotoXY (TAB, ++d);
  1763. X      ClrEoln ();
  1764. X    }
  1765. X    }
  1766. X}
  1767. X
  1768. Xvoid
  1769. XSearchStartStuff (short int side)
  1770. X{
  1771. X  short i;
  1772. X
  1773. X  signal (SIGINT, TerminateSearch);
  1774. X#ifdef MSDOS
  1775. X  side++;            /* shut up the compiler */
  1776. X#else
  1777. X  signal (SIGQUIT, TerminateSearch);
  1778. X#endif /* MSDOS */
  1779. X  for (i = 4; i < 14; i++)
  1780. X    {
  1781. X      gotoXY (TAB, i);
  1782. X      ClrEoln ();
  1783. X    }
  1784. X}
  1785. X
  1786. Xvoid
  1787. XOutputMove (void)
  1788. X{
  1789. X  int i;
  1790. X
  1791. X  UpdateDisplay (rootnode.f, rootnode.t, 0, (short) rootnode.flags);
  1792. X  gotoXY (TAB, 17);
  1793. X  printz (CP[84], mvstr[0]);    /*My move is %s*/
  1794. X  if (flag.beep)
  1795. X    putchar (7);
  1796. X  ClrEoln ();
  1797. X
  1798. X  gotoXY (TAB, 24);
  1799. X  if (rootnode.flags & draw)
  1800. X    printz (CP[58]);
  1801. X  else if (rootnode.score == -9999)
  1802. X    printz (CP[95]);
  1803. X  else if (rootnode.score == 9998)
  1804. X    printz (CP[44]);
  1805. X#ifdef VERYBUGGY
  1806. X  else if (rootnode.score < -9000)
  1807. X    printz (CP[96]);
  1808. X  else if (rootnode.score > 9000)
  1809. X    printz (CP[45]);
  1810. X#endif VERYBUGGY
  1811. X  ClrEoln ();
  1812. X  if (flag.post)
  1813. X    {
  1814. X      register short h, l, t;
  1815. X
  1816. X      h = TREE;
  1817. X      l = 0;
  1818. X      t = TREE >> 1;
  1819. X      while (l != t)
  1820. X    {
  1821. X      if (Tree[t].f || Tree[t].t)
  1822. X        l = t;
  1823. X      else
  1824. X        h = t;
  1825. X      t = (l + h) >> 1;
  1826. X    }
  1827. X
  1828. X      ShowNodeCnt (NodeCnt);
  1829. X      gotoXY (TAB, 22);
  1830. X      printz (CP[81], t);    /*Max Tree=*/
  1831. X      ClrEoln ();
  1832. X    }
  1833. X  ShowSidetoMove ();
  1834. X}
  1835. X
  1836. Xvoid
  1837. XUpdateClocks (void)
  1838. X{
  1839. X  short m, s;
  1840. X
  1841. X  m = (short) (et / 6000);
  1842. X  s = (short) (et - 6000 * (long) m) / 100;
  1843. X  if (TCflag)
  1844. X    {
  1845. X      m = (short) ((TimeControl.clock[player] - et) / 6000);
  1846. X      s = (short) ((TimeControl.clock[player] - et - 6000 * (long) m) / 100);
  1847. X    }
  1848. X  if (m < 0)
  1849. X    m = 0;
  1850. X  if (s < 0)
  1851. X    s = 0;
  1852. X  if (player == white)
  1853. X    gotoXY (20, (flag.reverse) ? 2 : 23);
  1854. X  else
  1855. X    gotoXY (20, (flag.reverse) ? 23 : 2);
  1856. X  printz ("%d:%02d   ", m, s);
  1857. X  if (flag.post)
  1858. X    ShowNodeCnt (NodeCnt);
  1859. X  refresh ();
  1860. X}
  1861. X
  1862. Xvoid
  1863. XgotoXY (short int x, short int y)
  1864. X{
  1865. X#ifdef MSDOS
  1866. X  putchar (ESC);
  1867. X  putchar ('[');
  1868. X  param (y);
  1869. X  putchar (';');
  1870. X  param (x);
  1871. X  putchar ('H');
  1872. X#else
  1873. X  move (y - 1, x - 1);
  1874. X#endif /* MSDOS */
  1875. X}
  1876. X
  1877. Xvoid
  1878. XClrScreen (void)
  1879. X{
  1880. X#ifdef MSDOS
  1881. X  putchar (ESC);
  1882. X  putchar ('[');
  1883. X  putchar ('2');
  1884. X  putchar ('J');
  1885. X#else
  1886. X  clear ();
  1887. X#endif /* MSDOS */
  1888. X  refresh ();
  1889. X}
  1890. X
  1891. Xvoid
  1892. XClrEoln (void)
  1893. X{
  1894. X#ifdef MSDOS
  1895. X  putchar (ESC);
  1896. X  putchar ('[');
  1897. X  putchar ('K');
  1898. X#else
  1899. X  clrtoeol ();
  1900. X#endif /* MSDOS */
  1901. X  refresh ();
  1902. X}
  1903. X
  1904. X#ifdef MSDOS
  1905. Xvoid
  1906. Xparam (short n)
  1907. X{
  1908. X  if (n >= 10)
  1909. X    {
  1910. X      register short d, q;
  1911. X
  1912. X      q = n / 10;
  1913. X      d = n % 10;
  1914. X      putchar (q + '0');
  1915. X      putchar (d + '0');
  1916. X    }
  1917. X  else
  1918. X    putchar (n + '0');
  1919. X}
  1920. X
  1921. X#endif /* MSDOS */
  1922. X
  1923. Xvoid
  1924. XDrawPiece (short int sq)
  1925. X{
  1926. X  register char x;
  1927. X
  1928. X  if (color[sq] == black)
  1929. X#if defined(MSDOS) && !defined(SEVENBIT)
  1930. X    x = '7';            /* print WHITE boldface, */
  1931. X  else
  1932. X    x = '1';            /* print BLACK inverted     */
  1933. X  gotoXY (6 + 5 * VIR_C (sq), 5 + 2 * (7 - VIR_R (sq)));
  1934. X  printz ("\033[%cm%c\033[0m", x, pxx[board[sq]]);
  1935. X#else
  1936. X    x = '*';
  1937. X  else
  1938. X    x = ' ';
  1939. X  gotoXY (5 + 5 * VIR_C (sq), 5 + 2 * (7 - VIR_R (sq)));
  1940. X  printz ("%c%c ", x, pxx[board[sq]]);
  1941. X#endif /* MSDOS && !SEVENBIT */
  1942. X}
  1943. X
  1944. Xvoid
  1945. XShowPostnValue (short int sq)
  1946. X
  1947. X/*
  1948. X * must have called ExaminePosition() first
  1949. X */
  1950. X
  1951. X{
  1952. X  short score;
  1953. X
  1954. X  gotoXY (4 + 5 * VIR_C (sq), 5 + 2 * (7 - VIR_R (sq)));
  1955. X  score = ScorePosition (color[sq]);
  1956. X  if (color[sq] != neutral)
  1957. X    printz ("%3d ", svalue[sq]);
  1958. X  else
  1959. X    printz ("   ");
  1960. X}
  1961. X
  1962. Xvoid
  1963. XShowPostnValues (void)
  1964. X{
  1965. X  short sq, score;
  1966. X
  1967. X  ExaminePosition ();
  1968. X  for (sq = 0; sq < 64; sq++)
  1969. X    ShowPostnValue (sq);
  1970. X  score = ScorePosition (opponent);
  1971. X  gotoXY (TAB, 5);
  1972. X  printz (CP[103], score, mtl[computer], pmtl[computer], pscore[computer], mtl[opponent], pmtl[opponent], pscore[opponent]);
  1973. X  ClrEoln ();
  1974. X}
  1975. X
  1976. Xvoid
  1977. XUpdateDisplay (short int f, short int t, short int redraw, short int isspec)
  1978. X{
  1979. X  short i, sq, z;
  1980. X
  1981. X  if (redraw)
  1982. X    {
  1983. X      ShowHeader ();
  1984. X      ShowPlayers ();
  1985. X
  1986. X      i = 3;
  1987. X      gotoXY (3, ++i);
  1988. X#if defined(MSDOS) && !defined(SEVENBIT)
  1989. X      printz ("\332\304\304\304\304\302\304\304\304\304\302\304\304\304\304" \
  1990. X        "\302\304\304\304\304\302\304\304\304\304\302\304\304\304\304" \
  1991. X          "\302\304\304\304\304\302\304\304\304\304\277");
  1992. X#else
  1993. X      printz ("+----+----+----+----+----+----+----+----+");
  1994. X#endif /* MSDOS && !SEVENBIT */
  1995. X      while (i < 19)
  1996. X    {
  1997. X      gotoXY (1, ++i);
  1998. X      if (flag.reverse)
  1999. X        z = (i / 2) - 1;
  2000. X      else
  2001. X        z = 10 - (i / 2);
  2002. X#if defined(MSDOS) && !defined(SEVENBIT)
  2003. X      printz ("%d \263    \263    \263    \263    \263    \263    " \
  2004. X          "\263    \263    \263", z);
  2005. X#else
  2006. X      printz ("%d |    |    |    |    |    |    |    |    |", z);
  2007. X#endif /* MSDOS && !SEVENBIT */
  2008. X      gotoXY (3, ++i);
  2009. X      if (i < 19)
  2010. X#if defined(MSDOS) && !defined(SEVENBIT)
  2011. X        printz ("\303\304\304\304\304\305\304\304\304\304\305\304\304" \
  2012. X            "\304\304\305\304\304\304\304\305\304\304\304\304\305" \
  2013. X            "\304\304\304\304\305\304\304\304\304\305\304\304\304" \
  2014. X            "\304\264");
  2015. X#else
  2016. X        printz ("+----+----+----+----+----+----+----+----+");
  2017. X#endif /* MSDOS && !SEVENBIT */
  2018. X    }
  2019. X#if defined(MSDOS) && !defined(SEVENBIT)
  2020. X      printz ("\300\304\304\304\304\301\304\304\304\304\301\304\304\304\304" \
  2021. X        "\301\304\304\304\304\301\304\304\304\304\301\304\304\304\304" \
  2022. X          "\301\304\304\304\304\301\304\304\304\304\331");
  2023. X#else
  2024. X      printz ("+----+----+----+----+----+----+----+----+");
  2025. X#endif /* MSDOS && !SEVENBIT */
  2026. X      gotoXY (3, 21);
  2027. X      if (flag.reverse)
  2028. X    printz (CP[16]);
  2029. X      else
  2030. X    printz (CP[15]);
  2031. X      for (sq = 0; sq < 64; sq++)
  2032. X    DrawPiece (sq);
  2033. X    }
  2034. X  else
  2035. X    {
  2036. X      DrawPiece (f);
  2037. X      DrawPiece (t);
  2038. X      if (isspec & cstlmask)
  2039. X    if (t > f)
  2040. X      {
  2041. X        DrawPiece (f + 3);
  2042. X        DrawPiece (t - 1);
  2043. X      }
  2044. X    else
  2045. X      {
  2046. X        DrawPiece (f - 4);
  2047. X        DrawPiece (t + 1);
  2048. X      }
  2049. X      else if (isspec & epmask)
  2050. X    {
  2051. X      DrawPiece (t - 8);
  2052. X      DrawPiece (t + 8);
  2053. X    }
  2054. X    }
  2055. X  refresh ();
  2056. X}
  2057. X
  2058. Xchar *InPtr;
  2059. Xvoid
  2060. Xskip ()
  2061. X{
  2062. X  while (*InPtr != ' ')
  2063. X    InPtr++;
  2064. X  while (*InPtr == ' ')
  2065. X    InPtr++;
  2066. X}
  2067. Xvoid
  2068. Xskipb ()
  2069. X{
  2070. X  while (*InPtr == ' ')
  2071. X    InPtr++;
  2072. X}
  2073. X
  2074. Xvoid
  2075. XChangeAlphaWindow (void)
  2076. X{
  2077. X  ShowMessage (CP[114]);
  2078. X  scanz ("%hd", &WAwindow);
  2079. X  ShowMessage (CP[34]);
  2080. X  scanz ("%hd", &BAwindow);
  2081. X}
  2082. X
  2083. Xvoid
  2084. XChangeBetaWindow (void)
  2085. X{
  2086. X  ShowMessage (CP[115]);
  2087. X  scanz ("%hd", &WBwindow);
  2088. X  ShowMessage (CP[35]);
  2089. X  scanz ("%hd", &BBwindow);
  2090. X}
  2091. X
  2092. Xvoid
  2093. XGiveHint (void)
  2094. X{
  2095. X  char s[40];
  2096. X  if (hint)
  2097. X    {
  2098. X      algbr ((short) (hint >> 8), (short) (hint & 0xFF), false);
  2099. X      strcpy (s, CP[198]);    /*try*/
  2100. X      strcat (s, mvstr[0]);
  2101. X      ShowMessage (s);
  2102. X    }
  2103. X  else
  2104. X    ShowMessage (CP[223]);
  2105. X}
  2106. X
  2107. Xvoid
  2108. XChangeHashDepth (void)
  2109. X{
  2110. X  ShowMessage (CP[163]);
  2111. X  scanz ("%hd", &HashDepth);
  2112. X  ShowMessage (CP[82]);
  2113. X  scanz ("%hd", &HashMoveLimit);
  2114. X}
  2115. X
  2116. Xvoid
  2117. XChangeSearchDepth (void)
  2118. X{
  2119. X  ShowMessage (CP[150]);
  2120. X  scanz ("%hd", &MaxSearchDepth);
  2121. X  TCflag = !(MaxSearchDepth > 0);
  2122. X}
  2123. X
  2124. Xvoid
  2125. XSetContempt (void)
  2126. X{
  2127. X  ShowMessage (CP[142]);
  2128. X  scanz ("%hd", &contempt);
  2129. X}
  2130. X
  2131. Xvoid
  2132. XChangeXwindow (void)
  2133. X{
  2134. X  ShowMessage (CP[208]);
  2135. X  scanz ("%hd", &xwndw);
  2136. X}
  2137. X
  2138. Xvoid
  2139. XSelectLevel (void)
  2140. X{
  2141. X  ClrScreen ();
  2142. X  gotoXY (32, 2);
  2143. X  printz (CP[41]);
  2144. X  gotoXY (20, 4);
  2145. X  printz (CP[18]);
  2146. X  gotoXY (20, 5);
  2147. X  printz (CP[19]);
  2148. X  gotoXY (20, 6);
  2149. X  printz (CP[20]);
  2150. X  gotoXY (20, 7);
  2151. X  printz (CP[21]);
  2152. X  gotoXY (20, 8);
  2153. X  printz (CP[22]);
  2154. X  gotoXY (20, 9);
  2155. X  printz (CP[23]);
  2156. X  gotoXY (20, 10);
  2157. X  printz (CP[24]);
  2158. X  gotoXY (20, 11);
  2159. X  printz (CP[25]);
  2160. X  gotoXY (20, 12);
  2161. X  printz (CP[26]);
  2162. X  gotoXY (20, 13);
  2163. X  printz (CP[27]);
  2164. X
  2165. X  OperatorTime = 0;
  2166. X  TCmoves = 60;
  2167. X  TCminutes = 5;
  2168. X  TCseconds = 0;
  2169. X
  2170. X  gotoXY (20, 17);
  2171. X  printz (CP[62]);
  2172. X  refresh ();
  2173. X  scanz ("%ld", &Level);
  2174. X  switch ((int) Level)
  2175. X    {
  2176. X    case 1:
  2177. X      TCmoves = 60;
  2178. X      TCminutes = 5;
  2179. X      break;
  2180. X    case 2:
  2181. X      TCmoves = 60;
  2182. X      TCminutes = 15;
  2183. X      break;
  2184. X    case 3:
  2185. X      TCmoves = 60;
  2186. X      TCminutes = 30;
  2187. X      break;
  2188. X    case 4:
  2189. X      TCmoves = 40;
  2190. X      TCminutes = 30;
  2191. X      break;
  2192. X    case 5:
  2193. X      TCmoves = 40;
  2194. X      TCminutes = 60;
  2195. X      break;
  2196. X    case 6:
  2197. X      TCmoves = 40;
  2198. X      TCminutes = 120;
  2199. X      break;
  2200. X    case 7:
  2201. X      TCmoves = 40;
  2202. X      TCminutes = 240;
  2203. X      break;
  2204. X    case 8:
  2205. X      TCmoves = 1;
  2206. X      TCminutes = 15;
  2207. X      break;
  2208. X    case 9:
  2209. X      TCmoves = 1;
  2210. X      TCminutes = 60;
  2211. X      break;
  2212. X    case 10:
  2213. X      TCmoves = 1;
  2214. X      TCminutes = 600;
  2215. X      break;
  2216. X    }
  2217. X
  2218. X  TCflag = (TCmoves > 0);
  2219. X  SetTimeControl ();
  2220. X  ClrScreen ();
  2221. X  UpdateDisplay (0, 0, 1, 0);
  2222. X}
  2223. X
  2224. Xvoid
  2225. XDoDebug (void)
  2226. X{
  2227. X  short c, p, sq, tp, tc, tsq, score;
  2228. X  char s[40];
  2229. X
  2230. X  ExaminePosition ();
  2231. X  ShowMessage (CP[65]);
  2232. X  scanz ("%s", s);
  2233. X  c = neutral;
  2234. X  if (s[0] == CP[9][0] || s[0] == CP[9][1])    /* w W*/
  2235. X    c = white;
  2236. X  if (s[0] == CP[9][2] || s[0] == CP[9][3])    /*b B*/
  2237. X    c = black;
  2238. X  for (p = king; p > no_piece; p--)
  2239. X    if ((s[1] == pxx[p]) || (s[1] == qxx[p]))
  2240. X      break;
  2241. X  for (sq = 0; sq < 64; sq++)
  2242. X    {
  2243. X      tp = board[sq];
  2244. X      tc = color[sq];
  2245. X      board[sq] = p;
  2246. X      color[sq] = c;
  2247. X      tsq = PieceList[c][1];
  2248. X      PieceList[c][1] = sq;
  2249. X      ShowPostnValue (sq);
  2250. X      PieceList[c][1] = tsq;
  2251. X      board[sq] = tp;
  2252. X      color[sq] = tc;
  2253. X    }
  2254. X  score = ScorePosition (opponent);
  2255. X  gotoXY (TAB, 5);
  2256. X  printz (CP[103], score, mtl[computer], pmtl[computer], pscore[computer], mtl[opponent], pmtl[opponent], pscore[opponent]);
  2257. X  ClrEoln ();
  2258. X}
  2259. END_OF_FILE
  2260. if test 17782 -ne `wc -c <'src/uxdsp.c'`; then
  2261.     echo shar: \"'src/uxdsp.c'\" unpacked with wrong size!
  2262. fi
  2263. # end of 'src/uxdsp.c'
  2264. fi
  2265. if test -f 'test/test-mchess' -a "${1}" != "-c" ; then 
  2266.   echo shar: Will not clobber existing file \"'test/test-mchess'\"
  2267. else
  2268. echo shar: Extracting \"'test/test-mchess'\" \(500 characters\)
  2269. sed "s/^X//" >'test/test-mchess' <<'END_OF_FILE'
  2270. XBlack comPuter White Human 1 #correct move d4d5
  2271. XCastled White false Black false
  2272. XTimeControl 0 OPerator Time 0
  2273. XWhite Clock 0000 Moves 0
  2274. XBlack Clock 0000 Moves 0
  2275. X
  2276. X8 R....RK. 10 10 10 10 10 10 10 10
  2277. X7 .PP...BP 10 10 10 10 10 10 10 10
  2278. X6 P..P.... 10 10 10 10 10 10 10 10
  2279. X5 ...QBb. 10 10 10 10 10 10 10 10
  2280. X4 ....P.P 10 10 10 10 10 10 10 10
  2281. X3 .n...N. 10 10 10 10 10 10 10 10
  2282. X2 p.q..p. 10 10 10 10 10 10 10 10
  2283. X1 .bkrr... 10 10 10 10 10 10 10 10
  2284. X  abcdefgh
  2285. X
  2286. Xmove  score dePth  nodes  time flags caPture color
  2287. END_OF_FILE
  2288. if test 500 -ne `wc -c <'test/test-mchess'`; then
  2289.     echo shar: \"'test/test-mchess'\" unpacked with wrong size!
  2290. fi
  2291. # end of 'test/test-mchess'
  2292. fi
  2293. echo shar: End of archive 5 \(of 12\).
  2294. cp /dev/null ark5isdone
  2295. MISSING=""
  2296. for I in 1 2 3 4 5 6 7 8 9 10 11 12 ; do
  2297.     if test ! -f ark${I}isdone ; then
  2298.     MISSING="${MISSING} ${I}"
  2299.     fi
  2300. done
  2301. if test "${MISSING}" = "" ; then
  2302.     echo You have unpacked all 12 archives.
  2303.     rm -f ark[1-9]isdone ark[1-9][0-9]isdone
  2304.     echo Building book file.
  2305.     cat misc/book.xaa misc/book.xab > misc/gnuchess.nunn.book
  2306.     rm misc/book.xaa misc/book.xab
  2307. else
  2308.     echo You still need to unpack the following archives:
  2309.     echo "        " ${MISSING}
  2310. fi
  2311. ##  End of shell archive.
  2312. exit 0
  2313.