#include "cm_leaf_queries_private.h"
#include "coduo_x87emu.h" /* defines EMULATE_X87; x87 shim when it is 1 */

enum {
    PLANE_SIGNBITS_TABLE_COUNT = 8,
    PLANE_SIDE_INVALID_READ_ADDRESS = 1
};

/*
 * Stock VA 0x80cb2ba..0x80cb462 keeps both normal.corner dot products in x87
 * registers with NO fstp DWORD (the long double locals model that) and fcomp's
 * each 80-bit dot against plane->dist unrounded (0x80cb449/0x80cb450).  Under
 * EMULATE_X87 long double collapses to double on arm64, so the dot is kept as
 * x87f and the compares are full-width; BOPS_DOT parameterizes the per-signbits
 * corner selection so the switch body is identical in both modes.
 */
#if EMULATE_X87
typedef x87f coduo_bops_dist_t;
#define BOPS_DOT(cx, cy, cz)                                                   \
    x87f_add(                                                                 \
        x87f_add(x87f_mul(x87f_load_f32(plane->normal[0]), x87f_load_f32(cx)),\
                 x87f_mul(x87f_load_f32(plane->normal[1]), x87f_load_f32(cy))),\
        x87f_mul(x87f_load_f32(plane->normal[2]), x87f_load_f32(cz)))
#else
typedef long double coduo_bops_dist_t;
#define BOPS_DOT(cx, cy, cz)                                                   \
    (plane->normal[0] * (cx) + plane->normal[1] * (cy) + plane->normal[2] * (cz))
#endif

int32_t BoxOnPlaneSide(const vec3_t emins, const vec3_t emaxs,
                       const cplane_t *plane)
{
    coduo_bops_dist_t dist1;
    coduo_bops_dist_t dist2;
    int32_t sides;

    /* ORIGINAL_BINARY_BUG:
     * Stock VA 0x080cb2a3..0x080cb46d zero-extends signbits, compares the
     * low byte with signed jge, and for values 8..127 branches to
     * "mov eax, ds:0x1; ret".  Values 128..255 instead index beyond the
     * eight-entry jump table into unrelated data.  Address 1 is not a real
     * plane-side result and neither is the out-of-range indirect branch:
     * valid producers build signbits as the three-bit normal mask 0..7, and
     * this portable representation preserves the original invalid-state
     * failure class for every corrupt byte.  See
     * original-bugs/engine-box-on-plane-side-invalid-signbits.md.
     */
    if (plane->signbits >= PLANE_SIGNBITS_TABLE_COUNT) {
        return *(volatile const int32_t *)(uintptr_t)
            PLANE_SIDE_INVALID_READ_ADDRESS;
    }

    switch (plane->signbits) {
    case 0:
        dist1 = BOPS_DOT(emaxs[0], emaxs[1], emaxs[2]);
        dist2 = BOPS_DOT(emins[0], emins[1], emins[2]);
        break;
    case 1:
        dist1 = BOPS_DOT(emins[0], emaxs[1], emaxs[2]);
        dist2 = BOPS_DOT(emaxs[0], emins[1], emins[2]);
        break;
    case 2:
        dist1 = BOPS_DOT(emaxs[0], emins[1], emaxs[2]);
        dist2 = BOPS_DOT(emins[0], emaxs[1], emins[2]);
        break;
    case 3:
        dist1 = BOPS_DOT(emins[0], emins[1], emaxs[2]);
        dist2 = BOPS_DOT(emaxs[0], emaxs[1], emins[2]);
        break;
    case 4:
        dist1 = BOPS_DOT(emaxs[0], emaxs[1], emins[2]);
        dist2 = BOPS_DOT(emins[0], emins[1], emaxs[2]);
        break;
    case 5:
        dist1 = BOPS_DOT(emins[0], emaxs[1], emins[2]);
        dist2 = BOPS_DOT(emaxs[0], emins[1], emaxs[2]);
        break;
    case 6:
        dist1 = BOPS_DOT(emaxs[0], emins[1], emins[2]);
        dist2 = BOPS_DOT(emins[0], emaxs[1], emaxs[2]);
        break;
    case 7:
    default:
        dist1 = BOPS_DOT(emins[0], emins[1], emins[2]);
        dist2 = BOPS_DOT(emaxs[0], emaxs[1], emaxs[2]);
        break;
    }

    sides = 0;
    /* fcomp each 80-bit dot vs plane->dist (float), unrounded -> full-width. */
#if EMULATE_X87
    if (x87f_le(x87f_load_f32(plane->dist), dist1)) {
        sides = 1;
    }
    if (x87f_lt(dist2, x87f_load_f32(plane->dist))) {
        sides |= 2;
    }
#else
    if (dist1 >= plane->dist) {
        sides = 1;
    }
    if (dist2 < plane->dist) {
        sides |= 2;
    }
#endif
    return sides;
}

#undef BOPS_DOT
