Esempio n. 1
0
char get_chesspiece(char p)
{
    if (is_king(p))
        return KING;

    if (is_queen(p))
        return QUEEN;

    if (is_rook(p))
        return ROOK;

    if (is_bishop(p))
        return BISHOP;

    if (is_knight(p))
        return KNIGHT;

    if (is_pawn(p))
        return PAWN;

    return ERROR;
}
Esempio n. 2
0
void print_chesspiece(char p, FILE * f)
{
    char output, black;

    output = '?';

    if (is_black(p))
        black = 1;
    else
        black = 0;

    if (is_king(p))
        output = 'K';

    if (is_queen(p))
        output = 'Q';

    if (is_rook(p))
        output = 'R';

    if (is_bishop(p))
        output = 'B';

    if (is_knight(p))
        output = 'N';

    if (is_pawn(p))
        output = 'P';

    if (black)
        output += 'a' - 'A';

    if (is_free(p))
        output = ' ';

    fprintf(f, "%c", output);
}
Esempio n. 3
0
// Non-capturing checks.
//------------------------------------------------------------------------------
MoveGen *generate_checks(MoveGen *self) {
    Position *p = self->p;
    int color = p->color, enemy = p->color ^ 1;
    int square = (int)p->king[enemy];

    // Non-capturing Knight checks.
    Bitmask prohibit = maskNone;
    Bitmask checks = knightMoves[square];
    Bitmask outposts = p->outposts[knight(color)];
    while (any(outposts)) {
        int from = pop(&outposts);
        add_piece_move(self, from, knightMoves[from] & checks & ~p->board);
    }

    // Non-capturing Bishop or Queen checks.
    checks = targets_for(p, square, bishop(enemy));
    outposts = p->outposts[bishop(color)] | p->outposts[queen(color)];
    while (any(outposts)) {
        int from = pop(&outposts);
        Bitmask squares = targets_for(p, from, bishop(enemy)) & checks & ~p->outposts[enemy];
        while (any(squares)) {
            int to = pop(&squares);
            Piece piece = p->pieces[to];
            if (!piece) {
                // Empty square: simply move a bishop to check.
                append(self, new_move(p, from, to));
            } else if (color(piece) == color && any(maskDiagonal[from][square])) {
                // Non-empty square occupied by friendly piece on the same
                // diagonal: moving the piece away causes discovered check.
                switch (kind(piece)) {
                case Pawn:
                    // Block pawn promotions (since they are treated as
                    // captures) and en-passant captures.
                    prohibit = maskRank[0] | maskRank[7];
                    if (p->enpassant) {
                        prohibit |= bit[p->enpassant];
                    }
                    add_pawn_move(self, to, targets(p, to) & ~p->board & ~prohibit);
                    break;
                case King:
                    // Make sure the king steps out of attack diaginal.
                    add_king_move(self, to, targets(p, to) & ~p->board & ~maskBlock[from][square]);
                    break;
                default:
                    add_piece_move(self, to, targets(p, to) & ~p->board);
                }
            }
        }
        if (is_queen(p->pieces[from])) {
            // Queen could move straight as a rook and check diagonally as a bishop
            // or move diagonally as a bishop and check straight as a rook.
            Bitmask squares = (targets_for(p, from, rook(color)) & checks) |
                  (targets_for(p, from, bishop(color)) & targets_for(p, square, rook(color)));
            add_piece_move(self, from, squares & ~p->board);
        }
    }

    // Non-capturing Rook or Queen checks.
    checks = targets_for(p, square, rook(enemy));
    outposts = p->outposts[rook(color)] | p->outposts[queen(color)];
    while (any(outposts)) {
        int from = pop(&outposts);
        Bitmask squares = targets_for(p, from, rook(enemy)) & checks & ~p->outposts[enemy];
        while (any(squares)) {
            int to = pop(&squares);
            Piece piece = p->pieces[to];
            if (!piece) {
                // Empty square: simply move a rook to check.
                append(self, new_move(p, from, to));
            } else if (color(piece) == color) {
                if (any(maskStraight[from][square])) {
                    // Non-empty square occupied by friendly piece on the same
                    // file or rank: moving the piece away causes discovered check.
                    switch (kind(piece)) {
                    case Pawn:
                        // If pawn and rook share the same file then non-capturing
                        // discovered check is not possible since the pawn is going
                        // to stay on the same file no matter what.
                        if (col(from) == col(to)) {
                            continue;
                        }
                        // Block pawn promotions (since they are treated as captures)
                        // and en-passant captures.
                        prohibit = maskRank[0] | maskRank[7];
                        if (p->enpassant) {
                            prohibit |= bit[p->enpassant];
                        }
                        add_pawn_move(self, to, targets(p, to) & ~p->board & ~prohibit);
                        break;
                    case King:
                        // Make sure the king steps out of attack file or rank.
                        prohibit = maskNone;
                        if (row(from) == row(square)) {
                            prohibit = maskRank[row(from)];
                        } else {
                            prohibit = maskFile[col(square)];
                        }
                        add_king_move(self, to, targets(p, to) & ~p->board & ~prohibit);
                        break;
                    default:
                        add_piece_move(self, to, targets(p, to) & ~p->board);
                    }
                }
            }
        }
    }

    // Non-capturing Pawn checks.
    outposts = p->outposts[pawn(color)] & maskIsolated[col(square)];
    while (any(outposts)) {
        int from = pop(&outposts);
        Bitmask target = maskPawn[color][square] & targets(p, from);
        if (any(target)) {
            append(self, new_pawn_move(p, from, pop(&target)));
        }
    }

    return self;
}