home *** CD-ROM | disk | FTP | other *** search
/ Dream 57 / Amiga_Dream_57.iso / Amiga / Jeux / Reflexion / Crafty-15.19.lha / crafty-15.19 / src / searchmp.c < prev    next >
C/C++ Source or Header  |  1998-09-13  |  8KB  |  178 lines

  1. #include <stdio.h>
  2. #include <stdlib.h>
  3. #include <string.h>
  4. #include "chess.h"
  5. #include "data.h"
  6. #include "epdglue.h"
  7.  
  8. /* modified 04/08/98 */
  9. /*
  10. ********************************************************************************
  11. *                                                                              *
  12. *   SearchSMP() is the recursive routine used to implement the alpha/beta      *
  13. *   negamax search using parallel threads.  when this code is called, the      *
  14. *   first move has already been searched, so all that is left is to search the *
  15. *   remainder of the moves and then return.  note that the hash table and such *
  16. *   can't be modified here since this only represents a part of the search at  *
  17. *   this ply.                                                                  *
  18. *                                                                              *
  19. ********************************************************************************
  20. */
  21. #if defined(SMP)
  22. int SearchSMP(TREE *tree, int alpha, int beta, int value, int wtm,
  23.               int depth, int ply, int threat) {
  24.   register int extensions;
  25. /*
  26.  ----------------------------------------------------------
  27. |                                                          |
  28. |   now iterate through the move list and search the       |
  29. |   resulting positions.  note that Search() culls any     |
  30. |   move that is not legal by using Check().  the special  |
  31. |   case is that we must find one legal move to search to  |
  32. |   confirm that it's not a mate or draw.                  |
  33. |                                                          |
  34.  ----------------------------------------------------------
  35. */
  36.   while (1) {
  37.     Lock(tree->parent->lock);
  38.     tree->current_phase[ply]=(tree->in_check[ply]) ? 
  39.                              NextEvasion((TREE*)tree->parent,ply,wtm) : 
  40.                              NextMove((TREE*)tree->parent,ply,wtm);
  41.     tree->current_move[ply]=tree->parent->current_move[ply];
  42.     UnLock(tree->parent->lock);
  43.     if (!tree->current_phase[ply]) break;
  44.     tree->extended_reason[ply]&=check_extension;
  45. #if !defined(FAST)
  46.     if (ply <= trace_level)
  47.       SearchTrace(tree,ply,depth,wtm,alpha,beta,"SearchSMP",tree->current_phase[ply]);
  48. #endif
  49. /*
  50.  ----------------------------------------------------------
  51. |                                                          |
  52. |   if two successive moves are capture / re-capture so    |
  53. |   that the material score is restored, extend the search |
  54. |   by one ply on the re-capture since it is pretty much   |
  55. |   forced and easy to analyze.                            |
  56. |                                                          |
  57.  ----------------------------------------------------------
  58. */
  59.     extensions=-60;
  60.     if (threat) extensions+=threat_depth;
  61.     if (Captured(tree->current_move[ply]) && Captured(tree->current_move[ply-1]) &&
  62.         To(tree->current_move[ply-1]) == To(tree->current_move[ply]) &&
  63.         (p_values[Captured(tree->current_move[ply-1])+7] == 
  64.          p_values[Captured(tree->current_move[ply])+7] ||
  65.          Promote(tree->current_move[ply-1])) &&
  66.         !(tree->extended_reason[ply-1]&recapture_extension)) {
  67.       tree->extended_reason[ply]|=recapture_extension;
  68.       tree->recapture_extensions_done++;
  69.       extensions+=recap_depth;
  70.     }
  71. /*
  72.  ----------------------------------------------------------
  73. |                                                          |
  74. |   if we push a passed pawn, we need to look deeper to    |
  75. |   see if it is a legitimate threat.                      |
  76. |                                                          |
  77.  ----------------------------------------------------------
  78. */
  79.     if (Piece(tree->current_move[ply])==pawn && 
  80.          ((wtm && To(tree->current_move[ply])>H5 && TotalBlackPieces<16 &&
  81.           !And(mask_pawn_passed_w[To(tree->current_move[ply])],BlackPawns)) ||
  82.          (!wtm && To(tree->current_move[ply])<A4 && TotalWhitePieces<16 &&
  83.           !And(mask_pawn_passed_b[To(tree->current_move[ply])],WhitePawns)) ||
  84.          push_extensions[To(tree->current_move[ply])]) &&
  85.          Swap(tree,From(tree->current_move[ply]),To(tree->current_move[ply]),wtm) ==
  86.            p_values[Captured(tree->current_move[ply])+7]) {
  87.       tree->extended_reason[ply]|=passed_pawn_extension;
  88.       tree->passed_pawn_extensions_done++;
  89.       extensions+=pushpp_depth;
  90.     }
  91. /*
  92.  ----------------------------------------------------------
  93. |                                                          |
  94. |   now make the move and search the resulting position.   |
  95. |   if we are in check, the current move must be legal     |
  96. |   since NextEvasion ensures this, otherwise we have to   |
  97. |   make sure the side-on-move is not in check after the   |
  98. |   move to weed out illegal moves and save time.          |
  99. |                                                          |
  100.  ----------------------------------------------------------
  101. */
  102.     MakeMove(tree,ply,tree->current_move[ply],wtm);
  103.     if (tree->in_check[ply] || !Check(wtm)) {
  104. /*
  105.  ----------------------------------------------------------
  106. |                                                          |
  107. |   if the move to be made checks the opponent, then we    |
  108. |   need to remember that he's in check and also extend    |
  109. |   the depth by one ply for him to get out.               |
  110. |                                                          |
  111.  ----------------------------------------------------------
  112. */
  113.       if (Check(ChangeSide(wtm))) {
  114.         tree->in_check[ply+1]=1;
  115.         tree->extended_reason[ply+1]=check_extension;
  116.         tree->check_extensions_done++;
  117.         extensions+=incheck_depth;
  118.       }
  119.       else {
  120.         tree->in_check[ply+1]=0;
  121.         tree->extended_reason[ply+1]=no_extension;
  122.       }
  123. /*
  124.  ----------------------------------------------------------
  125. |                                                          |
  126. |   now we toss in the "razoring" trick, which simply says |
  127. |   if we are doing fairly badly, we can reduce the depth  |
  128. |   an additional ply, if there was nothing at the current |
  129. |   ply that caused an extension.                          |
  130. |                                                          |
  131.  ----------------------------------------------------------
  132. */
  133.       if (depth<3*INCREMENT_PLY && depth>=2*INCREMENT_PLY &&
  134.           !tree->in_check[ply] && extensions == -60) {
  135.         register int value=-Evaluate(tree,ply+1,ChangeSide(wtm),
  136.                                      -(beta+51),-(alpha-51));
  137.         if (value+50 < alpha) extensions-=60;
  138.       }
  139.       extensions=Min(extensions,0);
  140.       value=-ABSearch(tree,-alpha-1,-alpha,ChangeSide(wtm),
  141.                       depth+extensions,ply+1,DO_NULL);
  142.       if (abort_search || tree->stop) {
  143.         UnMakeMove(tree,ply,tree->current_move[ply],wtm);
  144.         break;
  145.       }
  146.       if (value>alpha && value<beta) {
  147.         value=-ABSearch(tree,-beta,-alpha,ChangeSide(wtm),
  148.                         depth+extensions,ply+1,DO_NULL);
  149.         if (abort_search || tree->stop) {
  150.           UnMakeMove(tree,ply,tree->current_move[ply],wtm);
  151.           break;
  152.         }
  153.       }
  154.       if (value > alpha) {
  155.         if(value >= beta) {
  156.           register int proc;
  157.           UnMakeMove(tree,ply,tree->current_move[ply],wtm);
  158.           tree->search_value=value;
  159.           Lock(tree->parent->lock);
  160.           if (!tree->stop) {
  161.             for (proc=0;proc<max_threads;proc++)
  162.               if (tree->parent->siblings[proc] && proc != tree->thread_id)
  163.                 ThreadStop(tree->parent->siblings[proc]);
  164.           }
  165.           UnLock(tree->parent->lock);
  166.           break;
  167.         }
  168.         alpha=value;
  169.       }
  170.     }
  171.     UnMakeMove(tree,ply,tree->current_move[ply],wtm);
  172.     tree->search_value=alpha;
  173.   }
  174.   tree->parent->done=1;
  175.   return(0);
  176. }
  177. #endif
  178.