/
Sample2.c
198 lines (154 loc) · 9.52 KB
/
Sample2.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
#include <stdio.h>
#include <stdlib.h>
/*
Chess Magics usage sample
Compiler: gcc
*/
#define U64 unsigned long long
#define U32 unsigned int
#define B2G7 0x007E7E7E7E7E7E00LL
// pre-generated constants, magicgen bc16
static const U64 BishopMagics[] = {
// Magics for bishops
0x6CFFD8B9D37E06BBLL /*A1*/, 0x7C178C7BF7F57CAELL /*B1*/, 0xBD98AC81272FB5B8LL /*C1*/, 0xEDFAE51870C9F19FLL /*D1*/, 0x87F47FB1C074593ALL /*E1*/, 0xD7C16D85CA270CF5LL /*F1*/, 0x5BA782D5B7C17BB3LL /*G1*/, 0x3A4C9A5ACF80510DLL /*H1*/,
0x6D57FAB6246EF2B3LL /*A2*/, 0x0BD74D62FC617A7BLL /*B2*/, 0x9584DA4D20B959BDLL /*C2*/, 0x6F723DEBECA069F4LL /*D2*/, 0xF4ACC795CB2D5CB5LL /*E2*/, 0x43C4F193D04AD6A9LL /*F2*/, 0x612085F344704B15LL /*G2*/, 0xE1A9E4CF7060D21FLL /*H2*/,
0x596BEA7F05C0FE36LL /*A3*/, 0x6214025A7E63AD2FLL /*B3*/, 0x15912315DA5016A0LL /*C3*/, 0xBB3A96FA5092215FLL /*D3*/, 0x51C771E8BDF392C0LL /*E3*/, 0x7AEB8FC497D0BC32LL /*F3*/, 0x36FB5CF010EC579ELL /*G3*/, 0x34EB7C64AE28C243LL /*H3*/,
0x4212BD8C83A6E4C0LL /*A4*/, 0xE0412592D1C1C3FFLL /*B4*/, 0x7751B104DA2A81FBLL /*C4*/, 0xF730B59B8571381CLL /*D4*/, 0x634900EA035C3400LL /*E4*/, 0xC840D3F3B6F9B929LL /*F4*/, 0x39C239F3FC93CB76LL /*G4*/, 0x66C5D96788357B03LL /*H4*/,
0xD9824BEFC9415C11LL /*A5*/, 0xCD7DF0EFE183E6E3LL /*B5*/, 0xD79C76F086E33E64LL /*C5*/, 0x4DBA5F8501CE2400LL /*D5*/, 0xCBAF744A8043F100LL /*E5*/, 0x617DBA463E646CFFLL /*F5*/, 0x61B7B064856AD941LL /*G5*/, 0x5E682D8D0B916E5DLL /*H5*/,
0xFD9CACF9DA01803ELL /*A6*/, 0xF6779696FF3E7EE0LL /*B6*/, 0x6FE2E5338E0C1248LL /*C6*/, 0x72165A308C570B6ELL /*D6*/, 0xAF7756B732E846E2LL /*E6*/, 0x6B1A5D734E172568LL /*F6*/, 0x2197A3345514B9D9LL /*G6*/, 0x678DBC7501FB2C50LL /*H6*/,
0x78612467DABD1F04LL /*A7*/, 0x33966792F76720D1LL /*B7*/, 0x96C66374DDFB3360LL /*C7*/, 0x53860F0EE0C8CD45LL /*D7*/, 0x534290A02B766B2CLL /*E7*/, 0x5595C747518329FBLL /*F7*/, 0x4370788E0145B955LL /*G7*/, 0xFD35BBAF299013D9LL /*H7*/,
0x6E266965ADAF646CLL /*A8*/, 0xA1DEEFF0A585674FLL /*B8*/, 0xD262607972DD3A36LL /*C8*/, 0xD46BC2B72BF218A5LL /*D8*/, 0x562CDC3F02EC43F5LL /*E8*/, 0x2AA80F72248BE656LL /*F8*/, 0x91F23AC46A1EE715LL /*G8*/, 0x013FB443B15EB41ALL /*H8*/,
0
};
static const U64 RookMagics[] = {
// Magics for rooks
0xFF260527D2CAC700LL /*A1*/, 0x4CF0F24E7D5A5800LL /*B1*/, 0x829576FC130A3080LL /*C1*/, 0x5CFB475FC91E1100LL /*D1*/, 0x1C6E08D3004F2600LL /*E1*/, 0xF1B1998208AC1078LL /*F1*/, 0x06FCBDB2CB1BC4A8LL /*G1*/, 0x938C7FC1E07D6298LL /*H1*/,
0x4E2D37B8F9E42E39LL /*A2*/, 0x45719CD9ACBBEB00LL /*B2*/, 0x29FBB48EFBF98AC0LL /*C2*/, 0xBBE3DBB8542C8C80LL /*D2*/, 0x1B0CBBC889E0A010LL /*E2*/, 0x784844442DBFABB8LL /*F2*/, 0x08320F627EE206D0LL /*G2*/, 0xE651EECBDD946AE0LL /*H2*/,
0xBD8AEA197A509A03LL /*A3*/, 0x6412AE5F67893D00LL /*B3*/, 0x4CD4742FDEAA6A00LL /*C3*/, 0x324FDAC71DBAE100LL /*D3*/, 0x0D6F612384FF4DB0LL /*E3*/, 0xC0322570866933F0LL /*F3*/, 0xFE527633BA19DCCCLL /*G3*/, 0x65DD6D0E8C0A245CLL /*H3*/,
0xCCD36B245D1A34BFLL /*A4*/, 0x301B25F9D1808F00LL /*B4*/, 0xCDD5B0E696401E00LL /*C4*/, 0xAA567462A1BFE7C0LL /*D4*/, 0xCB8D9FFE2B0A4540LL /*E4*/, 0xB002D050508A8808LL /*F4*/, 0x90DBCB9AA74E5DECLL /*G4*/, 0x52BD607AD16823CELL /*H4*/,
0x6789D8D2F2B06E12LL /*A5*/, 0x84DBDAD1C0C9E180LL /*B5*/, 0xECA9A368B64154C0LL /*C5*/, 0xCB663F3098641DE0LL /*D5*/, 0x900DB76EA2B3CE30LL /*E5*/, 0x09A70669D4010E20LL /*F5*/, 0xC512D6EE770DE5A0LL /*G5*/, 0x797423BE8627BC94LL /*H5*/,
0x8A3D575077F24F63LL /*A6*/, 0x0EC9B8F218AB9D00LL /*B6*/, 0x0C8587D6C0DD33C0LL /*C6*/, 0x60AF95CADD982560LL /*D6*/, 0xACC5169EB71CA590LL /*E6*/, 0x160D1C32B7BC6398LL /*F6*/, 0x88B6F3A8886C2D2ALL /*G6*/, 0x4C5BC7A588A0AB5CLL /*H6*/,
0x0A2F0CEF3B7D0C39LL /*A7*/, 0xEF4D5C4858599E00LL /*B7*/, 0x1B041BF13B674200LL /*C7*/, 0xFB6B678E03BAAE00LL /*D7*/, 0xC277382FB0280FE0LL /*E7*/, 0x5C8971741F006128LL /*F7*/, 0x8A909A7AC999AAACLL /*G7*/, 0x5405CD9DAE7D3E08LL /*H7*/,
0x9D4D6B7CC2DAD786LL /*A8*/, 0xCE3D0AD07A35766ALL /*B8*/, 0xC0EA25A977591592LL /*C8*/, 0xC5C9BB5E7D8EF022LL /*D8*/, 0xB1552E04EC9C49E9LL /*E8*/, 0x9C16B80885B53F9ELL /*F8*/, 0xDE285EF1DAC7D27ALL /*G8*/, 0x441830E566CDF37ALL /*H8*/,
0
};
// pre-calculated masks to make keys list
static const U64 BishopMask[] = {
0x8040201008040200LL,0x0080402010080500LL,0x0000804020110A00LL,0x0000008041221400LL,0x0000000182442800LL,0x0000010204885000LL,0x000102040810A000LL,0x0102040810204000LL,0x4020100804020002LL,0x8040201008050005LL,0x00804020110A000ALL,0x0000804122140014LL,0x0000018244280028LL,0x0001020488500050LL,0x0102040810A000A0LL,0x0204081020400040LL,0x2010080402000204LL,0x4020100805000508LL,0x804020110A000A11LL,0x0080412214001422LL,0x0001824428002844LL,0x0102048850005088LL,0x02040810A000A010LL,0x0408102040004020LL,0x1008040200020408LL,0x2010080500050810LL,0x4020110A000A1120LL,0x8041221400142241LL,0x0182442800284482LL,0x0204885000508804LL,0x040810A000A01008LL,0x0810204000402010LL,0x0804020002040810LL,0x1008050005081020LL,0x20110A000A112040LL,0x4122140014224180LL,0x8244280028448201LL,0x0488500050880402LL,0x0810A000A0100804LL,0x1020400040201008LL,0x0402000204081020LL,0x0805000508102040LL,0x110A000A11204080LL,0x2214001422418000LL,0x4428002844820100LL,0x8850005088040201LL,0x10A000A010080402LL,0x2040004020100804LL,0x0200020408102040LL,0x0500050810204080LL,0x0A000A1120408000LL,0x1400142241800000LL,0x2800284482010000LL,0x5000508804020100LL,0xA000A01008040201LL,0x4000402010080402LL,0x0002040810204080LL,0x0005081020408000LL,0x000A112040800000LL,0x0014224180000000LL,0x0028448201000000LL,0x0050880402010000LL,0x00A0100804020100LL,0x0040201008040201LL,
0};
static const U64 RookMask[] = {
0x01010101010101FELL,0x02020202020202FDLL,0x04040404040404FBLL,0x08080808080808F7LL,0x10101010101010EFLL,0x20202020202020DFLL,0x40404040404040BFLL,0x808080808080807FLL,0x010101010101FE01LL,0x020202020202FD02LL,0x040404040404FB04LL,0x080808080808F708LL,0x101010101010EF10LL,0x202020202020DF20LL,0x404040404040BF40LL,0x8080808080807F80LL,0x0101010101FE0101LL,0x0202020202FD0202LL,0x0404040404FB0404LL,0x0808080808F70808LL,0x1010101010EF1010LL,0x2020202020DF2020LL,0x4040404040BF4040LL,0x80808080807F8080LL,0x01010101FE010101LL,0x02020202FD020202LL,0x04040404FB040404LL,0x08080808F7080808LL,0x10101010EF101010LL,0x20202020DF202020LL,0x40404040BF404040LL,0x808080807F808080LL,0x010101FE01010101LL,0x020202FD02020202LL,0x040404FB04040404LL,0x080808F708080808LL,0x101010EF10101010LL,0x202020DF20202020LL,0x404040BF40404040LL,0x8080807F80808080LL,0x0101FE0101010101LL,0x0202FD0202020202LL,0x0404FB0404040404LL,0x0808F70808080808LL,0x1010EF1010101010LL,0x2020DF2020202020LL,0x4040BF4040404040LL,0x80807F8080808080LL,0x01FE010101010101LL,0x02FD020202020202LL,0x04FB040404040404LL,0x08F7080808080808LL,0x10EF101010101010LL,0x20DF202020202020LL,0x40BF404040404040LL,0x807F808080808080LL,0xFE01010101010101LL,0xFD02020202020202LL,0xFB04040404040404LL,0xF708080808080808LL,0xEF10101010101010LL,0xDF20202020202020LL,0xBF40404040404040LL,0x7F80808080808080LL,
0};
// arrays to prepare
// The lookup table of legal moves, shifting 16 bits
U64 BishopLegalsTable[64][1<<16];
U64 RookLegalsTable[64][1<<16];
U64 getBishopMove(int square, U64 occupancy ) {
return BishopLegalsTable[square]
[((occupancy & BishopMask[square])*BishopMagics[square] ) >> 48 ];
}
U64 getRookMove(int square, U64 occupancy ) {
return RookLegalsTable[square]
[((occupancy & RookMask[square])*RookMagics[square] ) >> 48 ];
}
// ---------------------- prepares arrays
//
U64 Bo1,Bo2; // boards
int SqI; // square to prepare
int b_r; // 1-bishops, 0-rooks
void dir(int dv, int dh) {
int V=(SqI>>3),H=(SqI&7);
V+=dv; H+=dh;
while( (V>=0 && V<8) && (H>=0 && H<8) ) {
int sq = (V<<3)|H;
Bo2 |= (1LL<<sq);
if( Bo1 & (1LL<<sq) ) return;
V+=dv; H+=dh;
}
}
void genBdir() { //bishops
dir(-1,-1); dir(+1,-1); dir(-1,+1); dir(+1,+1);
}
void genRdir() { // rooks
dir(-1,0); dir(+1,0); dir(0,+1); dir(0,-1);
}
// Does all the permutations for the current square and Bo1 board
void Permutate() {
int bits[64]; // This will contain square numbers
int n=0,sq=0;
for(;sq<64;sq++) {
if( Bo1 & (1LL<<sq) ) bits[n++]=sq;
}
int LEN = (1<<n); // length of permutations table
for(int i=0;i<LEN;i++) { // go through all the cases
Bo1 = 0LL;
for(int j=0;j<n;j++) // scan as bits
{
if(i&(1<<j)) Bo1|=(1LL<<bits[j]);
}
// now Bo1 contains occupancy
U64 mult = Bo1 * (b_r ? BishopMagics[SqI] : RookMagics[SqI]);
U32 index = mult >> 48;
// find legal moves for square, put in Bo2, then table
Bo2 = 0;
if(b_r) {
genBdir();
BishopLegalsTable[SqI][index] = Bo2;
}
else {
genRdir();
RookLegalsTable[SqI][index] = Bo2;
}
}
}
void prepare_tables() {
for(SqI=0;SqI<64;SqI++) {
for(b_r=0; b_r<2; b_r++) {
Bo1 = (b_r ? BishopMask[SqI] : RookMask[SqI]);
Permutate();
}
}
}
// ----------------------
void displayBitboard(U64 N) {
for(int V=7;V>=0;V--) {
for(int H=0;H<=7;H++) {
int i=(V<<3)|H;
printf("%c", ((N&(1LL<<i))?'X':'o'));
}
printf("\n");
}
printf("\n");
}
int main(int argc, char *argv[])
{
prepare_tables();
// put any pieces on A8 B7 E1
U64 Occupancy =(1LL<<56)|(1LL<<49)|(1LL<<4);
U64 bishop_E4 = getBishopMove(28,Occupancy);
displayBitboard(bishop_E4);
U64 rook_B2 = getRookMove(9,Occupancy);
displayBitboard(rook_B2);
printf("\nPress a key to close...\n");
getch();
return(0);
}
/*
Displays:
oooooooo
oXoooooX
ooXoooXo
oooXoXoo
oooooooo
oooXoXoo
ooXoooXo
oXoooooX
oooooooo
oXoooooo
oXoooooo
oXoooooo
oXoooooo
oXoooooo
XoXXXXXX
oXoooooo
*/