Method: LZ4::BlockDecoder#update

Defined in:
ext/blockapi.c

#update(src, dest = "") ⇒ Object #update(src, max_dest_size, dest = "") ⇒ Object Also known as: decode, decompress, uncompress

Decode block lz4 data of stream block.

Given arguments and return values are same as LZ4#block_decode. See LZ4#block_decode for about its.

出力先は、max_dest_size が与えられていない場合、必要に応じて自動的に拡張されます。この場合、いったん圧縮された LZ4 データを走査するため、事前に僅かな CPU 時間を必要とします。



862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
# File 'ext/blockapi.c', line 862

static VALUE
blkdec_update(int argc, VALUE argv[], VALUE dec)
{
    struct blockdecoder *p = getdecoder(dec);
    if (!p->context) { rb_raise(extlz4_eError, "need reset (context not initialized)"); }
    VALUE src, dest;
    size_t maxsize;
    blockprocess_args(argc, argv, &src, &dest, &maxsize, NULL, aux_lz4_scansize);
    const char *srcp;
    size_t srcsize;
    RSTRING_GETMEM(src, srcp, srcsize);
    LZ4_setStreamDecode(p->context, p->dictbuf, aux_size2int(p->dictsize));
    int s = aux_LZ4_decompress_safe_continue(p->context, srcp, RSTRING_PTR(dest), aux_size2int(srcsize), aux_size2int(maxsize));
    if (s < 0) {
        rb_raise(extlz4_eError,
                "`max_dest_size' too small, or corrupt lz4'd data");
    }
    rb_str_set_len(dest, s);

    /* copy prefix */
    if ((size_t)s < sizeof(p->dictbuf)) {
        ssize_t discard = (p->dictsize + s) - sizeof(p->dictbuf);
        if (discard > 0) {
            size_t remain = p->dictsize - discard;
            memmove(p->dictbuf, (const char *)(p->dictbuf + discard), remain);
            p->dictsize = remain;
        }

        memcpy(p->dictbuf + p->dictsize, RSTRING_PTR(dest), s);
        p->dictsize += s;
    } else {
        memcpy(p->dictbuf, RSTRING_END(dest) - sizeof(p->dictbuf), sizeof(p->dictbuf));
        p->dictsize = sizeof(p->dictbuf);
    }

    return dest;
}