Coverage Report

Created: 2026-05-30 06:33

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/lzo-2.10/src/lzo1b_d.ch
Line
Count
Source
1
/* lzo1b_d.ch -- implementation of the LZO1B decompression algorithm
2
3
   This file is part of the LZO real-time data compression library.
4
5
   Copyright (C) 1996-2017 Markus Franz Xaver Johannes Oberhumer
6
   All Rights Reserved.
7
8
   The LZO library is free software; you can redistribute it and/or
9
   modify it under the terms of the GNU General Public License as
10
   published by the Free Software Foundation; either version 2 of
11
   the License, or (at your option) any later version.
12
13
   The LZO library is distributed in the hope that it will be useful,
14
   but WITHOUT ANY WARRANTY; without even the implied warranty of
15
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16
   GNU General Public License for more details.
17
18
   You should have received a copy of the GNU General Public License
19
   along with the LZO library; see the file COPYING.
20
   If not, write to the Free Software Foundation, Inc.,
21
   51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
22
23
   Markus F.X.J. Oberhumer
24
   <markus@oberhumer.com>
25
   http://www.oberhumer.com/opensource/lzo/
26
 */
27
28
29
#include "lzo1_d.ch"
30
31
32
/***********************************************************************
33
// decompress a block of data.
34
************************************************************************/
35
36
LZO_PUBLIC(int)
37
DO_DECOMPRESS    ( const lzo_bytep in , lzo_uint  in_len,
38
                         lzo_bytep out, lzo_uintp out_len,
39
                         lzo_voidp wrkmem )
40
7.77k
{
41
7.77k
    lzo_bytep op;
42
7.77k
    const lzo_bytep ip;
43
7.77k
    lzo_uint t;
44
7.77k
    const lzo_bytep m_pos;
45
46
7.77k
    const lzo_bytep const ip_end = in + in_len;
47
#if defined(HAVE_ANY_OP)
48
998
    lzo_bytep const op_end = out + *out_len;
49
#endif
50
51
7.77k
    LZO_UNUSED(wrkmem);
52
53
7.77k
    op = out;
54
7.77k
    ip = in;
55
56
1.54M
    while (TEST_IP_AND_TEST_OP)
57
1.81M
    {
58
1.81M
        t = *ip++;      /* get marker */
59
60
1.81M
        if (t < R0MIN)      /* a literal run */
61
721k
        {
62
721k
            if (t == 0)             /* a R0 literal run */
63
103k
            {
64
103k
                NEED_IP(1);
65
21.7k
                t = *ip++;
66
103k
                if (t >= R0FAST - R0MIN)            /* a long R0 run */
67
26.7k
                {
68
26.7k
                    t -= R0FAST - R0MIN;
69
26.7k
                    if (t == 0)
70
13.0k
                        t = R0FAST;
71
13.6k
                    else
72
13.6k
                    {
73
#if 0
74
                        t = 256u << ((unsigned) t);
75
#else
76
                        /* help the optimizer */
77
13.6k
                        lzo_uint tt = 256;
78
27.0k
                        do tt <<= 1; while (--t > 0);
79
13.6k
                        t = tt;
80
13.6k
#endif
81
13.6k
                    }
82
83
26.7k
                    NEED_IP(t); NEED_OP(t);
84
3.05k
#if 1 && (LZO_OPT_UNALIGNED32)
85
4.11M
                    do {
86
4.11M
                        UA_COPY4(op+0, ip+0);
87
4.11M
                        UA_COPY4(op+4, ip+4);
88
4.11M
                        op += 8; ip += 8;
89
4.11M
                        t -= 8;
90
4.11M
                    } while (t > 0);
91
#else
92
                    MEMCPY8_DS(op,ip,t);
93
#endif
94
3.05k
                    continue;
95
3.06k
                }
96
76.6k
                t += R0MIN;                         /* a short R0 run */
97
76.6k
            }
98
99
695k
            NEED_IP(t); NEED_OP(t);
100
            /* copy literal run */
101
59.6k
#if 1 && (LZO_OPT_UNALIGNED32)
102
694k
            if (t >= 4)
103
303k
            {
104
2.00M
                do {
105
2.00M
                    UA_COPY4(op, ip);
106
2.00M
                    op += 4; ip += 4; t -= 4;
107
2.00M
                } while (t >= 4);
108
369k
                if (t > 0) do *op++ = *ip++; while (--t > 0);
109
303k
            }
110
391k
            else
111
391k
#endif
112
391k
            {
113
#if (M3O_BITS < 7)
114
190k
literal1:
115
190k
#endif
116
771k
                do *op++ = *ip++; while (--t > 0);
117
190k
            }
118
119
#if (M3O_BITS == 7)
120
literal2:
121
#endif
122
123
            /* after a literal a match must follow */
124
757k
            while (TEST_IP_AND_TEST_OP)
125
1.38M
            {
126
1.38M
                t = *ip++;          /* get R1 marker */
127
1.38M
                if (t >= R0MIN)
128
775k
                    goto match;
129
130
613k
                NEED_IP(2); NEED_OP(M2_MIN_LEN + 1);
131
132
            /* R1 match - a M2_MIN_LEN match + 1 byte literal */
133
551k
                assert((t & M2O_MASK) == t);
134
613k
                m_pos = op - M2_MIN_OFFSET;
135
613k
                m_pos -= t | (((lzo_uint) *ip++) << M2O_BITS);
136
551k
                assert(m_pos >= out); assert(m_pos < op);
137
613k
                TEST_LB(m_pos);
138
613k
                COPY_M2;
139
551k
                *op++ = *ip++;
140
551k
            }
141
142
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
143
62
            break;
144
#endif
145
303k
        }
146
147
1.86M
match:
148
149
1.86M
        if (t >= M2_MARKER)             /* a M2 match */
150
1.29M
        {
151
            /* get match offset */
152
1.29M
            NEED_IP(1);
153
1.29M
            m_pos = op - M2_MIN_OFFSET;
154
1.29M
            m_pos -= (t & M2O_MASK) | (((lzo_uint) *ip++) << M2O_BITS);
155
224k
            assert(m_pos >= out); assert(m_pos < op);
156
1.29M
            TEST_LB(m_pos);
157
158
            /* get match len */
159
1.29M
            t = (t >> M2O_BITS) - 1;
160
1.29M
            NEED_OP(t + M2_MIN_LEN - 1);
161
1.29M
            COPY_M2X;
162
1.29M
            MEMCPY_DS(op,m_pos,t);
163
224k
        }
164
578k
        else                            /* a M3 or M4 match */
165
578k
        {
166
            /* get match len */
167
578k
            t &= M3L_MASK;
168
578k
            if (t == 0)         /* a M4 match */
169
168k
            {
170
168k
                NEED_IP(1);
171
3.16M
                while (*ip == 0)
172
2.99M
                {
173
2.99M
                    t += 255;
174
2.99M
                    ip++;
175
2.99M
                    TEST_OV(t);
176
2.99M
                    NEED_IP(1);
177
2.49M
                }
178
168k
                t += (M4_MIN_LEN - M3_MIN_LEN) + *ip++;
179
7.44k
            }
180
181
            /* get match offset */
182
578k
            NEED_IP(2);
183
577k
            m_pos = op - (M3_MIN_OFFSET - M3_EOF_OFFSET);
184
577k
            m_pos -= *ip++ & M3O_MASK;
185
577k
            m_pos -= (lzo_uint)(*ip++) << M3O_BITS;
186
62.6k
#if defined(LZO_EOF_CODE)
187
577k
            if (m_pos == op)
188
6.83k
                goto eof_found;
189
571k
#endif
190
191
            /* copy match */
192
571k
            assert(m_pos >= out); assert(m_pos < op);
193
571k
            TEST_LB(m_pos); NEED_OP(t + M3_MIN_LEN - 1);
194
62.5k
#if (LZO_OPT_UNALIGNED32)
195
571k
            if (t >= 2 * 4 - (M3_MIN_LEN - 1) && (op - m_pos) >= 4)
196
406k
            {
197
406k
                UA_COPY4(op, m_pos);
198
406k
                op += 4; m_pos += 4; t -= 4 - (M3_MIN_LEN - 1);
199
18.7M
                do {
200
18.7M
                    UA_COPY4(op, m_pos);
201
18.7M
                    op += 4; m_pos += 4; t -= 4;
202
18.7M
                } while (t >= 4);
203
569k
                if (t > 0) do *op++ = *m_pos++; while (--t > 0);
204
406k
            }
205
164k
            else
206
164k
#endif
207
164k
            {
208
164k
            COPY_M3X;
209
164k
            MEMCPY_DS(op,m_pos,t);
210
164k
            }
211
212
213
#if (M3O_BITS < 7)
214
191k
            t = ip[-2] >> M3O_BITS;
215
191k
            if (t)
216
80.9k
            {
217
80.9k
                NEED_IP(t); NEED_OP(t);
218
19.8k
                goto literal1;
219
19.8k
            }
220
#elif (M3O_BITS == 7)
221
            /* optimized version */
222
            if (ip[-2] & (1 << M3O_BITS))
223
            {
224
                NEED_IP(1); NEED_OP(1);
225
                *op++ = *ip++;
226
                goto literal2;
227
            }
228
#endif
229
62.5k
        }
230
1.86M
    }
231
232
233
160
#if defined(LZO_EOF_CODE)
234
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
235
    /* no EOF code was found */
236
160
    *out_len = pd(op, out);
237
160
    return LZO_E_EOF_NOT_FOUND;
238
0
#endif
239
240
6.83k
eof_found:
241
6.83k
    assert(t == 1);
242
6.83k
#endif
243
6.83k
    *out_len = pd(op, out);
244
6.83k
    return (ip == ip_end ? LZO_E_OK :
245
6.83k
           (ip < ip_end  ? LZO_E_INPUT_NOT_CONSUMED : LZO_E_INPUT_OVERRUN));
246
247
248
#if defined(HAVE_NEED_IP)
249
477
input_overrun:
250
477
    *out_len = pd(op, out);
251
477
    return LZO_E_INPUT_OVERRUN;
252
0
#endif
253
254
#if defined(HAVE_NEED_OP)
255
68
output_overrun:
256
68
    *out_len = pd(op, out);
257
68
    return LZO_E_OUTPUT_OVERRUN;
258
0
#endif
259
260
#if defined(LZO_TEST_OVERRUN_LOOKBEHIND)
261
237
lookbehind_overrun:
262
237
    *out_len = pd(op, out);
263
237
    return LZO_E_LOOKBEHIND_OVERRUN;
264
#endif
265
7.77k
}
lzo1b_decompress
Line
Count
Source
40
4.30k
{
41
4.30k
    lzo_bytep op;
42
4.30k
    const lzo_bytep ip;
43
4.30k
    lzo_uint t;
44
4.30k
    const lzo_bytep m_pos;
45
46
4.30k
    const lzo_bytep const ip_end = in + in_len;
47
#if defined(HAVE_ANY_OP)
48
    lzo_bytep const op_end = out + *out_len;
49
#endif
50
51
4.30k
    LZO_UNUSED(wrkmem);
52
53
4.30k
    op = out;
54
4.30k
    ip = in;
55
56
1.09M
    while (TEST_IP_AND_TEST_OP)
57
1.09M
    {
58
1.09M
        t = *ip++;      /* get marker */
59
60
1.09M
        if (t < R0MIN)      /* a literal run */
61
462k
        {
62
462k
            if (t == 0)             /* a R0 literal run */
63
52.6k
            {
64
52.6k
                NEED_IP(1);
65
52.6k
                t = *ip++;
66
52.6k
                if (t >= R0FAST - R0MIN)            /* a long R0 run */
67
12.7k
                {
68
12.7k
                    t -= R0FAST - R0MIN;
69
12.7k
                    if (t == 0)
70
6.33k
                        t = R0FAST;
71
6.39k
                    else
72
6.39k
                    {
73
#if 0
74
                        t = 256u << ((unsigned) t);
75
#else
76
                        /* help the optimizer */
77
6.39k
                        lzo_uint tt = 256;
78
11.9k
                        do tt <<= 1; while (--t > 0);
79
6.39k
                        t = tt;
80
6.39k
#endif
81
6.39k
                    }
82
83
12.7k
                    NEED_IP(t); NEED_OP(t);
84
12.7k
#if 1 && (LZO_OPT_UNALIGNED32)
85
1.45M
                    do {
86
1.45M
                        UA_COPY4(op+0, ip+0);
87
1.45M
                        UA_COPY4(op+4, ip+4);
88
1.45M
                        op += 8; ip += 8;
89
1.45M
                        t -= 8;
90
1.45M
                    } while (t > 0);
91
#else
92
                    MEMCPY8_DS(op,ip,t);
93
#endif
94
12.7k
                    continue;
95
12.7k
                }
96
39.9k
                t += R0MIN;                         /* a short R0 run */
97
39.9k
            }
98
99
449k
            NEED_IP(t); NEED_OP(t);
100
            /* copy literal run */
101
449k
#if 1 && (LZO_OPT_UNALIGNED32)
102
449k
            if (t >= 4)
103
181k
            {
104
1.20M
                do {
105
1.20M
                    UA_COPY4(op, ip);
106
1.20M
                    op += 4; ip += 4; t -= 4;
107
1.20M
                } while (t >= 4);
108
238k
                if (t > 0) do *op++ = *ip++; while (--t > 0);
109
181k
            }
110
267k
            else
111
267k
#endif
112
267k
            {
113
#if (M3O_BITS < 7)
114
literal1:
115
#endif
116
424k
                do *op++ = *ip++; while (--t > 0);
117
267k
            }
118
119
#if (M3O_BITS == 7)
120
literal2:
121
#endif
122
123
            /* after a literal a match must follow */
124
494k
            while (TEST_IP_AND_TEST_OP)
125
494k
            {
126
494k
                t = *ip++;          /* get R1 marker */
127
494k
                if (t >= R0MIN)
128
449k
                    goto match;
129
130
44.7k
                NEED_IP(2); NEED_OP(M2_MIN_LEN + 1);
131
132
            /* R1 match - a M2_MIN_LEN match + 1 byte literal */
133
44.7k
                assert((t & M2O_MASK) == t);
134
44.7k
                m_pos = op - M2_MIN_OFFSET;
135
44.7k
                m_pos -= t | (((lzo_uint) *ip++) << M2O_BITS);
136
44.7k
                assert(m_pos >= out); assert(m_pos < op);
137
44.7k
                TEST_LB(m_pos);
138
44.7k
                COPY_M2;
139
44.7k
                *op++ = *ip++;
140
44.7k
            }
141
142
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
143
            break;
144
#endif
145
449k
        }
146
147
1.08M
match:
148
149
1.08M
        if (t >= M2_MARKER)             /* a M2 match */
150
719k
        {
151
            /* get match offset */
152
719k
            NEED_IP(1);
153
719k
            m_pos = op - M2_MIN_OFFSET;
154
719k
            m_pos -= (t & M2O_MASK) | (((lzo_uint) *ip++) << M2O_BITS);
155
719k
            assert(m_pos >= out); assert(m_pos < op);
156
719k
            TEST_LB(m_pos);
157
158
            /* get match len */
159
719k
            t = (t >> M2O_BITS) - 1;
160
719k
            NEED_OP(t + M2_MIN_LEN - 1);
161
719k
            COPY_M2X;
162
719k
            MEMCPY_DS(op,m_pos,t);
163
719k
        }
164
367k
        else                            /* a M3 or M4 match */
165
367k
        {
166
            /* get match len */
167
367k
            t &= M3L_MASK;
168
367k
            if (t == 0)         /* a M4 match */
169
118k
            {
170
118k
                NEED_IP(1);
171
468k
                while (*ip == 0)
172
350k
                {
173
350k
                    t += 255;
174
350k
                    ip++;
175
350k
                    TEST_OV(t);
176
350k
                    NEED_IP(1);
177
350k
                }
178
118k
                t += (M4_MIN_LEN - M3_MIN_LEN) + *ip++;
179
118k
            }
180
181
            /* get match offset */
182
367k
            NEED_IP(2);
183
367k
            m_pos = op - (M3_MIN_OFFSET - M3_EOF_OFFSET);
184
367k
            m_pos -= *ip++ & M3O_MASK;
185
367k
            m_pos -= (lzo_uint)(*ip++) << M3O_BITS;
186
367k
#if defined(LZO_EOF_CODE)
187
367k
            if (m_pos == op)
188
4.30k
                goto eof_found;
189
362k
#endif
190
191
            /* copy match */
192
367k
            assert(m_pos >= out); assert(m_pos < op);
193
362k
            TEST_LB(m_pos); NEED_OP(t + M3_MIN_LEN - 1);
194
362k
#if (LZO_OPT_UNALIGNED32)
195
362k
            if (t >= 2 * 4 - (M3_MIN_LEN - 1) && (op - m_pos) >= 4)
196
246k
            {
197
246k
                UA_COPY4(op, m_pos);
198
246k
                op += 4; m_pos += 4; t -= 4 - (M3_MIN_LEN - 1);
199
10.1M
                do {
200
10.1M
                    UA_COPY4(op, m_pos);
201
10.1M
                    op += 4; m_pos += 4; t -= 4;
202
10.1M
                } while (t >= 4);
203
337k
                if (t > 0) do *op++ = *m_pos++; while (--t > 0);
204
246k
            }
205
116k
            else
206
116k
#endif
207
116k
            {
208
116k
            COPY_M3X;
209
116k
            MEMCPY_DS(op,m_pos,t);
210
116k
            }
211
212
213
#if (M3O_BITS < 7)
214
            t = ip[-2] >> M3O_BITS;
215
            if (t)
216
            {
217
                NEED_IP(t); NEED_OP(t);
218
                goto literal1;
219
            }
220
#elif (M3O_BITS == 7)
221
            /* optimized version */
222
            if (ip[-2] & (1 << M3O_BITS))
223
            {
224
                NEED_IP(1); NEED_OP(1);
225
                *op++ = *ip++;
226
                goto literal2;
227
            }
228
#endif
229
362k
        }
230
1.08M
    }
231
232
233
0
#if defined(LZO_EOF_CODE)
234
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
235
    /* no EOF code was found */
236
    *out_len = pd(op, out);
237
    return LZO_E_EOF_NOT_FOUND;
238
#endif
239
240
4.30k
eof_found:
241
4.30k
    assert(t == 1);
242
4.30k
#endif
243
4.30k
    *out_len = pd(op, out);
244
4.30k
    return (ip == ip_end ? LZO_E_OK :
245
4.30k
           (ip < ip_end  ? LZO_E_INPUT_NOT_CONSUMED : LZO_E_INPUT_OVERRUN));
246
247
248
#if defined(HAVE_NEED_IP)
249
input_overrun:
250
    *out_len = pd(op, out);
251
    return LZO_E_INPUT_OVERRUN;
252
#endif
253
254
#if defined(HAVE_NEED_OP)
255
output_overrun:
256
    *out_len = pd(op, out);
257
    return LZO_E_OUTPUT_OVERRUN;
258
#endif
259
260
#if defined(LZO_TEST_OVERRUN_LOOKBEHIND)
261
lookbehind_overrun:
262
    *out_len = pd(op, out);
263
    return LZO_E_LOOKBEHIND_OVERRUN;
264
#endif
265
4.30k
}
lzo1c_decompress
Line
Count
Source
40
2.46k
{
41
2.46k
    lzo_bytep op;
42
2.46k
    const lzo_bytep ip;
43
2.46k
    lzo_uint t;
44
2.46k
    const lzo_bytep m_pos;
45
46
2.46k
    const lzo_bytep const ip_end = in + in_len;
47
#if defined(HAVE_ANY_OP)
48
    lzo_bytep const op_end = out + *out_len;
49
#endif
50
51
2.46k
    LZO_UNUSED(wrkmem);
52
53
2.46k
    op = out;
54
2.46k
    ip = in;
55
56
445k
    while (TEST_IP_AND_TEST_OP)
57
445k
    {
58
445k
        t = *ip++;      /* get marker */
59
60
445k
        if (t < R0MIN)      /* a literal run */
61
196k
        {
62
196k
            if (t == 0)             /* a R0 literal run */
63
28.8k
            {
64
28.8k
                NEED_IP(1);
65
28.8k
                t = *ip++;
66
28.8k
                if (t >= R0FAST - R0MIN)            /* a long R0 run */
67
10.8k
                {
68
10.8k
                    t -= R0FAST - R0MIN;
69
10.8k
                    if (t == 0)
70
4.94k
                        t = R0FAST;
71
5.89k
                    else
72
5.89k
                    {
73
#if 0
74
                        t = 256u << ((unsigned) t);
75
#else
76
                        /* help the optimizer */
77
5.89k
                        lzo_uint tt = 256;
78
12.5k
                        do tt <<= 1; while (--t > 0);
79
5.89k
                        t = tt;
80
5.89k
#endif
81
5.89k
                    }
82
83
10.8k
                    NEED_IP(t); NEED_OP(t);
84
10.8k
#if 1 && (LZO_OPT_UNALIGNED32)
85
2.32M
                    do {
86
2.32M
                        UA_COPY4(op+0, ip+0);
87
2.32M
                        UA_COPY4(op+4, ip+4);
88
2.32M
                        op += 8; ip += 8;
89
2.32M
                        t -= 8;
90
2.32M
                    } while (t > 0);
91
#else
92
                    MEMCPY8_DS(op,ip,t);
93
#endif
94
10.8k
                    continue;
95
10.8k
                }
96
18.0k
                t += R0MIN;                         /* a short R0 run */
97
18.0k
            }
98
99
186k
            NEED_IP(t); NEED_OP(t);
100
            /* copy literal run */
101
186k
#if 1 && (LZO_OPT_UNALIGNED32)
102
186k
            if (t >= 4)
103
86.6k
            {
104
584k
                do {
105
584k
                    UA_COPY4(op, ip);
106
584k
                    op += 4; ip += 4; t -= 4;
107
584k
                } while (t >= 4);
108
105k
                if (t > 0) do *op++ = *ip++; while (--t > 0);
109
86.6k
            }
110
99.3k
            else
111
99.3k
#endif
112
99.3k
            {
113
99.3k
#if (M3O_BITS < 7)
114
160k
literal1:
115
160k
#endif
116
264k
                do *op++ = *ip++; while (--t > 0);
117
160k
            }
118
119
#if (M3O_BITS == 7)
120
literal2:
121
#endif
122
123
            /* after a literal a match must follow */
124
263k
            while (TEST_IP_AND_TEST_OP)
125
263k
            {
126
263k
                t = *ip++;          /* get R1 marker */
127
263k
                if (t >= R0MIN)
128
247k
                    goto match;
129
130
16.5k
                NEED_IP(2); NEED_OP(M2_MIN_LEN + 1);
131
132
            /* R1 match - a M2_MIN_LEN match + 1 byte literal */
133
16.5k
                assert((t & M2O_MASK) == t);
134
16.5k
                m_pos = op - M2_MIN_OFFSET;
135
16.5k
                m_pos -= t | (((lzo_uint) *ip++) << M2O_BITS);
136
16.5k
                assert(m_pos >= out); assert(m_pos < op);
137
16.5k
                TEST_LB(m_pos);
138
16.5k
                COPY_M2;
139
16.5k
                *op++ = *ip++;
140
16.5k
            }
141
142
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
143
            break;
144
#endif
145
247k
        }
146
147
495k
match:
148
149
495k
        if (t >= M2_MARKER)             /* a M2 match */
150
347k
        {
151
            /* get match offset */
152
347k
            NEED_IP(1);
153
347k
            m_pos = op - M2_MIN_OFFSET;
154
347k
            m_pos -= (t & M2O_MASK) | (((lzo_uint) *ip++) << M2O_BITS);
155
347k
            assert(m_pos >= out); assert(m_pos < op);
156
347k
            TEST_LB(m_pos);
157
158
            /* get match len */
159
347k
            t = (t >> M2O_BITS) - 1;
160
347k
            NEED_OP(t + M2_MIN_LEN - 1);
161
347k
            COPY_M2X;
162
347k
            MEMCPY_DS(op,m_pos,t);
163
347k
        }
164
148k
        else                            /* a M3 or M4 match */
165
148k
        {
166
            /* get match len */
167
148k
            t &= M3L_MASK;
168
148k
            if (t == 0)         /* a M4 match */
169
42.6k
            {
170
42.6k
                NEED_IP(1);
171
187k
                while (*ip == 0)
172
145k
                {
173
145k
                    t += 255;
174
145k
                    ip++;
175
145k
                    TEST_OV(t);
176
145k
                    NEED_IP(1);
177
145k
                }
178
42.6k
                t += (M4_MIN_LEN - M3_MIN_LEN) + *ip++;
179
42.6k
            }
180
181
            /* get match offset */
182
148k
            NEED_IP(2);
183
148k
            m_pos = op - (M3_MIN_OFFSET - M3_EOF_OFFSET);
184
148k
            m_pos -= *ip++ & M3O_MASK;
185
148k
            m_pos -= (lzo_uint)(*ip++) << M3O_BITS;
186
148k
#if defined(LZO_EOF_CODE)
187
148k
            if (m_pos == op)
188
2.46k
                goto eof_found;
189
145k
#endif
190
191
            /* copy match */
192
148k
            assert(m_pos >= out); assert(m_pos < op);
193
145k
            TEST_LB(m_pos); NEED_OP(t + M3_MIN_LEN - 1);
194
145k
#if (LZO_OPT_UNALIGNED32)
195
145k
            if (t >= 2 * 4 - (M3_MIN_LEN - 1) && (op - m_pos) >= 4)
196
109k
            {
197
109k
                UA_COPY4(op, m_pos);
198
109k
                op += 4; m_pos += 4; t -= 4 - (M3_MIN_LEN - 1);
199
4.27M
                do {
200
4.27M
                    UA_COPY4(op, m_pos);
201
4.27M
                    op += 4; m_pos += 4; t -= 4;
202
4.27M
                } while (t >= 4);
203
163k
                if (t > 0) do *op++ = *m_pos++; while (--t > 0);
204
109k
            }
205
36.5k
            else
206
36.5k
#endif
207
36.5k
            {
208
36.5k
            COPY_M3X;
209
36.5k
            MEMCPY_DS(op,m_pos,t);
210
36.5k
            }
211
212
213
145k
#if (M3O_BITS < 7)
214
145k
            t = ip[-2] >> M3O_BITS;
215
145k
            if (t)
216
61.0k
            {
217
61.0k
                NEED_IP(t); NEED_OP(t);
218
61.0k
                goto literal1;
219
61.0k
            }
220
#elif (M3O_BITS == 7)
221
            /* optimized version */
222
            if (ip[-2] & (1 << M3O_BITS))
223
            {
224
                NEED_IP(1); NEED_OP(1);
225
                *op++ = *ip++;
226
                goto literal2;
227
            }
228
#endif
229
145k
        }
230
495k
    }
231
232
233
0
#if defined(LZO_EOF_CODE)
234
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
235
    /* no EOF code was found */
236
    *out_len = pd(op, out);
237
    return LZO_E_EOF_NOT_FOUND;
238
#endif
239
240
2.46k
eof_found:
241
2.46k
    assert(t == 1);
242
2.46k
#endif
243
2.46k
    *out_len = pd(op, out);
244
2.46k
    return (ip == ip_end ? LZO_E_OK :
245
2.46k
           (ip < ip_end  ? LZO_E_INPUT_NOT_CONSUMED : LZO_E_INPUT_OVERRUN));
246
247
248
#if defined(HAVE_NEED_IP)
249
input_overrun:
250
    *out_len = pd(op, out);
251
    return LZO_E_INPUT_OVERRUN;
252
#endif
253
254
#if defined(HAVE_NEED_OP)
255
output_overrun:
256
    *out_len = pd(op, out);
257
    return LZO_E_OUTPUT_OVERRUN;
258
#endif
259
260
#if defined(LZO_TEST_OVERRUN_LOOKBEHIND)
261
lookbehind_overrun:
262
    *out_len = pd(op, out);
263
    return LZO_E_LOOKBEHIND_OVERRUN;
264
#endif
265
2.46k
}
lzo1b_decompress_safe
Line
Count
Source
40
482
{
41
482
    lzo_bytep op;
42
482
    const lzo_bytep ip;
43
482
    lzo_uint t;
44
482
    const lzo_bytep m_pos;
45
46
482
    const lzo_bytep const ip_end = in + in_len;
47
482
#if defined(HAVE_ANY_OP)
48
482
    lzo_bytep const op_end = out + *out_len;
49
482
#endif
50
51
482
    LZO_UNUSED(wrkmem);
52
53
482
    op = out;
54
482
    ip = in;
55
56
482
    while (TEST_IP_AND_TEST_OP)
57
132k
    {
58
132k
        t = *ip++;      /* get marker */
59
60
132k
        if (t < R0MIN)      /* a literal run */
61
25.3k
        {
62
25.3k
            if (t == 0)             /* a R0 literal run */
63
6.01k
            {
64
6.01k
                NEED_IP(1);
65
6.00k
                t = *ip++;
66
6.00k
                if (t >= R0FAST - R0MIN)            /* a long R0 run */
67
1.75k
                {
68
1.75k
                    t -= R0FAST - R0MIN;
69
1.75k
                    if (t == 0)
70
1.07k
                        t = R0FAST;
71
681
                    else
72
681
                    {
73
#if 0
74
                        t = 256u << ((unsigned) t);
75
#else
76
                        /* help the optimizer */
77
681
                        lzo_uint tt = 256;
78
1.34k
                        do tt <<= 1; while (--t > 0);
79
681
                        t = tt;
80
681
#endif
81
681
                    }
82
83
1.75k
                    NEED_IP(t); NEED_OP(t);
84
1.70k
#if 1 && (LZO_OPT_UNALIGNED32)
85
181k
                    do {
86
181k
                        UA_COPY4(op+0, ip+0);
87
181k
                        UA_COPY4(op+4, ip+4);
88
181k
                        op += 8; ip += 8;
89
181k
                        t -= 8;
90
181k
                    } while (t > 0);
91
#else
92
                    MEMCPY8_DS(op,ip,t);
93
#endif
94
1.70k
                    continue;
95
1.71k
                }
96
4.24k
                t += R0MIN;                         /* a short R0 run */
97
4.24k
            }
98
99
23.5k
            NEED_IP(t); NEED_OP(t);
100
            /* copy literal run */
101
23.4k
#if 1 && (LZO_OPT_UNALIGNED32)
102
23.4k
            if (t >= 4)
103
10.0k
            {
104
63.1k
                do {
105
63.1k
                    UA_COPY4(op, ip);
106
63.1k
                    op += 4; ip += 4; t -= 4;
107
63.1k
                } while (t >= 4);
108
10.0k
                if (t > 0) do *op++ = *ip++; while (--t > 0);
109
10.0k
            }
110
13.4k
            else
111
13.4k
#endif
112
13.4k
            {
113
#if (M3O_BITS < 7)
114
literal1:
115
#endif
116
28.0k
                do *op++ = *ip++; while (--t > 0);
117
13.4k
            }
118
119
#if (M3O_BITS == 7)
120
literal2:
121
#endif
122
123
            /* after a literal a match must follow */
124
23.4k
            while (TEST_IP_AND_TEST_OP)
125
291k
            {
126
291k
                t = *ip++;          /* get R1 marker */
127
291k
                if (t >= R0MIN)
128
23.3k
                    goto match;
129
130
268k
                NEED_IP(2); NEED_OP(M2_MIN_LEN + 1);
131
132
            /* R1 match - a M2_MIN_LEN match + 1 byte literal */
133
268k
                assert((t & M2O_MASK) == t);
134
268k
                m_pos = op - M2_MIN_OFFSET;
135
268k
                m_pos -= t | (((lzo_uint) *ip++) << M2O_BITS);
136
268k
                assert(m_pos >= out); assert(m_pos < op);
137
268k
                TEST_LB(m_pos);
138
268k
                COPY_M2;
139
268k
                *op++ = *ip++;
140
268k
            }
141
142
23
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
143
23
            break;
144
23.4k
#endif
145
23.4k
        }
146
147
130k
match:
148
149
130k
        if (t >= M2_MARKER)             /* a M2 match */
150
113k
        {
151
            /* get match offset */
152
113k
            NEED_IP(1);
153
113k
            m_pos = op - M2_MIN_OFFSET;
154
113k
            m_pos -= (t & M2O_MASK) | (((lzo_uint) *ip++) << M2O_BITS);
155
113k
            assert(m_pos >= out); assert(m_pos < op);
156
113k
            TEST_LB(m_pos);
157
158
            /* get match len */
159
113k
            t = (t >> M2O_BITS) - 1;
160
113k
            NEED_OP(t + M2_MIN_LEN - 1);
161
113k
            COPY_M2X;
162
113k
            MEMCPY_DS(op,m_pos,t);
163
113k
        }
164
16.7k
        else                            /* a M3 or M4 match */
165
16.7k
        {
166
            /* get match len */
167
16.7k
            t &= M3L_MASK;
168
16.7k
            if (t == 0)         /* a M4 match */
169
1.70k
            {
170
1.70k
                NEED_IP(1);
171
1.05M
                while (*ip == 0)
172
1.05M
                {
173
1.05M
                    t += 255;
174
1.05M
                    ip++;
175
1.05M
                    TEST_OV(t);
176
1.05M
                    NEED_IP(1);
177
1.05M
                }
178
1.67k
                t += (M4_MIN_LEN - M3_MIN_LEN) + *ip++;
179
1.67k
            }
180
181
            /* get match offset */
182
16.7k
            NEED_IP(2);
183
16.6k
            m_pos = op - (M3_MIN_OFFSET - M3_EOF_OFFSET);
184
16.6k
            m_pos -= *ip++ & M3O_MASK;
185
16.6k
            m_pos -= (lzo_uint)(*ip++) << M3O_BITS;
186
16.6k
#if defined(LZO_EOF_CODE)
187
16.6k
            if (m_pos == op)
188
27
                goto eof_found;
189
16.6k
#endif
190
191
            /* copy match */
192
16.6k
            assert(m_pos >= out); assert(m_pos < op);
193
16.6k
            TEST_LB(m_pos); NEED_OP(t + M3_MIN_LEN - 1);
194
16.5k
#if (LZO_OPT_UNALIGNED32)
195
16.5k
            if (t >= 2 * 4 - (M3_MIN_LEN - 1) && (op - m_pos) >= 4)
196
14.0k
            {
197
14.0k
                UA_COPY4(op, m_pos);
198
14.0k
                op += 4; m_pos += 4; t -= 4 - (M3_MIN_LEN - 1);
199
1.66M
                do {
200
1.66M
                    UA_COPY4(op, m_pos);
201
1.66M
                    op += 4; m_pos += 4; t -= 4;
202
1.66M
                } while (t >= 4);
203
19.8k
                if (t > 0) do *op++ = *m_pos++; while (--t > 0);
204
14.0k
            }
205
2.52k
            else
206
2.52k
#endif
207
2.52k
            {
208
2.52k
            COPY_M3X;
209
2.52k
            MEMCPY_DS(op,m_pos,t);
210
2.52k
            }
211
212
213
#if (M3O_BITS < 7)
214
            t = ip[-2] >> M3O_BITS;
215
            if (t)
216
            {
217
                NEED_IP(t); NEED_OP(t);
218
                goto literal1;
219
            }
220
#elif (M3O_BITS == 7)
221
            /* optimized version */
222
            if (ip[-2] & (1 << M3O_BITS))
223
            {
224
                NEED_IP(1); NEED_OP(1);
225
                *op++ = *ip++;
226
                goto literal2;
227
            }
228
#endif
229
16.5k
        }
230
130k
    }
231
232
233
66
#if defined(LZO_EOF_CODE)
234
66
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
235
    /* no EOF code was found */
236
66
    *out_len = pd(op, out);
237
66
    return LZO_E_EOF_NOT_FOUND;
238
0
#endif
239
240
27
eof_found:
241
27
    assert(t == 1);
242
27
#endif
243
27
    *out_len = pd(op, out);
244
27
    return (ip == ip_end ? LZO_E_OK :
245
27
           (ip < ip_end  ? LZO_E_INPUT_NOT_CONSUMED : LZO_E_INPUT_OVERRUN));
246
247
248
0
#if defined(HAVE_NEED_IP)
249
233
input_overrun:
250
233
    *out_len = pd(op, out);
251
233
    return LZO_E_INPUT_OVERRUN;
252
0
#endif
253
254
0
#if defined(HAVE_NEED_OP)
255
29
output_overrun:
256
29
    *out_len = pd(op, out);
257
29
    return LZO_E_OUTPUT_OVERRUN;
258
0
#endif
259
260
0
#if defined(LZO_TEST_OVERRUN_LOOKBEHIND)
261
127
lookbehind_overrun:
262
127
    *out_len = pd(op, out);
263
127
    return LZO_E_LOOKBEHIND_OVERRUN;
264
482
#endif
265
482
}
lzo1c_decompress_safe
Line
Count
Source
40
516
{
41
516
    lzo_bytep op;
42
516
    const lzo_bytep ip;
43
516
    lzo_uint t;
44
516
    const lzo_bytep m_pos;
45
46
516
    const lzo_bytep const ip_end = in + in_len;
47
516
#if defined(HAVE_ANY_OP)
48
516
    lzo_bytep const op_end = out + *out_len;
49
516
#endif
50
51
516
    LZO_UNUSED(wrkmem);
52
53
516
    op = out;
54
516
    ip = in;
55
56
516
    while (TEST_IP_AND_TEST_OP)
57
139k
    {
58
139k
        t = *ip++;      /* get marker */
59
60
139k
        if (t < R0MIN)      /* a literal run */
61
37.6k
        {
62
37.6k
            if (t == 0)             /* a R0 literal run */
63
15.7k
            {
64
15.7k
                NEED_IP(1);
65
15.7k
                t = *ip++;
66
15.7k
                if (t >= R0FAST - R0MIN)            /* a long R0 run */
67
1.40k
                {
68
1.40k
                    t -= R0FAST - R0MIN;
69
1.40k
                    if (t == 0)
70
725
                        t = R0FAST;
71
680
                    else
72
680
                    {
73
#if 0
74
                        t = 256u << ((unsigned) t);
75
#else
76
                        /* help the optimizer */
77
680
                        lzo_uint tt = 256;
78
1.29k
                        do tt <<= 1; while (--t > 0);
79
680
                        t = tt;
80
680
#endif
81
680
                    }
82
83
1.40k
                    NEED_IP(t); NEED_OP(t);
84
1.35k
#if 1 && (LZO_OPT_UNALIGNED32)
85
155k
                    do {
86
155k
                        UA_COPY4(op+0, ip+0);
87
155k
                        UA_COPY4(op+4, ip+4);
88
155k
                        op += 8; ip += 8;
89
155k
                        t -= 8;
90
155k
                    } while (t > 0);
91
#else
92
                    MEMCPY8_DS(op,ip,t);
93
#endif
94
1.35k
                    continue;
95
1.35k
                }
96
14.3k
                t += R0MIN;                         /* a short R0 run */
97
14.3k
            }
98
99
36.2k
            NEED_IP(t); NEED_OP(t);
100
            /* copy literal run */
101
36.1k
#if 1 && (LZO_OPT_UNALIGNED32)
102
36.1k
            if (t >= 4)
103
25.5k
            {
104
158k
                do {
105
158k
                    UA_COPY4(op, ip);
106
158k
                    op += 4; ip += 4; t -= 4;
107
158k
                } while (t >= 4);
108
25.5k
                if (t > 0) do *op++ = *ip++; while (--t > 0);
109
25.5k
            }
110
10.6k
            else
111
10.6k
#endif
112
10.6k
            {
113
10.6k
#if (M3O_BITS < 7)
114
30.4k
literal1:
115
30.4k
#endif
116
53.4k
                do *op++ = *ip++; while (--t > 0);
117
30.4k
            }
118
119
#if (M3O_BITS == 7)
120
literal2:
121
#endif
122
123
            /* after a literal a match must follow */
124
55.9k
            while (TEST_IP_AND_TEST_OP)
125
339k
            {
126
339k
                t = *ip++;          /* get R1 marker */
127
339k
                if (t >= R0MIN)
128
55.8k
                    goto match;
129
130
283k
                NEED_IP(2); NEED_OP(M2_MIN_LEN + 1);
131
132
            /* R1 match - a M2_MIN_LEN match + 1 byte literal */
133
283k
                assert((t & M2O_MASK) == t);
134
283k
                m_pos = op - M2_MIN_OFFSET;
135
283k
                m_pos -= t | (((lzo_uint) *ip++) << M2O_BITS);
136
283k
                assert(m_pos >= out); assert(m_pos < op);
137
283k
                TEST_LB(m_pos);
138
283k
                COPY_M2;
139
283k
                *op++ = *ip++;
140
283k
            }
141
142
39
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
143
39
            break;
144
55.9k
#endif
145
55.9k
        }
146
147
157k
match:
148
149
157k
        if (t >= M2_MARKER)             /* a M2 match */
150
111k
        {
151
            /* get match offset */
152
111k
            NEED_IP(1);
153
111k
            m_pos = op - M2_MIN_OFFSET;
154
111k
            m_pos -= (t & M2O_MASK) | (((lzo_uint) *ip++) << M2O_BITS);
155
111k
            assert(m_pos >= out); assert(m_pos < op);
156
111k
            TEST_LB(m_pos);
157
158
            /* get match len */
159
111k
            t = (t >> M2O_BITS) - 1;
160
111k
            NEED_OP(t + M2_MIN_LEN - 1);
161
111k
            COPY_M2X;
162
111k
            MEMCPY_DS(op,m_pos,t);
163
111k
        }
164
46.0k
        else                            /* a M3 or M4 match */
165
46.0k
        {
166
            /* get match len */
167
46.0k
            t &= M3L_MASK;
168
46.0k
            if (t == 0)         /* a M4 match */
169
5.79k
            {
170
5.79k
                NEED_IP(1);
171
1.44M
                while (*ip == 0)
172
1.43M
                {
173
1.43M
                    t += 255;
174
1.43M
                    ip++;
175
1.43M
                    TEST_OV(t);
176
1.43M
                    NEED_IP(1);
177
1.43M
                }
178
5.76k
                t += (M4_MIN_LEN - M3_MIN_LEN) + *ip++;
179
5.76k
            }
180
181
            /* get match offset */
182
46.0k
            NEED_IP(2);
183
46.0k
            m_pos = op - (M3_MIN_OFFSET - M3_EOF_OFFSET);
184
46.0k
            m_pos -= *ip++ & M3O_MASK;
185
46.0k
            m_pos -= (lzo_uint)(*ip++) << M3O_BITS;
186
46.0k
#if defined(LZO_EOF_CODE)
187
46.0k
            if (m_pos == op)
188
29
                goto eof_found;
189
45.9k
#endif
190
191
            /* copy match */
192
46.0k
            assert(m_pos >= out); assert(m_pos < op);
193
45.9k
            TEST_LB(m_pos); NEED_OP(t + M3_MIN_LEN - 1);
194
45.9k
#if (LZO_OPT_UNALIGNED32)
195
45.9k
            if (t >= 2 * 4 - (M3_MIN_LEN - 1) && (op - m_pos) >= 4)
196
36.1k
            {
197
36.1k
                UA_COPY4(op, m_pos);
198
36.1k
                op += 4; m_pos += 4; t -= 4 - (M3_MIN_LEN - 1);
199
2.66M
                do {
200
2.66M
                    UA_COPY4(op, m_pos);
201
2.66M
                    op += 4; m_pos += 4; t -= 4;
202
2.66M
                } while (t >= 4);
203
48.6k
                if (t > 0) do *op++ = *m_pos++; while (--t > 0);
204
36.1k
            }
205
9.74k
            else
206
9.74k
#endif
207
9.74k
            {
208
9.74k
            COPY_M3X;
209
9.74k
            MEMCPY_DS(op,m_pos,t);
210
9.74k
            }
211
212
213
45.9k
#if (M3O_BITS < 7)
214
45.9k
            t = ip[-2] >> M3O_BITS;
215
45.9k
            if (t)
216
19.8k
            {
217
19.8k
                NEED_IP(t); NEED_OP(t);
218
19.8k
                goto literal1;
219
19.8k
            }
220
#elif (M3O_BITS == 7)
221
            /* optimized version */
222
            if (ip[-2] & (1 << M3O_BITS))
223
            {
224
                NEED_IP(1); NEED_OP(1);
225
                *op++ = *ip++;
226
                goto literal2;
227
            }
228
#endif
229
45.9k
        }
230
157k
    }
231
232
233
94
#if defined(LZO_EOF_CODE)
234
94
#if defined(HAVE_TEST_IP) || defined(HAVE_TEST_OP)
235
    /* no EOF code was found */
236
94
    *out_len = pd(op, out);
237
94
    return LZO_E_EOF_NOT_FOUND;
238
0
#endif
239
240
29
eof_found:
241
29
    assert(t == 1);
242
29
#endif
243
29
    *out_len = pd(op, out);
244
29
    return (ip == ip_end ? LZO_E_OK :
245
29
           (ip < ip_end  ? LZO_E_INPUT_NOT_CONSUMED : LZO_E_INPUT_OVERRUN));
246
247
248
0
#if defined(HAVE_NEED_IP)
249
244
input_overrun:
250
244
    *out_len = pd(op, out);
251
244
    return LZO_E_INPUT_OVERRUN;
252
0
#endif
253
254
0
#if defined(HAVE_NEED_OP)
255
39
output_overrun:
256
39
    *out_len = pd(op, out);
257
39
    return LZO_E_OUTPUT_OVERRUN;
258
0
#endif
259
260
0
#if defined(LZO_TEST_OVERRUN_LOOKBEHIND)
261
110
lookbehind_overrun:
262
110
    *out_len = pd(op, out);
263
110
    return LZO_E_LOOKBEHIND_OVERRUN;
264
516
#endif
265
516
}
266
267
268
/* vim:set ts=4 sw=4 et: */