Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
41 commits
Select commit Hold shift + click to select a range
3b02225
cleanup comments
winapiadmin May 24, 2026
4dfc386
Reverted .github/workflows/test.yml
winapiadmin May 24, 2026
1981a08
Apply automatic changes
winapiadmin May 24, 2026
fbfc046
ah yeah fixed bugs and A FEATURE!
winapiadmin May 24, 2026
3b2384a
Merge branch 'tiny_cleanup' of https://github.com/winapiadmin/chessli…
winapiadmin May 24, 2026
4de483f
format code
winapiadmin May 24, 2026
2a9cc78
fixed issues, but note that we have to disable some exception tests
winapiadmin May 25, 2026
f7e19da
some fixes
winapiadmin May 25, 2026
84e1cd6
format
winapiadmin May 25, 2026
44b749c
Update moves_io.cpp
winapiadmin May 25, 2026
80e902f
Update moves_io.cpp
winapiadmin May 25, 2026
25504cf
makes tests debuggable
winapiadmin May 25, 2026
c3a9fa6
portable exceptions
winapiadmin May 25, 2026
106986b
Apply automatic changes
winapiadmin May 25, 2026
32099a5
the max legal moves is 271
winapiadmin May 27, 2026
5daca6e
strict FEN parsing
winapiadmin May 27, 2026
31227bc
deprecation
winapiadmin May 27, 2026
5585979
Apply automatic changes
winapiadmin May 27, 2026
437ed66
allow support for some kind of FENs that doesn't have kings
winapiadmin May 28, 2026
62c60b5
Merge branch 'tiny_cleanup' of https://github.com/winapiadmin/chessli…
winapiadmin May 28, 2026
87e0eb5
Apply automatic changes
winapiadmin May 28, 2026
e7da937
Update position.cpp
winapiadmin May 28, 2026
9447b7b
remove unnecessary params in is_insufficient_material
winapiadmin May 28, 2026
9df54e1
Merge branch 'tiny_cleanup' of https://github.com/winapiadmin/chessli…
winapiadmin May 28, 2026
8afd18b
bugs
winapiadmin May 28, 2026
e61b5ac
Apply automatic changes
winapiadmin May 28, 2026
39e69ee
KNvKN, KBvKN, KNNvK detection, remove test_compile.yml, ERROR_MODE te…
winapiadmin May 28, 2026
5ab7066
Merge branch 'tiny_cleanup' of https://github.com/winapiadmin/chessli…
winapiadmin May 28, 2026
d59b17f
fix workflow
winapiadmin May 28, 2026
8ff9ec1
Apply automatic changes
winapiadmin May 28, 2026
cefe38e
fix workflow
winapiadmin May 28, 2026
ae39d62
Merge branch 'tiny_cleanup' of https://github.com/winapiadmin/chessli…
winapiadmin May 28, 2026
2f7bb5b
optimizations
winapiadmin May 29, 2026
2d08c85
Apply automatic changes
winapiadmin May 29, 2026
ffd8eaf
fix asserts
winapiadmin May 29, 2026
21755fb
Merge branch 'tiny_cleanup' of https://github.com/winapiadmin/chessli…
winapiadmin May 29, 2026
d7e8d4a
fix invalid tests
winapiadmin May 29, 2026
e1c7020
fix bugs
winapiadmin May 30, 2026
c216ae2
fixing some final bugs before force merging
winapiadmin May 30, 2026
cde76bd
fixing syntax
winapiadmin May 30, 2026
ba9bb66
exclude release+assert (NDEBUG is defined)
winapiadmin May 30, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
31 changes: 7 additions & 24 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -42,32 +42,15 @@ jobs:
matrix:
os: [ubuntu-latest, windows-latest]
build_type: [Debug, Release]
c_compiler: [gcc, clang, cl]

include:
# Windows
- os: windows-latest
c_compiler: cl
cpp_compiler: cl
- os: windows-latest
c_compiler: clang
cpp_compiler: clang++
- os: windows-latest
c_compiler: gcc
cpp_compiler: g++

# Linux
- os: ubuntu-latest
c_compiler: gcc
cpp_compiler: g++
- os: ubuntu-latest
c_compiler: clang
cpp_compiler: clang++
cpp_compiler: [g++, clang++, cl]
error_mode: [ASSERT, THROW, NONE]
Comment thread
winapiadmin marked this conversation as resolved.

exclude:
- os: ubuntu-latest
c_compiler: cl

cpp_compiler: cl
Comment thread
winapiadmin marked this conversation as resolved.
- build_type: Release
error_mode: ASSERT

steps:
- uses: actions/checkout@v4

Expand All @@ -87,10 +70,10 @@ jobs:
fi
fi
cmake -B "${{ steps.vars.outputs.dir }}" \
-DCMAKE_C_COMPILER=${{ matrix.c_compiler }} \
-DCMAKE_CXX_COMPILER=${{ matrix.cpp_compiler }} \
-DCMAKE_BUILD_TYPE=${{ matrix.build_type }} \
-DSANITIZERS=${SANITIZERS} \
-DCHESSLIB_ERROR_MODE=${{ matrix.error_mode }} \
-DDART_TESTING_TIMEOUT=0 \
-S "${{ github.workspace }}"

Expand Down
59 changes: 0 additions & 59 deletions .github/workflows/try_compile.yml

This file was deleted.

46 changes: 22 additions & 24 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -21,45 +21,43 @@ project(chesslib LANGUAGES CXX)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

# --- Core Library ---
set(SOURCES
position.cpp
attacks.cpp "zobrist.cpp"
"moves_io.cpp" "printers.cpp" "movegen.cpp")
add_library(chesslib STATIC ${SOURCES})
target_include_directories(chesslib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_compile_definitions(chesslib PRIVATE GENERATE_AT_RUNTIME)
set(CHESSLIB_ERROR_MODE "THROW" CACHE STRING "ASSERT|THROW|NONE")
set_property(CACHE CHESSLIB_ERROR_MODE PROPERTY STRINGS ASSERT THROW NONE)

if(NOT CHESSLIB_ERROR_MODE MATCHES "^(ASSERT|THROW|NONE)$")
message(FATAL_ERROR "Invalid ERROR_MODE: ${CHESSLIB_ERROR_MODE}")
endif()
# --- Compiler tuning ---
if (CMAKE_CXX_COMPILER_ID STREQUAL "Clang")
if (CMAKE_CXX_COMPILER_FRONTEND_VARIANT STREQUAL "MSVC")
# clang-cl: forward GCC/Clang style constexpr flags via /clang:
add_compile_options(
/clang:-fconstexpr-steps=2000000000
/clang:-fconstexpr-depth=1024
target_compile_options(chesslib PRIVATE
/clang:-march=native
/clang:-mtune=native
/clang:-ftemplate-backtrace-limit=0
)
else()
# native clang++ on *nix or Windows
add_compile_options(
-fconstexpr-steps=2000000000
-fconstexpr-depth=1024
target_compile_options(chesslib PRIVATE
-march=native -mtune=native
-ftemplate-backtrace-limit=0 -static
)
endif()
elseif (CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
add_compile_options(-fconstexpr-ops-limit=2000000000 -fconstexpr-depth=1024 -march=native -mtune=native -ftemplate-backtrace-limit=0 -static)
target_compile_options(chesslib PRIVATE -march=native -mtune=native)

elseif (CMAKE_CXX_COMPILER_ID STREQUAL "MSVC")
set(ARCH_FLAG "/arch:AVX2" CACHE STRING "MSVC architecture flag (/arch:SSE2, /arch:AVX, /arch:AVX2, /arch:AVX512)")
add_compile_options(/constexpr:steps2000000000 /constexpr:depth1024 ${ARCH_FLAG})
target_compile_options(chesslib PRIVATE ${ARCH_FLAG})
endif()

add_compile_definitions(GENERATE_AT_RUNTIME)
if(CMAKE_BUILD_TYPE MATCHES "Debug")
add_compile_definitions(_DEBUG)
endif()
# --- Core Library ---
set(SOURCES
position.cpp
attacks.cpp "zobrist.cpp"
"moves_io.cpp" "printers.cpp" "movegen.cpp")
add_library(chesslib STATIC ${SOURCES})
target_include_directories(chesslib PUBLIC ${CMAKE_CURRENT_SOURCE_DIR})
target_compile_definitions(chesslib PUBLIC _CHESSLIB_ERROR_MODE_${CHESSLIB_ERROR_MODE})
# --- Enable CTest integration ---
include(CTest)

Expand All @@ -81,9 +79,9 @@ if(BUILD_TESTING)
target_link_libraries(NonImportantTests PRIVATE chesslib doctest::doctest)
target_link_libraries(test_chess960 PRIVATE chesslib doctest::doctest)

add_test(NAME test_normal COMMAND test_normal)
add_test(NAME test_api COMMAND NonImportantTests)
add_test(NAME test_chess960 COMMAND test_chess960)
add_test(NAME test_normal COMMAND test_normal --abort-after=1)
add_test(NAME test_api COMMAND NonImportantTests --abort-after=1)
add_test(NAME test_chess960 COMMAND test_chess960 --abort-after=1)
if (UNIX AND CMAKE_BUILD_TYPE MATCHES "Debug")
set(SANITIZERS "" CACHE STRING "sanitizers such as undefined,address")

Expand Down
53 changes: 32 additions & 21 deletions attacks.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,17 @@
You should have received a copy of the GNU General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/

/// @file attacks.cpp
/// @brief Magic-bitboard generation, hyperbola-quintessence helpers, and between-square table.

#include "attacks.h"

namespace chess::_chess {
// [INTERNAL]

// Reverse bits horizontally in 64-bit integer
/// @brief Reverse bits horizontally in a 64-bit integer.
/// @details Used by the hyperbola quintessence algorithm.
static constexpr Bitboard reverse(Bitboard b) {
b = (b & 0x5555555555555555ULL) << 1 | ((b >> 1) & 0x5555555555555555ULL);
b = (b & 0x3333333333333333ULL) << 2 | ((b >> 2) & 0x3333333333333333ULL);
Expand All @@ -32,14 +37,19 @@ static constexpr Bitboard reverse(Bitboard b) {
return b;
}

/// @brief Hyperbola quintessence attack computation for a single line.
/// @param sliderBB Bitboard with the slider's square set.
/// @param occ Occupancy bitboard.
/// @param mask Line mask (rank, file, or diagonal).
/// @return Attacks along the masked line.
static constexpr Bitboard hyp_quint(Bitboard sliderBB, Bitboard occ, Bitboard mask) {
Bitboard occ_masked = occ & mask;
Bitboard left = occ_masked - 2 * sliderBB;
Bitboard right = reverse(occ_masked) - 2 * reverse(sliderBB);
return (left ^ reverse(right)) & mask;
}

// For Bishop: Mask for diagonal and anti-diagonal
/// @brief Compute the diagonal mask through a square.
static constexpr Bitboard diag_mask(Square sq) {
int r = rank_of(sq);
int f = file_of(sq);
Expand All @@ -53,6 +63,7 @@ static constexpr Bitboard diag_mask(Square sq) {
}
return mask;
}
/// @brief Compute the anti-diagonal mask through a square.
static constexpr Bitboard antidiag_mask(Square sq) {
int r = rank_of(sq);
int f = file_of(sq);
Expand All @@ -68,20 +79,21 @@ static constexpr Bitboard antidiag_mask(Square sq) {
return mask;
}

// Hyperbola Quintessence for Bishop
/// @brief Bishop attacks via hyperbola quintessence.
static constexpr Bitboard _HyperbolaBishopAttacks(Square sq, Bitboard occ) {
Bitboard slider = 1ULL << sq;
Bitboard d_mask = diag_mask(sq);
Bitboard ad_mask = antidiag_mask(sq);
return hyp_quint(slider, occ, d_mask) | hyp_quint(slider, occ, ad_mask);
}

// For Rook: Rank and File Masks
/// @brief Rank mask for a square.
static constexpr Bitboard rank_mask(Square sq) { return attacks::MASK_RANK[rank_of(sq)]; }

/// @brief File mask for a square.
static constexpr Bitboard file_mask(Square sq) { return attacks::MASK_FILE[file_of(sq)]; }

// Hyperbola Quintessence for Rook
/// @brief Rook attacks via hyperbola quintessence.
static constexpr Bitboard _HyperbolaRookAttacks(Square sq, Bitboard occ) {
Bitboard slider = 1ULL << sq;
Bitboard r_mask = rank_mask(sq);
Expand Down Expand Up @@ -134,6 +146,12 @@ _POSSIBLY_CONSTEXPR std::array<uint64_t, 64> BishopMagics = {
};

// clang-format on

/// @brief Generate magic-bitboard lookup tables.
/// @tparam AttackFunc The hyperbola attack function to use.
/// @tparam TableSize Total number of attack entries.
/// @tparam IsBishop true for bishop, false for rook.
/// @return Pair of (magic table, attack table).
template <auto AttackFunc, size_t TableSize, bool IsBishop>
_POSSIBLY_CONSTEXPR std::pair<std::array<Magic, 64>, std::array<Bitboard, TableSize>> generate_magic_table() {
std::array<Magic, 64> table{};
Expand Down Expand Up @@ -184,34 +202,27 @@ _POSSIBLY_CONSTEXPR std::pair<std::array<Magic, 64>, std::array<Bitboard, 0x1900
generate_magic_table<_chess::_HyperbolaRookAttacks, 0x19000, false>();
_POSSIBLY_CONSTEXPR std::array<Magic, 64> RookTable = rookData.first;
_POSSIBLY_CONSTEXPR std::array<Bitboard, 0x19000> RookAttacks = rookData.second;
/**
* @brief Returns the bishop attacks for a given square
* @param sq
* @param occupied
* @return
*/

/// @brief Look up bishop attacks from the precomputed magic table.
[[nodiscard]] Bitboard bishop(Square sq, Bitboard occupied) {
return BishopAttacks[BishopTable[(int)sq].index + BishopTable[(int)sq](occupied)];
}

/**
* @brief Returns the rook attacks for a given square
* @param sq
* @param occupied
* @return
*/
/// @brief Look up rook attacks from the precomputed magic table.
[[nodiscard]] Bitboard rook(Square sq, Bitboard occupied) {
return RookAttacks[RookTable[(int)sq].index + RookTable[(int)sq](occupied)];
}

} // namespace chess::attacks
namespace chess::movegen {

/// @brief Hyperbola attack for bishop or rook (used for between-table generation).
inline static Bitboard att(PieceType pt, Square sq, Bitboard occ) {
return (pt == BISHOP) ? chess::_chess::_HyperbolaBishopAttacks(sq, occ) : chess::_chess::_HyperbolaRookAttacks(sq, occ);
}

inline static std::array<std::array<Bitboard, SQ_NONE + 1>, SQ_NONE + 1> generate_between() {
std::array<std::array<Bitboard, SQ_NONE + 1>, SQ_NONE + 1> squares_between_bb{};
/// @brief Generate the between-square table at program startup.
inline static std::array<std::array<Bitboard, 64>, 64> generate_between() {
std::array<std::array<Bitboard, 64>, 64> squares_between_bb{};

for (int sq1 = 0; sq1 < 64; ++sq1) {
for (PieceType pt : { BISHOP, ROOK }) {
Expand All @@ -226,5 +237,5 @@ inline static std::array<std::array<Bitboard, SQ_NONE + 1>, SQ_NONE + 1> generat

return squares_between_bb;
}
std::array<std::array<Bitboard, SQ_NONE + 1>, SQ_NONE + 1> SQUARES_BETWEEN_BB = generate_between();
std::array<std::array<Bitboard, 64>, 64> SQUARES_BETWEEN_BB = generate_between();
} // namespace chess::movegen
Loading
Loading