comparison src/libpst.c @ 46:b2a7f2e0926a

more fixes for 64 bit format
author carl
date Sat, 12 Jan 2008 15:20:53 -0800
parents b961bcdadd0e
children 5fb8d997feed
comparison
equal deleted inserted replaced
45:b961bcdadd0e 46:b2a7f2e0926a
32 //efine INDEX_DEPTH 0x4C 32 //efine INDEX_DEPTH 0x4C
33 //efine SECOND_DEPTH 0x5C 33 //efine SECOND_DEPTH 0x5C
34 #define INDEX_TYPE32 0x0E 34 #define INDEX_TYPE32 0x0E
35 #define INDEX_TYPE64 0x17 35 #define INDEX_TYPE64 0x17
36 36
37 #define FILE_SIZE_POINTER32 0xA8 37 #define FILE_SIZE_POINTER32 (off_t)0xA8
38 #define INDEX_POINTER32 0xC4 38 #define INDEX_POINTER32 (off_t)0xC4
39 #define INDEX_COUNT32 0xC0 39 #define INDEX_BACK32 (off_t)0xC0
40 #define SECOND_POINTER32 0xBC 40 #define SECOND_POINTER32 (off_t)0xBC
41 #define SECOND_COUNT32 0xB8 41 #define SECOND_BACK32 (off_t)0xB8
42 #define INDEX_TYPE_OFFSET32 0x0A 42 #define INDEX_TYPE_OFFSET32 (off_t)0x0A
43 #define ENC_OFFSET32 0x1CD 43 #define ENC_OFFSET32 (off_t)0x1CD
44 44
45 #define FILE_SIZE_POINTER64 0xB8 45 #define FILE_SIZE_POINTER64 (off_t)0xB8
46 #define INDEX_POINTER64 0xF0 46 #define INDEX_POINTER64 (off_t)0xF0
47 #define INDEX_COUNT64 0xE8 47 #define INDEX_BACK64 (off_t)0xE8
48 #define SECOND_POINTER64 0xE0 48 #define SECOND_POINTER64 (off_t)0xE0
49 #define SECOND_COUNT64 0xD8 49 #define SECOND_BACK64 (off_t)0xD8
50 #define INDEX_TYPE_OFFSET64 0x0A 50 #define INDEX_TYPE_OFFSET64 (off_t)0x0A
51 #define ENC_OFFSET64 0x201 51 #define ENC_OFFSET64 (off_t)0x201
52 52
53 #define FILE_SIZE_POINTER ((do_read64) ? FILE_SIZE_POINTER64 : FILE_SIZE_POINTER32) 53 #define FILE_SIZE_POINTER ((pf->do_read64) ? FILE_SIZE_POINTER64 : FILE_SIZE_POINTER32)
54 #define INDEX_POINTER ((do_read64) ? INDEX_POINTER64 : INDEX_POINTER32) 54 #define INDEX_POINTER ((pf->do_read64) ? INDEX_POINTER64 : INDEX_POINTER32)
55 #define INDEX_COUNT ((do_read64) ? INDEX_COUNT64 : INDEX_COUNT32) 55 #define INDEX_BACK ((pf->do_read64) ? INDEX_BACK64 : INDEX_BACK32)
56 #define SECOND_POINTER ((do_read64) ? SECOND_POINTER64 : SECOND_POINTER32) 56 #define SECOND_POINTER ((pf->do_read64) ? SECOND_POINTER64 : SECOND_POINTER32)
57 #define SECOND_COUNT ((do_read64) ? SECOND_COUNT64 : SECOND_COUNT32) 57 #define SECOND_BACK ((pf->do_read64) ? SECOND_BACK64 : SECOND_BACK32)
58 #define INDEX_TYPE_OFFSET ((do_read64) ? INDEX_TYPE_OFFSET64 : INDEX_TYPE_OFFSET32) 58 #define INDEX_TYPE_OFFSET ((pf->do_read64) ? INDEX_TYPE_OFFSET64 : INDEX_TYPE_OFFSET32)
59 #define INDEX_TYPE ((do_read64) ? INDEX_TYPE64 : INDEX_TYPE32) 59 #define INDEX_TYPE ((pf->do_read64) ? INDEX_TYPE64 : INDEX_TYPE32)
60 #define ENC_OFFSET ((do_read64) ? ENC_OFFSET64 : ENC_OFFSET32) 60 #define ENC_OFFSET ((pf->do_read64) ? ENC_OFFSET64 : ENC_OFFSET32)
61 61
62 #define PST_SIGNATURE 0x4E444221 62 #define PST_SIGNATURE 0x4E444221
63 63
64 int do_read64 = 0; //set this to 1 in order to try and read 64-bit pst files (Outlook 2003) 64
65 65 struct pst_table_ptr_struct32{
66 struct _pst_table_ptr_struct32{ 66 uint32_t start;
67 int32_t start; 67 uint32_t u1;
68 int32_t u1; 68 uint32_t offset;
69 int32_t offset;
70 }; 69 };
71 struct _pst_table_ptr_structn{ 70 struct pst_table_ptr_structn{
72 int64_t start; 71 uint64_t start;
73 int64_t u1; 72 uint64_t u1;
74 int64_t offset; 73 uint64_t offset;
75 }; 74 };
76 75
77 typedef struct _pst_block_header { 76 typedef struct pst_block_header {
78 int16_t type; 77 uint16_t type;
79 int16_t count; 78 uint16_t count;
80 } pst_block_header; 79 } pst_block_header;
81 80
82 typedef struct _pst_id2_assoc { 81 typedef struct pst_id2_assoc32 {
83 uint32_t id2; 82 uint32_t id2;
84 uint32_t id; 83 uint32_t id;
85 int32_t table2; 84 uint32_t table2;
85 } pst_id2_assoc32;
86
87 typedef struct pst_id2_assoc {
88 uint64_t id2;
89 uint64_t id;
90 uint64_t table2;
86 } pst_id2_assoc; 91 } pst_id2_assoc;
87 92
88 // this is an array of the un-encrypted values. the un-encrypted value is in the position 93 // this is an array of the un-encrypted values. the un-encrypted value is in the position
89 // of the encrypted value. ie the encrypted value 0x13 represents 0x02 94 // of the encrypted value. ie the encrypted value 0x13 represents 0x02
90 // 0 1 2 3 4 5 6 7 95 // 0 1 2 3 4 5 6 7
91 // 8 9 a b c d e f 96 // 8 9 a b c d e f
92 unsigned char comp_enc [] = 97 static unsigned char comp_enc [] =
93 { 0x47, 0xf1, 0xb4, 0xe6, 0x0b, 0x6a, 0x72, 0x48, 98 { 0x47, 0xf1, 0xb4, 0xe6, 0x0b, 0x6a, 0x72, 0x48,
94 0x85, 0x4e, 0x9e, 0xeb, 0xe2, 0xf8, 0x94, 0x53, /*0x0f*/ 99 0x85, 0x4e, 0x9e, 0xeb, 0xe2, 0xf8, 0x94, 0x53, /*0x0f*/
95 0xe0, 0xbb, 0xa0, 0x02, 0xe8, 0x5a, 0x09, 0xab, 100 0xe0, 0xbb, 0xa0, 0x02, 0xe8, 0x5a, 0x09, 0xab,
96 0xdb, 0xe3, 0xba, 0xc6, 0x7c, 0xc3, 0x10, 0xdd, /*0x1f*/ 101 0xdb, 0xe3, 0xba, 0xc6, 0x7c, 0xc3, 0x10, 0xdd, /*0x1f*/
97 0x39, 0x05, 0x96, 0x30, 0xf5, 0x37, 0x60, 0x82, 102 0x39, 0x05, 0x96, 0x30, 0xf5, 0x37, 0x60, 0x82,
122 0x0e, 0x81, 0x65, 0x73, 0xe4, 0xc2, 0xa2, 0x8a, /*0xef*/ 127 0x0e, 0x81, 0x65, 0x73, 0xe4, 0xc2, 0xa2, 0x8a, /*0xef*/
123 0xd4, 0xe1, 0x11, 0xd0, 0x08, 0x8b, 0x2a, 0xf2, 128 0xd4, 0xe1, 0x11, 0xd0, 0x08, 0x8b, 0x2a, 0xf2,
124 0xed, 0x9a, 0x64, 0x3f, 0xc1, 0x6c, 0xf9, 0xec}; /*0xff*/ 129 0xed, 0x9a, 0x64, 0x3f, 0xc1, 0x6c, 0xf9, 0xec}; /*0xff*/
125 130
126 131
127 void dump_desc(off_t off, int depth, int i, pst_descn *desc_rec ) { 132 int pst_open(pst_file *pf, char *name, char *mode) {
128 //desc_rec->d_id = 0x0102030405060708; 133 int32_t sig;
129 DEBUG_INDEX(("%08x [%i] Item(%#x) = [d_id = %#llx, desc_id = %#llx, "
130 "list_id = %#llx, parent_id = %#x, u1 = %#x] %#x %p %p\n",
131 off,
132 depth, i, desc_rec->d_id,
133 desc_rec->desc_id, desc_rec->list_id, desc_rec->parent_id, desc_rec->u1));
134 DEBUG_HEXDUMPC( (char*)desc_rec, sizeof( pst_descn ), 0x10 );
135 DEBUG_INDEX(("WTF? %d %x %x %x %x %x\n",
136 sizeof( uint32_t ),
137 (int)(&desc_rec->d_id) - (int)desc_rec,
138 (int)(&desc_rec->desc_id) - (int)desc_rec,
139 (int)(&desc_rec->list_id) - (int)desc_rec,
140 (int)(&desc_rec->parent_id) - (int)desc_rec,
141 (int)(&desc_rec->u1) - (int)desc_rec ));
142 }
143
144
145 int32_t pst_open(pst_file *pf, char *name, char *mode) {
146 uint32_t sig;
147 134
148 unicode_init(); 135 unicode_init();
149 136
150 DEBUG_ENT("pst_open"); 137 DEBUG_ENT("pst_open");
151 138
152 if (!pf) { 139 if (!pf) {
153 WARN (("cannot be passed a NULL pst_file\n")); 140 WARN (("cannot be passed a NULL pst_file\n"));
154 DEBUG_RET(); 141 DEBUG_RET();
155 return -1; 142 return -1;
156 } 143 }
157 memset(pf, 0, sizeof(pst_file)); 144 memset(pf, 0, sizeof(*pf));
158 145
159 #ifdef _MSC_VER 146 #ifdef _MSC_VER
160 // set the default open mode for windows 147 // set the default open mode for windows
161 _fmode = _O_BINARY; 148 _fmode = _O_BINARY;
162 #endif //_MSC_VER 149 #endif //_MSC_VER
165 DEBUG_RET(); 152 DEBUG_RET();
166 return -1; 153 return -1;
167 } 154 }
168 155
169 // Check pst file magic 156 // Check pst file magic
170 if (fread(&sig, sizeof(sig), 1, pf->fp) == 0) { 157 if (fread(&sig, sizeof(sig), (size_t)1, pf->fp) == 0) {
171 fclose(pf->fp); 158 (void)fclose(pf->fp);
172 WARN(("cannot read signature from PST file. Closing on error\n")); 159 WARN(("cannot read signature from PST file. Closing on error\n"));
173 DEBUG_RET(); 160 DEBUG_RET();
174 return -1; 161 return -1;
175 } 162 }
176 LE32_CPU(sig); 163 LE32_CPU(sig);
177 DEBUG_INFO(("sig = %X\n", sig)); 164 DEBUG_INFO(("sig = %X\n", sig));
178 if (sig != PST_SIGNATURE) { 165 if (sig != (int32_t)PST_SIGNATURE) {
179 fclose(pf->fp); 166 (void)fclose(pf->fp);
180 WARN(("not a PST file that I know. Closing with error\n")); 167 WARN(("not a PST file that I know. Closing with error\n"));
181 DEBUG_RET(); 168 DEBUG_RET();
182 return -1; 169 return -1;
183 } 170 }
184 171
185 // read index type 172 // read index type
186 do_read64 = 0; // start with 32 bit format 173 pf->do_read64 = 0; // start with 32 bit format
187 _pst_getAtPos(pf->fp, INDEX_TYPE_OFFSET, &(pf->ind_type), sizeof(unsigned char)); 174 (void)pst_getAtPos(pf->fp, INDEX_TYPE_OFFSET, &(pf->ind_type), sizeof(pf->ind_type));
188 DEBUG_INFO(("index_type = %i\n", pf->ind_type)); 175 DEBUG_INFO(("index_type = %i\n", pf->ind_type));
189 if (pf->ind_type != INDEX_TYPE) { 176 if (pf->ind_type != INDEX_TYPE) {
190 // try with 64 bit format 177 // try with 64 bit format
191 do_read64 = 1; 178 pf->do_read64 = 1;
192 if (pf->ind_type != INDEX_TYPE) { 179 if (pf->ind_type != INDEX_TYPE) {
193 WARN(("unknown .pst format, possibly newer than Outlook 2003 PST file?\n")); 180 WARN(("unknown .pst format, possibly newer than Outlook 2003 PST file?\n"));
194 DEBUG_RET(); 181 DEBUG_RET();
195 return -1; 182 return -1;
196 } 183 }
198 WARN(("switching to 64 bit format...\n")); 185 WARN(("switching to 64 bit format...\n"));
199 } 186 }
200 } 187 }
201 188
202 // read encryption setting 189 // read encryption setting
203 _pst_getAtPos(pf->fp, ENC_OFFSET, &(pf->encryption), sizeof(unsigned char)); 190 (void)pst_getAtPos(pf->fp, ENC_OFFSET, &(pf->encryption), sizeof(pf->encryption));
204 DEBUG_INFO(("encrypt = %i\n", pf->encryption)); 191 DEBUG_INFO(("encrypt = %i\n", pf->encryption));
205 192
206 pf->index2_count = _pst_getIntAtPos(pf->fp, SECOND_COUNT); 193 pf->index2_back = pst_getIntAtPos(pf, SECOND_BACK);
207 pf->index2 = _pst_getIntAtPos(pf->fp, SECOND_POINTER ); 194 pf->index2 = pst_getIntAtPos(pf, SECOND_POINTER);
208 pf->size = _pst_getIntAtPos( pf->fp, FILE_SIZE_POINTER ); 195 pf->size = pst_getIntAtPos(pf, FILE_SIZE_POINTER);
209 DEBUG_INFO(("Pointer2 is %#X, count %i[%#x]\n", pf->index2, pf->index2_count, pf->index2_count)); 196 DEBUG_INFO(("Pointer2 is %#llx, count %lli[%#llx]\n", pf->index2, pf->index2_back, pf->index2_back));
210 197
211 pf->index1_count = _pst_getIntAtPos(pf->fp, INDEX_COUNT); 198 pf->index1_back = pst_getIntAtPos(pf, INDEX_BACK);
212 pf->index1 = _pst_getIntAtPos(pf->fp, INDEX_POINTER); 199 pf->index1 = pst_getIntAtPos(pf, INDEX_POINTER);
213 DEBUG_INFO(("Pointer1 is %#X, count %i[%#x]\n", pf->index1, pf->index1_count, pf->index1_count)); 200 DEBUG_INFO(("Pointer1 is %#llx, count %lli[%#llx]\n", pf->index1, pf->index1_back, pf->index1_back));
214 201
215 DEBUG_RET(); 202 DEBUG_RET();
216 return 0; 203 return 0;
217 } 204 }
218 205
219 206
220 int32_t pst_close(pst_file *pf) { 207 int pst_close(pst_file *pf) {
221 DEBUG_ENT("pst_close"); 208 DEBUG_ENT("pst_close");
222 if (!pf->fp) { 209 if (!pf->fp) {
223 WARN(("cannot close NULL fp\n")); 210 WARN(("cannot close NULL fp\n"));
224 DEBUG_RET(); 211 DEBUG_RET();
225 return -1; 212 return -1;
228 WARN(("fclose returned non-zero value\n")); 215 WARN(("fclose returned non-zero value\n"));
229 DEBUG_RET(); 216 DEBUG_RET();
230 return -1; 217 return -1;
231 } 218 }
232 // we must free the id linklist and the desc tree 219 // we must free the id linklist and the desc tree
233 _pst_free_id (pf->i_head); 220 pst_free_id (pf->i_head);
234 _pst_free_desc (pf->d_head); 221 pst_free_desc (pf->d_head);
235 _pst_free_xattrib (pf->x_head); 222 pst_free_xattrib (pf->x_head);
236 DEBUG_RET(); 223 DEBUG_RET();
237 return 0; 224 return 0;
238 } 225 }
239 226
240 227
245 DEBUG_INDEX(("There isn't a top of folder record here.\n")); 232 DEBUG_INDEX(("There isn't a top of folder record here.\n"));
246 ret = NULL; 233 ret = NULL;
247 } else if (!root->message_store->top_of_personal_folder) { 234 } else if (!root->message_store->top_of_personal_folder) {
248 // this is the OST way 235 // this is the OST way
249 // ASSUMPTION: Top Of Folders record in PST files is *always* descid 0x2142 236 // ASSUMPTION: Top Of Folders record in PST files is *always* descid 0x2142
250 ret = _pst_getDptr(pf, 0x2142); 237 ret = pst_getDptr(pf, (uint64_t)0x2142);
251 } else { 238 } else {
252 ret = _pst_getDptr(pf, root->message_store->top_of_personal_folder->id); 239 ret = pst_getDptr(pf, root->message_store->top_of_personal_folder->id);
253 } 240 }
254 DEBUG_RET(); 241 DEBUG_RET();
255 return ret; 242 return ret;
256 } 243 }
257 244
258 245
259 int32_t pst_attach_to_mem(pst_file *pf, pst_item_attach *attach, unsigned char **b){ 246 size_t pst_attach_to_mem(pst_file *pf, pst_item_attach *attach, unsigned char **b){
260 int32_t size=0; 247 size_t size=0;
261 pst_index_ll *ptr; 248 pst_index_ll *ptr;
262 struct holder h = {b, NULL, 0, "", 0}; 249 struct holder h = {b, NULL, 0, "", 0};
263 DEBUG_ENT("pst_attach_to_mem"); 250 DEBUG_ENT("pst_attach_to_mem");
264 if (attach->id_val != -1) { 251 if (attach->id_val != (uint64_t)-1) {
265 ptr = _pst_getID(pf, attach->id_val); 252 ptr = pst_getID(pf, attach->id_val);
266 if (ptr) { 253 if (ptr) {
267 size = _pst_ff_getID2data(pf, ptr, &h); 254 size = pst_ff_getID2data(pf, ptr, &h);
268 } else { 255 } else {
269 DEBUG_WARN(("Couldn't find ID pointer. Cannot handle attachment\n")); 256 DEBUG_WARN(("Couldn't find ID pointer. Cannot handle attachment\n"));
270 size = 0; 257 size = 0;
271 } 258 }
272 attach->size = size; // may as well update it to what is correct for this instance 259 attach->size = size; // may as well update it to what is correct for this instance
276 DEBUG_RET(); 263 DEBUG_RET();
277 return size; 264 return size;
278 } 265 }
279 266
280 267
281 int32_t pst_attach_to_file(pst_file *pf, pst_item_attach *attach, FILE* fp) { 268 size_t pst_attach_to_file(pst_file *pf, pst_item_attach *attach, FILE* fp) {
282 pst_index_ll *ptr; 269 pst_index_ll *ptr;
283 struct holder h = {NULL, fp, 0, "", 0}; 270 struct holder h = {NULL, fp, 0, "", 0};
284 int32_t size; 271 size_t size;
285 DEBUG_ENT("pst_attach_to_file"); 272 DEBUG_ENT("pst_attach_to_file");
286 if (attach->id_val != -1) { 273 if (attach->id_val != (uint64_t)-1) {
287 ptr = _pst_getID(pf, attach->id_val); 274 ptr = pst_getID(pf, attach->id_val);
288 if (ptr) { 275 if (ptr) {
289 size = _pst_ff_getID2data(pf, ptr, &h); 276 size = pst_ff_getID2data(pf, ptr, &h);
290 } else { 277 } else {
291 DEBUG_WARN(("Couldn't find ID pointer. Cannot save attachment to file\n")); 278 DEBUG_WARN(("Couldn't find ID pointer. Cannot save attachment to file\n"));
292 size = 0; 279 size = 0;
293 } 280 }
294 attach->size = size; 281 attach->size = size;
295 } else { 282 } else {
296 // save the attachment to file 283 // save the attachment to file
297 size = attach->size; 284 size = attach->size;
298 pst_fwrite(attach->data, 1, size, fp); 285 (void)pst_fwrite(attach->data, (size_t)1, size, fp);
299 } 286 }
300 DEBUG_RET(); 287 DEBUG_RET();
301 return 1; 288 return size;
302 } 289 }
303 290
304 291
305 int32_t pst_attach_to_file_base64(pst_file *pf, pst_item_attach *attach, FILE* fp) { 292 size_t pst_attach_to_file_base64(pst_file *pf, pst_item_attach *attach, FILE* fp) {
306 pst_index_ll *ptr; 293 pst_index_ll *ptr;
307 struct holder h = {NULL, fp, 1, "", 0}; 294 struct holder h = {NULL, fp, 1, "", 0};
308 int32_t size; 295 size_t size;
309 char *c; 296 char *c;
310 DEBUG_ENT("pst_attach_to_file_base64"); 297 DEBUG_ENT("pst_attach_to_file_base64");
311 if (attach->id_val != -1) { 298 if (attach->id_val != (uint64_t)-1) {
312 ptr = _pst_getID(pf, attach->id_val); 299 ptr = pst_getID(pf, attach->id_val);
313 if (ptr) { 300 if (ptr) {
314 size = _pst_ff_getID2data(pf, ptr, &h); 301 size = pst_ff_getID2data(pf, ptr, &h);
315 // will need to encode any bytes left over 302 // will need to encode any bytes left over
316 c = base64_encode(h.base64_extra_chars, h.base64_extra); 303 c = base64_encode(h.base64_extra_chars, (size_t)h.base64_extra);
317 if (c) { 304 if (c) {
318 pst_fwrite(c, 1, strlen(c), fp); 305 (void)pst_fwrite(c, (size_t)1, strlen(c), fp);
319 free(c); // caught by valgrind 306 free(c); // caught by valgrind
320 } 307 }
321 } else { 308 } else {
322 DEBUG_WARN (("Couldn't find ID pointer. Cannot save attachment to Base64\n")); 309 DEBUG_WARN (("Couldn't find ID pointer. Cannot save attachment to Base64\n"));
323 size = 0; 310 size = 0;
325 attach->size = size; 312 attach->size = size;
326 } else { 313 } else {
327 // encode the attachment to the file 314 // encode the attachment to the file
328 c = base64_encode(attach->data, attach->size); 315 c = base64_encode(attach->data, attach->size);
329 if (c) { 316 if (c) {
330 pst_fwrite(c, 1, strlen(c), fp); 317 (void)pst_fwrite(c, (size_t)1, strlen(c), fp);
331 free(c); // caught by valgrind 318 free(c); // caught by valgrind
332 } 319 }
333 size = attach->size; 320 size = attach->size;
334 } 321 }
335 DEBUG_RET(); 322 DEBUG_RET();
336 return 1; 323 return size;
337 } 324 }
338 325
339 326
340 int32_t pst_load_index (pst_file *pf) { 327 int pst_load_index (pst_file *pf) {
341 int32_t x; 328 int x;
342 uint64_t y; 329 uint64_t y;
343 DEBUG_ENT("pst_load_index"); 330 DEBUG_ENT("pst_load_index");
344 if (!pf) { 331 if (!pf) {
345 WARN(("Cannot load index for a NULL pst_file\n")); 332 WARN(("Cannot load index for a NULL pst_file\n"));
346 DEBUG_RET(); 333 DEBUG_RET();
347 return -1; 334 return -1;
348 } 335 }
349 336
350 x = _pst_build_id_ptr(pf, pf->index1, 0, pf->index1_count, 0, UINT64_MAX); 337 x = pst_build_id_ptr(pf, pf->index1, 0, pf->index1_back, 0, UINT64_MAX);
351 DEBUG_INDEX(("build id ptr returns %i\n", x)); 338 DEBUG_INDEX(("build id ptr returns %i\n", x));
352 339
353 y = 0; 340 y = 0;
354 x = _pst_build_desc_ptr(pf, pf->index2, 0, pf->index2_count, &y, 0x21, UINT64_MAX); 341 x = pst_build_desc_ptr(pf, pf->index2, 0, pf->index2_back, &y, (uint64_t)0x21, UINT64_MAX);
355 DEBUG_INDEX(("build desc ptr returns %i\n", x)); 342 DEBUG_INDEX(("build desc ptr returns %i\n", x));
356 343
357 DEBUG_CODE(_pst_printDptr(pf);); 344 DEBUG_CODE((void)pst_printDptr(pf););
358 DEBUG_RET(); 345 DEBUG_RET();
359 return 0; 346 return 0;
360 } 347 }
361 348
362 349
372 DEBUG_RET(); 359 DEBUG_RET();
373 return r; 360 return r;
374 } 361 }
375 362
376 363
377 typedef struct _pst_x_attrib { 364 typedef struct pst_x_attrib {
378 uint16_t extended; 365 uint16_t extended;
379 uint16_t zero; 366 uint16_t zero;
380 uint16_t type; 367 uint16_t type;
381 uint16_t map; 368 uint16_t map;
382 } pst_x_attrib; 369 } pst_x_attrib;
383 370
384 371
385 int32_t pst_load_extended_attributes(pst_file *pf) { 372 int pst_load_extended_attributes(pst_file *pf) {
386 // for PST files this will load up ID2 0x61 and check it's "list" attribute. 373 // for PST files this will load up ID2 0x61 and check it's "list" attribute.
387 pst_desc_ll *p; 374 pst_desc_ll *p;
388 pst_num_array *na; 375 pst_num_array *na;
389 pst_index2_ll *list2 = NULL; 376 pst_index2_ll *id2_head = NULL;
390 unsigned char * buffer=NULL, *headerbuffer=NULL;//, *tc; 377 unsigned char *buffer=NULL, *headerbuffer=NULL;
378 size_t bsize=0, hsize=0, bptr=0;
391 pst_x_attrib xattrib; 379 pst_x_attrib xattrib;
392 int32_t bptr = 0, bsize, hsize, tint, err=0, x; 380 int32_t tint, err=0, x;
393 pst_x_attrib_ll *ptr, *p_head=NULL, *p_sh=NULL, *p_sh2=NULL; 381 pst_x_attrib_ll *ptr, *p_head=NULL, *p_sh=NULL, *p_sh2=NULL;
394 382
395 DEBUG_ENT("pst_loadExtendedAttributes"); 383 DEBUG_ENT("pst_loadExtendedAttributes");
396 if ((p = _pst_getDptr(pf, 0x61)) == NULL) { 384 if ((p = pst_getDptr(pf, (uint64_t)0x61)) == NULL) {
397 DEBUG_WARN(("Cannot find DescID 0x61 for loading the Extended Attributes\n")); 385 DEBUG_WARN(("Cannot find DescID 0x61 for loading the Extended Attributes\n"));
398 DEBUG_RET(); 386 DEBUG_RET();
399 return 0; 387 return 0;
400 } 388 }
401 389
404 DEBUG_RET(); 392 DEBUG_RET();
405 return 0; 393 return 0;
406 } 394 }
407 395
408 if (p->list_index) { 396 if (p->list_index) {
409 list2 = _pst_build_id2(pf, p->list_index, NULL); 397 id2_head = pst_build_id2(pf, p->list_index, NULL);
410 _pst_printID2ptr(list2); 398 (void)pst_printID2ptr(id2_head);
411 } else { 399 } else {
412 DEBUG_WARN(("Have not been able to fetch any id2 values for item 0x61. Brace yourself!\n")); 400 DEBUG_WARN(("Have not been able to fetch any id2 values for item 0x61. Brace yourself!\n"));
413 } 401 }
414 402
415 na = _pst_parse_block(pf, p->desc->id, list2); 403 na = pst_parse_block(pf, p->desc->id, id2_head);
416 if (!na) { 404 if (!na) {
417 DEBUG_WARN(("Cannot process desc block for item 0x61. Not loading extended Attributes\n")); 405 DEBUG_WARN(("Cannot process desc block for item 0x61. Not loading extended Attributes\n"));
418 if (list2) _pst_free_id2(list2); 406 if (id2_head) pst_free_id2(id2_head);
419 DEBUG_RET(); 407 DEBUG_RET();
420 return 0; 408 return 0;
421 } 409 }
422 410
423 x = 0; 411 x = 0;
424 while (x < na->count_item) { 412 while (x < na->count_item) {
425 if (na->items[x]->id == 0x0003) { 413 if (na->items[x]->id == (uint32_t)0x0003) {
426 buffer = na->items[x]->data; 414 buffer = na->items[x]->data;
427 bsize = na->items[x]->size; 415 bsize = na->items[x]->size;
428 } else if (na->items[x]->id == 0x0004) { 416 } else if (na->items[x]->id == (uint32_t)0x0004) {
429 headerbuffer = na->items[x]->data; 417 headerbuffer = na->items[x]->data;
430 hsize = na->items[x]->size; 418 hsize = na->items[x]->size;
419 } else {
420 // leave them null
431 } 421 }
432 x++; 422 x++;
433 } 423 }
434 424
435 if (!buffer) { 425 if (!buffer) {
436 if (na) _pst_free_list(na); 426 if (na) pst_free_list(na);
437 DEBUG_WARN(("No extended attributes buffer found. Not processing\n")); 427 DEBUG_WARN(("No extended attributes buffer found. Not processing\n"));
438 DEBUG_RET(); 428 DEBUG_RET();
439 return 0; 429 return 0;
440 } 430 }
441 431
445 LE16_CPU(xattrib.type); 435 LE16_CPU(xattrib.type);
446 LE16_CPU(xattrib.map); 436 LE16_CPU(xattrib.map);
447 bptr += sizeof(xattrib); 437 bptr += sizeof(xattrib);
448 438
449 while (xattrib.type != 0 && bptr < bsize) { 439 while (xattrib.type != 0 && bptr < bsize) {
450 ptr = (pst_x_attrib_ll*) xmalloc(sizeof(pst_x_attrib_ll)); 440 ptr = (pst_x_attrib_ll*) xmalloc(sizeof(*ptr));
451 memset(ptr, 0, sizeof(pst_x_attrib_ll)); 441 memset(ptr, 0, sizeof(*ptr));
452 ptr->type = xattrib.type; 442 ptr->type = xattrib.type;
453 ptr->map = xattrib.map+0x8000; 443 ptr->map = xattrib.map+0x8000;
454 ptr->next = NULL; 444 ptr->next = NULL;
455 DEBUG_INDEX(("xattrib: ext = %#hx, zero = %#hx, type = %#hx, map = %#hx\n", 445 DEBUG_INDEX(("xattrib: ext = %#hx, zero = %#hx, type = %#hx, map = %#hx\n",
456 xattrib.extended, xattrib.zero, xattrib.type, xattrib.map)); 446 xattrib.extended, xattrib.zero, xattrib.type, xattrib.map));
457 err=0; 447 err=0;
458 if (xattrib.type & 0x0001) { // if the Bit 1 is set 448 if (xattrib.type & 0x0001) { // if the Bit 1 is set
460 if (xattrib.extended < hsize) { 450 if (xattrib.extended < hsize) {
461 char *wt; 451 char *wt;
462 // copy the size of the header. It is 32 bit int 452 // copy the size of the header. It is 32 bit int
463 memcpy(&tint, &(headerbuffer[xattrib.extended]), sizeof(tint)); 453 memcpy(&tint, &(headerbuffer[xattrib.extended]), sizeof(tint));
464 LE32_CPU(tint); 454 LE32_CPU(tint);
465 wt = (char*) xmalloc(tint+2); // plus 2 for a uni-code zero 455 wt = (char*) xmalloc((size_t)(tint+2)); // plus 2 for a uni-code zero
466 memset(wt, 0, tint+2); 456 memset(wt, 0, (size_t)(tint+2));
467 memcpy(wt, &(headerbuffer[xattrib.extended+sizeof(tint)]), tint); 457 memcpy(wt, &(headerbuffer[xattrib.extended+sizeof(tint)]), (size_t)tint);
468 ptr->data = _pst_wide_to_single(wt, tint); 458 ptr->data = pst_wide_to_single(wt, tint);
469 free(wt); 459 free(wt);
470 DEBUG_INDEX(("Read string (converted from UTF-16): %s\n", ptr->data)); 460 DEBUG_INDEX(("Read string (converted from UTF-16): %s\n", ptr->data));
471 } else { 461 } else {
472 DEBUG_INDEX(("Cannot read outside of buffer [%i !< %i]\n", xattrib.extended, hsize)); 462 DEBUG_INDEX(("Cannot read outside of buffer [%i !< %i]\n", xattrib.extended, hsize));
473 } 463 }
474 ptr->mytype = PST_MAP_HEADER; 464 ptr->mytype = PST_MAP_HEADER;
475 } else { 465 } else {
476 // contains the attribute code to map to. 466 // contains the attribute code to map to.
477 ptr->data = (int*)xmalloc(sizeof(int32_t)); 467 ptr->data = (uint32_t*)xmalloc(sizeof(uint32_t));
478 memset(ptr->data, 0, sizeof(int32_t)); 468 memset(ptr->data, 0, sizeof(uint32_t));
479 *((int32_t*)ptr->data) = xattrib.extended; 469 *((uint32_t*)ptr->data) = xattrib.extended;
480 ptr->mytype = PST_MAP_ATTRIB; 470 ptr->mytype = PST_MAP_ATTRIB;
481 DEBUG_INDEX(("Mapped attribute %#x to %#x\n", ptr->map, *((int32_t*)ptr->data))); 471 DEBUG_INDEX(("Mapped attribute %#x to %#x\n", ptr->map, *((int32_t*)ptr->data)));
482 } 472 }
483 473
484 if (err==0) { 474 if (err==0) {
507 LE16_CPU(xattrib.zero); 497 LE16_CPU(xattrib.zero);
508 LE16_CPU(xattrib.type); 498 LE16_CPU(xattrib.type);
509 LE16_CPU(xattrib.map); 499 LE16_CPU(xattrib.map);
510 bptr += sizeof(xattrib); 500 bptr += sizeof(xattrib);
511 } 501 }
512 if (list2) _pst_free_id2(list2); 502 if (id2_head) pst_free_id2(id2_head);
513 if (na) _pst_free_list(na); 503 if (na) pst_free_list(na);
514 pf->x_head = p_head; 504 pf->x_head = p_head;
515 DEBUG_RET(); 505 DEBUG_RET();
516 return 1; 506 return 1;
517 } 507 }
518 508
534 #define ITEM_SIZE64 24 524 #define ITEM_SIZE64 24
535 #define DESC_SIZE64 32 525 #define DESC_SIZE64 32
536 #define INDEX_COUNT_MAX64 20 // max active items 526 #define INDEX_COUNT_MAX64 20 // max active items
537 #define DESC_COUNT_MAX64 15 // max active items 527 #define DESC_COUNT_MAX64 15 // max active items
538 528
539 #define BLOCK_SIZE ((do_read64) ? BLOCK_SIZE64 : BLOCK_SIZE32) 529 #define BLOCK_SIZE (size_t)((pf->do_read64) ? BLOCK_SIZE64 : BLOCK_SIZE32)
540 #define DESC_BLOCK_SIZE ((do_read64) ? DESC_BLOCK_SIZE64 : DESC_BLOCK_SIZE32) 530 #define DESC_BLOCK_SIZE (size_t)((pf->do_read64) ? DESC_BLOCK_SIZE64 : DESC_BLOCK_SIZE32)
541 #define ITEM_COUNT_OFFSET ((do_read64) ? ITEM_COUNT_OFFSET64 : ITEM_COUNT_OFFSET32) 531 #define ITEM_COUNT_OFFSET (size_t)((pf->do_read64) ? ITEM_COUNT_OFFSET64 : ITEM_COUNT_OFFSET32)
542 #define LEVEL_INDICATOR_OFFSET ((do_read64) ? LEVEL_INDICATOR_OFFSET64 : LEVEL_INDICATOR_OFFSET32) 532 #define LEVEL_INDICATOR_OFFSET (size_t)((pf->do_read64) ? LEVEL_INDICATOR_OFFSET64 : LEVEL_INDICATOR_OFFSET32)
543 #define BACKLINK_OFFSET ((do_read64) ? BACKLINK_OFFSET64 : BACKLINK_OFFSET32) 533 #define BACKLINK_OFFSET (size_t)((pf->do_read64) ? BACKLINK_OFFSET64 : BACKLINK_OFFSET32)
544 #define ITEM_SIZE ((do_read64) ? ITEM_SIZE64 : ITEM_SIZE32) 534 #define ITEM_SIZE (size_t)((pf->do_read64) ? ITEM_SIZE64 : ITEM_SIZE32)
545 #define DESC_SIZE ((do_read64) ? DESC_SIZE64 : DESC_SIZE32) 535 #define DESC_SIZE (size_t)((pf->do_read64) ? DESC_SIZE64 : DESC_SIZE32)
546 #define INDEX_COUNT_MAX ((do_read64) ? INDEX_COUNT_MAX64 : INDEX_COUNT_MAX32) 536 #define INDEX_COUNT_MAX (int32_t)((pf->do_read64) ? INDEX_COUNT_MAX64 : INDEX_COUNT_MAX32)
547 #define DESC_COUNT_MAX ((do_read64) ? DESC_COUNT_MAX64 : DESC_COUNT_MAX32) 537 #define DESC_COUNT_MAX (int32_t)((pf->do_read64) ? DESC_COUNT_MAX64 : DESC_COUNT_MAX32)
548 538
549 539
550 int _pst_decode_desc( pst_descn *desc, char *buf ) { 540 static size_t pst_decode_desc(pst_file *pf, pst_descn *desc, char *buf);
551 int r; 541 static size_t pst_decode_desc(pst_file *pf, pst_descn *desc, char *buf) {
552 if (do_read64) { 542 size_t r;
543 if (pf->do_read64) {
553 DEBUG_INDEX(("Decoding desc64\n")); 544 DEBUG_INDEX(("Decoding desc64\n"));
554 DEBUG_HEXDUMPC(buf, sizeof(pst_descn), 0x10); 545 DEBUG_HEXDUMPC(buf, sizeof(pst_descn), 0x10);
555 memcpy(desc, buf, sizeof(pst_descn)); 546 memcpy(desc, buf, sizeof(pst_descn));
556 LE64_CPU(desc->d_id); 547 LE64_CPU(desc->d_id);
557 LE64_CPU(desc->desc_id); 548 LE64_CPU(desc->desc_id);
578 } 569 }
579 return r; 570 return r;
580 } 571 }
581 572
582 573
583 int _pst_decode_table( struct _pst_table_ptr_structn *table, char *buf ) { 574 static size_t pst_decode_table(pst_file *pf, struct pst_table_ptr_structn *table, char *buf);
584 int r; 575 static size_t pst_decode_table(pst_file *pf, struct pst_table_ptr_structn *table, char *buf) {
585 if (do_read64) { 576 size_t r;
577 if (pf->do_read64) {
586 DEBUG_INDEX(("Decoding table64\n")); 578 DEBUG_INDEX(("Decoding table64\n"));
587 DEBUG_HEXDUMPC(buf, sizeof(struct _pst_table_ptr_structn), 0x10); 579 DEBUG_HEXDUMPC(buf, sizeof(struct pst_table_ptr_structn), 0x10);
588 memcpy(table, buf, sizeof(struct _pst_table_ptr_structn)); 580 memcpy(table, buf, sizeof(struct pst_table_ptr_structn));
589 LE64_CPU(table->start); 581 LE64_CPU(table->start);
590 LE64_CPU(table->u1); 582 LE64_CPU(table->u1);
591 LE64_CPU(table->offset); 583 LE64_CPU(table->offset);
592 r =sizeof(struct _pst_table_ptr_structn); 584 r =sizeof(struct pst_table_ptr_structn);
593 } 585 }
594 else { 586 else {
595 struct _pst_table_ptr_struct32 t32; 587 struct pst_table_ptr_struct32 t32;
596 DEBUG_INDEX(("Decoding table32\n")); 588 DEBUG_INDEX(("Decoding table32\n"));
597 DEBUG_HEXDUMPC(buf, sizeof( struct _pst_table_ptr_struct32), 0x10); 589 DEBUG_HEXDUMPC(buf, sizeof( struct pst_table_ptr_struct32), 0x10);
598 memcpy(&t32, buf, sizeof(struct _pst_table_ptr_struct32)); 590 memcpy(&t32, buf, sizeof(struct pst_table_ptr_struct32));
599 LE32_CPU(t32.start); 591 LE32_CPU(t32.start);
600 LE32_CPU(t32.u1); 592 LE32_CPU(t32.u1);
601 LE32_CPU(t32.offset); 593 LE32_CPU(t32.offset);
602 table->start = t32.start; 594 table->start = t32.start;
603 table->u1 = t32.u1; 595 table->u1 = t32.u1;
604 table->offset = t32.offset; 596 table->offset = t32.offset;
605 r = sizeof(struct _pst_table_ptr_struct32); 597 r = sizeof(struct pst_table_ptr_struct32);
606 } 598 }
607 return r; 599 return r;
608 } 600 }
609 601
610 602
611 int _pst_decode_index( pst_index *index, char *buf ) { 603 static size_t pst_decode_index(pst_file *pf, pst_index *index, char *buf);
612 int r; 604 static size_t pst_decode_index(pst_file *pf, pst_index *index, char *buf) {
613 if (do_read64) { 605 size_t r;
606 if (pf->do_read64) {
614 DEBUG_INDEX(("Decoding index64\n")); 607 DEBUG_INDEX(("Decoding index64\n"));
615 DEBUG_HEXDUMPC(buf, sizeof(pst_index), 0x10); 608 DEBUG_HEXDUMPC(buf, sizeof(pst_index), 0x10);
616 memcpy(index, buf, sizeof(pst_index)); 609 memcpy(index, buf, sizeof(pst_index));
617 LE64_CPU(index->id); 610 LE64_CPU(index->id);
618 LE64_CPU(index->offset); 611 LE64_CPU(index->offset);
623 } else { 616 } else {
624 pst_index32 index32; 617 pst_index32 index32;
625 DEBUG_INDEX(("Decoding index32\n")); 618 DEBUG_INDEX(("Decoding index32\n"));
626 DEBUG_HEXDUMPC(buf, sizeof(pst_index32), 0x10); 619 DEBUG_HEXDUMPC(buf, sizeof(pst_index32), 0x10);
627 memcpy(&index32, buf, sizeof(pst_index32)); 620 memcpy(&index32, buf, sizeof(pst_index32));
628 LE32_CPU(index32->id); 621 LE32_CPU(index32.id);
629 LE32_CPU(index32->offset); 622 LE32_CPU(index32.offset);
630 LE16_CPU(index32->size); 623 LE16_CPU(index32.size);
631 LE16_CPU(index32->u1); 624 LE16_CPU(index32.u1);
632 index->id = index32.id; 625 index->id = index32.id;
633 index->offset = index32.offset; 626 index->offset = index32.offset;
634 index->size = index32.size; 627 index->size = index32.size;
635 index->u1 = index32.u1; 628 index->u1 = index32.u1;
636 r = sizeof(pst_index32); 629 r = sizeof(pst_index32);
637 } 630 }
638 return r; 631 return r;
639 } 632 }
640 633
641 634
642 int32_t _pst_build_id_ptr(pst_file *pf, off_t offset, int32_t depth, int64_t linku1, uint64_t start_val, uint64_t end_val) { 635 static size_t pst_decode_assoc(pst_file *pf, pst_id2_assoc *assoc, char *buf);
643 struct _pst_table_ptr_structn table, table2; 636 static size_t pst_decode_assoc(pst_file *pf, pst_id2_assoc *assoc, char *buf) {
637 size_t r;
638 if (pf->do_read64) {
639 DEBUG_INDEX(("Decoding assoc64\n"));
640 DEBUG_HEXDUMPC(buf, sizeof(pst_id2_assoc), 0x10);
641 memcpy(assoc, buf, sizeof(pst_id2_assoc));
642 LE64_CPU(assoc->id2);
643 LE64_CPU(assoc->id);
644 LE64_CPU(assoc->table2);
645 r = sizeof(pst_id2_assoc);
646 } else {
647 pst_id2_assoc32 assoc32;
648 DEBUG_INDEX(("Decoding assoc32\n"));
649 DEBUG_HEXDUMPC(buf, sizeof(pst_id2_assoc32), 0x10);
650 memcpy(&assoc32, buf, sizeof(pst_id2_assoc32));
651 LE32_CPU(assoc32.id2);
652 LE32_CPU(assoc32.id);
653 LE32_CPU(assoc32.table2);
654 assoc->id2 = assoc32.id2;
655 assoc->id = assoc32.id;
656 assoc->table2 = assoc32.table2;
657 r = sizeof(pst_id2_assoc32);
658 }
659 return r;
660 }
661
662
663 int pst_build_id_ptr(pst_file *pf, off_t offset, int32_t depth, uint64_t linku1, uint64_t start_val, uint64_t end_val) {
664 struct pst_table_ptr_structn table, table2;
644 pst_index_ll *i_ptr=NULL; 665 pst_index_ll *i_ptr=NULL;
645 pst_index index; 666 pst_index index;
646 int32_t x, item_count; 667 int32_t x, item_count;
647 uint64_t old = start_val; 668 uint64_t old = start_val;
648 char *buf = NULL, *bptr; 669 char *buf = NULL, *bptr;
649 670
650 DEBUG_ENT("_pst_build_id_ptr"); 671 DEBUG_ENT("pst_build_id_ptr");
651 DEBUG_INDEX(("offset %x depth %i linku1 %llx start %llx end %llx\n", offset, depth, linku1, start_val, end_val)); 672 DEBUG_INDEX(("offset %x depth %i linku1 %llx start %llx end %llx\n", offset, depth, linku1, start_val, end_val));
652 if (end_val <= start_val) { 673 if (end_val <= start_val) {
653 DEBUG_WARN(("The end value is BEFORE the start value. This function will quit. Soz. [start:%#llx, end:%#llx]\n", start_val, end_val)); 674 DEBUG_WARN(("The end value is BEFORE the start value. This function will quit. Soz. [start:%#llx, end:%#llx]\n", start_val, end_val));
654 DEBUG_RET(); 675 DEBUG_RET();
655 return -1; 676 return -1;
656 } 677 }
657 DEBUG_INDEX(("Reading index block\n")); 678 DEBUG_INDEX(("Reading index block\n"));
658 if (_pst_read_block_size(pf, offset, BLOCK_SIZE, &buf, 0, 0) < BLOCK_SIZE) { 679 if (pst_read_block_size(pf, offset, BLOCK_SIZE, &buf, 0, 0) < BLOCK_SIZE) {
659 DEBUG_WARN(("Failed to read %i bytes\n", BLOCK_SIZE)); 680 DEBUG_WARN(("Failed to read %i bytes\n", BLOCK_SIZE));
660 if (buf) free(buf); 681 if (buf) free(buf);
661 DEBUG_RET(); 682 DEBUG_RET();
662 return -1; 683 return -1;
663 } 684 }
664 bptr = buf; 685 bptr = buf;
665 DEBUG_HEXDUMPC(buf, BLOCK_SIZE, ITEM_SIZE32); 686 DEBUG_HEXDUMPC(buf, BLOCK_SIZE, ITEM_SIZE32);
666 item_count = (int)(unsigned)(buf[ITEM_COUNT_OFFSET]); 687 item_count = (int32_t)(unsigned)(buf[ITEM_COUNT_OFFSET]);
667 if (item_count > INDEX_COUNT_MAX) { 688 if (item_count > INDEX_COUNT_MAX) {
668 DEBUG_WARN(("Item count %i too large, max is %i\n", item_count, INDEX_COUNT_MAX)); 689 DEBUG_WARN(("Item count %i too large, max is %i\n", item_count, INDEX_COUNT_MAX));
669 if (buf) free(buf); 690 if (buf) free(buf);
670 DEBUG_RET(); 691 DEBUG_RET();
671 return -1; 692 return -1;
672 } 693 }
673 index.id = _getIntAt(buf+BACKLINK_OFFSET); 694 index.id = pst_getIntAt(pf, buf+BACKLINK_OFFSET);
674 if (index.id != linku1) { 695 if (index.id != linku1) {
675 DEBUG_WARN(("Backlink %#llx in this node does not match required %#llx\n", index.id, linku1)); 696 DEBUG_WARN(("Backlink %#llx in this node does not match required %#llx\n", index.id, linku1));
676 if (buf) free(buf); 697 if (buf) free(buf);
677 DEBUG_RET(); 698 DEBUG_RET();
678 return -1; 699 return -1;
680 701
681 if (buf[LEVEL_INDICATOR_OFFSET] == '\0') { 702 if (buf[LEVEL_INDICATOR_OFFSET] == '\0') {
682 // this node contains leaf pointers 703 // this node contains leaf pointers
683 x = 0; 704 x = 0;
684 while (x < item_count) { 705 while (x < item_count) {
685 bptr += _pst_decode_index(&index, bptr); 706 bptr += pst_decode_index(pf, &index, bptr);
686 x++; 707 x++;
687 if (index.id == 0) break; 708 if (index.id == 0) break;
688 DEBUG_INDEX(("[%i]%i Item [id = %#x, offset = %#x, u1 = %#x, size = %i(%#x)]\n", 709 DEBUG_INDEX(("[%i]%i Item [id = %#llx, offset = %#llx, u1 = %#x, size = %i(%#x)]\n",
689 depth, x, index.id, index.offset, index.u1, index.size, index.size)); 710 depth, x, index.id, index.offset, index.u1, index.size, index.size));
690 // if (index.id & 0x02) DEBUG_INDEX(("two-bit set!!\n")); 711 // if (index.id & 0x02) DEBUG_INDEX(("two-bit set!!\n"));
691 if ((index.id >= end_val) || (index.id < old)) { 712 if ((index.id >= end_val) || (index.id < old)) {
692 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n")); 713 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n"));
693 if (buf) free(buf); 714 if (buf) free(buf);
694 DEBUG_RET(); 715 DEBUG_RET();
695 return -1; 716 return -1;
696 } 717 }
697 old = index.id; 718 old = index.id;
698 if (x == 1) { // first entry 719 if (x == (int32_t)1) { // first entry
699 if ((start_val) && (index.id != start_val)) { 720 if ((start_val) && (index.id != start_val)) {
700 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n")); 721 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n"));
701 if (buf) free(buf); 722 if (buf) free(buf);
702 DEBUG_RET(); 723 DEBUG_RET();
703 return -1; 724 return -1;
715 } 736 }
716 } else { 737 } else {
717 // this node contains node pointers 738 // this node contains node pointers
718 x = 0; 739 x = 0;
719 while (x < item_count) { 740 while (x < item_count) {
720 bptr += _pst_decode_table(&table, bptr); 741 bptr += pst_decode_table(pf, &table, bptr);
721 x++; 742 x++;
722 if (table.start == 0) break; 743 if (table.start == 0) break;
723 if (x < item_count) { 744 if (x < item_count) {
724 _pst_decode_table(&table2, bptr); 745 (void)pst_decode_table(pf, &table2, bptr);
725 } 746 }
726 else { 747 else {
727 table2.start = end_val; 748 table2.start = end_val;
728 } 749 }
729 DEBUG_INDEX(("[%i] %i Index Table [start id = %#x, u1 = %#x, offset = %#x, end id = %#x]\n", 750 DEBUG_INDEX(("[%i] %i Index Table [start id = %#llx, u1 = %#llx, offset = %#llx, end id = %#llx]\n",
730 depth, x, table.start, table.u1, table.offset, table2.start)); 751 depth, x, table.start, table.u1, table.offset, table2.start));
731 if ((table.start >= end_val) || (table.start < old)) { 752 if ((table.start >= end_val) || (table.start < old)) {
732 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n")); 753 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n"));
733 if (buf) free(buf); 754 if (buf) free(buf);
734 DEBUG_RET(); 755 DEBUG_RET();
735 return -1; 756 return -1;
736 } 757 }
737 old = table.start; 758 old = table.start;
738 if (x == 1) { // first entry 759 if (x == (int32_t)1) { // first entry
739 if ((start_val) && (table.start != start_val)) { 760 if ((start_val) && (table.start != start_val)) {
740 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n")); 761 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n"));
741 if (buf) free(buf); 762 if (buf) free(buf);
742 DEBUG_RET(); 763 DEBUG_RET();
743 return -1; 764 return -1;
744 } 765 }
745 } 766 }
746 _pst_build_id_ptr(pf, table.offset, depth+1, table.u1, table.start, table2.start); 767 (void)pst_build_id_ptr(pf, table.offset, depth+1, table.u1, table.start, table2.start);
747 } 768 }
748 } 769 }
749 if (buf) free (buf); 770 if (buf) free (buf);
750 DEBUG_RET(); 771 DEBUG_RET();
751 return 0; 772 return 0;
763 /** only used for lost and found lists */ 784 /** only used for lost and found lists */
764 uint64_t parent; 785 uint64_t parent;
765 struct cache_list_node *next; 786 struct cache_list_node *next;
766 struct cache_list_node *prev; 787 struct cache_list_node *prev;
767 }; 788 };
768 struct cache_list_node *cache_head; 789 static struct cache_list_node *cache_head;
769 struct cache_list_node *cache_tail; 790 static struct cache_list_node *cache_tail;
770 struct cache_list_node *lostfound_head; 791 static struct cache_list_node *lostfound_head;
771 int32_t cache_count; 792 static int cache_count;
772 793
773 794
774 /** 795 /**
775 add the d_ptr descriptor into the global tree 796 add the d_ptr descriptor into the global tree
776 */ 797 */
777 void record_descriptor(pst_file *pf, pst_desc_ll *d_ptr, uint64_t parent_id) { 798 static void record_descriptor(pst_file *pf, pst_desc_ll *d_ptr, uint64_t parent_id);
799 static void record_descriptor(pst_file *pf, pst_desc_ll *d_ptr, uint64_t parent_id) {
778 struct cache_list_node *lostfound_ptr = NULL; 800 struct cache_list_node *lostfound_ptr = NULL;
779 struct cache_list_node *cache_ptr = NULL; 801 struct cache_list_node *cache_ptr = NULL;
780 pst_desc_ll *parent = NULL; 802 pst_desc_ll *parent = NULL;
781 803
782 if (parent_id == 0 || parent_id == d_ptr->id) { 804 if (parent_id == 0 || parent_id == d_ptr->id) {
795 // check in the cache for the parent 817 // check in the cache for the parent
796 cache_ptr = cache_head; 818 cache_ptr = cache_head;
797 while (cache_ptr && (cache_ptr->ptr->id != parent_id)) { 819 while (cache_ptr && (cache_ptr->ptr->id != parent_id)) {
798 cache_ptr = cache_ptr->next; 820 cache_ptr = cache_ptr->next;
799 } 821 }
800 if (!cache_ptr && (parent = _pst_getDptr(pf, parent_id)) == NULL) { 822 if (!cache_ptr && (parent = pst_getDptr(pf, parent_id)) == NULL) {
801 // check in the lost/found list 823 // check in the lost/found list
802 lostfound_ptr = lostfound_head; 824 lostfound_ptr = lostfound_head;
803 while (lostfound_ptr && (lostfound_ptr->ptr->id != parent_id)) { 825 while (lostfound_ptr && (lostfound_ptr->ptr->id != parent_id)) {
804 lostfound_ptr = lostfound_ptr->next; 826 lostfound_ptr = lostfound_ptr->next;
805 } 827 }
806 if (!lostfound_ptr) { 828 if (!lostfound_ptr) {
807 DEBUG_WARN(("ERROR -- cannot find parent with id %#x. Adding to lost/found\n", parent_id)); 829 DEBUG_WARN(("ERROR -- cannot find parent with id %#llx. Adding to lost/found\n", parent_id));
808 lostfound_ptr = (struct cache_list_node*) xmalloc(sizeof(struct cache_list_node)); 830 lostfound_ptr = (struct cache_list_node*) xmalloc(sizeof(struct cache_list_node));
809 lostfound_ptr->prev = NULL; 831 lostfound_ptr->prev = NULL;
810 lostfound_ptr->next = lostfound_head; 832 lostfound_ptr->next = lostfound_head;
811 lostfound_ptr->parent = parent_id; 833 lostfound_ptr->parent = parent_id;
812 lostfound_ptr->ptr = d_ptr; 834 lostfound_ptr->ptr = d_ptr;
813 lostfound_head = lostfound_ptr; 835 lostfound_head = lostfound_ptr;
814 } else { 836 } else {
815 parent = lostfound_ptr->ptr; 837 parent = lostfound_ptr->ptr;
816 DEBUG_INDEX(("Found parent (%#x) in Lost and Found\n", parent->id)); 838 DEBUG_INDEX(("Found parent (%#llx) in Lost and Found\n", parent->id));
817 } 839 }
818 } 840 }
819 841
820 if (cache_ptr || parent) { 842 if (cache_ptr || parent) {
821 if (cache_ptr) 843 if (cache_ptr)
849 parent->child_tail = d_ptr; 871 parent->child_tail = d_ptr;
850 } 872 }
851 } 873 }
852 } 874 }
853 875
854 int32_t _pst_build_desc_ptr (pst_file *pf, off_t offset, int32_t depth, int64_t linku1, uint64_t *high_id, uint64_t start_val, uint64_t end_val) { 876 int pst_build_desc_ptr (pst_file *pf, off_t offset, int32_t depth, uint64_t linku1, uint64_t *high_id, uint64_t start_val, uint64_t end_val) {
855 struct _pst_table_ptr_structn table, table2; 877 struct pst_table_ptr_structn table, table2;
856 pst_descn desc_rec; 878 pst_descn desc_rec;
857 pst_desc_ll *d_ptr=NULL, *parent=NULL; 879 pst_desc_ll *d_ptr=NULL, *parent=NULL;
858 int32_t x, item_count; 880 int32_t x, item_count;
859 uint32_t old = start_val; 881 uint32_t old = start_val;
860 char *buf = NULL, *bptr; 882 char *buf = NULL, *bptr;
869 cache_tail = NULL; 891 cache_tail = NULL;
870 lostfound_head = NULL; 892 lostfound_head = NULL;
871 cache_count = 0; 893 cache_count = 0;
872 } 894 }
873 895
874 DEBUG_ENT("_pst_build_desc_ptr"); 896 DEBUG_ENT("pst_build_desc_ptr");
875 DEBUG_INDEX(("offset %x depth %i linku1 %x start %x end %x\n", offset, depth, linku1, start_val, end_val)); 897 DEBUG_INDEX(("offset %llx depth %i linku1 %llx start %llx end %llx\n", offset, depth, linku1, start_val, end_val));
876 if (end_val <= start_val) { 898 if (end_val <= start_val) {
877 DEBUG_WARN(("The end value is BEFORE the start value. This function will quit. Soz. [start:%#x, end:%#x]\n", start_val, end_val)); 899 DEBUG_WARN(("The end value is BEFORE the start value. This function will quit. Soz. [start:%#llx, end:%#llx]\n", start_val, end_val));
878 DEBUG_RET(); 900 DEBUG_RET();
879 return -1; 901 return -1;
880 } 902 }
881 DEBUG_INDEX(("Reading desc block\n")); 903 DEBUG_INDEX(("Reading desc block\n"));
882 if (_pst_read_block_size(pf, offset, DESC_BLOCK_SIZE, &buf, 0, 0) < DESC_BLOCK_SIZE) { 904 if (pst_read_block_size(pf, offset, DESC_BLOCK_SIZE, &buf, 0, 0) < DESC_BLOCK_SIZE) {
883 DEBUG_WARN(("Failed to read %i bytes\n", DESC_BLOCK_SIZE)); 905 DEBUG_WARN(("Failed to read %i bytes\n", DESC_BLOCK_SIZE));
884 if (buf) free(buf); 906 if (buf) free(buf);
885 DEBUG_RET(); 907 DEBUG_RET();
886 return -1; 908 return -1;
887 } 909 }
888 bptr = buf; 910 bptr = buf;
889 item_count = (int)(unsigned)(buf[ITEM_COUNT_OFFSET]); 911 item_count = (int32_t)(unsigned)(buf[ITEM_COUNT_OFFSET]);
890 912
891 desc_rec.d_id = _getIntAt(buf+BACKLINK_OFFSET); 913 desc_rec.d_id = pst_getIntAt(pf, buf+BACKLINK_OFFSET);
892 if (desc_rec.d_id != linku1) { 914 if (desc_rec.d_id != linku1) {
893 DEBUG_WARN(("Backlink %#x in this node does not match required %#x\n", desc_rec.d_id, linku1)); 915 DEBUG_WARN(("Backlink %#llx in this node does not match required %#llx\n", desc_rec.d_id, linku1));
894 if (buf) free(buf); 916 if (buf) free(buf);
895 DEBUG_RET(); 917 DEBUG_RET();
896 return -1; 918 return -1;
897 } 919 }
898 if (buf[LEVEL_INDICATOR_OFFSET] == '\0') { 920 if (buf[LEVEL_INDICATOR_OFFSET] == '\0') {
904 DEBUG_RET(); 926 DEBUG_RET();
905 return -1; 927 return -1;
906 } 928 }
907 x = 0; 929 x = 0;
908 while (x < item_count) { 930 while (x < item_count) {
909 bptr += _pst_decode_desc(&desc_rec, bptr); 931 bptr += pst_decode_desc(pf, &desc_rec, bptr);
910 x++; 932 x++;
911 if (desc_rec.d_id == 0) break; 933 if (desc_rec.d_id == 0) break;
912 DEBUG_INDEX(("[%i] Item(%#x) = [d_id = %#x, desc_id = %#x, list_id = %#x, parent_id = %#x]\n", 934 DEBUG_INDEX(("[%i] Item(%#x) = [d_id = %#llx, desc_id = %#llx, list_id = %#llx, parent_id = %#x]\n",
913 depth, x, desc_rec.d_id, desc_rec.desc_id, desc_rec.list_id, desc_rec.parent_id)); 935 depth, x, desc_rec.d_id, desc_rec.desc_id, desc_rec.list_id, desc_rec.parent_id));
914 if ((desc_rec.d_id >= end_val) || (desc_rec.d_id < old)) { 936 if ((desc_rec.d_id >= end_val) || (desc_rec.d_id < old)) {
915 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n")); 937 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n"));
916 DEBUG_HEXDUMPC(buf, DESC_BLOCK_SIZE, 16); 938 DEBUG_HEXDUMPC(buf, DESC_BLOCK_SIZE, 16);
917 if (buf) free(buf); 939 if (buf) free(buf);
918 DEBUG_RET(); 940 DEBUG_RET();
919 return -1; 941 return -1;
920 } 942 }
921 old = desc_rec.d_id; 943 old = desc_rec.d_id;
922 if (x == 1) { // first entry 944 if (x == (int32_t)1) { // first entry
923 if (start_val && (desc_rec.d_id != start_val)) { 945 if (start_val && (desc_rec.d_id != start_val)) {
924 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n")); 946 DEBUG_WARN(("This item isn't right. Must be corruption, or I got it wrong!\n"));
925 if (buf) free(buf); 947 if (buf) free(buf);
926 DEBUG_RET(); 948 DEBUG_RET();
927 return -1; 949 return -1;
928 } 950 }
929 } 951 }
930 // When duplicates found, just update the info.... perhaps this is correct functionality 952 // When duplicates found, just update the info.... perhaps this is correct functionality
931 DEBUG_INDEX(("Searching for existing record\n")); 953 DEBUG_INDEX(("Searching for existing record\n"));
932 if (desc_rec.d_id <= *high_id && (d_ptr = _pst_getDptr(pf, desc_rec.d_id))) { 954 if (desc_rec.d_id <= *high_id && (d_ptr = pst_getDptr(pf, desc_rec.d_id))) {
933 DEBUG_INDEX(("Updating Existing Values\n")); 955 DEBUG_INDEX(("Updating Existing Values\n"));
934 d_ptr->list_index = _pst_getID(pf, desc_rec.list_id); 956 d_ptr->list_index = pst_getID(pf, desc_rec.list_id);
935 d_ptr->desc = _pst_getID(pf, desc_rec.desc_id); 957 d_ptr->desc = pst_getID(pf, desc_rec.desc_id);
936 DEBUG_INDEX(("\tdesc = %#x\tlist_index=%#x\n", 958 DEBUG_INDEX(("\tdesc = %#llx\tlist_index=%#llx\n",
937 (d_ptr->desc==NULL?0:d_ptr->desc->id), 959 (d_ptr->desc==NULL?0LL:d_ptr->desc->id),
938 (d_ptr->list_index==NULL?0:d_ptr->list_index->id))); 960 (d_ptr->list_index==NULL?0LL:d_ptr->list_index->id)));
939 if (d_ptr->parent && desc_rec.parent_id != d_ptr->parent->id) { 961 if (d_ptr->parent && desc_rec.parent_id != d_ptr->parent->id) {
940 DEBUG_INDEX(("WARNING -- Parent of record has changed. Moving it\n")); 962 DEBUG_INDEX(("WARNING -- Parent of record has changed. Moving it\n"));
941 //hmmm, we must move the record. 963 //hmmm, we must move the record.
942 // first we must remove from current location 964 // first we must remove from current location
943 // change previous record to point next to our next 965 // change previous record to point next to our next
971 *high_id = desc_rec.d_id; 993 *high_id = desc_rec.d_id;
972 } 994 }
973 DEBUG_INDEX(("New Record\n")); 995 DEBUG_INDEX(("New Record\n"));
974 d_ptr = (pst_desc_ll*) xmalloc(sizeof(pst_desc_ll)); 996 d_ptr = (pst_desc_ll*) xmalloc(sizeof(pst_desc_ll));
975 d_ptr->id = desc_rec.d_id; 997 d_ptr->id = desc_rec.d_id;
976 d_ptr->list_index = _pst_getID(pf, desc_rec.list_id); 998 d_ptr->list_index = pst_getID(pf, desc_rec.list_id);
977 d_ptr->desc = _pst_getID(pf, desc_rec.desc_id); 999 d_ptr->desc = pst_getID(pf, desc_rec.desc_id);
978 d_ptr->prev = NULL; 1000 d_ptr->prev = NULL;
979 d_ptr->next = NULL; 1001 d_ptr->next = NULL;
980 d_ptr->parent = NULL; 1002 d_ptr->parent = NULL;
981 d_ptr->child = NULL; 1003 d_ptr->child = NULL;
982 d_ptr->child_tail = NULL; 1004 d_ptr->child_tail = NULL;
987 // check here to see if d_ptr is the parent of any of the items in the lost / found list 1009 // check here to see if d_ptr is the parent of any of the items in the lost / found list
988 lostfound_ptr = lostfound_head; 1010 lostfound_ptr = lostfound_head;
989 lostfound_shd = NULL; 1011 lostfound_shd = NULL;
990 while (lostfound_ptr) { 1012 while (lostfound_ptr) {
991 if (lostfound_ptr->parent == d_ptr->id) { 1013 if (lostfound_ptr->parent == d_ptr->id) {
992 DEBUG_INDEX(("Found a child (%#x) of the current record. Joining to main structure.\n", lostfound_ptr->ptr->id)); 1014 DEBUG_INDEX(("Found a child (%#llx) of the current record. Joining to main structure.\n", lostfound_ptr->ptr->id));
993 parent = d_ptr; 1015 parent = d_ptr;
994 d_ptr = lostfound_ptr->ptr; 1016 d_ptr = lostfound_ptr->ptr;
995 parent->no_child++; 1017 parent->no_child++;
996 d_ptr->parent = parent; 1018 d_ptr->parent = parent;
997 if (parent->child_tail) parent->child_tail->next = d_ptr; 1019 if (parent->child_tail) parent->child_tail->next = d_ptr;
1018 DEBUG_RET(); 1040 DEBUG_RET();
1019 return -1; 1041 return -1;
1020 } 1042 }
1021 x = 0; 1043 x = 0;
1022 while (x < item_count) { 1044 while (x < item_count) {
1023 bptr += _pst_decode_table(&table, bptr); 1045 bptr += pst_decode_table(pf, &table, bptr);
1024 x++; 1046 x++;
1025 if (table.start == 0) break; 1047 if (table.start == 0) break;
1026 if (x < item_count) { 1048 if (x < item_count) {
1027 _pst_decode_table(&table2, bptr); 1049 (void)pst_decode_table(pf, &table2, bptr);
1028 } 1050 }
1029 else { 1051 else {
1030 table2.start = end_val; 1052 table2.start = end_val;
1031 } 1053 }
1032 DEBUG_INDEX(("[%i] %i Descriptor Table [start id = %#x, u1 = %#x, offset = %#x, end id = %#x]\n", 1054 DEBUG_INDEX(("[%i] %i Descriptor Table [start id = %#llx, u1 = %#llx, offset = %#llx, end id = %#llx]\n",
1033 depth, x, table.start, table.u1, table.offset, table2.start)); 1055 depth, x, table.start, table.u1, table.offset, table2.start));
1034 if ((table.start >= end_val) || (table.start < old)) { 1056 if ((table.start >= end_val) || (table.start < old)) {
1035 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n")); 1057 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n"));
1036 if (buf) free(buf); 1058 if (buf) free(buf);
1037 DEBUG_RET(); 1059 DEBUG_RET();
1038 return -1; 1060 return -1;
1039 } 1061 }
1040 old = table.start; 1062 old = table.start;
1041 if (x == 1) { // first entry 1063 if (x == (int32_t)1) { // first entry
1042 if (start_val != -1 && table.start != start_val) { 1064 if (start_val && (table.start != start_val)) {
1043 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n")); 1065 DEBUG_WARN(("This table isn't right. Must be corruption, or I got it wrong!\n"));
1044 if (buf) free(buf); 1066 if (buf) free(buf);
1045 DEBUG_RET(); 1067 DEBUG_RET();
1046 return -1; 1068 return -1;
1047 } 1069 }
1048 } 1070 }
1049 _pst_build_desc_ptr(pf, table.offset, depth+1, table.u1, high_id, table.start, table2.start); 1071 (void)pst_build_desc_ptr(pf, table.offset, depth+1, table.u1, high_id, table.start, table2.start);
1050 } 1072 }
1051 } 1073 }
1052 if (depth == 0) { 1074 if (depth == 0) {
1053 // free the quick cache 1075 // free the quick cache
1054 while (cache_head) { 1076 while (cache_head) {
1057 cache_head = cache_ptr; 1079 cache_head = cache_ptr;
1058 } 1080 }
1059 // free the lost and found 1081 // free the lost and found
1060 while (lostfound_head) { 1082 while (lostfound_head) {
1061 lostfound_ptr = lostfound_head->next; 1083 lostfound_ptr = lostfound_head->next;
1062 WARN(("unused lost/found item with parent %d))", lostfound_head->parent)); 1084 WARN(("unused lost/found item with parent %lld))", lostfound_head->parent));
1063 free(lostfound_head); 1085 free(lostfound_head);
1064 lostfound_head = lostfound_ptr; 1086 lostfound_head = lostfound_ptr;
1065 } 1087 }
1066 } 1088 }
1067 if (buf) free(buf); 1089 if (buf) free(buf);
1068 DEBUG_RET(); 1090 DEBUG_RET();
1069 return 0; 1091 return 0;
1070 } 1092 }
1071 1093
1072 1094
1073 pst_item* _pst_parse_item(pst_file *pf, pst_desc_ll *d_ptr) { 1095 pst_item* pst_parse_item(pst_file *pf, pst_desc_ll *d_ptr) {
1074 pst_num_array * list; 1096 pst_num_array * list;
1075 pst_index2_ll *id2_head = NULL; 1097 pst_index2_ll *id2_head = NULL;
1076 pst_index_ll *id_ptr = NULL; 1098 pst_index_ll *id_ptr = NULL;
1077 pst_item *item = NULL; 1099 pst_item *item = NULL;
1078 pst_item_attach *attach = NULL; 1100 pst_item_attach *attach = NULL;
1079 int x; 1101 int32_t x;
1080 DEBUG_ENT("_pst_parse_item"); 1102 DEBUG_ENT("pst_parse_item");
1081 if (!d_ptr) { 1103 if (!d_ptr) {
1082 DEBUG_WARN(("you cannot pass me a NULL! I don't want it!\n")); 1104 DEBUG_WARN(("you cannot pass me a NULL! I don't want it!\n"));
1083 DEBUG_RET(); 1105 DEBUG_RET();
1084 return NULL; 1106 return NULL;
1085 } 1107 }
1089 DEBUG_RET(); 1111 DEBUG_RET();
1090 return NULL; 1112 return NULL;
1091 } 1113 }
1092 1114
1093 if (d_ptr->list_index) { 1115 if (d_ptr->list_index) {
1094 id2_head = _pst_build_id2(pf, d_ptr->list_index, NULL); 1116 id2_head = pst_build_id2(pf, d_ptr->list_index, NULL);
1095 _pst_printID2ptr(id2_head); 1117 (void)pst_printID2ptr(id2_head);
1096 } else { 1118 } else {
1097 DEBUG_WARN(("Have not been able to fetch any id2 values for this item. Brace yourself!\n")); 1119 DEBUG_WARN(("Have not been able to fetch any id2 values for this item. Brace yourself!\n"));
1098 } 1120 }
1099 1121
1100 list = _pst_parse_block(pf, d_ptr->desc->id, id2_head); 1122 list = pst_parse_block(pf, d_ptr->desc->id, id2_head);
1101 if (!list) { 1123 if (!list) {
1102 DEBUG_WARN(("_pst_parse_block() returned an error for d_ptr->desc->id [%#x]\n", d_ptr->desc->id)); 1124 DEBUG_WARN(("pst_parse_block() returned an error for d_ptr->desc->id [%#llx]\n", d_ptr->desc->id));
1103 if (id2_head) _pst_free_id2(id2_head); 1125 if (id2_head) pst_free_id2(id2_head);
1104 DEBUG_RET(); 1126 DEBUG_RET();
1105 return NULL; 1127 return NULL;
1106 } 1128 }
1107 1129
1108 item = (pst_item*) xmalloc(sizeof(pst_item)); 1130 item = (pst_item*) xmalloc(sizeof(pst_item));
1109 memset(item, 0, sizeof(pst_item)); 1131 memset(item, 0, sizeof(pst_item));
1110 1132
1111 if (_pst_process(list, item, NULL)) { 1133 if (pst_process(list, item, NULL)) {
1112 DEBUG_WARN(("_pst_process() returned non-zero value. That is an error\n")); 1134 DEBUG_WARN(("pst_process() returned non-zero value. That is an error\n"));
1113 if (item) _pst_freeItem(item); 1135 if (item) pst_freeItem(item);
1114 if (list) _pst_free_list(list); 1136 if (list) pst_free_list(list);
1115 if (id2_head) _pst_free_id2(id2_head); 1137 if (id2_head) pst_free_id2(id2_head);
1116 DEBUG_RET(); 1138 DEBUG_RET();
1117 return NULL; 1139 return NULL;
1118 } 1140 }
1119 if (list) _pst_free_list(list); 1141 if (list) pst_free_list(list);
1120 list = NULL; //_pst_process will free the items in the list 1142 list = NULL; //pst_process will free the items in the list
1121 1143
1122 if ((id_ptr = _pst_getID2(id2_head, 0x671))) { 1144 if ((id_ptr = pst_getID2(id2_head, (uint64_t)0x671))) {
1123 // attachments exist - so we will process them 1145 // attachments exist - so we will process them
1124 while (item->attach) { 1146 while (item->attach) {
1125 attach = item->attach->next; 1147 attach = item->attach->next;
1126 free(item->attach); 1148 free(item->attach);
1127 item->attach = attach; 1149 item->attach = attach;
1128 } 1150 }
1129 1151
1130 DEBUG_EMAIL(("ATTACHMENT processing attachment\n")); 1152 DEBUG_EMAIL(("ATTACHMENT processing attachment\n"));
1131 if ((list = _pst_parse_block(pf, id_ptr->id, id2_head)) == NULL) { 1153 if ((list = pst_parse_block(pf, id_ptr->id, id2_head)) == NULL) {
1132 DEBUG_WARN(("ERROR error processing main attachment record\n")); 1154 DEBUG_WARN(("ERROR error processing main attachment record\n"));
1133 if (item) _pst_freeItem(item); 1155 if (item) pst_freeItem(item);
1134 if (id2_head) _pst_free_id2(id2_head); 1156 if (id2_head) pst_free_id2(id2_head);
1135 DEBUG_RET(); 1157 DEBUG_RET();
1136 return NULL; 1158 return NULL;
1137 } 1159 }
1138 else { 1160 else {
1139 x = 0; 1161 x = 0;
1143 attach->next = item->attach; 1165 attach->next = item->attach;
1144 item->attach = attach; 1166 item->attach = attach;
1145 x++; 1167 x++;
1146 } 1168 }
1147 1169
1148 if (_pst_process(list, item, item->attach)) { 1170 if (pst_process(list, item, item->attach)) {
1149 DEBUG_WARN(("ERROR _pst_process() failed with attachments\n")); 1171 DEBUG_WARN(("ERROR pst_process() failed with attachments\n"));
1150 if (item) _pst_freeItem(item); 1172 if (item) pst_freeItem(item);
1151 if (list) _pst_free_list(list); 1173 if (list) pst_free_list(list);
1152 if (id2_head) _pst_free_id2(id2_head); 1174 if (id2_head) pst_free_id2(id2_head);
1153 DEBUG_RET(); 1175 DEBUG_RET();
1154 return NULL; 1176 return NULL;
1155 } 1177 }
1156 if (list) _pst_free_list(list); 1178 if (list) pst_free_list(list);
1157 list = NULL; 1179 list = NULL;
1158 1180
1159 // now we will have initial information of each attachment stored in item->attach... 1181 // now we will have initial information of each attachment stored in item->attach...
1160 // we must now read the secondary record for each based on the id2 val associated with 1182 // we must now read the secondary record for each based on the id2 val associated with
1161 // each attachment 1183 // each attachment
1162 attach = item->attach; 1184 attach = item->attach;
1163 while (attach) { 1185 while (attach) {
1164 if ((id_ptr = _pst_getID2(id2_head, attach->id2_val))) { 1186 if ((id_ptr = pst_getID2(id2_head, attach->id2_val))) {
1165 // id_ptr is a record describing the attachment 1187 // id_ptr is a record describing the attachment
1166 // we pass NULL instead of id2_head cause we don't want it to 1188 // we pass NULL instead of id2_head cause we don't want it to
1167 // load all the extra stuff here. 1189 // load all the extra stuff here.
1168 if ((list = _pst_parse_block(pf, id_ptr->id, NULL)) == NULL) { 1190 if ((list = pst_parse_block(pf, id_ptr->id, NULL)) == NULL) {
1169 DEBUG_WARN(("ERROR error processing an attachment record\n")); 1191 DEBUG_WARN(("ERROR error processing an attachment record\n"));
1170 attach = attach->next; 1192 attach = attach->next;
1171 continue; 1193 continue;
1172 } 1194 }
1173 if (_pst_process(list, item, attach)) { 1195 if (pst_process(list, item, attach)) {
1174 DEBUG_WARN(("ERROR _pst_process() failed with an attachment\n")); 1196 DEBUG_WARN(("ERROR pst_process() failed with an attachment\n"));
1175 if (list) _pst_free_list(list); 1197 if (list) pst_free_list(list);
1176 list = NULL; 1198 list = NULL;
1177 attach = attach->next; 1199 attach = attach->next;
1178 continue; 1200 continue;
1179 } 1201 }
1180 if (list) _pst_free_list(list); 1202 if (list) pst_free_list(list);
1181 list = NULL; 1203 list = NULL;
1182 id_ptr = _pst_getID2(id2_head, attach->id2_val); 1204 id_ptr = pst_getID2(id2_head, attach->id2_val);
1183 if (id_ptr) { 1205 if (id_ptr) {
1184 // id2_val has been updated to the ID2 value of the datablock containing the 1206 // id2_val has been updated to the ID2 value of the datablock containing the
1185 // attachment data 1207 // attachment data
1186 attach->id_val = id_ptr->id; 1208 attach->id_val = id_ptr->id;
1187 } else { 1209 } else {
1188 DEBUG_WARN(("have not located the correct value for the attachment [%#x]\n", attach->id2_val)); 1210 DEBUG_WARN(("have not located the correct value for the attachment [%#llx]\n", attach->id2_val));
1189 } 1211 }
1190 } else { 1212 } else {
1191 DEBUG_WARN(("ERROR cannot locate id2 value %#x\n", attach->id2_val)); 1213 DEBUG_WARN(("ERROR cannot locate id2 value %#llx\n", attach->id2_val));
1192 } 1214 }
1193 attach = attach->next; 1215 attach = attach->next;
1194 } 1216 }
1195 } 1217 }
1196 } 1218 }
1197 1219
1198 _pst_free_id2(id2_head); 1220 if (id2_head) pst_free_id2(id2_head);
1199 id2_head = NULL;
1200 DEBUG_RET(); 1221 DEBUG_RET();
1201 return item; 1222 return item;
1202 } 1223 }
1203 1224
1204 1225
1205 void freeall(unsigned char *buf, pst_block_offset_pointer *p1, 1226 static void freeall(unsigned char *buf, pst_block_offset_pointer *p1,
1206 pst_block_offset_pointer *p2, 1227 pst_block_offset_pointer *p2,
1207 pst_block_offset_pointer *p3, 1228 pst_block_offset_pointer *p3,
1208 pst_block_offset_pointer *p4, 1229 pst_block_offset_pointer *p4,
1209 pst_block_offset_pointer *p5, 1230 pst_block_offset_pointer *p5,
1210 pst_block_offset_pointer *p6, 1231 pst_block_offset_pointer *p6,
1211 pst_block_offset_pointer *p7) { 1232 pst_block_offset_pointer *p7);
1233 static void freeall(unsigned char *buf, pst_block_offset_pointer *p1,
1234 pst_block_offset_pointer *p2,
1235 pst_block_offset_pointer *p3,
1236 pst_block_offset_pointer *p4,
1237 pst_block_offset_pointer *p5,
1238 pst_block_offset_pointer *p6,
1239 pst_block_offset_pointer *p7) {
1212 if (buf) free(buf); 1240 if (buf) free(buf);
1213 if (p1->needfree) free(p1->from); 1241 if (p1->needfree) free(p1->from);
1214 if (p2->needfree) free(p2->from); 1242 if (p2->needfree) free(p2->from);
1215 if (p3->needfree) free(p3->from); 1243 if (p3->needfree) free(p3->from);
1216 if (p4->needfree) free(p4->from); 1244 if (p4->needfree) free(p4->from);
1218 if (p6->needfree) free(p6->from); 1246 if (p6->needfree) free(p6->from);
1219 if (p7->needfree) free(p7->from); 1247 if (p7->needfree) free(p7->from);
1220 } 1248 }
1221 1249
1222 1250
1223 pst_num_array * _pst_parse_block(pst_file *pf, uint32_t block_id, pst_index2_ll *i2_head) { 1251 pst_num_array * pst_parse_block(pst_file *pf, uint64_t block_id, pst_index2_ll *i2_head) {
1224 unsigned char *buf = NULL; 1252 unsigned char *buf = NULL;
1225 pst_num_array *na_ptr = NULL, *na_head = NULL; 1253 pst_num_array *na_ptr = NULL, *na_head = NULL;
1226 pst_block_offset_pointer block_offset1; 1254 pst_block_offset_pointer block_offset1;
1227 pst_block_offset_pointer block_offset2; 1255 pst_block_offset_pointer block_offset2;
1228 pst_block_offset_pointer block_offset3; 1256 pst_block_offset_pointer block_offset3;
1229 pst_block_offset_pointer block_offset4; 1257 pst_block_offset_pointer block_offset4;
1230 pst_block_offset_pointer block_offset5; 1258 pst_block_offset_pointer block_offset5;
1231 pst_block_offset_pointer block_offset6; 1259 pst_block_offset_pointer block_offset6;
1232 pst_block_offset_pointer block_offset7; 1260 pst_block_offset_pointer block_offset7;
1233 uint32_t size; 1261 int32_t x;
1234 uint32_t x; 1262 int num_recs;
1235 uint32_t num_recs; 1263 int count_rec;
1236 uint32_t count_rec; 1264 int32_t num_list;
1237 uint32_t num_list; 1265 int32_t cur_list;
1238 uint32_t cur_list; 1266 int32_t block_type;
1239 uint32_t block_type;
1240 uint32_t rec_size = 0; 1267 uint32_t rec_size = 0;
1241 uint32_t ind_ptr; 1268 uint32_t ind_ptr;
1242 unsigned char* list_start; 1269 unsigned char* list_start;
1243 unsigned char* t_ptr;
1244 unsigned char* fr_ptr; 1270 unsigned char* fr_ptr;
1245 unsigned char* to_ptr; 1271 unsigned char* to_ptr;
1246 unsigned char* ind2_end; 1272 unsigned char* ind2_end = NULL;
1247 unsigned char* ind2_ptr = NULL; 1273 unsigned char* ind2_ptr = NULL;
1248 size_t read_size=0; 1274 size_t read_size=0;
1249 pst_x_attrib_ll *mapptr; 1275 pst_x_attrib_ll *mapptr;
1250 1276
1251 struct { 1277 struct {
1283 struct _type_d_rec { 1309 struct _type_d_rec {
1284 uint32_t id; 1310 uint32_t id;
1285 uint32_t u1; 1311 uint32_t u1;
1286 } * type_d_rec; 1312 } * type_d_rec;
1287 1313
1288 DEBUG_ENT("_pst_parse_block"); 1314 DEBUG_ENT("pst_parse_block");
1289 if ((read_size = _pst_ff_getIDblock_dec(pf, block_id, &buf)) == 0) { 1315 if ((read_size = pst_ff_getIDblock_dec(pf, block_id, &buf)) == 0) {
1290 WARN(("Error reading block id %#x\n", block_id)); 1316 WARN(("Error reading block id %#llx\n", block_id));
1291 if (buf) free (buf); 1317 if (buf) free (buf);
1292 DEBUG_RET(); 1318 DEBUG_RET();
1293 return NULL; 1319 return NULL;
1294 } 1320 }
1295 1321
1307 LE32_CPU(block_hdr.offset); 1333 LE32_CPU(block_hdr.offset);
1308 DEBUG_EMAIL(("block header (index_offset=%#hx, type=%#hx, offset=%#hx\n", block_hdr.index_offset, block_hdr.type, block_hdr.offset)); 1334 DEBUG_EMAIL(("block header (index_offset=%#hx, type=%#hx, offset=%#hx\n", block_hdr.index_offset, block_hdr.type, block_hdr.offset));
1309 1335
1310 ind_ptr = block_hdr.index_offset; 1336 ind_ptr = block_hdr.index_offset;
1311 1337
1312 if (block_hdr.type == 0xBCEC) { //type 1 1338 if (block_hdr.type == (uint16_t)0xBCEC) { //type 1
1313 block_type = 1; 1339 block_type = 1;
1314 1340
1315 if (_pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, block_hdr.offset, &block_offset1)) { 1341 if (pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, block_hdr.offset, &block_offset1)) {
1316 DEBUG_WARN(("internal error (bc.b5 offset %#x) in reading block id %#x\n", block_hdr.offset, block_id)); 1342 DEBUG_WARN(("internal error (bc.b5 offset %#x) in reading block id %#x\n", block_hdr.offset, block_id));
1317 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1343 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1318 DEBUG_RET(); 1344 DEBUG_RET();
1319 return NULL; 1345 return NULL;
1320 } 1346 }
1322 LE16_CPU(table_rec.type); 1348 LE16_CPU(table_rec.type);
1323 LE16_CPU(table_rec.ref_type); 1349 LE16_CPU(table_rec.ref_type);
1324 LE32_CPU(table_rec.value); 1350 LE32_CPU(table_rec.value);
1325 DEBUG_EMAIL(("table_rec (type=%#hx, ref_type=%#hx, value=%#x)\n", table_rec.type, table_rec.ref_type, table_rec.value)); 1351 DEBUG_EMAIL(("table_rec (type=%#hx, ref_type=%#hx, value=%#x)\n", table_rec.type, table_rec.ref_type, table_rec.value));
1326 1352
1327 if (table_rec.type != 0x02B5) { 1353 if (table_rec.type != (uint16_t)0x02B5) {
1328 WARN(("Unknown second block constant - %#X for id %#x\n", table_rec.type, block_id)); 1354 WARN(("Unknown second block constant - %#hx for id %#llx\n", table_rec.type, block_id));
1329 DEBUG_HEXDUMPC(buf, sizeof(table_rec), 0x10); 1355 DEBUG_HEXDUMPC(buf, sizeof(table_rec), 0x10);
1330 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1356 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1331 DEBUG_RET(); 1357 DEBUG_RET();
1332 return NULL; 1358 return NULL;
1333 } 1359 }
1334 1360
1335 if (_pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, table_rec.value, &block_offset2)) { 1361 if (pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, table_rec.value, &block_offset2)) {
1336 DEBUG_WARN(("internal error (bc.b5.desc offset) in reading block id %#x\n", table_rec.value, block_id)); 1362 DEBUG_WARN(("internal error (bc.b5.desc offset) in reading block id %#x\n", table_rec.value, block_id));
1337 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1363 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1338 DEBUG_RET(); 1364 DEBUG_RET();
1339 return NULL; 1365 return NULL;
1340 } 1366 }
1341 list_start = block_offset2.from; 1367 list_start = block_offset2.from;
1342 to_ptr = block_offset2.to; 1368 to_ptr = block_offset2.to;
1343 num_list = (to_ptr - list_start)/sizeof(table_rec); 1369 num_list = (to_ptr - list_start)/sizeof(table_rec);
1344 num_recs = 1; // only going to be one object in these blocks 1370 num_recs = 1; // only going to be one object in these blocks
1345 } 1371 }
1346 else if (block_hdr.type == 0x7CEC) { //type 2 1372 else if (block_hdr.type == (uint16_t)0x7CEC) { //type 2
1347 block_type = 2; 1373 block_type = 2;
1348 1374
1349 if (_pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, block_hdr.offset, &block_offset3)) { 1375 if (pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, block_hdr.offset, &block_offset3)) {
1350 DEBUG_WARN(("internal error (7c.7c offset %#x) in reading block id %#x\n", block_hdr.offset, block_id)); 1376 DEBUG_WARN(("internal error (7c.7c offset %#x) in reading block id %#x\n", block_hdr.offset, block_id));
1351 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1377 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1352 DEBUG_RET(); 1378 DEBUG_RET();
1353 return NULL; 1379 return NULL;
1354 } 1380 }
1374 } 1400 }
1375 1401
1376 rec_size = seven_c_blk.rec_size; 1402 rec_size = seven_c_blk.rec_size;
1377 num_list = seven_c_blk.item_count; 1403 num_list = seven_c_blk.item_count;
1378 1404
1379 if (_pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, seven_c_blk.b_five_offset, &block_offset4)) { 1405 if (pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, seven_c_blk.b_five_offset, &block_offset4)) {
1380 DEBUG_WARN(("internal error (7c.b5 offset %#x) in reading block id %#x\n", seven_c_blk.b_five_offset, block_id)); 1406 DEBUG_WARN(("internal error (7c.b5 offset %#x) in reading block id %#x\n", seven_c_blk.b_five_offset, block_id));
1381 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1407 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1382 DEBUG_RET(); 1408 DEBUG_RET();
1383 return NULL; 1409 return NULL;
1384 } 1410 }
1385 memcpy(&table_rec, block_offset4.from, sizeof(table_rec)); 1411 memcpy(&table_rec, block_offset4.from, sizeof(table_rec));
1386 LE16_CPU(table_rec.type); 1412 LE16_CPU(table_rec.type);
1387 LE16_CPU(table_rec.ref_type); 1413 LE16_CPU(table_rec.ref_type);
1388 LE32_CPU(table_rec.value); 1414 LE32_CPU(table_rec.value);
1389 1415
1390 if (table_rec.type != 0x04B5) { // different constant than a type 1 record 1416 if (table_rec.type != (uint16_t)0x04B5) { // different constant than a type 1 record
1391 WARN(("Unknown second block constant - %#X for id %#x\n", table_rec.type, block_id)); 1417 WARN(("Unknown second block constant - %#hx for id %#llx\n", table_rec.type, block_id));
1392 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1418 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1393 DEBUG_RET(); 1419 DEBUG_RET();
1394 return NULL; 1420 return NULL;
1395 } 1421 }
1396 1422
1397 if (_pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, table_rec.value, &block_offset5)) { 1423 if (pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, table_rec.value, &block_offset5)) {
1398 DEBUG_WARN(("internal error (7c.5b.desc offset %#x) in reading block id %#x\n", table_rec.value, block_id)); 1424 DEBUG_WARN(("internal error (7c.5b.desc offset %#x) in reading block id %#llx\n", table_rec.value, block_id));
1399 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1425 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1400 DEBUG_RET(); 1426 DEBUG_RET();
1401 return NULL; 1427 return NULL;
1402 } 1428 }
1403 num_recs = (block_offset5.to - block_offset5.from) / 6; // this will give the number of records in this block 1429 num_recs = (block_offset5.to - block_offset5.from) / 6; // this will give the number of records in this block
1404 1430
1405 if (_pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, seven_c_blk.ind2_offset, &block_offset6)) { 1431 if (pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, seven_c_blk.ind2_offset, &block_offset6)) {
1406 DEBUG_WARN(("internal error (7c.ind2 offset %#x) in reading block id %#x\n", seven_c_blk.ind2_offset, block_id)); 1432 DEBUG_WARN(("internal error (7c.ind2 offset %#x) in reading block id %#x\n", seven_c_blk.ind2_offset, block_id));
1407 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1433 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1408 DEBUG_RET(); 1434 DEBUG_RET();
1409 return NULL; 1435 return NULL;
1410 } 1436 }
1411 ind2_ptr = block_offset6.from; 1437 ind2_ptr = block_offset6.from;
1412 ind2_end = block_offset6.to; 1438 ind2_end = block_offset6.to;
1413 } 1439 }
1414 else if (block_hdr.index_offset == 0x0101) { //type 2 1440 else if (block_hdr.index_offset == (uint16_t)0x0101) { //type 3
1415 unsigned char *buf2 = NULL; 1441 unsigned char *buf2 = NULL;
1416 int n = block_hdr.type; // count 1442 uint16_t n = block_hdr.type; // count
1417 int m = sizeof(table3_rec); 1443 size_t m = sizeof(table3_rec);
1418 int i; 1444 uint16_t i;
1419 block_type = 3; 1445 block_type = 3;
1420 for (i=0; i<n; i++) { 1446 for (i=0; i<n; i++) {
1421 memcpy(&table3_rec, buf+8+i*m, m); 1447 memcpy(&table3_rec, buf+8+i*m, m);
1422 LE32_CPU(table3_rec.id); 1448 LE32_CPU(table3_rec.id);
1423 _pst_ff_getIDblock_dec(pf, table3_rec.id, &buf2); 1449 (void)pst_ff_getIDblock_dec(pf, table3_rec.id, &buf2);
1424 if (buf2) free(buf2); 1450 if (buf2) free(buf2);
1425 buf2 = NULL; 1451 buf2 = NULL;
1426 } 1452 }
1427 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1453 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1428 DEBUG_RET(); 1454 DEBUG_RET();
1429 return NULL; 1455 return NULL;
1430 } else { 1456 } else {
1431 WARN(("ERROR: Unknown block constant - %#X for id %#x\n", block_hdr.type, block_id)); 1457 WARN(("ERROR: Unknown block constant - %#hx for id %#llx\n", block_hdr.type, block_id));
1432 DEBUG_HEXDUMPC(buf, read_size,0x10); 1458 DEBUG_HEXDUMPC(buf, read_size,0x10);
1433 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1459 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1434 DEBUG_RET(); 1460 DEBUG_RET();
1435 return NULL; 1461 return NULL;
1436 } 1462 }
1439 for (count_rec=0; count_rec<num_recs; count_rec++) { 1465 for (count_rec=0; count_rec<num_recs; count_rec++) {
1440 na_ptr = (pst_num_array*) xmalloc(sizeof(pst_num_array)); 1466 na_ptr = (pst_num_array*) xmalloc(sizeof(pst_num_array));
1441 memset(na_ptr, 0, sizeof(pst_num_array)); 1467 memset(na_ptr, 0, sizeof(pst_num_array));
1442 na_ptr->next = na_head; 1468 na_ptr->next = na_head;
1443 na_head = na_ptr; 1469 na_head = na_ptr;
1444 // allocate an array of count num_recs to contain sizeof(struct_pst_num_item) 1470 // allocate an array of count num_recs to contain sizeof(structpst_num_item)
1445 na_ptr->items = (struct _pst_num_item**) xmalloc(sizeof(struct _pst_num_item)*num_list); 1471 na_ptr->items = (struct pst_num_item**) xmalloc(sizeof(struct pst_num_item)*num_list);
1446 na_ptr->count_item = num_list; 1472 na_ptr->count_item = num_list;
1447 na_ptr->orig_count = num_list; 1473 na_ptr->orig_count = num_list;
1448 na_ptr->count_array = num_recs; // each record will have a record of the total number of records 1474 na_ptr->count_array = num_recs; // each record will have a record of the total number of records
1449 for (x=0; x<num_list; x++) na_ptr->items[x] = NULL; 1475 for (x=0; x<num_list; x++) na_ptr->items[x] = NULL;
1450 x = 0; 1476 x = 0;
1452 DEBUG_EMAIL(("going to read %i (%#x) items\n", na_ptr->count_item, na_ptr->count_item)); 1478 DEBUG_EMAIL(("going to read %i (%#x) items\n", na_ptr->count_item, na_ptr->count_item));
1453 1479
1454 fr_ptr = list_start; // initialize fr_ptr to the start of the list. 1480 fr_ptr = list_start; // initialize fr_ptr to the start of the list.
1455 for (cur_list=0; cur_list<num_list; cur_list++) { //we will increase fr_ptr as we progress through index 1481 for (cur_list=0; cur_list<num_list; cur_list++) { //we will increase fr_ptr as we progress through index
1456 unsigned char* value_pointer = NULL; // needed for block type 2 with values larger than 4 bytes 1482 unsigned char* value_pointer = NULL; // needed for block type 2 with values larger than 4 bytes
1457 int value_size = 0; 1483 size_t value_size = 0;
1458 if (block_type == 1) { 1484 if (block_type == (int32_t)1) {
1459 memcpy(&table_rec, fr_ptr, sizeof(table_rec)); 1485 memcpy(&table_rec, fr_ptr, sizeof(table_rec));
1460 LE16_CPU(table_rec.type); 1486 LE16_CPU(table_rec.type);
1461 LE16_CPU(table_rec.ref_type); 1487 LE16_CPU(table_rec.ref_type);
1462 //LE32_CPU(table_rec.value); // done later, some may be order invariant 1488 //LE32_CPU(table_rec.value); // done later, some may be order invariant
1463 fr_ptr += sizeof(table_rec); 1489 fr_ptr += sizeof(table_rec);
1464 } else if (block_type == 2) { 1490 } else if (block_type == (int32_t)2) {
1465 // we will copy the table2_rec values into a table_rec record so that we can keep the rest of the code 1491 // we will copy the table2_rec values into a table_rec record so that we can keep the rest of the code
1466 memcpy(&table2_rec, fr_ptr, sizeof(table2_rec)); 1492 memcpy(&table2_rec, fr_ptr, sizeof(table2_rec));
1467 LE16_CPU(table2_rec.ref_type); 1493 LE16_CPU(table2_rec.ref_type);
1468 LE16_CPU(table2_rec.type); 1494 LE16_CPU(table2_rec.type);
1469 LE16_CPU(table2_rec.ind2_off); 1495 LE16_CPU(table2_rec.ind2_off);
1471 // table_rec and table2_rec are arranged differently, so assign the values across 1497 // table_rec and table2_rec are arranged differently, so assign the values across
1472 table_rec.type = table2_rec.type; 1498 table_rec.type = table2_rec.type;
1473 table_rec.ref_type = table2_rec.ref_type; 1499 table_rec.ref_type = table2_rec.ref_type;
1474 table_rec.value = 0; 1500 table_rec.value = 0;
1475 if ((ind2_end - ind2_ptr) >= (table2_rec.ind2_off + table2_rec.size)) { 1501 if ((ind2_end - ind2_ptr) >= (table2_rec.ind2_off + table2_rec.size)) {
1476 int n = table2_rec.size; 1502 size_t n = table2_rec.size;
1477 int m = sizeof(table_rec.value); 1503 size_t m = sizeof(table_rec.value);
1478 if (n <= m) { 1504 if (n <= m) {
1479 memcpy(&table_rec.value, ind2_ptr + table2_rec.ind2_off, n); 1505 memcpy(&table_rec.value, ind2_ptr + table2_rec.ind2_off, n);
1480 } 1506 }
1481 else { 1507 else {
1482 value_pointer = ind2_ptr + table2_rec.ind2_off; 1508 value_pointer = ind2_ptr + table2_rec.ind2_off;
1490 } 1516 }
1491 fr_ptr += sizeof(table2_rec); 1517 fr_ptr += sizeof(table2_rec);
1492 } else { 1518 } else {
1493 WARN(("Missing code for block_type %i\n", block_type)); 1519 WARN(("Missing code for block_type %i\n", block_type));
1494 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1520 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1495 if (na_head) _pst_free_list(na_head); 1521 if (na_head) pst_free_list(na_head);
1496 DEBUG_RET(); 1522 DEBUG_RET();
1497 return NULL; 1523 return NULL;
1498 } 1524 }
1499 DEBUG_EMAIL(("reading block %i (type=%#x, ref_type=%#x, value=%#x)\n", 1525 DEBUG_EMAIL(("reading block %i (type=%#x, ref_type=%#x, value=%#x)\n",
1500 x, table_rec.type, table_rec.ref_type, table_rec.value)); 1526 x, table_rec.type, table_rec.ref_type, table_rec.value));
1501 1527
1502 if (!na_ptr->items[x]) { 1528 if (!na_ptr->items[x]) {
1503 na_ptr->items[x] = (struct _pst_num_item*) xmalloc(sizeof(struct _pst_num_item)); 1529 na_ptr->items[x] = (struct pst_num_item*) xmalloc(sizeof(struct pst_num_item));
1504 } 1530 }
1505 memset(na_ptr->items[x], 0, sizeof(struct _pst_num_item)); //init it 1531 memset(na_ptr->items[x], 0, sizeof(struct pst_num_item)); //init it
1506 1532
1507 // check here to see if the id of the attribute is a mapped one 1533 // check here to see if the id of the attribute is a mapped one
1508 mapptr = pf->x_head; 1534 mapptr = pf->x_head;
1509 while (mapptr && (mapptr->map < table_rec.type)) mapptr = mapptr->next; 1535 while (mapptr && (mapptr->map < table_rec.type)) mapptr = mapptr->next;
1510 if (mapptr && (mapptr->map == table_rec.type)) { 1536 if (mapptr && (mapptr->map == table_rec.type)) {
1511 if (mapptr->mytype == PST_MAP_ATTRIB) { 1537 if (mapptr->mytype == PST_MAP_ATTRIB) {
1512 na_ptr->items[x]->id = *((int*)mapptr->data); 1538 na_ptr->items[x]->id = *((uint32_t*)mapptr->data);
1513 DEBUG_EMAIL(("Mapped attrib %#x to %#x\n", table_rec.type, na_ptr->items[x]->id)); 1539 DEBUG_EMAIL(("Mapped attrib %#x to %#x\n", table_rec.type, na_ptr->items[x]->id));
1514 } else if (mapptr->mytype == PST_MAP_HEADER) { 1540 } else if (mapptr->mytype == PST_MAP_HEADER) {
1515 DEBUG_EMAIL(("Internet Header mapping found %#x\n", table_rec.type)); 1541 DEBUG_EMAIL(("Internet Header mapping found %#x\n", table_rec.type));
1516 na_ptr->items[x]->id = PST_ATTRIB_HEADER; 1542 na_ptr->items[x]->id = (uint32_t)PST_ATTRIB_HEADER;
1517 na_ptr->items[x]->extra = mapptr->data; 1543 na_ptr->items[x]->extra = mapptr->data;
1544 }
1545 else {
1546 // nothing, should be assertion failure here
1518 } 1547 }
1519 } else { 1548 } else {
1520 na_ptr->items[x]->id = table_rec.type; 1549 na_ptr->items[x]->id = table_rec.type;
1521 } 1550 }
1522 na_ptr->items[x]->type = 0; // checked later before it is set 1551 na_ptr->items[x]->type = 0; // checked later before it is set
1540 0x1014 - Array of 64bit values 1569 0x1014 - Array of 64bit values
1541 0x101E - Array of Strings 1570 0x101E - Array of Strings
1542 0x1102 - Array of Binary data 1571 0x1102 - Array of Binary data
1543 */ 1572 */
1544 1573
1545 if (table_rec.ref_type == 0x0002 || 1574 if (table_rec.ref_type == (uint16_t)0x0002 ||
1546 table_rec.ref_type == 0x0003 || 1575 table_rec.ref_type == (uint16_t)0x0003 ||
1547 table_rec.ref_type == 0x000b) { 1576 table_rec.ref_type == (uint16_t)0x000b) {
1548 //contains 32 bits of data 1577 //contains 32 bits of data
1549 na_ptr->items[x]->size = sizeof(int32_t); 1578 na_ptr->items[x]->size = sizeof(int32_t);
1550 na_ptr->items[x]->type = table_rec.ref_type; 1579 na_ptr->items[x]->type = table_rec.ref_type;
1551 na_ptr->items[x]->data = xmalloc(sizeof(int32_t)); 1580 na_ptr->items[x]->data = xmalloc(sizeof(int32_t));
1552 memcpy(na_ptr->items[x]->data, &(table_rec.value), sizeof(int32_t)); 1581 memcpy(na_ptr->items[x]->data, &(table_rec.value), sizeof(int32_t));
1553 1582
1554 } else if (table_rec.ref_type == 0x0005 || 1583 } else if (table_rec.ref_type == (uint16_t)0x0005 ||
1555 table_rec.ref_type == 0x000d || 1584 table_rec.ref_type == (uint16_t)0x000d ||
1556 table_rec.ref_type == 0x0014 || 1585 table_rec.ref_type == (uint16_t)0x0014 ||
1557 table_rec.ref_type == 0x001e || 1586 table_rec.ref_type == (uint16_t)0x001e ||
1558 table_rec.ref_type == 0x001f || 1587 table_rec.ref_type == (uint16_t)0x001f ||
1559 table_rec.ref_type == 0x0040 || 1588 table_rec.ref_type == (uint16_t)0x0040 ||
1560 table_rec.ref_type == 0x0048 || 1589 table_rec.ref_type == (uint16_t)0x0048 ||
1561 table_rec.ref_type == 0x0102 || 1590 table_rec.ref_type == (uint16_t)0x0102 ||
1562 table_rec.ref_type == 0x1003 || 1591 table_rec.ref_type == (uint16_t)0x1003 ||
1563 table_rec.ref_type == 0x1014 || 1592 table_rec.ref_type == (uint16_t)0x1014 ||
1564 table_rec.ref_type == 0x101e || 1593 table_rec.ref_type == (uint16_t)0x101e ||
1565 table_rec.ref_type == 0x1102) { 1594 table_rec.ref_type == (uint16_t)0x1102) {
1566 //contains index reference to data 1595 //contains index reference to data
1567 LE32_CPU(table_rec.value); 1596 LE32_CPU(table_rec.value);
1568 if (value_pointer) { 1597 if (value_pointer) {
1569 // in a type 2 block, with a value that is more than 4 bytes 1598 // in a type 2 block, with a value that is more than 4 bytes
1570 // directly stored in this block. 1599 // directly stored in this block.
1571 na_ptr->items[x]->size = value_size; 1600 na_ptr->items[x]->size = value_size;
1572 na_ptr->items[x]->type = table_rec.ref_type; 1601 na_ptr->items[x]->type = table_rec.ref_type;
1573 na_ptr->items[x]->data = xmalloc(value_size); 1602 na_ptr->items[x]->data = xmalloc(value_size);
1574 memcpy(na_ptr->items[x]->data, value_pointer, value_size); 1603 memcpy(na_ptr->items[x]->data, value_pointer, value_size);
1575 } 1604 }
1576 else if (_pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, table_rec.value, &block_offset7)) { 1605 else if (pst_getBlockOffsetPointer(pf, i2_head, buf, read_size, ind_ptr, table_rec.value, &block_offset7)) {
1577 if ((table_rec.value & 0xf) == 0xf) { 1606 if ((table_rec.value & 0xf) == (uint32_t)0xf) {
1578 DEBUG_WARN(("failed to get block offset for table_rec.value of %#x to be read later.\n", table_rec.value)); 1607 DEBUG_WARN(("failed to get block offset for table_rec.value of %#x to be read later.\n", table_rec.value));
1579 na_ptr->items[x]->size = 0; 1608 na_ptr->items[x]->size = 0;
1580 na_ptr->items[x]->data = NULL; 1609 na_ptr->items[x]->data = NULL;
1581 na_ptr->items[x]->type = table_rec.value; 1610 na_ptr->items[x]->type = table_rec.value;
1582 } 1611 }
1594 na_ptr->items[x]->type = table_rec.ref_type; 1623 na_ptr->items[x]->type = table_rec.ref_type;
1595 na_ptr->items[x]->data = xmalloc(value_size+1); 1624 na_ptr->items[x]->data = xmalloc(value_size+1);
1596 memcpy(na_ptr->items[x]->data, block_offset7.from, value_size); 1625 memcpy(na_ptr->items[x]->data, block_offset7.from, value_size);
1597 na_ptr->items[x]->data[value_size] = '\0'; // it might be a string, null terminate it. 1626 na_ptr->items[x]->data[value_size] = '\0'; // it might be a string, null terminate it.
1598 } 1627 }
1599 if (table_rec.ref_type == 0xd) { 1628 if (table_rec.ref_type == (uint16_t)0xd) {
1600 // there is still more to do for the type of 0xD embedded objects 1629 // there is still more to do for the type of 0xD embedded objects
1601 type_d_rec = (struct _type_d_rec*) na_ptr->items[x]->data; 1630 type_d_rec = (struct _type_d_rec*) na_ptr->items[x]->data;
1602 LE32_CPU(type_d_rec->id); 1631 LE32_CPU(type_d_rec->id);
1603 na_ptr->items[x]->size = _pst_ff_getID2block(pf, type_d_rec->id, i2_head, &(na_ptr->items[x]->data)); 1632 na_ptr->items[x]->size = pst_ff_getID2block(pf, type_d_rec->id, i2_head, &(na_ptr->items[x]->data));
1604 if (!na_ptr->items[x]->size){ 1633 if (!na_ptr->items[x]->size){
1605 DEBUG_WARN(("not able to read the ID2 data. Setting to be read later. %#x\n", type_d_rec->id)); 1634 DEBUG_WARN(("not able to read the ID2 data. Setting to be read later. %#x\n", type_d_rec->id));
1606 na_ptr->items[x]->type = type_d_rec->id; // fetch before freeing data, alias pointer 1635 na_ptr->items[x]->type = type_d_rec->id; // fetch before freeing data, alias pointer
1607 free(na_ptr->items[x]->data); 1636 free(na_ptr->items[x]->data);
1608 na_ptr->items[x]->data = NULL; 1637 na_ptr->items[x]->data = NULL;
1609 } 1638 }
1610 } 1639 }
1611 if (table_rec.ref_type == 0x1f) { 1640 if (table_rec.ref_type == (uint16_t)0x1f) {
1612 // there is more to do for the type 0x1f unicode strings 1641 // there is more to do for the type 0x1f unicode strings
1613 VBUF_STATIC(strbuf, 1024); 1642 static vbuf *strbuf = NULL;
1614 VBUF_STATIC(unibuf, 1024); 1643 static vbuf *unibuf = NULL;
1644 if (!strbuf) strbuf=vballoc((size_t)1024);
1645 if (!unibuf) unibuf=vballoc((size_t)1024);
1646
1647 // splint barfed on the following lines
1648 //VBUF_STATIC(strbuf, 1024);
1649 //VBUF_STATIC(unibuf, 1024);
1650
1615 //need UTF-16 zero-termination 1651 //need UTF-16 zero-termination
1616 vbset(strbuf, na_ptr->items[x]->data, na_ptr->items[x]->size); 1652 vbset(strbuf, na_ptr->items[x]->data, na_ptr->items[x]->size);
1617 vbappend(strbuf, "\0\0", 2); 1653 vbappend(strbuf, "\0\0", (size_t)2);
1618 DEBUG_INDEX(("Iconv in:\n")); 1654 DEBUG_INDEX(("Iconv in:\n"));
1619 DEBUG_HEXDUMPC(strbuf->b, strbuf->dlen, 0x10); 1655 DEBUG_HEXDUMPC(strbuf->b, strbuf->dlen, 0x10);
1620 vb_utf16to8(unibuf, strbuf->b, strbuf->dlen); 1656 (void)vb_utf16to8(unibuf, strbuf->b, strbuf->dlen);
1621 free(na_ptr->items[x]->data); 1657 free(na_ptr->items[x]->data);
1622 na_ptr->items[x]->size = unibuf->dlen; 1658 na_ptr->items[x]->size = unibuf->dlen;
1623 na_ptr->items[x]->data = xmalloc(unibuf->dlen); 1659 na_ptr->items[x]->data = xmalloc(unibuf->dlen);
1624 memcpy(na_ptr->items[x]->data, unibuf->b, unibuf->dlen); 1660 memcpy(na_ptr->items[x]->data, unibuf->b, unibuf->dlen);
1625 DEBUG_INDEX(("Iconv out:\n")); 1661 DEBUG_INDEX(("Iconv out:\n"));
1626 DEBUG_HEXDUMPC(na_ptr->items[x]->data, na_ptr->items[x]->size, 0x10); 1662 DEBUG_HEXDUMPC(na_ptr->items[x]->data, na_ptr->items[x]->size, 0x10);
1627 } 1663 }
1628 if (na_ptr->items[x]->type == 0) na_ptr->items[x]->type = table_rec.ref_type; 1664 if (na_ptr->items[x]->type == 0) na_ptr->items[x]->type = table_rec.ref_type;
1629 } else { 1665 } else {
1630 WARN(("ERROR Unknown ref_type %#x\n", table_rec.ref_type)); 1666 WARN(("ERROR Unknown ref_type %#hx\n", table_rec.ref_type));
1631 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7); 1667 freeall(buf, &block_offset1, &block_offset2, &block_offset3, &block_offset4, &block_offset5, &block_offset6, &block_offset7);
1632 if (na_head) _pst_free_list(na_head); 1668 if (na_head) pst_free_list(na_head);
1633 DEBUG_RET(); 1669 DEBUG_RET();
1634 return NULL; 1670 return NULL;
1635 } 1671 }
1636 x++; 1672 x++;
1637 } 1673 }
1653 #define MALLOC_APPOINTMENT(x) { if (!x->appointment) { x->appointment = (pst_item_appointment*) xmalloc(sizeof(pst_item_appointment)); memset(x->appointment, 0, sizeof(pst_item_appointment) );} } 1689 #define MALLOC_APPOINTMENT(x) { if (!x->appointment) { x->appointment = (pst_item_appointment*) xmalloc(sizeof(pst_item_appointment)); memset(x->appointment, 0, sizeof(pst_item_appointment) );} }
1654 // malloc space and copy the current item's data null terminated 1690 // malloc space and copy the current item's data null terminated
1655 #define LIST_COPY(targ, type) { \ 1691 #define LIST_COPY(targ, type) { \
1656 targ = type realloc(targ, list->items[x]->size+1); \ 1692 targ = type realloc(targ, list->items[x]->size+1); \
1657 memcpy(targ, list->items[x]->data, list->items[x]->size); \ 1693 memcpy(targ, list->items[x]->data, list->items[x]->size); \
1658 memset(((char*)targ)+list->items[x]->size, 0, 1); \ 1694 memset(((char*)targ)+list->items[x]->size, 0, (size_t)1); \
1659 } 1695 }
1660 // malloc space and copy the current item's data and size 1696 // malloc space and copy the current item's data and size
1661 #define LIST_COPY_SIZE(targ, type, mysize) { \ 1697 #define LIST_COPY_SIZE(targ, type, mysize) { \
1662 mysize = list->items[x]->size; \ 1698 mysize = list->items[x]->size; \
1663 targ = type realloc(targ, mysize); \ 1699 targ = type realloc(targ, mysize); \
1680 next=0;\ 1716 next=0;\
1681 }\ 1717 }\
1682 } 1718 }
1683 1719
1684 1720
1685 int32_t _pst_process(pst_num_array *list , pst_item *item, pst_item_attach *attach) { 1721 int pst_process(pst_num_array *list , pst_item *item, pst_item_attach *attach) {
1686 int32_t x, t; 1722 int32_t x, t;
1687 int32_t next = 0; 1723 int32_t next = 0;
1688 pst_item_extra_field *ef; 1724 pst_item_extra_field *ef;
1689 1725
1690 DEBUG_ENT("_pst_process"); 1726 DEBUG_ENT("pst_process");
1691 if (!item) { 1727 if (!item) {
1692 DEBUG_EMAIL(("item cannot be NULL.\n")); 1728 DEBUG_EMAIL(("item cannot be NULL.\n"));
1693 DEBUG_RET(); 1729 DEBUG_RET();
1694 return -1; 1730 return -1;
1695 } 1731 }
2023 break; 2059 break;
2024 case 0x007D: // PR_TRANSPORT_MESSAGE_HEADERS Internet Header 2060 case 0x007D: // PR_TRANSPORT_MESSAGE_HEADERS Internet Header
2025 DEBUG_EMAIL(("Internet Header - ")); 2061 DEBUG_EMAIL(("Internet Header - "));
2026 MALLOC_EMAIL(item); 2062 MALLOC_EMAIL(item);
2027 LIST_COPY(item->email->header, (char*)); 2063 LIST_COPY(item->email->header, (char*));
2028 //DEBUG_EMAIL(("%s\n", item->email->header)); 2064 DEBUG_EMAIL(("%s\n", item->email->header));
2029 DEBUG_EMAIL(("NOT PRINTED\n")); 2065 DEBUG_EMAIL(("NOT PRINTED\n"));
2030 break; 2066 break;
2031 case 0x0C17: // PR_REPLY_REQUESTED 2067 case 0x0C17: // PR_REPLY_REQUESTED
2032 DEBUG_EMAIL(("Reply Requested - ")); 2068 DEBUG_EMAIL(("Reply Requested - "));
2033 MALLOC_EMAIL(item); 2069 MALLOC_EMAIL(item);
2362 DEBUG_EMAIL(("Binary Data [Size %i] - ", list->items[x]->size)); 2398 DEBUG_EMAIL(("Binary Data [Size %i] - ", list->items[x]->size));
2363 NULL_CHECK(attach); 2399 NULL_CHECK(attach);
2364 MOVE_NEXT(attach); 2400 MOVE_NEXT(attach);
2365 if (!list->items[x]->data) { //special case 2401 if (!list->items[x]->data) { //special case
2366 attach->id2_val = list->items[x]->type; 2402 attach->id2_val = list->items[x]->type;
2367 DEBUG_EMAIL(("Seen a Reference. The data hasn't been loaded yet. [%#x][%#x]\n", 2403 DEBUG_EMAIL(("Seen a Reference. The data hasn't been loaded yet. [%#llx][%#x]\n",
2368 attach->id2_val, list->items[x]->type)); 2404 attach->id2_val, list->items[x]->type));
2369 } else { 2405 } else {
2370 LIST_COPY(attach->data, (char*)); 2406 LIST_COPY(attach->data, (char*));
2371 attach->size = list->items[x]->size; 2407 attach->size = list->items[x]->size;
2372 DEBUG_EMAIL(("NOT PRINTED\n")); 2408 DEBUG_EMAIL(("NOT PRINTED\n"));
2930 item->record_key_size=16; 2966 item->record_key_size=16;
2931 DEBUG_EMAIL_HEXPRINT((char*)item->record_key, 16); 2967 DEBUG_EMAIL_HEXPRINT((char*)item->record_key, 16);
2932 break; 2968 break;
2933 case 0x67F2: // ID2 value of the attachments proper record 2969 case 0x67F2: // ID2 value of the attachments proper record
2934 DEBUG_EMAIL(("Attachment ID2 value - ")); 2970 DEBUG_EMAIL(("Attachment ID2 value - "));
2935 if (attach){ 2971 if (attach) {
2972 uint32_t tempid;
2936 MOVE_NEXT(attach); 2973 MOVE_NEXT(attach);
2937 memcpy(&(attach->id2_val), list->items[x]->data, sizeof(attach->id2_val)); 2974 memcpy(&(tempid), list->items[x]->data, sizeof(tempid));
2938 LE32_CPU(attach->id2_val); 2975 LE32_CPU(tempid);
2939 DEBUG_EMAIL(("%#x\n", attach->id2_val)); 2976 attach->id2_val = tempid;
2977 DEBUG_EMAIL(("%#llx\n", attach->id2_val));
2940 } else { 2978 } else {
2941 DEBUG_EMAIL(("NOT AN ATTACHMENT: %#x\n", list->items[x]->id)); 2979 DEBUG_EMAIL(("NOT AN ATTACHMENT: %#x\n", list->items[x]->id));
2942 } 2980 }
2943 break; 2981 break;
2944 case 0x67FF: // Extra Property Identifier (Password CheckSum) 2982 case 0x67FF: // Extra Property Identifier (Password CheckSum)
3280 DEBUG_RET(); 3318 DEBUG_RET();
3281 return 0; 3319 return 0;
3282 } 3320 }
3283 3321
3284 3322
3285 int32_t _pst_free_list(pst_num_array *list) { 3323 void pst_free_list(pst_num_array *list) {
3286 pst_num_array *l; 3324 pst_num_array *l;
3287 DEBUG_ENT("_pst_free_list"); 3325 DEBUG_ENT("pst_free_list");
3288 while (list) { 3326 while (list) {
3289 if (list->items) { 3327 if (list->items) {
3290 int32_t x; 3328 int32_t x;
3291 for (x=0; x < list->orig_count; x++) { 3329 for (x=0; x < list->orig_count; x++) {
3292 if (list->items[x]) { 3330 if (list->items[x]) {
3299 l = list; 3337 l = list;
3300 list = list->next; 3338 list = list->next;
3301 free (l); 3339 free (l);
3302 } 3340 }
3303 DEBUG_RET(); 3341 DEBUG_RET();
3304 return 1; 3342 }
3305 } 3343
3306 3344
3307 3345 void pst_free_id2(pst_index2_ll * head) {
3308 int32_t _pst_free_id2(pst_index2_ll * head) {
3309 pst_index2_ll *t; 3346 pst_index2_ll *t;
3310 DEBUG_ENT("_pst_free_id2"); 3347 DEBUG_ENT("pst_free_id2");
3311 while (head) { 3348 while (head) {
3312 t = head->next; 3349 t = head->next;
3313 free (head); 3350 free (head);
3314 head = t; 3351 head = t;
3315 } 3352 }
3316 DEBUG_RET(); 3353 DEBUG_RET();
3317 return 1; 3354 }
3318 } 3355
3319 3356
3320 3357 void pst_free_id (pst_index_ll *head) {
3321 int32_t _pst_free_id (pst_index_ll *head) {
3322 pst_index_ll *t; 3358 pst_index_ll *t;
3323 DEBUG_ENT("_pst_free_id"); 3359 DEBUG_ENT("pst_free_id");
3324 while (head) { 3360 while (head) {
3325 t = head->next; 3361 t = head->next;
3326 free(head); 3362 free(head);
3327 head = t; 3363 head = t;
3328 } 3364 }
3329 DEBUG_RET(); 3365 DEBUG_RET();
3330 return 1; 3366 }
3331 } 3367
3332 3368
3333 3369 void pst_free_desc (pst_desc_ll *head) {
3334 int32_t _pst_free_desc (pst_desc_ll *head) {
3335 pst_desc_ll *t; 3370 pst_desc_ll *t;
3336 DEBUG_ENT("_pst_free_desc"); 3371 DEBUG_ENT("pst_free_desc");
3337 while (head) { 3372 while (head) {
3338 while (head->child) { 3373 while (head->child) {
3339 head = head->child; 3374 head = head->child;
3340 } 3375 }
3341 3376
3350 else DIE(("head is NULL")); 3385 else DIE(("head is NULL"));
3351 3386
3352 head = t; 3387 head = t;
3353 } 3388 }
3354 DEBUG_RET(); 3389 DEBUG_RET();
3355 return 1; 3390 }
3356 } 3391
3357 3392
3358 3393 void pst_free_xattrib(pst_x_attrib_ll *x) {
3359 int32_t _pst_free_xattrib(pst_x_attrib_ll *x) {
3360 pst_x_attrib_ll *t; 3394 pst_x_attrib_ll *t;
3361 DEBUG_ENT("_pst_free_xattrib"); 3395 DEBUG_ENT("pst_free_xattrib");
3362 while (x) { 3396 while (x) {
3363 if (x->data) free(x->data); 3397 if (x->data) free(x->data);
3364 t = x->next; 3398 t = x->next;
3365 free(x); 3399 free(x);
3366 x = t; 3400 x = t;
3367 } 3401 }
3368 DEBUG_RET(); 3402 DEBUG_RET();
3369 return 1; 3403 }
3370 } 3404
3371 3405
3372 3406 pst_index2_ll * pst_build_id2(pst_file *pf, pst_index_ll* list, pst_index2_ll* head_ptr) {
3373 pst_index2_ll * _pst_build_id2(pst_file *pf, pst_index_ll* list, pst_index2_ll* head_ptr) {
3374 pst_block_header block_head; 3407 pst_block_header block_head;
3375 pst_index2_ll *head = NULL, *tail = NULL; 3408 pst_index2_ll *head = NULL, *tail = NULL;
3376 int32_t x = 0, b_ptr = 0; 3409 uint16_t x = 0;
3410 char *b_ptr = NULL;
3377 char *buf = NULL; 3411 char *buf = NULL;
3378 pst_id2_assoc id2_rec; 3412 pst_id2_assoc id2_rec;
3379 pst_index_ll *i_ptr = NULL; 3413 pst_index_ll *i_ptr = NULL;
3380 pst_index2_ll *i2_ptr = NULL; 3414 pst_index2_ll *i2_ptr = NULL;
3381 DEBUG_ENT("_pst_build_id2"); 3415 DEBUG_ENT("pst_build_id2");
3382 3416
3383 if (head_ptr) { 3417 if (head_ptr) {
3384 head = head_ptr; 3418 head = head_ptr;
3385 while (head_ptr) head_ptr = (tail = head_ptr)->next; 3419 while (head_ptr) head_ptr = (tail = head_ptr)->next;
3386 } 3420 }
3387 if (_pst_read_block_size(pf, list->offset, list->size, &buf, PST_NO_ENC, 0) < list->size) { 3421 if (pst_read_block_size(pf, list->offset, list->size, &buf, PST_NO_ENC, 0) < list->size) {
3388 //an error occured in block read 3422 //an error occured in block read
3389 WARN(("block read error occured. offset = %#llx, size = %#llx\n", list->offset, list->size)); 3423 WARN(("block read error occured. offset = %#llx, size = %#llx\n", list->offset, list->size));
3390 if (buf) free(buf); 3424 if (buf) free(buf);
3391 DEBUG_RET(); 3425 DEBUG_RET();
3392 return NULL; 3426 return NULL;
3395 3429
3396 memcpy(&block_head, buf, sizeof(block_head)); 3430 memcpy(&block_head, buf, sizeof(block_head));
3397 LE16_CPU(block_head.type); 3431 LE16_CPU(block_head.type);
3398 LE16_CPU(block_head.count); 3432 LE16_CPU(block_head.count);
3399 3433
3400 if (block_head.type != 0x0002) { // some sort of constant? 3434 if (block_head.type != (uint16_t)0x0002) { // some sort of constant?
3401 WARN(("Unknown constant [%#x] at start of id2 values [offset %#llx].\n", block_head.type, list->offset)); 3435 WARN(("Unknown constant [%#x] at start of id2 values [offset %#llx].\n", block_head.type, list->offset));
3402 if (buf) free(buf); 3436 if (buf) free(buf);
3403 DEBUG_RET(); 3437 DEBUG_RET();
3404 return NULL; 3438 return NULL;
3405 } 3439 }
3406 3440
3407 DEBUG_INDEX(("ID %#x is likely to be a description record. Count is %i (offset %#x)\n", 3441 DEBUG_INDEX(("ID %#llx is likely to be a description record. Count is %i (offset %#llx)\n",
3408 list->id, block_head.count, list->offset)); 3442 list->id, block_head.count, list->offset));
3409 x = 0; 3443 x = 0;
3410 b_ptr = 0x04; 3444 b_ptr = buf + ((pf->do_read64) ? 0x08 : 0x04);
3411 while (x < block_head.count) { 3445 while (x < block_head.count) {
3412 memcpy(&id2_rec, &(buf[b_ptr]), sizeof(id2_rec)); 3446 b_ptr += pst_decode_assoc(pf, &id2_rec, b_ptr);
3413 LE32_CPU(id2_rec.id2); 3447 // memcpy(&id2_rec, &(buf[b_ptr]), sizeof(id2_rec));
3414 LE32_CPU(id2_rec.id); 3448 // LE32_CPU(id2_rec.id2);
3415 LE32_CPU(id2_rec.table2); 3449 // LE32_CPU(id2_rec.id);
3416 3450 // LE32_CPU(id2_rec.table2);
3417 b_ptr += sizeof(id2_rec); 3451 //
3418 DEBUG_INDEX(("\tid2 = %#x, id = %#x, table2 = %#x\n", id2_rec.id2, id2_rec.id, id2_rec.table2)); 3452 // b_ptr += sizeof(id2_rec);
3419 if ((i_ptr = _pst_getID(pf, id2_rec.id)) == NULL) { 3453 DEBUG_INDEX(("\tid2 = %#llx, id = %#llx, table2 = %#llx\n", id2_rec.id2, id2_rec.id, id2_rec.table2));
3420 DEBUG_WARN(("\t\t%#x - Not Found\n", id2_rec.id)); 3454 if ((i_ptr = pst_getID(pf, id2_rec.id)) == NULL) {
3455 DEBUG_WARN(("\t\t%#llx - Not Found\n", id2_rec.id));
3421 } else { 3456 } else {
3422 DEBUG_INDEX(("\t\t%#x - Offset %#x, u1 %#x, Size %i(%#x)\n", i_ptr->id, i_ptr->offset, i_ptr->u1, i_ptr->size, i_ptr->size)); 3457 DEBUG_INDEX(("\t\t%#llx - Offset %#llx, u1 %#llx, Size %lli(%#llx)\n", i_ptr->id, i_ptr->offset, i_ptr->u1, i_ptr->size, i_ptr->size));
3423 // add it to the linked list 3458 // add it to the linked list
3424 i2_ptr = (pst_index2_ll*) xmalloc(sizeof(pst_index2_ll)); 3459 i2_ptr = (pst_index2_ll*) xmalloc(sizeof(pst_index2_ll));
3425 i2_ptr->id2 = id2_rec.id2; 3460 i2_ptr->id2 = id2_rec.id2;
3426 i2_ptr->id = i_ptr; 3461 i2_ptr->id = i_ptr;
3427 i2_ptr->next = NULL; 3462 i2_ptr->next = NULL;
3428 if (!head) head = i2_ptr; 3463 if (!head) head = i2_ptr;
3429 if (tail) tail->next = i2_ptr; 3464 if (tail) tail->next = i2_ptr;
3430 tail = i2_ptr; 3465 tail = i2_ptr;
3431 if (id2_rec.table2 != 0) { 3466 if (id2_rec.table2 != 0) {
3432 if ((i_ptr = _pst_getID(pf, id2_rec.table2)) == NULL) { 3467 if ((i_ptr = pst_getID(pf, id2_rec.table2)) == NULL) {
3433 DEBUG_WARN(("\tTable2 [%#x] not found\n", id2_rec.table2)); 3468 DEBUG_WARN(("\tTable2 [%#x] not found\n", id2_rec.table2));
3434 } 3469 }
3435 else { 3470 else {
3436 DEBUG_INDEX(("\tGoing deeper for table2 [%#x]\n", id2_rec.table2)); 3471 DEBUG_INDEX(("\tGoing deeper for table2 [%#x]\n", id2_rec.table2));
3437 if ((i2_ptr = _pst_build_id2(pf, i_ptr, head))) { 3472 if ((i2_ptr = pst_build_id2(pf, i_ptr, head))) {
3438 // DEBUG_INDEX(("_pst_build_id2(): \t\tAdding new list onto end of current\n")); 3473 // DEBUG_INDEX(("pst_build_id2(): \t\tAdding new list onto end of current\n"));
3439 // if (!head) 3474 // if (!head)
3440 // head = i2_ptr; 3475 // head = i2_ptr;
3441 // if (tail) 3476 // if (tail)
3442 // tail->next = i2_ptr; 3477 // tail->next = i2_ptr;
3443 // while (i2_ptr->next) 3478 // while (i2_ptr->next)
3461 3496
3462 3497
3463 // This version of free does NULL check first 3498 // This version of free does NULL check first
3464 #define SAFE_FREE(x) {if (x) free(x);} 3499 #define SAFE_FREE(x) {if (x) free(x);}
3465 3500
3466 void _pst_freeItem(pst_item *item) { 3501 void pst_freeItem(pst_item *item) {
3467 pst_item_attach *t; 3502 pst_item_attach *t;
3468 pst_item_extra_field *et; 3503 pst_item_extra_field *et;
3469 3504
3470 DEBUG_ENT("_pst_freeItem"); 3505 DEBUG_ENT("pst_freeItem");
3471 if (item) { 3506 if (item) {
3472 if (item->email) { 3507 if (item->email) {
3473 SAFE_FREE(item->email->arrival_date); 3508 SAFE_FREE(item->email->arrival_date);
3474 SAFE_FREE(item->email->body); 3509 SAFE_FREE(item->email->body);
3475 SAFE_FREE(item->email->cc_address); 3510 SAFE_FREE(item->email->cc_address);
3655 /** 3690 /**
3656 * The offset might be zero, in which case we have no data, so return a pair of null pointers. 3691 * The offset might be zero, in which case we have no data, so return a pair of null pointers.
3657 * Or, the offset might end in 0xf, so it is an id2 pointer, in which case we read the id2 block. 3692 * Or, the offset might end in 0xf, so it is an id2 pointer, in which case we read the id2 block.
3658 * Otherwise, the offset>>4 is an index into the table of offsets in the buffer. 3693 * Otherwise, the offset>>4 is an index into the table of offsets in the buffer.
3659 */ 3694 */
3660 int32_t _pst_getBlockOffsetPointer(pst_file *pf, pst_index2_ll *i2_head, unsigned char *buf, int32_t read_size, int32_t i_offset, int32_t offset, pst_block_offset_pointer *p) { 3695 int pst_getBlockOffsetPointer(pst_file *pf, pst_index2_ll *i2_head, unsigned char *buf, size_t read_size, uint32_t i_offset, uint32_t offset, pst_block_offset_pointer *p) {
3661 int32_t size; 3696 size_t size;
3662 pst_block_offset block_offset; 3697 pst_block_offset block_offset;
3663 DEBUG_ENT("_pst_getBlockOffsetPointer"); 3698 DEBUG_ENT("pst_getBlockOffsetPointer");
3664 if (p->needfree) free(p->from); 3699 if (p->needfree) free(p->from);
3665 p->from = NULL; 3700 p->from = NULL;
3666 p->needfree = 0; 3701 p->needfree = 0;
3667 if (!offset) { 3702 if (!offset) {
3668 p->from = p->to = NULL; 3703 p->from = p->to = NULL;
3669 } 3704 }
3670 else if ((offset & 0xf) == 0xf) { 3705 else if ((offset & 0xf) == (uint32_t)0xf) {
3671 DEBUG_WARN(("Found id2 %#x value. Will follow it\n", offset)); 3706 DEBUG_WARN(("Found id2 %#x value. Will follow it\n", offset));
3672 size = _pst_ff_getID2block(pf, offset, i2_head, &(p->from)); 3707 size = pst_ff_getID2block(pf, offset, i2_head, &(p->from));
3673 if (size) { 3708 if (size) {
3674 p->to = p->from + size; 3709 p->to = p->from + size;
3675 p->needfree = 1; 3710 p->needfree = 1;
3676 } 3711 }
3677 else { 3712 else {
3678 p->from = p->to = NULL; 3713 p->from = p->to = NULL;
3679 } 3714 }
3680 } 3715 }
3681 else if (_pst_getBlockOffset(buf, read_size, i_offset, offset, &block_offset)) { 3716 else if (pst_getBlockOffset(buf, read_size, i_offset, offset, &block_offset)) {
3682 p->from = p->to = NULL; 3717 p->from = p->to = NULL;
3683 } 3718 }
3684 else { 3719 else {
3685 p->from = buf + block_offset.from; 3720 p->from = buf + block_offset.from;
3686 p->to = buf + block_offset.to; 3721 p->to = buf + block_offset.to;
3688 DEBUG_RET(); 3723 DEBUG_RET();
3689 return (p->from) ? 0 : 1; 3724 return (p->from) ? 0 : 1;
3690 } 3725 }
3691 3726
3692 3727
3693 int32_t _pst_getBlockOffset(unsigned char *buf, int32_t read_size, int32_t i_offset, int32_t offset, pst_block_offset *p) { 3728 int pst_getBlockOffset(unsigned char *buf, size_t read_size, uint32_t i_offset, uint32_t offset, pst_block_offset *p) {
3694 int32_t low = offset & 0xf; 3729 uint32_t low = offset & 0xf;
3695 int32_t of1 = offset >> 4; 3730 uint32_t of1 = offset >> 4;
3696 DEBUG_ENT("_pst_getBlockOffset"); 3731 DEBUG_ENT("pst_getBlockOffset");
3697 if (!p || !buf || !i_offset || low || (i_offset+2+of1+sizeof(*p) > read_size)) { 3732 if (!p || !buf || !i_offset || low || (i_offset+2+of1+sizeof(*p) > read_size)) {
3698 DEBUG_WARN(("p is NULL or buf is NULL or offset is 0 or offset has low bits or beyond read size (%p, %p, %#x, %i, %i)\n", p, buf, offset, read_size, i_offset)); 3733 DEBUG_WARN(("p is NULL or buf is NULL or offset is 0 or offset has low bits or beyond read size (%p, %p, %#x, %i, %i)\n", p, buf, offset, read_size, i_offset));
3699 DEBUG_RET(); 3734 DEBUG_RET();
3700 return -1; 3735 return -1;
3701 } 3736 }
3711 DEBUG_RET(); 3746 DEBUG_RET();
3712 return 0; 3747 return 0;
3713 } 3748 }
3714 3749
3715 3750
3716 pst_index_ll* _pst_getID(pst_file* pf, uint64_t id) { 3751 pst_index_ll* pst_getID(pst_file* pf, uint64_t id) {
3717 pst_index_ll *ptr = NULL; 3752 pst_index_ll *ptr = NULL;
3718 DEBUG_ENT("_pst_getID"); 3753 DEBUG_ENT("pst_getID");
3719 if (id == 0) { 3754 if (id == 0) {
3720 DEBUG_RET(); 3755 DEBUG_RET();
3721 return NULL; 3756 return NULL;
3722 } 3757 }
3723 3758
3724 //if (id & 1) DEBUG_INDEX(("have odd id bit %#x\n", id)); 3759 //if (id & 1) DEBUG_INDEX(("have odd id bit %#llx\n", id));
3725 //if (id & 2) DEBUG_INDEX(("have two id bit %#x\n", id)); 3760 //if (id & 2) DEBUG_INDEX(("have two id bit %#llx\n", id));
3726 id -= (id & 1); 3761 id -= (id & 1);
3727 3762
3728 DEBUG_INDEX(("Trying to find %#llx\n", id)); 3763 DEBUG_INDEX(("Trying to find %#llx\n", id));
3729 if (!ptr) ptr = pf->i_head; 3764 if (!ptr) ptr = pf->i_head;
3730 while (ptr && (ptr->id != id)) { 3765 while (ptr && (ptr->id != id)) {
3731 ptr = ptr->next; 3766 ptr = ptr->next;
3732 } 3767 }
3733 if (ptr) {DEBUG_INDEX(("Found Value %#x\n", id)); } 3768 if (ptr) {DEBUG_INDEX(("Found Value %#llx\n", id)); }
3734 else {DEBUG_INDEX(("ERROR: Value %#x not found\n", id)); } 3769 else {DEBUG_INDEX(("ERROR: Value %#llx not found\n", id)); }
3735 DEBUG_RET(); 3770 DEBUG_RET();
3736 return ptr; 3771 return ptr;
3737 } 3772 }
3738 3773
3739 3774
3740 pst_index_ll * _pst_getID2(pst_index2_ll *ptr, uint32_t id) { 3775 pst_index_ll * pst_getID2(pst_index2_ll *ptr, uint64_t id) {
3741 DEBUG_ENT("_pst_getID2"); 3776 DEBUG_ENT("pst_getID2");
3742 DEBUG_INDEX(("Head = %p\n", ptr)); 3777 DEBUG_INDEX(("Head = %p\n", ptr));
3743 DEBUG_INDEX(("Trying to find %#x\n", id)); 3778 DEBUG_INDEX(("Trying to find %#x\n", id));
3744 while (ptr && (ptr->id2 != id)) { 3779 while (ptr && (ptr->id2 != id)) {
3745 ptr = ptr->next; 3780 ptr = ptr->next;
3746 } 3781 }
3747 if (ptr) { 3782 if (ptr) {
3748 if (ptr->id) {DEBUG_INDEX(("Found value %#x\n", ptr->id->id)); } 3783 if (ptr->id) {DEBUG_INDEX(("Found value %#llx\n", ptr->id->id)); }
3749 else {DEBUG_INDEX(("Found value, though it is NULL!\n"));} 3784 else {DEBUG_INDEX(("Found value, though it is NULL!\n"));}
3750 DEBUG_RET(); 3785 DEBUG_RET();
3751 return ptr->id; 3786 return ptr->id;
3752 } 3787 }
3753 DEBUG_INDEX(("ERROR Not Found\n")); 3788 DEBUG_INDEX(("ERROR Not Found\n"));
3762 * @param pf global pst file pointer 3797 * @param pf global pst file pointer
3763 * @param id the id we are looking for 3798 * @param id the id we are looking for
3764 * 3799 *
3765 * @return pointer to the pst_desc_ll node in the descriptor tree 3800 * @return pointer to the pst_desc_ll node in the descriptor tree
3766 */ 3801 */
3767 pst_desc_ll* _pst_getDptr(pst_file *pf, uint32_t id) { 3802 pst_desc_ll* pst_getDptr(pst_file *pf, uint64_t id) {
3768 pst_desc_ll *ptr = pf->d_head; 3803 pst_desc_ll *ptr = pf->d_head;
3769 DEBUG_ENT("_pst_getDptr"); 3804 DEBUG_ENT("pst_getDptr");
3770 while (ptr && (ptr->id != id)) { 3805 while (ptr && (ptr->id != id)) {
3771 if (ptr->child) { 3806 if (ptr->child) {
3772 ptr = ptr->child; 3807 ptr = ptr->child;
3773 continue; 3808 continue;
3774 } 3809 }
3780 DEBUG_RET(); 3815 DEBUG_RET();
3781 return ptr; // will be NULL or record we are looking for 3816 return ptr; // will be NULL or record we are looking for
3782 } 3817 }
3783 3818
3784 3819
3785 int32_t _pst_printDptr(pst_file *pf) { 3820 int32_t pst_printDptr(pst_file *pf) {
3786 pst_desc_ll *ptr = pf->d_head; 3821 pst_desc_ll *ptr = pf->d_head;
3787 int32_t depth = 0; 3822 int32_t depth = 0;
3788 char spaces[100]; 3823 char spaces[100];
3789 DEBUG_ENT("_pst_printDptr"); 3824 DEBUG_ENT("pst_printDptr");
3790 memset(spaces, ' ', 99); 3825 memset(spaces, ' ', 99);
3791 spaces[99] = '\0'; 3826 spaces[99] = '\0';
3792 while (ptr) { 3827 while (ptr) {
3793 DEBUG_INDEX(("%s%#x [%i] desc=%#x, list=%#x\n", &(spaces[(99-depth<0?0:99-depth)]), ptr->id, ptr->no_child, 3828 DEBUG_INDEX(("%s%#x [%i] desc=%#x, list=%#x\n", &(spaces[(99-depth<0?0:99-depth)]), ptr->id, ptr->no_child,
3794 (ptr->desc==NULL?0:ptr->desc->id), 3829 (ptr->desc==NULL?0:ptr->desc->id),
3807 DEBUG_RET(); 3842 DEBUG_RET();
3808 return 0; 3843 return 0;
3809 } 3844 }
3810 3845
3811 3846
3812 int32_t _pst_printIDptr(pst_file* pf) { 3847 int32_t pst_printIDptr(pst_file* pf) {
3813 pst_index_ll *ptr = pf->i_head; 3848 pst_index_ll *ptr = pf->i_head;
3814 DEBUG_ENT("_pst_printIDptr"); 3849 DEBUG_ENT("pst_printIDptr");
3815 while (ptr) { 3850 while (ptr) {
3816 DEBUG_INDEX(("%#x offset=%#x size=%#x\n", ptr->id, ptr->offset, ptr->size)); 3851 DEBUG_INDEX(("%#x offset=%#x size=%#x\n", ptr->id, ptr->offset, ptr->size));
3817 ptr = ptr->next; 3852 ptr = ptr->next;
3818 } 3853 }
3819 DEBUG_RET(); 3854 DEBUG_RET();
3820 return 0; 3855 return 0;
3821 } 3856 }
3822 3857
3823 3858
3824 int32_t _pst_printID2ptr(pst_index2_ll *ptr) { 3859 int32_t pst_printID2ptr(pst_index2_ll *ptr) {
3825 DEBUG_ENT("_pst_printID2ptr"); 3860 DEBUG_ENT("pst_printID2ptr");
3826 while (ptr) { 3861 while (ptr) {
3827 DEBUG_INDEX(("%#x id=%#x\n", ptr->id2, (ptr->id!=NULL?ptr->id->id:0))); 3862 DEBUG_INDEX(("%#x id=%#x\n", ptr->id2, (ptr->id!=NULL?ptr->id->id:0)));
3828 ptr = ptr->next; 3863 ptr = ptr->next;
3829 } 3864 }
3830 DEBUG_RET(); 3865 DEBUG_RET();
3831 return 0; 3866 return 0;
3832 }
3833
3834
3835 size_t _pst_read_block(FILE *fp, off_t offset, void **buf) {
3836 int16_t size16;
3837 size_t size;
3838 off_t fpos;
3839 DEBUG_ENT("_pst_read_block");
3840 DEBUG_READ(("Reading block from %#x\n", offset));
3841 fpos = ftell(fp);
3842 fseek(fp, offset, SEEK_SET);
3843 fread(&size16, sizeof(int16_t), 1, fp);
3844 LE16_CPU(size16);
3845 size = size16;
3846 fseek(fp, offset, SEEK_SET);
3847 DEBUG_READ(("Allocating %i bytes\n", size));
3848 if (*buf) {
3849 DEBUG_READ(("Freeing old memory\n"));
3850 free(*buf);
3851 }
3852 *buf = (void*)xmalloc(size);
3853 size = fread(*buf, 1, size, fp);
3854 fseek(fp, fpos, SEEK_SET);
3855 DEBUG_RET();
3856 return size;
3857 } 3867 }
3858 3868
3859 3869
3860 // when the first byte of the block being read is 01, then we can assume 3870 // when the first byte of the block being read is 01, then we can assume
3861 // that it is a list of further ids to read and we will follow those ids 3871 // that it is a list of further ids to read and we will follow those ids
3862 // recursively calling this function until we have all the data 3872 // recursively calling this function until we have all the data
3863 // we could do decryption of the encrypted PST files here 3873 // we could do decryption of the encrypted PST files here
3864 size_t _pst_read_block_size(pst_file *pf, off_t offset, size_t size, char **buf, int32_t do_enc, unsigned char is_index) { 3874 size_t pst_read_block_size(pst_file *pf, off_t offset, size_t size, char **buf, int32_t do_enc, unsigned char is_index) {
3865 off_t fpos; 3875 off_t fpos;
3866 int32_t x; 3876 uint32_t x;
3867 int16_t count, y; 3877 int16_t count, y;
3868 char *buf2 = NULL, *buf3 = NULL; 3878 char *buf2 = NULL, *buf3 = NULL;
3869 unsigned char fdepth; 3879 unsigned char fdepth;
3870 pst_index_ll *ptr = NULL; 3880 pst_index_ll *ptr = NULL;
3871 size_t rsize, z; 3881 size_t rsize, z;
3872 3882
3873 DEBUG_ENT("_pst_read_block_size"); 3883 DEBUG_ENT("pst_read_block_size");
3874 DEBUG_READ(("Reading block from %#x, %i bytes\n", offset, size)); 3884 DEBUG_READ(("Reading block from %#x, %i bytes\n", offset, size));
3875 3885
3876 fpos = ftell(pf->fp); 3886 fpos = ftell(pf->fp);
3877 fseek(pf->fp, offset, SEEK_SET); 3887 (void)fseek(pf->fp, offset, SEEK_SET);
3878 if (*buf) { 3888 if (*buf) {
3879 DEBUG_READ(("Freeing old memory\n")); 3889 DEBUG_READ(("Freeing old memory\n"));
3880 free(*buf); 3890 free(*buf);
3881 } 3891 }
3882 3892
3883 *buf = (void*) xmalloc(size+1); //plus one so that we can NUL terminate it later 3893 *buf = (void*) xmalloc(size+1); //plus one so that we can NUL terminate it later
3884 rsize = fread(*buf, 1, size, pf->fp); 3894 rsize = fread(*buf, (size_t)1, size, pf->fp);
3885 if (rsize != size) { 3895 if (rsize != size) {
3886 DEBUG_WARN(("Didn't read all that I could. fread returned less [%i instead of %i]\n", rsize, size)); 3896 DEBUG_WARN(("Didn't read all that I could. fread returned less [%i instead of %i]\n", rsize, size));
3887 if (feof(pf->fp)) { 3897 if (feof(pf->fp)) {
3888 DEBUG_WARN(("We tried to read past the end of the file at [offset %#x, size %#x]\n", offset, size)); 3898 DEBUG_WARN(("We tried to read past the end of the file at [offset %#x, size %#x]\n", offset, size));
3889 } else if (ferror(pf->fp)) { 3899 } else if (ferror(pf->fp)) {
3895 } 3905 }
3896 3906
3897 // DEBUG_HEXDUMP(*buf, size); 3907 // DEBUG_HEXDUMP(*buf, size);
3898 3908
3899 /* if (is_index) { 3909 /* if (is_index) {
3900 DEBUG_READ(("_pst_read_block_size: ODD_BLOCK should be here\n")); 3910 DEBUG_READ(("pst_read_block_size: ODD_BLOCK should be here\n"));
3901 DEBUG_READ(("\t: byte 0-1: %#x %#x\n", (*buf)[0], (*buf)[1])); 3911 DEBUG_READ(("\t: byte 0-1: %#x %#x\n", (*buf)[0], (*buf)[1]));
3902 }*/ 3912 }*/
3903 3913
3904 if ((*buf)[0] == 0x01 && (*buf)[1] != 0x00 && is_index) { 3914 if ((*buf)[0] == 0x01 && (*buf)[1] != 0x00 && is_index) {
3905 //don't do this recursion if we should be at a leaf node 3915 //don't do this recursion if we should be at a leaf node
3911 DEBUG_READ(("There are %i ids\n", count)); 3921 DEBUG_READ(("There are %i ids\n", count));
3912 // if first 2 blocks are 01 01 then index to blocks 3922 // if first 2 blocks are 01 01 then index to blocks
3913 size = 0; 3923 size = 0;
3914 y = 0; 3924 y = 0;
3915 while (y < count) { 3925 while (y < count) {
3916 memcpy(&x, &(*buf)[0x08+(y*4)], sizeof(int32_t)); 3926 memcpy(&x, &(*buf)[0x08+(y*4)], sizeof(uint32_t));
3917 LE32_CPU(x); 3927 LE32_CPU(x);
3918 if ((ptr = _pst_getID(pf, x)) == NULL) { 3928 if ((ptr = pst_getID(pf, x)) == NULL) {
3919 WARN(("Error. Cannot find ID [%#x] during multi-block read\n", x)); 3929 WARN(("Error. Cannot find ID [%#x] during multi-block read\n", x));
3920 buf3 = (char*) realloc(buf3, size+1); 3930 buf3 = (char*) realloc(buf3, size+1);
3921 buf3[size] = '\0'; 3931 buf3[size] = '\0';
3922 *buf = buf3; 3932 *buf = buf3;
3923 fseek(pf->fp, fpos, SEEK_SET); 3933 fseek(pf->fp, fpos, SEEK_SET);
3924 DEBUG_RET(); 3934 DEBUG_RET();
3925 return size; 3935 return size;
3926 } 3936 }
3927 if ((z = _pst_read_block_size(pf, ptr->offset, ptr->size, &buf2, do_enc, fdepth-1)) < ptr->size) { 3937 if ((z = pst_read_block_size(pf, ptr->offset, ptr->size, &buf2, do_enc, fdepth-1)) < ptr->size) {
3928 buf3 = (char*) realloc(buf3, size+1); 3938 buf3 = (char*) realloc(buf3, size+1);
3929 buf3[size] = '\0'; 3939 buf3[size] = '\0';
3930 *buf = buf3; 3940 *buf = buf3;
3931 fseek(pf->fp, fpos, SEEK_SET); 3941 fseek(pf->fp, fpos, SEEK_SET);
3932 DEBUG_RET(); 3942 DEBUG_RET();
3942 free(*buf); 3952 free(*buf);
3943 if (buf2) free(buf2); 3953 if (buf2) free(buf2);
3944 if (!buf3) { 3954 if (!buf3) {
3945 // this can happen if count == 0. We should create an empty buffer so we don't 3955 // this can happen if count == 0. We should create an empty buffer so we don't
3946 // confuse any clients 3956 // confuse any clients
3947 buf3 = (char*) xmalloc(1); 3957 buf3 = (char*) xmalloc((size_t)1);
3948 } 3958 }
3949 *buf = buf3; 3959 *buf = buf3;
3950 } else if (do_enc && pf->encryption) 3960 } else if (do_enc && pf->encryption) {
3951 _pst_decrypt(*buf, size, pf->encryption); 3961 (void)pst_decrypt(*buf, size, pf->encryption);
3962 } else {
3963 // nothing to do
3964 }
3952 3965
3953 (*buf)[size] = '\0'; //should be byte after last one read 3966 (*buf)[size] = '\0'; //should be byte after last one read
3954 fseek(pf->fp, fpos, SEEK_SET); 3967 (void)fseek(pf->fp, fpos, SEEK_SET);
3955 DEBUG_RET(); 3968 DEBUG_RET();
3956 return size; 3969 return size;
3957 } 3970 }
3958 3971
3959 3972
3960 int32_t _pst_decrypt(unsigned char *buf, size_t size, int32_t type) { 3973 int pst_decrypt(unsigned char *buf, size_t size, unsigned char type) {
3961 size_t x = 0; 3974 size_t x = 0;
3962 unsigned char y; 3975 unsigned char y;
3963 DEBUG_ENT("_pst_decrypt"); 3976 DEBUG_ENT("pst_decrypt");
3964 if (!buf) { 3977 if (!buf) {
3965 DEBUG_RET(); 3978 DEBUG_RET();
3966 return -1; 3979 return -1;
3967 } 3980 }
3968 3981
3982 DEBUG_RET(); 3995 DEBUG_RET();
3983 return 0; 3996 return 0;
3984 } 3997 }
3985 3998
3986 3999
3987 int64_t _getIntAt(char *buf) { 4000 uint64_t pst_getIntAt(pst_file *pf, char *buf) {
3988 int64_t buf64; 4001 uint64_t buf64;
3989 int32_t buf32; 4002 uint32_t buf32;
3990 if (do_read64) { 4003 if (pf->do_read64) {
3991 memcpy(&buf64, buf, sizeof(buf64)); 4004 memcpy(&buf64, buf, sizeof(buf64));
3992 LE64_CPU(buf64); 4005 LE64_CPU(buf64);
3993 return buf64; 4006 return buf64;
3994 } 4007 }
3995 else { 4008 else {
3998 return buf32; 4011 return buf32;
3999 } 4012 }
4000 } 4013 }
4001 4014
4002 4015
4003 int64_t _pst_getIntAtPos(FILE *fp, off_t pos ) { 4016 uint64_t pst_getIntAtPos(pst_file *pf, off_t pos ) {
4004 int64_t buf64; 4017 uint64_t buf64;
4005 int32_t buf32; 4018 uint32_t buf32;
4006 if (do_read64) { 4019 if (pf->do_read64) {
4007 _pst_getAtPos(fp, pos, &buf64, sizeof(buf64)); 4020 (void)pst_getAtPos(pf->fp, pos, &buf64, sizeof(buf64));
4008 LE64_CPU(buf64); 4021 LE64_CPU(buf64);
4009 return buf64; 4022 return buf64;
4010 } 4023 }
4011 else { 4024 else {
4012 _pst_getAtPos(fp, pos, &buf32, sizeof(buf32)); 4025 (void)pst_getAtPos(pf->fp, pos, &buf32, sizeof(buf32));
4013 LE32_CPU(buf32); 4026 LE32_CPU(buf32);
4014 return buf32; 4027 return buf32;
4015 } 4028 }
4016 } 4029 }
4017 4030
4018 4031
4019 int32_t _pst_getAtPos(FILE *fp, off_t pos, void* buf, uint32_t size) { 4032 int pst_getAtPos(FILE *fp, off_t pos, void* buf, size_t size) {
4020 DEBUG_ENT("_pst_getAtPos"); 4033 DEBUG_ENT("pst_getAtPos");
4021 if (fseek(fp, pos, SEEK_SET) == -1) { 4034 if (fseek(fp, pos, SEEK_SET) == -1) {
4022 DEBUG_RET(); 4035 DEBUG_RET();
4023 return 1; 4036 return 1;
4024 } 4037 }
4025 if (fread(buf, 1, size, fp) < size) { 4038 if (fread(buf, 1, size, fp) < size) {
4029 DEBUG_RET(); 4042 DEBUG_RET();
4030 return 0; 4043 return 0;
4031 } 4044 }
4032 4045
4033 4046
4034 int32_t _pst_get (FILE *fp, void *buf, uint32_t size) { 4047 int pst_get (FILE *fp, void *buf, size_t size) {
4035 DEBUG_ENT("_pst_get"); 4048 DEBUG_ENT("pst_get");
4036 if (fread(buf, 1, size, fp) < size) { 4049 if (fread(buf, 1, size, fp) < size) {
4037 DEBUG_RET(); 4050 DEBUG_RET();
4038 return 1; 4051 return 1;
4039 } 4052 }
4040 DEBUG_RET(); 4053 DEBUG_RET();
4041 return 0; 4054 return 0;
4042 } 4055 }
4043 4056
4044 4057
4045 size_t _pst_ff_getIDblock_dec(pst_file *pf, uint32_t id, unsigned char **b) { 4058 size_t pst_ff_getIDblock_dec(pst_file *pf, uint64_t id, unsigned char **b) {
4046 size_t r; 4059 size_t r;
4047 DEBUG_ENT("_pst_ff_getIDblock_dec"); 4060 int noenc = (int)(id & 2); // disable encryption
4061 DEBUG_ENT("pst_ff_getIDblock_dec");
4048 DEBUG_INDEX(("for id %#x\n", id)); 4062 DEBUG_INDEX(("for id %#x\n", id));
4049 r = _pst_ff_getIDblock(pf, id, b); 4063 r = pst_ff_getIDblock(pf, id, b);
4050 int noenc = (id & 2); // disable encryption 4064 if ((pf->encryption) && !(noenc)) {
4051 if ((pf->encryption) & !(noenc)) { 4065 (void)pst_decrypt(*b, r, pf->encryption);
4052 _pst_decrypt(*b, r, pf->encryption);
4053 } 4066 }
4054 DEBUG_HEXDUMPC(*b, r, 16); 4067 DEBUG_HEXDUMPC(*b, r, 16);
4055 DEBUG_RET(); 4068 DEBUG_RET();
4056 return r; 4069 return r;
4057 } 4070 }
4058 4071
4059 4072
4060 size_t _pst_ff_getIDblock(pst_file *pf, uint32_t id, unsigned char** b) { 4073 size_t pst_ff_getIDblock(pst_file *pf, uint64_t id, unsigned char** b) {
4061 pst_index_ll *rec; 4074 pst_index_ll *rec;
4062 size_t rsize = 0;//, re_size=0; 4075 size_t rsize = 0;
4063 DEBUG_ENT("_pst_ff_getIDblock"); 4076 DEBUG_ENT("pst_ff_getIDblock");
4064 if ((rec = _pst_getID(pf, id)) == NULL) { 4077 if ((rec = pst_getID(pf, id)) == NULL) {
4065 DEBUG_INDEX(("Cannot find ID %#x\n", id)); 4078 DEBUG_INDEX(("Cannot find ID %#x\n", id));
4066 DEBUG_RET(); 4079 DEBUG_RET();
4067 return 0; 4080 return 0;
4068 } 4081 }
4069 fseek(pf->fp, rec->offset, SEEK_SET); 4082 (void)fseek(pf->fp, rec->offset, SEEK_SET);
4070 if (*b) { 4083 if (*b) {
4071 DEBUG_INDEX(("freeing old memory in b\n")); 4084 DEBUG_INDEX(("freeing old memory in b\n"));
4072 free(*b); 4085 free(*b);
4073 } 4086 }
4074 4087
4089 return rsize; 4102 return rsize;
4090 } 4103 }
4091 4104
4092 4105
4093 #define PST_PTR_BLOCK_SIZE 0x120 4106 #define PST_PTR_BLOCK_SIZE 0x120
4094 size_t _pst_ff_getID2block(pst_file *pf, uint32_t id2, pst_index2_ll *id2_head, unsigned char** buf) { 4107 size_t pst_ff_getID2block(pst_file *pf, uint64_t id2, pst_index2_ll *id2_head, unsigned char** buf) {
4095 pst_index_ll* ptr; 4108 pst_index_ll* ptr;
4096 // size_t ret; 4109 // size_t ret;
4097 struct holder h = {buf, NULL, 0, "", 0}; 4110 struct holder h = {buf, NULL, 0, "", 0};
4098 DEBUG_ENT("_pst_ff_getID2block"); 4111 DEBUG_ENT("pst_ff_getID2block");
4099 ptr = _pst_getID2(id2_head, id2); 4112 ptr = pst_getID2(id2_head, id2);
4100 4113
4101 if (!ptr) { 4114 if (!ptr) {
4102 DEBUG_INDEX(("Cannot find id2 value %#x\n", id2)); 4115 DEBUG_INDEX(("Cannot find id2 value %#x\n", id2));
4103 DEBUG_RET(); 4116 DEBUG_RET();
4104 return 0; 4117 return 0;
4105 } 4118 }
4106 DEBUG_RET(); 4119 DEBUG_RET();
4107 return _pst_ff_getID2data(pf, ptr, &h); 4120 return pst_ff_getID2data(pf, ptr, &h);
4108 } 4121 }
4109 4122
4110 4123
4111 size_t _pst_ff_getID2data(pst_file *pf, pst_index_ll *ptr, struct holder *h) { 4124 size_t pst_ff_getID2data(pst_file *pf, pst_index_ll *ptr, struct holder *h) {
4112 int32_t ret; 4125 size_t ret;
4113 unsigned char *b = NULL, *t; 4126 unsigned char *b = NULL, *t;
4114 DEBUG_ENT("_pst_ff_getID2data"); 4127 DEBUG_ENT("pst_ff_getID2data");
4115 if (!(ptr->id & 0x02)) { 4128 if (!(ptr->id & 0x02)) {
4116 ret = _pst_ff_getIDblock_dec(pf, ptr->id, &b); 4129 ret = pst_ff_getIDblock_dec(pf, ptr->id, &b);
4117 if (h->buf) { 4130 if (h->buf) {
4118 *(h->buf) = b; 4131 *(h->buf) = b;
4119 } else if ((h->base64 == 1) && h->fp) { 4132 } else if ((h->base64 == 1) && h->fp) {
4120 t = base64_encode(b, ret); 4133 t = base64_encode(b, ret);
4121 if (t) { 4134 if (t) {
4122 pst_fwrite(t, 1, strlen(t), h->fp); 4135 (void)pst_fwrite(t, 1, strlen(t), h->fp);
4123 free(t); // caught by valgrind 4136 free(t); // caught by valgrind
4124 } 4137 }
4125 free(b); 4138 free(b);
4126 } else if (h->fp) { 4139 } else if (h->fp) {
4127 pst_fwrite(b, 1, ret, h->fp); 4140 (void)pst_fwrite(b, 1, ret, h->fp);
4128 free(b); 4141 free(b);
4129 } 4142 } else {
4143 // h-> does not specify any output
4144 }
4145
4130 } else { 4146 } else {
4131 // here we will assume it is a block that points to others 4147 // here we will assume it is a block that points to others
4132 DEBUG_READ(("Assuming it is a multi-block record because of it's id\n")); 4148 DEBUG_READ(("Assuming it is a multi-block record because of it's id\n"));
4133 ret = _pst_ff_compile_ID(pf, ptr->id, h, 0); 4149 ret = pst_ff_compile_ID(pf, ptr->id, h, (size_t)0);
4134 } 4150 }
4135 if (h->buf && *h->buf) 4151 if (h->buf && *h->buf)
4136 (*(h->buf))[ret]='\0'; 4152 (*(h->buf))[ret]='\0';
4137 DEBUG_RET(); 4153 DEBUG_RET();
4138 return ret; 4154 return ret;
4139 } 4155 }
4140 4156
4141 4157
4142 size_t _pst_ff_compile_ID(pst_file *pf, uint32_t id, struct holder *h, int32_t size) { 4158 size_t pst_ff_compile_ID(pst_file *pf, uint64_t id, struct holder *h, size_t size) {
4143 size_t z, a; 4159 size_t z, a;
4144 uint16_t count, y; 4160 uint16_t count, y;
4145 uint32_t x, b; 4161 uint32_t x, b;
4146 unsigned char * buf3 = NULL, *buf2 = NULL, *t; 4162 unsigned char * buf3 = NULL, *buf2 = NULL, *t;
4147 unsigned char fdepth; 4163 unsigned char fdepth;
4148 4164
4149 DEBUG_ENT("_pst_ff_compile_ID"); 4165 DEBUG_ENT("pst_ff_compile_ID");
4150 a = _pst_ff_getIDblock(pf, id, &buf3); 4166 a = pst_ff_getIDblock(pf, id, &buf3);
4151 if (!a) { 4167 if (!a) {
4152 if (buf3) free(buf3); 4168 if (buf3) free(buf3);
4153 return 0; 4169 return 0;
4154 } 4170 }
4155 if ((buf3[0] != 0x1)) { // if bit 8 is set) { 4171 if ((buf3[0] != 0x1)) { // if bit 8 is set) {
4156 // if ((buf3)[0] != 0x1 && (buf3)[1] > 4) { 4172 // if ((buf3)[0] != 0x1 && (buf3)[1] > 4) {
4157 DEBUG_WARN(("WARNING: buffer doesn't start with 0x1, but I expected it to or doesn't have it's two-bit set!\n")); 4173 DEBUG_WARN(("WARNING: buffer doesn't start with 0x1, but I expected it to or doesn't have it's two-bit set!\n"));
4158 DEBUG_WARN(("Treating as normal buffer\n")); 4174 DEBUG_WARN(("Treating as normal buffer\n"));
4159 if (pf->encryption) _pst_decrypt(buf3, a, pf->encryption); 4175 if (pf->encryption) (void)pst_decrypt(buf3, a, pf->encryption);
4160 if (h->buf) 4176 if (h->buf)
4161 *(h->buf) = buf3; 4177 *(h->buf) = buf3;
4162 else if (h->base64 == 1 && h->fp) { 4178 else if (h->base64 == 1 && h->fp) {
4163 t = base64_encode(buf3, a); 4179 t = base64_encode(buf3, a);
4164 if (t) { 4180 if (t) {
4165 pst_fwrite(t, 1, strlen(t), h->fp); 4181 (void)pst_fwrite(t, 1, strlen(t), h->fp);
4166 free(t); // caught by valgrind 4182 free(t); // caught by valgrind
4167 } 4183 }
4168 free(buf3); 4184 free(buf3);
4169 } else if (h->fp) { 4185 } else if (h->fp) {
4170 pst_fwrite(buf3, 1, a, h->fp); 4186 (void)pst_fwrite(buf3, 1, a, h->fp);
4171 free(buf3); 4187 free(buf3);
4188 } else {
4189 // h-> does not specify any output
4172 } 4190 }
4173 DEBUG_RET(); 4191 DEBUG_RET();
4174 return a; 4192 return a;
4175 } 4193 }
4176 memcpy (&count, &(buf3[2]), sizeof(int16_t)); 4194 memcpy (&count, &(buf3[2]), sizeof(int16_t));
4182 y = 0; 4200 y = 0;
4183 while (y < count) { 4201 while (y < count) {
4184 memcpy(&x, &buf3[0x08+(y*4)], sizeof(int32_t)); 4202 memcpy(&x, &buf3[0x08+(y*4)], sizeof(int32_t));
4185 LE32_CPU(x); 4203 LE32_CPU(x);
4186 if (fdepth == 0x1) { 4204 if (fdepth == 0x1) {
4187 if ((z = _pst_ff_getIDblock(pf, x, &buf2)) == 0) { 4205 if ((z = pst_ff_getIDblock(pf, x, &buf2)) == 0) {
4188 DEBUG_WARN(("call to getIDblock returned zero %i\n", z)); 4206 DEBUG_WARN(("call to getIDblock returned zero %i\n", z));
4189 if (buf2) free(buf2); 4207 if (buf2) free(buf2);
4190 free(buf3); 4208 free(buf3);
4191 return z; 4209 return z;
4192 } 4210 }
4193 if (pf->encryption) _pst_decrypt(buf2, z, pf->encryption); 4211 if (pf->encryption) (void)pst_decrypt(buf2, z, pf->encryption);
4194 if (h->buf) { 4212 if (h->buf) {
4195 *(h->buf) = realloc(*(h->buf), size+z+1); 4213 *(h->buf) = realloc(*(h->buf), size+z+1);
4196 DEBUG_READ(("appending read data of size %i onto main buffer from pos %i\n", z, size)); 4214 DEBUG_READ(("appending read data of size %i onto main buffer from pos %i\n", z, size));
4197 memcpy(&((*(h->buf))[size]), buf2, z); 4215 memcpy(&((*(h->buf))[size]), buf2, z);
4198 } 4216 } else if ((h->base64 == 1) && h->fp) {
4199 else if ((h->base64 == 1) && h->fp) {
4200 // include any byte left over from the last one encoding 4217 // include any byte left over from the last one encoding
4201 buf2 = (char*)realloc(buf2, z+h->base64_extra); 4218 buf2 = (char*)realloc(buf2, z+h->base64_extra);
4202 memmove(buf2+h->base64_extra, buf2, z); 4219 memmove(buf2+h->base64_extra, buf2, z);
4203 memcpy(buf2, h->base64_extra_chars, h->base64_extra); 4220 memcpy(buf2, h->base64_extra_chars, h->base64_extra);
4204 z+= h->base64_extra; 4221 z += h->base64_extra;
4205 4222
4206 b = z % 3; // find out how many bytes will be left over after the encoding. 4223 b = z % 3; // find out how many bytes will be left over after the encoding.
4207 // and save them 4224 // and save them
4208 memcpy(h->base64_extra_chars, &(buf2[z-b]), b); 4225 memcpy(h->base64_extra_chars, &(buf2[z-b]), b);
4209 h->base64_extra = b; 4226 h->base64_extra = b;
4210 t = base64_encode(buf2, z-b); 4227 t = base64_encode(buf2, z-b);
4211 if (t) { 4228 if (t) {
4212 DEBUG_READ(("writing %i bytes to file as base64 [%i]. Currently %i\n", z, strlen(t), size)); 4229 DEBUG_READ(("writing %i bytes to file as base64 [%i]. Currently %i\n", z, strlen(t), size));
4213 pst_fwrite(t, 1, strlen(t), h->fp); 4230 (void)pst_fwrite(t, 1, strlen(t), h->fp);
4214 free(t); // caught by valgrind 4231 free(t); // caught by valgrind
4215 } 4232 }
4216 } 4233 } else if (h->fp) {
4217 else if (h->fp) {
4218 DEBUG_READ(("writing %i bytes to file. Currently %i\n", z, size)); 4234 DEBUG_READ(("writing %i bytes to file. Currently %i\n", z, size));
4219 pst_fwrite(buf2, 1, z, h->fp); 4235 (void)pst_fwrite(buf2, 1, z, h->fp);
4236 } else {
4237 // h-> does not specify any output
4220 } 4238 }
4221 size += z; 4239 size += z;
4222 y++; 4240 y++;
4223 } 4241 }
4224 else { 4242 else {
4225 if ((z = _pst_ff_compile_ID(pf, x, h, size)) == 0) { 4243 if ((z = pst_ff_compile_ID(pf, x, h, size)) == 0) {
4226 DEBUG_WARN(("recursive called returned zero %i\n", z)); 4244 DEBUG_WARN(("recursive called returned zero %i\n", z));
4227 free(buf3); 4245 free(buf3);
4228 DEBUG_RET(); 4246 DEBUG_RET();
4229 return z; 4247 return z;
4230 } 4248 }
4275 } 4293 }
4276 4294
4277 4295
4278 #endif //_MSC_VER 4296 #endif //_MSC_VER
4279 4297
4280 int32_t pst_stricmp(char *a, char *b) { 4298 int pst_stricmp(char *a, char *b) {
4281 // compare strings case-insensitive. 4299 // compare strings case-insensitive.
4282 // returns -1 if a < b, 0 if a==b, 1 if a > b 4300 // returns -1 if a < b, 0 if a==b, 1 if a > b
4283 while(*a != '\0' && *b != '\0' && toupper(*a)==toupper(*b)) { 4301 while(*a != '\0' && *b != '\0' && toupper(*a)==toupper(*b)) {
4284 a++; b++; 4302 a++; b++;
4285 } 4303 }
4290 else 4308 else
4291 return 1; 4309 return 1;
4292 } 4310 }
4293 4311
4294 4312
4295 int32_t pst_strincmp(char *a, char *b, int32_t x) { 4313 int pst_strincmp(char *a, char *b, size_t x) {
4296 // compare upto x chars in string a and b case-insensitively 4314 // compare upto x chars in string a and b case-insensitively
4297 // returns -1 if a < b, 0 if a==b, 1 if a > b 4315 // returns -1 if a < b, 0 if a==b, 1 if a > b
4298 int32_t y = 0; 4316 size_t y = 0;
4299 while (*a != '\0' && *b != '\0' && y < x && toupper(*a)==toupper(*b)) { 4317 while (*a != '\0' && *b != '\0' && y < x && toupper(*a)==toupper(*b)) {
4300 a++; b++; y++; 4318 a++; b++; y++;
4301 } 4319 }
4302 // if we have reached the end of either string, or a and b still match 4320 // if we have reached the end of either string, or a and b still match
4303 if (*a == '\0' || *b == '\0' || toupper(*a)==toupper(*b)) 4321 if (*a == '\0' || *b == '\0' || toupper(*a)==toupper(*b))
4321 DEBUG_RET(); 4339 DEBUG_RET();
4322 return r; 4340 return r;
4323 } 4341 }
4324 4342
4325 4343
4326 char * _pst_wide_to_single(char *wt, int32_t size) { 4344 char * pst_wide_to_single(char *wt, int32_t size) {
4327 // returns the first byte of each wide char. the size is the number of bytes in source 4345 // returns the first byte of each wide char. the size is the number of bytes in source
4328 char *x, *y; 4346 char *x, *y;
4329 DEBUG_ENT("_pst_wide_to_single"); 4347 DEBUG_ENT("pst_wide_to_single");
4330 x = xmalloc((size/2)+1); 4348 x = xmalloc((size/2)+1);
4331 y = x; 4349 y = x;
4332 while (size != 0 && *wt != '\0') { 4350 while (size != 0 && *wt != '\0') {
4333 *y = *wt; 4351 *y = *wt;
4334 wt+=2; 4352 wt+=2;
4394 } 4412 }
4395 4413
4396 4414
4397 int pst_chr_count(char *str, char x) { 4415 int pst_chr_count(char *str, char x) {
4398 int r = 0; 4416 int r = 0;
4399 while (*str != '\0') { 4417 while (*str) {
4400 if (*str == x) 4418 if (*str == x) r++;
4401 r++;
4402 str++; 4419 str++;
4403 } 4420 }
4404 return r; 4421 return r;
4405 } 4422 }
4406 4423