1 /*
2  * The Sleuth Kit
3  *
4  */
5 
6 /** \file tsk_base_i.h
7  * Contains the general internal TSK type and function definitions.
8  * This is needed by the library as it is built.
9  */
10 #ifndef _TSK_BASE_I_H
11 #define _TSK_BASE_I_H
12 
13 // include the autoconf header file
14 #if HAVE_CONFIG_H
15 #include "tsk/tsk_config.h"
16 #endif
17 
18 /* Some Linux systems need LARGEFILE64_SOURCE and autoconf does
19  * not define it, so we hack it here */
20 #ifdef _LARGEFILE_SOURCE
21 #ifndef _LARGEFILE64_SOURCE
22 #define _LARGEFILE64_SOURCE 1
23 #endif
24 #endif
25 
26 #include "tsk_base.h"
27 
28 // most of the local files need this, so we include it here
29 #include <string.h>
30 
31 
32 #ifdef __cplusplus
33 extern "C" {
34 #endif
35 
36 
37     extern void tsk_init_lock(tsk_lock_t *);
38     extern void tsk_deinit_lock(tsk_lock_t *);
39     extern void tsk_take_lock(tsk_lock_t *);
40     extern void tsk_release_lock(tsk_lock_t *);
41 
42 #ifndef rounddown
43 #define rounddown(x, y)	\
44     ((((x) % (y)) == 0) ? (x) : \
45     (roundup((x),(y)) - (y)))
46 #endif
47 
48     extern void *tsk_malloc(size_t);
49     extern void *tsk_realloc(void *, size_t);
50 
51 // getopt for windows
52 #ifdef TSK_WIN32
53     extern int tsk_optind;
54     extern TSK_TCHAR *tsk_optarg;
55     extern int tsk_getopt(int argc, TSK_TCHAR * const argv[],
56         const TSK_TCHAR * optstring);
57 #endif
58 
59 
60 
61 
62 /* Endian Ordering */
63 /* macros to read in multi-byte fields
64 * file system is an array of 8-bit values, not 32-bit values
65 */
66     extern uint8_t tsk_guess_end_u16(TSK_ENDIAN_ENUM *, uint8_t *,
67         uint16_t);
68     extern uint8_t tsk_guess_end_u32(TSK_ENDIAN_ENUM *, uint8_t *,
69         uint32_t);
70     extern uint8_t tsk_guess_end_u64(TSK_ENDIAN_ENUM *, uint8_t *,
71         uint64_t);
72 
73 
74 /** \internal
75 * Read a 16-bit unsigned value.
76 * @param endian Flag that identifies local ordering.
77 * @param x Byte array to read from
78 * @returns 16-bit unsigned value
79 */
80 #define tsk_getu16(endian, x)   \
81 (uint16_t)(((endian) == TSK_LIT_ENDIAN) ? \
82            (((uint8_t *)(x))[0] + (((uint8_t *)(x))[1] << 8)) :    \
83            (((uint8_t *)(x))[1] + (((uint8_t *)(x))[0] << 8)) )
84 
85 /** \internal
86 * Read a 16-bit signed value.
87 * @param endian Flag that identifies local ordering.
88 * @param x Byte array to read from
89 * @returns 16-bit signed value
90 */
91 #define tsk_gets16(endian, x)	\
92 ((int16_t)tsk_getu16(endian, x))
93 
94 /** \internal
95  * Read a 24-bit unsigned value into a uint32_t variable.
96  * @param endian Flag that identifies local ordering.
97  * @param x Byte array to read from
98  * @returns 16-bit unsigned value
99  */
100 #define tsk_getu24(endian, x)   \
101 		(uint32_t)(((endian) == TSK_LIT_ENDIAN) ? \
102 				(((uint8_t *)(x))[0] + (((uint8_t *)(x))[1] << 8) + (((uint8_t *)(x))[2] << 16)) :    \
103 				(((uint8_t *)(x))[2] + (((uint8_t *)(x))[1] << 8) + (((uint8_t *)(x))[0] << 16)) )
104 
105 
106 
107 /** \internal
108 * Read a 32-bit unsigned value.
109 * @param endian Flag that identifies local ordering.
110 * @param x Byte array to read from
111 * @returns 32-bit unsigned value
112 */
113 #define tsk_getu32(endian, x)	\
114 (uint32_t)( ((endian) == TSK_LIT_ENDIAN)  ?	\
115             ((((uint8_t *)(x))[0] <<  0) + \
116              (((uint8_t *)(x))[1] <<  8) + \
117              (((uint8_t *)(x))[2] << 16) + \
118              (((uint8_t *)(x))[3] << 24) ) \
119                                           :	\
120             ((((uint8_t *)(x))[3] <<  0) + \
121              (((uint8_t *)(x))[2] <<  8) + \
122              (((uint8_t *)(x))[1] << 16) + \
123              (((uint8_t *)(x))[0] << 24) ) )
124 
125 /** \internal
126 * Read a 32-bit signed value.
127 * @param endian Flag that identifies local ordering.
128 * @param x Byte array to read from
129 * @returns 32-bit signed value
130 */
131 #define tsk_gets32(endian, x)	\
132 ((int32_t)tsk_getu32(endian, x))
133 
134 /** \internal
135 * Read a 48-bit unsigned value.
136 * @param endian Flag that identifies local ordering.
137 * @param x Byte array to read from
138 * @returns 48-bit unsigned value
139 */
140 #define tsk_getu48(endian, x)   \
141 (uint64_t)( ((endian) == TSK_LIT_ENDIAN)  ?	\
142             ((uint64_t) \
143              ((uint64_t)((uint8_t *)(x))[0] <<  0)+ \
144              ((uint64_t)((uint8_t *)(x))[1] <<  8) + \
145              ((uint64_t)((uint8_t *)(x))[2] << 16) + \
146              ((uint64_t)((uint8_t *)(x))[3] << 24) + \
147              ((uint64_t)((uint8_t *)(x))[4] << 32) + \
148              ((uint64_t)((uint8_t *)(x))[5] << 40)) \
149                                           : \
150             ((uint64_t) \
151              ((uint64_t)((uint8_t *)(x))[5] <<  0)+ \
152              ((uint64_t)((uint8_t *)(x))[4] <<  8) + \
153              ((uint64_t)((uint8_t *)(x))[3] << 16) + \
154              ((uint64_t)((uint8_t *)(x))[2] << 24) + \
155              ((uint64_t)((uint8_t *)(x))[1] << 32) + \
156              ((uint64_t)((uint8_t *)(x))[0] << 40)) )
157 
158 
159 /** \internal
160 * Read a 64-bit unsigned value.
161 * @param endian Flag that identifies local ordering.
162 * @param x Byte array to read from
163 * @returns 64-bit unsigned value
164 */
165 #define tsk_getu64(endian, x)   \
166 (uint64_t)( ((endian) == TSK_LIT_ENDIAN)  ?	\
167             ((uint64_t) \
168              ((uint64_t)((uint8_t *)(x))[0] << 0)  + \
169              ((uint64_t)((uint8_t *)(x))[1] << 8) + \
170              ((uint64_t)((uint8_t *)(x))[2] << 16) + \
171              ((uint64_t)((uint8_t *)(x))[3] << 24) + \
172              ((uint64_t)((uint8_t *)(x))[4] << 32) + \
173              ((uint64_t)((uint8_t *)(x))[5] << 40) + \
174              ((uint64_t)((uint8_t *)(x))[6] << 48) + \
175              ((uint64_t)((uint8_t *)(x))[7] << 56)) \
176                                           : \
177             ((uint64_t) \
178              ((uint64_t)((uint8_t *)(x))[7] <<  0) + \
179              ((uint64_t)((uint8_t *)(x))[6] <<  8) + \
180              ((uint64_t)((uint8_t *)(x))[5] << 16) + \
181              ((uint64_t)((uint8_t *)(x))[4] << 24) + \
182              ((uint64_t)((uint8_t *)(x))[3] << 32) + \
183              ((uint64_t)((uint8_t *)(x))[2] << 40) + \
184              ((uint64_t)((uint8_t *)(x))[1] << 48) + \
185              ((uint64_t)((uint8_t *)(x))[0] << 56)) )
186 
187 /** \internal
188 * Read a 64-bit signed value.
189 * @param endian Flag that identifies local ordering.
190 * @param x Byte array to read from
191 * @returns 64-bit signed value
192 */
193 #define tsk_gets64(endian, x)	\
194 ((int64_t)tsk_getu64(endian, x))
195 
196 
197 #define TSK_IS_CNTRL(x) \
198 (((x) < 0x20) && ((x) >= 0x00))
199 
200 
201 /** \name Unicode */
202 //@{
203     // basic check to see if a Unicode file has been included
204     // in an app that is using this as a library
205 #ifndef TSK_UNI_REPLACEMENT_CHAR
206 
207 /**************** UNICODE *******************/
208 /*
209  * Copyright 2001-2004 Unicode, Inc.
210  *
211  * Disclaimer
212  *
213  * This source code is provided as is by Unicode, Inc. No claims are
214  * made as to fitness for any particular purpose. No warranties of any
215  * kind are expressed or implied. The recipient agrees to determine
216  * applicability of information provided. If this file has been
217  * purchased on magnetic or optical media from Unicode, Inc., the
218  * sole remedy for any claim will be exchange of defective media
219  * within 90 days of receipt.
220  *
221  * Limitations on Rights to Redistribute This Code
222  *
223  * Unicode, Inc. hereby grants the right to freely use the information
224  * supplied in this file in the creation of products supporting the
225  * Unicode Standard, and to make copies of this file in any form
226  * for internal or external distribution as long as this notice
227  * remains attached.
228  */
229 
230 /* ---------------------------------------------------------------------
231 
232     Conversions between UTF32, UTF-16, and UTF-8.  Header file.
233 
234     Several functions are included here, forming a complete set of
235     conversions between the three formats.  UTF-7 is not included
236     here, but is handled in a separate source file.
237 
238     Each of these routines takes pointers to input buffers and output
239     buffers.  The input buffers are const.
240 
241     Each routine converts the text between *sourceStart and sourceEnd,
242     putting the result into the buffer between *targetStart and
243     targetEnd. Note: the end pointers are *after* the last item: e.g.
244     *(sourceEnd - 1) is the last item.
245 
246     The return result indicates whether the conversion was successful,
247     and if not, whether the problem was in the source or target buffers.
248     (Only the first encountered problem is indicated.)
249 
250     After the conversion, *sourceStart and *targetStart are both
251     updated to point to the end of last text successfully converted in
252     the respective buffers.
253 
254     Input parameters:
255 	sourceStart - pointer to a pointer to the source buffer.
256 		The contents of this are modified on return so that
257 		it points at the next thing to be converted.
258 	targetStart - similarly, pointer to pointer to the target buffer.
259 	sourceEnd, targetEnd - respectively pointers to the ends of the
260 		two buffers, for overflow checking only.
261 
262     These conversion functions take a TSKConversionFlags argument. When this
263     flag is set to strict, both irregular sequences and isolated surrogates
264     will cause an error.  When the flag is set to lenient, both irregular
265     sequences and isolated surrogates are converted.
266 
267     Whether the flag is strict or lenient, all illegal sequences will cause
268     an error return. This includes sequences such as: <F4 90 80 80>, <C0 80>,
269     or <A0> in UTF-8, and values above 0x10FFFF in UTF-32. Conformant code
270     must check for illegal sequences.
271 
272     When the flag is set to lenient, characters over 0x10FFFF are converted
273     to the replacement character; otherwise (when the flag is set to strict)
274     they constitute an error.
275 
276     Output parameters:
277 	The value "TSKsourceIllegal" is returned from some routines if the input
278 	sequence is malformed.  When "TSKsourceIllegal" is returned, the source
279 	value will point to the illegal value that caused the problem. E.g.,
280 	in UTF-8 when a sequence is malformed, it points to the start of the
281 	malformed sequence.
282 
283     Author: Mark E. Davis, 1994.
284     Rev History: Rick McGowan, fixes & updates May 2001.
285 		 Fixes & updates, Sept 2001.
286 
287 ------------------------------------------------------------------------ */
288 
289 /* ---------------------------------------------------------------------
290     The following 4 definitions are compiler-specific.
291     The C standard does not guarantee that wchar_t has at least
292     16 bits, so wchar_t is no less portable than unsigned short!
293     All should be unsigned values to avoid sign extension during
294     bit mask & shift operations.
295 ------------------------------------------------------------------------ */
296 
297 
298     typedef unsigned short UTF16;       /* at least 16 bits */
299     typedef unsigned char UTF8; /* typically 8 bits */
300     typedef unsigned char Boolean;      /* 0 or 1 */
301 
302 
303     typedef enum {
304         TSKconversionOK,        ///< conversion successful
305         TSKsourceExhausted,     ///< partial character in source, but hit end
306         TSKtargetExhausted,     ///< insuff. room in target for conversion
307         TSKsourceIllegal        ///< source sequence is illegal/malformed
308     } TSKConversionResult;
309 
310     typedef enum {
311         TSKstrictConversion = 0,        ///< Error if invalid surrogate pairs are found
312         TSKlenientConversion    ///< Ignore invalid surrogate pairs
313     } TSKConversionFlags;
314 
315     extern TSKConversionResult tsk_UTF8toUTF16(const UTF8 ** sourceStart,
316         const UTF8 * sourceEnd,
317         UTF16 ** targetStart, UTF16 * targetEnd, TSKConversionFlags flags);
318 
319     extern TSKConversionResult tsk_UTF16toUTF8(TSK_ENDIAN_ENUM,
320         const UTF16 ** sourceStart, const UTF16 * sourceEnd,
321         UTF8 ** targetStart, UTF8 * targetEnd, TSKConversionFlags flags);
322 
323     extern TSKConversionResult
324         tsk_UTF16toUTF8_lclorder(const UTF16 ** sourceStart,
325         const UTF16 * sourceEnd, UTF8 ** targetStart,
326         UTF8 * targetEnd, TSKConversionFlags flags);
327 
328     extern TSKConversionResult
329         tsk_UTF16WtoUTF8_lclorder(const wchar_t ** sourceStart,
330         const wchar_t * sourceEnd, UTF8 ** targetStart,
331         UTF8 * targetEnd, TSKConversionFlags flags);
332 
333     extern Boolean tsk_isLegalUTF8Sequence(const UTF8 * source,
334         const UTF8 * sourceEnd);
335 
336     extern void
337      tsk_cleanupUTF8(char *source, const char replacement);
338 #endif
339 //@}
340 
341 
342 
343 #ifdef __cplusplus
344 }
345 #endif
346 #endif
347