Let PROMOTED and DEMOTED macros use argument
[xboard.git] / parser.c
index 496fef1..471ae94 100644 (file)
--- a/parser.c
+++ b/parser.c
@@ -1,7 +1,7 @@
 /*
  * parser.c --
  *
- * Copyright 2011, 2012, 2013, 2014 Free Software Foundation, Inc.
+ * Copyright 2011, 2012, 2013, 2014, 2015 Free Software Foundation, Inc.
  * ------------------------------------------------------------------------
  *
  * GNU XBoard is free software: you can redistribute it and/or modify
@@ -22,6 +22,7 @@
 
 #include "config.h"
 #include <stdio.h>
+#include <stdlib.h>
 #include <ctype.h>
 #include <string.h>
 #include "common.h"
@@ -418,7 +419,10 @@ NextUnit (char **p)
        if(**p == '+') (*p)++, promoted++;
        if(**p >= 'a' && **p <= 'z' && (*p)[1]== '@') piece =*(*p)++ + 'A' - 'a'; else
        if(**p >= 'A' && **p <= 'Z') {
+            static char s[] = SUFFIXES;
+            char *q;
             piece = *(*p)++; // Note we could test for 2-byte non-ascii names here
+            if(q = strchr(s, **p)) (*p)++, piece += 64*(q - s + 1);
             if(**p == '/') slash = *(*p)++;
        }
         while(n < 4) {
@@ -489,9 +493,9 @@ NextUnit (char **p)
            else if(toY >= BOARD_HEIGHT || toY < 0)   return ImpossibleMove; // vert off-board to-square
            if(toX < BOARD_LEFT || toX >= BOARD_RGHT) return ImpossibleMove;
            if(piece) {
-               cl.pieceIn = CharToPiece(wom ? piece : ToLower(piece));
+               cl.pieceIn = CharToPiece(wom ? piece : piece + 'a' - 'A');
                if(cl.pieceIn == EmptySquare) return ImpossibleMove; // non-existent piece
-               if(promoted) cl.pieceIn = (ChessSquare) (CHUPROMOTED cl.pieceIn);
+               if(promoted) cl.pieceIn = (ChessSquare) (CHUPROMOTED(cl.pieceIn));
            } else cl.pieceIn = EmptySquare;
            if(separator == '@' || separator == '*') { // drop move. We only get here without from-square or promoted piece
                fromY = DROP_RANK; fromX = cl.pieceIn;
@@ -523,11 +527,11 @@ NextUnit (char **p)
                    ChessSquare realPiece = boards[yyboardindex][fromY][fromX];
                    // Note that Disambiguate does not work for illegal moves, but flags them as impossible
                    if(piece) { // check if correct piece indicated
-                       if(PieceToChar(realPiece) == '~') realPiece = (ChessSquare) (DEMOTED realPiece);
+                       if(PieceToChar(realPiece) == '~') realPiece = (ChessSquare) (DEMOTED(realPiece));
                        if(!(appData.icsActive && PieceToChar(realPiece) == '+') && // trust ICS if it moves promoted pieces
                           piece && realPiece != cl.pieceIn) return ImpossibleMove;
                    } else if(!separator && **p == '+') { // could be a protocol move, where bare '+' suffix means shogi-style promotion
-                       if(realPiece < (wom ?  WhiteCannon : BlackCannon) && PieceToChar(PROMOTED realPiece) == '+') // seems to be that
+                       if(realPiece < (wom ?  WhiteCannon : BlackCannon) && PieceToChar(PROMOTED(realPiece)) == '+') // seems to be that
                           currentMoveString[4] = cl.promoCharIn = *(*p)++; // append promochar after all
                    }
                    result = LegalityTest(boards[yyboardindex], PosFlags(yyboardindex), fromY, fromX, toY, toX, cl.promoCharIn);
@@ -616,12 +620,12 @@ badMove:// we failed to find algebraic move
                if (yyskipmoves) return (int) AmbiguousMove; /* not disambiguated */
 
                if (wom) {
-                   rf = 0;
-                   rt = 0;
+                   rf = castlingRank[0];
+                   rt = castlingRank[0];
                    king = WhiteKing;
                } else {
-                   rf = BOARD_HEIGHT-1;
-                   rt = BOARD_HEIGHT-1;
+                   rf = castlingRank[3];
+                   rt = castlingRank[3];
                    king = BlackKing;
                }
                ff = (BOARD_WIDTH-1)>>1; // this would be d-file
@@ -629,8 +633,12 @@ badMove:// we failed to find algebraic move
                    /* ICS wild castling */
                    ft = castlingType == 1 ? BOARD_LEFT+1 : (gameInfo.variant == VariantJanus ? BOARD_RGHT-2 : BOARD_RGHT-3);
                } else {
+                   char *q;
                    ff = BOARD_WIDTH>>1; // e-file
                    ft = castlingType == 1 ? BOARD_RGHT-2 : BOARD_LEFT+2;
+                   if(pieceDesc[king] && (q = strchr(pieceDesc[king], 'O'))) { // redefined to non-default King stride
+                       ft = (castlingType == 1 ? ff + atoi(q+1) : ff - atoi(q+1));
+                   }
                }
                if(PosFlags(0) & F_FRC_TYPE_CASTLING) {
                    if (wom) {