MCPcopy Create free account
hub / github.com/InteractiveComputerGraphics/SPlisHSPlasH / deflate_rle

Function deflate_rle

extern/zlib/src/deflate.c:2038–2103  ·  view source on GitHub ↗

=========================================================================== * For Z_RLE, simply look for runs of bytes, generate matches only of distance * one. Do not maintain a hash table. (It will be regenerated if this run of * deflate switches away from Z_RLE.) */

Source from the content-addressed store, hash-verified

2036 * deflate switches away from Z_RLE.)
2037 */
2038local block_state deflate_rle(deflate_state *s, int flush) {
2039 int bflush; /* set if current block must be flushed */
2040 uInt prev; /* byte at distance one to match */
2041 Bytef *scan, *strend; /* scan goes up to strend for length of run */
2042
2043 for (;;) {
2044 /* Make sure that we always have enough lookahead, except
2045 * at the end of the input file. We need MAX_MATCH bytes
2046 * for the longest run, plus one for the unrolled loop.
2047 */
2048 if (s->lookahead <= MAX_MATCH) {
2049 fill_window(s);
2050 if (s->lookahead <= MAX_MATCH && flush == Z_NO_FLUSH) {
2051 return need_more;
2052 }
2053 if (s->lookahead == 0) break; /* flush the current block */
2054 }
2055
2056 /* See how many times the previous byte repeats */
2057 s->match_length = 0;
2058 if (s->lookahead >= MIN_MATCH && s->strstart > 0) {
2059 scan = s->window + s->strstart - 1;
2060 prev = *scan;
2061 if (prev == *++scan && prev == *++scan && prev == *++scan) {
2062 strend = s->window + s->strstart + MAX_MATCH;
2063 do {
2064 } while (prev == *++scan && prev == *++scan &&
2065 prev == *++scan && prev == *++scan &&
2066 prev == *++scan && prev == *++scan &&
2067 prev == *++scan && prev == *++scan &&
2068 scan < strend);
2069 s->match_length = MAX_MATCH - (uInt)(strend - scan);
2070 if (s->match_length > s->lookahead)
2071 s->match_length = s->lookahead;
2072 }
2073 Assert(scan <= s->window + (uInt)(s->window_size - 1),
2074 "wild scan");
2075 }
2076
2077 /* Emit match if have run of MIN_MATCH or longer, else emit literal */
2078 if (s->match_length >= MIN_MATCH) {
2079 check_match(s, s->strstart, s->strstart - 1, s->match_length);
2080
2081 _tr_tally_dist(s, 1, s->match_length - MIN_MATCH, bflush);
2082
2083 s->lookahead -= s->match_length;
2084 s->strstart += s->match_length;
2085 s->match_length = 0;
2086 } else {
2087 /* No match, output a literal byte */
2088 Tracevv((stderr,"%c", s->window[s->strstart]));
2089 _tr_tally_lit(s, s->window[s->strstart], bflush);
2090 s->lookahead--;
2091 s->strstart++;
2092 }
2093 if (bflush) FLUSH_BLOCK(s, 0);
2094 }
2095 s->insert = 0;

Callers 1

deflateFunction · 0.85

Calls 2

fill_windowFunction · 0.85
check_matchFunction · 0.85

Tested by

no test coverage detected