comparison src/msg.cpp @ 313:0f19cd173eab

fix to/cc/bcc recipients in .msg file output format
author Carl Byington <carl@five-ten-sg.com>
date Mon, 24 May 2010 21:50:19 -0700
parents 0c42a22f88fc
children 6bf6b60a9751
comparison
equal deleted inserted replaced
312:b7f79da5fd55 313:0f19cd173eab
70 70
71 71
72 static void string_property(GsfOutfile *out, property_list &prop, uint32_t tag, const char *contents, size_t size); 72 static void string_property(GsfOutfile *out, property_list &prop, uint32_t tag, const char *contents, size_t size);
73 static void string_property(GsfOutfile *out, property_list &prop, uint32_t tag, const char *contents, size_t size) { 73 static void string_property(GsfOutfile *out, property_list &prop, uint32_t tag, const char *contents, size_t size) {
74 if (!contents) return; 74 if (!contents) return;
75 size_t term = ((tag & 0x0000ffff) == 0x001e) ? 1 :
76 ((tag & 0x0000ffff) == 0x001f) ? 2 : 0; // null terminator
75 vector<char> n(50); 77 vector<char> n(50);
76 snprintf(&n[0], n.size(), "__substg1.0_%08X", tag); 78 snprintf(&n[0], n.size(), "__substg1.0_%08X", tag);
79 fprintf(stdout, "dumping string property %08X size %d with data %s\n", tag, (int)size, contents);
77 GsfOutput* dst = gsf_outfile_new_child(out, &n[0], false); 80 GsfOutput* dst = gsf_outfile_new_child(out, &n[0], false);
78 gsf_output_write(dst, size, (const guint8*)contents); 81 gsf_output_write(dst, size, (const guint8*)contents);
82 if (term) {
83 memset(&n[0], 0, term);
84 gsf_output_write(dst, term, (const guint8*)&n[0]);
85 size += term;
86 }
79 gsf_output_close(dst); 87 gsf_output_close(dst);
80 g_object_unref(G_OBJECT(dst)); 88 g_object_unref(G_OBJECT(dst));
81 89
82 int bias = ((tag & 0x0000ffff) == 0x001e) ? 1 : 0;
83 property p; 90 property p;
84 p.tag = tag; 91 p.tag = tag;
85 p.flags = 0x6; // make all the properties writable 92 p.flags = 0x6; // make all the properties writable
86 p.length = bias + size; 93 p.length = size;
87 p.reserved = 0; 94 p.reserved = 0;
88 prop.push_back(p); 95 prop.push_back(p);
89 } 96 }
90 97
91 98
280 // any property over 0x8000 needs entries in the __nameid to make them 287 // any property over 0x8000 needs entries in the __nameid to make them
281 // either string named or numerical named properties. 288 // either string named or numerical named properties.
282 289
283 { 290 {
284 vector<char> n(50); 291 vector<char> n(50);
285 snprintf(&n[0], n.size(), "__recip_version1.0_#%08X", top_head.recipient_count);
286 GsfOutput *output = gsf_outfile_new_child(out, &n[0], true);
287 { 292 {
288 int v = (email.message_recip_me) ? 1 : // to 293 snprintf(&n[0], n.size(), "__recip_version1.0_#%08X", top_head.recipient_count);
289 (email.message_cc_me) ? 2 : // cc 294 GsfOutput *output = gsf_outfile_new_child(out, &n[0], true);
290 3; // bcc 295 {
291 property_list prop_list; 296 int v = 1; // to
292 int_property(prop_list, 0x0C150003, 0x6, v); // PidTagRecipientType 297 property_list prop_list;
293 int_property(prop_list, 0x30000003, 0x6, top_head.recipient_count); // PR_ROWID 298 int_property(prop_list, 0x0C150003, 0x6, v); // PidTagRecipientType
294 GsfOutfile *out = GSF_OUTFILE (output); 299 int_property(prop_list, 0x30000003, 0x6, top_head.recipient_count); // PR_ROWID
295 string_property(out, prop_list, 0x3001001E, body_charset, item->file_as); 300 GsfOutfile *out = GSF_OUTFILE (output);
296 if (item->contact) { 301 string_property(out, prop_list, 0x3001001E, body_charset, item->file_as);
297 string_property(out, prop_list, 0x3002001E, body_charset, item->contact->address1_transport); 302 if (item->contact) {
298 string_property(out, prop_list, 0x3003001E, body_charset, item->contact->address1); 303 string_property(out, prop_list, 0x3002001E, body_charset, item->contact->address1_transport);
304 string_property(out, prop_list, 0x3003001E, body_charset, item->contact->address1);
305 string_property(out, prop_list, 0x5ff6001E, body_charset, item->contact->address1);
306 }
307 strin0_property(out, prop_list, 0x300B0102, body_charset, email.outlook_search_key);
308 write_properties(out, prop_list, (const guint8*)&top_head, 8); // convenient 8 bytes of reserved zeros
309 gsf_output_close(output);
310 g_object_unref(G_OBJECT(output));
311 top_head.next_recipient++;
312 top_head.recipient_count++;
299 } 313 }
300 strin0_property(out, prop_list, 0x300B0102, body_charset, email.outlook_search_key); 314 }
301 write_properties(out, prop_list, (const guint8*)&top_head, 8); // convenient 8 bytes of reserved zeros 315 if (email.cc_address.str) {
302 gsf_output_close(output); 316 snprintf(&n[0], n.size(), "__recip_version1.0_#%08X", top_head.recipient_count);
303 g_object_unref(G_OBJECT(output)); 317 GsfOutput *output = gsf_outfile_new_child(out, &n[0], true);
304 top_head.next_recipient++; 318 {
305 top_head.recipient_count++; 319 int v = 2; // cc
320 property_list prop_list;
321 int_property(prop_list, 0x0C150003, 0x6, v); // PidTagRecipientType
322 int_property(prop_list, 0x30000003, 0x6, top_head.recipient_count); // PR_ROWID
323 GsfOutfile *out = GSF_OUTFILE (output);
324 string_property(out, prop_list, 0x3001001E, body_charset, email.cc_address);
325 string_property(out, prop_list, 0x3003001E, body_charset, email.cc_address);
326 string_property(out, prop_list, 0x5ff6001E, body_charset, email.cc_address);
327 write_properties(out, prop_list, (const guint8*)&top_head, 8); // convenient 8 bytes of reserved zeros
328 gsf_output_close(output);
329 g_object_unref(G_OBJECT(output));
330 top_head.next_recipient++;
331 top_head.recipient_count++;
332 }
333 }
334 if (email.bcc_address.str) {
335 snprintf(&n[0], n.size(), "__recip_version1.0_#%08X", top_head.recipient_count);
336 GsfOutput *output = gsf_outfile_new_child(out, &n[0], true);
337 {
338 int v = 3; // bcc
339 property_list prop_list;
340 int_property(prop_list, 0x0C150003, 0x6, v); // PidTagRecipientType
341 int_property(prop_list, 0x30000003, 0x6, top_head.recipient_count); // PR_ROWID
342 GsfOutfile *out = GSF_OUTFILE (output);
343 string_property(out, prop_list, 0x3001001E, body_charset, email.bcc_address);
344 string_property(out, prop_list, 0x3003001E, body_charset, email.bcc_address);
345 string_property(out, prop_list, 0x5ff6001E, body_charset, email.bcc_address);
346 write_properties(out, prop_list, (const guint8*)&top_head, 8); // convenient 8 bytes of reserved zeros
347 gsf_output_close(output);
348 g_object_unref(G_OBJECT(output));
349 top_head.next_recipient++;
350 top_head.recipient_count++;
351 }
306 } 352 }
307 } 353 }
308 354
309 pst_item_attach *a = item->attach; 355 pst_item_attach *a = item->attach;
310 while (a) { 356 while (a) {
344 } 390 }
345 } 391 }
346 a = a->next; 392 a = a->next;
347 } 393 }
348 394
395 write_properties(out, prop_list, (const guint8*)&top_head, sizeof(top_head));
396
349 { 397 {
350 GsfOutput *output = gsf_outfile_new_child(out, "__nameid_version1.0", true); 398 GsfOutput *output = gsf_outfile_new_child(out, "__nameid_version1.0", true);
351 { 399 {
352 GsfOutfile *out = GSF_OUTFILE (output); 400 GsfOutfile *out = GSF_OUTFILE (output);
353 empty_property(out, 0x00020102); 401 empty_property(out, 0x00020102);
356 gsf_output_close(output); 404 gsf_output_close(output);
357 g_object_unref(G_OBJECT(output)); 405 g_object_unref(G_OBJECT(output));
358 } 406 }
359 } 407 }
360 408
361 write_properties(out, prop_list, (const guint8*)&top_head, sizeof(top_head));
362 gsf_output_close(output); 409 gsf_output_close(output);
363 g_object_unref(G_OBJECT(output)); 410 g_object_unref(G_OBJECT(output));
364 411
365 gsf_shutdown(); 412 gsf_shutdown();
366 DEBUG_RET(); 413 DEBUG_RET();