summaryrefslogtreecommitdiff
path: root/apps/plugins/chessbox/chessbox_pgn.c
diff options
context:
space:
mode:
authorWilliam Wilgus <me.theuser@yahoo.com>2017-01-31 04:28:02 +0100
committerWilliam Wilgus <me.theuser@yahoo.com>2017-02-01 01:33:48 +0100
commit1fa7c5635184e3a8c16b696a658c027fcc0862d8 (patch)
treedebeb03ca2da9a20ccfae5ece4fc512847046014 /apps/plugins/chessbox/chessbox_pgn.c
parent37522ec63ae8fd2f88a66ed3d7020ebe95e9980e (diff)
downloadrockbox-1fa7c5635184e3a8c16b696a658c027fcc0862d8.tar.gz
rockbox-1fa7c5635184e3a8c16b696a658c027fcc0862d8.zip
Fix for Chessbox bug FS#10363
Chessbox was overflowing GameList[240] causing the board to flip + crash GameCnt changed to unsigned char which allows the array to roll over to 0 after 255 define MAX_GAME_CNT 256 and GameList[MAX_GAME_CNT] along with 1 byte GameCnt should fix this issue dbg save routine left in for now to help identify any other problems Added bounds checking to prevent second bug found when loading .pgn files Change-Id: I2b615c8ecbed4368724412f80ce07346f3cf30a7
Diffstat (limited to 'apps/plugins/chessbox/chessbox_pgn.c')
-rw-r--r--apps/plugins/chessbox/chessbox_pgn.c70
1 files changed, 47 insertions, 23 deletions
diff --git a/apps/plugins/chessbox/chessbox_pgn.c b/apps/plugins/chessbox/chessbox_pgn.c
index 98d9e29431..f5f19e2688 100644
--- a/apps/plugins/chessbox/chessbox_pgn.c
+++ b/apps/plugins/chessbox/chessbox_pgn.c
@@ -159,9 +159,10 @@ static char pgn_from_piece(unsigned short piece, unsigned short color){
159 return pgn_piece; 159 return pgn_piece;
160} 160}
161 161
162static void pgn_to_coords(struct pgn_ply_node* ply){ 162static bool pgn_to_coords(struct pgn_ply_node* ply){
163 bool success = true;
163 unsigned short str_length = rb->strlen(ply->pgn_text); 164 unsigned short str_length = rb->strlen(ply->pgn_text);
164 char str[10]; 165 char str[9];
165 rb->strcpy(str,ply->pgn_text); 166 rb->strcpy(str,ply->pgn_text);
166 ply->column_from = 0xFF; 167 ply->column_from = 0xFF;
167 ply->row_from = 0xFF; 168 ply->row_from = 0xFF;
@@ -172,6 +173,7 @@ static void pgn_to_coords(struct pgn_ply_node* ply){
172 ply->enpassant = false; 173 ply->enpassant = false;
173 ply->castle = false; 174 ply->castle = false;
174 ply->promotion = false; 175 ply->promotion = false;
176
175 unsigned short i, j, piece; 177 unsigned short i, j, piece;
176 bool found = false; 178 bool found = false;
177 179
@@ -342,16 +344,25 @@ static void pgn_to_coords(struct pgn_ply_node* ply){
342 /* leave a very complete log of the parsing of the game while it gets stable */ 344 /* leave a very complete log of the parsing of the game while it gets stable */
343 for (i=0;i<8;i++){ 345 for (i=0;i<8;i++){
344 for (j=0;j<8;j++) { 346 for (j=0;j<8;j++) {
347
345 rb->fdprintf(loghandler,"%c",pgn_from_piece(board[locn[7-i][j]],color[locn[7-i][j]])); 348 rb->fdprintf(loghandler,"%c",pgn_from_piece(board[locn[7-i][j]],color[locn[7-i][j]]));
346 } 349 }
347 rb->fdprintf(loghandler,"\n"); 350 rb->fdprintf(loghandler,"\n");
348 } 351 }
349 352 /* check bounds of row and columns should be 0-7 bad .pgn returns 0xFF */
353 if ((ply->row_to | ply->column_to | ply->row_from | ply->column_from) < 8)
354 {
350 /* update the board */ 355 /* update the board */
351 board[locn[ply->row_to][ply->column_to]] = board[locn[ply->row_from][ply->column_from]]; 356 board[locn[ply->row_to][ply->column_to]] =
352 color[locn[ply->row_to][ply->column_to]] = color[locn[ply->row_from][ply->column_from]]; 357 board[locn[ply->row_from][ply->column_from]];
353 board[locn[ply->row_from][ply->column_from]] = no_piece; 358 color[locn[ply->row_to][ply->column_to]] =
354 color[locn[ply->row_from][ply->column_from]] = neutral; 359 color[locn[ply->row_from][ply->column_from]];
360 board[locn[ply->row_from][ply->column_from]] = no_piece;
361 color[locn[ply->row_from][ply->column_from]] = neutral;
362 }
363 else
364 success = false; /*ERROR*/
365 return success;
355} 366}
356 367
357static void coords_to_pgn(struct pgn_ply_node* ply){ 368static void coords_to_pgn(struct pgn_ply_node* ply){
@@ -657,9 +668,10 @@ void pgn_parse_game(const char* filename,
657 struct pgn_game_node* selected_game){ 668 struct pgn_game_node* selected_game){
658 struct pgn_ply_node size_ply, *first_ply = NULL; 669 struct pgn_ply_node size_ply, *first_ply = NULL;
659 struct pgn_ply_node *temp_ply = NULL, *curr_node = NULL; 670 struct pgn_ply_node *temp_ply = NULL, *curr_node = NULL;
671 bool success = true;
660 int fhandler, i; 672 int fhandler, i;
661 char line_buffer[128]; 673 char line_buffer[128];
662 char token_buffer[10]; 674 char token_buffer[9];
663 unsigned short pos; 675 unsigned short pos;
664 unsigned short curr_player = white; 676 unsigned short curr_player = white;
665 677
@@ -685,24 +697,35 @@ void pgn_parse_game(const char* filename,
685 || (token_buffer[0] >= 'a' && token_buffer[0] <= 'z') 697 || (token_buffer[0] >= 'a' && token_buffer[0] <= 'z')
686 || (token_buffer[0] == '0' && token_buffer[2] != '1')){ 698 || (token_buffer[0] == '0' && token_buffer[2] != '1')){
687 temp_ply = (struct pgn_ply_node *)pl_malloc(sizeof size_ply); 699 temp_ply = (struct pgn_ply_node *)pl_malloc(sizeof size_ply);
688 temp_ply->player = curr_player; 700 /* Null pointer can be returned from pl_malloc check for this */
689 curr_player = (curr_player==white)?black:white; 701 if (temp_ply)
690 rb->strcpy(temp_ply->pgn_text, token_buffer); 702 {
691 pgn_to_coords(temp_ply); 703 temp_ply->player = curr_player;
692 temp_ply->prev_node = NULL; 704 curr_player = (curr_player==white)?black:white;
693 temp_ply->next_node = NULL; 705 rb->strcpy(temp_ply->pgn_text, token_buffer);
694 if (first_ply == NULL) { 706 success = pgn_to_coords(temp_ply);
695 first_ply = curr_node = temp_ply; 707 temp_ply->prev_node = NULL;
696 } else { 708 temp_ply->next_node = NULL;
697 curr_node->next_node = temp_ply; 709 if (first_ply == NULL && success) {
698 temp_ply->prev_node = curr_node; 710 first_ply = curr_node = temp_ply;
699 curr_node = temp_ply; 711 } else if (success){
700 } 712 curr_node->next_node = temp_ply;
701 rb->fdprintf(loghandler, 713 temp_ply->prev_node = curr_node;
702 "player: %u; pgn: %s; from: %u,%u; to: %u,%u; taken: %u.\n", 714 curr_node = temp_ply;
715 } else{
716 /* bad .pgn break loop and notify user */
717 first_ply = NULL;
718 break;
719 }
720
721 rb->fdprintf(loghandler,
722 "player: %u; pgn: %s; from: %u,%u; to: %u,%u; taken: %u.\n",
703 temp_ply->player, temp_ply->pgn_text, temp_ply->row_from, 723 temp_ply->player, temp_ply->pgn_text, temp_ply->row_from,
704 temp_ply->column_from, temp_ply->row_to, 724 temp_ply->column_from, temp_ply->row_to,
705 temp_ply->column_to, temp_ply->taken_piece); 725 temp_ply->column_to, temp_ply->taken_piece);
726 }
727 else
728 first_ply = NULL;
706 } 729 }
707 } 730 }
708 } 731 }
@@ -719,6 +742,7 @@ void pgn_parse_game(const char* filename,
719 curr_node->next_node = temp_ply; 742 curr_node->next_node = temp_ply;
720 } 743 }
721 selected_game->first_ply = first_ply; 744 selected_game->first_ply = first_ply;
745
722 rb->close(fhandler); 746 rb->close(fhandler);
723} 747}
724 748