diff options
Diffstat (limited to 'src/ct1986.c')
| -rw-r--r-- | src/ct1986.c | 394 |
1 files changed, 197 insertions, 197 deletions
diff --git a/src/ct1986.c b/src/ct1986.c index 93dd7b9..f9046ce 100644 --- a/src/ct1986.c +++ b/src/ct1986.c @@ -1,21 +1,21 @@ /* - ct1986, an interface to the ct library designed to be embedded on - a Raspberry Pi Zero + ct1986, an interface to the ct library designed to be embedded on + a Raspberry Pi Zero - Copyright (C) 2021, tslil clingman + 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 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. + 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 <https://www.gnu.org/licenses/>. + You should have received a copy of the GNU General Public License + along with this program. If not, see <https://www.gnu.org/licenses/>. */ #include <stdlib.h> @@ -33,92 +33,92 @@ static char *gamelog = 0; static void new_game(uint8_t size) { - reset_state(size); - lcd_printf_line(L_SCROLL, "New 5s game @ D%d", - negamax_search_depth); - if (gamelog) gamelog = realloc(gamelog, sizeof(char)); - else gamelog = malloc(sizeof(char)); - gamelog[0] = 0; + reset_state(size); + lcd_printf_line(L_SCROLL, "New 5s game @ D%d", + negamax_search_depth); + if (gamelog) gamelog = realloc(gamelog, sizeof(char)); + else gamelog = malloc(sizeof(char)); + gamelog[0] = 0; } static int append_to_gamelog(const char *line, const uint8_t win_line) { - // I _could_ dynamically compute the size but ... don't let - // `perfect' be the enemy of `good' ? - - if (gamelog == NULL) return EXIT_FAILURE; - - char prepend[8]; - - if (win_line) { - prepend[0] = '\n'; - prepend[1] = 0; - } else if (ply & 1) { - snprintf(prepend, 7, "%s%d. ", - (ply == 1) ? "" : "\n", ply/2+1); - } else { - strcpy(prepend, " "); - } - // Make room for this line - gamelog = realloc(gamelog, - strlen(gamelog) - + strlen(prepend) - + strlen(line) + 1); - // TODO: trap errno - strcat(gamelog, prepend); - strcat(gamelog, line); - - return EXIT_SUCCESS; + // I _could_ dynamically compute the size but ... don't let + // `perfect' be the enemy of `good' ? + + if (gamelog == NULL) return EXIT_FAILURE; + + char prepend[8]; + + if (win_line) { + prepend[0] = '\n'; + prepend[1] = 0; + } else if (ply & 1) { + snprintf(prepend, 7, "%s%d. ", + (ply == 1) ? "" : "\n", ply/2+1); + } else { + strcpy(prepend, " "); + } + // Make room for this line + gamelog = realloc(gamelog, + strlen(gamelog) + + strlen(prepend) + + strlen(line) + 1); + // TODO: trap errno + strcat(gamelog, prepend); + strcat(gamelog, line); + + return EXIT_SUCCESS; } static void end_game(char *line, char *win) { - append_to_gamelog(line, 0); - append_to_gamelog(win, 1); - lcd_printf_line(L_SCROLL, "Game over: %s", win); + append_to_gamelog(line, 0); + append_to_gamelog(win, 1); + lcd_printf_line(L_SCROLL, "Game over: %s", win); } static int handle_turn(char *line) { - // Track win state - uint8_t new_win = (won == 0xFF); - switch (do_ptn(line)) { - // Errors - case ACT_INVALID_PTN: { - lcd_put_line(L_SCROLL, "Invalid PTN."); - break; - } - case ACT_ILLEGAL: { - lcd_put_line(L_SCROLL, "Illegal ply."); - break; } - case ACT_OVERFLOW: { - lcd_put_line(L_SCROLL, "Overflow."); - break; - } - // Game has ended - case GAME_END: { - // Did it end this turn? - if (new_win) { - switch (won) { - case WIN_DRAW: { end_game(line,"1/2-1/2"); break; } - case WIN_FLAT_BLACK: { end_game(line,"0-F"); break; } - case WIN_FLAT_WHITE: { end_game(line,"F-0"); break; } - case WIN_ROAD_BLACK: { end_game(line,"0-R"); break; } - case WIN_ROAD_WHITE: { end_game(line,"R-0"); break; } - } - return EXIT_SUCCESS; - } else { - lcd_put_line(L_SCROLL, "Game over."); - break; - } - } - // Valid, append to game log - default: { - append_to_gamelog(line, 0); - return EXIT_SUCCESS; - } + // Track win state + uint8_t new_win = (won == 0xFF); + switch (do_ptn(line)) { + // Errors + case ACT_INVALID_PTN: { + lcd_put_line(L_SCROLL, "Invalid PTN."); + break; + } + case ACT_ILLEGAL: { + lcd_put_line(L_SCROLL, "Illegal ply."); + break; } + case ACT_OVERFLOW: { + lcd_put_line(L_SCROLL, "Overflow."); + break; + } + // Game has ended + case GAME_END: { + // Did it end this turn? + if (new_win) { + switch (won) { + case WIN_DRAW: { end_game(line,"1/2-1/2"); break; } + case WIN_FLAT_BLACK: { end_game(line,"0-F"); break; } + case WIN_FLAT_WHITE: { end_game(line,"F-0"); break; } + case WIN_ROAD_BLACK: { end_game(line,"0-R"); break; } + case WIN_ROAD_WHITE: { end_game(line,"R-0"); break; } } - return EXIT_FAILURE; + return EXIT_SUCCESS; + } else { + lcd_put_line(L_SCROLL, "Game over."); + break; + } + } + // Valid, append to game log + default: { + append_to_gamelog(line, 0); + return EXIT_SUCCESS; + } + } + return EXIT_FAILURE; } @@ -127,53 +127,53 @@ static uint32_t perc; inline void negamax_display_progress(const uint8_t depth, const uint32_t length) { - if (depth == negamax_search_depth) { - lcd_printf_line(L_OVERWRITE, "Computing: %d%%", - (++perc*100)/length); - } + if (depth == negamax_search_depth) { + lcd_printf_line(L_OVERWRITE, "Computing: %d%%", + (++perc*100)/length); + } } static int negamax_turn() { - // Prepare progress bar - perc = 0; - lcd_put_line(L_SCROLL, "Computing: 0%"); - // Run the minimax - float minimax = negamax_generate(); - // Failed to find a move? - if (minimax < -infty) { - lcd_printf_line(L_SCROLL, "%s concedes!", - (ply & 1) ? "Black" : "White"); - return EXIT_FAILURE; - } else { - lcd_printf_line(L_SCROLL, "%s: %s", - (ply & 1) ? "Black" : "White", - negamax_ptn); - return handle_turn(negamax_ptn); - } + // Prepare progress bar + perc = 0; + lcd_put_line(L_SCROLL, "Computing: 0%"); + // Run the minimax + float minimax = negamax_generate(); + // Failed to find a move? + if (minimax < -infty) { + lcd_printf_line(L_SCROLL, "%s concedes!", + (ply & 1) ? "Black" : "White"); + return EXIT_FAILURE; + } else { + lcd_printf_line(L_SCROLL, "%s: %s", + (ply & 1) ? "Black" : "White", + negamax_ptn); + return handle_turn(negamax_ptn); + } } static void do_game_log(void) { - lcd_put_line(L_SCROLL, "TODO!"); + lcd_put_line(L_SCROLL, "TODO!"); } static int input_is_not_turn(const char *line) { - switch (line[0]) { - case 'l': { do_game_log(); break; } - case 'n': { new_game(5); break; } - case 'D': { - negamax_search_depth = line[1] - '0'; - lcd_printf_line(L_SCROLL, "Search depth: %d", - negamax_search_depth); - break; - } - case 'B': { human = 1; new_game(5); break; } - case 'W': { human = 0; new_game(5); break; } - default: return EXIT_FAILURE; - } - return EXIT_SUCCESS; + switch (line[0]) { + case 'l': { do_game_log(); break; } + case 'n': { new_game(5); break; } + case 'D': { + negamax_search_depth = line[1] - '0'; + lcd_printf_line(L_SCROLL, "Search depth: %d", + negamax_search_depth); + break; + } + case 'B': { human = 1; new_game(5); break; } + case 'W': { human = 0; new_game(5); break; } + default: return EXIT_FAILURE; + } + return EXIT_SUCCESS; } const char* license = "ct1986, an interface to the ct library designed to be embedded on a Raspberry Pi Zero\n\ @@ -187,85 +187,85 @@ static char line[LINE_BUFF_LEN+1]; static int poll_input(void) { - char c, *prompt; - int idx = 0, polling = 1; - - if (ply & 1) prompt = "Black: "; - else prompt = "White: "; - - lcd_put_line(L_SCROLL, prompt); - - line[0] = 0; - while (polling) { - lcd_printf_line(L_OVERWRITE, "%s%s", prompt, line); - c = getchar(); - switch (c) { - case 0x7F: { - if (idx>0) idx--; - line[idx] = 0; - break; - } - case 0xFF: // fall-through - case '\r': // fall-through - case '\n': { - polling = 0; - break; - } - default: { - if (idx+1<LINE_BUFF_LEN) { - line[idx] = c; - line[++idx] = 0; - } - break; - } - } + char c, *prompt; + int idx = 0, polling = 1; + + if (ply & 1) prompt = "Black: "; + else prompt = "White: "; + + lcd_put_line(L_SCROLL, prompt); + + line[0] = 0; + while (polling) { + lcd_printf_line(L_OVERWRITE, "%s%s", prompt, line); + c = getchar(); + switch (c) { + case 0x7F: { + if (idx>0) idx--; + line[idx] = 0; + break; + } + case 0xFF: // fall-through + case '\r': // fall-through + case '\n': { + polling = 0; + break; + } + default: { + if (idx+1<LINE_BUFF_LEN) { + line[idx] = c; + line[++idx] = 0; } - return idx; + break; + } + } + } + return idx; } int main(int argc, char **argv) { - (void)(argc); - (void)(argv); - - puts(license); - - if (lcd_begin() != EXIT_SUCCESS) - return EXIT_FAILURE; - - initscr(); - - negamax_search_depth = 3; - new_game(5); - negamax_init(5); - - human = 0; - for (int playing = 1; playing;) { - while (human == 0) { - lcd_set_blink(); - if (poll_input() > 0) { - if (input_is_not_turn(line)) { - int r = handle_turn(line); - if (r == EXIT_SUCCESS && won == 0xFF) { - human = 1; - } - } - } else { - playing = 0; - human = 1; - } - } - lcd_stop_blink(); - if (playing) { - negamax_turn(); - human = 0; - } + (void)(argc); + (void)(argv); + + puts(license); + + if (lcd_begin() != EXIT_SUCCESS) + return EXIT_FAILURE; + + initscr(); + + negamax_search_depth = 3; + new_game(5); + negamax_init(5); + + human = 0; + for (int playing = 1; playing;) { + while (human == 0) { + lcd_set_blink(); + if (poll_input() > 0) { + if (input_is_not_turn(line)) { + int r = handle_turn(line); + if (r == EXIT_SUCCESS && won == 0xFF) { + human = 1; + } } - - free(gamelog); - negamax_free(); - - lcd_end(); - endwin(); - - return EXIT_SUCCESS; + } else { + playing = 0; + human = 1; + } + } + lcd_stop_blink(); + if (playing) { + negamax_turn(); + human = 0; + } + } + + free(gamelog); + negamax_free(); + + lcd_end(); + endwin(); + + return EXIT_SUCCESS; } |
