Ejemplo n.º 1
0
static boolean is_not_pawn_make_to_base_line(numecoup n)
{
  square const sq_departure = move_generation_stack[n].departure;
  square const sq_arrival = move_generation_stack[n].arrival;
  boolean result;

  TraceFunctionEntry(__func__);
  TraceFunctionParamListEnd();

  result = !(is_pawn(get_walk_of_piece_on_square(sq_departure))
             && ((trait[nbply]==White && sq_arrival<=square_h1)
                 || (trait[nbply]==Black && sq_arrival>=square_a8)));

  TraceFunctionExit(__func__);
  TraceFunctionResult("%u",result);
  TraceFunctionResultEnd();
  return result;
}
Ejemplo n.º 2
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;
}
Ejemplo n.º 3
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);
}
Ejemplo n.º 4
0
// Decodes a string in long algebraic notation and returns a move. If the
// notation is not recognized the move is returned as (Move)0.
//------------------------------------------------------------------------------
Move new_move_from_string(Position *self, char *e2e4) {
    bool queen_side_castle = !strcmp(e2e4, "0-0-0");
    bool king_side_castle = !strcmp(e2e4, "0-0") && !queen_side_castle;

    if (king_side_castle || queen_side_castle) {
        bool king_side_ok = false, queen_side_ok = false;
        can_castle(self, self->color, &king_side_ok, &queen_side_ok);
        if (king_side_castle && king_side_ok) {
            int from = self->king[self->color];
            int to = G1 + self->color * A8;
            return validate(self, new_castle(self, from, to));
        }
        if (queen_side_castle && queen_side_ok) {
            int from = self->king[self->color];
            int to = C1 + self->color * A8;
            return validate(self, new_castle(self, from, to));
        }
        return (Move)0;
    }

    char notation[strlen(e2e4)];
    char *src = e2e4, *dst = notation;

    // Strip all optional characters.
    while (*src) {
        if (strchr("KkQqRrBbNn12345678acdefgh", *src)) {
            *dst++ = *src;            
        }
        src++;
    }
    *dst = '\0';

    if (strlen(notation) >= 4 && strlen(notation) <= 5) {
        // Validate optional piece character to make sure the actual piece it
        // represents is there.
        Piece piece = pawn(self->color);
        switch (notation[0]) {
        case 'K':
            piece = king(self->color);
            break;
        case 'Q':
            piece = queen(self->color);
            break;
        case 'R':
            piece = rook(self->color);
            break;
        case 'B':
            piece = bishop(self->color);
            break;
        case 'N':
            piece = knight(self->color);
        }

        int sq;
        if (is_pawn(piece)) {
            sq = square(notation[1] - '1', notation[0] - 'a');
        } else {
            sq = square(notation[2] - '1', notation[1] - 'a');
        }

        if (sq >= A1 && sq <= H8) {
            if (self->pieces[sq] == piece) {
                return validate(self, new_move_from_notation(self, is_pawn(piece) ? notation : notation + 1));
            }
        }
    }

    return (Move)0;
}
Ejemplo n.º 5
0
// -------------------------------------------------------------------
// Piece movement:
//  - this function must be passed a *VALID* move (e.g. one that has
//    been verified by can_move())
//  - promotion piece will be automatically cast to correct colour
// -------------------------------------------------------------------
game_status ChessBoard::do_move(int from, int to, piece_type promotion) {
    // Disable castling if rook is captured or moved
    for (int *sq=&to;sq;sq=sq==&to?&from:(int *)NULL)
        switch (*sq) {
        case a1:
            w_castle_q=false;
            break;
        case a8:
            b_castle_q=false;
            break;
        case h1:
            w_castle_k=false;
            break;
        case h8:
            b_castle_k=false;
        }

    // Reset castled flags
    b_castled=w_castled=false;

    // Mark en-passant square, if any
    if (square[from]==w_Pawn && to==from+2*Rank)
        en_passant=from+Rank;
    else if (square[from]==b_Pawn && to==from-2*Rank)
        en_passant=from-Rank;
    else
        en_passant=No_square;

    // Perform actual rearrangement of board pieces
    bool increment_fifty=true;
    if (w_castle_k && from==e1 && to==g1) {
        square[g1]=w_King;                      // White castles kingside
        square[f1]=w_Rook;
        square[e1]=square[h1]=Empty;
        w_castled=true;
    }
    else if (w_castle_q && from==e1 && to==c1) {
        square[c1]=w_King;                      // White castles queenside
        square[d1]=w_Rook;
        square[e1]=square[a1]=Empty;
        w_castled=true;
    }
    else if (b_castle_k && from==e8 && to==g8) {
        square[g8]=b_King;                      // Black castles kingside
        square[f8]=b_Rook;
        square[e8]=square[h8]=Empty;
        b_castled=true;
    }
    else if (b_castle_q && from==e8 && to==c8) {
        square[c8]=b_King;                      // Black castles queenside
        square[d8]=b_Rook;
        square[e8]=square[a8]=Empty;
        b_castled=true;
    }
    else if (square[from]==w_Pawn && square[to]==Empty && to!=from+Rank) {
        square[to]=w_Pawn;                      // White captures en-passant
        square[from]=square[to-Rank]=Empty;
        increment_fifty=false;
    }
    else if (square[from]==b_Pawn && square[to]==Empty && to!=from-Rank) {
        square[to]=b_Pawn;                      // Black captures en-passant
        square[from]=square[to+Rank]=Empty;
        increment_fifty=false;
    }
    else {                                      // Normal move
        if (square[to]!=Empty || is_pawn(square[from]))
            increment_fifty=false;
        promotion=make_colour(promotion, w_turn);
        square[to]=(promotion!=Empty)?promotion:square[from];
        square[from]=Empty;
    }

    // Disable castling if king was moved
    if (square[e1]!=w_King)
        w_castle_q=w_castle_k=false;
    if (square[e8]!=b_King)
        b_castle_q=b_castle_k=false;

    // Update king position
    if (square[to]==w_King)
        w_king_pos=to;
    else if (square[to]==b_King)
        b_king_pos=to;

    // Adjust 50-move rule counter
    fifty=increment_fifty?fifty+1:0;

    // Set check flag
    if (w_turn) {
        w_check=is_attacked(!w_turn, w_king_pos);
        b_check=is_attacked(w_turn, b_king_pos);
    }
    else {
        b_check=is_attacked(!w_turn, b_king_pos);
        w_check=is_attacked(w_turn, w_king_pos);
    }

    // Change active player
    w_turn=!w_turn;

    // Check for checkmate/stalemate
    move_list moves;
    for (int i=a1;i<=h8;i++) {
        if (is_colour(square[i], w_turn)) {
            switch (make_neutral(square[i])) {
            case King:
                moves=mobility_king(i); 
                break;
            case Pawn:
                moves=mobility_pawn(i);
                break;
            case Knight:
                moves=mobility_knight(i); 
                break;
            case Bishop:
                moves=mobility_bishop(i);
                break;
            case Rook:
                moves=mobility_rook(i);
                break;
            case Queen:
                moves=mobility_queen(i);
                break;
            }
        if (!moves.empty())
            break;
        }
    }

    // Update log of board configurations
    boardlog.append(*this);

    // Set game status
    if (triple_occurrence()) {
        status=TripleOccurrence;
        in_progress=false;
    }
    else if (moves.empty() && is_in_check(w_turn)) {
        status=Checkmate;
        in_progress=false;
    }
    else if (moves.empty()) {
        status=Stalemate;
        in_progress=false;
    }
    else if (fifty>=99) {
        status=FiftyMoves;
        in_progress=false;
    }
    else if (is_in_check(w_turn))
        status=Check;
    else
        status=Normal;

    return status;
}