]> git.sesse.net Git - stockfish/commitdiff
Merge remote-tracking branch 'upstream/master'
authorSteinar H. Gunderson <sgunderson@bigfoot.com>
Mon, 26 Dec 2022 08:41:43 +0000 (09:41 +0100)
committerSteinar H. Gunderson <sgunderson@bigfoot.com>
Mon, 26 Dec 2022 08:41:43 +0000 (09:41 +0100)
32 files changed:
.github/ISSUE_TEMPLATE/BUG-REPORT.yml [new file with mode: 0644]
.github/ISSUE_TEMPLATE/config.yml [new file with mode: 0644]
.github/workflows/stockfish.yml
.github/workflows/stockfish_arm_binaries.yml [new file with mode: 0644]
.github/workflows/stockfish_binaries.yml [new file with mode: 0644]
.github/workflows/stockfish_compile_test.yml [new file with mode: 0644]
.github/workflows/stockfish_sanitizers.yml [new file with mode: 0644]
.github/workflows/stockfish_test.yml [new file with mode: 0644]
AUTHORS
README.md
Top CPU Contributors.txt
src/Makefile
src/evaluate.cpp
src/evaluate.h
src/misc.cpp
src/movepick.cpp
src/movepick.h
src/nnue/evaluate_nnue.cpp
src/nnue/features/half_ka_v2_hm.cpp
src/nnue/features/half_ka_v2_hm.h
src/nnue/nnue_feature_transformer.h
src/position.cpp
src/search.cpp
src/search.h
src/syzygy/tbprobe.cpp
src/syzygy/tbprobe.h
src/thread.cpp
src/thread.h
src/timeman.cpp
src/types.h
src/uci.cpp
src/uci.h

diff --git a/.github/ISSUE_TEMPLATE/BUG-REPORT.yml b/.github/ISSUE_TEMPLATE/BUG-REPORT.yml
new file mode 100644 (file)
index 0000000..e46d2bf
--- /dev/null
@@ -0,0 +1,65 @@
+name: Report issue
+description: Create a report to help us fix issues with the engine
+body:
+- type: textarea
+  attributes:
+    label: Describe the issue
+    description: A clear and concise description of what you're experiencing.
+  validations:
+    required: true
+
+- type: textarea
+  attributes:
+    label: Expected behavior
+    description: A clear and concise description of what you expected to happen.
+  validations:
+    required: true
+
+- type: textarea
+  attributes:
+    label: Steps to reproduce
+    description: |
+      Steps to reproduce the behavior.
+      You can also use this section to paste the command line output.
+    placeholder: |
+      ```
+      position startpos moves g2g4 e7e5 f2f3
+      go mate 1
+      info string NNUE evaluation using nn-6877cd24400e.nnue enabled
+      info depth 1 seldepth 1 multipv 1 score mate 1 nodes 33 nps 11000 tbhits 0 time 3 pv d8h4
+      bestmove d8h4
+      ```
+  validations:
+    required: true
+
+- type: textarea
+  attributes:
+    label: Anything else?
+    description: |
+      Anything that will give us more context about the issue you are encountering.
+      You can also use this section to propose ideas on how to solve the issue. 
+  validations:
+    required: false
+
+- type: dropdown
+  attributes:
+    label: Operating system
+    options:
+      - All
+      - Windows
+      - Linux
+      - MacOS
+      - Android
+      - Other or N/A
+  validations:
+    required: true
+
+- type: input
+  attributes:
+    label: Stockfish version
+    description: |
+      This can be found by running the engine.
+      You can also use the commit ID.
+    placeholder: Stockfish 15 / e6e324e
+  validations:
+    required: true
diff --git a/.github/ISSUE_TEMPLATE/config.yml b/.github/ISSUE_TEMPLATE/config.yml
new file mode 100644 (file)
index 0000000..1f8694d
--- /dev/null
@@ -0,0 +1,8 @@
+blank_issues_enabled: false
+contact_links:
+  - name: Discord server
+    url: https://discord.gg/GWDRS3kU6R
+    about: Feel free to ask for support or have a chat with us in our Discord server!
+  - name: Discussions, Q&A, ideas, show us something...
+    url: https://github.com/official-stockfish/Stockfish/discussions/new
+    about: Do you have an idea for Stockfish? Do you want to show something that you made? Please open a discussion about it!
index b007ec789379af48cd0dc39dff533a7d3934adc2..6345b27cb7424efda303423cf2e88e13e97a1abd 100644 (file)
@@ -10,341 +10,15 @@ on:
       - master
       - tools
 jobs:
-  Stockfish:
-    name: ${{ matrix.config.name }}
-    runs-on: ${{ matrix.config.os }}
-    env:
-      COMPILER: ${{ matrix.config.compiler }}
-      COMP: ${{ matrix.config.comp }}
-      CXXFLAGS: "-Werror"
-    strategy:
-      matrix:
-        config:
-          # set the variable for the required tests:
-          # run_expensive_tests: true
-          # run_32bit_tests: true
-          # run_64bit_tests: true
-          # run_armv8_tests: true
-          # run_armv7_tests: true
-          - {
-              name: "Ubuntu 20.04 GCC",
-              os: ubuntu-20.04,
-              compiler: g++,
-              comp: gcc,
-              run_expensive_tests: true,
-              run_32bit_tests: true,
-              run_64bit_tests: true,
-              shell: 'bash {0}'
-            }
-          - {
-              name: "Ubuntu 20.04 Clang",
-              os: ubuntu-20.04,
-              compiler: clang++,
-              comp: clang,
-              run_32bit_tests: true,
-              run_64bit_tests: true,
-              shell: 'bash {0}'
-            }
-          - {
-              name: "Ubuntu 20.04 NDK armv8",
-              os: ubuntu-20.04,
-              compiler: aarch64-linux-android21-clang++,
-              comp: ndk,
-              run_armv8_tests: false,
-              shell: 'bash {0}'
-            }
-          - {
-              name: "Ubuntu 20.04 NDK armv7",
-              os: ubuntu-20.04,
-              compiler: armv7a-linux-androideabi21-clang++,
-              comp: ndk,
-              run_armv7_tests: false,
-              shell: 'bash {0}'
-            }
-          - {
-              name: "MacOS 10.15 Apple Clang",
-              os: macos-10.15,
-              compiler: clang++,
-              comp: clang,
-              run_64bit_tests: true,
-              shell: 'bash {0}'
-            }
-          - {
-              name: "MacOS 10.15 GCC 10",
-              os: macos-10.15,
-              compiler: g++-10,
-              comp: gcc,
-              run_64bit_tests: true,
-              shell: 'bash {0}'
-            }
-          - {
-              name: "Windows 2022 Mingw-w64 GCC x86_64",
-              os: windows-2022,
-              compiler: g++,
-              comp: mingw,
-              run_64bit_tests: true,
-              msys_sys: 'mingw64',
-              msys_env: 'x86_64-gcc',
-              shell: 'msys2 {0}'
-            }
-          - {
-              name: "Windows 2022 Mingw-w64 GCC i686",
-              os: windows-2022,
-              compiler: g++,
-              comp: mingw,
-              run_32bit_tests: true,
-              msys_sys: 'mingw32',
-              msys_env: 'i686-gcc',
-              shell: 'msys2 {0}'
-            }
-          - {
-              name: "Windows 2022 Mingw-w64 Clang x86_64",
-              os: windows-2022,
-              compiler: clang++,
-              comp: clang,
-              run_64bit_tests: true,
-              msys_sys: 'clang64',
-              msys_env: 'clang-x86_64-clang',
-              shell: 'msys2 {0}'
-            }
-
-    defaults:
-      run:
-        working-directory: src
-        shell: ${{ matrix.config.shell }}
-    steps:
-      - uses: actions/checkout@v2
-        with:
-          fetch-depth: 0
-
-      - name: Download required linux packages
-        if: runner.os == 'Linux'
-        run: |
-          sudo apt update
-          sudo apt install expect valgrind g++-multilib qemu-user
-
-      - name: Setup msys and install required packages
-        if: runner.os == 'Windows'
-        uses: msys2/setup-msys2@v2
-        with:
-          msystem: ${{matrix.config.msys_sys}}
-          install: mingw-w64-${{matrix.config.msys_env}} make git expect
-
-      - name: Download the used network from the fishtest framework
-        run: |
-          make net
-
-      - name: Extract the bench number from the commit history
-        run: |
-          git log HEAD | grep "\b[Bb]ench[ :]\+[0-9]\{7\}" | head -n 1 | sed "s/[^0-9]*\([0-9]*\).*/\1/g" > git_sig
-          [ -s git_sig ] && echo "benchref=$(cat git_sig)" >> $GITHUB_ENV && echo "Reference bench:" $(cat git_sig) || echo "No bench found"
-
-      - name: Check compiler
-        run: |
-          export PATH=$PATH:$ANDROID_NDK_HOME/toolchains/llvm/prebuilt/linux-x86_64/bin
-          $COMPILER -v
-
-      - name: Test help target
-        run: |
-          make help
-
-      # x86-32 tests
-
-      - name: Test debug x86-32 build
-        if: ${{ matrix.config.run_32bit_tests }}
-        run: |
-          export CXXFLAGS="-Werror -D_GLIBCXX_DEBUG"
-          make clean
-          make -j2 ARCH=x86-32 optimize=no debug=yes build
-          ../tests/signature.sh $benchref
-
-      - name: Test x86-32 build
-        if: ${{ matrix.config.run_32bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-32 build
-          ../tests/signature.sh $benchref
-
-      - name: Test x86-32-sse41-popcnt build
-        if: ${{ matrix.config.run_32bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-32-sse41-popcnt build
-          ../tests/signature.sh $benchref
-
-      - name: Test x86-32-sse2 build
-        if: ${{ matrix.config.run_32bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-32-sse2 build
-          ../tests/signature.sh $benchref
-
-      - name: Test general-32 build
-        if: ${{ matrix.config.run_32bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=general-32 build
-          ../tests/signature.sh $benchref
-
-      # x86-64 tests
-
-      - name: Test debug x86-64-modern build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          export CXXFLAGS="-Werror -D_GLIBCXX_DEBUG"
-          make clean
-          make -j2 ARCH=x86-64-modern optimize=no debug=yes build
-          ../tests/signature.sh $benchref
-
-      - name: Test x86-64-modern build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-modern build
-          ../tests/signature.sh $benchref
-
-      - name: Test x86-64-ssse3 build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-ssse3 build
-          ../tests/signature.sh $benchref
-
-      - name: Test x86-64-sse3-popcnt build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-sse3-popcnt build
-          ../tests/signature.sh $benchref
-
-      - name: Test x86-64 build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64 build
-          ../tests/signature.sh $benchref
-
-      - name: Test general-64 build
-        if: matrix.config.run_64bit_tests
-        run: |
-          make clean
-          make -j2 ARCH=general-64 build
-          ../tests/signature.sh $benchref
-
-      # x86-64 with newer extensions tests
-
-      - name: Compile x86-64-avx2 build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-avx2 build
-
-      - name: Compile x86-64-bmi2 build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-bmi2 build
-
-      - name: Compile x86-64-avx512 build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-avx512 build
-
-      - name: Compile x86-64-vnni512 build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-vnni512 build
-
-      - name: Compile x86-64-vnni256 build
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-vnni256 build
-
-      # armv8 tests
-
-      - name: Test armv8 build
-        if: ${{ matrix.config.run_armv8_tests }}
-        run: |
-          ANDROID_ROOT=/usr/local/lib/android
-          ANDROID_SDK_ROOT=${ANDROID_ROOT}/sdk
-          SDKMANAGER=${ANDROID_SDK_ROOT}/cmdline-tools/latest/bin/sdkmanager
-          echo "y" | $SDKMANAGER "ndk;21.4.7075529"
-          ANDROID_NDK_ROOT=${ANDROID_SDK_ROOT}/ndk-bundle
-          ln -sfn $ANDROID_SDK_ROOT/ndk/21.4.7075529 $ANDROID_NDK_ROOT
-          export PATH=$ANDROID_NDK_HOME/toolchains/llvm/prebuilt/linux-x86_64/bin:$PATH
-          export LDFLAGS="-static -Wno-unused-command-line-argument"
-          make clean
-          make -j2 ARCH=armv8 build
-          ../tests/signature.sh $benchref
-
-      # armv7 tests
-
-      - name: Test armv7 build
-        if: ${{ matrix.config.run_armv7_tests }}
-        run: |
-          ANDROID_ROOT=/usr/local/lib/android
-          ANDROID_SDK_ROOT=${ANDROID_ROOT}/sdk
-          SDKMANAGER=${ANDROID_SDK_ROOT}/cmdline-tools/latest/bin/sdkmanager
-          echo "y" | $SDKMANAGER "ndk;21.4.7075529"
-          ANDROID_NDK_ROOT=${ANDROID_SDK_ROOT}/ndk-bundle
-          ln -sfn $ANDROID_SDK_ROOT/ndk/21.4.7075529 $ANDROID_NDK_ROOT
-          export PATH=$ANDROID_NDK_HOME/toolchains/llvm/prebuilt/linux-x86_64/bin:$PATH
-          export LDFLAGS="-static -Wno-unused-command-line-argument"
-          make clean
-          make -j2 ARCH=armv7 build
-          ../tests/signature.sh $benchref
-
-      - name: Test armv7-neon build
-        if: ${{ matrix.config.run_armv7_tests }}
-        run: |
-          ANDROID_ROOT=/usr/local/lib/android
-          ANDROID_SDK_ROOT=${ANDROID_ROOT}/sdk
-          SDKMANAGER=${ANDROID_SDK_ROOT}/cmdline-tools/latest/bin/sdkmanager
-          echo "y" | $SDKMANAGER "ndk;21.4.7075529"
-          ANDROID_NDK_ROOT=${ANDROID_SDK_ROOT}/ndk-bundle
-          ln -sfn $ANDROID_SDK_ROOT/ndk/21.4.7075529 $ANDROID_NDK_ROOT
-          export PATH=$ANDROID_NDK_HOME/toolchains/llvm/prebuilt/linux-x86_64/bin:$PATH
-          export LDFLAGS="-static -Wno-unused-command-line-argument"
-          make clean
-          make -j2 ARCH=armv7-neon build
-          ../tests/signature.sh $benchref
-
-      # Other tests
-
-      - name: Check perft and search reproducibility
-        if: ${{ matrix.config.run_64bit_tests }}
-        run: |
-          make clean
-          make -j2 ARCH=x86-64-modern build
-          ../tests/perft.sh
-          ../tests/reprosearch.sh
-
-      # Sanitizers
-
-      - name: Run under valgrind
-        if: ${{ matrix.config.run_expensive_tests }}
-        run: |
-          export CXXFLAGS="-O1 -fno-inline"
-          make clean
-          make -j2 ARCH=x86-64-modern debug=yes optimize=no build > /dev/null
-          ../tests/instrumented.sh --valgrind
-          ../tests/instrumented.sh --valgrind-thread
-
-      - name: Run with UB sanitizer
-        if: ${{ matrix.config.run_expensive_tests }}
-        run: |
-          export CXXFLAGS="-O1 -fno-inline"
-          make clean
-          make -j2 ARCH=x86-64-modern sanitize=undefined optimize=no debug=yes build > /dev/null
-          ../tests/instrumented.sh --sanitizer-undefined
-
-      - name: Run with thread sanitizer
-        if: ${{ matrix.config.run_expensive_tests }}
-        run: |
-          export CXXFLAGS="-O1 -fno-inline"
-          make clean
-          make -j2 ARCH=x86-64-modern sanitize=thread optimize=no debug=yes build > /dev/null
-          ../tests/instrumented.sh --sanitizer-thread
+  Sanitizers:
+    uses: ./.github/workflows/stockfish_sanitizers.yml
+  Tests:
+    uses: ./.github/workflows/stockfish_test.yml
+  Compiles:
+    uses: ./.github/workflows/stockfish_compile_test.yml
+  Binaries:
+    if: github.ref == 'refs/heads/master'
+    uses: ./.github/workflows/stockfish_binaries.yml
+  ARM_Binaries:
+    if: github.ref == 'refs/heads/master'
+    uses: ./.github/workflows/stockfish_arm_binaries.yml
diff --git a/.github/workflows/stockfish_arm_binaries.yml b/.github/workflows/stockfish_arm_binaries.yml
new file mode 100644 (file)
index 0000000..a1b3cda
--- /dev/null
@@ -0,0 +1,117 @@
+name: Stockfish
+on:
+  workflow_call:
+jobs:
+  Stockfish:
+    name: ${{ matrix.config.name }} ${{ matrix.binaries }}
+    runs-on: ${{ matrix.config.os }}
+    env:
+      COMPILER: ${{ matrix.config.compiler }}
+      COMP: ${{ matrix.config.comp }}
+      EMU: ${{ matrix.config.emu }}
+      EXT: ${{ matrix.config.ext }}
+      OS: ${{ matrix.config.os }}
+      BINARY: ${{ matrix.binaries }}
+    strategy:
+      matrix:
+        config:
+          - name: Android NDK aarch64
+            os: ubuntu-22.04
+            compiler: aarch64-linux-android21-clang++
+            emu: qemu-aarch64
+            comp: ndk
+            shell: bash {0}
+          - name: Android NDK arm
+            os: ubuntu-22.04
+            compiler: armv7a-linux-androideabi21-clang++
+            emu: qemu-arm
+            comp: ndk
+            shell: bash {0}
+        binaries:
+          - armv8
+          - armv7
+          - armv7-neon
+        exclude:
+          - binaries: armv8
+            config: {compiler: armv7a-linux-androideabi21-clang++}
+          - binaries: armv7
+            config: {compiler: aarch64-linux-android21-clang++}
+          - binaries: armv7-neon
+            config: {compiler: aarch64-linux-android21-clang++}
+    defaults:
+      run:
+        working-directory: src
+        shell: ${{ matrix.config.shell }}
+    steps:
+      - uses: actions/checkout@v3
+        with:
+          fetch-depth: 0
+
+      - name: Download required linux packages
+        if: runner.os == 'Linux'
+        run: |
+          sudo apt update
+          sudo apt install qemu-user
+
+      - name: Install NDK
+        if: runner.os == 'Linux'
+        run: |
+          if [ $COMP == ndk ]; then
+            NDKV="21.4.7075529"
+            ANDROID_ROOT=/usr/local/lib/android
+            ANDROID_SDK_ROOT=$ANDROID_ROOT/sdk
+            SDKMANAGER=$ANDROID_SDK_ROOT/cmdline-tools/latest/bin/sdkmanager
+            echo "y" | $SDKMANAGER "ndk;$NDKV"
+            ANDROID_NDK_ROOT=$ANDROID_SDK_ROOT/ndk/$NDKV
+            ANDROID_NDK_BIN=$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin
+            echo "ANDROID_NDK_BIN=$ANDROID_NDK_BIN" >> $GITHUB_ENV
+          fi
+
+      - name: Download the used network from the fishtest framework
+        run: make net
+
+      - name: Check compiler
+        run: |
+          if [ $COMP == ndk ]; then
+            export PATH=${{ env.ANDROID_NDK_BIN }}:$PATH
+          fi
+          $COMPILER -v
+
+      - name: Test help target
+        run: make help
+
+      - name: Check git
+        run: git --version
+
+      # Compile profile guided builds
+
+      - name: Compile ${{ matrix.binaries }} build
+        run: |
+          if [ $COMP == ndk ]; then
+            export PATH=${{ env.ANDROID_NDK_BIN }}:$PATH
+            export LDFLAGS="-static -Wno-unused-command-line-argument"
+          fi
+          make clean
+          make -j2 profile-build ARCH=$BINARY COMP=$COMP WINE_PATH=$EMU
+          make strip ARCH=$BINARY COMP=$COMP
+          mv ./stockfish$EXT ../stockfish-android-$BINARY$EXT
+
+      - name: Remove non src files
+        run: rm -f *.o .depend *.nnue
+
+      - name: Create tar archive.
+        run: |
+          cd ..
+          mkdir stockfish
+          cp -r src stockfish/
+          cp stockfish-android-$BINARY$EXT stockfish/
+          cp "Top CPU Contributors.txt" stockfish/
+          cp Copying.txt stockfish/
+          cp AUTHORS stockfish/
+          tar -cvf stockfish-android-$BINARY.tar stockfish
+
+      - name: Upload binaries
+        uses: actions/upload-artifact@v3
+        with:
+          name: stockfish-android-${{ matrix.binaries }}
+          path: stockfish-android-${{ matrix.binaries }}.tar
diff --git a/.github/workflows/stockfish_binaries.yml b/.github/workflows/stockfish_binaries.yml
new file mode 100644 (file)
index 0000000..06b13a9
--- /dev/null
@@ -0,0 +1,101 @@
+name: Stockfish
+on:
+  workflow_call:
+jobs:
+  Stockfish:
+    name: ${{ matrix.config.name }} ${{ matrix.binaries }}
+    runs-on: ${{ matrix.config.os }}
+    env:
+      COMPILER: ${{ matrix.config.compiler }}
+      COMP: ${{ matrix.config.comp }}
+      EXT: ${{ matrix.config.ext }}
+      OS: ${{ matrix.config.os }}
+      BINARY: ${{ matrix.binaries }}
+    strategy:
+      matrix:
+        config:
+          - name: Ubuntu 20.04 GCC
+            os: ubuntu-20.04
+            compiler: g++
+            comp: gcc
+            shell: bash {0}
+          - name: MacOS 12 Apple Clang
+            os: macos-12
+            compiler: clang++
+            comp: clang
+            shell: bash {0}
+          - name: Windows 2022 Mingw-w64 GCC x86_64
+            os: windows-2022
+            compiler: g++
+            comp: mingw
+            msys_sys: mingw64
+            msys_env: x86_64-gcc
+            shell: msys2 {0}
+            ext: .exe
+        binaries:
+          - x86-64
+          - x86-64-modern
+          - x86-64-avx2
+        exclude:
+          - binaries: x86-64-avx2
+            config: {os: macos-12}
+    defaults:
+      run:
+        working-directory: src
+        shell: ${{ matrix.config.shell }}
+    steps:
+      - uses: actions/checkout@v3
+        with:
+          fetch-depth: 0
+
+      - name: Download required linux packages
+        if: runner.os == 'Linux'
+        run: sudo apt update
+
+      - name: Setup msys and install required packages
+        if: runner.os == 'Windows'
+        uses: msys2/setup-msys2@v2
+        with:
+          msystem: ${{ matrix.config.msys_sys }}
+          install: mingw-w64-${{ matrix.config.msys_env }} make git
+
+      - name: Download the used network from the fishtest framework
+        run: make net
+
+      - name: Check compiler
+        run: $COMPILER -v
+
+      - name: Test help target
+        run: make help
+
+      - name: Check git
+        run: git --version
+
+      # Compile profile guided builds
+
+      - name: Compile ${{ matrix.binaries }} build
+        run: |
+          make clean
+          make -j2 profile-build ARCH=$BINARY COMP=$COMP
+          make strip ARCH=$BINARY COMP=$COMP
+          mv ./stockfish$EXT ../stockfish-$OS-$BINARY$EXT
+
+      - name: Remove non src files
+        run: rm -f *.o .depend *.nnue
+
+      - name: Create tar archive.
+        run: |
+          cd ..
+          mkdir stockfish
+          cp -r src stockfish/
+          cp stockfish-$OS-$BINARY$EXT stockfish/
+          cp "Top CPU Contributors.txt" stockfish/
+          cp Copying.txt stockfish/
+          cp AUTHORS stockfish/
+          tar -cvf stockfish-$OS-$BINARY.tar stockfish
+
+      - name: Upload binaries
+        uses: actions/upload-artifact@v3
+        with:
+          name: stockfish-${{ matrix.config.os }}-${{ matrix.binaries }}
+          path: stockfish-${{ matrix.config.os }}-${{ matrix.binaries }}.tar
diff --git a/.github/workflows/stockfish_compile_test.yml b/.github/workflows/stockfish_compile_test.yml
new file mode 100644 (file)
index 0000000..c7280a8
--- /dev/null
@@ -0,0 +1,102 @@
+name: Stockfish
+on:
+  workflow_call:
+jobs:
+  Stockfish:
+    name: ${{ matrix.config.name }}
+    runs-on: ${{ matrix.config.os }}
+    env:
+      COMPILER: ${{ matrix.config.compiler }}
+      COMP: ${{ matrix.config.comp }}
+    strategy:
+      matrix:
+        config:
+          - name: Ubuntu 20.04 GCC
+            os: ubuntu-20.04
+            compiler: g++
+            comp: gcc
+            shell: bash {0}
+          - name: Ubuntu 20.04 Clang
+            os: ubuntu-20.04
+            compiler: clang++
+            comp: clang
+            shell: bash {0}
+          - name: MacOS 12 Apple Clang
+            os: macos-12
+            compiler: clang++
+            comp: clang
+            shell: bash {0}
+          - name: MacOS 12 GCC 11
+            os: macos-12
+            compiler: g++-11
+            comp: gcc
+            shell: bash {0}
+          - name: Windows 2022 Mingw-w64 GCC x86_64
+            os: windows-2022
+            compiler: g++
+            comp: mingw
+            msys_sys: mingw64
+            msys_env: x86_64-gcc
+            shell: msys2 {0}
+          - name: Windows 2022 Mingw-w64 Clang x86_64
+            os: windows-2022
+            compiler: clang++
+            comp: clang
+            msys_sys: clang64
+            msys_env: clang-x86_64-clang
+            shell: msys2 {0}
+
+    defaults:
+      run:
+        working-directory: src
+        shell: ${{ matrix.config.shell }}
+    steps:
+      - uses: actions/checkout@v3
+        with:
+          fetch-depth: 0
+
+      - name: Setup msys and install required packages
+        if: runner.os == 'Windows'
+        uses: msys2/setup-msys2@v2
+        with:
+          msystem: ${{matrix.config.msys_sys}}
+          install: mingw-w64-${{matrix.config.msys_env}} make git
+
+      - name: Download the used network from the fishtest framework
+        run: make net
+
+      - name: Check compiler
+        run: $COMPILER -v
+
+      - name: Test help target
+        run: make help
+
+      - name: Check git
+        run: git --version
+
+      # x86-64 with newer extensions tests
+
+      - name: Compile x86-64-avx2 build
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-avx2 build
+
+      - name: Compile x86-64-bmi2 build
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-bmi2 build
+
+      - name: Compile x86-64-avx512 build
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-avx512 build
+
+      - name: Compile x86-64-vnni512 build
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-vnni512 build
+
+      - name: Compile x86-64-vnni256 build
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-vnni256 build
diff --git a/.github/workflows/stockfish_sanitizers.yml b/.github/workflows/stockfish_sanitizers.yml
new file mode 100644 (file)
index 0000000..708c922
--- /dev/null
@@ -0,0 +1,66 @@
+name: Stockfish
+on:
+  workflow_call:
+jobs:
+  Stockfish:
+    name: ${{ matrix.sanitizers.name }}
+    runs-on: ${{ matrix.config.os }}
+    env:
+      COMPILER: ${{ matrix.config.compiler }}
+      COMP: ${{ matrix.config.comp }}
+      CXXFLAGS: "-Werror"
+    strategy:
+      matrix:
+        config:
+          - name: Ubuntu 20.04 GCC
+            os: ubuntu-20.04
+            compiler: g++
+            comp: gcc
+            shell: bash {0}
+        sanitizers:
+          - name: Run with thread sanitizer
+            make_option: sanitize=thread
+            instrumented_option: sanitizer-thread
+          - name: Run with UB sanitizer
+            make_option: sanitize=undefined
+            instrumented_option: sanitizer-undefined
+          - name: Run under valgrind
+            make_option: ""
+            instrumented_option: valgrind
+          - name: Run under valgrind-thread
+            make_option: ""
+            instrumented_option: valgrind-thread
+    defaults:
+      run:
+        working-directory: src
+        shell: ${{ matrix.config.shell }}
+    steps:
+      - uses: actions/checkout@v3
+        with:
+          fetch-depth: 0
+
+      - name: Download required linux packages
+        run: |
+          sudo apt update
+          sudo apt install expect valgrind g++-multilib
+
+      - name: Download the used network from the fishtest framework
+        run: make net
+
+      - name: Check compiler
+        run: $COMPILER -v
+
+      - name: Test help target
+        run: make help
+
+      - name: Check git
+        run: git --version
+
+      # Sanitizers
+
+      - name: ${{ matrix.sanitizers.name }}
+        run: |
+          export CXXFLAGS="-O1 -fno-inline"
+          make clean
+          make -j2 ARCH=x86-64-modern ${{ matrix.sanitizers.make_option }} debug=yes optimize=no build > /dev/null
+          ../tests/instrumented.sh --${{ matrix.sanitizers.instrumented_option }}
diff --git a/.github/workflows/stockfish_test.yml b/.github/workflows/stockfish_test.yml
new file mode 100644 (file)
index 0000000..8c383fe
--- /dev/null
@@ -0,0 +1,256 @@
+name: Stockfish
+on:
+  workflow_call:
+jobs:
+  Stockfish:
+    name: ${{ matrix.config.name }}
+    runs-on: ${{ matrix.config.os }}
+    env:
+      COMPILER: ${{ matrix.config.compiler }}
+      COMP: ${{ matrix.config.comp }}
+      CXXFLAGS: "-Werror"
+    strategy:
+      matrix:
+        config:
+          - name: Ubuntu 20.04 GCC
+            os: ubuntu-20.04
+            compiler: g++
+            comp: gcc
+            run_32bit_tests: true
+            run_64bit_tests: true
+            shell: bash {0}
+          - name: Ubuntu 20.04 Clang
+            os: ubuntu-20.04
+            compiler: clang++
+            comp: clang
+            run_32bit_tests: true
+            run_64bit_tests: true
+            shell: bash {0}
+          - name: Android NDK aarch64
+            os: ubuntu-22.04
+            compiler: aarch64-linux-android21-clang++
+            comp: ndk
+            run_armv8_tests: true
+            shell: bash {0}
+          - name: Android NDK arm
+            os: ubuntu-22.04
+            compiler: armv7a-linux-androideabi21-clang++
+            comp: ndk
+            run_armv7_tests: true
+            shell: bash {0}
+          - name: MacOS 12 Apple Clang
+            os: macos-12
+            compiler: clang++
+            comp: clang
+            run_64bit_tests: true
+            shell: bash {0}
+          - name: MacOS 12 GCC 11
+            os: macos-12
+            compiler: g++-11
+            comp: gcc
+            run_64bit_tests: true
+            shell: bash {0}
+          - name: Windows 2022 Mingw-w64 GCC x86_64
+            os: windows-2022
+            compiler: g++
+            comp: mingw
+            run_64bit_tests: true
+            msys_sys: mingw64
+            msys_env: x86_64-gcc
+            shell: msys2 {0}
+          - name: Windows 2022 Mingw-w64 GCC i686
+            os: windows-2022
+            compiler: g++
+            comp: mingw
+            run_32bit_tests: true
+            msys_sys: mingw32
+            msys_env: i686-gcc
+            shell: msys2 {0}
+          - name: Windows 2022 Mingw-w64 Clang x86_64
+            os: windows-2022
+            compiler: clang++
+            comp: clang
+            run_64bit_tests: true
+            msys_sys: clang64
+            msys_env: clang-x86_64-clang
+            shell: msys2 {0}
+    defaults:
+      run:
+        working-directory: src
+        shell: ${{ matrix.config.shell }}
+    steps:
+      - uses: actions/checkout@v3
+        with:
+          fetch-depth: 0
+
+      - name: Download required linux packages
+        if: runner.os == 'Linux'
+        run: |
+          sudo apt update
+          sudo apt install expect valgrind g++-multilib qemu-user
+
+      - name: Install NDK
+        if: runner.os == 'Linux'
+        run: |
+          if [ $COMP == ndk ]; then
+            NDKV="21.4.7075529"
+            ANDROID_ROOT=/usr/local/lib/android
+            ANDROID_SDK_ROOT=$ANDROID_ROOT/sdk
+            SDKMANAGER=$ANDROID_SDK_ROOT/cmdline-tools/latest/bin/sdkmanager
+            echo "y" | $SDKMANAGER "ndk;$NDKV"
+            ANDROID_NDK_ROOT=$ANDROID_SDK_ROOT/ndk/$NDKV
+            ANDROID_NDK_BIN=$ANDROID_NDK_ROOT/toolchains/llvm/prebuilt/linux-x86_64/bin
+            echo "ANDROID_NDK_BIN=$ANDROID_NDK_BIN" >> $GITHUB_ENV
+          fi
+
+      - name: Setup msys and install required packages
+        if: runner.os == 'Windows'
+        uses: msys2/setup-msys2@v2
+        with:
+          msystem: ${{ matrix.config.msys_sys }}
+          install: mingw-w64-${{ matrix.config.msys_env }} make git expect
+
+      - name: Download the used network from the fishtest framework
+        run: make net
+
+      - name: Extract the bench number from the commit history
+        run: |
+          git log HEAD | grep "\b[Bb]ench[ :]\+[0-9]\{7\}" | head -n 1 | sed "s/[^0-9]*\([0-9]*\).*/\1/g" > git_sig
+          [ -s git_sig ] && echo "benchref=$(cat git_sig)" >> $GITHUB_ENV && echo "Reference bench:" $(cat git_sig) || echo "No bench found"
+
+      - name: Check compiler
+        run: |
+          if [ $COMP == ndk ]; then
+            export PATH=${{ env.ANDROID_NDK_BIN }}:$PATH
+          fi
+          $COMPILER -v
+
+      - name: Test help target
+        run: make help
+
+      - name: Check git
+        run: git --version
+
+      # x86-32 tests
+
+      - name: Test debug x86-32 build
+        if: ${{ matrix.config.run_32bit_tests }}
+        run: |
+          export CXXFLAGS="-Werror -D_GLIBCXX_DEBUG"
+          make clean
+          make -j2 ARCH=x86-32 optimize=no debug=yes build
+          ../tests/signature.sh $benchref
+
+      - name: Test x86-32 build
+        if: ${{ matrix.config.run_32bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-32 build
+          ../tests/signature.sh $benchref
+
+      - name: Test x86-32-sse41-popcnt build
+        if: ${{ matrix.config.run_32bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-32-sse41-popcnt build
+          ../tests/signature.sh $benchref
+
+      - name: Test x86-32-sse2 build
+        if: ${{ matrix.config.run_32bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-32-sse2 build
+          ../tests/signature.sh $benchref
+
+      - name: Test general-32 build
+        if: ${{ matrix.config.run_32bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=general-32 build
+          ../tests/signature.sh $benchref
+
+      # x86-64 tests
+
+      - name: Test debug x86-64-modern build
+        if: ${{ matrix.config.run_64bit_tests }}
+        run: |
+          export CXXFLAGS="-Werror -D_GLIBCXX_DEBUG"
+          make clean
+          make -j2 ARCH=x86-64-modern optimize=no debug=yes build
+          ../tests/signature.sh $benchref
+
+      - name: Test x86-64-modern build
+        if: ${{ matrix.config.run_64bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-modern build
+          ../tests/signature.sh $benchref
+
+      - name: Test x86-64-ssse3 build
+        if: ${{ matrix.config.run_64bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-ssse3 build
+          ../tests/signature.sh $benchref
+
+      - name: Test x86-64-sse3-popcnt build
+        if: ${{ matrix.config.run_64bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-sse3-popcnt build
+          ../tests/signature.sh $benchref
+
+      - name: Test x86-64 build
+        if: ${{ matrix.config.run_64bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-64 build
+          ../tests/signature.sh $benchref
+
+      - name: Test general-64 build
+        if: matrix.config.run_64bit_tests
+        run: |
+          make clean
+          make -j2 ARCH=general-64 build
+          ../tests/signature.sh $benchref
+
+      # armv8 tests
+
+      - name: Test armv8 build
+        if: ${{ matrix.config.run_armv8_tests }}
+        run: |
+          export PATH=${{ env.ANDROID_NDK_BIN }}:$PATH
+          export LDFLAGS="-static -Wno-unused-command-line-argument"
+          make clean
+          make -j2 ARCH=armv8 build
+          ../tests/signature.sh $benchref
+
+      # armv7 tests
+
+      - name: Test armv7 build
+        if: ${{ matrix.config.run_armv7_tests }}
+        run: |
+          export PATH=${{ env.ANDROID_NDK_BIN }}:$PATH
+          export LDFLAGS="-static -Wno-unused-command-line-argument"
+          make clean
+          make -j2 ARCH=armv7 build
+          ../tests/signature.sh $benchref
+
+      - name: Test armv7-neon build
+        if: ${{ matrix.config.run_armv7_tests }}
+        run: |
+          export PATH=${{ env.ANDROID_NDK_BIN }}:$PATH
+          export LDFLAGS="-static -Wno-unused-command-line-argument"
+          make clean
+          make -j2 ARCH=armv7-neon build
+          ../tests/signature.sh $benchref
+
+      # Other tests
+
+      - name: Check perft and search reproducibility
+        if: ${{ matrix.config.run_64bit_tests }}
+        run: |
+          make clean
+          make -j2 ARCH=x86-64-modern build
+          ../tests/perft.sh
+          ../tests/reprosearch.sh
diff --git a/AUTHORS b/AUTHORS
index fc885acbf9cf3c595fbdedb268287f74b409c665..70b500ea79edc2168e2d04d50004516cceaa9627 100644 (file)
--- a/AUTHORS
+++ b/AUTHORS
@@ -39,16 +39,19 @@ Boštjan Mejak (PedanticHacker)
 braich
 Brian Sheppard (SapphireBrand, briansheppard-toast)
 Bruno de Melo Costa (BM123499)
+Bruno Pellanda (pellanda)
 Bryan Cross (crossbr)
 candirufish
 Chess13234
 Chris Cain (ceebo)
+clefrks
 Dale Weiler (graphitemaster)
 Dan Schmidt (dfannius)
 Daniel Axtens (daxtens)
 Daniel Dugovic (ddugovic)
 Dariusz Orzechowski (dorzechowski)
 David Zar
+David (dav1312)
 Daylen Yang (daylen)
 Deshawn Mohan-Smith (GoldenRare)
 Dieter Dobbelaere (ddobbelaere)
@@ -88,7 +91,7 @@ Hongzhi Cheng
 Ivan Ivec (IIvec)
 Jacques B. (Timshel)
 Jan Ondruš (hxim)
-Jared Kish (Kurtbusch)
+Jared Kish (Kurtbusch, kurt22i)
 Jarrod Torriero (DU-jdto)
 Jean Gauthier (OuaisBla)
 Jean-Francois Romang (jromang)
@@ -142,6 +145,7 @@ Mira
 Miroslav Fontán (Hexik)
 Moez Jellouli (MJZ1977)
 Mohammed Li (tthsqe12)
+Muzhen J (XInTheDark)
 Nathan Rugg (nmrugg)
 Nick Pelling (nickpelling)
 Nicklas Persson (NicklasPersson)
@@ -158,17 +162,18 @@ Panthee
 Pascal Romaret
 Pasquale Pigazzini (ppigazzini)
 Patrick Jansen (mibere)
-pellanda
 Peter Schneider (pschneider1968)
 Peter Zsifkovits (CoffeeOne)
+PikaCat
 Praveen Kumar Tummala (praveentml)
 Rahul Dsilva (silversolver1)
 Ralph Stößer (Ralph Stoesser)
 Raminder Singh
 renouve
-Reuven Peleg
-Richard Lloyd
+Reuven Peleg (R-Peleg)
+Richard Lloyd (Richard-Lloyd)
 Rodrigo Exterckötter Tjäder
+Rodrigo Roim (roim)
 Ron Britvich (Britvich)
 Ronald de Man (syzygy1, syzygy)
 rqs
@@ -188,6 +193,7 @@ Stefan Geschwentner (locutus2)
 Stefano Cardanobile (Stefano80)
 Steinar Gunderson (sesse)
 Stéphane Nicolet (snicolet)
+Syine Mineta (MinetaS)
 Prokop Randáček (ProkopRandacek)
 Thanar2
 thaspel
index b076ab6bc02a2687b124f5b483a710dffc2ea2b0..4cd5968e4be0917e3e8e5d4d41fd5307b8ab3f25 100644 (file)
--- a/README.md
+++ b/README.md
@@ -1,7 +1,7 @@
 <div align="center">
-  
+
   [![Stockfish][stockfish128-logo]][website-link]
-  
+
   [![Build][build-badge]][build-link]
   [![License][license-badge]][license-link]
   <br>
@@ -11,7 +11,7 @@
   [![Website][website-badge]][website-link]
   [![Fishtest][fishtest-badge]][fishtest-link]
   [![Discord][discord-badge]][discord-link]
-  
+
 </div>
 
 ## Overview
 Glaurung 2.1. Stockfish is not a complete chess program and requires a UCI-compatible
 graphical user interface (GUI) (e.g. XBoard with PolyGlot, Scid, Cute Chess, eboard,
 Arena, Sigma Chess, Shredder, Chess Partner or Fritz) in order to be used comfortably.
-Read the documentation for your GUI of choice for informationabout how to use
+Read the documentation for your GUI of choice for information about how to use
 Stockfish with it.
 
-The Stockfish engine features two evaluation functions for chess. The efficiently 
+The Stockfish engine features two evaluation functions for chess. The efficiently
 updatable neural network (NNUE) based evaluation is the default and by far the strongest.
-The classical evaluation based on handcrafted terms remains available. The strongest 
+The classical evaluation based on handcrafted terms remains available. The strongest
 network is integrated in the binary and downloaded automatically during the build process.
-The NNUE evaluation benefits from the vector intrinsics available on most CPUs (sse2, 
+The NNUE evaluation benefits from the vector intrinsics available on most CPUs (sse2,
 avx2, neon, or similar).
 
 ## Files
@@ -152,8 +152,8 @@ change them via a chess GUI. This is a list of available UCI options in Stockfis
 For developers the following non-standard commands might be of interest, mainly useful for debugging:
 
   * #### bench *ttSize threads limit fenFile limitType evalType*
-    Performs a standard benchmark using various options. The signature of a version 
-    (standard node count) is obtained using all defaults. `bench` is currently 
+    Performs a standard benchmark using various options. The signature of a version
+    (standard node count) is obtained using all defaults. `bench` is currently
     `bench 16 1 13 default depth mixed`.
 
   * #### compiler
@@ -201,9 +201,9 @@ the engine is somewhat lower (roughly 80% of nps is typical).
 
 Notes:
 
-1) the NNUE evaluation depends on the Stockfish binary and the network parameter file 
+1) the NNUE evaluation depends on the Stockfish binary and the network parameter file
 (see the EvalFile UCI option). Not every parameter file is compatible with a given
-Stockfish binary, but the default value of the EvalFile UCI option is the name of a 
+Stockfish binary, but the default value of the EvalFile UCI option is the name of a
 network that is guaranteed to be compatible with that binary.
 
 2) to use the NNUE evaluation, the additional data file with neural network parameters
@@ -337,40 +337,42 @@ using it as the starting point for a software project of your own.
 
 The only real limitation is that whenever you distribute Stockfish in
 some way, you MUST always include the license and the full source code
-(or a pointer to where the source code can be found) to generate the 
+(or a pointer to where the source code can be found) to generate the
 exact binary you are distributing. If you make any changes to the
 source code, these changes must also be made available under the GPL v3.
 
 For full details, read the copy of the GPL v3 found in the file named
 [*Copying.txt*][license-link].
 
-[authors-link]:https://github.com/official-stockfish/Stockfish/blob/master/AUTHORS
-[build-badge]:https://img.shields.io/github/workflow/status/official-stockfish/Stockfish/Stockfish?style=for-the-badge&label=stockfish&logo=github
-[build-link]:https://github.com/official-stockfish/Stockfish/actions/workflows/stockfish.yml
-[commits-badge]:https://img.shields.io/github/commits-since/official-stockfish/Stockfish/latest?style=for-the-badge
-[commits-link]:https://github.com/official-stockfish/Stockfish/commits/master
-[discord-badge]:https://img.shields.io/discord/435943710472011776?style=for-the-badge&label=discord&logo=Discord
-[discord-link]:https://discord.com/invite/aefaxmq
-[fishcooking-link]:https://groups.google.com/g/fishcooking
-[fishtest-badge]:https://img.shields.io/website?style=for-the-badge&down_color=red&down_message=Offline&label=Fishtest&up_color=success&up_message=Online&url=https%3A%2F%2Ftests.stockfishchess.org%2Ftests
-[fishtest-link]:https://tests.stockfishchess.org/tests
-[github-link]:https://github.com/official-stockfish/Stockfish
-[guideline-link]:https://github.com/glinscott/fishtest/wiki/Creating-my-first-test
-[license-badge]:https://img.shields.io/github/license/official-stockfish/Stockfish?style=for-the-badge&label=license&color=success
-[license-link]:https://github.com/official-stockfish/Stockfish/blob/master/Copying.txt
-[lockpages-link]:https://docs.microsoft.com/en-us/sql/database-engine/configure-windows/enable-the-lock-pages-in-memory-option-windows
-[nodchip-link]:https://github.com/nodchip/Stockfish
-[programming-link]:https://www.chessprogramming.org/Main_Page
-[programmingsf-link]:https://www.chessprogramming.org/Stockfish
-[pytorch-link]:https://github.com/glinscott/nnue-pytorch
-[rammap-link]:https://docs.microsoft.com/en-us/sysinternals/downloads/rammap
-[readme-link]:https://github.com/official-stockfish/Stockfish/blob/master/README.md
-[release-badge]:https://img.shields.io/github/v/release/official-stockfish/Stockfish?style=for-the-badge&label=official%20release
-[release-link]:https://github.com/official-stockfish/Stockfish/releases/latest
-[src-link]:https://github.com/official-stockfish/Stockfish/tree/master/src
-[stockfish128-logo]:https://stockfishchess.org/images/logo/icon_128x128.png
-[tools-link]:https://github.com/official-stockfish/Stockfish/tree/tools
-[uci-link]:https://www.shredderchess.com/download/div/uci.zip
-[website-badge]:https://img.shields.io/website?style=for-the-badge&down_color=red&down_message=Offline&label=website&up_color=success&up_message=Online&url=https%3A%2F%2Fstockfishchess.org
-[website-link]:https://stockfishchess.org
-[worker-link]:https://github.com/glinscott/fishtest/wiki/Running-the-worker:-overview
+
+[authors-link]:       https://github.com/official-stockfish/Stockfish/blob/master/AUTHORS
+[build-link]:         https://github.com/official-stockfish/Stockfish/actions/workflows/stockfish.yml
+[commits-link]:       https://github.com/official-stockfish/Stockfish/commits/master
+[discord-link]:       https://discord.gg/GWDRS3kU6R
+[fishcooking-link]:   https://groups.google.com/g/fishcooking
+[fishtest-link]:      https://tests.stockfishchess.org/tests
+[github-link]:        https://github.com/official-stockfish/Stockfish
+[guideline-link]:     https://github.com/glinscott/fishtest/wiki/Creating-my-first-test
+[license-link]:       https://github.com/official-stockfish/Stockfish/blob/master/Copying.txt
+[lockpages-link]:     https://docs.microsoft.com/en-us/sql/database-engine/configure-windows/enable-the-lock-pages-in-memory-option-windows
+[nodchip-link]:       https://github.com/nodchip/Stockfish
+[programming-link]:   https://www.chessprogramming.org/Main_Page
+[programmingsf-link]: https://www.chessprogramming.org/Stockfish
+[pytorch-link]:       https://github.com/glinscott/nnue-pytorch
+[rammap-link]:        https://docs.microsoft.com/en-us/sysinternals/downloads/rammap
+[readme-link]:        https://github.com/official-stockfish/Stockfish/blob/master/README.md
+[release-link]:       https://github.com/official-stockfish/Stockfish/releases/latest
+[src-link]:           https://github.com/official-stockfish/Stockfish/tree/master/src
+[stockfish128-logo]:  https://stockfishchess.org/images/logo/icon_128x128.png
+[tools-link]:         https://github.com/official-stockfish/Stockfish/tree/tools
+[uci-link]:           https://www.shredderchess.com/download/div/uci.zip
+[website-link]:       https://stockfishchess.org
+[worker-link]:        https://github.com/glinscott/fishtest/wiki/Running-the-worker:-overview
+
+[build-badge]:        https://img.shields.io/github/actions/workflow/status/official-stockfish/Stockfish/stockfish.yml?branch=master&style=for-the-badge&label=stockfish&logo=github
+[commits-badge]:      https://img.shields.io/github/commits-since/official-stockfish/Stockfish/latest?style=for-the-badge
+[discord-badge]:      https://img.shields.io/discord/435943710472011776?style=for-the-badge&label=discord&logo=Discord
+[fishtest-badge]:     https://img.shields.io/website?style=for-the-badge&down_color=red&down_message=Offline&label=Fishtest&up_color=success&up_message=Online&url=https%3A%2F%2Ftests.stockfishchess.org%2Ftests%2Ffinished
+[license-badge]:      https://img.shields.io/github/license/official-stockfish/Stockfish?style=for-the-badge&label=license&color=success
+[release-badge]:      https://img.shields.io/github/v/release/official-stockfish/Stockfish?style=for-the-badge&label=official%20release
+[website-badge]:      https://img.shields.io/website?style=for-the-badge&down_color=red&down_message=Offline&label=website&up_color=success&up_message=Online&url=https%3A%2F%2Fstockfishchess.org
index 23a5d7f97e21128b804804f26074124946764c2a..30c963d7c7e6389f8ebaee76249f7acebc35ea93 100644 (file)
-Contributors to Fishtest with >10,000 CPU hours, as of 2022-07-31.
+Contributors to Fishtest with >10,000 CPU hours, as of 2022-11-19.
 Thank you!
 
 Username                                CPU Hours     Games played
 ------------------------------------------------------------------
-noobpwnftw                               33202707       2423743815
-technologov                               5064327        270208248
-mlang                                     2963357        198937430
-dew                                       1677196         99717674
-grandphish2                               1231326         74551309
-okrout                                    1102747         98977462
-TueRens                                    925904         57404676
-pemo                                       911980         35581261
-tvijlbrief                                 795993         51894442
-JojoM                                      774270         47311084
+noobpwnftw                               36475307       2748033975
+technologov                              14570711        760073590
+mlang                                     3026000        200065824
+dew                                       1689222        100034318
+grandphish2                               1442171         86798057
+okrout                                    1439985        133471766
+pemo                                      1405374         44189811
+linrock                                   1299003         28382783
+TueRens                                   1163420         71159522
+JojoM                                      897158         55177114
+tvijlbrief                                 796125         51897690
 mibere                                     703840         46867607
-linrock                                    697283         18804969
-gvreuls                                    564284         36392236
-cw                                         515739         34775505
-fastgm                                     500949         30101898
-oz                                         439015         31794460
-CSU_Dynasty                                438017         29369136
+gvreuls                                    635982         40652394
+oz                                         590763         41201352
+sebastronomy                               581517         23307132
+cw                                         517915         34865769
+fastgm                                     504266         30264740
+CSU_Dynasty                                479901         31846710
+ctoks                                      433503         28180725
 crunchy                                    427035         27344275
-ctoks                                      422671         27812261
-bcross                                     363335         25108521
-leszek                                     360149         22674005
-velislav                                   333325         21444360
+leszek                                     416883         27493447
+bcross                                     409982         28062127
+velislav                                   345954         22232274
 Fisherman                                  327231         21829379
-Dantist                                    292327         17951982
-mgrabiak                                   247220         16137378
-nordlandia                                 226543         14601042
-robal                                      224740         14314972
-glinscott                                  217799         13780820
-ncfish1                                    207751         13909639
-drabel                                     203884         13922680
-mhoram                                     200022         12533963
+Dantist                                    296386         18031762
+mgrabiak                                   288928         18869896
+rpngn                                      259965         16281463
+robal                                      237653         15148350
+ncfish1                                    231764         15275003
+nordlandia                                 226923         14624832
+glinscott                                  208125         13277240
+drabel                                     204167         13930674
+mhoram                                     202894         12601997
 bking_US                                   198894         11876016
-rpngn                                      191764         12236583
+thirdlife                                  198844          5453268
 Thanar                                     179852         12365359
 vdv                                        175544          9904472
+armo9494                                   168201         11136452
 spams                                      157128         10319326
-marrco                                     150300          9402229
+marrco                                     151599          9551115
 sqrt2                                      147963          9724586
-vdbergh                                    137480          8958795
+vdbergh                                    137690          8971569
 CoffeeOne                                  137100          5024116
 malala                                     136182          8002293
+DesolatedDodo                              135276          8657464
 xoto                                       133759          9159372
-davar                                      128645          8367253
-DesolatedDodo                              124877          8056482
+davar                                      129023          8376525
 dsmith                                     122059          7570238
 amicic                                     119661          7938029
 Data                                       113305          8220352
 BrunoBanani                                112960          7436849
-CypressChess                               108321          7759588
+CypressChess                               108331          7759788
+skiminki                                   106518          7062598
 MaZePallas                                 102823          6633619
-skiminki                                   102168          6778440
 sterni1971                                 100532          5880772
 sunu                                       100167          7040199
+zeryl                                       99331          6221261
 ElbertoOne                                  99028          7023771
-zeryl                                       96984          6162287
+DMBK                                        97572          6950312
+Calis007                                    96779          5611552
+cuistot                                     93111          5536500
 brabos                                      92118          6186135
-cuistot                                     91738          5447070
+Wolfgang                                    91769          5720158
 psk                                         89957          5984901
-racerschmacer                               85712          6119648
+racerschmacer                               85805          6122790
+jcAEie                                      85527          5630616
 Vizvezdenec                                 83761          5344740
-sschnee                                     83003          4840890
+sschnee                                     83557          4853690
 0x3C33                                      82614          5271253
-armo9494                                    82501          5806056
 BRAVONE                                     81239          5054681
+Dubslow                                     78461          5042980
 nssy                                        76497          5259388
-thirdlife                                   76478          1544524
-Calis007                                    76457          4281018
-jromang                                     75885          5230523
+jromang                                     76106          5236025
 teddybaer                                   75125          5407666
+yurikvelo                                   73933          5031096
+tolkki963                                   73885          4721430
 Pking_cda                                   73776          5293873
-Wolfgang                                    72750          4538670
-sebastronomy                                70784          1329428
+Bobo1239                                    71675          4860987
 solarlight                                  70517          5028306
 dv8silencer                                 70287          3883992
-Bobo1239                                    68515          4652287
-yurikvelo                                   67651          4578970
+Gelma                                       69304          3980932
 manap                                       66273          4121774
+megaman7de                                  65419          4120200
+markkulix                                   65331          4114860
+bigpen0r                                    64932          4683883
 tinker                                      64333          4268790
 qurashee                                    61208          3429862
+AGI                                         58325          4258646
 robnjr                                      57262          4053117
-megaman7de                                  57023          3525850
 Freja                                       56938          3733019
-MaxKlaxxMiner                               56279          3410158
+MaxKlaxxMiner                               56879          3423958
 ttruscott                                   56010          3680085
 rkl                                         55132          4164467
 renouve                                     53811          3501516
-tolkki963                                   53294          3354682
-DMBK                                        52963          3933332
+Spprtr                                      52736          3410019
 finfish                                     51360          3370515
 eva42                                       51272          3599691
-Spprtr                                      51139          3299983
-eastorwest                                  51058          3451555
+eastorwest                                  51117          3454811
 rap                                         49985          3219146
+unixwizard                                  49734          2536230
 pb00067                                     49727          3298270
-bigpen0r                                    47667          3336927
 ronaldjerum                                 47654          3240695
 biffhero                                    46564          3111352
+GPUex                                       45861          2926502
 Fifis                                       45843          3088497
+oryx                                        45578          3493978
 VoyagerOne                                  45476          3452465
+Wencey                                      44943          2654490
 speedycpu                                   43842          3003273
 jbwiebe                                     43305          2805433
 Antihistamine                               41788          2761312
 mhunt                                       41735          2691355
+olafm                                       41277          3284344
 homyur                                      39893          2850481
 gri                                         39871          2515779
-oryx                                        39602          3024830
+MarcusTullius                               38303          2251097
+Garf                                        37741          2999686
+kdave                                       37424          2557406
 SC                                          37299          2731694
-Garf                                        37213          2986270
-Dubslow                                     36714          2409254
 csnodgrass                                  36207          2688994
 jmdana                                      36157          2210661
-markkulix                                   35994          2226860
 strelock                                    34716          2074055
 EthanOConnor                                33370          2090311
 slakovv                                     32915          2021889
-gopeto                                      31078          2033362
+gopeto                                      31669          2060958
 manapbk                                     30987          1810399
 Prcuvu                                      30377          2170122
 anst                                        30301          2190091
 jkiiski                                     30136          1904470
+spcc                                        30135          1903728
 hyperbolic.tom                              29840          2017394
+xwziegtm                                    29763          2347412
 chuckstablers                               29659          2093438
 Pyafue                                      29650          1902349
-MarcusTullius                               28611          1646671
-spcc                                        28241          1821198
-belzedar94                                  27935          1789106
+belzedar94                                  28846          1811530
 OuaisBla                                    27636          1578800
 chriswk                                     26902          1868317
 achambord                                   26582          1767323
 Patrick_G                                   26276          1801617
 yorkman                                     26193          1992080
+Ulysses                                     25289          1674274
 SFTUser                                     25182          1675689
 nabildanial                                 24942          1519409
 Sharaf_DG                                   24765          1786697
-rodneyc                                     24375          1416258
-Ulysses                                     24017          1626140
+rodneyc                                     24376          1416402
 agg177                                      23890          1395014
+Ente                                        23747          1674582
+Karpovbot                                   23629          1313186
 JanErik                                     23408          1703875
-Ente                                        23403          1660988
-kdave                                       23392          1630462
 Isidor                                      23388          1680691
-Norabor                                     23339          1602636
-cisco2015                                   22897          1762669
-Wencey                                      22573          1121406
+Norabor                                     23371          1603244
+cisco2015                                   22934          1763773
 Zirie                                       22542          1472937
 team-oh                                     22272          1636708
+Roady                                       22220          1465606
 MazeOfGalious                               21978          1629593
-sg4032                                      21947          1643265
+sg4032                                      21947          1643353
 ianh2105                                    21725          1632562
 xor12                                       21628          1680365
 dex                                         21612          1467203
 nesoneg                                     21494          1463031
-Roady                                       21323          1433822
+user213718                                  21454          1404128
+AndreasKrug                                 21227          1577833
 sphinx                                      21211          1384728
-user213718                                  21196          1397710
 jjoshua2                                    21001          1423089
 horst.prack                                 20878          1465656
+jsys14                                      20729          1221010
 0xB00B1ES                                   20590          1208666
 j3corre                                     20405           941444
 Adrian.Schmidt123                           20316          1281436
-jcAEie                                      20221          1504162
+bonsi                                       20022          1300682
 wei                                         19973          1745989
+dapper                                      19754          1167758
+Zake9298                                    19745          1458416
+fishtester                                  19617          1257388
 rstoesser                                   19569          1293588
 eudhan                                      19274          1283717
-fishtester                                  19145          1242668
 vulcan                                      18871          1729392
+Jopo12321                                   18803          1036284
 jundery                                     18445          1115855
-iisiraider                                  18247          1101015
 ville                                       17883          1384026
+5t0ckf15hTr4in3r                            17809          1105858
 chris                                       17698          1487385
+dju                                         17697           994333
 purplefishies                               17595          1092533
-dju                                         17353           978595
-AndreasKrug                                 17191          1317997
+iisiraider                                  17275          1049015
 DragonLord                                  17014          1162790
-Jopo12321                                   16966           944924
-GPUex                                       16744          1077826
-xwziegtm                                    16608          1276372
+Karby                                       16457          1010138
+Goatminola                                  16278          1145026
 IgorLeMasson                                16064          1147232
+Gaster319                                   16056          1109070
+redstone59                                  15953          1161664
+scuzzi                                      15757           968735
 ako027ako                                   15671          1173203
-jsys14                                      15474           917092
 Nikolay.IT                                  15154          1068349
 Andrew Grant                                15114           895539
-scuzzi                                      15112           960373
+Naven94                                     15054           834762
 OssumOpossum                                14857          1007129
-Karby                                       14808           867120
+qoo_charly_cai                              14490           847865
 enedene                                     14476           905279
-bpfliegel                                   14298           884523
+szupaw                                      14252           929130
+bpfliegel                                   14233           882523
 mpx86                                       14019           759568
 jpulman                                     13982           870599
-Naven94                                     13879           811552
-Karpovbot                                   13808           734276
 crocogoat                                   13803          1117422
-joster                                      13794           950160
 Nesa92                                      13786          1114691
+joster                                      13710           946160
 mbeier                                      13650          1044928
 Hjax                                        13535           915487
 Dark_wizzie                                 13422          1007152
 Rudolphous                                  13244           883140
 Machariel                                   13010           863104
+infinigon                                   12991           943216
+pirt                                        12925           985437
+Skiff84                                     12923           649994
 mabichito                                   12903           749391
 thijsk                                      12886           722107
 AdrianSA                                    12860           804972
-infinigon                                   12807           937332
 Flopzee                                     12698           894821
-pirt                                        12551           965597
 fatmurphy                                   12547           853210
+woutboat                                    12419           836696
 SapphireBrand                               12416           969604
+Oakwen                                      12406           840961
+deflectooor                                 12386           579392
 modolief                                    12386           896470
 Farseer                                     12249           694108
 pgontarz                                    12151           848794
 stocky                                      11954           699440
 mschmidt                                    11941           803401
-Oakwen                                      11925           818865
-MooTheCow                                   11851           772628
-deflectooor                                 11642           565132
-dbernier                                    11609           818636
-Skiff84                                     11604           602786
+MooTheCow                                   11871           773654
+Jackfish                                    11867           773550
+dbernier                                    11705           821780
+whelanh                                     11557           245188
 Maxim                                       11543           836024
+Nullvalue                                   11534           731410
+icewulf                                     11528           650470
+FormazChar                                  11523           861599
 infinity                                    11470           727027
-FormazChar                                  11430           856559
-aga                                         11409           695071
-Jackfish                                    11403           750526
+aga                                         11412           695127
 torbjo                                      11395           729145
 Thomas A. Anderson                          11372           732094
 savage84                                    11358           670860
+ali-al-zhrani                               11272           781310
 d64                                         11263           789184
-qoo_charly_cai                              11127           671959
+Bourbaki                                    11108           709144
 snicolet                                    11106           869170
-ali-al-zhrani                               11098           768494
-whelanh                                     11067           235676
+Alb11747                                    10855           696920
 basepi                                      10637           744851
 Cubox                                       10621           826448
-Alb11747                                    10558           689794
+Karmatron                                   10616           674818
 michaelrpg                                  10509           739239
 OIVAS7572                                   10420           995586
-Garruk                                      10343           704723
+Garruk                                      10348           704905
 dzjp                                        10343           732529
 ols                                         10259           570669
-lbraesch                                    10252           647825
-Karmatron                                   10195           661432
index 23c19bfb43c7253faafa30621fcf72892d06fe56..171f966cc2473b53a7c7ac531b3ba42778edb618 100644 (file)
@@ -119,7 +119,7 @@ ifeq ($(ARCH), $(filter $(ARCH), \
                  x86-64-vnni512 x86-64-vnni256 x86-64-avx512 x86-64-avxvnni x86-64-bmi2 \
                  x86-64-avx2 x86-64-sse41-popcnt x86-64-modern x86-64-ssse3 x86-64-sse3-popcnt \
                  x86-64 x86-32-sse41-popcnt x86-32-sse2 x86-32 ppc-64 ppc-32 e2k \
-                 armv7 armv7-neon armv8 apple-silicon general-64 general-32))
+                 armv7 armv7-neon armv8 apple-silicon general-64 general-32 riscv64))
    SUPPORTED_ARCH=true
 else
    SUPPORTED_ARCH=false
@@ -341,7 +341,11 @@ ifeq ($(findstring e2k,$(ARCH)),e2k)
        popcnt = yes
 endif
 
+ifeq ($(ARCH),riscv64)
+       arch = riscv64
 endif
+endif
+
 
 ### ==========================================================================
 ### Section 3. Low-level Configuration
@@ -367,11 +371,14 @@ ifeq ($(COMP),gcc)
        CXX=g++
        CXXFLAGS += -pedantic -Wextra
 
-       ifeq ($(arch),$(filter $(arch),armv7 armv8))
+       ifeq ($(arch),$(filter $(arch),armv7 armv8 riscv64))
                ifeq ($(OS),Android)
                        CXXFLAGS += -m$(bits)
                        LDFLAGS += -m$(bits)
                endif
+               ifeq ($(ARCH),riscv64)
+                       CXXFLAGS += -latomic
+               endif
        else
                CXXFLAGS += -m$(bits)
                LDFLAGS += -m$(bits)
@@ -432,11 +439,14 @@ ifeq ($(COMP),clang)
        endif
        endif
 
-       ifeq ($(arch),$(filter $(arch),armv7 armv8))
+       ifeq ($(arch),$(filter $(arch),armv7 armv8 riscv64))
                ifeq ($(OS),Android)
                        CXXFLAGS += -m$(bits)
                        LDFLAGS += -m$(bits)
                endif
+               ifeq ($(ARCH),riscv64)
+                       CXXFLAGS += -latomic
+               endif
        else
                CXXFLAGS += -m$(bits)
                LDFLAGS += -m$(bits)
@@ -505,7 +515,7 @@ endif
 
 ### Sometimes gcc is really clang
 ifeq ($(COMP),gcc)
-       gccversion = $(shell $(CXX) --version)
+       gccversion = $(shell $(CXX) --version 2>/dev/null)
        gccisclang = $(findstring clang,$(gccversion))
        ifneq ($(gccisclang),)
                profile_make = clang-profile-make
@@ -596,7 +606,7 @@ endif
 ifeq ($(avx2),yes)
        CXXFLAGS += -DUSE_AVX2
        ifeq ($(comp),$(filter $(comp),gcc clang mingw))
-               CXXFLAGS += -mavx2
+               CXXFLAGS += -mavx2 -mbmi
        endif
 endif
 
@@ -675,13 +685,25 @@ ifeq ($(pext),yes)
        endif
 endif
 
+### 3.7.1 Try to include git commit sha for versioning
+GIT_SHA = $(shell git rev-parse --short HEAD 2>/dev/null)
+ifneq ($(GIT_SHA), )
+       CXXFLAGS += -DGIT_SHA=\"$(GIT_SHA)\"
+endif
+
+### 3.7.2 Try to include git commit date for versioning
+GIT_DATE = $(shell git show -s --date=format:'%Y%m%d' --format=%cd HEAD 2>/dev/null)
+ifneq ($(GIT_DATE), )
+       CXXFLAGS += -DGIT_DATE=\"$(GIT_DATE)\"
+endif
+
 ### 3.8 Link Time Optimization
 ### This is a mix of compile and link time options because the lto link phase
 ### needs access to the optimization flags.
 ifeq ($(optimize),yes)
 ifeq ($(debug), no)
        ifeq ($(comp),clang)
-               CXXFLAGS += -flto
+               CXXFLAGS += -flto=full
                ifeq ($(target_windows),yes)
                        CXXFLAGS += -fuse-ld=lld
                endif
@@ -691,21 +713,19 @@ ifeq ($(debug), no)
 # GCC on some systems.
        else ifeq ($(comp),gcc)
        ifeq ($(gccisclang),)
-               CXXFLAGS += -flto
+               CXXFLAGS += -flto -flto-partition=one
                LDFLAGS += $(CXXFLAGS) -flto=jobserver
        else
-               CXXFLAGS += -flto
+               CXXFLAGS += -flto=full
                LDFLAGS += $(CXXFLAGS)
        endif
 
 # To use LTO and static linking on Windows,
 # the tool chain requires gcc version 10.1 or later.
        else ifeq ($(comp),mingw)
-       ifneq ($(arch),i386)
-               CXXFLAGS += -flto
+               CXXFLAGS += -flto -flto-partition=one
                LDFLAGS += $(CXXFLAGS) -save-temps
        endif
-       endif
 endif
 endif
 
@@ -730,9 +750,9 @@ help:
        @echo "Supported targets:"
        @echo ""
        @echo "help                    > Display architecture details"
-       @echo "build                   > Standard build"
+       @echo "profile-build           > standard build with profile-guided optimization"
+       @echo "build                   > skip profile-guided optimization"
        @echo "net                     > Download the default nnue net"
-       @echo "profile-build           > Faster build (with profile-guided optimization)"
        @echo "strip                   > Strip executable"
        @echo "install                 > Install executable"
        @echo "clean                   > Clean up"
@@ -762,6 +782,7 @@ help:
        @echo "apple-silicon           > Apple silicon ARM64"
        @echo "general-64              > unspecified 64-bit"
        @echo "general-32              > unspecified 32-bit"
+       @echo "riscv64                 > RISC-V 64-bit"
        @echo ""
        @echo "Supported compilers:"
        @echo ""
@@ -771,14 +792,15 @@ help:
        @echo "icc                     > Intel compiler"
        @echo "ndk                     > Google NDK to cross-compile for Android"
        @echo ""
-       @echo "Simple examples. If you don't know what to do, you likely want to run: "
+       @echo "Simple examples. If you don't know what to do, you likely want to run one of: "
        @echo ""
-       @echo "make -j build ARCH=x86-64  (A portable, slow compile for 64-bit systems)"
-       @echo "make -j build ARCH=x86-32  (A portable, slow compile for 32-bit systems)"
+       @echo "make -j profile-build ARCH=x86-64-avx2    # typically a fast compile for common systems "
+       @echo "make -j profile-build ARCH=x86-64-modern  # A more portable compile for 64-bit systems "
+       @echo "make -j profile-build ARCH=x86-64         # A portable compile for 64-bit systems "
        @echo ""
-       @echo "Advanced examples, for experienced users looking for performance: "
+       @echo "Advanced examples, for experienced users: "
        @echo ""
-       @echo "make    help  ARCH=x86-64-bmi2"
+       @echo "make -j profile-build ARCH=x86-64-bmi2"
        @echo "make -j profile-build ARCH=x86-64-bmi2 COMP=gcc COMPCXX=g++-9.0"
        @echo "make -j build ARCH=x86-64-ssse3 COMP=clang"
        @echo ""
@@ -794,7 +816,7 @@ endif
 
 .PHONY: help build profile-build strip install clean net objclean profileclean \
         config-sanity icc-profile-use icc-profile-make gcc-profile-use gcc-profile-make \
-        clang-profile-use clang-profile-make
+        clang-profile-use clang-profile-make FORCE
 
 build: net config-sanity
        $(MAKE) ARCH=$(ARCH) COMP=$(COMP) all
@@ -834,7 +856,7 @@ net:
        $(eval nnuedownloadurl2 := https://github.com/official-stockfish/networks/raw/master/$(nnuenet))
        $(eval curl_or_wget := $(shell if hash curl 2>/dev/null; then echo "curl -skL"; elif hash wget 2>/dev/null; then echo "wget -qO-"; fi))
        @if [ "x$(curl_or_wget)" = "x" ]; then \
-           echo "Automatic download failed: neither curl nor wget is installed. Install one of these tools or download the net manually"; exit 1; \
+           echo "Neither curl nor wget is installed. Install one of these tools unless the net has been downloaded manually"; \
         fi
        $(eval shasum_command := $(shell if hash shasum 2>/dev/null; then echo "shasum -a 256 "; elif hash sha256sum 2>/dev/null; then echo "sha256sum "; fi))
        @if [ "x$(shasum_command)" = "x" ]; then \
@@ -845,7 +867,9 @@ net:
              echo "$(nnuenet) available."; \
           else \
              if [ "x$(curl_or_wget)" != "x" ]; then \
-                echo "Downloading $${nnuedownloadurl}"; $(curl_or_wget) $${nnuedownloadurl} > $(nnuenet);\
+                 echo "Downloading $${nnuedownloadurl}"; $(curl_or_wget) $${nnuedownloadurl} > $(nnuenet);\
+              else \
+                 echo "No net found and download not possible"; exit 1;\
              fi; \
           fi; \
           if [ "x$(shasum_command)" != "x" ]; then \
@@ -921,7 +945,7 @@ config-sanity: net
        @test "$(SUPPORTED_ARCH)" = "true"
        @test "$(arch)" = "any" || test "$(arch)" = "x86_64" || test "$(arch)" = "i386" || \
         test "$(arch)" = "ppc64" || test "$(arch)" = "ppc" || test "$(arch)" = "e2k" || \
-        test "$(arch)" = "armv7" || test "$(arch)" = "armv8" || test "$(arch)" = "arm64"
+        test "$(arch)" = "armv7" || test "$(arch)" = "armv8" || test "$(arch)" = "arm64" || test "$(arch)" = "riscv64"
        @test "$(bits)" = "32" || test "$(bits)" = "64"
        @test "$(prefetch)" = "yes" || test "$(prefetch)" = "no"
        @test "$(popcnt)" = "yes" || test "$(popcnt)" = "no"
@@ -942,6 +966,10 @@ config-sanity: net
 $(EXE): $(OBJS)
        +$(CXX) -o $@ $(OBJS) $(LDFLAGS)
 
+# Force recompilation to ensure version info is up-to-date
+misc.o: FORCE
+FORCE:
+
 clang-profile-make:
        $(MAKE) ARCH=$(ARCH) COMP=$(COMP) \
        EXTRACXXFLAGS='-fprofile-instr-generate ' \
@@ -1010,4 +1038,6 @@ client: $(CLIOBJS)
 .depend: $(SRCS)
        -@$(CXX) $(DEPENDFLAGS) -MM $(SRCS) > $@ 2> /dev/null
 
+ifeq (, $(filter $(MAKECMDGOALS), help strip install clean net objclean profileclean config-sanity))
 -include .depend
+endif
index 85700bcc60dc2b5d26251c9ebec4d8336a2c6cd9..7619398e01fcb9f334a519c92999f2c967e6b438 100644 (file)
@@ -159,7 +159,7 @@ namespace Trace {
 
   Score scores[TERM_NB][COLOR_NB];
 
-  double to_cp(Value v) { return double(v) / PawnValueEg; }
+  double to_cp(Value v) { return double(v) / UCI::NormalizeToPawnValue; }
 
   void add(int idx, Color c, Score s) {
     scores[idx][c] = s;
@@ -981,7 +981,7 @@ namespace {
     // Initialize score by reading the incrementally updated scores included in
     // the position object (material + piece square tables) and the material
     // imbalance. Score is computed internally from the white point of view.
-    Score score = pos.psq_score() + me->imbalance() + pos.this_thread()->trend;
+    Score score = pos.psq_score() + me->imbalance();
 
     // Probe the pawn hash table
     pe = Pawns::probe(pos);
@@ -1051,39 +1051,47 @@ make_v:
 Value Eval::evaluate(const Position& pos, int* complexity) {
 
   Value v;
-  Color stm = pos.side_to_move();
   Value psq = pos.psq_eg_stm();
 
   // We use the much less accurate but faster Classical eval when the NNUE
   // option is set to false. Otherwise we use the NNUE eval unless the
-  // PSQ advantage is decisive and several pieces remain (~3 Elo)
+  // PSQ advantage is decisive and several pieces remain. (~3 Elo)
   bool useClassical = !useNNUE || (pos.count<ALL_PIECES>() > 7 && abs(psq) > 1760);
+
   if (useClassical)
       v = Evaluation<NO_TRACE>(pos).value();
   else
   {
       int nnueComplexity;
-      int scale = 1064 + 106 * pos.non_pawn_material() / 5120;
+      int scale = 1076 + 96 * pos.non_pawn_material() / 5120;
+
+      Color stm = pos.side_to_move();
       Value optimism = pos.this_thread()->optimism[stm];
 
       Value nnue = NNUE::evaluate(pos, true, &nnueComplexity);
+
       // Blend nnue complexity with (semi)classical complexity
-      nnueComplexity = (104 * nnueComplexity + 131 * abs(nnue - psq)) / 256;
-      if (complexity) // Return hybrid NNUE complexity to caller
+      nnueComplexity = (  412 * nnueComplexity
+                        + 428 * abs(psq - nnue)
+                        + (optimism  > 0 ? int(optimism) * int(psq - nnue) : 0)
+                        ) / 1024;
+
+      // Return hybrid NNUE complexity to caller
+      if (complexity)
           *complexity = nnueComplexity;
 
-      optimism = optimism * (269 + nnueComplexity) / 256;
-      v = (nnue * scale + optimism * (scale - 754)) / 1024;
+      optimism = optimism * (278 + nnueComplexity) / 256;
+      v = (nnue * scale + optimism * (scale - 755)) / 1024;
   }
 
   // Damp down the evaluation linearly when shuffling
-  v = v * (195 - pos.rule50_count()) / 211;
+  v = v * (197 - pos.rule50_count()) / 214;
 
   // Guarantee evaluation does not hit the tablebase range
   v = std::clamp(v, VALUE_TB_LOSS_IN_MAX_PLY + 1, VALUE_TB_WIN_IN_MAX_PLY - 1);
 
   // When not using NNUE, return classical complexity to caller
-  if (complexity && (!useNNUE || useClassical))
+  if (complexity && useClassical)
       *complexity = abs(v - psq);
 
   return v;
@@ -1107,7 +1115,6 @@ std::string Eval::trace(Position& pos) {
   std::memset(scores, 0, sizeof(scores));
 
   // Reset any global variable used in eval
-  pos.this_thread()->trend           = SCORE_ZERO;
   pos.this_thread()->bestValue       = VALUE_ZERO;
   pos.this_thread()->optimism[WHITE] = VALUE_ZERO;
   pos.this_thread()->optimism[BLACK] = VALUE_ZERO;
index f5ac3263c3380267cc7c9ce15bc66830e6ce4d56..d1398dd5ba859e9eec68760adf66e86e52937ff3 100644 (file)
@@ -39,7 +39,7 @@ namespace Eval {
   // The default net name MUST follow the format nn-[SHA256 first 12 digits].nnue
   // for the build process (profile-build and fishtest) to work. Do not change the
   // name of the macro, as it is used in the Makefile.
-  #define EvalFileDefaultName   "nn-ad9b42354671.nnue"
+  #define EvalFileDefaultName   "nn-335a9b2d8a80.nnue"
 
   namespace NNUE {
 
index 9cfd63047606555db23fb81f35ba781337e5701b..3c336c3014c7b5a4524df40c7b03c04dd560f866 100644 (file)
@@ -67,9 +67,8 @@ namespace Stockfish {
 
 namespace {
 
-/// Version number. If Version is left empty, then compile date in the format
-/// DD-MM-YY and show in engine_info.
-const string Version = "";
+/// Version number or dev.
+const string version = "dev";
 
 /// Our fancy logging facility. The trick here is to replace cin.rdbuf() and
 /// cout.rdbuf() with two Tie objects that tie cin and cout to a file stream. We
@@ -138,23 +137,34 @@ public:
 } // namespace
 
 
-/// engine_info() returns the full name of the current Stockfish version. This
-/// will be either "Stockfish <Tag> DD-MM-YY" (where DD-MM-YY is the date when
-/// the program was compiled) or "Stockfish <Version>", depending on whether
-/// Version is empty.
+/// engine_info() returns the full name of the current Stockfish version.
+/// For local dev compiles we try to append the commit sha and commit date
+/// from git if that fails only the local compilation date is set and "nogit" is specified:
+/// Stockfish dev-YYYYMMDD-SHA
+/// or
+/// Stockfish dev-YYYYMMDD-nogit
+///
+/// For releases (non dev builds) we only include the version number:
+/// Stockfish version
 
 string engine_info(bool to_uci) {
+  stringstream ss;
+  ss << "Stockfish " << version << setfill('0');
 
-  const string months("Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec");
-  string month, day, year;
-  stringstream ss, date(__DATE__); // From compiler, format is "Sep 21 2008"
-
-  ss << "Stockfish " << Version << setfill('0');
-
-  if (Version.empty())
+  if (version == "dev")
   {
+      ss << "-";
+      #ifdef GIT_DATE
+      ss << GIT_DATE;
+      #else
+      const string months("Jan Feb Mar Apr May Jun Jul Aug Sep Oct Nov Dec");
+      string month, day, year;
+      stringstream date(__DATE__); // From compiler, format is "Sep 21 2008"
+
       date >> month >> day >> year;
-      ss << setw(2) << day << setw(2) << (1 + months.find(month) / 4) << year.substr(2);
+      ss << year << setw(2) << setfill('0') << (1 + months.find(month) / 4) << setw(2) << setfill('0') << day;
+      #endif
+
       ss << "-asn";
   }
 
index 3428a764f1ad3116d765828a50a4e9a522e16804..564adc286ea8221e01cac1dce4ac3d2d5cf72ca1 100644 (file)
@@ -83,14 +83,13 @@ MovePicker::MovePicker(const Position& p, Move ttm, Depth d, const ButterflyHist
 
   stage = (pos.checkers() ? EVASION_TT : QSEARCH_TT) +
           !(   ttm
-            && (pos.checkers() || depth > DEPTH_QS_RECAPTURES || to_sq(ttm) == recaptureSquare)
             && pos.pseudo_legal(ttm));
 }
 
 /// MovePicker constructor for ProbCut: we generate captures with SEE greater
 /// than or equal to the given threshold.
-MovePicker::MovePicker(const Position& p, Move ttm, Value th, Depth d, const CapturePieceToHistory* cph)
-           : pos(p), captureHistory(cph), ttMove(ttm), threshold(th), depth(d)
+MovePicker::MovePicker(const Position& p, Move ttm, Value th, const CapturePieceToHistory* cph)
+           : pos(p), captureHistory(cph), ttMove(ttm), threshold(th)
 {
   assert(!pos.checkers());
 
@@ -101,7 +100,7 @@ MovePicker::MovePicker(const Position& p, Move ttm, Value th, Depth d, const Cap
 
 /// MovePicker::score() assigns a numerical value to each move in a list, used
 /// for sorting. Captures are ordered by Most Valuable Victim (MVV), preferring
-/// captures with a good history. Quiets moves are ordered using the histories.
+/// captures with a good history. Quiets moves are ordered using the history tables.
 template<GenType Type>
 void MovePicker::score() {
 
@@ -124,8 +123,8 @@ void MovePicker::score() {
 
   for (auto& m : *this)
       if constexpr (Type == CAPTURES)
-          m.value =  6 * int(PieceValue[MG][pos.piece_on(to_sq(m))])
-                   +     (*captureHistory)[pos.moved_piece(m)][to_sq(m)][type_of(pos.piece_on(to_sq(m)))];
+          m.value =  (7 * int(PieceValue[MG][pos.piece_on(to_sq(m))])
+                   +     (*captureHistory)[pos.moved_piece(m)][to_sq(m)][type_of(pos.piece_on(to_sq(m)))]) / 16;
 
       else if constexpr (Type == QUIETS)
           m.value =  2 * (*mainHistory)[pos.side_to_move()][from_to(m)]
@@ -192,13 +191,13 @@ top:
       endMoves = generate<CAPTURES>(pos, cur);
 
       score<CAPTURES>();
-      partial_insertion_sort(cur, endMoves, -3000 * depth);
+      partial_insertion_sort(cur, endMoves, std::numeric_limits<int>::min());
       ++stage;
       goto top;
 
   case GOOD_CAPTURE:
       if (select<Next>([&](){
-                       return pos.see_ge(*cur, Value(-69 * cur->value / 1024)) ?
+                       return pos.see_ge(*cur, Value(-cur->value)) ?
                               // Move losing capture to endBadCaptures to be tried later
                               true : (*endBadCaptures++ = *cur, false); }))
           return *(cur - 1);
index 55fcc6442dc871923400ac2fbd804d1453e0f907..e4c4a5bfdeaa6008db744a9e527bb822aca1f60c 100644 (file)
@@ -128,7 +128,7 @@ public:
                                            const CapturePieceToHistory*,
                                            const PieceToHistory**,
                                            Square);
-  MovePicker(const Position&, Move, Value, Depth, const CapturePieceToHistory*);
+  MovePicker(const Position&, Move, Value, const CapturePieceToHistory*);
   Move next_move(bool skipQuiets = false);
 
   Bitboard threatenedPieces;
index ba2ed36746c00cb2bf4da9c1fd2457c4309350cd..4715fed07d6c71e27e0d1fa69169f12f9f853017 100644 (file)
@@ -220,7 +220,7 @@ namespace Stockfish::Eval::NNUE {
 
     buffer[0] = (v < 0 ? '-' : v > 0 ? '+' : ' ');
 
-    int cp = std::abs(100 * v / PawnValueEg);
+    int cp = std::abs(100 * v / UCI::NormalizeToPawnValue);
     if (cp >= 10000)
     {
         buffer[1] = '0' + cp / 10000; cp %= 10000;
@@ -251,7 +251,7 @@ namespace Stockfish::Eval::NNUE {
 
     buffer[0] = (v < 0 ? '-' : v > 0 ? '+' : ' ');
 
-    double cp = 1.0 * std::abs(int(v)) / PawnValueEg;
+    double cp = 1.0 * std::abs(int(v)) / UCI::NormalizeToPawnValue;
     sprintf(&buffer[1], "%6.2f", cp);
   }
 
index 07a1d7a154dca59ec6d0e977937169de37458153..7dbd3415624c973d47727d5f6f0d92ebfe140766 100644 (file)
 
 namespace Stockfish::Eval::NNUE::Features {
 
-  // Orient a square according to perspective (rotates by 180 for black)
-  inline Square HalfKAv2_hm::orient(Color perspective, Square s, Square ksq) {
-    return Square(int(s) ^ (bool(perspective) * SQ_A8) ^ ((file_of(ksq) < FILE_E) * SQ_H1));
-  }
-
   // Index of a feature for a given king position and another piece on some square
-  inline IndexType HalfKAv2_hm::make_index(Color perspective, Square s, Piece pc, Square ksq) {
-    Square o_ksq = orient(perspective, ksq, ksq);
-    return IndexType(orient(perspective, s, ksq) + PieceSquareIndex[perspective][pc] + PS_NB * KingBuckets[o_ksq]);
+  template<Color Perspective>
+  inline IndexType HalfKAv2_hm::make_index(Square s, Piece pc, Square ksq) {
+    return IndexType((int(s) ^ OrientTBL[Perspective][ksq]) + PieceSquareIndex[Perspective][pc] + KingBuckets[Perspective][ksq]);
   }
 
   // Get a list of indices for active features
+  template<Color Perspective>
   void HalfKAv2_hm::append_active_indices(
     const Position& pos,
-    Color perspective,
     IndexList& active
   ) {
-    Square ksq = pos.square<KING>(perspective);
+    Square ksq = pos.square<KING>(Perspective);
     Bitboard bb = pos.pieces();
     while (bb)
     {
       Square s = pop_lsb(bb);
-      active.push_back(make_index(perspective, s, pos.piece_on(s), ksq));
+      active.push_back(make_index<Perspective>(s, pos.piece_on(s), ksq));
     }
   }
 
+  // Explicit template instantiations
+  template void HalfKAv2_hm::append_active_indices<WHITE>(const Position& pos, IndexList& active);
+  template void HalfKAv2_hm::append_active_indices<BLACK>(const Position& pos, IndexList& active);
 
   // append_changed_indices() : get a list of indices for recently changed features
-
+  template<Color Perspective>
   void HalfKAv2_hm::append_changed_indices(
     Square ksq,
     const DirtyPiece& dp,
-    Color perspective,
     IndexList& removed,
     IndexList& added
   ) {
     for (int i = 0; i < dp.dirty_num; ++i) {
       if (dp.from[i] != SQ_NONE)
-        removed.push_back(make_index(perspective, dp.from[i], dp.piece[i], ksq));
+        removed.push_back(make_index<Perspective>(dp.from[i], dp.piece[i], ksq));
       if (dp.to[i] != SQ_NONE)
-        added.push_back(make_index(perspective, dp.to[i], dp.piece[i], ksq));
+        added.push_back(make_index<Perspective>(dp.to[i], dp.piece[i], ksq));
     }
   }
 
+  // Explicit template instantiations
+  template void HalfKAv2_hm::append_changed_indices<WHITE>(Square ksq, const DirtyPiece& dp, IndexList& removed, IndexList& added);
+  template void HalfKAv2_hm::append_changed_indices<BLACK>(Square ksq, const DirtyPiece& dp, IndexList& removed, IndexList& added);
+
   int HalfKAv2_hm::update_cost(const StateInfo* st) {
     return st->dirtyPiece.dirty_num;
   }
index 1e6da0bfe2b83c27d176a3518d1ac6ec58e98e17..a95d4328bb4f55f25e618a740abfd6a9a72a7c11 100644 (file)
@@ -49,8 +49,8 @@ namespace Stockfish::Eval::NNUE::Features {
       PS_B_ROOK   =  7 * SQUARE_NB,
       PS_W_QUEEN  =  8 * SQUARE_NB,
       PS_B_QUEEN  =  9 * SQUARE_NB,
-      PS_KING     =  10 * SQUARE_NB,
-      PS_NB       =  11 * SQUARE_NB
+      PS_KING     = 10 * SQUARE_NB,
+      PS_NB       = 11 * SQUARE_NB
     };
 
     static constexpr IndexType PieceSquareIndex[COLOR_NB][PIECE_NB] = {
@@ -62,11 +62,9 @@ namespace Stockfish::Eval::NNUE::Features {
         PS_NONE, PS_W_PAWN, PS_W_KNIGHT, PS_W_BISHOP, PS_W_ROOK, PS_W_QUEEN, PS_KING, PS_NONE }
     };
 
-    // Orient a square according to perspective (rotates by 180 for black)
-    static Square orient(Color perspective, Square s, Square ksq);
-
     // Index of a feature for a given king position and another piece on some square
-    static IndexType make_index(Color perspective, Square s, Piece pc, Square ksq);
+    template<Color Perspective>
+    static IndexType make_index(Square s, Piece pc, Square ksq);
 
    public:
     // Feature name
@@ -79,15 +77,45 @@ namespace Stockfish::Eval::NNUE::Features {
     static constexpr IndexType Dimensions =
         static_cast<IndexType>(SQUARE_NB) * static_cast<IndexType>(PS_NB) / 2;
 
-    static constexpr int KingBuckets[64] = {
-      -1, -1, -1, -1, 31, 30, 29, 28,
-      -1, -1, -1, -1, 27, 26, 25, 24,
-      -1, -1, -1, -1, 23, 22, 21, 20,
-      -1, -1, -1, -1, 19, 18, 17, 16,
-      -1, -1, -1, -1, 15, 14, 13, 12,
-      -1, -1, -1, -1, 11, 10,  9,  8,
-      -1, -1, -1, -1,  7,  6,  5,  4,
-      -1, -1, -1, -1,  3,  2,  1,  0
+#define B(v) (v * PS_NB)
+    static constexpr int KingBuckets[COLOR_NB][SQUARE_NB] = {
+      { B(28), B(29), B(30), B(31), B(31), B(30), B(29), B(28),
+        B(24), B(25), B(26), B(27), B(27), B(26), B(25), B(24),
+        B(20), B(21), B(22), B(23), B(23), B(22), B(21), B(20),
+        B(16), B(17), B(18), B(19), B(19), B(18), B(17), B(16),
+        B(12), B(13), B(14), B(15), B(15), B(14), B(13), B(12),
+        B( 8), B( 9), B(10), B(11), B(11), B(10), B( 9), B( 8),
+        B( 4), B( 5), B( 6), B( 7), B( 7), B( 6), B( 5), B( 4),
+        B( 0), B( 1), B( 2), B( 3), B( 3), B( 2), B( 1), B( 0) },
+      { B( 0), B( 1), B( 2), B( 3), B( 3), B( 2), B( 1), B( 0),
+        B( 4), B( 5), B( 6), B( 7), B( 7), B( 6), B( 5), B( 4),
+        B( 8), B( 9), B(10), B(11), B(11), B(10), B( 9), B( 8),
+        B(12), B(13), B(14), B(15), B(15), B(14), B(13), B(12),
+        B(16), B(17), B(18), B(19), B(19), B(18), B(17), B(16),
+        B(20), B(21), B(22), B(23), B(23), B(22), B(21), B(20),
+        B(24), B(25), B(26), B(27), B(27), B(26), B(25), B(24),
+        B(28), B(29), B(30), B(31), B(31), B(30), B(29), B(28) }
+    };
+#undef B
+
+    // Orient a square according to perspective (rotates by 180 for black)
+    static constexpr int OrientTBL[COLOR_NB][SQUARE_NB] = {
+      { SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1,
+        SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1,
+        SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1,
+        SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1,
+        SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1,
+        SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1,
+        SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1,
+        SQ_H1, SQ_H1, SQ_H1, SQ_H1, SQ_A1, SQ_A1, SQ_A1, SQ_A1 },
+      { SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8,
+        SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8,
+        SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8,
+        SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8,
+        SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8,
+        SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8,
+        SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8,
+        SQ_H8, SQ_H8, SQ_H8, SQ_H8, SQ_A8, SQ_A8, SQ_A8, SQ_A8 }
     };
 
     // Maximum number of simultaneously active features.
@@ -95,16 +123,16 @@ namespace Stockfish::Eval::NNUE::Features {
     using IndexList = ValueList<IndexType, MaxActiveDimensions>;
 
     // Get a list of indices for active features
+    template<Color Perspective>
     static void append_active_indices(
       const Position& pos,
-      Color perspective,
       IndexList& active);
 
     // Get a list of indices for recently changed features
+    template<Color Perspective>
     static void append_changed_indices(
       Square ksq,
       const DirtyPiece& dp,
-      Color perspective,
       IndexList& removed,
       IndexList& added
     );
index 34d7292c0065eb0b392d3062bfe3118bbc441fca..b6dd54d3378909ea44c8a1934f3037df2ff97043 100644 (file)
@@ -271,8 +271,8 @@ namespace Stockfish::Eval::NNUE {
 
     // Convert input features
     std::int32_t transform(const Position& pos, OutputType* output, int bucket) const {
-      update_accumulator(pos, WHITE);
-      update_accumulator(pos, BLACK);
+      update_accumulator<WHITE>(pos);
+      update_accumulator<BLACK>(pos);
 
       const Color perspectives[2] = {pos.side_to_move(), ~pos.side_to_move()};
       const auto& accumulation = pos.state()->accumulator.accumulation;
@@ -338,7 +338,8 @@ namespace Stockfish::Eval::NNUE {
 
 
    private:
-    void update_accumulator(const Position& pos, const Color perspective) const {
+    template<Color Perspective>
+    void update_accumulator(const Position& pos) const {
 
       // The size must be enough to contain the largest possible update.
       // That might depend on the feature set and generally relies on the
@@ -356,18 +357,18 @@ namespace Stockfish::Eval::NNUE {
       // of the estimated gain in terms of features to be added/subtracted.
       StateInfo *st = pos.state(), *next = nullptr;
       int gain = FeatureSet::refresh_cost(pos);
-      while (st->previous && !st->accumulator.computed[perspective])
+      while (st->previous && !st->accumulator.computed[Perspective])
       {
         // This governs when a full feature refresh is needed and how many
         // updates are better than just one full refresh.
-        if (   FeatureSet::requires_refresh(st, perspective)
+        if (   FeatureSet::requires_refresh(st, Perspective)
             || (gain -= FeatureSet::update_cost(st) + 1) < 0)
           break;
         next = st;
         st = st->previous;
       }
 
-      if (st->accumulator.computed[perspective])
+      if (st->accumulator.computed[Perspective])
       {
         if (next == nullptr)
           return;
@@ -376,17 +377,17 @@ namespace Stockfish::Eval::NNUE {
         // accumulator. Then, we update the current accumulator (pos.state()).
 
         // Gather all features to be updated.
-        const Square ksq = pos.square<KING>(perspective);
+        const Square ksq = pos.square<KING>(Perspective);
         FeatureSet::IndexList removed[2], added[2];
-        FeatureSet::append_changed_indices(
-          ksq, next->dirtyPiece, perspective, removed[0], added[0]);
+        FeatureSet::append_changed_indices<Perspective>(
+          ksq, next->dirtyPiece, removed[0], added[0]);
         for (StateInfo *st2 = pos.state(); st2 != next; st2 = st2->previous)
-          FeatureSet::append_changed_indices(
-            ksq, st2->dirtyPiece, perspective, removed[1], added[1]);
+          FeatureSet::append_changed_indices<Perspective>(
+            ksq, st2->dirtyPiece, removed[1], added[1]);
 
         // Mark the accumulators as computed.
-        next->accumulator.computed[perspective] = true;
-        pos.state()->accumulator.computed[perspective] = true;
+        next->accumulator.computed[Perspective] = true;
+        pos.state()->accumulator.computed[Perspective] = true;
 
         // Now update the accumulators listed in states_to_update[], where the last element is a sentinel.
         StateInfo *states_to_update[3] =
@@ -396,7 +397,7 @@ namespace Stockfish::Eval::NNUE {
         {
           // Load accumulator
           auto accTile = reinterpret_cast<vec_t*>(
-            &st->accumulator.accumulation[perspective][j * TileHeight]);
+            &st->accumulator.accumulation[Perspective][j * TileHeight]);
           for (IndexType k = 0; k < NumRegs; ++k)
             acc[k] = vec_load(&accTile[k]);
 
@@ -422,7 +423,7 @@ namespace Stockfish::Eval::NNUE {
 
             // Store accumulator
             accTile = reinterpret_cast<vec_t*>(
-              &states_to_update[i]->accumulator.accumulation[perspective][j * TileHeight]);
+              &states_to_update[i]->accumulator.accumulation[Perspective][j * TileHeight]);
             for (IndexType k = 0; k < NumRegs; ++k)
               vec_store(&accTile[k], acc[k]);
           }
@@ -432,7 +433,7 @@ namespace Stockfish::Eval::NNUE {
         {
           // Load accumulator
           auto accTilePsqt = reinterpret_cast<psqt_vec_t*>(
-            &st->accumulator.psqtAccumulation[perspective][j * PsqtTileHeight]);
+            &st->accumulator.psqtAccumulation[Perspective][j * PsqtTileHeight]);
           for (std::size_t k = 0; k < NumPsqtRegs; ++k)
             psqt[k] = vec_load_psqt(&accTilePsqt[k]);
 
@@ -458,7 +459,7 @@ namespace Stockfish::Eval::NNUE {
 
             // Store accumulator
             accTilePsqt = reinterpret_cast<psqt_vec_t*>(
-              &states_to_update[i]->accumulator.psqtAccumulation[perspective][j * PsqtTileHeight]);
+              &states_to_update[i]->accumulator.psqtAccumulation[Perspective][j * PsqtTileHeight]);
             for (std::size_t k = 0; k < NumPsqtRegs; ++k)
               vec_store_psqt(&accTilePsqt[k], psqt[k]);
           }
@@ -467,12 +468,12 @@ namespace Stockfish::Eval::NNUE {
   #else
         for (IndexType i = 0; states_to_update[i]; ++i)
         {
-          std::memcpy(states_to_update[i]->accumulator.accumulation[perspective],
-              st->accumulator.accumulation[perspective],
+          std::memcpy(states_to_update[i]->accumulator.accumulation[Perspective],
+              st->accumulator.accumulation[Perspective],
               HalfDimensions * sizeof(BiasType));
 
           for (std::size_t k = 0; k < PSQTBuckets; ++k)
-            states_to_update[i]->accumulator.psqtAccumulation[perspective][k] = st->accumulator.psqtAccumulation[perspective][k];
+            states_to_update[i]->accumulator.psqtAccumulation[Perspective][k] = st->accumulator.psqtAccumulation[Perspective][k];
 
           st = states_to_update[i];
 
@@ -482,10 +483,10 @@ namespace Stockfish::Eval::NNUE {
             const IndexType offset = HalfDimensions * index;
 
             for (IndexType j = 0; j < HalfDimensions; ++j)
-              st->accumulator.accumulation[perspective][j] -= weights[offset + j];
+              st->accumulator.accumulation[Perspective][j] -= weights[offset + j];
 
             for (std::size_t k = 0; k < PSQTBuckets; ++k)
-              st->accumulator.psqtAccumulation[perspective][k] -= psqtWeights[index * PSQTBuckets + k];
+              st->accumulator.psqtAccumulation[Perspective][k] -= psqtWeights[index * PSQTBuckets + k];
           }
 
           // Difference calculation for the activated features
@@ -494,10 +495,10 @@ namespace Stockfish::Eval::NNUE {
             const IndexType offset = HalfDimensions * index;
 
             for (IndexType j = 0; j < HalfDimensions; ++j)
-              st->accumulator.accumulation[perspective][j] += weights[offset + j];
+              st->accumulator.accumulation[Perspective][j] += weights[offset + j];
 
             for (std::size_t k = 0; k < PSQTBuckets; ++k)
-              st->accumulator.psqtAccumulation[perspective][k] += psqtWeights[index * PSQTBuckets + k];
+              st->accumulator.psqtAccumulation[Perspective][k] += psqtWeights[index * PSQTBuckets + k];
           }
         }
   #endif
@@ -506,9 +507,9 @@ namespace Stockfish::Eval::NNUE {
       {
         // Refresh the accumulator
         auto& accumulator = pos.state()->accumulator;
-        accumulator.computed[perspective] = true;
+        accumulator.computed[Perspective] = true;
         FeatureSet::IndexList active;
-        FeatureSet::append_active_indices(pos, perspective, active);
+        FeatureSet::append_active_indices<Perspective>(pos, active);
 
   #ifdef VECTOR
         for (IndexType j = 0; j < HalfDimensions / TileHeight; ++j)
@@ -528,7 +529,7 @@ namespace Stockfish::Eval::NNUE {
           }
 
           auto accTile = reinterpret_cast<vec_t*>(
-              &accumulator.accumulation[perspective][j * TileHeight]);
+              &accumulator.accumulation[Perspective][j * TileHeight]);
           for (unsigned k = 0; k < NumRegs; k++)
             vec_store(&accTile[k], acc[k]);
         }
@@ -548,27 +549,27 @@ namespace Stockfish::Eval::NNUE {
           }
 
           auto accTilePsqt = reinterpret_cast<psqt_vec_t*>(
-            &accumulator.psqtAccumulation[perspective][j * PsqtTileHeight]);
+            &accumulator.psqtAccumulation[Perspective][j * PsqtTileHeight]);
           for (std::size_t k = 0; k < NumPsqtRegs; ++k)
             vec_store_psqt(&accTilePsqt[k], psqt[k]);
         }
 
   #else
-        std::memcpy(accumulator.accumulation[perspective], biases,
+        std::memcpy(accumulator.accumulation[Perspective], biases,
             HalfDimensions * sizeof(BiasType));
 
         for (std::size_t k = 0; k < PSQTBuckets; ++k)
-          accumulator.psqtAccumulation[perspective][k] = 0;
+          accumulator.psqtAccumulation[Perspective][k] = 0;
 
         for (const auto index : active)
         {
           const IndexType offset = HalfDimensions * index;
 
           for (IndexType j = 0; j < HalfDimensions; ++j)
-            accumulator.accumulation[perspective][j] += weights[offset + j];
+            accumulator.accumulation[Perspective][j] += weights[offset + j];
 
           for (std::size_t k = 0; k < PSQTBuckets; ++k)
-            accumulator.psqtAccumulation[perspective][k] += psqtWeights[index * PSQTBuckets + k];
+            accumulator.psqtAccumulation[Perspective][k] += psqtWeights[index * PSQTBuckets + k];
         }
   #endif
       }
index 5dc6050f081fbfc412111dc1334df1bf259cfeb3..e0d432e8a7fe5d8aa2b484258c67eceb341c6214 100644 (file)
@@ -129,7 +129,7 @@ void Position::init() {
   // Prepare the cuckoo tables
   std::memset(cuckoo, 0, sizeof(cuckoo));
   std::memset(cuckooMove, 0, sizeof(cuckooMove));
-  int count = 0;
+  [[maybe_unused]] int count = 0;
   for (Piece pc : Pieces)
       for (Square s1 = SQ_A1; s1 <= SQ_H8; ++s1)
           for (Square s2 = Square(s1 + 1); s2 <= SQ_H8; ++s2)
index 3c2ae3e52df8b0c43f8cc05a132c2adb801bef81..0c8377d01ed6712630efaa665adf4aeb645906c4 100644 (file)
@@ -81,7 +81,7 @@ namespace {
 
   // History and stats update bonus, based on depth
   int stat_bonus(Depth d) {
-    return std::min((12 * d + 282) * d - 349 , 1594);
+    return std::min((12 * d + 282) * d - 349 , 1480);
   }
 
   // Add a small random component to draw evaluations to avoid 3-fold blindness
@@ -244,7 +244,7 @@ void MainThread::search() {
 
   // Send again PV info if we have a new best thread
   if (bestThread != this)
-      sync_cout << UCI::pv(bestThread->rootPos, bestThread->completedDepth, -VALUE_INFINITE, VALUE_INFINITE) << sync_endl;
+      sync_cout << UCI::pv(bestThread->rootPos, bestThread->completedDepth) << sync_endl;
 
   sync_cout << "bestmove " << UCI::move(bestThread->rootMoves[0].pv[0], rootPos.is_chess960());
 
@@ -309,7 +309,6 @@ void Thread::search() {
 
   complexityAverage.set(155, 1);
 
-  trend = SCORE_ZERO;
   optimism[us] = optimism[~us] = VALUE_ZERO;
 
   int searchAgainCounter = 0;
@@ -356,11 +355,7 @@ void Thread::search() {
               alpha = std::max(prev - delta,-VALUE_INFINITE);
               beta  = std::min(prev + delta, VALUE_INFINITE);
 
-              // Adjust trend and optimism based on root move's previousScore
-              int tr = 116 * prev / (std::abs(prev) + 89);
-              trend = (us == WHITE ?  make_score(tr, tr / 2)
-                                   : -make_score(tr, tr / 2));
-
+              // Adjust optimism based on root move's previousScore
               int opt = 118 * prev / (std::abs(prev) + 169);
               optimism[ us] = Value(opt);
               optimism[~us] = -optimism[us];
@@ -397,7 +392,7 @@ void Thread::search() {
                   && multiPV == 1
                   && (bestValue <= alpha || bestValue >= beta)
                   && Time.elapsed() > 3000)
-                  sync_cout << UCI::pv(rootPos, rootDepth, alpha, beta) << sync_endl;
+                  sync_cout << UCI::pv(rootPos, rootDepth) << sync_endl;
 
               // In case of failing low/high increase aspiration window and
               // re-search, otherwise exit the loop.
@@ -428,7 +423,7 @@ void Thread::search() {
 
           if (    mainThread
               && (Threads.stop || pvIdx + 1 == multiPV || Time.elapsed() > 3000))
-              sync_cout << UCI::pv(rootPos, rootDepth, alpha, beta) << sync_endl;
+              sync_cout << UCI::pv(rootPos, rootDepth) << sync_endl;
       }
 
       if (!Threads.stop)
@@ -492,12 +487,11 @@ void Thread::search() {
               else
                   Threads.stop = true;
           }
-          else if (   Threads.increaseDepth
-                   && !mainThread->ponder
+          else if (   !mainThread->ponder
                    && Time.elapsed() > totalTime * 0.53)
-                   Threads.increaseDepth = false;
+              Threads.increaseDepth = false;
           else
-                   Threads.increaseDepth = true;
+              Threads.increaseDepth = true;
       }
 
       mainThread->iterValue[iterIdx] = bestValue;
@@ -639,16 +633,16 @@ namespace {
         && ttValue != VALUE_NONE // Possible in case of TT access race
         && (tte->bound() & (ttValue >= beta ? BOUND_LOWER : BOUND_UPPER)))
     {
-        // If ttMove is quiet, update move sorting heuristics on TT hit (~1 Elo)
+        // If ttMove is quiet, update move sorting heuristics on TT hit (~2 Elo)
         if (ttMove)
         {
             if (ttValue >= beta)
             {
-                // Bonus for a quiet ttMove that fails high (~3 Elo)
+                // Bonus for a quiet ttMove that fails high (~2 Elo)
                 if (!ttCapture)
                     update_quiet_stats(pos, ss, ttMove, stat_bonus(depth));
 
-                // Extra penalty for early quiet moves of the previous ply (~0 Elo)
+                // Extra penalty for early quiet moves of the previous ply (~0 Elo on STC, ~2 Elo on LTC)
                 if ((ss-1)->moveCount <= 2 && !priorCapture)
                     update_continuation_histories(ss-1, pos.piece_on(prevSq), prevSq, -stat_bonus(depth + 1));
             }
@@ -740,7 +734,7 @@ namespace {
         else // Fall back to (semi)classical complexity for TT hits, the NNUE complexity is lost
             complexity = abs(ss->staticEval - pos.psq_eg_stm());
 
-        // ttValue can be used as a better position evaluation (~4 Elo)
+        // ttValue can be used as a better position evaluation (~7 Elo)
         if (    ttValue != VALUE_NONE
             && (tte->bound() & (ttValue > eval ? BOUND_LOWER : BOUND_UPPER)))
             eval = ttValue;
@@ -756,7 +750,7 @@ namespace {
 
     thisThread->complexityAverage.update(complexity);
 
-    // Use static evaluation difference to improve quiet move ordering (~3 Elo)
+    // Use static evaluation difference to improve quiet move ordering (~4 Elo)
     if (is_ok((ss-1)->currentMove) && !(ss-1)->inCheck && !priorCapture)
     {
         int bonus = std::clamp(-19 * int((ss-1)->staticEval + ss->staticEval), -1914, 1914);
@@ -772,18 +766,17 @@ namespace {
                   :                                    168;
     improving = improvement > 0;
 
-    // Step 7. Razoring.
+    // Step 7. Razoring (~1 Elo).
     // If eval is really low check with qsearch if it can exceed alpha, if it can't,
     // return a fail low.
-    if (   depth <= 7
-        && eval < alpha - 369 - 254 * depth * depth)
+    if (eval < alpha - 369 - 254 * depth * depth)
     {
         value = qsearch<NonPV>(pos, ss, alpha - 1, alpha);
         if (value < alpha)
             return value;
     }
 
-    // Step 8. Futility pruning: child node (~25 Elo).
+    // Step 8. Futility pruning: child node (~40 Elo).
     // The depth condition is important for mate finding.
     if (   !ss->ttPv
         &&  depth < 8
@@ -792,7 +785,7 @@ namespace {
         &&  eval < 28031) // larger than VALUE_KNOWN_WIN, but smaller than TB wins
         return eval;
 
-    // Step 9. Null move search with verification search (~22 Elo)
+    // Step 9. Null move search with verification search (~35 Elo)
     if (   !PvNode
         && (ss-1)->currentMove != MOVE_NULL
         && (ss-1)->statScore < 17139
@@ -844,7 +837,7 @@ namespace {
 
     probCutBeta = beta + 191 - 54 * improving;
 
-    // Step 10. ProbCut (~4 Elo)
+    // Step 10. ProbCut (~10 Elo)
     // If we have a good enough capture and a reduced search returns a value
     // much above beta, we can (almost) safely prune the previous move.
     if (   !PvNode
@@ -861,7 +854,7 @@ namespace {
     {
         assert(probCutBeta < VALUE_INFINITE);
 
-        MovePicker mp(pos, ttMove, probCutBeta - ss->staticEval, depth - 3, &captureHistory);
+        MovePicker mp(pos, ttMove, probCutBeta - ss->staticEval, &captureHistory);
 
         while ((move = mp.next_move()) != MOVE_NONE)
             if (move != excludedMove && pos.legal(move))
@@ -895,7 +888,7 @@ namespace {
     }
 
     // Step 11. If the position is not in TT, decrease depth by 3.
-    // Use qsearch if depth is equal or below zero (~4 Elo)
+    // Use qsearch if depth is equal or below zero (~9 Elo)
     if (    PvNode
         && !ttMove)
         depth -= 3;
@@ -910,7 +903,7 @@ namespace {
 
 moves_loop: // When in check, search starts here
 
-    // Step 12. A small Probcut idea, when we are in check (~0 Elo)
+    // Step 12. A small Probcut idea, when we are in check (~4 Elo)
     probCutBeta = beta + 417;
     if (   ss->inCheck
         && !PvNode
@@ -987,12 +980,12 @@ moves_loop: // When in check, search starts here
 
       Value delta = beta - alpha;
 
-      // Step 14. Pruning at shallow depth (~98 Elo). Depth conditions are important for mate finding.
+      // Step 14. Pruning at shallow depth (~120 Elo). Depth conditions are important for mate finding.
       if (  !rootNode
           && pos.non_pawn_material(us)
           && bestValue > VALUE_TB_LOSS_IN_MAX_PLY)
       {
-          // Skip quiet moves if movecount exceeds our FutilityMoveCount threshold (~7 Elo)
+          // Skip quiet moves if movecount exceeds our FutilityMoveCount threshold (~8 Elo)
           moveCountPruning = moveCount >= futility_move_count(improving, depth);
 
           // Reduced depth of the next LMR search
@@ -1001,7 +994,7 @@ moves_loop: // When in check, search starts here
           if (   capture
               || givesCheck)
           {
-              // Futility pruning for captures (~0 Elo)
+              // Futility pruning for captures (~2 Elo)
               if (   !givesCheck
                   && !PvNode
                   && lmrDepth < 7
@@ -1010,7 +1003,7 @@ moves_loop: // When in check, search starts here
                    + captureHistory[movedPiece][to_sq(move)][type_of(pos.piece_on(to_sq(move)))] / 6 < alpha)
                   continue;
 
-              // SEE based pruning (~9 Elo)
+              // SEE based pruning (~11 Elo)
               if (!pos.see_ge(move, Value(-222) * depth))
                   continue;
           }
@@ -1027,23 +1020,23 @@ moves_loop: // When in check, search starts here
 
               history += 2 * thisThread->mainHistory[us][from_to(move)];
 
-              // Futility pruning: parent node (~9 Elo)
+              // Futility pruning: parent node (~13 Elo)
               if (   !ss->inCheck
                   && lmrDepth < 13
                   && ss->staticEval + 106 + 145 * lmrDepth + history / 52 <= alpha)
                   continue;
 
-              // Prune moves with negative SEE (~3 Elo)
+              // Prune moves with negative SEE (~4 Elo)
               if (!pos.see_ge(move, Value(-24 * lmrDepth * lmrDepth - 15 * lmrDepth)))
                   continue;
           }
       }
 
-      // Step 15. Extensions (~66 Elo)
+      // Step 15. Extensions (~100 Elo)
       // We take care to not overdo to avoid search getting stuck.
       if (ss->ply < thisThread->rootDepth * 2)
       {
-          // Singular extension search (~58 Elo). If all moves but one fail low on a
+          // Singular extension search (~94 Elo). If all moves but one fail low on a
           // search of (alpha-s, beta-s), and just one fails high on (alpha, beta),
           // then that move is singular and should be extended. To verify this we do
           // a reduced search on all the other moves but the ttMove and if the
@@ -1072,8 +1065,11 @@ moves_loop: // When in check, search starts here
                   // Avoid search explosion by limiting the number of double extensions
                   if (  !PvNode
                       && value < singularBeta - 25
-                      && ss->doubleExtensions <= 9)
+                      && ss->doubleExtensions <= 10)
+                  {
                       extension = 2;
+                      depth += depth < 12;
+                  }
               }
 
               // Multi-cut pruning
@@ -1099,7 +1095,7 @@ moves_loop: // When in check, search starts here
                    && abs(ss->staticEval) > 82)
               extension = 1;
 
-          // Quiet ttMove extensions (~0 Elo)
+          // Quiet ttMove extensions (~1 Elo)
           else if (   PvNode
                    && move == ttMove
                    && move == ss->killers[0]
@@ -1124,62 +1120,62 @@ moves_loop: // When in check, search starts here
       // Step 16. Make the move
       pos.do_move(move, st, givesCheck);
 
-      // Step 17. Late moves reduction / extension (LMR, ~98 Elo)
-      // We use various heuristics for the sons of a node after the first son has
-      // been searched. In general we would like to reduce them, but there are many
-      // cases where we extend a son if it has good chances to be "interesting".
-      if (    depth >= 2
-          &&  moveCount > 1 + (PvNode && ss->ply <= 1)
-          && (   !ss->ttPv
-              || !capture
-              || (cutNode && (ss-1)->moveCount > 1)))
-      {
-          Depth r = reduction(improving, depth, moveCount, delta, thisThread->rootDelta);
+      Depth r = reduction(improving, depth, moveCount, delta, thisThread->rootDelta);
 
-          // Decrease reduction if position is or has been on the PV
-          // and node is not likely to fail low. (~3 Elo)
-          if (   ss->ttPv
-              && !likelyFailLow)
-              r -= 2;
+      // Decrease reduction if position is or has been on the PV
+      // and node is not likely to fail low. (~3 Elo)
+      if (   ss->ttPv
+          && !likelyFailLow)
+          r -= 2;
 
-          // Decrease reduction if opponent's move count is high (~1 Elo)
-          if ((ss-1)->moveCount > 7)
-              r--;
+      // Decrease reduction if opponent's move count is high (~1 Elo)
+      if ((ss-1)->moveCount > 7)
+          r--;
 
-          // Increase reduction for cut nodes (~3 Elo)
-          if (cutNode)
-              r += 2;
+      // Increase reduction for cut nodes (~3 Elo)
+      if (cutNode)
+          r += 2;
 
-          // Increase reduction if ttMove is a capture (~3 Elo)
-          if (ttCapture)
-              r++;
+      // Increase reduction if ttMove is a capture (~3 Elo)
+      if (ttCapture)
+          r++;
 
-          // Decrease reduction for PvNodes based on depth
-          if (PvNode)
-              r -= 1 + 11 / (3 + depth);
+      // Decrease reduction for PvNodes based on depth
+      if (PvNode)
+          r -= 1 + 11 / (3 + depth);
 
-          // Decrease reduction if ttMove has been singularly extended (~1 Elo)
-          if (singularQuietLMR)
-              r--;
+      // Decrease reduction if ttMove has been singularly extended (~1 Elo)
+      if (singularQuietLMR)
+          r--;
 
-          // Dicrease reduction if we move a threatened piece (~1 Elo)
-          if (   depth > 9
-              && (mp.threatenedPieces & from_sq(move)))
-              r--;
+      // Decrease reduction if we move a threatened piece (~1 Elo)
+      if (   depth > 9
+          && (mp.threatenedPieces & from_sq(move)))
+          r--;
 
-          // Increase reduction if next ply has a lot of fail high
-          if ((ss+1)->cutoffCnt > 3 && !PvNode)
-              r++;
+      // Increase reduction if next ply has a lot of fail high
+      if ((ss+1)->cutoffCnt > 3)
+          r++;
 
-          ss->statScore =  2 * thisThread->mainHistory[us][from_to(move)]
-                         + (*contHist[0])[movedPiece][to_sq(move)]
-                         + (*contHist[1])[movedPiece][to_sq(move)]
-                         + (*contHist[3])[movedPiece][to_sq(move)]
-                         - 4433;
+      ss->statScore =  2 * thisThread->mainHistory[us][from_to(move)]
+                     + (*contHist[0])[movedPiece][to_sq(move)]
+                     + (*contHist[1])[movedPiece][to_sq(move)]
+                     + (*contHist[3])[movedPiece][to_sq(move)]
+                     - 4433;
 
-          // Decrease/increase reduction for moves with a good/bad history (~30 Elo)
-          r -= ss->statScore / 13628;
+      // Decrease/increase reduction for moves with a good/bad history (~30 Elo)
+      r -= ss->statScore / (13000 + 4152 * (depth > 7 && depth < 19));
 
+      // Step 17. Late moves reduction / extension (LMR, ~117 Elo)
+      // We use various heuristics for the sons of a node after the first son has
+      // been searched. In general we would like to reduce them, but there are many
+      // cases where we extend a son if it has good chances to be "interesting".
+      if (    depth >= 2
+          &&  moveCount > 1 + (PvNode && ss->ply <= 1)
+          && (   !ss->ttPv
+              || !capture
+              || (cutNode && (ss-1)->moveCount > 1)))
+      {
           // In general we want to cap the LMR depth search at newDepth, but when
           // reduction is negative, we allow this move a limited search extension
           // beyond the first move depth. This may lead to hidden double extensions.
@@ -1190,8 +1186,18 @@ moves_loop: // When in check, search starts here
           // Do full depth search when reduced LMR search fails high
           if (value > alpha && d < newDepth)
           {
+              // Adjust full depth search based on LMR results - if result
+              // was good enough search deeper, if it was bad enough search shallower
               const bool doDeeperSearch = value > (alpha + 64 + 11 * (newDepth - d));
-              value = -search<NonPV>(pos, ss+1, -(alpha+1), -alpha, newDepth + doDeeperSearch, !cutNode);
+              const bool doEvenDeeperSearch = value > alpha + 582 && ss->doubleExtensions <= 5;
+              const bool doShallowerSearch = value < bestValue + newDepth;
+
+              ss->doubleExtensions = ss->doubleExtensions + doEvenDeeperSearch;
+
+              newDepth += doDeeperSearch - doShallowerSearch + doEvenDeeperSearch;
+
+              if (newDepth > d)
+                  value = -search<NonPV>(pos, ss+1, -(alpha+1), -alpha, newDepth, !cutNode);
 
               int bonus = value > alpha ?  stat_bonus(newDepth)
                                         : -stat_bonus(newDepth);
@@ -1203,10 +1209,10 @@ moves_loop: // When in check, search starts here
           }
       }
 
-      // Step 18. Full depth search when LMR is skipped
+      // Step 18. Full depth search when LMR is skipped. If expected reduction is high, reduce its depth by 1.
       else if (!PvNode || moveCount > 1)
       {
-              value = -search<NonPV>(pos, ss+1, -(alpha+1), -alpha, newDepth, !cutNode);
+               value = -search<NonPV>(pos, ss+1, -(alpha+1), -alpha, newDepth - (r > 4), !cutNode);
       }
 
       // For PV nodes only, do a full PV search on the first move or after a fail
@@ -1243,8 +1249,18 @@ moves_loop: // When in check, search starts here
           // PV move or new best move?
           if (moveCount == 1 || value > alpha)
           {
-              rm.score = value;
+              rm.score =  rm.uciScore = value;
               rm.selDepth = thisThread->selDepth;
+              rm.scoreLowerbound = rm.scoreUpperbound = false;
+
+              if (value >= beta) {
+                 rm.scoreLowerbound = true;
+                 rm.uciScore = beta;
+              }
+              else if (value <= alpha) {
+                 rm.scoreUpperbound = true;
+                 rm.uciScore = alpha;
+              }
               rm.pv.resize(1);
 
               assert((ss+1)->pv);
@@ -1286,7 +1302,7 @@ moves_loop: // When in check, search starts here
                       && depth < 6
                       && beta  <  VALUE_KNOWN_WIN
                       && alpha > -VALUE_KNOWN_WIN)
-                     depth -= 1;
+                      depth -= 1;
 
                   assert(depth > 0);
               }
@@ -1298,8 +1314,6 @@ moves_loop: // When in check, search starts here
               }
           }
       }
-      else
-         ss->cutoffCnt = 0;
 
 
       // If the move is worse than some previously searched move, remember it to update its stats later
@@ -1339,16 +1353,17 @@ moves_loop: // When in check, search starts here
                          quietsSearched, quietCount, capturesSearched, captureCount, depth);
 
     // Bonus for prior countermove that caused the fail low
-    else if (   (depth >= 5 || PvNode)
+    else if (   (depth >= 5 || PvNode || bestValue < alpha - 62 * depth)
              && !priorCapture)
     {
         //Assign extra bonus if current node is PvNode or cutNode
         //or fail low was really bad
         bool extraBonus =    PvNode
-                          || cutNode
-                          || bestValue < alpha - 62 * depth;
+                          || cutNode;
 
-        update_continuation_histories(ss-1, pos.piece_on(prevSq), prevSq, stat_bonus(depth) * (1 + extraBonus));
+        bool doubleExtraBonus = extraBonus && bestValue < alpha - 85 * depth;
+
+        update_continuation_histories(ss-1, pos.piece_on(prevSq), prevSq, stat_bonus(depth) * (1 + extraBonus + doubleExtraBonus));
     }
 
     if (PvNode)
@@ -1448,7 +1463,7 @@ moves_loop: // When in check, search starts here
             if ((ss->staticEval = bestValue = tte->eval()) == VALUE_NONE)
                 ss->staticEval = bestValue = evaluate(pos);
 
-            // ttValue can be used as a better position evaluation (~7 Elo)
+            // ttValue can be used as a better position evaluation (~13 Elo)
             if (    ttValue != VALUE_NONE
                 && (tte->bound() & (ttValue > bestValue ? BOUND_LOWER : BOUND_UPPER)))
                 bestValue = ttValue;
@@ -1506,14 +1521,13 @@ moves_loop: // When in check, search starts here
 
       moveCount++;
 
-      // Futility pruning and moveCount pruning (~5 Elo)
+      // Futility pruning and moveCount pruning (~10 Elo)
       if (    bestValue > VALUE_TB_LOSS_IN_MAX_PLY
           && !givesCheck
           &&  to_sq(move) != prevSq
           &&  futilityBase > -VALUE_KNOWN_WIN
           &&  type_of(move) != PROMOTION)
       {
-
           if (moveCount > 2)
               continue;
 
@@ -1546,19 +1560,18 @@ moves_loop: // When in check, search starts here
                                                                 [pos.moved_piece(move)]
                                                                 [to_sq(move)];
 
-      // Continuation history based pruning (~2 Elo)
+      // Continuation history based pruning (~3 Elo)
       if (   !capture
           && bestValue > VALUE_TB_LOSS_IN_MAX_PLY
           && (*contHist[0])[pos.moved_piece(move)][to_sq(move)] < 0
           && (*contHist[1])[pos.moved_piece(move)][to_sq(move)] < 0)
           continue;
 
-      // movecount pruning for quiet check evasions
+      // We prune after 2nd quiet check evasion where being 'in check' is implicitly checked through the counter
+      // and being a 'quiet' apart from being a tt move is assumed after an increment because captures are pushed ahead.
       if (   bestValue > VALUE_TB_LOSS_IN_MAX_PLY
-          && quietCheckEvasions > 1
-          && !capture
-          && ss->inCheck)
-          continue;
+          && quietCheckEvasions > 1)
+          break;
 
       quietCheckEvasions += !capture && ss->inCheck;
 
@@ -1822,7 +1835,7 @@ void MainThread::check_time() {
 /// UCI::pv() formats PV information according to the UCI protocol. UCI requires
 /// that all (if any) unsearched PV lines are sent using a previous search score.
 
-string UCI::pv(const Position& pos, Depth depth, Value alpha, Value beta) {
+string UCI::pv(const Position& pos, Depth depth) {
 
   std::stringstream ss;
   TimePoint elapsed = Time.elapsed() + 1;
@@ -1840,7 +1853,7 @@ string UCI::pv(const Position& pos, Depth depth, Value alpha, Value beta) {
           continue;
 
       Depth d = updated ? depth : std::max(1, depth - 1);
-      Value v = updated ? rootMoves[i].score : rootMoves[i].previousScore;
+      Value v = updated ? rootMoves[i].uciScore : rootMoves[i].previousScore;
 
       if (v == -VALUE_INFINITE)
           v = VALUE_ZERO;
@@ -1860,8 +1873,8 @@ string UCI::pv(const Position& pos, Depth depth, Value alpha, Value beta) {
       if (Options["UCI_ShowWDL"])
           ss << UCI::wdl(v, pos.game_ply());
 
-      if (!tb && i == pvIdx)
-          ss << (v >= beta ? " lowerbound" : v <= alpha ? " upperbound" : "");
+      if (i == pvIdx && !tb && updated) // tablebase- and previous-scores are exact
+         ss << (rootMoves[i].scoreLowerbound ? " lowerbound" : (rootMoves[i].scoreUpperbound ? " upperbound" : ""));
 
       ss << " nodes "    << nodesSearched
          << " nps "      << nodesSearched * 1000 / elapsed
index f264bcae84027972c52511f6e02fe5c67eb0c889..b620202d9178836f24619192409242b67166f564 100644 (file)
@@ -71,6 +71,9 @@ struct RootMove {
   Value score = -VALUE_INFINITE;
   Value previousScore = -VALUE_INFINITE;
   Value averageScore = -VALUE_INFINITE;
+  Value uciScore = -VALUE_INFINITE;
+  bool scoreLowerbound = false;
+  bool scoreUpperbound = false;
   int selDepth = 0;
   int tbRank = 0;
   Value tbScore;
index 43af89f0ec9f011b986d3b3f9d4bd7d68ab2edca..f2de036df4a540efe6921fce0941bfd75d7ef22c 100644 (file)
@@ -59,6 +59,7 @@ namespace Stockfish {
 namespace {
 
 constexpr int TBPIECES = 7; // Max number of supported pieces
+constexpr int MAX_DTZ = 1 << 18; // Max DTZ supported, large enough to deal with the syzygy TB limit.
 
 enum { BigEndian, LittleEndian };
 enum TBType { WDL, DTZ }; // Used as template parameter
@@ -1522,7 +1523,7 @@ bool Tablebases::root_probe(Position& pos, Search::RootMoves& rootMoves) {
     // Check whether a position was repeated since the last zeroing move.
     bool rep = pos.has_repeated();
 
-    int dtz, bound = Options["Syzygy50MoveRule"] ? 900 : 1;
+    int dtz, bound = Options["Syzygy50MoveRule"] ? (MAX_DTZ - 100) : 1;
 
     // Probe and rank each move
     for (auto& m : rootMoves)
@@ -1565,8 +1566,8 @@ bool Tablebases::root_probe(Position& pos, Search::RootMoves& rootMoves) {
 
         // Better moves are ranked higher. Certain wins are ranked equally.
         // Losing moves are ranked equally unless a 50-move draw is in sight.
-        int r =  dtz > 0 ? (dtz + cnt50 <= 99 && !rep ? 1000 : 1000 - (dtz + cnt50))
-               : dtz < 0 ? (-dtz * 2 + cnt50 < 100 ? -1000 : -1000 + (-dtz + cnt50))
+        int r =  dtz > 0 ? (dtz + cnt50 <= 99 && !rep ? MAX_DTZ : MAX_DTZ - (dtz + cnt50))
+               : dtz < 0 ? (-dtz * 2 + cnt50 < 100 ? -MAX_DTZ : -MAX_DTZ + (-dtz + cnt50))
                : 0;
         m.tbRank = r;
 
@@ -1574,9 +1575,9 @@ bool Tablebases::root_probe(Position& pos, Search::RootMoves& rootMoves) {
         // 1 cp to cursed wins and let it grow to 49 cp as the positions gets
         // closer to a real win.
         m.tbScore =  r >= bound ? VALUE_MATE - MAX_PLY - 1
-                   : r >  0     ? Value((std::max( 3, r - 800) * int(PawnValueEg)) / 200)
+                   : r >  0     ? Value((std::max( 3, r - (MAX_DTZ - 200)) * int(PawnValueEg)) / 200)
                    : r == 0     ? VALUE_DRAW
-                   : r > -bound ? Value((std::min(-3, r + 800) * int(PawnValueEg)) / 200)
+                   : r > -bound ? Value((std::min(-3, r + (MAX_DTZ - 200)) * int(PawnValueEg)) / 200)
                    :             -VALUE_MATE + MAX_PLY + 1;
     }
 
@@ -1590,7 +1591,7 @@ bool Tablebases::root_probe(Position& pos, Search::RootMoves& rootMoves) {
 // A return value false indicates that not all probes were successful.
 bool Tablebases::root_probe_wdl(Position& pos, Search::RootMoves& rootMoves) {
 
-    static const int WDL_to_rank[] = { -1000, -899, 0, 899, 1000 };
+    static const int WDL_to_rank[] = { -MAX_DTZ, -MAX_DTZ + 101, 0, MAX_DTZ - 101, MAX_DTZ };
 
     ProbeState result;
     StateInfo st;
index c2917fef636d53f0c8ed00e4ab709e5ddfe099de..179c75721c2335203bdbf4d914b20d885b0b5c07 100644 (file)
@@ -31,8 +31,6 @@ enum WDLScore {
     WDLDraw        =  0, // Draw
     WDLCursedWin   =  1, // Win, but draw under 50-move rule
     WDLWin         =  2, // Win
-
-    WDLScoreNone  = -1000
 };
 
 // Possible states after a probing operation
index 9ce408e059e02ac119d567a1eda7377f96110f7c..e8723eb7411bff10a386e837c832f4c31ea192cb 100644 (file)
@@ -221,11 +221,14 @@ Thread* ThreadPool::get_best_thread() const {
         minScore = std::min(minScore, th->rootMoves[0].score);
 
     // Vote according to score and depth, and select the best thread
+    auto thread_value = [minScore](Thread* th) {
+            return (th->rootMoves[0].score - minScore + 14) * int(th->completedDepth);
+        };
+
     for (Thread* th : *this)
-    {
-        votes[th->rootMoves[0].pv[0]] +=
-            (th->rootMoves[0].score - minScore + 14) * int(th->completedDepth);
+        votes[th->rootMoves[0].pv[0]] += thread_value(th);
 
+    for (Thread* th : *this)
         if (abs(bestThread->rootMoves[0].score) >= VALUE_TB_WIN_IN_MAX_PLY)
         {
             // Make sure we pick the shortest mate / TB conversion or stave off mate the longest
@@ -236,9 +239,9 @@ Thread* ThreadPool::get_best_thread() const {
                  || (   th->rootMoves[0].score > VALUE_TB_LOSS_IN_MAX_PLY
                      && (   votes[th->rootMoves[0].pv[0]] > votes[bestThread->rootMoves[0].pv[0]]
                          || (   votes[th->rootMoves[0].pv[0]] == votes[bestThread->rootMoves[0].pv[0]]
-                             && th->rootMoves[0].pv.size() > bestThread->rootMoves[0].pv.size()))))
+                             &&   thread_value(th) * int(th->rootMoves[0].pv.size() > 2)
+                                > thread_value(bestThread) * int(bestThread->rootMoves[0].pv.size() > 2)))))
             bestThread = th;
-    }
 
     return bestThread;
 }
index c430a8184e6da110a5addac0bbabd57acdcb3618..5f0b2c3ed9cb3d86397ec8c2de309cacc033bbf3 100644 (file)
@@ -75,7 +75,6 @@ public:
   ButterflyHistory mainHistory;
   CapturePieceToHistory captureHistory;
   ContinuationHistory continuationHistory[2][2];
-  Score trend;
 };
 
 
index 0400401e77950302e01fdb3778d0ee21cc8a6101..cab0d7671a2e7503c47b2d080a00db98838c5c22 100644 (file)
@@ -80,7 +80,7 @@ void TimeManagement::init(Search::LimitsType& limits, Color us, int ply) {
   // game time for the current move, so also cap to 20% of available game time.
   if (limits.movestogo == 0)
   {
-      optScale = std::min(0.0084 + std::pow(ply + 3.0, 0.5) * 0.0042,
+      optScale = std::min(0.0120 + std::pow(ply + 3.0, 0.45) * 0.0039,
                            0.2 * limits.time[us] / double(timeLeft))
                  * optExtra;
       maxScale = std::min(7.0, 4.0 + ply / 12.0);
index c2087c6c07b9e8fd84be7d3033c19da397f894b7..29c16ce7dbb8f877127f16e00cff5d618540fb56 100644 (file)
@@ -186,6 +186,9 @@ enum Value : int {
   VALUE_MATE_IN_MAX_PLY  =  VALUE_MATE - MAX_PLY,
   VALUE_MATED_IN_MAX_PLY = -VALUE_MATE_IN_MAX_PLY,
 
+  // In the code, we make the assumption that these values
+  // are such that non_pawn_material() can be used to uniquely
+  // identify the material on the board.
   PawnValueMg   = 126,   PawnValueEg   = 208,
   KnightValueMg = 781,   KnightValueEg = 854,
   BishopValueMg = 825,   BishopValueEg = 915,
index d5e2c2c358600d759c765b5a4467665505c9ec08..5d842d25e73b6635b1472d2fead5eb525f602336 100644 (file)
@@ -207,13 +207,17 @@ namespace {
      // The coefficients of a third-order polynomial fit is based on the fishtest data
      // for two parameters that need to transform eval to the argument of a logistic
      // function.
-     double as[] = { 0.50379905,  -4.12755858,  18.95487051, 152.00733652};
-     double bs[] = {-1.71790378,  10.71543602, -17.05515898,  41.15680404};
+     constexpr double as[] = {  -0.58270499,    2.68512549,   15.24638015,  344.49745382};
+     constexpr double bs[] = {  -2.65734562,   15.96509799,  -20.69040836,   73.61029937 };
+
+     // Enforce that NormalizeToPawnValue corresponds to a 50% win rate at ply 64
+     static_assert(UCI::NormalizeToPawnValue == int(as[0] + as[1] + as[2] + as[3]));
+
      double a = (((as[0] * m + as[1]) * m + as[2]) * m) + as[3];
      double b = (((bs[0] * m + bs[1]) * m + bs[2]) * m) + bs[3];
 
      // Transform the eval to centipawns with limited range
-     double x = std::clamp(double(100 * v) / PawnValueEg, -2000.0, 2000.0);
+     double x = std::clamp(double(v), -4000.0, 4000.0);
 
      // Return the win rate in per mille units rounded to the nearest value
      return int(0.5 + 1000 / (1 + std::exp((a - x) / b)));
@@ -312,7 +316,7 @@ string UCI::value(Value v) {
   stringstream ss;
 
   if (abs(v) < VALUE_MATE_IN_MAX_PLY)
-      ss << "cp " << v * 100 / PawnValueEg;
+      ss << "cp " << v * 100 / NormalizeToPawnValue;
   else
       ss << "mate " << (v > 0 ? VALUE_MATE - v + 1 : -VALUE_MATE - v) / 2;
 
index 76a893f90c4f0067b58cad0b7df91c7cdefd2806..3b5a6764b48c8897cf0392689dae131bc81dfa31 100644 (file)
--- a/src/uci.h
+++ b/src/uci.h
@@ -30,6 +30,13 @@ class Position;
 
 namespace UCI {
 
+// Normalizes the internal value as reported by evaluate or search
+// to the UCI centipawn result used in output. This value is derived from
+// the win_rate_model() such that Stockfish outputs an advantage of
+// "100 centipawns" for a position if the engine has a 50% probability to win
+// from this position in selfplay at fishtest LTC time control.
+const int NormalizeToPawnValue = 361;
+
 class Option;
 
 /// Define a custom comparator, because the UCI options should be case-insensitive
@@ -72,7 +79,7 @@ void loop(int argc, char* argv[]);
 std::string value(Value v);
 std::string square(Square s);
 std::string move(Move m, bool chess960);
-std::string pv(const Position& pos, Depth depth, Value alpha, Value beta);
+std::string pv(const Position& pos, Depth depth);
 std::string wdl(Value v, int ply);
 Move to_move(const Position& pos, std::string& str);