12940b44dSPeter Avalos ///////////////////////////////////////////////////////////////////////////////
22940b44dSPeter Avalos //
32940b44dSPeter Avalos /// \file delta_decoder.c
42940b44dSPeter Avalos /// \brief Delta filter decoder
52940b44dSPeter Avalos //
62940b44dSPeter Avalos // Author: Lasse Collin
72940b44dSPeter Avalos //
82940b44dSPeter Avalos // This file has been put into the public domain.
92940b44dSPeter Avalos // You can do whatever you want with this file.
102940b44dSPeter Avalos //
112940b44dSPeter Avalos ///////////////////////////////////////////////////////////////////////////////
122940b44dSPeter Avalos
132940b44dSPeter Avalos #include "delta_decoder.h"
142940b44dSPeter Avalos #include "delta_private.h"
152940b44dSPeter Avalos
162940b44dSPeter Avalos
172940b44dSPeter Avalos static void
decode_buffer(lzma_delta_coder * coder,uint8_t * buffer,size_t size)1846a2189dSzrj decode_buffer(lzma_delta_coder *coder, uint8_t *buffer, size_t size)
192940b44dSPeter Avalos {
202940b44dSPeter Avalos const size_t distance = coder->distance;
212940b44dSPeter Avalos
222940b44dSPeter Avalos for (size_t i = 0; i < size; ++i) {
232940b44dSPeter Avalos buffer[i] += coder->history[(distance + coder->pos) & 0xFF];
242940b44dSPeter Avalos coder->history[coder->pos-- & 0xFF] = buffer[i];
252940b44dSPeter Avalos }
262940b44dSPeter Avalos }
272940b44dSPeter Avalos
282940b44dSPeter Avalos
292940b44dSPeter Avalos static lzma_ret
delta_decode(void * coder_ptr,const lzma_allocator * allocator,const uint8_t * restrict in,size_t * restrict in_pos,size_t in_size,uint8_t * restrict out,size_t * restrict out_pos,size_t out_size,lzma_action action)3046a2189dSzrj delta_decode(void *coder_ptr, const lzma_allocator *allocator,
312940b44dSPeter Avalos const uint8_t *restrict in, size_t *restrict in_pos,
322940b44dSPeter Avalos size_t in_size, uint8_t *restrict out,
332940b44dSPeter Avalos size_t *restrict out_pos, size_t out_size, lzma_action action)
342940b44dSPeter Avalos {
3546a2189dSzrj lzma_delta_coder *coder = coder_ptr;
3646a2189dSzrj
372940b44dSPeter Avalos assert(coder->next.code != NULL);
382940b44dSPeter Avalos
392940b44dSPeter Avalos const size_t out_start = *out_pos;
402940b44dSPeter Avalos
412940b44dSPeter Avalos const lzma_ret ret = coder->next.code(coder->next.coder, allocator,
422940b44dSPeter Avalos in, in_pos, in_size, out, out_pos, out_size,
432940b44dSPeter Avalos action);
442940b44dSPeter Avalos
452940b44dSPeter Avalos decode_buffer(coder, out + out_start, *out_pos - out_start);
462940b44dSPeter Avalos
472940b44dSPeter Avalos return ret;
482940b44dSPeter Avalos }
492940b44dSPeter Avalos
502940b44dSPeter Avalos
512940b44dSPeter Avalos extern lzma_ret
lzma_delta_decoder_init(lzma_next_coder * next,const lzma_allocator * allocator,const lzma_filter_info * filters)5215ab8c86SJohn Marino lzma_delta_decoder_init(lzma_next_coder *next, const lzma_allocator *allocator,
532940b44dSPeter Avalos const lzma_filter_info *filters)
542940b44dSPeter Avalos {
552940b44dSPeter Avalos next->code = &delta_decode;
562940b44dSPeter Avalos return lzma_delta_coder_init(next, allocator, filters);
572940b44dSPeter Avalos }
582940b44dSPeter Avalos
592940b44dSPeter Avalos
602940b44dSPeter Avalos extern lzma_ret
lzma_delta_props_decode(void ** options,const lzma_allocator * allocator,const uint8_t * props,size_t props_size)6115ab8c86SJohn Marino lzma_delta_props_decode(void **options, const lzma_allocator *allocator,
622940b44dSPeter Avalos const uint8_t *props, size_t props_size)
632940b44dSPeter Avalos {
642940b44dSPeter Avalos if (props_size != 1)
652940b44dSPeter Avalos return LZMA_OPTIONS_ERROR;
662940b44dSPeter Avalos
672940b44dSPeter Avalos lzma_options_delta *opt
682940b44dSPeter Avalos = lzma_alloc(sizeof(lzma_options_delta), allocator);
692940b44dSPeter Avalos if (opt == NULL)
702940b44dSPeter Avalos return LZMA_MEM_ERROR;
712940b44dSPeter Avalos
722940b44dSPeter Avalos opt->type = LZMA_DELTA_TYPE_BYTE;
73*e151908bSDaniel Fojt opt->dist = props[0] + 1U;
742940b44dSPeter Avalos
752940b44dSPeter Avalos *options = opt;
762940b44dSPeter Avalos
772940b44dSPeter Avalos return LZMA_OK;
782940b44dSPeter Avalos }
79