1df9de0ebSDavid E. O'Brien
2df9de0ebSDavid E. O'Brien /* A test program written to test robustness to decompression of
3df9de0ebSDavid E. O'Brien corrupted data. Usage is
4df9de0ebSDavid E. O'Brien unzcrash filename
5df9de0ebSDavid E. O'Brien and the program will read the specified file, compress it (in memory),
6df9de0ebSDavid E. O'Brien and then repeatedly decompress it, each time with a different bit of
7df9de0ebSDavid E. O'Brien the compressed data inverted, so as to test all possible one-bit errors.
8df9de0ebSDavid E. O'Brien This should not cause any invalid memory accesses. If it does,
9df9de0ebSDavid E. O'Brien I want to know about it!
10df9de0ebSDavid E. O'Brien
111b79bae0SXin LI PS. As you can see from the above description, the process is
12df9de0ebSDavid E. O'Brien incredibly slow. A file of size eg 5KB will cause it to run for
13df9de0ebSDavid E. O'Brien many hours.
14df9de0ebSDavid E. O'Brien */
15df9de0ebSDavid E. O'Brien
161b79bae0SXin LI /* ------------------------------------------------------------------
171b79bae0SXin LI This file is part of bzip2/libbzip2, a program and library for
181b79bae0SXin LI lossless, block-sorting data compression.
191b79bae0SXin LI
20*51f61fc0SXin LI bzip2/libbzip2 version 1.0.8 of 13 July 2019
21*51f61fc0SXin LI Copyright (C) 1996-2019 Julian Seward <jseward@acm.org>
221b79bae0SXin LI
231b79bae0SXin LI Please read the WARNING, DISCLAIMER and PATENTS sections in the
241b79bae0SXin LI README file.
251b79bae0SXin LI
261b79bae0SXin LI This program is released under the terms of the license contained
271b79bae0SXin LI in the file LICENSE.
281b79bae0SXin LI ------------------------------------------------------------------ */
291b79bae0SXin LI
301b79bae0SXin LI
31df9de0ebSDavid E. O'Brien #include <stdio.h>
32df9de0ebSDavid E. O'Brien #include <assert.h>
33df9de0ebSDavid E. O'Brien #include "bzlib.h"
34df9de0ebSDavid E. O'Brien
35df9de0ebSDavid E. O'Brien #define M_BLOCK 1000000
36df9de0ebSDavid E. O'Brien
37df9de0ebSDavid E. O'Brien typedef unsigned char uchar;
38df9de0ebSDavid E. O'Brien
39df9de0ebSDavid E. O'Brien #define M_BLOCK_OUT (M_BLOCK + 1000000)
40df9de0ebSDavid E. O'Brien uchar inbuf[M_BLOCK];
41df9de0ebSDavid E. O'Brien uchar outbuf[M_BLOCK_OUT];
42df9de0ebSDavid E. O'Brien uchar zbuf[M_BLOCK + 600 + (M_BLOCK / 100)];
43df9de0ebSDavid E. O'Brien
44df9de0ebSDavid E. O'Brien int nIn, nOut, nZ;
45df9de0ebSDavid E. O'Brien
46df9de0ebSDavid E. O'Brien static char *bzerrorstrings[] = {
47df9de0ebSDavid E. O'Brien "OK"
48df9de0ebSDavid E. O'Brien ,"SEQUENCE_ERROR"
49df9de0ebSDavid E. O'Brien ,"PARAM_ERROR"
50df9de0ebSDavid E. O'Brien ,"MEM_ERROR"
51df9de0ebSDavid E. O'Brien ,"DATA_ERROR"
52df9de0ebSDavid E. O'Brien ,"DATA_ERROR_MAGIC"
53df9de0ebSDavid E. O'Brien ,"IO_ERROR"
54df9de0ebSDavid E. O'Brien ,"UNEXPECTED_EOF"
55df9de0ebSDavid E. O'Brien ,"OUTBUFF_FULL"
56df9de0ebSDavid E. O'Brien ,"???" /* for future */
57df9de0ebSDavid E. O'Brien ,"???" /* for future */
58df9de0ebSDavid E. O'Brien ,"???" /* for future */
59df9de0ebSDavid E. O'Brien ,"???" /* for future */
60df9de0ebSDavid E. O'Brien ,"???" /* for future */
61df9de0ebSDavid E. O'Brien ,"???" /* for future */
62df9de0ebSDavid E. O'Brien };
63df9de0ebSDavid E. O'Brien
flip_bit(int bit)64df9de0ebSDavid E. O'Brien void flip_bit ( int bit )
65df9de0ebSDavid E. O'Brien {
66df9de0ebSDavid E. O'Brien int byteno = bit / 8;
67df9de0ebSDavid E. O'Brien int bitno = bit % 8;
68df9de0ebSDavid E. O'Brien uchar mask = 1 << bitno;
69df9de0ebSDavid E. O'Brien //fprintf ( stderr, "(byte %d bit %d mask %d)",
70df9de0ebSDavid E. O'Brien // byteno, bitno, (int)mask );
71df9de0ebSDavid E. O'Brien zbuf[byteno] ^= mask;
72df9de0ebSDavid E. O'Brien }
73df9de0ebSDavid E. O'Brien
main(int argc,char ** argv)74df9de0ebSDavid E. O'Brien int main ( int argc, char** argv )
75df9de0ebSDavid E. O'Brien {
76df9de0ebSDavid E. O'Brien FILE* f;
77df9de0ebSDavid E. O'Brien int r;
78df9de0ebSDavid E. O'Brien int bit;
79df9de0ebSDavid E. O'Brien int i;
80df9de0ebSDavid E. O'Brien
81df9de0ebSDavid E. O'Brien if (argc != 2) {
82df9de0ebSDavid E. O'Brien fprintf ( stderr, "usage: unzcrash filename\n" );
83df9de0ebSDavid E. O'Brien return 1;
84df9de0ebSDavid E. O'Brien }
85df9de0ebSDavid E. O'Brien
86df9de0ebSDavid E. O'Brien f = fopen ( argv[1], "r" );
87df9de0ebSDavid E. O'Brien if (!f) {
88df9de0ebSDavid E. O'Brien fprintf ( stderr, "unzcrash: can't open %s\n", argv[1] );
89df9de0ebSDavid E. O'Brien return 1;
90df9de0ebSDavid E. O'Brien }
91df9de0ebSDavid E. O'Brien
92df9de0ebSDavid E. O'Brien nIn = fread ( inbuf, 1, M_BLOCK, f );
93df9de0ebSDavid E. O'Brien fprintf ( stderr, "%d bytes read\n", nIn );
94df9de0ebSDavid E. O'Brien
95df9de0ebSDavid E. O'Brien nZ = M_BLOCK;
96df9de0ebSDavid E. O'Brien r = BZ2_bzBuffToBuffCompress (
97df9de0ebSDavid E. O'Brien zbuf, &nZ, inbuf, nIn, 9, 0, 30 );
98df9de0ebSDavid E. O'Brien
99df9de0ebSDavid E. O'Brien assert (r == BZ_OK);
100df9de0ebSDavid E. O'Brien fprintf ( stderr, "%d after compression\n", nZ );
101df9de0ebSDavid E. O'Brien
102df9de0ebSDavid E. O'Brien for (bit = 0; bit < nZ*8; bit++) {
103df9de0ebSDavid E. O'Brien fprintf ( stderr, "bit %d ", bit );
104df9de0ebSDavid E. O'Brien flip_bit ( bit );
105df9de0ebSDavid E. O'Brien nOut = M_BLOCK_OUT;
106df9de0ebSDavid E. O'Brien r = BZ2_bzBuffToBuffDecompress (
107df9de0ebSDavid E. O'Brien outbuf, &nOut, zbuf, nZ, 0, 0 );
108df9de0ebSDavid E. O'Brien fprintf ( stderr, " %d %s ", r, bzerrorstrings[-r] );
109df9de0ebSDavid E. O'Brien
110df9de0ebSDavid E. O'Brien if (r != BZ_OK) {
111df9de0ebSDavid E. O'Brien fprintf ( stderr, "\n" );
112df9de0ebSDavid E. O'Brien } else {
113df9de0ebSDavid E. O'Brien if (nOut != nIn) {
114df9de0ebSDavid E. O'Brien fprintf(stderr, "nIn/nOut mismatch %d %d\n", nIn, nOut );
115df9de0ebSDavid E. O'Brien return 1;
116df9de0ebSDavid E. O'Brien } else {
117df9de0ebSDavid E. O'Brien for (i = 0; i < nOut; i++)
118df9de0ebSDavid E. O'Brien if (inbuf[i] != outbuf[i]) {
119df9de0ebSDavid E. O'Brien fprintf(stderr, "mismatch at %d\n", i );
120df9de0ebSDavid E. O'Brien return 1;
121df9de0ebSDavid E. O'Brien }
122df9de0ebSDavid E. O'Brien if (i == nOut) fprintf(stderr, "really ok!\n" );
123df9de0ebSDavid E. O'Brien }
124df9de0ebSDavid E. O'Brien }
125df9de0ebSDavid E. O'Brien
126df9de0ebSDavid E. O'Brien flip_bit ( bit );
127df9de0ebSDavid E. O'Brien }
128df9de0ebSDavid E. O'Brien
129df9de0ebSDavid E. O'Brien #if 0
130df9de0ebSDavid E. O'Brien assert (nOut == nIn);
131df9de0ebSDavid E. O'Brien for (i = 0; i < nOut; i++) {
132df9de0ebSDavid E. O'Brien if (inbuf[i] != outbuf[i]) {
133df9de0ebSDavid E. O'Brien fprintf ( stderr, "difference at %d !\n", i );
134df9de0ebSDavid E. O'Brien return 1;
135df9de0ebSDavid E. O'Brien }
136df9de0ebSDavid E. O'Brien }
137df9de0ebSDavid E. O'Brien #endif
138df9de0ebSDavid E. O'Brien
139df9de0ebSDavid E. O'Brien fprintf ( stderr, "all ok\n" );
140df9de0ebSDavid E. O'Brien return 0;
141df9de0ebSDavid E. O'Brien }
142