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