aboutsummaryrefslogtreecommitdiff
path: root/src/moves.c
diff options
context:
space:
mode:
authorSebastiano Tronto <sebastiano@tronto.net>2023-05-01 12:48:55 +0200
committerSebastiano Tronto <sebastiano@tronto.net>2023-05-01 12:48:55 +0200
commit6f4313bc1ed5be794146e6ca2fd73f48c7906061 (patch)
treea79c8be8613e8b4256d609477f98f440bfd7168c /src/moves.c
parent1a5bfe9b08707b0aef748d7921a419ba4a046fba (diff)
downloadnissy-classic-6f4313bc1ed5be794146e6ca2fd73f48c7906061.tar.gz
nissy-classic-6f4313bc1ed5be794146e6ca2fd73f48c7906061.zip
Reverted to 2.0.3
Diffstat (limited to 'src/moves.c')
-rw-r--r--src/moves.c417
1 files changed, 331 insertions, 86 deletions
diff --git a/src/moves.c b/src/moves.c
index a9dfdc0..02880ca 100644
--- a/src/moves.c
+++ b/src/moves.c
@@ -1,18 +1,79 @@
1#define MOVES_C
2
3#include "moves.h" 1#include "moves.h"
4 2
5/* Local functions ***********************************************************/ 3/* Local functions ***********************************************************/
6 4
5static Cube apply_move_cubearray(Move m, Cube cube, PieceFilter f);
7static void cleanup_aux(Alg *alg, Alg *ret, bool inv); 6static void cleanup_aux(Alg *alg, Alg *ret, bool inv);
7static bool read_mtables_file();
8static bool write_mtables_file();
8 9
9/* Tables and other data *****************************************************/ 10/* Tables and other data *****************************************************/
10 11
11/* Moves are represented as cubes and applied using compose(). Every move is * 12/* Every move is translated to a an <U, x, y> alg before filling the
12 * translated to a an <U, x, y> alg before filling the transition tables. * 13 transition tables, see init_moves() */
13 * See init_moves(). */ 14
15static int edge_cycle[NMOVES][12] =
16{
17 [U] = { UR, UF, UL, UB, DF, DL, DB, DR, FR, FL, BL, BR },
18 [x] = { DF, FL, UF, FR, DB, BL, UB, BR, DR, DL, UL, UR },
19 [y] = { UR, UF, UL, UB, DR, DF, DL, DB, BR, FR, FL, BL }
20};
21
22static int corner_cycle[NMOVES][8] =
23{
24 [U] = { UBR, UFR, UFL, UBL, DFR, DFL, DBL, DBR },
25 [x] = { DFR, DFL, UFL, UFR, DBR, DBL, UBL, UBR },
26 [y] = { UBR, UFR, UFL, UBL, DBR, DFR, DFL, DBL }
27};
28
29static int center_cycle[NMOVES][6] =
30{
31 [x] = { F_center, B_center, R_center, L_center, D_center, U_center },
32 [y] = { U_center, D_center, B_center, F_center, R_center, L_center }
33};
34
35static int eofb_flipped[NMOVES][12] = {
36 [x] = { [UF] = 1, [UB] = 1, [DF] = 1, [DB] = 1 },
37 [y] = { [FR] = 1, [FL] = 1, [BL] = 1, [BR] = 1 }
38};
39
40static int eorl_flipped[NMOVES][12] = {
41 [x] = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 },
42 [y] = { [FR] = 1, [FL] = 1, [BL] = 1, [BR] = 1 }
43};
44
45static int eoud_flipped[NMOVES][12] = {
46 [U] = { [UF] = 1, [UL] = 1, [UB] = 1, [UR] = 1 },
47 [x] = { [UF] = 1, [UB] = 1, [DF] = 1, [DB] = 1 },
48 [y] = { 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1 }
49};
50
51static int coud_flipped[NMOVES][8] = {
52 [x] = {
53 [UFR] = 2, [UBR] = 1, [UFL] = 1, [UBL] = 2,
54 [DBR] = 2, [DFR] = 1, [DBL] = 1, [DFL] = 2
55 }
56};
57
58static int corl_flipped[NMOVES][8] = {
59 [U] = { [UFR] = 1, [UBR] = 2, [UBL] = 1, [UFL] = 2 },
60 [y] = {
61 [UFR] = 1, [UBR] = 2, [UBL] = 1, [UFL] = 2,
62 [DFR] = 2, [DBR] = 1, [DBL] = 2, [DFL] = 1
63 }
64};
14 65
15static Cube move_array[NMOVES]; 66static int cofb_flipped[NMOVES][8] = {
67 [U] = { [UFR] = 2, [UBR] = 1, [UBL] = 2, [UFL] = 1 },
68 [x] = {
69 [UFR] = 1, [UBR] = 2, [UBL] = 1, [UFL] = 2,
70 [DFR] = 2, [DBR] = 1, [DBL] = 2, [DFL] = 1
71 },
72 [y] = {
73 [UFR] = 2, [UBR] = 1, [UBL] = 2, [UFL] = 1,
74 [DFR] = 1, [DBR] = 2, [DBL] = 1, [DFL] = 2
75 }
76};
16 77
17static char equiv_alg_string[100][NMOVES] = { 78static char equiv_alg_string[100][NMOVES] = {
18 [NULLMOVE] = "", 79 [NULLMOVE] = "",
@@ -76,52 +137,89 @@ static char equiv_alg_string[100][NMOVES] = {
76 [z3] = " y x yyy " 137 [z3] = " y x yyy "
77}; 138};
78 139
140/* Transition tables, to be loaded up at the beginning */
141int epose_mtable[NMOVES][FACTORIAL12/FACTORIAL8];
142int eposs_mtable[NMOVES][FACTORIAL12/FACTORIAL8];
143int eposm_mtable[NMOVES][FACTORIAL12/FACTORIAL8];
144int eofb_mtable[NMOVES][POW2TO11];
145int eorl_mtable[NMOVES][POW2TO11];
146int eoud_mtable[NMOVES][POW2TO11];
147int cp_mtable[NMOVES][FACTORIAL8];
148int coud_mtable[NMOVES][POW3TO7];
149int cofb_mtable[NMOVES][POW3TO7];
150int corl_mtable[NMOVES][POW3TO7];
151int cpos_mtable[NMOVES][FACTORIAL6];
152
153
154/* Local functions implementation ********************************************/
155
156static Cube
157apply_move_cubearray(Move m, Cube cube, PieceFilter f)
158{
159 /*init_moves();*/
160
161 CubeArray m_arr = {
162 edge_cycle[m],
163 eofb_flipped[m],
164 eorl_flipped[m],
165 eoud_flipped[m],
166 corner_cycle[m],
167 coud_flipped[m],
168 corl_flipped[m],
169 cofb_flipped[m],
170 center_cycle[m]
171 };
172
173 return move_via_arrays(&m_arr, cube, f);
174}
79 175
80/* Public functions **********************************************************/ 176/* Public functions **********************************************************/
81 177
82void 178Cube
83apply_alg(Alg *alg, Cube *cube) 179apply_alg_generic(Alg *alg, Cube c, PieceFilter f, bool a)
84{ 180{
85 Cube aux; 181 Cube ret = {0};
86 int i; 182 int i;
87 183
88 copy_cube(cube, &aux);
89 make_solved(cube);
90
91 for (i = 0; i < alg->len; i++) 184 for (i = 0; i < alg->len; i++)
92 if (alg->inv[i]) 185 if (alg->inv[i])
93 apply_move(alg->move[i], cube); 186 ret = a ? apply_move(alg->move[i], ret) :
187 apply_move_cubearray(alg->move[i], ret, f);
94 188
95 invert_cube(cube); 189 ret = compose_filtered(c, inverse_cube(ret), f);
96 compose(&aux, cube);
97 190
98 for (i = 0; i < alg->len; i++) 191 for (i = 0; i < alg->len; i++)
99 if (!alg->inv[i]) 192 if (!alg->inv[i])
100 apply_move(alg->move[i], cube); 193 ret = a ? apply_move(alg->move[i], ret) :
101} 194 apply_move_cubearray(alg->move[i], ret, f);
102 195
103void 196 return ret;
104apply_move(Move m, Cube *cube)
105{
106 compose(&move_array[m], cube);
107} 197}
108 198
109void 199Cube
110apply_move_centers(Move m, Cube *cube) 200apply_alg(Alg *alg, Cube cube)
111{ 201{
112 compose_centers(&move_array[m], cube); 202 return apply_alg_generic(alg, cube, pf_all, true);
113} 203}
114 204
115void 205Cube
116apply_move_corners(Move m, Cube *cube) 206apply_move(Move m, Cube cube)
117{ 207{
118 compose_corners(&move_array[m], cube); 208 /*init_moves();*/
119}
120 209
121void 210 return (Cube) {
122apply_move_edges(Move m, Cube *cube) 211 .epose = epose_mtable[m][cube.epose],
123{ 212 .eposs = eposs_mtable[m][cube.eposs],
124 compose_edges(&move_array[m], cube); 213 .eposm = eposm_mtable[m][cube.eposm],
214 .eofb = eofb_mtable[m][cube.eofb],
215 .eorl = eorl_mtable[m][cube.eorl],
216 .eoud = eoud_mtable[m][cube.eoud],
217 .coud = coud_mtable[m][cube.coud],
218 .cofb = cofb_mtable[m][cube.cofb],
219 .corl = corl_mtable[m][cube.corl],
220 .cp = cp_mtable[m][cube.cp],
221 .cpos = cpos_mtable[m][cube.cpos]
222 };
125} 223}
126 224
127Alg * 225Alg *
@@ -181,27 +279,31 @@ cleanup_aux(Alg *alg, Alg *ret, bool inv)
181{ 279{
182 int i, j; 280 int i, j;
183 Cube c, d; 281 Cube c, d;
184 Move m; 282 Move m, mm;
185 Alg *equiv_alg; 283 Alg *equiv_alg;
186 284
187 make_solved(&c); 285 c = (Cube){0};
188 for (i = 0; i < alg->len; i++) { 286 for (i = 0; i < alg->len; i++) {
189 if (alg->inv[i] != inv) 287 if (alg->inv[i] != inv)
190 continue; 288 continue;
191 289
192 equiv_alg = new_alg(equiv_alg_string[alg->move[i]]); 290 equiv_alg = new_alg(equiv_alg_string[alg->move[i]]);
193 291
194 for (j = 0; j < equiv_alg->len; j++) 292 for (j = 0; j < equiv_alg->len; j++) {
195 if (equiv_alg->move[j] == U) 293 m = equiv_alg->move[j];
196 append_move(ret, 3 * c.xp[U_center] + 1, inv); 294 if (m == U) {
197 else 295 mm = 3*what_center_at(c, U_center) + 1;
198 apply_move(equiv_alg->move[j], &c); 296 append_move(ret, mm, inv);
297 } else {
298 c = apply_move(m, c);
299 }
300 }
199 301
200 free_alg(equiv_alg); 302 free_alg(equiv_alg);
201 } 303 }
202 304
203 m = NULLMOVE; 305 m = NULLMOVE;
204 switch (c.xp[F_center]) { 306 switch (what_center_at(c, F_center)) {
205 case U_center: 307 case U_center:
206 m = x3; 308 m = x3;
207 break; 309 break;
@@ -215,7 +317,7 @@ cleanup_aux(Alg *alg, Alg *ret, bool inv)
215 m = y3; 317 m = y3;
216 break; 318 break;
217 case B_center: 319 case B_center:
218 if (c.xp[U_center] == U_center) 320 if (what_center_at(c, U_center) == U_center)
219 m = y2; 321 m = y2;
220 else 322 else
221 m = x2; 323 m = x2;
@@ -223,24 +325,120 @@ cleanup_aux(Alg *alg, Alg *ret, bool inv)
223 default: 325 default:
224 break; 326 break;
225 } 327 }
226 328 d = apply_move(m, (Cube){0});
227 make_solved(&d);
228 apply_move(m, &d);
229 if (m != NULLMOVE) 329 if (m != NULLMOVE)
230 append_move(ret, m, inv); 330 append_move(ret, m, inv);
231 331
232 m = NULLMOVE; 332 m = NULLMOVE;
233 if (c.xp[U_center] == d.xp[D_center]) { 333 if (what_center_at(c, U_center) == what_center_at(d, D_center)) {
234 m = z2; 334 m = z2;
235 } else if (c.xp[U_center] == d.xp[R_center]) { 335 } else if (what_center_at(c, U_center) == what_center_at(d, R_center)) {
236 m = z3; 336 m = z3;
237 } else if (c.xp[U_center] == d.xp[L_center]) { 337 } else if (what_center_at(c, U_center) == what_center_at(d, L_center)) {
238 m = z; 338 m = z;
239 } 339 }
240 if (m != NULLMOVE) 340 if (m != NULLMOVE)
241 append_move(ret, m, inv); 341 append_move(ret, m, inv);
242} 342}
243 343
344static bool
345read_mtables_file()
346{
347 init_env();
348
349 FILE *f;
350 char fname[strlen(tabledir)+20];
351 int m, b = sizeof(int);
352 bool r = true;
353
354 /* Table sizes, used for reading and writing files */
355 uint64_t me[11] = {
356 [0] = FACTORIAL12/FACTORIAL8,
357 [1] = FACTORIAL12/FACTORIAL8,
358 [2] = FACTORIAL12/FACTORIAL8,
359 [3] = POW2TO11,
360 [4] = POW2TO11,
361 [5] = POW2TO11,
362 [6] = FACTORIAL8,
363 [7] = POW3TO7,
364 [8] = POW3TO7,
365 [9] = POW3TO7,
366 [10] = FACTORIAL6
367 };
368
369 strcpy(fname, tabledir);
370 strcat(fname, "/mtables");
371
372 if ((f = fopen(fname, "rb")) == NULL)
373 return false;
374
375 for (m = 0; m < NMOVES; m++) {
376 r = r && fread(epose_mtable[m], b, me[0], f) == me[0];
377 r = r && fread(eposs_mtable[m], b, me[1], f) == me[1];
378 r = r && fread(eposm_mtable[m], b, me[2], f) == me[2];
379 r = r && fread(eofb_mtable[m], b, me[3], f) == me[3];
380 r = r && fread(eorl_mtable[m], b, me[4], f) == me[4];
381 r = r && fread(eoud_mtable[m], b, me[5], f) == me[5];
382 r = r && fread(cp_mtable[m], b, me[6], f) == me[6];
383 r = r && fread(coud_mtable[m], b, me[7], f) == me[7];
384 r = r && fread(corl_mtable[m], b, me[8], f) == me[8];
385 r = r && fread(cofb_mtable[m], b, me[9], f) == me[9];
386 r = r && fread(cpos_mtable[m], b, me[10], f) == me[10];
387 }
388
389 fclose(f);
390 return r;
391}
392
393static bool
394write_mtables_file()
395{
396 init_env();
397
398 FILE *f;
399 char fname[strlen(tabledir)+20];
400 int m, b = sizeof(int);
401 bool r = true;
402
403 /* Table sizes, used for reading and writing files */
404 uint64_t me[11] = {
405 [0] = FACTORIAL12/FACTORIAL8,
406 [1] = FACTORIAL12/FACTORIAL8,
407 [2] = FACTORIAL12/FACTORIAL8,
408 [3] = POW2TO11,
409 [4] = POW2TO11,
410 [5] = POW2TO11,
411 [6] = FACTORIAL8,
412 [7] = POW3TO7,
413 [8] = POW3TO7,
414 [9] = POW3TO7,
415 [10] = FACTORIAL6
416 };
417
418 strcpy(fname, tabledir);
419 strcat(fname, "/mtables");
420
421 if ((f = fopen(fname, "wb")) == NULL)
422 return false;
423
424 for (m = 0; m < NMOVES; m++) {
425 r = r && fwrite(epose_mtable[m], b, me[0], f) == me[0];
426 r = r && fwrite(eposs_mtable[m], b, me[1], f) == me[1];
427 r = r && fwrite(eposm_mtable[m], b, me[2], f) == me[2];
428 r = r && fwrite(eofb_mtable[m], b, me[3], f) == me[3];
429 r = r && fwrite(eorl_mtable[m], b, me[4], f) == me[4];
430 r = r && fwrite(eoud_mtable[m], b, me[5], f) == me[5];
431 r = r && fwrite(cp_mtable[m], b, me[6], f) == me[6];
432 r = r && fwrite(coud_mtable[m], b, me[7], f) == me[7];
433 r = r && fwrite(corl_mtable[m], b, me[8], f) == me[8];
434 r = r && fwrite(cofb_mtable[m], b, me[9], f) == me[9];
435 r = r && fwrite(cpos_mtable[m], b, me[10], f) == me[10];
436 }
437
438 fclose(f);
439 return r;
440}
441
244void 442void
245init_moves() { 443init_moves() {
246 static bool initialized = false; 444 static bool initialized = false;
@@ -248,54 +446,101 @@ init_moves() {
248 return; 446 return;
249 initialized = true; 447 initialized = true;
250 448
449 Cube c;
450 CubeArray arrs;
451 int i;
452 unsigned int ui;
251 Move m; 453 Move m;
252 Alg *equiv_alg[NMOVES]; 454 Alg *equiv_alg[NMOVES];
253 455
254 static const Cube mcu = { 456 init_cube();
255 .ep = { UR, UF, UL, UB, DF, DL, DB, DR, FR, FL, BL, BR }, 457
256 .cp = { UBR, UFR, UFL, UBL, DFR, DFL, DBL, DBR }, 458 for (i = 0; i < NMOVES; i++)
257 }; 459 equiv_alg[i] = new_alg(equiv_alg_string[i]);
258 static const Cube mcx = {
259 .ep = { DF, FL, UF, FR, DB, BL, UB, BR, DR, DL, UL, UR },
260 .eo = { [UF] = 1, [UB] = 1, [DF] = 1, [DB] = 1 },
261 .cp = { DFR, DFL, UFL, UFR, DBR, DBL, UBL, UBR },
262 .co = { [UFR] = 2, [UBR] = 1, [UFL] = 1, [UBL] = 2,
263 [DBR] = 2, [DFR] = 1, [DBL] = 1, [DFL] = 2 },
264 .xp = { F_center, B_center, R_center,
265 L_center, D_center, U_center },
266 };
267 static const Cube mcy = {
268 .ep = { UR, UF, UL, UB, DR, DF, DL, DB, BR, FR, FL, BL },
269 .eo = { [FR] = 1, [FL] = 1, [BL] = 1, [BR] = 1 },
270 .cp = { UBR, UFR, UFL, UBL, DBR, DFR, DFL, DBL },
271 .xp = { U_center, D_center, B_center,
272 F_center, R_center, L_center },
273 };
274 460
275 move_array[U] = mcu; 461 /* Generate all move cycles and flips; I do this regardless */
276 move_array[x] = mcx; 462 for (i = 0; i < NMOVES; i++) {
277 move_array[y] = mcy; 463 if (i == U || i == x || i == y)
464 continue;
465
466 c = apply_alg_generic(equiv_alg[i], (Cube){0}, pf_all, false);
467
468 arrs = (CubeArray) {
469 edge_cycle[i],
470 eofb_flipped[i],
471 eorl_flipped[i],
472 eoud_flipped[i],
473 corner_cycle[i],
474 coud_flipped[i],
475 corl_flipped[i],
476 cofb_flipped[i],
477 center_cycle[i]
478 };
479 cube_to_arrays(c, &arrs, pf_all);
480 }
481
482 if (read_mtables_file())
483 return;
278 484
279 for (m = 0; m < NMOVES; m++) 485 fprintf(stderr, "Cannot load %s, generating it\n", "mtables");
280 equiv_alg[m] = new_alg(equiv_alg_string[m]);
281 486
487 /* Initialize transition tables */
282 for (m = 0; m < NMOVES; m++) { 488 for (m = 0; m < NMOVES; m++) {
283 switch (m) { 489 for (ui = 0; ui < FACTORIAL12/FACTORIAL8; ui++) {
284 case NULLMOVE: 490 c = (Cube){ .epose = ui };
285 make_solved(&move_array[m]); 491 c = apply_move_cubearray(m, c, pf_e);
286 break; 492 epose_mtable[m][ui] = c.epose;
287 case U: 493
288 case x: 494 c = (Cube){ .eposs = ui };
289 case y: 495 c = apply_move_cubearray(m, c, pf_s);
290 break; 496 eposs_mtable[m][ui] = c.eposs;
291 default: 497
292 make_solved(&move_array[m]); 498 c = (Cube){ .eposm = ui };
293 apply_alg(equiv_alg[m], &move_array[m]); 499 c = apply_move_cubearray(m, c, pf_m);
294 break; 500 eposm_mtable[m][ui] = c.eposm;
501 }
502 for (ui = 0; ui < POW2TO11; ui++ ) {
503 c = (Cube){ .eofb = ui };
504 c = apply_move_cubearray(m, c, pf_eo);
505 eofb_mtable[m][ui] = c.eofb;
506
507 c = (Cube){ .eorl = ui };
508 c = apply_move_cubearray(m, c, pf_eo);
509 eorl_mtable[m][ui] = c.eorl;
510
511 c = (Cube){ .eoud = ui };
512 c = apply_move_cubearray(m, c, pf_eo);
513 eoud_mtable[m][ui] = c.eoud;
514 }
515 for (ui = 0; ui < POW3TO7; ui++) {
516 c = (Cube){ .coud = ui };
517 c = apply_move_cubearray(m, c, pf_co);
518 coud_mtable[m][ui] = c.coud;
519
520 c = (Cube){ .corl = ui };
521 c = apply_move_cubearray(m, c, pf_co);
522 corl_mtable[m][ui] = c.corl;
523
524 c = (Cube){ .cofb = ui };
525 c = apply_move_cubearray(m, c, pf_co);
526 cofb_mtable[m][ui] = c.cofb;
527 }
528 for (ui = 0; ui < FACTORIAL8; ui++) {
529 c = (Cube){ .cp = ui };
530 c = apply_move_cubearray(m, c, pf_cp);
531 cp_mtable[m][ui] = c.cp;
532 }
533 for (ui = 0; ui < FACTORIAL6; ui++) {
534 c = (Cube){ .cpos = ui };
535 c = apply_move_cubearray(m, c, pf_cpos);
536 cpos_mtable[m][ui] = c.cpos;
295 } 537 }
296 } 538 }
297 539
298 for (m = 0; m < NMOVES; m++) 540 if (!write_mtables_file())
299 free_alg(equiv_alg[m]); 541 fprintf(stderr, "Error writing mtables\n");
542
543 for (i = 0; i < NMOVES; i++)
544 free_alg(equiv_alg[i]);
300} 545}
301 546

Generated with cgit - Back to sebastiano.tronto.net