Skip to content

poly.c: arithmetic shift right instead of logical shift right leads to hang #17

@Juul-Mc-Goa

Description

@Juul-Mc-Goa

I've been trying to use Lazer for image modifications, which means I tend to aggregate many statements (one for each pixel). Here's a simplified example for applying grayscale:

deg = 512
VBIG = 0

# grayscale ring
BIGMOD_RING = polyring_t(deg, LAB_RING_40.mod)
PRIMESIZE = str(ceil(log2(BIGMOD_RING.mod)))

# int version of grayscale coefficients
r_int = 3566836
g_int = 11999065
b_int = 1211315
# poly version of grayscale coefficients
r_poly = int_to_poly(r_int, BIGMOD_RING)
g_poly = int_to_poly(g_int, BIGMOD_RING)
b_poly = int_to_poly(b_int, BIGMOD_RING)

ID = int_to_poly(1, BIGMOD_RING)

width = 512
height = 1024
poly_nb = ceil(width * height / float(deg))

rgb_img = [random_pixels_poly() for _ in range(3 * poly_nb)]
grayscale_img = img_float_gr(rgb_img)
grayscale_error = img_diff_gr(rgb_img)

max_l2_u8 = (255**2) * deg
max_l2_diff = (418**2) * deg # difference between exact and floating point computations
norms = [max_l2_u8] * 3 + [max_l2_diff]

deg_list = [deg] * len(norms) * poly_nb
num_pols_list = [1] * len(norms) * poly_nb
norm_list = norms * poly_nb
num_constraints = poly_nb
PS = proof_statement(deg_list, num_pols_list, norm_list, num_constraints, PRIMESIZE)

j = 0
stat_left = [
    r_poly,
    g_poly,
    b_poly,
    ID,
]

while j < grayscale_nb:
    wit = witness(rgb_img, grayscale_error, j)

    if is_witness_small(wit):
        rhs = right_hand_side(grayscale_img, j)
        PS.fresh_statement(stat_left, wit, rhs)
        j += 1
    else:
        print("Too BIG in ", j)
        VBIG += 1

stmnt = PS.output_statement()
PS.smpl_verify()

When width = 512 and height = 1024, the program often hangs (but not always), and I have to kill my terminal.

This seems to be caused by an infinite loop in the labrador.c:project function: the condition jlproj_normsq(pi->p) > normsq here is always verified.

This in turn seems to result from a faulty computation of iwt->normsq: sometimes for some i, iwt->normsq[i] < 0.

It seems to boil down to the polyvec_sprodz function, which uses arithmetic shift right here instead of logical shift right.
Changing the poly.c file to have:

    g = _mm512_srli_epi64(h,32);
    f = _mm512_srli_epi64(f,32);

solves the issue.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions