packages feed

KpqC-0.1.0: cbits/third_party/SMAUG-T/src/packring.c

// SPDX-License-Identifier: MIT

#include "packring.h"
#include "poly.h"

#include <string.h>

#if SMAUGT_LOG_P_PRIME == 3
/*************************************************
 * Name:        pack_R2_3
 *
 * Description: Transform to bytes array from polynomial in Rp' where p' = 2^3
 *              Use 3 bits to encode each coefficient in [0, 2^3).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_CTPOLY2_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rp'
 **************************************************/
void pack_R2_3(uint8_t bytes[SMAUGT_CTPOLY2_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_CTPOLY2_BYTES);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint32_t packed = 0;
        for (i = 0; i < 8; ++i) {

            packed |=
                ((uint32_t)(data->coeffs[data_idx + i] & 0x0007) << (3 * i));
        }

        bytes[bytes_idx++] = (uint8_t)(packed & 0x000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 8) & 0x000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 16) & 0x000000ff);
    }
}

/*************************************************
 * Name:        unpack_R2_3
 *
 * Description: Transform to polynomial in Rp' from bytes array, where p' = 2^3
 *              Use 3 bits to decode each coefficient in [0, 2^3).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rp'
 *              - const uint8_t bytes[SMAUGT_CTPOLY2_BYTES]: pointer to input
 *              bytes
 **************************************************/
void unpack_R2_3(poly *data, const uint8_t bytes[SMAUGT_CTPOLY2_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint32_t packed = 0;
        packed = packed | ((uint32_t)bytes[bytes_idx++] & 0x000000ff);
        packed = packed | (((uint32_t)bytes[bytes_idx++] << 8) & 0x0000ff00);
        packed = packed | (((uint32_t)bytes[bytes_idx++] << 16) & 0x00ff0000);

        for (i = 0; i < 8; i++) {
            data->coeffs[data_idx + i] =
                (int16_t)((packed >> (3 * i)) & 0x00000007);
        }
    }
}
#elif SMAUGT_LOG_P_PRIME == 4
/*************************************************
 * Name:        pack_R2_4
 *
 * Description: Transform to bytes array from polynomial in Rp' where p' = 2^4
 *              Use 4 bits to encode each coefficient in [0, 2^4).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_CTPOLY2_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rp'
 **************************************************/
void pack_R2_4(uint8_t bytes[SMAUGT_CTPOLY2_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_CTPOLY2_BYTES);
    size_t bytes_idx = 0;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 2) {
        bytes[bytes_idx] = (uint8_t)(data->coeffs[data_idx] & 0x000f);
        bytes[bytes_idx++] |=
            (uint8_t)((data->coeffs[data_idx + 1] & 0x000f) << 4);
    }
}

/*************************************************
 * Name:        unpack_R2_4
 *
 * Description: Transform to polynomial in Rp' from bytes array, where p' = 2^4
 *              Use 4 bits to decode each coefficient in [0, 2^4).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rp'
 *              - const uint8_t bytes[SMAUGT_CTPOLY2_BYTES]: pointer to input
 *              bytes
 **************************************************/
void unpack_R2_4(poly *data, const uint8_t bytes[SMAUGT_CTPOLY2_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t bytes_idx = 0;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 2) {
        data->coeffs[data_idx] = (int16_t)(bytes[bytes_idx] & 0x000f);
        data->coeffs[data_idx + 1] =
            (int16_t)((bytes[bytes_idx++] >> 4) & 0x000f);
    }
}
#elif SMAUGT_LOG_P_PRIME == 5
/*************************************************
 * Name:        pack_R2_5
 *
 * Description: Transform to bytes array from polynomial in Rp' where p' = 2^5
 *              Use 5 bits to encode each coefficient in [0, 2^5).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_CTPOLY2_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rp'
 **************************************************/
void pack_R2_5(uint8_t bytes[SMAUGT_CTPOLY2_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_CTPOLY2_BYTES);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;

        for (i = 0; i < 8; ++i) {
            packed |=
                ((uint64_t)(data->coeffs[data_idx + i] & 0x001f) << (5 * i));
        }

        bytes[bytes_idx++] = (uint8_t)(packed & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 8) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 16) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 24) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 32) & 0x00000000000000ff);
    }
}

/*************************************************
 * Name:        unpack_R2_5
 *
 * Description: Transform to polynomial in Rp' from bytes array, where p' = 2^5
 *              Use 5 bits to decode each coefficient in [0, 2^5).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rp'
 *              - const uint8_t bytes[SMAUGT_CTPOLY2_BYTES]: pointer to input
 *              bytes
 **************************************************/
void unpack_R2_5(poly *data, const uint8_t bytes[SMAUGT_CTPOLY2_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;
        packed = packed | ((uint64_t)bytes[bytes_idx++] & 0x00000000000000ff);
        packed =
            packed | (((uint64_t)bytes[bytes_idx++] << 8) & 0x000000000000ff00);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 16) & 0x0000000000ff0000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 24) & 0x00000000ff000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 32) & 0x000000ff00000000);

        for (i = 0; i < 8; i++) {
            data->coeffs[data_idx + i] =
                (int16_t)((packed >> (5 * i)) & 0x000000000000001f);
        }
    }
}
#elif SMAUGT_LOG_P_PRIME == 7
/*************************************************
 * Name:        pack_R2_7
 *
 * Description: Transform to bytes array from polynomial in Rp' where p' = 2^7
 *              Use 7 bits to encode each coefficient in [0, 2^7).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_CTPOLY2_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rp'
 **************************************************/
void pack_R2_7(uint8_t bytes[SMAUGT_CTPOLY2_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_CTPOLY2_BYTES);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;
        for (i = 0; i < 8; ++i) {
            packed |=
                ((uint64_t)(data->coeffs[data_idx + i] & 0x007f) << (7 * i));
        }

        bytes[bytes_idx++] = (uint8_t)(packed & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 8) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 16) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 24) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 32) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 40) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 48) & 0x00000000000000ff);
    }
}

/*************************************************
 * Name:        unpack_R2_7
 *
 * Description: Transform to polynomial in Rp' from bytes array, where p' = 2^7
 *              Use 7 bits to decode each coefficient in [0, 2^7).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rp'
 *              - const bytes[SMAUGT_CTPOLY2_BYTES]: pointer to input bytes
 **************************************************/
void unpack_R2_7(poly *data, const uint8_t bytes[SMAUGT_CTPOLY2_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;
        packed = packed | ((uint64_t)bytes[bytes_idx++] & 0x00000000000000ff);
        packed =
            packed | (((uint64_t)bytes[bytes_idx++] << 8) & 0x000000000000ff00);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 16) & 0x0000000000ff0000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 24) & 0x00000000ff000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 32) & 0x000000ff00000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 40) & 0x0000ff0000000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 48) & 0x00ff000000000000);

        for (i = 0; i < 8; i++) {
            data->coeffs[data_idx + i] =
                (int16_t)((packed >> (7 * i)) & 0x000000000000007f);
        }
    }
}
#endif

#if SMAUGT_LOG_P == 8
/*************************************************
 * Name:        pack_R2_8
 *
 * Description: Transform to bytes array from polynomial in Rp where p = 2^8
 *              Use 8 bits to encode each coefficient in [0, 2^8).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_CTPOLY1_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rp
 **************************************************/
void pack_R2_8(uint8_t bytes[SMAUGT_CTPOLY1_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_CTPOLY1_BYTES);
    size_t i;
    for (i = 0; i < SMAUGT_N; ++i)
        bytes[i] = (uint8_t)(data->coeffs[i] & 0x00ff);
}

/*************************************************
 * Name:        unpack_R2_8
 *
 * Description: Transform to polynomial in Rp from bytes array, where p = 2^8
 *              Use 8 bits to decode each coefficient in [0, 2^8).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rp
 *              - const uint8_t bytes[SMAUGT_CTPOLY1_BYTES]: pointer to input
 *              bytes
 **************************************************/
void unpack_R2_8(poly *data, const uint8_t bytes[SMAUGT_CTPOLY1_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t i;
    for (i = 0; i < SMAUGT_N; ++i)
        data->coeffs[i] = (int16_t)(bytes[i] & 0xff);
}
#elif SMAUGT_LOG_P == 9
/*************************************************
 * Name:        pack_R2_9
 *
 * Description: Transform to bytes array from polynomial in Rp where p = 2^9
 *              Use 9 bits to encode each coefficient in [0, 2^9).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_CTPOLY1_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rp
 **************************************************/
void pack_R2_9(uint8_t bytes[SMAUGT_CTPOLY1_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_CTPOLY1_BYTES);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;
        uint8_t packed2 = 0;
        for (i = 0; i < 7; ++i) {
            packed |=
                ((uint64_t)(data->coeffs[data_idx + i] & 0x01ff) << (9 * i));
        }
        packed |= (uint64_t)(data->coeffs[data_idx + 7] & 0x0001) << 63;
        packed2 = (uint8_t)(data->coeffs[data_idx + 7] >> 1);

        bytes[bytes_idx++] = (uint8_t)(packed & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 8) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 16) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 24) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 32) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 40) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 48) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 56) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)(packed2 & 0xff);
    }
}

/*************************************************
 * Name:        unpack_R2_9
 *
 * Description: Transform to polynomial in Rp from bytes array, where p = 2^9
 *              Use 9 bits to decode each coefficient in [0, 2^9).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rp
 *              - const uint8_t bytes[SMAUGT_CTPOLY1_BYTES]: pointer to input
 *              bytes
 **************************************************/
void unpack_R2_9(poly *data, const uint8_t bytes[SMAUGT_CTPOLY1_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;
        uint8_t packed2 = 0;
        packed = packed | ((uint64_t)bytes[bytes_idx++] & 0x00000000000000ff);
        packed =
            packed | (((uint64_t)bytes[bytes_idx++] << 8) & 0x000000000000ff00);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 16) & 0x0000000000ff0000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 24) & 0x00000000ff000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 32) & 0x000000ff00000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 40) & 0x0000ff0000000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 48) & 0x00ff000000000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 56) & 0xff00000000000000);
        packed2 = bytes[bytes_idx++];

        for (i = 0; i < 7; i++) {
            data->coeffs[data_idx + i] =
                (int16_t)((packed >> (9 * i)) & 0x00000000000001ff);
        }
        data->coeffs[data_idx + 7] = (int16_t)(packed >> 63) & 0x0001;
        data->coeffs[data_idx + 7] |= ((int16_t)packed2 << 1 & 0x01fe);
    }
}
#endif

#if SMAUGT_LOG_Q == 10
/*************************************************
 * Name:        pack_R2_10
 *
 * Description: Transform to bytes array from polynomial in Rq where q = 2^10
 *              Use 10 bits to encode each coefficient in [0, 2^10).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_PKPOLY_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rq
 **************************************************/
void pack_R2_10(uint8_t bytes[SMAUGT_PKPOLY_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_PKPOLY_BYTES);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 4) {
        uint64_t packed = 0;
        for (i = 0; i < 4; ++i) {
            packed |= ((uint64_t)((data->coeffs[data_idx + i] >> 6) & 0x03ff)
                       << (10 * i));
        }

        bytes[bytes_idx++] = (uint8_t)(packed & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 8) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 16) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 24) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 32) & 0x00000000000000ff);
    }
}

/*************************************************
 * Name:        unpack_R2_10
 *
 * Description: Transform to polynomial in Rq from bytes array, where q = 2^10
 *              Use 10 bits to decode each coefficient in [0, 2^10).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rq
 *              - const uint8_t bytes[SMAUGT_PKPOLY_BYTES]: pointer to input
 *              bytes
 **************************************************/
void unpack_R2_10(poly *data, const uint8_t bytes[SMAUGT_PKPOLY_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 4) {
        uint64_t packed = 0;
        packed = packed | ((uint64_t)bytes[bytes_idx++] & 0x00000000000000ff);
        packed =
            packed | (((uint64_t)bytes[bytes_idx++] << 8) & 0x000000000000ff00);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 16) & 0x0000000000ff0000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 24) & 0x00000000ff000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 32) & 0x000000ff00000000);

        for (i = 0; i < 4; i++) {
            data->coeffs[data_idx + i] =
                (int16_t)(((packed >> (10 * i)) & 0x00000000000003ff) << 6);
        }
    }
}
#elif SMAUGT_LOG_Q == 11
/*************************************************
 * Name:        pack_R2_11
 *
 * Description: Transform to bytes array from polynomial in Rq where q = 2^11
 *              Use 11 bits to encode each coefficient in [0, 2^11).
 *
 * Arguments:   - uint8_t bytes[SMAUGT_PKPOLY_BYTES]: pointer to output bytes
 *              - const poly *data: pointer to input polynomial in Rq
 **************************************************/
void pack_R2_11(uint8_t bytes[SMAUGT_PKPOLY_BYTES], const poly *data) {
    memset(bytes, 0, sizeof(uint8_t) * SMAUGT_PKPOLY_BYTES);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;
        uint32_t packed2 = 0;

        for (i = 0; i < 5; ++i) {
            packed |= ((uint64_t)((data->coeffs[data_idx + i] >> 5) & 0x07ff)
                       << (11 * i));
        }
        packed |= (uint64_t)((data->coeffs[data_idx + 5] >> 5) & 0x0001) << 55;

        packed2 = (uint32_t)((data->coeffs[data_idx + 5] >> 6) & 0x03ff);
        for (i = 0; i < 2; ++i) {
            packed2 |=
                ((uint64_t)((data->coeffs[data_idx + 6 + i] >> 5) & 0x07ff)
                 << (10 + 11 * i));
        }

        bytes[bytes_idx++] = (uint8_t)(packed & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 8) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 16) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 24) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 32) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 40) & 0x00000000000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed >> 48) & 0x00000000000000ff);

        bytes[bytes_idx++] = (uint8_t)(packed2 & 0x000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed2 >> 8) & 0x000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed2 >> 16) & 0x000000ff);
        bytes[bytes_idx++] = (uint8_t)((packed2 >> 24) & 0x000000ff);
    }
}

/*************************************************
 * Name:        unpack_R2_11
 *
 * Description: Transform to polynomial in Rq from bytes array, where q = 2^11
 *              Use 11 bits to decode each coefficient in [0, 2^11).
 *
 * Arguments:   - poly *data: pointer to output polynomial in Rq
 *              - const uint8_t bytes[SMAUGT_PKPOLY_BYTES]: pointer to input
 *              bytes
 **************************************************/
void unpack_R2_11(poly *data, const uint8_t bytes[SMAUGT_PKPOLY_BYTES]) {
    memset(data, 0, sizeof(int16_t) * SMAUGT_N);
    size_t bytes_idx = 0;
    size_t i;
    for (size_t data_idx = 0; data_idx < SMAUGT_N; data_idx += 8) {
        uint64_t packed = 0;
        uint32_t packed2 = 0;
        packed = packed | ((uint64_t)bytes[bytes_idx++] & 0x00000000000000ff);
        packed =
            packed | (((uint64_t)bytes[bytes_idx++] << 8) & 0x000000000000ff00);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 16) & 0x0000000000ff0000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 24) & 0x00000000ff000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 32) & 0x000000ff00000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 40) & 0x0000ff0000000000);
        packed = packed |
                 (((uint64_t)bytes[bytes_idx++] << 48) & 0x00ff000000000000);

        packed2 = packed2 | ((uint64_t)bytes[bytes_idx++] & 0x00000000000000ff);
        packed2 = packed2 |
                  (((uint64_t)bytes[bytes_idx++] << 8) & 0x000000000000ff00);
        packed2 = packed2 |
                  (((uint64_t)bytes[bytes_idx++] << 16) & 0x0000000000ff0000);
        packed2 = packed2 |
                  (((uint64_t)bytes[bytes_idx++] << 24) & 0x00000000ff000000);

        for (i = 0; i < 5; i++) {
            data->coeffs[data_idx + i] =
                (int16_t)(((packed >> (11 * i)) & 0x00000000000007ff) << 5);
        }
        data->coeffs[data_idx + 5] = (int16_t)(((packed >> 55) & 0x0001) << 5);

        data->coeffs[data_idx + 5] |= (int16_t)((packed2 & 0x03ff) << 6);
        for (i = 0; i < 2; i++) {
            data->coeffs[data_idx + 6 + i] =
                (int16_t)(((packed2 >> (10 + 11 * i)) & 0x000007ff) << 5);
        }
    }
}
#endif