/* cttei, a TEI interface to the ct library & its computer opponent Copyright (C) 2021, tslil clingman This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program. If not, see . */ #include #include #include #include #include #include // Set up output function for negamax inline void negamax_display_progress(const uint8_t cur_depth, const uint8_t init_depth, const uint32_t length) { (void)(cur_depth); (void)(init_depth); (void)(length); } enum TEI_RETURN { TEI_QUIT, TEI_OK, TEI_FAILURE }; // expects ``(startpos|tps ) moves '' static enum TEI_RETURN parse_position_string(tak_state_p state, char *line) { // Find the word ``moves'' char *beg = strstr(line, "moves"); if (!strncasecmp(line, "tps", 3)) { // Split the string on the space before moves if (beg) *(beg - 1) = 0; // so that we can load it as a TPS description load_tps(state, line + 4); } else if (!strncasecmp(line, "startpos", 8)) { reset_state(state, 5); } else { return TEI_FAILURE; } if (beg == NULL) return TEI_OK; // parse the PTN sequence strtok(beg, " "); char *ptn = strtok(NULL, " "); while (ptn != NULL) { if (do_ptn(state, ptn) != ACT_OK) return TEI_FAILURE; ptn = strtok(NULL, " "); } return TEI_OK; } static enum TEI_RETURN handle_tei(tak_state_p state, char *line) { if (!strcmp(line, "quit")) { return TEI_QUIT; } if (!strcmp(line, "isready")) { puts("readyok"); } else if (!strncmp(line, "setoption Depth value ", 22)) { negamax_search_depth = atoi(line + 23); } else if (!strncmp(line, "go", 2)) { // TODO: for now we ignore all of the parameters float minimax = negamax_generate(state); enum ACT_RESULT r = do_ptn(state, negamax_ptn); if (r != ACT_OK && r != GAME_END) return TEI_FAILURE; printf("info score cp %f pv %s\nbestmove %s\n", minimax, negamax_ptn, negamax_ptn); } else if (!strncmp(line, "position", 8)) { return parse_position_string(state, line + 9); } else if (!strncmp(line, "teinewgame", 10)) { if (line[11] != '5') return TEI_FAILURE; const uint8_t size = atoi(line + 11); if (size != 5) { return TEI_FAILURE; } else { reset_state(state, 5); } } fflush(stdout); return TEI_OK; } const char *license = "cttei, a TEI interface to the ct library & its computer opponent\n\ \n\ Copyright (C) 2021, tslil clingman\n\ \n\ This program comes with ABSOLUTELY NO WARRANTY; and is made available under the terms of the GNU GPL v3 license. This is free software, and you are welcome to redistribute it under certain conditions; see COPYING for details.\n"; int main(int argc, char **argv) { (void)(argc); (void)(argv); puts(license); char *line = NULL; ssize_t read = -1; size_t alloc_size; // Wait for tei while ((read = getline(&line, &alloc_size, stdin))) { if (read > 0 && !strncmp("tei", line, 3)) { break; } else return EXIT_FAILURE; } if (line) free(line); line = NULL; // Identify ourselves, and send the options puts("id name cttei"); puts("id author tslil clingman"); puts("option name Depth type spin default 4 min 2 max 6"); puts("teiok"); fflush(stdout); // Set default option tak_state_p state = new_tak_state(5); negamax_search_depth = 4; negamax_init(5); reset_state(state, 5); for (int playing = 1; playing;) { if ((read = getline(&line, &alloc_size, stdin)) > 0) { line[read - 1] = 0; switch (handle_tei(state, line)) { case TEI_FAILURE: return EXIT_FAILURE; case TEI_QUIT: playing = 0; // fall-through case TEI_OK: { if (line) { free(line); line = NULL; } break; } } } else { break; } } if (line) free(line); negamax_free(); return EXIT_SUCCESS; }