// A compiled version of std/machines/large_field/binary.asm

namespace main(128);
    col witness binary_op, a, b, c;
    // Dummy connection constraint
    [binary_op, a, b, c] is main_binary::latch * main_binary::sel[0] $ [main_binary::operation_id, main_binary::A, main_binary::B, main_binary::C];

namespace main_binary(128);
    col witness operation_id;
    (main_binary::operation_id' - main_binary::operation_id) * (1 - main_binary::latch) = 0;
    col fixed latch(i) { if i % 4_int == 3_int { 1_fe } else { 0_fe } };
    col fixed FACTOR(i) { 1_int << (i + 1_int) % 4_int * 8_int };
    col witness A_byte;
    col witness B_byte;
    col witness C_byte;
    col witness A;
    col witness B;
    col witness C;
    main_binary::A' = main_binary::A * (1 - main_binary::latch) + main_binary::A_byte * main_binary::FACTOR;
    main_binary::B' = main_binary::B * (1 - main_binary::latch) + main_binary::B_byte * main_binary::FACTOR;
    main_binary::C' = main_binary::C * (1 - main_binary::latch) + main_binary::C_byte * main_binary::FACTOR;
    col witness operation_id_next;
    main_binary::operation_id' = main_binary::operation_id_next;
    col witness sel[3];
    main_binary::sel[0] * (1 - main_binary::sel[0]) = 0;
    main_binary::sel[1] * (1 - main_binary::sel[1]) = 0;
    main_binary::sel[2] * (1 - main_binary::sel[2]) = 0;
    [main_binary::operation_id_next, main_binary::A_byte, main_binary::B_byte, main_binary::C_byte] in [main_byte_binary::P_operation, main_byte_binary::P_A, main_byte_binary::P_B, main_byte_binary::P_C];

namespace main_byte_binary(262144);
    let bit_counts: int[] = [256_int, 256_int, 3_int];
    let inputs: (int -> int)[] = std::utils::cross_product(main_byte_binary::bit_counts);
    let a: int -> int = main_byte_binary::inputs[0_int];
    let b: int -> int = main_byte_binary::inputs[1_int];
    let op: int -> int = main_byte_binary::inputs[2_int];
    let P_A: col = main_byte_binary::a;
    let P_B: col = main_byte_binary::b;
    let P_operation: col = main_byte_binary::op;
    col fixed P_C(i) { match main_byte_binary::op(i) {
        0 => main_byte_binary::a(i) & main_byte_binary::b(i),
        1 => main_byte_binary::a(i) | main_byte_binary::b(i),
        2 => main_byte_binary::a(i) ^ main_byte_binary::b(i),
    } };
namespace std::array;
    let<T> len: T[] -> int = [];

namespace std::utils;
    let cross_product: int[] -> (int -> int)[] = |sizes| std::utils::cross_product_internal(1_int, 0_int, sizes);
    let cross_product_internal: int, int, int[] -> (int -> int)[] = |cycle_len, pos, sizes| if pos >= std::array::len::<int>(sizes) { [] } else { [|i| i / cycle_len % sizes[pos]] + std::utils::cross_product_internal(cycle_len * sizes[pos], pos + 1_int, sizes) };