All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros
csaClient.cc
Go to the documentation of this file.
1 /* csaClient.cc
2  */
9 #include "osl/record/csa.h"
10 #include "osl/record/csaIOError.h"
12 #include "osl/sennichite.h"
13 #include "osl/misc/ctime.h"
14 #include <boost/foreach.hpp>
15 #include <iostream>
16 
19  CsaLogger *l, std::istream& is, std::ostream& os)
20  : CuiClient(black, white, l, is, os),
21  show_move_with_comment(false), silent(false), line(128,' ')
22 {
23  setComputerPlayer(WHITE, true);
24 }
25 
28 {
29 }
30 
33 {
34  char ctime_buf[64];
35  if (! silent) {
36  std::cerr << "\nCsaClient start waiting ";
37  const time_t now = time(0);
38  std::cerr << ctime_r(&now, ctime_buf)
39  << state->state()
40  << "TIME[" << time_keeper.timeElapsed(BLACK)
41  << ":" << time_keeper.timeElapsed(WHITE)
42  << "] ";
43  const MoveStack& history = state->moveHistory();
44  const vector<int>& eval_history = state->evalStack();
45  for (int i=1; i<=8 && history.hasLastMove(i); ++i) {
46  std::cerr << "(" << history.size() - i + 1 << ")" << record::csa::show(history.lastMove(i));
47  if (i-1 < (int)eval_history.size() && eval_history[eval_history.size()-i])
48  std::cerr << "<" << eval_history[eval_history.size()-i] << ">";
49  std::cerr << " ";
50  }
51  std::cerr << std::endl << std::endl;
52  }
54  std::getline(is, line);
55  if (! silent) {
56  std::cerr << "\nCsaClient read " << line << " ";
57  const time_t now = time(0);
58  std::cerr << ctime_r(&now, ctime_buf)
59  << std::endl;
60  }
61  const long op_think_time = timer.read();
62  if (! is)
63  {
64  const char *message = "istream error (maybe closed)";
65  std::cerr << message << std::cerr;
66  logger->writeComment(message);
67  throw EndGame();
68  }
69 
70  if (line == "%TORYO")
71  {
72  logger->resign(state->state().turn());
73  throw EndGame();
74  }
75 
76  // TODO: %MATTA, %CHUDAN
77  try
78  {
79  const Move op_move=record::csa::strToMove(line, state->state());
80  const GameState::MoveType illegal_move = state->isIllegal(op_move);
81  if (illegal_move)
82  {
83  std::cerr << "illegal move: " << line << "\n";
84  logger->inputError(line.c_str());
85  if (illegal_move == GameState::PAWN_DROP_FOUL)
86  logger->writeComment("pawn drop foul");
87  else if (illegal_move == GameState::UNSAFE_KING)
88  logger->writeComment("unsafe king");
89  else if (illegal_move == GameState::OTHER_INVALID)
90  logger->writeComment("other illegal move");
91  os << "%CHUDAN" << std::endl;
92  throw EndGame();
93  }
94  const Sennichite result = pushMove(MoveWithComment(op_move), op_think_time);
95  if (! result.isNormal())
96  {
97  os << "%SENNICHITE" << std::endl;
98  logger->endByRepetition(result);
99  throw EndGame();
100  }
101  if (! silent) {
102  std::cerr << state->state()
103  << "TIME[" << time_keeper.timeElapsed(BLACK)
104  << ":" << time_keeper.timeElapsed(WHITE)
105  << "] ";
106  const MoveStack& history = state->moveHistory();
107  const vector<int>& eval_history = state->evalStack();
108  for (int i=1; i<=8 && history.hasLastMove(i); ++i) {
109  std::cerr << "(" << history.size() - i + 1 << ")" << record::csa::show(history.lastMove(i));
110  if (i-1 < (int)eval_history.size() && eval_history[eval_history.size()-i])
111  std::cerr << "<" << eval_history[eval_history.size()-i] << "> ";
112  std::cerr << " ";
113  }
114  std::cerr << std::endl << std::endl;
115  }
116  }
117  catch (record::csa::CsaIOError&)
118  {
119  std::cerr << "bad input: " << line << "\n";
120  logger->inputError(line.c_str());
121  throw EndGame();
122  }
123  return false;
124 }
125 
128 {
129  show_move_with_comment = value;
130 }
131 
133 CsaClient::processComputerMove(const MoveWithComment& selected,
134  int my_think_time)
135 {
136  static std::string reserved="+7776FU";
137  const Move best_move = selected.move;
138  if ((! best_move.isNormal())
139  || (state->isIllegal(best_move)))
140  {
141  if (best_move == Move::DeclareWin())
142  {
143  os << "%KACHI\n";
144  logger->endByDeclaration(state->state().turn());
145  }
146  else
147  {
148  if (best_move.isNormal()) {
149  std::cerr << "error: prefer resign to playing illegal move " << best_move << " code " << state->isIllegal(best_move) << "\n";
150  logger->writeComment("error: prefer abort to playing illegal move");
151  abort();
152  }
153  os << "%TORYO\n";
154  logger->resign(state->state().turn());
155  }
156  throw EndGame();
157  }
158 
159  os << record::csa::show(best_move, reserved);
160  if (show_move_with_comment && (! selected.moves.empty() || selected.value != 0))
161  {
162  os << ",'* " << selected.value;
163  BOOST_FOREACH(Move move, selected.moves)
164  {
165  os << " ";
166  os << record::csa::show(move, reserved);
167  }
168  }
169  os << std::endl << std::flush;
170 
171  assert(isComputer(state->state().turn()));
172 
173  const Sennichite result = pushMove(selected, my_think_time);
174  if (! result.isNormal())
175  {
176  logger->endByRepetition(result);
177  throw EndGame();
178  }
179 }
180 
181 /* ------------------------------------------------------------------------- */
182 // ;;; Local Variables:
183 // ;;; mode:c++
184 // ;;; c-basic-offset:2
185 // ;;; End: