/*************************************************************************** * Brutal Chess * http://brutalchess.sf.net * * File : board.h * Authors : Mike Cook, Joe Flint, Neil Pankey **************************************************************************/ #ifndef BOARD_H #define BOARD_H #include #include #include #include "bitboard.h" #include "boardmove.h" using std::vector; struct SerialBoard { unsigned long long pieces[Piece::LAST_TYPE+1]; unsigned long long color[Piece::LAST_COLOR+1]; union { int all_flags; struct { int white_enpassant:8; int black_enpassant:8; int white_turn:1; int wk_castling:1; int wq_castling:1; int bk_castling:1; int bq_castling:1; int:11; }; }; }; /** * This class represents a chess board. */ class Board { public: /** Default constructor. Creates an empty board. */ Board(); /** Board destructor. Deletes all the board stuff */ ~Board(); /** Performs all the static initializations */ static void init(); /** Reset the board to an empty state. */ void reset(); void setupPieces(); /** Returns the piece at the BoardPosition 'bp'. */ Piece* getPiece(const BoardPosition & bp) const; /** * Returns the bit board with the positions of pieces of type t * @param t - The type of pieces to return */ BitBoard getPieces(Piece::Type t) const { return BitBoard(m_pieces[t]); } /** * Returns the bit board with the positions of pieces of type t and color c * @param c - The color of pieces to return * @param t - The type of pieces to return */ BitBoard getPieces(Piece::Color c, Piece::Type t) const {return BitBoard(m_pieces[t] & m_color[c]);} /** * Sets the internal bitboard at BoardPosition bp to indicate a piece of * type t and color c * @param c - The Piece::Color to assign the piece. * @param t - The Piece::Type to assign the piece. * @param bp - The BoardPosition to set the piece at. */ void setPiece(Piece::Color c, Piece::Type t, const BoardPosition& bp); /* Puts a new piece onto the board. Overwrites whatever is at that * BoardPosition. * @param - Piece to be created * @param - BoardPosition where piece is being created */ void setPiece(Piece * piece, const BoardPosition & bp); /** * Remove the piece from given BoardPosition * @param bp - BoardPosition to remove piece from */ void removePiece(const BoardPosition & bp); /** * Returns true if there are no pieces between start and end exclusive. * @param start - The starting BoardPosition. * @param end - The ending BoardPosition. */ bool isPathClear(const BoardPosition & start, const BoardPosition & end) const; /** * Returns true if there are no pieces between start and end of the BoardMove, * exclusive. * @param bm - The BoardMove to check path for. */ bool isPathClear(const BoardMove & bm) const { return isPathClear(bm.origin(), bm.dest()); } /** * Returns true if a piece is present at the specified BoardPosition. * @param pos - The BoardPosition to check. */ bool isOccupied(const BoardPosition & pos) const; /** * Returns true if a move is legal for the piece at its origin for the * current board setup. * @param bm - The BoardMove to be validated. */ bool isMoveLegal(const BoardMove & bm) const; /** * Returns true if the given position is under attack by the opposing color, * returns false otherwise. * @param bp - The BoardPosition to check. * @param c - The Color that could be under attack */ unsigned long long isAttacked(const BoardPosition & bp, Piece::Color c) const; /** * Returns true if the players attempted move leaves him in check, returns * false otherwies. * @param bm - The BoardMove being attempted. */ bool isResultCheck(const BoardMove & bm) const; /** * Returns true if the players is in check, false otherwies. * @param c - The color that could be in check */ bool isCheck(Piece::Color c) const { return (0 != this->isAttacked(m_king_pos[c], c)); } /** * Returns true if the player is in checkmate, false otherwies. * @param c - The color that could be in checkmate */ bool isCheckMate(Piece::Color c) const; /** * Returns true if either player is in Check Mate */ bool containsCheckMate() const { return (isCheckMate(Piece::WHITE) || isCheckMate(Piece::BLACK)); } /** * Returns true if the players is in stalemate, false otherwies. * @param c - The color that could be in stalemate */ bool isStaleMate(Piece::Color c) const; bool isMaterialDraw() const; /** * Returns true if a Pawn can move to the specified BoardPosition to * perform an en-passant move. * @param bp - The BoardPosition at which to check the en passant bit. */ bool isEnPassantSet(const BoardPosition & bp) const { return (0 != (getMask(bp) & m_enpassant_flags)); } vector possibleMoves(Piece::Color color, bool findOne=false) const; /** */ BoardPosition getKing(Piece::Color c) const { return m_king_pos[c]; } /** */ int getRankState(const BoardPosition & bp) const; /** */ int getFileState(const BoardPosition & bp) const; /** */ int getSEDiagState(const BoardPosition & bp) const; /** */ int getNEDiagState(const BoardPosition & bp) const; /** * This function handles the setting and removal of castling and en * passant flags on the specialty flag boards. * @param bm - The BoardMove that just occured. */ void setSpecialPieceFlags(const BoardMove & bm); /** * Given a valid and legal move, updates the board to reflect the move. * This function should only be called from ChessGame::tryMove. * @param bm - The move to update the board with. */ void update(const BoardMove & bm); /** */ void addPiece(Piece * p, const BoardPosition & bp); /** */ SerialBoard serialize() const; /** * This is just the size of the board, useful for looping over a board. */ const static int BOARDSIZE = 8; static unsigned long long pawnAttacks[2][64]; static unsigned long long knightAttacks[64]; static unsigned long long kingAttacks[64]; static unsigned long long rankAttacks[64][256]; static unsigned long long fileAttacks[64][256]; static unsigned long long diagAttacksSE[64][256]; static unsigned long long diagAttacksNE[64][256]; friend class BrutalPlayer; private: static Piece* m_allpieces[Piece::LAST_COLOR + 1][Piece::LAST_TYPE + 1]; static bool m_setup; int m_total_pieces[Piece::LAST_COLOR + 1]; int m_piece_count[Piece::LAST_COLOR + 1][Piece::LAST_TYPE + 1]; // Current state of the board unsigned long long m_pieces[Piece::LAST_TYPE + 1]; unsigned long long m_color[Piece::LAST_COLOR + 1]; unsigned long long m_enpassant_flags; unsigned long long m_castling_flags; // Nice to have this around BoardPosition m_king_pos[Piece::LAST_COLOR + 1]; inline void unsetAllBits(const BoardPosition & bp); }; static int pow2[8]; std::ostream& operator<< (std::ostream & os, const Board & b); inline unsigned long long getMask(const BoardPosition & bp) { return 1LL << (Board::BOARDSIZE*(bp.m_rank0) + bp.m_file0); } inline unsigned long long maskRank(const BoardPosition & bp) { return (0xffLL << bp.rank0()*8); } inline unsigned long long maskFile(const BoardPosition & bp) { unsigned long long mask = 0LL; for (int i = 0; i < 8; ++i) mask |= (1LL << (bp.file0() + 8*i)); return mask; } inline void setBit(unsigned long long & bitfield, const BoardPosition & bp) { bitfield |= getMask(bp); } inline void unsetBit(unsigned long long & bitfield, const BoardPosition & bp) { bitfield ^= getMask(bp); } #endif // End of file board.h