From 57a7520545134ab95f7bb0397dcbe991c906a3e9 Mon Sep 17 00:00:00 2001 From: Sebastiano Tronto Date: Wed, 6 Aug 2025 16:34:21 +0200 Subject: Added HTR solver --- src/arch/avx2.h | 24 +++++++++++++++++++++++- src/arch/common.h | 39 +++++++++++++++++++++++++++++++++++++++ src/arch/neon.h | 23 ++++++++++++++++++++++- src/arch/portable.h | 16 ++++++++++++++++ 4 files changed, 100 insertions(+), 2 deletions(-) (limited to 'src/arch') diff --git a/src/arch/avx2.h b/src/arch/avx2.h index 74aad53..1c7248b 100644 --- a/src/arch/avx2.h +++ b/src/arch/avx2.h @@ -437,5 +437,27 @@ is_eo_even(cube_t cube) e = _mm256_slli_epi16(e, 7-EOSHIFT); mask = _mm256_movemask_epi8(e); - return popcount_u32(mask) % 2; + return popcount_u32(mask) % 2 == 0; +} + +STATIC_INLINE uint64_t +coord_epudsep(cube_t cube) +{ + uint8_t aux[32]; + + _mm256_storeu_si256((__m256i_u *)aux, cube); + return coord_epudsep_array(aux + 16); +} + +STATIC_INLINE cube_t +invcoord_epudsep(uint64_t i) +{ + cube_t cube, elow; + uint8_t e[32]; + + invcoord_epudsep_array(i, e+16); + elow = _mm256_load_si256((__m256i *)e); + cube = _mm256_set_epi64x(SOLVED_H, 0, 0, SOLVED_L); + + return _mm256_or_si256(elow, cube); } diff --git a/src/arch/common.h b/src/arch/common.h index d76b65f..f06f8d7 100644 --- a/src/arch/common.h +++ b/src/arch/common.h @@ -29,6 +29,8 @@ STATIC_INLINE uint64_t coord_cocsep(cube_t); STATIC_INLINE uint64_t coord_eo(cube_t); STATIC_INLINE uint64_t coord_esep(cube_t); STATIC_INLINE cube_t invcoord_esep(uint64_t); +STATIC_INLINE uint64_t coord_epudsep(cube_t); +STATIC_INLINE cube_t invcoord_epudsep(uint64_t); STATIC_INLINE bool is_eo_even(cube_t); @@ -38,6 +40,8 @@ STATIC_INLINE void set_eo(cube_t [static 1], uint64_t); STATIC_INLINE void invcoord_esep_array(uint64_t, uint64_t, uint8_t[static 12]); STATIC_INLINE cube_t invcoord_eoesep(uint64_t); +STATIC_INLINE uint64_t coord_epudsep_array(const uint8_t [8]); +STATIC_INLINE void invcoord_epudsep_array(uint64_t, uint8_t [8]); STATIC_INLINE uint64_t coord_cp(cube_t); STATIC_INLINE cube_t invcoord_cp(uint64_t); @@ -85,3 +89,38 @@ invcoord_eoesep(uint64_t i) return c; } + +STATIC_INLINE uint64_t +coord_epudsep_array(const uint8_t e[8]) +{ + uint8_t i, k, is; + uint64_t ret; + + ret = 0; + k = 4; + for (i = 0; i < 8; i++) { + is = (e[i] & UINT8_C(4)) >> UINT8_C(2); + ret += is * binomial[7-i][k]; + k -= is; + } + + return ret; +} + +STATIC_INLINE void +invcoord_epudsep_array(uint64_t c, uint8_t ret[8]) +{ + uint8_t i, k, is, x, y; + + k = 4; + x = 0; + y = 4; + for (i = 0; i < 8; i++) { + is = c >= binomial[7-i][k]; + ret[i] = is*y + (1-is)*x; + y += is; + x += 1-is; + c -= is * binomial[7-i][k]; + k -= is; + } +} diff --git a/src/arch/neon.h b/src/arch/neon.h index 2c35c58..9871125 100644 --- a/src/arch/neon.h +++ b/src/arch/neon.h @@ -453,7 +453,7 @@ invcoord_cp(uint64_t i) { return (cube_t) { .corner = indextoperm_8x8(i), - .edge = vcombine_u8(vld1_u8(SOLVED_L), vld1_u8(SOLVED_H)) + .edge = vcombine_u8(vld1_u8(SOLVED_L), vld1_u8(SOLVED_H)) }; } @@ -515,3 +515,24 @@ is_eo_even(cube_t cube) return count % 2 == 0; } + +STATIC_INLINE uint64_t +coord_epudsep(cube_t cube) +{ + uint8_t e[8]; + + vst1_u8(e, vget_low_u8(cube.edge)); + return coord_epudsep_array(e); +} + +STATIC_INLINE cube_t +invcoord_epudsep(uint64_t i) +{ + uint8_t e[8]; + + invcoord_epudsep_array(i, e); + return (cube_t) { + .corner = vld1_u8(SOLVED_L), + .edge = vcombine_u8(vld1_u8(e), vld1_u8(SOLVED_H)) + }; +} diff --git a/src/arch/portable.h b/src/arch/portable.h index d673f15..c7f2de0 100644 --- a/src/arch/portable.h +++ b/src/arch/portable.h @@ -367,3 +367,19 @@ is_eo_even(cube_t cube) return count % 2 == 0; } + +STATIC_INLINE uint64_t +coord_epudsep(cube_t cube) +{ + return coord_epudsep_array(cube.edge); +} + +STATIC_INLINE cube_t +invcoord_epudsep(uint64_t c) +{ + cube_t ret; + + ret = SOLVED_CUBE; + invcoord_epudsep_array(c, ret.edge); + return ret; +} -- cgit v1.3