From 0d35054f3550329c3902bc775ce4c42ba854d9f1 Mon Sep 17 00:00:00 2001
From: Calcitem <calcitem@outlook.com>
Date: Fri, 1 Jan 2021 23:35:41 +0800
Subject: [PATCH] Fix TSC issues

---
 src/position.cpp                         | 14 +++++++-------
 src/position.h                           |  3 ++-
 src/test/test.cpp                        |  6 +-----
 src/thread.cpp                           |  8 ++++----
 src/ui/flutter/command/command_queue.cpp |  8 ++++----
 src/ui/flutter/command/engine_main.cpp   |  2 +-
 src/ui/qt/game.cpp                       | 18 +++++++++---------
 7 files changed, 28 insertions(+), 31 deletions(-)

diff --git a/src/position.cpp b/src/position.cpp
index b3aaadb4..36e35a5b 100644
--- a/src/position.cpp
+++ b/src/position.cpp
@@ -558,7 +558,7 @@ bool Position::reset()
             break;
     }
 
-    if (sprintf(record, "r%1u s%03u t%02u",
+    if (snprintf(record, RECORD_LEN_MAX, "r%1u s%03u t%02u",
                 r + 1, rule.maxStepsLedToDraw, 0) > 0) {
         return true;
     }
@@ -590,7 +590,7 @@ bool Position::start()
 bool Position::put_piece(Square s, bool updateRecord)
 {
     Piece piece = NO_PIECE;
-    int us = sideToMove;
+    Color us = sideToMove;
 
     if (phase == Phase::gameOver ||
         action != Action::place ||
@@ -614,7 +614,7 @@ bool Position::put_piece(Square s, bool updateRecord)
         update_key(s);
 
         if (updateRecord) {
-            sprintf(record, "(%1u,%1u)", file_of(s), rank_of(s));
+            snprintf(record, RECORD_LEN_MAX, "(%1u,%1u)", file_of(s), rank_of(s));
         }
 
         currentSquare = s;
@@ -667,7 +667,7 @@ bool Position::put_piece(Square s, bool updateRecord)
         }
 
         if (updateRecord) {
-            sprintf(record, "(%1u,%1u)->(%1u,%1u)",
+            snprintf(record, RECORD_LEN_MAX, "(%1u,%1u)->(%1u,%1u)",
                     file_of(currentSquare), rank_of(currentSquare),
                     file_of(s), rank_of(s));
             st.rule50++;
@@ -758,7 +758,7 @@ bool Position::remove_piece(Square s, bool updateRecord)
     }
 
     if (updateRecord) {
-        sprintf(record, "-(%1u,%1u)", file_of(s), rank_of(s));
+        snprintf(record, RECORD_LEN_MAX, "-(%1u,%1u)", file_of(s), rank_of(s));
         st.rule50 = 0;     // TODO: Need to move out?
     }
 
@@ -833,7 +833,7 @@ bool Position::resign(Color loser)
 
     set_gameover(~loser, GameOverReason::loseReasonResign);
 
-    //sprintf(record, "Player%d give up!", loser);
+    //snprintf(record, RECORD_LEN_MAX, "Player%d give up!", loser);
     update_score();
 
     return true;
@@ -888,7 +888,7 @@ bool Position::command(const char *cmd)
         winner = DRAW;
         score_draw++;
         gameOverReason = GameOverReason::drawReasonThreefoldRepetition;
-        //sprintf(record, "Threefold Repetition. Draw!");
+        //snprintf(record, RECORD_LEN_MAX, "Threefold Repetition. Draw!");
         return true;
     }
 #endif /* THREEFOLD_REPETITION */
diff --git a/src/position.h b/src/position.h
index 35a7c370..86101a37 100644
--- a/src/position.h
+++ b/src/position.h
@@ -189,7 +189,8 @@ public:
     Square currentSquare;
     int gamesPlayedCount { 0 };
 
-    char record[64] { '\0' };
+    const static int RECORD_LEN_MAX = 64;
+    char record[RECORD_LEN_MAX] { '\0' };
 
     Move move { MOVE_NONE };
 };
diff --git a/src/test/test.cpp b/src/test/test.cpp
index e9162f5e..ff2c9dac 100644
--- a/src/test/test.cpp
+++ b/src/test/test.cpp
@@ -171,11 +171,7 @@ void Test::writeToMemory(const QString &record)
     }
 
     char from[BUFSIZ] = { 0 };
-#ifdef _WIN32
-    strcpy_s(from, record.toStdString().c_str());
-#else
-    strcpy(from, record.toStdString().c_str());
-#endif
+    strncpy(from, record.toStdString().c_str(), BUFSIZ);
 
     while (true) {
         sharedMemory.lock();
diff --git a/src/thread.cpp b/src/thread.cpp
index e7c56a28..9d57d728 100644
--- a/src/thread.cpp
+++ b/src/thread.cpp
@@ -237,9 +237,9 @@ void sq2str(char *str)
     rank = rank_of(sq);
 
     if (sig == 1) {
-        sprintf_s(str, 16, "(%d,%d)", file, rank);
+        snprintf(str, Position::RECORD_LEN_MAX, 16, "(%d,%d)", file, rank);
     } else {
-        sprintf_s(str, 16, "-(%d,%d)", file, rank);
+        snprintf(str, Position::RECORD_LEN_MAX, "-(%d,%d)", file, rank);
     }
 }
 #endif // OPENING_BOOK
@@ -366,7 +366,7 @@ void Thread::analyze(Color c)
 #ifndef QT_GUI_LIB
     total = nbwin + nwwin + ndraw;
 
-    if (total == 0) {
+    if (total < 0.01) {
         bwinrate = 0;
         wwinrate = 0;
         drawrate = 0;
@@ -556,7 +556,7 @@ string Thread::nextMove()
     if (gameOptions.getResignIfMostLose() == true) {
         if (root->value <= -VALUE_MATE) {
             gameOverReason = loseReasonResign;
-            //sprintf(record, "Player%d give up!", position->sideToMove);
+            //snprintf(record, Position::RECORD_LEN_MAX, "Player%d give up!", position->sideToMove);
             return record;
         }
     }
diff --git a/src/ui/flutter/command/command_queue.cpp b/src/ui/flutter/command/command_queue.cpp
index 5c97b913..b546d099 100644
--- a/src/ui/flutter/command/command_queue.cpp
+++ b/src/ui/flutter/command/command_queue.cpp
@@ -23,7 +23,7 @@
 CommandQueue::CommandQueue()
 {
     for (int i = 0; i < MAX_COMMAND_COUNT; i++) {
-        strcpy(commands[i], "");
+        commands[i][0] = '\0';
     }
 
     writeIndex = 0;
@@ -38,7 +38,7 @@ bool CommandQueue::write(const char *command)
         return false;
     }
 
-    strcpy(commands[writeIndex], command);
+    strncpy(commands[writeIndex], command, COMMAND_LENGTH);
 
     if (readIndex == -1) {
         readIndex = writeIndex;
@@ -59,8 +59,8 @@ bool CommandQueue::read(char *dest)
         return false;
     }
 
-    strcpy(dest, commands[readIndex]);
-    strcpy(commands[readIndex], "");
+    strncpy(dest, commands[readIndex], COMMAND_LENGTH);
+    strncpy(commands[readIndex], "", COMMAND_LENGTH);
 
     if (++readIndex == MAX_COMMAND_COUNT) {
         readIndex = 0;
diff --git a/src/ui/flutter/command/engine_main.cpp b/src/ui/flutter/command/engine_main.cpp
index 7f9898bf..def189d5 100644
--- a/src/ui/flutter/command/engine_main.cpp
+++ b/src/ui/flutter/command/engine_main.cpp
@@ -32,7 +32,7 @@ void println(const char *str, ...) {
     va_start(args, str);
 
     char buffer[256] = {0};
-    vsprintf(buffer, str, args);
+    vsnprintf(buffer, 256, str, args);
 
     va_end(args);
 
diff --git a/src/ui/qt/game.cpp b/src/ui/qt/game.cpp
index 5d74b0e8..d53af240 100644
--- a/src/ui/qt/game.cpp
+++ b/src/ui/qt/game.cpp
@@ -359,7 +359,7 @@ void Game::setRule(int ruleNo, int stepLimited /*= -1*/, int timeLimited /*= -1*
     elapsedSeconds[BLACK] = elapsedSeconds[WHITE] = 0;
 
     char record[64] = { 0 };
-    if (sprintf(record, "r%1d s%03d t%02d", r + 1, rule.maxStepsLedToDraw, 0) <= 0) {
+    if (snprintf(record, Position::RECORD_LEN_MAX, "r%1d s%03d t%02d", r + 1, rule.maxStepsLedToDraw, 0) <= 0) {
         assert(0);
     }
     string cmd(record);
@@ -1488,28 +1488,28 @@ void Game::appendGameOverReasonToMoveHistory()
     char record[64] = { 0 };
     switch (position.gameOverReason) {
     case GameOverReason::loseReasonNoWay:
-        sprintf(record, "Player%d no way to go. Player%d win!", position.sideToMove, position.winner);
+        snprintf(record, Position::RECORD_LEN_MAX, "Player%d no way to go. Player%d win!", position.sideToMove, position.winner);
         break;
     case GameOverReason::loseReasonTimeOver:
-        sprintf(record, "Time over. Player%d win!", position.winner);
+        snprintf(record, Position::RECORD_LEN_MAX, "Time over. Player%d win!", position.winner);
         break;
     case GameOverReason::drawReasonThreefoldRepetition:
-        sprintf(record, "Threefold Repetition. Draw!");
+        snprintf(record, Position::RECORD_LEN_MAX, "Threefold Repetition. Draw!");
         break;
     case GameOverReason::drawReasonRule50:
-        sprintf(record, "Steps over. In draw!");
+        snprintf(record, Position::RECORD_LEN_MAX, "Steps over. In draw!");
         break;
     case GameOverReason::loseReasonBoardIsFull:
-        sprintf(record, "Player2 win!");
+        snprintf(record, Position::RECORD_LEN_MAX, "Player2 win!");
         break;
     case GameOverReason::drawReasonBoardIsFull:
-        sprintf(record, "Full. In draw!");
+        snprintf(record, Position::RECORD_LEN_MAX, "Full. In draw!");
         break;
     case GameOverReason::loseReasonlessThanThree:
-        sprintf(record, "Player%d win!", position.winner);
+        snprintf(record, Position::RECORD_LEN_MAX, "Player%d win!", position.winner);
         break;
     case GameOverReason::loseReasonResign:
-        sprintf(record, "Player%d give up!", ~position.winner);
+        snprintf(record, Position::RECORD_LEN_MAX, "Player%d give up!", ~position.winner);
         break;
     default:
         loggerDebug("No Game Over Reason");