* lib: add heatshrink compress library * canvas: new icons format * scripts: add icons compression to assets generation script * assets: update assets * furi-hal: introduce furi-hal-compress * canvas: rework icon drawing with furi-hal-compress * lib: rework heatshrink lib for dynamic buffer allocation API * furi-hal-compress: add encode and decode API * furi-hal-compress: working decode * furi-hal-compress: support f6 target * scripts: format sources * furi-hal-compress: fix incorrect encoder reset * furi-hal: add compress initialization to f6 target Co-authored-by: あく <alleteam@gmail.com>
		
			
				
	
	
		
			101 lines
		
	
	
		
			3.8 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
			
		
		
	
	
			101 lines
		
	
	
		
			3.8 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
#ifndef HEATSHRINK_DECODER_H
 | 
						|
#define HEATSHRINK_DECODER_H
 | 
						|
 | 
						|
#include <stdint.h>
 | 
						|
#include <stddef.h>
 | 
						|
#include "heatshrink_common.h"
 | 
						|
#include "heatshrink_config.h"
 | 
						|
 | 
						|
typedef enum {
 | 
						|
    HSDR_SINK_OK,               /* data sunk, ready to poll */
 | 
						|
    HSDR_SINK_FULL,             /* out of space in internal buffer */
 | 
						|
    HSDR_SINK_ERROR_NULL=-1,    /* NULL argument */
 | 
						|
} HSD_sink_res;
 | 
						|
 | 
						|
typedef enum {
 | 
						|
    HSDR_POLL_EMPTY,            /* input exhausted */
 | 
						|
    HSDR_POLL_MORE,             /* more data remaining, call again w/ fresh output buffer */
 | 
						|
    HSDR_POLL_ERROR_NULL=-1,    /* NULL arguments */
 | 
						|
    HSDR_POLL_ERROR_UNKNOWN=-2,
 | 
						|
} HSD_poll_res;
 | 
						|
 | 
						|
typedef enum {
 | 
						|
    HSDR_FINISH_DONE,           /* output is done */
 | 
						|
    HSDR_FINISH_MORE,           /* more output remains */
 | 
						|
    HSDR_FINISH_ERROR_NULL=-1,  /* NULL arguments */
 | 
						|
} HSD_finish_res;
 | 
						|
 | 
						|
#if HEATSHRINK_DYNAMIC_ALLOC
 | 
						|
#define HEATSHRINK_DECODER_INPUT_BUFFER_SIZE(BUF) \
 | 
						|
    ((BUF)->input_buffer_size)
 | 
						|
#define HEATSHRINK_DECODER_WINDOW_BITS(BUF) \
 | 
						|
    ((BUF)->window_sz2)
 | 
						|
#define HEATSHRINK_DECODER_LOOKAHEAD_BITS(BUF) \
 | 
						|
    ((BUF)->lookahead_sz2)
 | 
						|
#else
 | 
						|
#define HEATSHRINK_DECODER_INPUT_BUFFER_SIZE(_) \
 | 
						|
    HEATSHRINK_STATIC_INPUT_BUFFER_SIZE
 | 
						|
#define HEATSHRINK_DECODER_WINDOW_BITS(_) \
 | 
						|
    (HEATSHRINK_STATIC_WINDOW_BITS)
 | 
						|
#define HEATSHRINK_DECODER_LOOKAHEAD_BITS(BUF) \
 | 
						|
    (HEATSHRINK_STATIC_LOOKAHEAD_BITS)
 | 
						|
#endif
 | 
						|
 | 
						|
typedef struct {
 | 
						|
    uint16_t input_size;        /* bytes in input buffer */
 | 
						|
    uint16_t input_index;       /* offset to next unprocessed input byte */
 | 
						|
    uint16_t output_count;      /* how many bytes to output */
 | 
						|
    uint16_t output_index;      /* index for bytes to output */
 | 
						|
    uint16_t head_index;        /* head of window buffer */
 | 
						|
    uint8_t state;              /* current state machine node */
 | 
						|
    uint8_t current_byte;       /* current byte of input */
 | 
						|
    uint8_t bit_index;          /* current bit index */
 | 
						|
 | 
						|
#if HEATSHRINK_DYNAMIC_ALLOC
 | 
						|
    /* Fields that are only used if dynamically allocated. */
 | 
						|
    uint8_t window_sz2;         /* window buffer bits */
 | 
						|
    uint8_t lookahead_sz2;      /* lookahead bits */
 | 
						|
    uint16_t input_buffer_size; /* input buffer size */
 | 
						|
 | 
						|
    /* Input buffer, then expansion window buffer */
 | 
						|
    uint8_t* buffers;
 | 
						|
#else
 | 
						|
    /* Input buffer, then expansion window buffer */
 | 
						|
    uint8_t buffers[(1 << HEATSHRINK_DECODER_WINDOW_BITS(_))
 | 
						|
        + HEATSHRINK_DECODER_INPUT_BUFFER_SIZE(_)];
 | 
						|
#endif
 | 
						|
} heatshrink_decoder;
 | 
						|
 | 
						|
#if HEATSHRINK_DYNAMIC_ALLOC
 | 
						|
/* Allocate a decoder with an input buffer of INPUT_BUFFER_SIZE bytes,
 | 
						|
 * an expansion buffer size of 2^WINDOW_SZ2, and a lookahead
 | 
						|
 * size of 2^lookahead_sz2. (The window buffer and lookahead sizes
 | 
						|
 * must match the settings used when the data was compressed.)
 | 
						|
 * Returns NULL on error. */
 | 
						|
heatshrink_decoder *heatshrink_decoder_alloc(uint8_t* buffer, uint16_t input_buffer_size,
 | 
						|
    uint8_t expansion_buffer_sz2, uint8_t lookahead_sz2);
 | 
						|
 | 
						|
/* Free a decoder. */
 | 
						|
void heatshrink_decoder_free(heatshrink_decoder *hsd);
 | 
						|
#endif
 | 
						|
 | 
						|
/* Reset a decoder. */
 | 
						|
void heatshrink_decoder_reset(heatshrink_decoder *hsd);
 | 
						|
 | 
						|
/* Sink at most SIZE bytes from IN_BUF into the decoder. *INPUT_SIZE is set to
 | 
						|
 * indicate how many bytes were actually sunk (in case a buffer was filled). */
 | 
						|
HSD_sink_res heatshrink_decoder_sink(heatshrink_decoder *hsd,
 | 
						|
    uint8_t *in_buf, size_t size, size_t *input_size);
 | 
						|
 | 
						|
/* Poll for output from the decoder, copying at most OUT_BUF_SIZE bytes into
 | 
						|
 * OUT_BUF (setting *OUTPUT_SIZE to the actual amount copied). */
 | 
						|
HSD_poll_res heatshrink_decoder_poll(heatshrink_decoder *hsd,
 | 
						|
    uint8_t *out_buf, size_t out_buf_size, size_t *output_size);
 | 
						|
 | 
						|
/* Notify the dencoder that the input stream is finished.
 | 
						|
 * If the return value is HSDR_FINISH_MORE, there is still more output, so
 | 
						|
 * call heatshrink_decoder_poll and repeat. */
 | 
						|
HSD_finish_res heatshrink_decoder_finish(heatshrink_decoder *hsd);
 | 
						|
 | 
						|
#endif
 |