예제 #1
0
        private static void generate_castle(CastlingSide Side, bool OnlyChecks, Position pos, MoveStack[] ms, ref int mpos, Color us)
        {
            if (pos.castle_impeded(us, Side) || (pos.can_castle_CR(Utils.make_castle_right(us, Side)) == 0))
            {
                return;
            }

            // After castling, the rook and king final positions are the same in Chess960
            // as they would be in standard chess.
            Square kfrom = pos.king_square(us);
            Square rfrom = pos.castle_rook_square(us, Side);
            Square kto   = Utils.relative_square(us, Side == CastlingSideC.KING_SIDE ? SquareC.SQ_G1 : SquareC.SQ_C1);

            Bitboard enemies = pos.pieces_C(us ^ 1);

            Debug.Assert(!pos.in_check());

            for (Square s = Math.Min(kfrom, kto), e = Math.Max(kfrom, kto); s <= e; s++)
            {
                if (s != kfrom && // We are not in check
                    ((pos.attackers_to(s) & enemies) != 0))
                {
                    return;
                }
            }

            // Because we generate only legal castling moves we need to verify that
            // when moving the castling rook we do not discover some hidden checker.
            // For instance an enemy queen in SQ_A1 when castling rook is in SQ_B1.
            if (pos.chess960 &&
                ((pos.attackers_to(kto, Utils.xor_bit(pos.occupied_squares, rfrom)) & enemies) != 0))
            {
                return;
            }

            Move m = Utils.make_castle(kfrom, rfrom);

            if (OnlyChecks)
            {
                CheckInfo ci = CheckInfoBroker.GetObject();
                ci.CreateCheckInfo(pos);
                bool givesCheck = pos.move_gives_check(m, ci);
                CheckInfoBroker.Free();
                if (!givesCheck)
                {
                    return;
                }
            }

            ms[mpos++].move = m;
        }
예제 #2
0
        internal static void generate_quiet_check(Position pos, MoveStack[] ms, ref int mpos)
        {
            /// generate<MV_NON_CAPTURE_CHECK> generates all pseudo-legal non-captures and knight
            /// underpromotions that give check. Returns a pointer to the end of the move list.
            Debug.Assert(!pos.in_check());

            Color     us = pos.sideToMove;
            CheckInfo ci = CheckInfoBroker.GetObject();

            ci.CreateCheckInfo(pos);
            Bitboard dc = ci.dcCandidates;

            while (dc != 0)
            {
                Square    from = Utils.pop_1st_bit(ref dc);
                PieceType pt   = Utils.type_of(pos.piece_on(from));

                if (pt == PieceTypeC.PAWN)
                {
                    continue; // Will be generated together with direct checks
                }
                Bitboard b = pos.attacks_from_PTS(pt, from) & ~pos.occupied_squares;

                if (pt == PieceTypeC.KING)
                {
                    b &= ~Utils.PseudoAttacks[PieceTypeC.QUEEN][ci.ksq];
                }

                while (b != 0)
                {
                    ms[mpos++].move = Utils.make_move(from, Utils.pop_1st_bit(ref b));
                }
            }

            generate_pawn_moves(us, MoveType.MV_QUIET_CHECK, pos, ms, ref mpos, ci.dcCandidates, ci.ksq);

            generate_direct_checks(PieceTypeC.KNIGHT, pos, ms, ref mpos, us, ci);
            generate_direct_checks(PieceTypeC.BISHOP, pos, ms, ref mpos, us, ci);
            generate_direct_checks(PieceTypeC.ROOK, pos, ms, ref mpos, us, ci);
            generate_direct_checks(PieceTypeC.QUEEN, pos, ms, ref mpos, us, ci);

            if (pos.can_castle_C(us) != 0)
            {
                generate_castle(CastlingSideC.KING_SIDE, true, pos, ms, ref mpos, us);
                generate_castle(CastlingSideC.QUEEN_SIDE, true, pos, ms, ref mpos, us);
            }

            CheckInfoBroker.Free();
        }
예제 #3
0
파일: ob.cs 프로젝트: SethKitchen/ChessAI
        internal static void Warmup()
        {
            // Bench 128 4 17 yields:

            // CheckInfoBroker: 140 (4/32/40/32/32)
            // EvalInfoBroker: 16 (4/4/4/4)
            // SwapListBroker: 16 (4/4/4/4)
            // MovesSearchedBroker: 120 (28/36/28/28)
            // PositionBroker: 32 (8/8/8/8)
            // StateInfoArrayBroker: 16 (4/4/4/4)

            // MListBroker: 20 (4/4/4/4/4)
            // LoopStackBroker: 32 (8/8/8/8)
            // MovePickerBroker: 136 (32/40/32/32)
            // StateInfoBroker: 132 (32/36/32/32)

            // Specific allocation not to overallocate memory for nothing
            int i, brokerSize;

            // Reusing brokers
            brokerSize = 40; for (i = 0; i < brokerSize; i++)
            {
                CheckInfoBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                CheckInfoBroker.Free();
            }
            brokerSize = 4; for (i = 0; i < brokerSize; i++)
            {
                EvalInfoBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                EvalInfoBroker.Free();
            }
            brokerSize = 4; for (i = 0; i < brokerSize; i++)
            {
                SwapListBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                SwapListBroker.Free();
            }
            brokerSize = 36; for (i = 0; i < brokerSize; i++)
            {
                MovesSearchedBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                MovesSearchedBroker.Free();
            }
            brokerSize = 8; for (i = 0; i < brokerSize; i++)
            {
                PositionBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                PositionBroker.Free();
            }
            brokerSize = 4; for (i = 0; i < brokerSize; i++)
            {
                StateInfoArrayBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                StateInfoArrayBroker.Free();
            }
            brokerSize = 4; for (i = 0; i < brokerSize; i++)
            {
                MListBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                MListBroker.Free();
            }
            brokerSize = 36; for (i = 0; i < brokerSize; i++)
            {
                StateInfoBroker.GetObject();
            }
            for (i = 0; i < brokerSize; i++)
            {
                StateInfoBroker.Free();
            }

            // Recycling brokers
            brokerSize = 8; LoopStack[] arrLoopStack = new LoopStack[brokerSize]; for (i = 0; i < brokerSize; i++)
            {
                arrLoopStack[i] = LoopStackBroker.GetObject();
            }
            for (i = brokerSize - 1; i >= 0; i--)
            {
                LoopStackBroker.Free(arrLoopStack[i]);
            }
            brokerSize = 40; MovePicker[] arrMovePicker = new MovePicker[brokerSize]; for (i = 0; i < brokerSize; i++)
            {
                arrMovePicker[i] = MovePickerBroker.GetObject();
            }
            for (i = brokerSize - 1; i >= 0; i--)
            {
                MovePickerBroker.Free(arrMovePicker[i]);
            }
        }