Repository: ClickHouse/ClickHouse
File: src/Compression/LZ4_decompress_faster.cpp (C++)

Code before:
    };

    static constexpr UInt8 shifts[]
        = {0, 1, 2, 2, 4, 2, 2, 4, 8, 5, 2, 10, 8, 6, 4, 2, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1};

    if (offset >= 16)
    {
        unalignedStore<uint8x16_t>(op,
            unalignedLoad<uint8x16_t>(match));

        unalignedStore<uint8x16_t>(op + 16,
            unalignedLoad<uint8x16_t>(match + 16));
    }
    else
    {
        unalignedStore<uint8x8_t>(op,
            vtbl2_u8(unalignedLoad<uint8x8x2_t>(match), unalignedLoad<uint8x8_t>(masks_lo + 16 * offset)));

        unalignedStore<uint8x8_t>(op + 8,
            vtbl2_u8(unalignedLoad<uint8x8x2_t>(match), unalignedLoad<uint8x8_t>(masks_lo + 16 * offset + 8)));

        unalignedStore<uint8x8_t>(op + 16,
            vtbl2_u8(unalignedLoad<uint8x8x2_t>(match), unalignedLoad<uint8x8_t>(masks_hi + 16 * offset)));

        unalignedStore<uint8x8_t>(op + 24,
            vtbl2_u8(unalignedLoad<uint8x8x2_t>(match), unalignedLoad<uint8x8_t>(masks_hi + 16 * offset + 8)));
    }

    match += shifts[offset];

#else
    /// 4 % n
    static constexpr UInt8 shift1[] = {0, 1, 2, 1, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4, 4};

    /// 8 % n
    static constexpr UInt8 shift2[] = {0, 1, 2, 2, 4, 3, 2, 1, 0, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8};

    /// 16 % n
    static constexpr UInt8 shift3[]
        = {0, 1, 2, 1, 4, 1, 4, 2, 8, 7, 6, 5, 4, 3, 2, 1, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16};

    /// 32 % n
    static constexpr UInt8 shift4[]
        = {0, 1, 2, 2, 4, 2, 2, 4, 8, 5, 2, 10, 8, 6, 4, 2, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1};

    op[0] = match[0];
    op[1] = match[1];
    op[2] = match[2];
    op[3] = match[3];

    memcpy(op + 4, match + shift1[offset], 4);

Review comment (suggestion):
Just a comment: IIRC some time ago `vtbl2_u8` intrinsic required a 16-bit mask because `uint8x8x2_t` used two consecutive registers. A common work around for this to ensure 32 and 64 bits compatibility; was to use a `uint8x16_t` instead to force it.

Code after:

    /// Where to read from for the next 16 bytes (positions 16-31): equals (16 % offset) when that's non-zero, else 16.
    /// For offset=3: shift3[3]=1, because 16%3=1.
    /// For offset=5: shift3[5]=1, because 16%5=1.
    /// For offset=9: shift3[9]=7, because 16%9=7.
    /// For offset>=16: shift3[n]=16, reading the next fresh 16 bytes without wrapping.
    static constexpr UInt8 shift3[]
        = {0, 1, 2, 1, 4, 1, 4, 2, 8, 7, 6, 5, 4, 3, 2, 1, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16, 16};

    /// How far to advance match pointer after copying all 32 bytes: equals (32 % offset).
    /// This determines the final position after all four copy stages complete.
    /// Same values as the SSSE3 shifts table.
    static constexpr UInt8 shift4[]
        = {0, 1, 2, 2, 4, 2, 2, 4, 8, 5, 2, 10, 8, 6, 4, 2, 16, 15, 14, 13, 12, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1};

    /// Copy the first 4 bytes directly.
    op[0] = match[0];
    op[1] = match[1];
    op[2] = match[2];
    op[3] = match[3];

    /// Copy in stages, each reading from a position that maintains the repeating pattern.
    memcpy(op + 4, match + shift1[offset], 4);
    memcpy(op + 8, match + shift2[offset], 8);
    memcpy(op + 16, match + shift3[offset], 16);
    match += shift4[offset];
#endif
}


template <size_t copy_amount>
bool NO_INLINE decompressImpl(const char * const source, char * const dest, size_t source_size, size_t dest_size)
{
    const UInt8 * ip = reinterpret_cast<const UInt8 *>(source);
    UInt8 * op = reinterpret_cast<UInt8 *>(dest);
    const UInt8 * const input_end = ip + source_size;
    UInt8 * const output_begin = op;
    UInt8 * const output_end = op + dest_size;

    while (true)
    {
        size_t length;

        auto continue_read_length = [&]
        {
            unsigned s;
            do
            {
                s = *ip++;
                length += s;
            } while (unlikely(s == 255 && ip < input_end));