1 /*
2 This product contains certain software code or other information
3 ("AT&T Software") proprietary to AT&T Corp. ("AT&T").  The AT&T
4 Software is provided to you "AS IS".  YOU ASSUME TOTAL RESPONSIBILITY
5 AND RISK FOR USE OF THE AT&T SOFTWARE.  AT&T DOES NOT MAKE, AND
6 EXPRESSLY DISCLAIMS, ANY EXPRESS OR IMPLIED WARRANTIES OF ANY KIND
7 WHATSOEVER, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
8 MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE, WARRANTIES OF
9 TITLE OR NON-INFRINGEMENT OF ANY INTELLECTUAL PROPERTY RIGHTS, ANY
10 WARRANTIES ARISING BY USAGE OF TRADE, COURSE OF DEALING OR COURSE OF
11 PERFORMANCE, OR ANY WARRANTY THAT THE AT&T SOFTWARE IS "ERROR FREE" OR
12 WILL MEET YOUR REQUIREMENTS.
13 
14 Unless you accept a license to use the AT&T Software, you shall not
15 reverse compile, disassemble or otherwise reverse engineer this
16 product to ascertain the source code for any AT&T Software.
17 
18 (c) AT&T Corp. All rights reserved.  AT&T is a registered trademark of AT&T Corp.
19 
20 ***********************************************************************
21 
22 Description:
23 
24 		The in-memory API to the XMill (de)compression routines
25 
26 History:
27 
28       10/11/2002  - created by Hedzer Westra <hedzer@adlibsoft.com>
29 
30 */
31 
32 #pragma once
33 
34 /* "conversion from 'size_t' to 'int', possible loss of data" */
35 #pragma warning (disable: 4267)
36 
37 /* macros */
38 #ifndef min
39 #define min(x,y)  ( (x)>(y) ? (y) : (x))
40 #endif
41 
42 /* defines */
43 #ifndef FALSE
44 #define FALSE 0
45 #endif
46 #ifndef TRUE
47 #define TRUE 1
48 #endif
49 
50 /* general-purpose compression types */
51 #define XMILL_GPC_NONE             -1
52 #define XMILL_GPC_GZIP              0
53 #define XMILL_GPC_BZIP              1
54 #define XMILL_GPC_PPMDI             2
55 
56 #define XMILL_GZIP_IDX              6		// default GZIP compression index (0-9)
57 #define XMILL_PPMDI_IDX             0     // default ppmdi compression index (0-(XMILL_PPMDI_IDXS-1))
58 #define XMILL_PPMDI_IDXS            19
59 
60 /* error codes */
61 #define XMILL_ERR_NOMEM					1
62 #define XMILL_ERR_CORRUPT				2
63 #define XMILL_ERR_FILENOTFOUND		3
64 #define XMILL_ERR_IN_FILE				4
65 #define XMILL_ERR_NO_XMI				5
66 #define XMILL_ERR_CREATE_FAILED		6
67 #define XMILL_ERR_BLOCK_TOO_LARGE	7
68 #define XMILL_ERR_DECOMPRESS			8
69 #define XMILL_ERR_FATAL					9
70 #define XMILL_ERR_NO_COMPRESSOR		10
71 #define XMILL_ERR_PARSE					11
72 #define XMILL_ERR_WRITE					12
73 #define XMILL_ERR_ARGUMENTS			13
74 #define XMILL_ERR_CREATE				14
75 #define XMILL_ERR_READ					15
76 #define XMILL_ERR_ZLIB					16
77 #define XMILL_ERR_FILETOOLARGE		17
78 #define XMILL_ERR_XMIFILELARGER		18
79 #define XMILL_ERR_XMI_IS_XML			19
80 #define XMILL_ERR_XMILL_SYNTAX		20
81 #define XMILL_ERR_PRINTCOMPRESSOR	21
82 #define XMILL_ERR_NULL_POINTER		22
83 
84 /* Init() types */
85 #define XMILL_INIT_INIT			1
86 #define XMILL_INIT_REINIT		2
87 #define XMILL_INIT_USERINIT	3
88 
89 /* verbosity levels */
90 #define XMILL_VERBOSE_SILENT	0
91 #define XMILL_VERBOSE_ERR		1
92 #define XMILL_VERBOSE_WARN		2
93 #define XMILL_VERBOSE_STATS	3
94 #define XMILL_VERBOSE_ALL		4
95 
96 /* file extensions */
97 #define XMILL_EXT_XMI			"xmi"
98 #define XMILL_EXT_XMILL			"xmill"
99 
100 /* XML end markers */
101 #define XMILL_END_NONE	0		// no end-of-data found yet, data was cut off
102 #define XMILL_END_BLOCK	1		// end-of-block found, more data will follow
103 #define XMILL_END_DATA	2		// end-of-data, compression ends
104 
105 /* XML output types */
106 #define XMILL_OUT_STRING_OR_FILE	0		// output XML as text in a string or file
107 #define XMILL_OUT_MSXML				1		// create an MSXML instance (WIN32 only)
108 #define XMILL_OUT_SAX				2		// SAX events (future)
109 #define XMILL_OUT_AIS_RECORD		3		// Adlib Information Systems special: convert adlibXML directly to a RECORD*
110 													// this code is not released!
111 #define XMILL_OUT_AIS_FILES		4		// Adlib Information Systems special: convert to a vector of files
112 													// this code is not released!
113 
114 /* forward references */
115 class Session;
116 class Settings;
117 class Input;
118 class XMLOutput;
119 class XMLParse;
120 class Output;
121 class SAXClient;
122 
123 /* XMillException struct and class headers */
124 #define ERRMSG_MAXLEN   8192   // The maximum length of all error messages together
125 
126 struct ErrLine
127 {
128    ErrLine  *next;
129    char     line[1];
130 };
131 
132 class XMillException
133 {
134 	ErrLine  *curerrline;
135 	char  errmsg[ERRMSG_MAXLEN+1];
136 	char  *curptr;
137 	char  *msgptr;
138 public:
139 	int code;
140 
141 	XMillException(int code, char *str,int len=0);
142 
143 	void Error(char *str,int len=0);   // Starts a new error msg
144 	void ErrorCont(char *str,int len=0);  // Continues the current error msg
145 
146 	void PrintErrorMsg();   // Prints the current error messsages
147 	char *GetErrorMsg();
148 
149 	void ResetErr();
150 };
151 
152 
153 /* utility functions */
154 int readfile(char *filename, char **buf, int *buflength);
155 char* str_save(char *str);
156 
157 /* the XMill file & memory API class */
158 class XMill
159 {
160 	SAXClient *saxclient;
161 	char saved_use_bzip;
162 	char **decompoutbuf;
163 	int *decompoutlen;
164 
165 	int CompressIt(XMLParse *xmlparse, Output *output);
166 	void UncompressIt(Input *input, XMLOutput *output);
167 
168 	void EndCompressBlock();
169 	void InitCompressIt();
170 	void InitCompressItRun();
171 	char CompressItRun(XMLParse *xmlparse);
172 	void EndCompressItRun(Output *output);
173 	void EndCompressIt();
174 
175 	void FirstInit();
176 
177 public:
178 	Session *session;
179 	Settings *settings;
180 
181 	XMill(char *s);
182 	XMill(int outtype = XMILL_OUT_STRING_OR_FILE, bool lossy = true,
183 				  char usebzip = XMILL_GPC_BZIP,
184 				  char **pathexpr = NULL,
185 				  bool usedos = true,
186 				  char igntype = 'n', bool ignore = true,
187 				  int indenttype = -1, int indentcount = 1,
188 				  int gpcidx = XMILL_GZIP_IDX);
189 	~XMill();
190 
191 	/* Call this for global (re-)initialization of XMill
192 	* default settings:
193 	*  lossy compression (drop all whitespace)
194 	*  no path expressions
195 	*  use CR/LF
196 	*  don't ignore PI/CDATA/comments/DOCTYPE
197 	*  use default indentation (1 space)
198 	*  zlib compression level XMILL_GZIP_IDX (6)
199    * throws XMillException
200 	*/
201 	void Init(int outtype = XMILL_OUT_STRING_OR_FILE, char type = XMILL_INIT_INIT,
202 				  bool lossy = true,
203 				  char usebzip = XMILL_GPC_BZIP,
204 				  char **pathexpr = NULL,
205 				  bool usedos = true,
206 				  char igntype = 'n', bool ignore = true,
207 				  int indenttype = -1, int indentcount = 1,
208 				  int gpcidx = XMILL_GZIP_IDX,
209 				  bool copyxml = TRUE);
210 
211 	/* read an .xmill file to memory
212 	   Max maxexprs-1 expressions are read; the list is terminated with a NULL char*.
213 	   The caller must free() all pathexprs char*'s when he/she is done compressing */
214 	static int readExprsFromFile(char *filename, char **pathexprs, int maxexprs, int *numexprs);
215 
216 	/* memory operation, all throw XMillException */
217 
218 	/* block operations */
219 	void InitCompress(char **outbuf, int *outlen, int *bytesread);
220 	void CompressBlock(char *inbuf, int inlen, int *endmarker);
221 	void EndCompress();
222 	/* compress an ASCIIZ XML buffer, or part of it */
223 	void Compress(char *inbuf, int inlen, char **outbuf, int *outlen, int *bytesread);
224 
225 	/* block operations */
226 	void InitDecompress(char **outbuf, int *outlen, int *bytesread);
227 	void DecompressBlock(char *inbuf, int inlen, int *endmarker);
228 	void EndDecompress();
229 	/* decompress (part of) an XMI buffer to ASCIIZ XML */
230 	void Decompress(char *inbuf, int buflen, char **outbuf, int *outlen, int *bytesread);
231 
232 	/* file operations */
233 	void Compress(char *srcfile, char *destfile);
234 	void Uncompress(char *sourcefile, char *destfile);
235 
236 	/* get/set methods */
237 	void SetVerbose(char verb);
238 	void SetNoIncrease(bool inc = true);
239 	char GetCompressionMode();
240 };