00001 #ifndef _GENERATER_ADD_EFFECT_WITH_EFFECT_TCC
00002 #define _GENERATER_ADD_EFFECT_WITH_EFFECT_TCC
00003
00004 #include "osl/move_generator/addEffectWithEffect.h"
00005 #include "osl/move_generator/open.h"
00006 #include "osl/move_generator/open.tcc"
00007 #include "osl/move_generator/pieceOnBoard.tcc"
00008 #include "osl/checkmate/king8Info.h"
00009
00010
00011
00012 namespace osl
00013 {
00014 namespace move_generator
00015 {
00016 namespace detail
00017 {
00030 template<osl::Player P,class Action>
00031 void generateMovePiecePtypeMask(const NumEffectState& state,Piece p,Square to,Piece toP,Action& action,unsigned int ptypeMask)
00032 {
00033 assert(p.isOnBoardByOwner<P>());
00034 assert(toP==state.pieceAt(to));
00035 Ptype ptype=p.ptype();
00036 Square from=p.square();
00037 if(canPromote(ptype) &&
00038 (to.canPromote<P>() || from.canPromote<P>())){
00039 Ptype pptype=osl::promote(ptype);
00040 if(((1<<pptype)&ptypeMask)!=0)
00041 action.unknownMove(from,to,toP,pptype,true,P);
00042 if(Move::ignoreUnpromote<P>(ptype,from,to)) return;
00043 }
00044
00045 if(((1<<ptype)&ptypeMask)!=0)
00046 action.unknownMove(p.square(),to,toP,ptype,false,P);
00047 }
00058 template<osl::Player P,class Action>
00059 void generateMoveToPtypeMaskWithPieceMask(const NumEffectState& state,Square to,Piece toP,Action& action,unsigned int ptypeMask,PieceMask pieceMask)
00060 {
00061 if(pieceMask.test(KingTraits<P>::index)){
00062 const Player altP=PlayerTraits<P>::opponent;
00063 if(!state.hasEffectAt<altP>(to)){
00064 action.unknownMove(state.kingSquare<P>(),to,toP,KING,false,P);
00065 }
00066 pieceMask.reset(KingTraits<P>::index);
00067 }
00068 while (pieceMask.any()){
00069 const int num=pieceMask.takeOneBit();
00070 Piece p=state.pieceOf(num);
00071 if(state.pinOrOpen(P).test(num)){
00072 Direction d=state.pinnedDir<P>(p);
00073 Direction d1=Board_Table.template getShort8Unsafe<P>(p.square(),to);
00074 if(primDir(d)!=primDirUnsafe(d1)) continue;
00075 }
00076 generateMovePiecePtypeMask<P,Action>(state,p,to,toP,action,ptypeMask);
00077 }
00078 }
00079 template<osl::Player P,class Action>
00080 void generateMoveToPtypeMask(const NumEffectState& state,Square to,Piece toP,Action& action,unsigned int ptypeMask)
00081 {
00082 PieceMask pieceMask=state.piecesOnBoard(P)&state.effectSetAt(to);
00083 const Player altP=PlayerTraits<P>::opponent;
00084 pieceMask.reset(KingTraits<P>::index);
00085 pieceMask &= ~state.pinOrOpen(altP);
00086 generateMoveToPtypeMaskWithPieceMask<P,Action>(state,to,toP,action,ptypeMask,pieceMask);
00087 }
00088 #ifndef GENERATE_PAWNDROP_CHECKMATE
00089
00092 template<osl::Player P>
00093 bool
00094 #ifdef __GNUC__
00095 __attribute__ ((pure))
00096 #endif
00097 blockingU(const NumEffectState& state,Square pos)
00098 {
00099 const osl::Player altP=PlayerTraits<P>::opponent;
00100 NumBitmapEffect effect=state.effectSetAt(pos);
00101 mask_t mask=(effect.getMask(1)& NumBitmapEffect::longEffectMask());
00102 mask&=state.piecesOnBoard(P).getMask(1)<<8;
00103 while(mask.any()){
00104 int num=mask.takeOneBit()+NumBitmapEffect::longToNumOffset;
00105 Square from=state.pieceOf(num).square();
00106 if( (P==BLACK ? from.y()>=pos.y() : pos.y()>=from.y()) ){
00107 Square shadowPos=pos+Board_Table.getShortOffset(Offset32(pos,from));
00108 assert((P==BLACK ? shadowPos.y()<=pos.y() : pos.y()<=shadowPos.y()) );
00109 Piece p=state.pieceAt(shadowPos);
00110 if(p.canMoveOn<altP>() && !state.hasMultipleEffectAt(P,shadowPos)){
00111 return true;
00112 }
00113 }
00114 }
00115 return false;
00116 }
00117 #endif
00118
00124 template<osl::Player P,int DirType,class Action>
00125 void generateDir(const NumEffectState& state,Square target,Action& action,bool& hasPawnCheckmate,Offset dirOffset,Direction Dir,Direction primDir,int ptypeMaskNotKing)
00126 {
00127 const Player altP=PlayerTraits<P>::opponent;
00128 Square pos=target-dirOffset;
00129 if(!pos.isOnBoard()) return;
00130 Piece p=state.pieceAt(pos);
00131 if(p.isOnBoardByOwner<P>()){
00132 if(DirType==0 && state.hasLongEffectAt<LANCE>(P,pos)){
00133 PieceOnBoard<Action>::template generate<P,true>(state,p,action,1<<primDir);
00134 }
00135 return;
00136 }
00137 if((state.Iking8Info(altP)&(1ull<<(40+Dir)))!=0){
00138
00139
00140 generateMoveToPtypeMask<P,Action>(state,pos,p,action,
00141 ptypeMaskNotKing);
00142 }
00143 if(DirType !=0) return;
00144 if(p.isEmpty()){
00145 Square pos1=state.kingMobilityOfPlayer(altP,Dir);
00146 mask_t lance_mask=state.longEffectAt<LANCE>(pos1,P);
00147 if(lance_mask.any()){
00148 Piece p1=state.pieceAt(pos1);
00149 if(p1.isOnBoardByOwner<P>()){
00150 PieceOnBoard<Action>::template generate<P,true>(state,p1,action,1<<primDir);
00151
00152 if(state.hasEffectByPiece(p1,pos)){
00153 PieceOnBoard<Action>::template generatePiece<P>(state,p1,pos,Piece::EMPTY(),action);
00154 }
00155 }
00156 else if(p1.isOnBoardByOwner<altP>()){
00157 assert(!lance_mask.hasMultipleBit());
00158 int num=lance_mask.bsf()+PtypeFuns<LANCE>::indexNum*32;
00159 Piece p2=state.pieceOf(num);
00160 if(!state.pinOrOpen(P).test(num) ||
00161 state.kingSquare<P>().isUD(p2.square())){
00162 action.unknownMove(p2.square(),pos1,p1,LANCE,false,P);
00163 }
00164 }
00165 }
00166
00167
00168 if(! state.isPawnMaskSet<P>(target.x()) &&
00169 state.hasPieceOnStand<PAWN>(P)){
00170
00171 #ifndef GENERATE_PAWNDROP_CHECKMATE
00172 if(((state.Iking8Info(altP)&(0xff00ull|(1ull<<(U+24))))^(1ull<<(U+24)))!=0 || blockingU<P>(state,pos))
00173 action.dropMove(pos,PAWN,P);
00174 else
00175 hasPawnCheckmate=true;
00176 #else
00177 action.dropMove(pos,PAWN,P);
00178 #endif
00179 }
00180 if(state.hasPieceOnStand<LANCE>(P)){
00181 action.dropMove(pos,LANCE,P);
00182 for(pos-=DirectionPlayerTraits<U,P>::offset();
00183 pos!=pos1;pos-=DirectionPlayerTraits<U,P>::offset()){
00184 action.dropMove(pos,LANCE,P);
00185 }
00186 }
00187 }
00188 }
00189
00190 template<osl::Player P,int DirType,class Action,Direction Dir>
00191 void generateDir(const NumEffectState& state,Square target,Action& action,bool& hasPawnCheckmate)
00192 {
00193 generateDir<P,DirType,Action>(state,target,action,hasPawnCheckmate,
00194 DirectionPlayerTraits<Dir,P>::offset(),Dir,DirectionTraits<Dir>::primDir,DirectionTraits<Dir>::ptypeMaskNotKing);
00195 }
00202 template<osl::Player P,int DirType,class Action>
00203 void generateDirNotKing(const NumEffectState& state,Square target,Action& action,CArray<unsigned char,8>& pieceMobility, int& spaces, PieceMask const& notPieceMask,Offset dirOffset,Direction Dir,Direction primDir,int ptypeMask,Direction dirByBlack
00204 )
00205 {
00206 const Player altP=PlayerTraits<P>::opponent;
00207 Square pos=target-dirOffset;
00208 if(!pos.isOnBoard()){
00209 pieceMobility[dirByBlack]=pos.uintValue();
00210 return;
00211 }
00212 Piece p=state.pieceAt(pos);
00213 if(p.canMoveOn<P>()){
00214
00215 const PieceMask pieceMask=state.piecesOnBoard(P)&state.effectSetAt(pos)¬PieceMask & ~state.effectSetAt(target);
00216 if(pieceMask.any())
00217 detail:: template generateMoveToPtypeMaskWithPieceMask<P,Action>(state,pos,p,action,
00218 ptypeMask,pieceMask);
00219 }
00220 Square nextSquare=pos;
00221 if(p.isEmpty()){
00222 spaces|=(1u<<Dir);
00223 if(DirType==0 && ! state.isPawnMaskSet<P>(target.x()) &&
00224 state.hasPieceOnStand<PAWN>(P))
00225 action.dropMove(pos,PAWN,P);
00226 do{
00227 pos-=dirOffset;
00228 p=state.pieceAt(pos);
00229 } while(p.isEmpty());
00230 }
00231 if(p.isOnBoardByOwner<P>() && state.hasEffectByPiece(p,target)){
00232 for(;;){
00233 Piece p1=state.findLongAttackAt(P,p,inverse(Dir));
00234 if(!p1.isOnBoardByOwner<P>()){
00235 break;
00236 }
00237 p=p1;
00238 }
00239 pos=p.square()-dirOffset;
00240 while((p=state.pieceAt(pos)).isEmpty())
00241 pos-=dirOffset;
00242 }
00243 else if (p.isOnBoardByOwner<altP>() && state.hasEffectByPiece(p,target)){
00244
00245 Piece p1=state.findLongAttackAt(altP,p,Dir);
00246 if(p1.isOnBoardByOwner<P>()){
00247 if(pos!=nextSquare){
00248 if(p1.ptype()==LANCE){
00249 int num=p1.number();
00250 if(!state.pinOrOpen(P).test(num) ||
00251 p1.square().isUD(state.kingSquare<P>())){
00252 action.unknownMove(p1.square(),pos,p,LANCE,false,P);
00253 }
00254 }
00255 else
00256 PieceOnBoard<Action>::template generatePiece<P>(state,p1,pos,p,action);
00257 }
00258 pos=p1.square();
00259 p=p1;
00260 }
00261 else{
00262 pos=p.square()-dirOffset;
00263 while((p=state.pieceAt(pos)).isEmpty())
00264 pos-=dirOffset;
00265 }
00266 }
00267 pieceMobility[dirByBlack]=pos.uintValue();
00268 if(p.isOnBoardByOwner<P>()){
00269 Piece p1=state.findLongAttackAt(P,p,inverse(Dir));
00270 if(p1.isOnBoardByOwner<P>()){
00271 Open<Action>::template generate<P>(state,p,action,target,primDir);
00272 }
00273 }
00274 else if(p.isOnBoardByOwner<altP>() && pos!=nextSquare){
00275 if(DirType==0){
00276 mask_t lance_mask=state.longEffectAt<LANCE>(pos,P);
00277 if(lance_mask.any()){
00278 assert(!lance_mask.hasMultipleBit());
00279 int num=lance_mask.bsf()+PtypeFuns<LANCE>::indexNum*32;
00280 Piece p2=state.pieceOf(num);
00281 if(!state.pinOrOpen(P).test(num) ||
00282 state.kingSquare<P>().isUD(p2.square())){
00283 action.unknownMove(p2.square(),pos,p,LANCE,false,P);
00284 }
00285 }
00286 }
00287 if(DirType <= 1){
00288 mask_t rook_mask=state.allEffectAt<ROOK>(P,pos);
00289 while(rook_mask.any()){
00290 int num=rook_mask.takeOneBit()+PtypeFuns<ROOK>::indexNum*32;
00291 Piece p2=state.pieceOf(num);
00292 if(p2.square()==target) continue;
00293 PieceOnBoard<Action>::template generatePiece<P>(state,p2,pos,p,action);
00294 }
00295 }
00296 if(DirType == 2){
00297 mask_t bishop_mask=state.allEffectAt<BISHOP>(P,pos);
00298
00299 while(bishop_mask.any()){
00300 int num=bishop_mask.takeOneBit()+PtypeFuns<BISHOP>::indexNum*32;
00301 Piece p2=state.pieceOf(num);
00302 if(p2.square()==target) continue;
00303 PieceOnBoard<Action>::template generatePiece<P>(state,p2,pos,p,action);
00304 }
00305 }
00306 }
00307
00308
00309
00310 if(DirType == 0){
00311 if(state.hasPieceOnStand<LANCE>(P)){
00312 for(pos+=DirectionPlayerTraits<U,P>::offset();
00313 pos!=target;pos+=DirectionPlayerTraits<U,P>::offset()){
00314 if(state.pieceAt(pos).isEmpty())
00315 action.dropMove(pos,LANCE,P);
00316 }
00317 }
00318 }
00319 }
00320
00321 template<osl::Player P,int DirType,class Action,Direction Dir>
00322 void generateDirNotKing(const NumEffectState& state,Square target,Action& action,CArray<unsigned char,8>& pieceMobility, int& spaces, PieceMask const& notPieceMask)
00323 {
00324 generateDirNotKing<P,DirType,Action>(state,target,action,pieceMobility,spaces,notPieceMask,
00325 DirectionPlayerTraits<Dir,P>::offset(),Dir,DirectionTraits<Dir>::primDir,DirectionTraits<Dir>::ptypeMask,DirectionPlayerTraits<Dir,P>::directionByBlack);
00326
00327 }
00328 template<osl::Player P,osl::Direction Dir,class Action,bool hasKnight>
00329 void generateKnightDir(const NumEffectState& state,Square target,Action& action)
00330 {
00331 Square pos=target-DirectionPlayerTraits<Dir,P>::offset();
00332 if(!pos.isOnBoard()) return;
00333 Piece p=state.pieceAt(pos);
00334 if(!p.canMoveOn<P>()) return;
00335 mask_t mask=state.allEffectAt<KNIGHT>(P, pos);
00336 mask &= ~state.promotedPieces().getMask<KNIGHT>();
00337
00338 mask &= ~state.pinOrOpen(P).getMask(PtypeFuns<KNIGHT>::indexNum);
00339 while(mask.any()){
00340 const int num = mask.takeOneBit()+PtypeFuns<KNIGHT>::indexNum*32;
00341 Piece p1=state.pieceOf(num);
00342 action.unknownMove(p1.square(),pos,p,KNIGHT,false,P);
00343 }
00344 if(hasKnight && p.isEmpty()){
00345 action.dropMove(pos,KNIGHT,P);
00346 }
00347 }
00348 template<osl::Player P,class Action>
00349 void generateKnightAll(const NumEffectState& state,Square target,Action& action)
00350 {
00351 if(state.hasPieceOnStand<KNIGHT>(P)){
00352 detail::generateKnightDir<P,UUL,Action,true>(state,target,action);
00353 detail::generateKnightDir<P,UUR,Action,true>(state,target,action);
00354 }
00355 else{
00356 detail::generateKnightDir<P,UUL,Action,false>(state,target,action);
00357 detail::generateKnightDir<P,UUR,Action,false>(state,target,action);
00358 }
00359 }
00360 template <osl::Player P,class Action>
00361 void generateDrop(Square target,Action& action,int spaceMask,osl::Ptype T,int dirMask,Offset offset)
00362 {
00363 if((spaceMask&dirMask)!=0){
00364 Square pos=target-offset;
00365 action.dropMove(pos,T,P);
00366 }
00367 }
00368 template <osl::Player P,class Action,Direction Dir>
00369 void generateDropDir(Square target,Action& action,int spaceMask,osl::Ptype T)
00370 {
00371 generateDrop<P,Action>(target,action,spaceMask,T,(1<<Dir),DirectionPlayerTraits<Dir,P>::offset());
00372 }
00373 template<Player P,class Action,bool mustCareSilver>
00374 void generateOpenOrCapture(const NumEffectState& state,Square target,Piece p,int num,Action& action)
00375 {
00376
00377 Direction d=Board_Table.template getShort8<P>(p.square(),target);
00378 Square mid=state.mobilityOf((P==BLACK ? d : inverse(d)),num);
00379 assert(mid.isOnBoard());
00380 const Player altP=PlayerTraits<P>::opponent;
00381 Square mid1=state.kingMobilityOfPlayer(altP,d);
00382 if(mid==mid1){
00383 Piece p1=state.pieceAt(mid);
00384 assert(p1.isPiece());
00385 Square target_next=target-Board_Table.getShort8OffsetUnsafe(p.square(),target);
00386 if((P==BLACK ? p1.pieceIsBlack() : !p1.pieceIsBlack())){
00387
00388 PieceOnBoard<Action>::template generate<P,true>(state,p1,action,(1<<primDir(d)));
00389
00390 if(state.hasEffectByPiece(p1,target_next)){
00391
00392 if(mustCareSilver && p1.ptype()==SILVER &&
00393 (P==BLACK ? target.y()>mid.y() : target.y()<mid.y())){
00394
00395 if(!state.pinOrOpen(P).test(p1.number())){
00396 action.unknownMove(mid,target_next,Piece::EMPTY(),SILVER,false,P);
00397 }
00398 }
00399 else
00400 PieceOnBoard<Action>::template generatePiece<P>(state,p1,target_next,Piece::EMPTY(),action);
00401 }
00402 }
00403 else{
00404
00405 if(mid==target_next)
00406 return;
00407 PieceOnBoard<Action>::template generatePiece<P>(state,p,mid,p1,action);
00408 }
00409 }
00410 }
00411
00412 template<osl::Player P,class Action>
00413 void generateRookLongMove(const NumEffectState& state,Square target,Action& action)
00414 {
00415 const Player altP=PlayerTraits<P>::opponent;
00416 for(int num=PtypeTraits<ROOK>::indexMin;num<PtypeTraits<ROOK>::indexLimit;num++){
00417
00418 if(state.pinOrOpen(altP).test(num)) continue;
00419 Piece p=state.pieceOf(num);
00420 if(!p.isOnBoardByOwner<P>()) continue;
00421 if(target.isULRD(p.square())){
00422 generateOpenOrCapture<P,Action,false>(state,target,p,num,action);
00423 continue;
00424 }
00425 int target_x=target.x();
00426 int target_y=target.y();
00427 int rook_x=p.square().x();
00428 int rook_y=p.square().y();
00429 if(p.isPromoted()){
00430 if((unsigned int)(target_x-rook_x+1)>2u){
00431 if((unsigned int)(target_y-rook_y+1)>2u){
00432 {
00433 Square pos(rook_x,target_y);
00434 Piece p1=state.pieceAt(pos);
00435 if(state.effectSetAt(pos).test(num) &&
00436 p1.canMoveOn<P>() &&
00437 state.kingMobilityAbs(altP,R).uintValue() >= pos.uintValue() &&
00438 pos.uintValue() >= state.kingMobilityAbs(altP,L).uintValue() &&
00439 (!state.pinOrOpen(P).test(num) ||
00440 p.square().isUD(state.kingSquare<P>()))
00441 ){
00442 action.unknownMove(p.square(),pos,p1,PROOK,false,P);
00443 }
00444 }
00445 {
00446 Square pos(target_x,rook_y);
00447 Piece p1=state.pieceAt(pos);
00448 if(state.effectSetAt(pos).test(num) &&
00449 p1.canMoveOn<P>() &&
00450 state.kingMobilityAbs(altP,U).uintValue() >= pos.uintValue() &&
00451 pos.uintValue() >= state.kingMobilityAbs(altP,D).uintValue() &&
00452 (!state.pinOrOpen(P).test(num) ||
00453 p.square().isLR(state.kingSquare<P>()))
00454 ){
00455 action.unknownMove(p.square(),pos,p1,PROOK,false,P);
00456 }
00457 }
00458 }
00459 else{
00460 int min_x=state.kingMobilityAbs(altP,L).x();
00461 int max_x=state.kingMobilityAbs(altP,R).x();
00462 if(target_x>rook_x) max_x=target_x-2;
00463 else min_x=target_x+2;
00464 min_x=std::max(min_x,rook_x-1);
00465 max_x=std::min(max_x,rook_x+1);
00466 for(int x=min_x;x<=max_x;x++){
00467 Square pos=Square::makeNoCheck(x,target_y);
00468 Piece p1=state.pieceAt(pos);
00469 if(p1.canMoveOn<P>())
00470 PieceOnBoard<Action>::template generatePiecePtype<P,PROOK>(state,p,pos,p1,action);
00471 }
00472 }
00473 }
00474 else if((unsigned int)(target_y-rook_y+1)>2u){
00475 int min_y=state.kingMobilityAbs(altP,D).y();
00476 int max_y=state.kingMobilityAbs(altP,U).y();
00477 if(target_y>rook_y) max_y=target_y-2;
00478 else min_y=target_y+2;
00479 min_y=std::max(min_y,rook_y-1);
00480 max_y=std::min(max_y,rook_y+1);
00481 for(int y=min_y;y<=max_y;y++){
00482 Square pos=Square::makeNoCheck(target_x,y);
00483 Piece p1=state.pieceAt(pos);
00484 if(p1.canMoveOn<P>())
00485 PieceOnBoard<Action>::template generatePiecePtype<P,PROOK>(state,p,pos,p1,action);
00486 }
00487 }
00488 }
00489 else{
00490
00491 if((unsigned int)(target_x-rook_x+1)>2u){
00492 Square pos(rook_x,target_y);
00493 Piece p1=state.pieceAt(pos);
00494 if(state.effectSetAt(pos).test(num) &&
00495 p1.canMoveOn<P>() &&
00496 state.kingMobilityAbs(altP,R).uintValue() >= pos.uintValue() &&
00497 pos.uintValue() >= state.kingMobilityAbs(altP,L).uintValue() &&
00498 (!state.pinOrOpen(P).test(num) ||
00499 p.square().isUD(state.kingSquare<P>()))
00500 ){
00501 if(Square::canPromoteY<P>(rook_y) || Square::canPromoteY<P>(target_y)){
00502 action.unknownMove(p.square(),pos,p1,PROOK,true,P);
00503 }
00504 else action.unknownMove(p.square(),pos,p1,ROOK,false,P);
00505 }
00506 }
00507
00508 if((unsigned int)(target_y-rook_y+1)>2u){
00509 Square pos(target_x,rook_y);
00510 Piece p1=state.pieceAt(pos);
00511 if(state.effectSetAt(pos).test(num) &&
00512 p1.canMoveOn<P>() &&
00513 state.kingMobilityAbs(altP,U).uintValue() >= pos.uintValue() &&
00514 pos.uintValue() >= state.kingMobilityAbs(altP,D).uintValue() &&
00515 (!state.pinOrOpen(P).test(num) ||
00516 p.square().isLR(state.kingSquare<P>()))
00517 ){
00518 if(Square::canPromoteY<P>(rook_y)){
00519 action.unknownMove(p.square(),pos,p1,PROOK,true,P);
00520 }
00521 else
00522 action.unknownMove(p.square(),pos,p1,ROOK,false,P);
00523 }
00524 }
00525 }
00526 }
00527 }
00528 template<osl::Player P,class Action>
00529 void generateRookLongMoveNotKing(const NumEffectState& state,Square target,Action& action,CArray<unsigned char,8> const& pieceMobility)
00530 {
00531 for(int num=PtypeTraits<ROOK>::indexMin;num<PtypeTraits<ROOK>::indexLimit;num++){
00532 Piece p=state.pieceOf(num);
00533 if(!p.isOnBoardByOwner<P>()) continue;
00534 if(target.isULRD(p.square())){
00535 continue;
00536 }
00537 int dirMask=0;
00538 if(state.pin(P).test(num)){
00539 Direction d=state.pinnedDir<P>(p);
00540 dirMask=(~(1<<primDir(d)));
00541 }
00542 int target_x=target.x();
00543 int target_y=target.y();
00544 int rook_x=p.square().x();
00545 int rook_y=p.square().y();
00546 if(p.isPromoted()){
00547 if((unsigned int)(target_x-rook_x+1)>2u){
00548 if((unsigned int)(target_y-rook_y+1)>2u){
00549 {
00550 Square pos(rook_x,target_y);
00551 Piece p1=state.pieceAt(pos);
00552 if(p1.canMoveOn<P>() &&
00553 pieceMobility[R] > pos.uintValue() &&
00554 pos.uintValue() > pieceMobility[L] &&
00555 (dirMask&(1<<U))==0 &&
00556 state.effectSetAt(pos).test(num)
00557 ){
00558 action.unknownMove(p.square(),pos,p1,PROOK,false,P);
00559 }
00560 }
00561 {
00562 Square pos(target_x,rook_y);
00563 Piece p1=state.pieceAt(pos);
00564 if(p1.canMoveOn<P>() &&
00565 pieceMobility[U] > pos.uintValue() &&
00566 pos.uintValue() > pieceMobility[D] &&
00567 (dirMask&(1<<L))==0 &&
00568 state.effectSetAt(pos).test(num)){
00569 action.unknownMove(p.square(),pos,p1,PROOK,false,P);
00570 }
00571 }
00572 }
00573 else{
00574 int min_x=Square::makeDirect(pieceMobility[L]).x()+1;
00575 int max_x=Square::makeDirect(pieceMobility[R]).x()-1;
00576 if(target_x>rook_x) max_x=target_x-2;
00577 else min_x=target_x+2;
00578 min_x=std::max(min_x,rook_x-1);
00579 max_x=std::min(max_x,rook_x+1);
00580 for(int x=min_x;x<=max_x;x++){
00581 Square pos=Square::makeNoCheck(x,target_y);
00582 if(((1<<primDirUnsafe(Board_Table.getShort8Unsafe<P>(p.square(),pos)))&dirMask)!=0) continue;
00583 Piece p1=state.pieceAt(pos);
00584 if(p1.canMoveOn<P>())
00585 action.unknownMove(p.square(),pos,p1,PROOK,false,P);
00586 }
00587 }
00588 }
00589 else if((unsigned int)(target_y-rook_y+1)>2u){
00590 int min_y=Square::makeDirect(pieceMobility[D]).y()+1;
00591 int max_y=Square::makeDirect(pieceMobility[U]).y()-1;
00592 if(target_y>rook_y) max_y=target_y-2;
00593 else min_y=target_y+2;
00594 min_y=std::max(min_y,rook_y-1);
00595 max_y=std::min(max_y,rook_y+1);
00596 for(int y=min_y;y<=max_y;y++){
00597 Square pos=Square::makeNoCheck(target_x,y);
00598 if(((1<<primDirUnsafe(Board_Table.getShort8Unsafe<P>(p.square(),pos)))&dirMask)!=0) continue;
00599 Piece p1=state.pieceAt(pos);
00600 if(p1.canMoveOn<P>())
00601 action.unknownMove(p.square(),pos,p1,PROOK,false,P);
00602 }
00603 }
00604 }
00605 else{
00606
00607 if((unsigned int)(target_x-rook_x+1)>2u){
00608 Square pos(rook_x,target_y);
00609 Piece p1=state.pieceAt(pos);
00610 if(p1.canMoveOn<P>() &&
00611 pieceMobility[R] > pos.uintValue() &&
00612 pos.uintValue() > pieceMobility[L] &&
00613 (dirMask&(1<<U))==0 &&
00614 state.effectSetAt(pos).test(num)
00615 ){
00616 if(Square::canPromoteY<P>(rook_y) || Square::canPromoteY<P>(target_y)){
00617 action.unknownMove(p.square(),pos,p1,PROOK,true,P);
00618 }
00619 else
00620 action.unknownMove(p.square(),pos,p1,ROOK,false,P);
00621 }
00622 }
00623
00624 if((unsigned int)(target_y-rook_y+1)>2u){
00625 Square pos(target_x,rook_y);
00626 Piece p1=state.pieceAt(pos);
00627 if(p1.template canMoveOn<P>() &&
00628 pieceMobility[U] > pos.uintValue() &&
00629 pos.uintValue() > pieceMobility[D] &&
00630 (dirMask&(1<<L))==0 &&
00631 state.effectSetAt(pos).test(num)
00632 ){
00633 if(Square::canPromoteY<P>(rook_y)){
00634 action.unknownMove(p.square(),pos,p1,PROOK,true,P);
00635 }
00636 else
00637 action.unknownMove(p.square(),pos,p1,ROOK,false,P);
00638 }
00639 }
00640 }
00641 }
00642 }
00643 template<Player P,Ptype T,class Action>
00644 void generateBishopLongMove(const NumEffectState& state,Square target,Action& action,Piece p,int num)
00645 {
00646 const Player altP=PlayerTraits<P>::opponent;
00647 int target_x=target.x();
00648 int target_y=target.y();
00649 int target_xPy=target_x+target_y;
00650 int target_xMy=target_x-target_y;
00651 int bishop_x=p.square().x();
00652 int bishop_y=p.square().y();
00653 int bishop_xPy=bishop_x+bishop_y;
00654 int bishop_xMy=bishop_x-bishop_y;
00655 if(((target_xPy^bishop_xPy)&1)!=0){
00656 if(T==BISHOP) return;
00657
00658 if((unsigned int)(target_xPy-bishop_xPy+1)<=2u){
00659 Square ul=state.kingMobilityAbs(altP,UL);
00660 Square dr=state.kingMobilityAbs(altP,DR);
00661 int min_xMy=ul.x()-ul.y();
00662 int max_xMy=dr.x()-dr.y();
00663 if(target_xMy>bishop_xMy) max_xMy=target_xMy-4;
00664 else min_xMy=target_xMy+4;
00665 min_xMy=std::max(min_xMy,bishop_xMy-1);
00666 max_xMy=std::min(max_xMy,bishop_xMy+1);
00667 for(int xMy=min_xMy;xMy<=max_xMy;xMy+=2){
00668 int pos_x=(target_xPy+xMy)>>1;
00669 int pos_y=(target_xPy-xMy)>>1;
00670 Square pos=Square::makeNoCheck(pos_x,pos_y);
00671 Piece p1=state.pieceAt(pos);
00672 if(p1.canMoveOn<P>())
00673 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00674 }
00675 }
00676 else if((unsigned int)(target_xMy-bishop_xMy+1)<=2u){
00677 Square dl=state.kingMobilityAbs(altP,DL);
00678 Square ur=state.kingMobilityAbs(altP,UR);
00679 int min_xPy=dl.x()+dl.y();
00680 int max_xPy=ur.x()+ur.y();
00681 if(target_xPy>bishop_xPy) max_xPy=target_xPy-4;
00682 else min_xPy=target_xPy+4;
00683 min_xPy=std::max(min_xPy,bishop_xPy-1);
00684 max_xPy=std::min(max_xPy,bishop_xPy+1);
00685 for(int xPy=min_xPy;xPy<=max_xPy;xPy+=2){
00686 int pos_x=(xPy+target_xMy)>>1;
00687 int pos_y=(xPy-target_xMy)>>1;
00688 Square pos=Square::makeNoCheck(pos_x,pos_y);
00689 Piece p1=state.pieceAt(pos);
00690 if(p1.canMoveOn<P>())
00691 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00692 }
00693 }
00694 return;
00695 }
00696
00697 if((unsigned int)(target_xPy-bishop_xPy+2)>4u){
00698 int pos_x=(bishop_xPy+target_xMy)>>1;
00699 int pos_y=(bishop_xPy-target_xMy)>>1;
00700 Square pos=Square::makeNoCheck(pos_x,pos_y);
00701 if(pos.isOnBoard()){
00702 Piece p1=state.pieceAt(pos);
00703 if(state.effectSetAt(pos).test(num) &&
00704 p1.canMoveOn<P>() &&
00705 state.kingMobilityAbs(altP,UR).uintValue() >= pos.uintValue() &&
00706 pos.uintValue() >= state.kingMobilityAbs(altP,DL).uintValue()
00707 ){
00708 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00709 }
00710 }
00711 }
00712 else if(target_xPy==bishop_xPy){
00713 generateOpenOrCapture<P,Action,true>(state,target,p,num,action);
00714 return;
00715 }
00716
00717 if((unsigned int)(target_xMy-bishop_xMy+2)>4u){
00718 int pos_x=(target_xPy+bishop_xMy)>>1;
00719 int pos_y=(target_xPy-bishop_xMy)>>1;
00720 Square pos=Square::makeNoCheck(pos_x,pos_y);
00721 if(pos.isOnBoard()){
00722 Piece p1=state.pieceAt(pos);
00723 if(state.effectSetAt(pos).test(num) &&
00724 p1.canMoveOn<P>() &&
00725 state.kingMobilityAbs(altP,DR).uintValue() >= pos.uintValue() &&
00726 pos.uintValue() >= state.kingMobilityAbs(altP,UL).uintValue()
00727 ){
00728 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00729 }
00730 }
00731 }
00732 else if(target_xMy==bishop_xMy){
00733 generateOpenOrCapture<P,Action,true>(state,target,p,num,action);
00734 return;
00735 }
00736
00737 }
00738 template<osl::Player P,Ptype T,class Action>
00739 void generateBishopLongMoveNotKing(const NumEffectState& state,Square target,Action& action,CArray<unsigned char,8> const& pieceMobility,Piece p,int num)
00740 {
00741 int target_x=target.x();
00742 int target_y=target.y();
00743 int target_xPy=target_x+target_y;
00744 int target_xMy=target_x-target_y;
00745 int bishop_x=p.square().x();
00746 int bishop_y=p.square().y();
00747 int bishop_xPy=bishop_x+bishop_y;
00748 int bishop_xMy=bishop_x-bishop_y;
00749 if(((target_xPy^bishop_xPy)&1)!=0){
00750 if(T!=PBISHOP) return;
00751
00752 if((unsigned int)(target_xPy-bishop_xPy+1)<=2u){
00753 Square ul=Square::makeDirect(pieceMobility[UL]);
00754 Square dr=Square::makeDirect(pieceMobility[DR]);
00755 int min_xMy=ul.x()-ul.y()+2;
00756 int max_xMy=dr.x()-dr.y()-2;
00757 if(target_xMy>bishop_xMy) max_xMy=target_xMy-4;
00758 else min_xMy=target_xMy+4;
00759 min_xMy=std::max(min_xMy,bishop_xMy-1);
00760 max_xMy=std::min(max_xMy,bishop_xMy+1);
00761 for(int xMy=min_xMy;xMy<=max_xMy;xMy+=2){
00762 int pos_x=(target_xPy+xMy)>>1;
00763 int pos_y=(target_xPy-xMy)>>1;
00764 Square pos=Square::makeNoCheck(pos_x,pos_y);
00765 Piece p1=state.pieceAt(pos);
00766 if(p1.canMoveOn<P>())
00767 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00768 }
00769 return;
00770 }
00771 else if((unsigned int)(target_xMy-bishop_xMy+1)<=2u){
00772 Square dl=Square::makeDirect(pieceMobility[DL]);
00773 Square ur=Square::makeDirect(pieceMobility[UR]);
00774 int min_xPy=dl.x()+dl.y()+2;
00775 int max_xPy=ur.x()+ur.y()-2;
00776 if(target_xPy>bishop_xPy) max_xPy=target_xPy-4;
00777 else min_xPy=target_xPy+4;
00778 min_xPy=std::max(min_xPy,bishop_xPy-1);
00779 max_xPy=std::min(max_xPy,bishop_xPy+1);
00780 for(int xPy=min_xPy;xPy<=max_xPy;xPy+=2){
00781 int pos_x=(xPy+target_xMy)>>1;
00782 int pos_y=(xPy-target_xMy)>>1;
00783 Square pos=Square::makeNoCheck(pos_x,pos_y);
00784 Piece p1=state.pieceAt(pos);
00785 if(p1.canMoveOn<P>())
00786 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00787 }
00788 }
00789 return;
00790 }
00791
00792 if((unsigned int)(target_xPy-bishop_xPy+2)>4u){
00793 int pos_x=(bishop_xPy+target_xMy)>>1;
00794 int pos_y=(bishop_xPy-target_xMy)>>1;
00795 Square pos=Square::makeNoCheck(pos_x,pos_y);
00796 if(pos.isOnBoard()){
00797 if(pieceMobility[UR] > pos.uintValue() &&
00798 pos.uintValue() > pieceMobility[DL] &&
00799 state.effectSetAt(pos).test(num)){
00800 Piece p1=state.pieceAt(pos);
00801 if(p1.canMoveOn<P>())
00802 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00803 }
00804 }
00805 }
00806
00807 if((unsigned int)(target_xMy-bishop_xMy+2)>4u){
00808 int pos_x=(target_xPy+bishop_xMy)>>1;
00809 int pos_y=(target_xPy-bishop_xMy)>>1;
00810 Square pos=Square::makeNoCheck(pos_x,pos_y);
00811 if(pos.isOnBoard()){
00812 if(pieceMobility[DR] > pos.uintValue() &&
00813 pos.uintValue() > pieceMobility[UL] &&
00814 state.effectSetAt(pos).test(num)
00815 ){
00816 Piece p1=state.pieceAt(pos);
00817 if(p1.canMoveOn<P>())
00818 PieceOnBoard<Action>::template generatePiecePtype<P,T>(state,p,pos,p1,action);
00819 }
00820 }
00821 }
00822 }
00823
00824 template<Player P,class Action>
00825 void generateDropGold(const NumEffectState& state,Square target,Action& action,int spaces)
00826 {
00827 if(!state.hasPieceOnStand<GOLD>(P)) return;
00828 unsigned int gold_mask=spaces&((1<<U)|(1<<UR)|(1<<UL)|(1<<L)|(1<<R)|(1<<D));
00829 if(gold_mask==0) return;
00830 generateDropDir<P,Action,U>(target,action,gold_mask,GOLD);
00831 generateDropDir<P,Action,UL>(target,action,gold_mask,GOLD);
00832 generateDropDir<P,Action,UR>(target,action,gold_mask,GOLD);
00833 generateDropDir<P,Action,L>(target,action,gold_mask,GOLD);
00834 generateDropDir<P,Action,R>(target,action,gold_mask,GOLD);
00835 generateDropDir<P,Action,D>(target,action,gold_mask,GOLD);
00836 }
00837 template<Player P,class Action>
00838 void generateDropSilver(const NumEffectState& state,Square target,Action& action,int spaces)
00839 {
00840 if(!state.hasPieceOnStand<SILVER>(P)) return;
00841 unsigned int silver_mask=spaces&((1<<U)|(1<<UR)|(1<<UL)|(1<<DL)|(1<<DR));
00842 if(silver_mask ==0) return;
00843
00844 generateDropDir<P,Action,DL>(target,action,silver_mask,SILVER);
00845 generateDropDir<P,Action,DR>(target,action,silver_mask,SILVER);
00846 generateDropDir<P,Action,U>(target,action,silver_mask,SILVER);
00847 generateDropDir<P,Action,UL>(target,action,silver_mask,SILVER);
00848 generateDropDir<P,Action,UR>(target,action,silver_mask,SILVER);
00849 }
00853 template<Player P,class Action,bool allEmpty>
00854 void generateDropBishop(const NumEffectState& state,Square target,Action& action,Square ul,Square dr,Square ur,Square dl)
00855 {
00856 for(Square pos=dl+DirectionPlayerTraits<DL,P>::offset();
00857 pos!=target;pos+=DirectionPlayerTraits<DL,P>::offset())
00858 if(allEmpty || state.pieceAt(pos).isEmpty())
00859 action.dropMove(pos,BISHOP,P);
00860 for(Square pos=dr-DirectionPlayerTraits<UL,P>::offset();
00861 pos!=target;pos-=DirectionPlayerTraits<UL,P>::offset())
00862 if(allEmpty || state.pieceAt(pos).isEmpty())
00863 action.dropMove(pos,BISHOP,P);
00864 for(Square pos=ul+DirectionPlayerTraits<UL,P>::offset();
00865 pos!=target;pos+=DirectionPlayerTraits<UL,P>::offset())
00866 if(allEmpty || state.pieceAt(pos).isEmpty())
00867 action.dropMove(pos,BISHOP,P);
00868 for(Square pos=ur-DirectionPlayerTraits<DL,P>::offset();
00869 pos!=target;pos-=DirectionPlayerTraits<DL,P>::offset())
00870 if(allEmpty || state.pieceAt(pos).isEmpty())
00871 action.dropMove(pos,BISHOP,P);
00872 }
00873
00874 template<Player P,class Action,bool allEmpty>
00875 void generateDropRook(const NumEffectState& state,Square target,Action& action,Square l,Square r,Square d,Square u)
00876 {
00877 for(Square pos=u-DirectionPlayerTraits<D,P>::offset();
00878 pos!=target;pos-=DirectionPlayerTraits<D,P>::offset())
00879 if(allEmpty || state.pieceAt(pos).isEmpty())
00880 action.dropMove(pos,ROOK,P);
00881 for(Square pos=l+DirectionPlayerTraits<L,P>::offset();
00882 pos!=target;pos+=DirectionPlayerTraits<L,P>::offset())
00883 if(allEmpty || state.pieceAt(pos).isEmpty())
00884 action.dropMove(pos,ROOK,P);
00885 for(Square pos=r-DirectionPlayerTraits<L,P>::offset();
00886 pos!=target;pos-=DirectionPlayerTraits<L,P>::offset())
00887 if(allEmpty || state.pieceAt(pos).isEmpty())
00888 action.dropMove(pos,ROOK,P);
00889 for(Square pos=d+DirectionPlayerTraits<D,P>::offset();
00890 pos!=target;pos+=DirectionPlayerTraits<D,P>::offset())
00891 if(allEmpty || state.pieceAt(pos).isEmpty())
00892 action.dropMove(pos,ROOK,P);
00893 }
00894 template<osl::Player P,class Action>
00895 void generateKing(const NumEffectState& state,Square target,Action& action,bool &hasPawnCheckmate)
00896 {
00897
00898 const Player altP=PlayerTraits<P>::opponent;
00899 assert(target==state.kingSquare(altP));
00900 generateDir<P,0,Action,U>(state,target,action,hasPawnCheckmate);
00901 generateKnightAll<P,Action>(state,target,action);
00902 generateDir<P,2,Action,UL>(state,target,action,hasPawnCheckmate);
00903 generateDir<P,2,Action,UR>(state,target,action,hasPawnCheckmate);
00904 generateDir<P,1,Action,L>(state,target,action,hasPawnCheckmate);
00905 generateDir<P,1,Action,R>(state,target,action,hasPawnCheckmate);
00906 generateDir<P,1,Action,D>(state,target,action,hasPawnCheckmate);
00907 generateDir<P,2,Action,DL>(state,target,action,hasPawnCheckmate);
00908 generateDir<P,2,Action,DR>(state,target,action,hasPawnCheckmate);
00909 detail::generateRookLongMove<P,Action>(state,target,action);
00910 for(int num=PtypeTraits<BISHOP>::indexMin;num<PtypeTraits<BISHOP>::indexLimit;num++){
00911
00912 if(state.pinOrOpen(altP).test(num)) continue;
00913 Piece p=state.pieceOf(num);
00914 if(!p.isOnBoardByOwner<P>()) continue;
00915 if(p.isPromoted())
00916 generateBishopLongMove<P,PBISHOP,Action>(state,target,action,p,num);
00917 else
00918 generateBishopLongMove<P,BISHOP,Action>(state,target,action,p,num);
00919 }
00920 int spaces=King8Info(state.Iking8Info(altP)).spaces();
00921 generateDropGold<P,Action>(state,target,action,spaces);
00922 generateDropSilver<P,Action>(state,target,action,spaces);
00923
00924 if(state.hasPieceOnStand<BISHOP>(P)){
00925 generateDropBishop<P,Action,true>(state,target,action,
00926 state.kingMobilityOfPlayer(altP,UL),
00927 state.kingMobilityOfPlayer(altP,DR),
00928 state.kingMobilityOfPlayer(altP,UR),
00929 state.kingMobilityOfPlayer(altP,DL));
00930 }
00931 if(state.hasPieceOnStand<ROOK>(P)){
00932 Square l,r,d,u;
00933 l=state.kingMobilityOfPlayer(altP,L);
00934 r=state.kingMobilityOfPlayer(altP,R);
00935 d=state.kingMobilityOfPlayer(altP,D);
00936 u=state.kingMobilityOfPlayer(altP,U);
00937 generateDropRook<P,Action,true>(state,target,action,l,r,d,u);
00938 }
00939 }
00940 template<osl::Player P,class Action>
00941 void generateNotKing(const NumEffectState& state,Square target,Action& action)
00942 {
00943 int spaces=0;
00944 CArray<unsigned char,8> pieceMobility;
00945 PieceMask notPieceMask;
00946 notPieceMask.setAll();
00947 int num=state.pieceAt(target).number();
00948 if(num != EMPTY_NUM){
00949 notPieceMask.reset(num);
00950 }
00951 generateDirNotKing<P,0,Action,U>(state,target,action,pieceMobility,spaces,notPieceMask);
00952 generateKnightAll<P,Action>(state,target,action);
00953 generateDirNotKing<P,2,Action,UL>(state,target,action,pieceMobility,spaces,notPieceMask);
00954 generateDirNotKing<P,2,Action,UR>(state,target,action,pieceMobility,spaces,notPieceMask);
00955 generateDirNotKing<P,1,Action,L>(state,target,action,pieceMobility,spaces,notPieceMask);
00956 generateDirNotKing<P,1,Action,R>(state,target,action,pieceMobility,spaces,notPieceMask);
00957 generateDirNotKing<P,1,Action,D>(state,target,action,pieceMobility,spaces,notPieceMask);
00958 generateDirNotKing<P,2,Action,DL>(state,target,action,pieceMobility,spaces,notPieceMask);
00959 generateDirNotKing<P,2,Action,DR>(state,target,action,pieceMobility,spaces,notPieceMask);
00960
00961 generateRookLongMoveNotKing<P,Action>(state,target,action,pieceMobility);
00962
00963 for(int num=PtypeTraits<BISHOP>::indexMin;num<PtypeTraits<BISHOP>::indexLimit;num++){
00964 Piece p=state.pieceOf(num);
00965 if(!p.isOnBoardByOwner<P>()) continue;
00966 if(p.isPromoted())
00967 generateBishopLongMoveNotKing<P,PBISHOP,Action>(state,target,action,pieceMobility,p,num);
00968 else
00969 generateBishopLongMoveNotKing<P,BISHOP,Action>(state,target,action,pieceMobility,p,num);
00970 }
00971 generateDropGold<P,Action>(state,target,action,spaces);
00972 generateDropSilver<P,Action>(state,target,action,spaces);
00973 if(state.hasPieceOnStand<BISHOP>(P)){
00974 Square ul,dr,dl,ur;
00975 ul=Square::makeDirect(pieceMobility[P==BLACK ? UL : DR]);
00976 dr=Square::makeDirect(pieceMobility[P==BLACK ? DR : UL]);
00977 ur=Square::makeDirect(pieceMobility[P==BLACK ? UR : DL]);
00978 dl=Square::makeDirect(pieceMobility[P==BLACK ? DL : UR]);
00979 generateDropBishop<P,Action,false>(state,target,action,ul,dr,ur,dl);
00980 }
00981 if(state.hasPieceOnStand<ROOK>(P)){
00982 Square l,r,d,u;
00983 l=Square::makeDirect(pieceMobility[P==BLACK ? L : R]);
00984 r=Square::makeDirect(pieceMobility[P==BLACK ? R : L]);
00985 d=Square::makeDirect(pieceMobility[P==BLACK ? D : U]);
00986 u=Square::makeDirect(pieceMobility[P==BLACK ? U : D]);
00987 generateDropRook<P,Action,false>(state,target,action,l,r,d,u);
00988 }
00989 }
00990 }
00991 template <class Action>
00992 template <osl::Player P,bool isAttackToKing>
00993 void osl::move_generator::AddEffectWithEffect<Action>::
00994 generate(const NumEffectState& state,Square target,Action& action,bool &hasPawnCheckmate)
00995 {
00996 if(!isAttackToKing){
00997 detail::template generateNotKing<P,Action>(state,target,action);
00998 }
00999 else{
01000 detail::template generateKing<P,Action>(state,target,action,hasPawnCheckmate);
01001 }
01002 }
01003 template<bool isAttackToKing>
01004 void osl::move_generator::GenerateAddEffectWithEffect::
01005 generate(Player player, const NumEffectState& state, Square target,
01006 move_action::Store& store)
01007 {
01008 using namespace osl::move_action;
01009 bool dummy;
01010 if(player==BLACK){
01011 AddEffectWithEffect<Store>::generate<BLACK,isAttackToKing>(state,target,store,dummy);
01012 }
01013 else{
01014 AddEffectWithEffect<Store>::generate<WHITE,isAttackToKing>(state,target,store,dummy);
01015 }
01016 }
01017
01018 }
01019 }
01020 #endif
01021
01022
01023
01024