message::attachment_container_type message::fetch_attachments() { mapi_object_t attachment_table; mapi_object_init(&attachment_table); if (GetAttachmentTable(&m_object, &attachment_table) != MAPI_E_SUCCESS) { mapi_object_release(&attachment_table); throw mapi_exception(GetLastError(), "message::fetch_attachments : GetAttachmentTable"); } SPropTagArray* property_tag_array = set_SPropTagArray(m_session.get_memory_ctx(), 0x1, PR_ATTACH_NUM); if (SetColumns(&attachment_table, property_tag_array) != MAPI_E_SUCCESS) { MAPIFreeBuffer(property_tag_array); mapi_object_release(&attachment_table); throw mapi_exception(GetLastError(), "message::fetch_attachments : SetColumns"); } MAPIFreeBuffer(property_tag_array); SRowSet row_set; attachment_container_type attachment_container; while( (QueryRows(&attachment_table, 0x32, TBL_ADVANCE, TBL_FORWARD_READ, &row_set) == MAPI_E_SUCCESS) && row_set.cRows) { for (unsigned int i = 0; i < row_set.cRows; ++i) { try { attachment_container.push_back(attachment_shared_ptr(new attachment(*this, row_set.aRow[i].lpProps[0].value.l))); } catch(mapi_exception e) { mapi_object_release(&attachment_table); throw; } } } mapi_object_release(&attachment_table); return attachment_container; }
static uint32_t _module_fetchmail_run(TALLOC_CTX *mem_ctx, struct mapi_session *session) { enum MAPISTATUS retval; mapi_object_t obj_store; mapi_object_t obj_inbox; mapi_object_t obj_table; mapi_object_t obj_message; mapi_object_t obj_table_attach; mapi_object_t obj_attach; mapi_object_t obj_stream; uint64_t id_inbox = 0; struct SPropTagArray *SPropTagArray; struct SRowSet SRowSet; struct SRowSet SRowSet_attach; uint32_t i, j; uint32_t count; const uint8_t *has_attach; const uint32_t *attach_num; uint16_t read_size; unsigned char buf[MAX_READ_SIZE]; /* Log onto the store */ memset(&obj_store, 0, sizeof(mapi_object_t)); memset(&obj_inbox, 0, sizeof(mapi_object_t)); memset(&obj_table, 0, sizeof(mapi_object_t)); memset(&obj_message, 0, sizeof(mapi_object_t)); memset(&obj_table_attach, 0, sizeof(mapi_object_t)); memset(&obj_attach, 0, sizeof(mapi_object_t)); memset(&obj_stream, 0, sizeof(mapi_object_t)); mapi_object_init(&obj_store); retval = OpenMsgStore(session, &obj_store); if (retval) { mapi_errstr("OpenMsgStore", GetLastError()); return OCSIM_ERROR; } /* Open default receive folder (Inbox) */ retval = GetReceiveFolder(&obj_store, &id_inbox, NULL); if (retval) { mapi_errstr("GetReceiveFolder", GetLastError()); return OCSIM_ERROR; } retval = OpenFolder(&obj_store, id_inbox, &obj_inbox); if (retval) { mapi_errstr("OpenFolder", GetLastError()); return OCSIM_ERROR; } /* Open the contents table and customize the view */ mapi_object_init(&obj_table); retval = GetContentsTable(&obj_inbox, &obj_table, 0, &count); if (retval) { mapi_errstr("GetContentsTable", GetLastError()); return OCSIM_ERROR; } SPropTagArray = set_SPropTagArray(mem_ctx, 0x5, PR_FID, PR_MID, PR_INST_ID, PR_INSTANCE_NUM, PR_SUBJECT); retval = SetColumns(&obj_table, SPropTagArray); MAPIFreeBuffer(SPropTagArray); if (retval) { mapi_errstr("SetColumns", GetLastError()); return OCSIM_ERROR; } /* Retrieve the messages and attachments */ while ((retval = QueryRows(&obj_table, count, TBL_ADVANCE, &SRowSet)) != MAPI_E_NOT_FOUND && SRowSet.cRows) { count -= SRowSet.cRows; for (i = 0; i < SRowSet.cRows; i++) { mapi_object_init(&obj_message); retval = OpenMessage(&obj_store, SRowSet.aRow[i].lpProps[0].value.d, SRowSet.aRow[i].lpProps[0].value.d, &obj_message, 0); if (GetLastError() == MAPI_E_SUCCESS) { struct SPropValue *lpProps; struct SRow aRow; SPropTagArray = set_SPropTagArray(mem_ctx, 0x1, PR_HASATTACH); lpProps = talloc_zero(mem_ctx, struct SPropValue); retval = GetProps(&obj_message, 0, SPropTagArray, &lpProps, &count); MAPIFreeBuffer(SPropTagArray); if (retval) { mapi_errstr("GetProps", GetLastError()); return OCSIM_ERROR; } aRow.ulAdrEntryPad = 0; aRow.cValues = count; aRow.lpProps = lpProps; retval = fetchmail_get_contents(mem_ctx, &obj_message); has_attach = (const uint8_t *) get_SPropValue_SRow_data(&aRow, PR_HASATTACH); if (has_attach && *has_attach) { mapi_object_init(&obj_table_attach); retval = GetAttachmentTable(&obj_message, &obj_table_attach); if (retval == MAPI_E_SUCCESS) { SPropTagArray = set_SPropTagArray(mem_ctx, 0x1, PR_ATTACH_NUM); retval = SetColumns(&obj_table_attach, SPropTagArray); if (retval != MAPI_E_SUCCESS) return retval; MAPIFreeBuffer(SPropTagArray); retval = QueryRows(&obj_table_attach, 0xA, TBL_ADVANCE, &SRowSet_attach); if (retval != MAPI_E_SUCCESS) return retval; for (j = 0; j < SRowSet_attach.cRows; j++) { attach_num = (const uint32_t *) find_SPropValue_data(&(SRowSet_attach.aRow[j]), PR_ATTACH_NUM); mapi_object_init(&obj_attach); retval = OpenAttach(&obj_message, *attach_num, &obj_attach); if (retval == MAPI_E_SUCCESS) { struct SPropValue *lpProps2; uint32_t count2; SPropTagArray = set_SPropTagArray(mem_ctx, 0x3, PR_ATTACH_FILENAME, PR_ATTACH_LONG_FILENAME, PR_ATTACH_SIZE); lpProps2 = talloc_zero(mem_ctx, struct SPropValue); retval = GetProps(&obj_attach, 0, SPropTagArray, &lpProps2, &count2); MAPIFreeBuffer(SPropTagArray); if (retval != MAPI_E_SUCCESS) { MAPIFreeBuffer(lpProps2); return retval; } MAPIFreeBuffer(lpProps2); mapi_object_init(&obj_stream); retval = OpenStream(&obj_attach, PR_ATTACH_DATA_BIN, 0, &obj_stream); if (retval != MAPI_E_SUCCESS) return retval; read_size = 0; do { retval = ReadStream(&obj_stream, buf, MAX_READ_SIZE, &read_size); if (retval != MAPI_E_SUCCESS) break; } while (read_size); mapi_object_release(&obj_stream); mapi_object_release(&obj_attach); } } } } MAPIFreeBuffer(lpProps); } mapi_object_release(&obj_message); }
static uint8_t exchange2ical_exception_from_EmbeddedObj(struct exchange2ical *exchange2ical, struct exchange2ical_check *exchange2ical_check) { mapi_object_t obj_tb_attach; mapi_object_t obj_attach; struct SRowSet rowset_attach; struct SPropTagArray *SPropTagArray; const uint32_t *attach_num; struct SPropValue *lpProps; enum MAPISTATUS retval; unsigned int i; uint32_t count; struct SRow aRow2; struct SRow aRowT; mapi_object_init(&obj_tb_attach); retval = GetAttachmentTable(&exchange2ical->obj_message, &obj_tb_attach); if (retval != MAPI_E_SUCCESS) { return 1; }else { SPropTagArray = set_SPropTagArray(exchange2ical->mem_ctx, 0x1, PR_ATTACH_NUM); retval = SetColumns(&obj_tb_attach, SPropTagArray); MAPIFreeBuffer(SPropTagArray); retval = QueryRows(&obj_tb_attach, 0xa, TBL_ADVANCE, TBL_FORWARD_READ, &rowset_attach); for (i = 0; i < rowset_attach.cRows; i++) { attach_num = (const uint32_t *)find_SPropValue_data(&(rowset_attach.aRow[i]), PR_ATTACH_NUM); retval = OpenAttach(&exchange2ical->obj_message, *attach_num, &obj_attach); if (retval != MAPI_E_SUCCESS) { return 1; }else { SPropTagArray = set_SPropTagArray(exchange2ical->mem_ctx, 0x3, PR_ATTACH_METHOD, PR_ATTACHMENT_FLAGS, PR_ATTACHMENT_HIDDEN ); lpProps = NULL; retval = GetProps(&obj_attach, 0, SPropTagArray, &lpProps, &count); MAPIFreeBuffer(SPropTagArray); if (retval != MAPI_E_SUCCESS) { return 1; }else { aRow2.ulAdrEntryPad = 0; aRow2.cValues = count; aRow2.lpProps = lpProps; uint32_t *attachmentFlags; uint32_t *attachMethod; uint8_t *attachmentHidden; attachmentFlags = (uint32_t *) octool_get_propval(&aRow2, PR_ATTACHMENT_FLAGS); attachMethod = (uint32_t *) octool_get_propval(&aRow2, PR_ATTACH_METHOD); attachmentHidden = (uint8_t *) octool_get_propval(&aRow2, PR_ATTACHMENT_HIDDEN); if(attachmentFlags && (*attachmentFlags & 0x00000002) && (*attachMethod == 0x00000005) && (attachmentHidden && (*attachmentHidden))) { struct exchange2ical exception; exchange2ical_init(exchange2ical->mem_ctx,&exception); mapi_object_init(&exception.obj_message); retval = OpenEmbeddedMessage(&obj_attach, &exception.obj_message, MAPI_READONLY); if (retval != MAPI_E_SUCCESS) { return 1; }else { SPropTagArray = set_SPropTagArray(exchange2ical->mem_ctx, 0x2d, PidLidFExceptionalBody, PidLidRecurring, PidLidAppointmentRecur, PidLidAppointmentStateFlags, PidLidTimeZoneDescription, PidLidTimeZoneStruct, PidLidAppointmentStartWhole, PidLidAppointmentEndWhole, PidLidAppointmentSubType, PidLidOwnerCriticalChange, PidLidLocation, PidLidExceptionReplaceTime, PidLidNonSendableBcc, PidLidAppointmentSequence, PidLidBusyStatus, PidLidIntendedBusyStatus, PidLidCleanGlobalObjectId, PidLidAttendeeCriticalChange, PidLidAppointmentReplyTime, PidLidAppointmentNotAllowPropose, PidLidAllowExternalCheck, PidLidAppointmentLastSequence, PidLidAppointmentSequenceTime, PidLidAutoFillLocation, PidLidAutoStartCheck, PidLidCollaborateDoc, PidLidConferencingCheck, PidLidConferencingType, PidLidDirectory, PidLidNetShowUrl, PidLidOnlinePassword, PidLidOrganizerAlias, PidLidReminderSet, PidLidReminderDelta, PR_MESSAGE_CLASS_UNICODE, PR_BODY_UNICODE, PR_CREATION_TIME, PR_LAST_MODIFICATION_TIME, PR_IMPORTANCE, PR_RESPONSE_REQUESTED, PR_SUBJECT_UNICODE, PR_OWNER_APPT_ID, PR_SENDER_NAME, PR_SENDER_EMAIL_ADDRESS, PR_MESSAGE_LOCALE_ID ); retval = GetProps(&exception.obj_message, MAPI_UNICODE, SPropTagArray, &lpProps, &count); if (retval == MAPI_E_SUCCESS) { aRow2.ulAdrEntryPad = 0; aRow2.cValues = count; aRow2.lpProps = lpProps; /*Get required properties to check if right event*/ exchange2ical_get_properties(exchange2ical->mem_ctx, &aRow2, &exception, exchange2ical_check->eFlags); /*Check to see if event is acceptable*/ if (!checkEvent(&exception, exchange2ical_check, get_tm_from_FILETIME(exception.apptStartWhole))){ break; } /*Grab Rest of Properties*/ exchange2ical_get_properties(exchange2ical->mem_ctx, &aRow2, &exception, exchange2ical_check->eFlags | EntireFlag); uint8_t *dBody = (uint8_t *) octool_get_propval(&aRow2, PidLidFExceptionalBody); retval = GetRecipientTable(&exception.obj_message, &exception.Recipients.SRowSet, &exception.Recipients.SPropTagArray); /*Check for set subject*/ if (!exception.Subject){ exception.Subject=exchange2ical->Subject; } /*Check for a set apptSubType*/ if (!exception.apptSubType){ exception.apptSubType=exchange2ical->apptSubType; } /*check for a set Location*/ if (!exception.Location){ exception.Location=exchange2ical->Location; } /*check for set valarm info*/ if(!exception.ReminderSet){ exception.ReminderSet=exchange2ical->ReminderSet; } if(!exception.ReminderDelta){ exception.ReminderDelta=exchange2ical->ReminderDelta; } /*Set to same vcalendar as parent*/ exception.vcalendar=exchange2ical->vcalendar; /*Set to same uid fallback in case GlobalObjId is missing*/ exception.idx=exchange2ical->idx; /*has a modified summary*/ if(dBody && *dBody){ SPropTagArray = set_SPropTagArray(exchange2ical->mem_ctx, 0x1, PR_BODY_HTML_UNICODE); retval = GetProps(&exception.obj_message, MAPI_UNICODE, SPropTagArray, &lpProps, &count); MAPIFreeBuffer(SPropTagArray); if (retval == MAPI_E_SUCCESS) { aRowT.ulAdrEntryPad = 0; aRowT.cValues = count; aRowT.lpProps = lpProps; exception.bodyHTML = (const char *)octool_get_propval(&aRowT, PR_BODY_HTML_UNICODE); } /* has the same summary as parent*/ } else{ exception.body=exchange2ical->body; exception.bodyHTML=exchange2ical->bodyHTML; } ical_component_VEVENT(&exception); exception.vcalendar=NULL; exchange2ical_clear(&exception); } } mapi_object_release(&exception.obj_message); } MAPIFreeBuffer(lpProps); } } } } mapi_object_release(&obj_tb_attach); return 0; }
void ical_property_ATTACH(struct exchange2ical *exchange2ical) { mapi_object_t obj_tb_attach; mapi_object_t obj_attach; mapi_object_t obj_stream; struct SRowSet rowset_attach; struct SPropTagArray *SPropTagArray = NULL; const uint32_t *attach_num = NULL; struct SPropValue *lpProps; enum MAPISTATUS retval; unsigned int i; uint32_t count; struct SRow aRow2; mapi_object_init(&obj_tb_attach); retval = GetAttachmentTable(&exchange2ical->obj_message, &obj_tb_attach); if (retval == MAPI_E_SUCCESS) { SPropTagArray = set_SPropTagArray(exchange2ical->mem_ctx, 0x1, PR_ATTACH_NUM); retval = SetColumns(&obj_tb_attach, SPropTagArray); MAPIFreeBuffer(SPropTagArray); retval = QueryRows(&obj_tb_attach, 0xa, TBL_ADVANCE, &rowset_attach); for (i = 0; i < rowset_attach.cRows; i++) { attach_num = (const uint32_t *)find_SPropValue_data(&(rowset_attach.aRow[i]), PR_ATTACH_NUM); retval = OpenAttach(&exchange2ical->obj_message, *attach_num, &obj_attach); if (retval == MAPI_E_SUCCESS) { SPropTagArray = set_SPropTagArray(exchange2ical->mem_ctx, 0x7, PR_ATTACH_FILENAME, PR_ATTACH_LONG_FILENAME, PR_ATTACH_METHOD, PR_ATTACHMENT_FLAGS, PR_ATTACHMENT_HIDDEN, PR_ATTACH_MIME_TAG, PR_ATTACH_DATA_BIN ); lpProps = NULL; retval = GetProps(&obj_attach, MAPI_UNICODE, SPropTagArray, &lpProps, &count); MAPIFreeBuffer(SPropTagArray); if (retval == MAPI_E_SUCCESS) { uint32_t *attachmentFlags = NULL; uint32_t *attachMethod = NULL; uint8_t *attachmentHidden = NULL; const char *data = NULL; const char *fmttype = NULL; const char *attach_filename = NULL; DATA_BLOB body; icalattach *icalattach = NULL; icalproperty *prop = NULL; icalparameter *param = NULL; aRow2.ulAdrEntryPad = 0; aRow2.cValues = count; aRow2.lpProps = lpProps; attachmentFlags = octool_get_propval(&aRow2, PR_ATTACHMENT_FLAGS); attachMethod = octool_get_propval(&aRow2, PR_ATTACH_METHOD); attachmentHidden = octool_get_propval(&aRow2, PR_ATTACHMENT_HIDDEN); if(attachmentFlags && !(*attachmentFlags & 0x00000007) && (*attachMethod == 0x00000001) && (!attachmentHidden || !(*attachmentHidden))) { /* Get data of attachment */ retval = OpenStream(&obj_attach, PR_ATTACH_DATA_BIN, 0, &obj_stream); retval = octool_get_stream(exchange2ical->mem_ctx, &obj_stream, &body); data=ldb_base64_encode(exchange2ical->mem_ctx, (const char *)body.data, body.length); /*Create a new icalattach from above data*/ #if HAVE_ICAL_0_46 /* the function signature for icalattach_new_from_data() changed in 0.46, released 2010-08-30 */ /* we can switch to just using the new signature after everyone has had a reasonable chance to update (say end of 2011) */ icalattach = icalattach_new_from_data(data, 0, 0); #else icalattach = icalattach_new_from_data((unsigned char *)data,0,0); #endif /*Add attach property to vevent component*/ prop = icalproperty_new_attach(icalattach); icalcomponent_add_property(exchange2ical->vevent, prop); /* Attachment filename for X-FILENAME parameter*/ attach_filename = get_filename(octool_get_propval(&aRow2, PR_ATTACH_LONG_FILENAME)); if (!attach_filename || (attach_filename && !strcmp(attach_filename, ""))) { attach_filename = get_filename(octool_get_propval(&aRow2, PR_ATTACH_FILENAME)); } /* fmttype parameter */ fmttype = (const char *) octool_get_propval(&aRow2, PR_ATTACH_MIME_TAG); if(fmttype) { param = icalparameter_new_fmttype(fmttype); icalproperty_add_parameter(prop, param); } /* ENCODING parameter */ param =icalparameter_new_encoding(ICAL_ENCODING_BASE64); icalproperty_add_parameter(prop,param); /* VALUE parameter */ param=icalparameter_new_value(ICAL_VALUE_BINARY); icalproperty_add_parameter(prop,param); /* X-FILENAME parameter */ param = icalparameter_new_x(attach_filename); icalparameter_set_xname(param,"X-FILENAME"); icalproperty_add_parameter(prop,param); } MAPIFreeBuffer(lpProps); } } } } mapi_object_release(&obj_tb_attach); }