diff --git a/ChangeLog b/ChangeLog index f56576038..bbc599857 100644 --- a/ChangeLog +++ b/ChangeLog @@ -17,6 +17,18 @@ 2011-07-13 Wolfgang Sourdeau + * OpenChange/MAPIStoreContext.m (-init): removed the messages + cache dictionary, as its purpose has been superseeded by the + features of the "POC api". + + * OpenChange/MAPIStoreSOGo.m (sogo_op_openmessage) + (sogo_op_createmessage): now return a "poc api"-compatible + object. + (sogo_op_savechangesmessage, sogo_op_submitmessage) + (sogo_op_modifyrecipients): replaced methods with pocop + implementations. + (sogo_op_*attach*): methods to their final form' + * OpenChange/NSObject+MAPIStore.m (MAPIStoreTallocWrapperDestroy): the object release now occurs within an NSAutoreleasePool. diff --git a/OpenChange/MAPIStoreAttachment.h b/OpenChange/MAPIStoreAttachment.h index 413d80062..5013fcede 100644 --- a/OpenChange/MAPIStoreAttachment.h +++ b/OpenChange/MAPIStoreAttachment.h @@ -25,6 +25,7 @@ #import "MAPIStoreObject.h" +@class NSData; @class MAPIStoreAttachmentMessage; @interface MAPIStoreAttachment : MAPIStoreObject @@ -35,10 +36,10 @@ - (void) setAID: (uint32_t) newAID; - (uint32_t) AID; -- (int) openEmbeddedMessage: (MAPIStoreAttachmentMessage **) message +- (int) openEmbeddedMessage: (MAPIStoreAttachmentMessage **) messagePtr withMID: (uint64_t *) mid - withMAPIStoreMsg: (struct mapistore_message *) mapistoreMsg - andFlags: (enum OpenEmbeddedMessage_OpenModeFlags) flags; + withMAPIStoreMsg: (struct mapistore_message **) mapistoreMsgPtr + inMemCtx: (TALLOC_CTX *) memCtx; /* helpers */ - (NSData *) mimeAttachTag; diff --git a/OpenChange/MAPIStoreAttachment.m b/OpenChange/MAPIStoreAttachment.m index 311a5b78d..738fe41e5 100644 --- a/OpenChange/MAPIStoreAttachment.m +++ b/OpenChange/MAPIStoreAttachment.m @@ -91,29 +91,33 @@ return rc; } -- (int) openEmbeddedMessage: (MAPIStoreAttachmentMessage **) message +- (int) openEmbeddedMessage: (MAPIStoreAttachmentMessage **) messagePtr withMID: (uint64_t *) mid - withMAPIStoreMsg: (struct mapistore_message *) mapistoreMsg - andFlags: (enum OpenEmbeddedMessage_OpenModeFlags) flags + withMAPIStoreMsg: (struct mapistore_message **) mapistoreMsgPtr + inMemCtx: (TALLOC_CTX *) memCtx { MAPIStoreAttachmentMessage *attMessage; MAPIStoreMapping *mapping; - - memset (mapistoreMsg, 0, sizeof (struct mapistore_message)); + struct mapistore_message *mapistoreMsg; + + mapistoreMsg = talloc_zero (memCtx, struct mapistore_message); mapping = [[self context] mapping]; attMessage = [self openEmbeddedMessage]; if (attMessage) - *mid = [mapping idFromURL: [attMessage url]]; - else if (flags == MAPI_CREATE) { - attMessage = [self createEmbeddedMessage]; - if (attMessage) - [mapping registerURL: [attMessage url] - withID: *mid]; + *mid = [mapping idFromURL: [attMessage url]]; + *messagePtr = attMessage; + *mapistoreMsgPtr = mapistoreMsg; } - *message = attMessage; + // else if (flags == MAPI_CREATE) + // { + // attMessage = [self createEmbeddedMessage]; + // if (attMessage) + // [mapping registerURL: [attMessage url] + // withID: *mid]; + // } return (attMessage ? MAPISTORE_SUCCESS : MAPISTORE_ERROR); } diff --git a/OpenChange/MAPIStoreCalendarMessage.m b/OpenChange/MAPIStoreCalendarMessage.m index f92b449d1..756736c49 100644 --- a/OpenChange/MAPIStoreCalendarMessage.m +++ b/OpenChange/MAPIStoreCalendarMessage.m @@ -410,8 +410,8 @@ _fillAppointmentRecurrencePattern (struct AppointmentRecurrencePattern *arp, return rc; } -- (void) openMessage: (struct mapistore_message *) msg - inMemCtx: (TALLOC_CTX *) memCtx +- (void) getMessageData: (struct mapistore_message **) dataPtr + inMemCtx: (TALLOC_CTX *) memCtx { NSString *text; NSArray *attendees; @@ -419,14 +419,15 @@ _fillAppointmentRecurrencePattern (struct AppointmentRecurrencePattern *arp, struct SRowSet *recipients; int count, max; iCalEvent *event; + struct mapistore_message *msgData; - [super openMessage: msg inMemCtx: memCtx]; + [super getMessageData: &msgData inMemCtx: memCtx]; event = [sogoObject component: NO secure: NO]; attendees = [event attendees]; max = [attendees count]; - recipients = talloc_zero (memCtx, struct SRowSet); + recipients = talloc_zero (msgData, struct SRowSet); recipients->cRows = max; recipients->aRow = talloc_array (recipients, struct SRow, max); for (count = 0; count < max; count++) @@ -463,7 +464,8 @@ _fillAppointmentRecurrencePattern (struct AppointmentRecurrencePattern *arp, [text asUnicodeInMemCtx: recipients->aRow]); } } - msg->recipients = recipients; + msgData->recipients = recipients; + *dataPtr = msgData; } - (void) save diff --git a/OpenChange/MAPIStoreContext.h b/OpenChange/MAPIStoreContext.h index 99909675c..407aed9f4 100644 --- a/OpenChange/MAPIStoreContext.h +++ b/OpenChange/MAPIStoreContext.h @@ -47,6 +47,7 @@ @class MAPIStoreAttachmentTable; @class MAPIStoreFolder; @class MAPIStoreMapping; +@class MAPIStoreMessage; @class MAPIStoreTable; @interface MAPIStoreContext : NSObject @@ -64,9 +65,6 @@ MAPIStoreFolder *baseFolder; - /* for active messages (NSDictionary instances) */ - NSMutableDictionary *messages; - /* for active folders (NSDictionary instances) */ NSMutableDictionary *folders; @@ -117,17 +115,15 @@ - (int) readCount: (uint32_t *) rowCount ofTableType: (uint8_t) tableType inFID: (uint64_t) fid; -- (int) openMessage: (struct mapistore_message *) msg +- (int) openMessage: (MAPIStoreMessage **) messagePtr + andMessageData: (struct mapistore_message **) dataPtr withMID: (uint64_t) mid inFID: (uint64_t) fid inMemCtx: (TALLOC_CTX *) memCtx; -- (int) createMessageWithMID: (uint64_t) mid - inFID: (uint64_t) fid - isAssociated: (BOOL) isAssociated; -- (int) saveChangesInMessageWithMID: (uint64_t) mid - andFlags: (uint8_t) flags; -- (int) submitMessageWithMID: (uint64_t) mid - andFlags: (uint8_t) flags; +- (int) createMessage: (MAPIStoreMessage **) messagePtr + withMID: (uint64_t) mid + inFID: (uint64_t) fid + isAssociated: (BOOL) isAssociated; - (int) getProperties: (struct SPropTagArray *) SPropTagArray ofTableType: (uint8_t) tableType inRow: (struct SRow *) aRow @@ -136,9 +132,6 @@ - (int) setPropertiesWithFMID: (uint64_t) fmid ofTableType: (uint8_t) tableType inRow: (struct SRow *) aRow; -- (int) modifyRecipientsWithMID: (uint64_t) mid - inRows: (struct ModifyRecipientRow *) rows - withCount: (NSUInteger) max; - (int) deleteMessageWithMID: (uint64_t) mid inFID: (uint64_t) fid withFlags: (uint8_t) flags; @@ -163,18 +156,6 @@ tableType: (uint8_t) tableType andHandleId: (uint32_t) handleId; -- (int) getAttachmentTable: (MAPIStoreAttachmentTable **) tablePtr - andRowCount: (uint32_t *) count - withMID: (uint64_t) mid; -- (int) getAttachment: (MAPIStoreAttachment **) attachmentPr - withAID: (uint32_t) aid - inMID: (uint64_t) mid; - - -- (int) createAttachment: (MAPIStoreAttachment **) attachmentPtr - inAID: (uint32_t *) aid - withMessage: (uint64_t) mid; - @end #endif /* MAPISTORECONTEXT_H */ diff --git a/OpenChange/MAPIStoreContext.m b/OpenChange/MAPIStoreContext.m index ca11e240e..455877c99 100644 --- a/OpenChange/MAPIStoreContext.m +++ b/OpenChange/MAPIStoreContext.m @@ -191,7 +191,6 @@ _prepareContextClass (struct mapistore_context *newMemCtx, { if ((self = [super init])) { - messages = [NSMutableDictionary new]; folders = [NSMutableDictionary new]; woContext = [WOContext contextWithRequest: nil]; [woContext retain]; @@ -238,7 +237,6 @@ _prepareContextClass (struct mapistore_context *newMemCtx, - (void) dealloc { - [messages release]; [folders release]; [cachedTable release]; [cachedFolder release]; @@ -644,51 +642,43 @@ _prepareContextClass (struct mapistore_context *newMemCtx, // [self logWithFormat: @"%@ --> %@", resStr, MAPIStringForRestrictionState (state)]; // } -- (int) openMessage: (struct mapistore_message *) msg +- (int) openMessage: (MAPIStoreMessage **) messagePtr + andMessageData: (struct mapistore_message **) dataPtr withMID: (uint64_t) mid inFID: (uint64_t) fid - inMemCtx: (TALLOC_CTX *) memCtx + inMemCtx: (TALLOC_CTX *) memCtx; { NSString *messageKey, *messageURL; MAPIStoreMessage *message; MAPIStoreFolder *folder; - NSNumber *midKey, *fidKey; - int rc; + NSNumber *fidKey; + int rc = MAPISTORE_ERR_NOT_FOUND; - midKey = [NSNumber numberWithUnsignedLongLong: mid]; - message = [messages objectForKey: midKey]; - if (message) - rc = MAPISTORE_SUCCESS; - else + messageURL = [mapping urlFromID: mid]; + if (messageURL) { - rc = MAPISTORE_ERR_NOT_FOUND; - - messageURL = [mapping urlFromID: mid]; - if (messageURL) + fidKey = [NSNumber numberWithUnsignedLongLong: fid]; + folder = [folders objectForKey: fidKey]; + messageKey = [self extractChildNameFromURL: messageURL + andFolderURLAt: NULL]; + message = [folder lookupChild: messageKey]; + if (message) { - fidKey = [NSNumber numberWithUnsignedLongLong: fid]; - folder = [folders objectForKey: fidKey]; - messageKey = [self extractChildNameFromURL: messageURL - andFolderURLAt: NULL]; - message = [folder lookupChild: messageKey]; - if (message) - { - [message openMessage: msg inMemCtx: memCtx]; - [messages setObject: message forKey: midKey]; - rc = MAPISTORE_SUCCESS; - } + [message getMessageData: dataPtr inMemCtx: memCtx]; + *messagePtr = message; + rc = MAPISTORE_SUCCESS; } } - [message setMAPIRetainCount: [message mapiRetainCount] + 1]; return rc; } -- (int) createMessageWithMID: (uint64_t) mid - inFID: (uint64_t) fid - isAssociated: (BOOL) isAssociated +- (int) createMessage: (MAPIStoreMessage **) messagePtr + withMID: (uint64_t) mid + inFID: (uint64_t) fid + isAssociated: (BOOL) isAssociated { - NSNumber *midKey, *fidKey; + NSNumber *fidKey; NSString *childURL; MAPIStoreMessage *message; MAPIStoreFolder *folder; @@ -697,9 +687,7 @@ _prepareContextClass (struct mapistore_context *newMemCtx, [self logWithFormat: @"METHOD '%s' -- mid: 0x%.16x, fid: 0x%.16x, associated: %d", __FUNCTION__, mid, fid, isAssociated]; - midKey = [NSNumber numberWithUnsignedLongLong: mid]; - message = [messages objectForKey: midKey]; - if (message) + if ([mapping urlFromID: mid]) rc = MAPISTORE_ERR_EXIST; else { @@ -710,24 +698,14 @@ _prepareContextClass (struct mapistore_context *newMemCtx, message = [folder createMessage: isAssociated]; if (message) { - [messages setObject: message forKey: midKey]; - [message setMAPIRetainCount: [message mapiRetainCount] + 1]; childURL = [NSString stringWithFormat: @"%@%@", [folder url], [message nameInContainer]]; [mapping registerURL: childURL withID: mid]; + *messagePtr = message; rc = MAPISTORE_SUCCESS; } else rc = MAPISTORE_ERROR; - - // { - // if (![folderURL hasSuffix: @"/"]) - // folderURL = [NSString stringWithFormat: @"%@/", folderURL]; - // messageURL = [NSString stringWithFormat: @"%@%@", folderURL, - // [message nameInContainer]]; - // [mapping registerURL: messageURL withID: mid]; - - } else rc = MAPISTORE_ERR_NOT_FOUND; @@ -736,129 +714,13 @@ _prepareContextClass (struct mapistore_context *newMemCtx, return rc; } -- (int) _saveOrSubmitChangesInMessageWithMID: (uint64_t) mid - andFlags: (uint8_t) flags - save: (BOOL) isSave -{ - int rc; - MAPIStoreMessage *message; - MAPIStoreFolder *folder; - NSNumber *midKey; - NSArray *activeTables; - NSUInteger count, max; - // NSArray *propKeys; - struct mapistore_object_notification_parameters *notif_parameters; - // uint16_t count, max; - uint64_t folderId; - - midKey = [NSNumber numberWithUnsignedLongLong: mid]; - message = [messages objectForKey: midKey]; - if (message) - { - rc = MAPISTORE_SUCCESS; - folder = (MAPIStoreFolder *) [message container]; - [self logWithFormat: @"folder for message is: %p", folder]; - if (isSave) - { - /* notifications */ - folderId = [folder objectId]; - - /* folder modified */ - notif_parameters - = talloc_zero(NULL, - struct mapistore_object_notification_parameters); - notif_parameters->object_id = folderId; - if ([message isNew]) - { - notif_parameters->tag_count = 3; - notif_parameters->tags = talloc_array (notif_parameters, - enum MAPITAGS, 3); - notif_parameters->tags[0] = PR_CONTENT_COUNT; - notif_parameters->tags[1] = PR_MESSAGE_SIZE; - notif_parameters->tags[2] = PR_NORMAL_MESSAGE_SIZE; - notif_parameters->new_message_count = true; - notif_parameters->message_count = [[folder messageKeys] count] + 1; - } - mapistore_push_notification (connInfo->mstore_ctx, - MAPISTORE_FOLDER, - MAPISTORE_OBJECT_MODIFIED, - notif_parameters); - talloc_free (notif_parameters); - - /* message created */ - if ([message isNew]) - { - notif_parameters - = talloc_zero(NULL, - struct mapistore_object_notification_parameters); - notif_parameters->object_id = [message objectId]; - notif_parameters->folder_id = folderId; - - notif_parameters->tag_count = 0xffff; - mapistore_push_notification (connInfo->mstore_ctx, - MAPISTORE_MESSAGE, - MAPISTORE_OBJECT_CREATED, - notif_parameters); - talloc_free (notif_parameters); - } - - /* we ensure the table caches are loaded so that old and new state - can be compared */ - activeTables = ([message isKindOfClass: MAPIStoreFAIMessageK] - ? [folder activeFAIMessageTables] - : [folder activeMessageTables]); - max = [activeTables count]; - for (count = 0; count < max; count++) - [[activeTables objectAtIndex: count] restrictedChildKeys]; - - [message save]; - - /* table modified */ - for (count = 0; count < max; count++) - [[activeTables objectAtIndex: count] - notifyChangesForChild: message]; - } - else - [message submit]; - [message setIsNew: NO]; - [message resetNewProperties]; - [folder cleanupCaches]; - } - else - rc = MAPISTORE_ERROR; - - return rc; -} - -- (int) saveChangesInMessageWithMID: (uint64_t) mid - andFlags: (uint8_t) flags -{ - [self logWithFormat: @"METHOD '%s' -- mid: 0x%.16x, flags: 0x%x", - __FUNCTION__, mid, flags]; - - return [self _saveOrSubmitChangesInMessageWithMID: mid - andFlags: flags - save: YES]; -} - -- (int) submitMessageWithMID: (uint64_t) mid - andFlags: (uint8_t) flags -{ - [self logWithFormat: @"METHOD '%s' -- mid: 0x%.16x, flags: 0x%x", - __FUNCTION__, mid, flags]; - - return [self _saveOrSubmitChangesInMessageWithMID: mid - andFlags: flags - save: NO]; -} - - (int) getProperties: (struct SPropTagArray *) sPropTagArray ofTableType: (uint8_t) tableType inRow: (struct SRow *) aRow withMID: (uint64_t) fmid inMemCtx: (TALLOC_CTX *) memCtx { - NSNumber *midKey; + NSNumber *fidKey; MAPIStoreObject *child; NSInteger count; void *propValue; @@ -871,10 +733,8 @@ _prepareContextClass (struct mapistore_context *newMemCtx, [self logWithFormat: @"METHOD '%s' -- fmid: 0x%.16x, tableType: %d", __FUNCTION__, fmid, tableType]; - midKey = [NSNumber numberWithUnsignedLongLong: fmid]; - child = [messages objectForKey: midKey]; - if (!child) - child = [folders objectForKey: midKey]; + fidKey = [NSNumber numberWithUnsignedLongLong: fmid]; + child = [folders objectForKey: fidKey]; if (child) { data = talloc_array (memCtx, struct mapistore_property_data, @@ -931,6 +791,7 @@ _prepareContextClass (struct mapistore_context *newMemCtx, else { [self errorWithFormat: @"no message/folder found for fmid %lld", fmid]; + abort(); rc = MAPI_E_INVALID_OBJECT; } @@ -989,47 +850,18 @@ _prepareContextClass (struct mapistore_context *newMemCtx, ofTableType: (uint8_t) tableType inRow: (struct SRow *) aRow { - MAPIStoreMessage *message; MAPIStoreFolder *folder; - NSMutableDictionary *properties; - NSNumber *fmidKey; - struct SPropValue *cValue; - NSUInteger counter; + NSNumber *fidKey; int rc; - [self logWithFormat: @"METHOD '%s' -- fmid: 0x%.16x, tableType: %d", + [self logWithFormat: @"METHOD '%s' -- fid: 0x%.16x, tableType: %d", __FUNCTION__, fmid, tableType]; - fmidKey = [NSNumber numberWithUnsignedLongLong: fmid]; + fidKey = [NSNumber numberWithUnsignedLongLong: fmid]; switch (tableType) { - case MAPISTORE_MESSAGE: - message = [messages objectForKey: fmidKey]; - if (message) - { - properties - = [NSMutableDictionary dictionaryWithCapacity: aRow->cValues]; - [self logWithFormat: @"fmid 0x%.16x found", fmid]; - for (counter = 0; counter < aRow->cValues; counter++) - { - cValue = aRow->lpProps + counter; - [properties setObject: NSObjectFromSPropValue (cValue) - forKey: MAPIPropertyKey (cValue->ulPropTag)]; - } - [message addNewProperties: properties]; - [self logWithFormat: @"(%s) message props after op", __PRETTY_FUNCTION__]; - MAPIStoreDumpMessageProperties (properties); - rc = MAPISTORE_SUCCESS; - } - else - { - [self errorWithFormat: @"fmid 0x%.16x *not* found (faking success)", - fmid]; - rc = MAPISTORE_SUCCESS; - } - break; case MAPISTORE_FOLDER: - folder = [folders objectForKey: fmidKey]; + folder = [folders objectForKey: fidKey]; if (folder) rc = [folder setProperties: aRow]; else @@ -1038,124 +870,14 @@ _prepareContextClass (struct mapistore_context *newMemCtx, default: [self errorWithFormat: @"%s: value of tableType not handled: %d", __FUNCTION__, tableType]; + [NSException raise: @"MAPIStoreIOException" + format: @"unsupported object type"]; rc = MAPISTORE_ERROR; } return rc; } -- (NSDictionary *) _convertRecipientFromRow: (struct RecipientRow *) row -{ - NSMutableDictionary *recipient; - NSString *value; - SOGoUser *recipientUser; - - recipient = [NSMutableDictionary dictionaryWithCapacity: 5]; - - if ((row->RecipientFlags & 0x07) == 1) - { - value = [NSString stringWithUTF8String: row->X500DN.recipient_x500name]; - [recipient setObject: value forKey: @"x500dn"]; - - recipientUser = [SOGoUser userWithLogin: [value lowercaseString]]; - if (recipientUser) - { - value = [recipientUser cn]; - if ([value length] > 0) - [recipient setObject: value forKey: @"fullName"]; - value = [[recipientUser allEmails] objectAtIndex: 0]; - if ([value length] > 0) - [recipient setObject: value forKey: @"email"]; - } - } - else - { - switch ((row->RecipientFlags & 0x208)) - { - case 0x08: - // TODO: we cheat - value = [NSString stringWithUTF8String: row->EmailAddress.lpszA]; - break; - case 0x208: - value = [NSString stringWithUTF8String: row->EmailAddress.lpszW]; - break; - default: - value = nil; - } - if (value) - [recipient setObject: value forKey: @"email"]; - - switch ((row->RecipientFlags & 0x210)) - { - case 0x10: - // TODO: we cheat - value = [NSString stringWithUTF8String: row->DisplayName.lpszA]; - break; - case 0x210: - value = [NSString stringWithUTF8String: row->DisplayName.lpszW]; - break; - default: - value = nil; - } - if (value) - [recipient setObject: value forKey: @"fullName"]; - } - - return recipient; -} - -- (int) modifyRecipientsWithMID: (uint64_t) mid - inRows: (struct ModifyRecipientRow *) rows - withCount: (NSUInteger) max -{ - static NSString *recTypes[] = { @"orig", @"to", @"cc", @"bcc" }; - MAPIStoreMessage *message; - NSDictionary *newProperties; - NSMutableDictionary *recipients; - NSMutableArray *list; - NSString *recType; - struct ModifyRecipientRow *currentRow; - NSUInteger count; - int rc; - - [self logWithFormat: @"METHOD '%s' -- mid: 0x%.16x", __FUNCTION__, mid]; - - message = [messages - objectForKey: [NSNumber numberWithUnsignedLongLong: mid]]; - if (message) - { - recipients = [NSMutableDictionary new]; - newProperties = [NSDictionary dictionaryWithObject: recipients - forKey: @"recipients"]; - [recipients release]; - for (count = 0; count < max; count++) - { - currentRow = rows + count; - - if (currentRow->RecipClass >= MAPI_ORIG - && currentRow->RecipClass < MAPI_BCC) - { - recType = recTypes[currentRow->RecipClass]; - list = [recipients objectForKey: recType]; - if (!list) - { - list = [NSMutableArray new]; - [recipients setObject: list forKey: recType]; - [list release]; - } - [list addObject: [self _convertRecipientFromRow: - &(currentRow->RecipientRow)]]; - } - } - [message addNewProperties: newProperties]; - rc = MAPISTORE_SUCCESS; - } - else - rc = MAPISTORE_ERR_NOT_FOUND; - - return rc; -} - - (int) deleteMessageWithMID: (uint64_t) mid inFID: (uint64_t) fid withFlags: (uint8_t) flags @@ -1263,32 +985,26 @@ _prepareContextClass (struct mapistore_context *newMemCtx, - (int) releaseRecordWithFMID: (uint64_t) fmid ofTableType: (uint8_t) tableType { - NSNumber *fmidKey; + NSNumber *fidKey; MAPIStoreObject *child; NSUInteger retainCount; - NSMutableDictionary *childCache; int rc = MAPISTORE_SUCCESS; - switch (tableType) + if (tableType != MAPISTORE_FOLDER_TABLE) { - case MAPISTORE_MESSAGE_TABLE: - childCache = messages; - break; - case MAPISTORE_FOLDER_TABLE: - childCache = folders; - break; - default: [self errorWithFormat: @"%s: value of tableType not handled: %d", __FUNCTION__, tableType]; [self logWithFormat: @" fmid: 0x%.16x tableType: %d", fmid, tableType]; + [NSException raise: @"MAPIStoreAPIException" + format: @"unsupported object type"]; rc = MAPISTORE_ERR_INVALID_PARAMETER; } if (rc == MAPISTORE_SUCCESS) { - fmidKey = [NSNumber numberWithUnsignedLongLong: fmid]; - child = [childCache objectForKey: fmidKey]; + fidKey = [NSNumber numberWithUnsignedLongLong: fmid]; + child = [folders objectForKey: fidKey]; if (child) { retainCount = [child mapiRetainCount]; @@ -1297,7 +1013,7 @@ _prepareContextClass (struct mapistore_context *newMemCtx, [self logWithFormat: @"child with mid %.16x successfully removed" @" from child cache", fmid]; - [childCache removeObjectForKey: fmidKey]; + [folders removeObjectForKey: fidKey]; } else [child setMAPIRetainCount: retainCount - 1]; @@ -1384,93 +1100,6 @@ _prepareContextClass (struct mapistore_context *newMemCtx, return MAPISTORE_SUCCESS; } -- (int) getAttachmentTable: (MAPIStoreAttachmentTable **) tablePtr - andRowCount: (uint32_t *) count - withMID: (uint64_t) mid -{ - MAPIStoreAttachmentTable *attTable; - MAPIStoreMessage *message; - NSNumber *midKey; - int rc; - - rc = MAPISTORE_ERR_NOT_FOUND; - - midKey = [NSNumber numberWithUnsignedLongLong: mid]; - message = [messages objectForKey: midKey]; - if (message) - { - *count = [[message childKeysMatchingQualifier: nil - andSortOrderings: nil] count]; - attTable = [message attachmentTable]; - if (attTable) - { - *tablePtr = attTable; - rc = MAPISTORE_SUCCESS; - } - } - - return rc; -} - -- (int) getAttachment: (MAPIStoreAttachment **) attachmentPtr - withAID: (uint32_t) aid - inMID: (uint64_t) mid -{ - MAPIStoreMessage *message; - MAPIStoreAttachment *attachment; - NSNumber *midKey; - NSArray *keys; - int rc; - - rc = MAPISTORE_ERR_NOT_FOUND; - - midKey = [NSNumber numberWithUnsignedLongLong: mid]; - message = [messages objectForKey: midKey]; - if (message) - { - keys = [message childKeysMatchingQualifier: nil - andSortOrderings: nil]; - if (aid < [keys count]) - { - attachment = [message lookupChild: [keys objectAtIndex: aid]]; - if (attachment) - { - *attachmentPtr = attachment; - rc = MAPISTORE_SUCCESS; - } - } - } - - return rc; -} - -- (int) createAttachment: (MAPIStoreAttachment **) attachmentPtr - inAID: (uint32_t *) aid - withMessage: (uint64_t) mid -{ - MAPIStoreMessage *message; - MAPIStoreAttachment *attachment; - NSNumber *midKey; - int rc; - - rc = MAPISTORE_ERR_NOT_FOUND; - - midKey = [NSNumber numberWithUnsignedLongLong: mid]; - message = [messages objectForKey: midKey]; - if (message) - { - attachment = [message createAttachment]; - if (attachment) - { - *attachmentPtr = attachment; - *aid = [attachment AID]; - rc = MAPISTORE_SUCCESS; - } - } - - return rc; -} - /* subclasses */ + (NSString *) MAPIModuleName diff --git a/OpenChange/MAPIStoreDraftsMessage.h b/OpenChange/MAPIStoreDraftsMessage.h index 926fab1e2..5e446d490 100644 --- a/OpenChange/MAPIStoreDraftsMessage.h +++ b/OpenChange/MAPIStoreDraftsMessage.h @@ -29,6 +29,8 @@ @interface MAPIStoreDraftsMessage : MAPIStoreMailMessage +- (int) submitWithFlags: (enum SubmitFlags) flags; + @end #endif /* MAPISTOREDRAFTSMESSAGE_H */ diff --git a/OpenChange/MAPIStoreDraftsMessage.m b/OpenChange/MAPIStoreDraftsMessage.m index f5d3e8bb0..7edc5d343 100644 --- a/OpenChange/MAPIStoreDraftsMessage.m +++ b/OpenChange/MAPIStoreDraftsMessage.m @@ -232,6 +232,16 @@ e) [self logWithFormat: @"ignored scheduling message"]; } +- (int) submitWithFlags: (enum SubmitFlags) flags +{ + [self submit]; + [self setIsNew: NO]; + [self resetNewProperties]; + [[self container] cleanupCaches]; + + return MAPISTORE_SUCCESS; +} + - (void) save { NSString *msgClass; diff --git a/OpenChange/MAPIStoreFAIMessage.m b/OpenChange/MAPIStoreFAIMessage.m index b1c2cc6f3..6a0d1ac94 100644 --- a/OpenChange/MAPIStoreFAIMessage.m +++ b/OpenChange/MAPIStoreFAIMessage.m @@ -20,10 +20,22 @@ * Boston, MA 02111-1307, USA. */ +#import "MAPIStoreActiveTables.h" + #import "MAPIStoreFAIMessage.h" +#undef DEBUG +#include + @implementation MAPIStoreFAIMessage +- (NSArray *) activeContainerMessageTables +{ + return [[MAPIStoreActiveTables activeTables] + activeTablesForFMID: [container objectId] + andType: MAPISTORE_FAI_TABLE]; +} + - (int) getPrAssociated: (void **) data inMemCtx: (TALLOC_CTX *) memCtx { diff --git a/OpenChange/MAPIStoreMailFolder.m b/OpenChange/MAPIStoreMailFolder.m index c0e47b722..392e13734 100644 --- a/OpenChange/MAPIStoreMailFolder.m +++ b/OpenChange/MAPIStoreMailFolder.m @@ -127,10 +127,7 @@ static Class SOGoMailFolderK; - (MAPIStoreMessageTable *) messageTable { if (!messageTable) - { - ASSIGN (messageTable, [MAPIStoreMailMessageTable tableForContainer: self]); - [self logWithFormat: @"new message table"]; - } + ASSIGN (messageTable, [MAPIStoreMailMessageTable tableForContainer: self]); return messageTable; } diff --git a/OpenChange/MAPIStoreMailMessage.m b/OpenChange/MAPIStoreMailMessage.m index 486d80246..607b682ef 100644 --- a/OpenChange/MAPIStoreMailMessage.m +++ b/OpenChange/MAPIStoreMailMessage.m @@ -695,20 +695,21 @@ static Class NSExceptionK, MAPIStoreSentItemsFolderK, MAPIStoreDraftsFolderK; return [self getYes: data inMemCtx: memCtx]; } -- (void) openMessage: (struct mapistore_message *) msg - inMemCtx: (TALLOC_CTX *) memCtx +- (void) getMessageData: (struct mapistore_message **) dataPtr + inMemCtx: (TALLOC_CTX *) memCtx { struct SRowSet *recipients; NSArray *to; NSInteger count, max; NGImap4EnvelopeAddress *currentAddress; NSString *text; + struct mapistore_message *msgData; - [super openMessage: msg inMemCtx: memCtx]; + [super getMessageData: &msgData inMemCtx: memCtx]; /* Retrieve recipients from the message */ to = [sogoObject toEnvelopeAddresses]; max = [to count]; - recipients = talloc_zero (memCtx, struct SRowSet); + recipients = talloc_zero (msgData, struct SRowSet); recipients->cRows = max; recipients->aRow = talloc_array (recipients, struct SRow, max); for (count = 0; count < max; count++) @@ -747,7 +748,8 @@ static Class NSExceptionK, MAPIStoreSentItemsFolderK, MAPIStoreDraftsFolderK; [text asUnicodeInMemCtx: recipients->aRow]); } } - msg->recipients = recipients; + msgData->recipients = recipients; + *dataPtr = msgData; } - (void) _fetchAttachmentPartsInBodyInfo: (NSDictionary *) bodyInfo diff --git a/OpenChange/MAPIStoreMessage.h b/OpenChange/MAPIStoreMessage.h index 74220bdba..b7a2dc254 100644 --- a/OpenChange/MAPIStoreMessage.h +++ b/OpenChange/MAPIStoreMessage.h @@ -41,15 +41,26 @@ NSMutableArray *activeTables; } -- (void) openMessage: (struct mapistore_message *) msg - inMemCtx: (TALLOC_CTX *) memCtx; +- (void) getMessageData: (struct mapistore_message **) dataPtr + inMemCtx: (TALLOC_CTX *) memCtx; + +- (int) modifyRecipientsWithRows: (struct ModifyRecipientRow *) rows + andCount: (NSUInteger) max; + +- (int) createAttachment: (MAPIStoreAttachment **) attachmentPtr + inAID: (uint32_t *) aidPtr; +- (int) getAttachment: (MAPIStoreAttachment **) attachmentPtr + withAID: (uint32_t) aid; +- (int) getAttachmentTable: (MAPIStoreAttachmentTable **) tablePtr + andRowCount: (uint32_t *) countPtr; +- (int) saveMessage; /* helper getters */ - (int) getSMTPAddrType: (void **) data inMemCtx: (TALLOC_CTX *) memCtx; +- (NSArray *) activeContainerMessageTables; /* subclasses */ -- (void) submit; - (void) save; /* attachments (subclasses) */ diff --git a/OpenChange/MAPIStoreMessage.m b/OpenChange/MAPIStoreMessage.m index 5df7399a6..d0fa797c1 100644 --- a/OpenChange/MAPIStoreMessage.m +++ b/OpenChange/MAPIStoreMessage.m @@ -21,13 +21,18 @@ */ #import +#import #import #import #import #import +#import +#import "MAPIStoreActiveTables.h" +#import "MAPIStoreAttachment.h" #import "MAPIStoreAttachmentTable.h" #import "MAPIStoreContext.h" +#import "MAPIStoreFolder.h" #import "MAPIStoreTypes.h" #import "NSData+MAPIStore.h" #import "NSString+MAPIStore.h" @@ -70,8 +75,8 @@ [super dealloc]; } -- (void) openMessage: (struct mapistore_message *) msg - inMemCtx: (TALLOC_CTX *) memCtx +- (void) getMessageData: (struct mapistore_message **) dataPtr + inMemCtx: (TALLOC_CTX *) memCtx { static enum MAPITAGS tags[] = { PR_SUBJECT_PREFIX_UNICODE, PR_NORMALIZED_SUBJECT_UNICODE }; @@ -80,23 +85,26 @@ NSInteger count, max; const char *propName; void *propValue; + struct mapistore_message *msgData; // [self logWithFormat: @"INCOMPLETE METHOD '%s' (%d): no recipient handling", // __FUNCTION__, __LINE__]; - recipients = talloc_zero (memCtx, struct SRowSet); + msgData = talloc_zero (memCtx, struct mapistore_message); + + recipients = talloc_zero (msgData, struct SRowSet); recipients->cRows = 0; recipients->aRow = NULL; - msg->recipients = recipients; + msgData->recipients = recipients; max = 2; - properties = talloc_zero (memCtx, struct SRow); + properties = talloc_zero (msgData, struct SRow); properties->cValues = 0; properties->ulAdrEntryPad = 0; properties->lpProps = talloc_array (properties, struct SPropValue, max); for (count = 0; count < max; count++) { - if ([self getProperty: &propValue withTag: tags[count] inMemCtx: memCtx] + if ([self getProperty: &propValue withTag: tags[count] inMemCtx: msgData] == MAPI_E_SUCCESS) { if (propValue == NULL) @@ -117,7 +125,246 @@ } } } - msg->properties = properties; + msgData->properties = properties; + *dataPtr = msgData; +} + +- (NSDictionary *) _convertRecipientFromRow: (struct RecipientRow *) row +{ + NSMutableDictionary *recipient; + NSString *value; + SOGoUser *recipientUser; + + recipient = [NSMutableDictionary dictionaryWithCapacity: 5]; + + if ((row->RecipientFlags & 0x07) == 1) + { + value = [NSString stringWithUTF8String: row->X500DN.recipient_x500name]; + [recipient setObject: value forKey: @"x500dn"]; + + recipientUser = [SOGoUser userWithLogin: [value lowercaseString]]; + if (recipientUser) + { + value = [recipientUser cn]; + if ([value length] > 0) + [recipient setObject: value forKey: @"fullName"]; + value = [[recipientUser allEmails] objectAtIndex: 0]; + if ([value length] > 0) + [recipient setObject: value forKey: @"email"]; + } + } + else + { + switch ((row->RecipientFlags & 0x208)) + { + case 0x08: + // TODO: we cheat + value = [NSString stringWithUTF8String: row->EmailAddress.lpszA]; + break; + case 0x208: + value = [NSString stringWithUTF8String: row->EmailAddress.lpszW]; + break; + default: + value = nil; + } + if (value) + [recipient setObject: value forKey: @"email"]; + + switch ((row->RecipientFlags & 0x210)) + { + case 0x10: + // TODO: we cheat + value = [NSString stringWithUTF8String: row->DisplayName.lpszA]; + break; + case 0x210: + value = [NSString stringWithUTF8String: row->DisplayName.lpszW]; + break; + default: + value = nil; + } + if (value) + [recipient setObject: value forKey: @"fullName"]; + } + + return recipient; +} + +- (int) modifyRecipientsWithRows: (struct ModifyRecipientRow *) rows + andCount: (NSUInteger) max +{ + static NSString *recTypes[] = { @"orig", @"to", @"cc", @"bcc" }; + NSDictionary *recipientProperties; + NSMutableDictionary *recipients; + NSMutableArray *list; + NSString *recType; + struct ModifyRecipientRow *currentRow; + NSUInteger count; + + [self logWithFormat: @"METHOD '%s'", __FUNCTION__]; + + recipients = [NSMutableDictionary new]; + recipientProperties = [NSDictionary dictionaryWithObject: recipients + forKey: @"recipients"]; + [recipients release]; + + for (count = 0; count < max; count++) + { + currentRow = rows + count; + + if (currentRow->RecipClass >= MAPI_ORIG + && currentRow->RecipClass < MAPI_BCC) + { + recType = recTypes[currentRow->RecipClass]; + list = [recipients objectForKey: recType]; + if (!list) + { + list = [NSMutableArray new]; + [recipients setObject: list forKey: recType]; + [list release]; + } + [list addObject: [self _convertRecipientFromRow: + &(currentRow->RecipientRow)]]; + } + } + [self addNewProperties: recipientProperties]; + + return MAPISTORE_SUCCESS; +} + +- (int) createAttachment: (MAPIStoreAttachment **) attachmentPtr + inAID: (uint32_t *) aidPtr +{ + MAPIStoreAttachment *attachment; + int rc = MAPISTORE_SUCCESS; + + attachment = [self createAttachment]; + if (attachment) + { + *attachmentPtr = attachment; + *aidPtr = [attachment AID]; + } + else + rc = MAPISTORE_ERR_NOT_FOUND; + + return rc; +} + +- (int) getAttachment: (MAPIStoreAttachment **) attachmentPtr + withAID: (uint32_t) aid +{ + MAPIStoreAttachment *attachment; + NSArray *keys; + int rc = MAPISTORE_ERR_NOT_FOUND; + + keys = [self childKeysMatchingQualifier: nil + andSortOrderings: nil]; + if (aid < [keys count]) + { + attachment = [self lookupChild: [keys objectAtIndex: aid]]; + if (attachment) + { + *attachmentPtr = attachment; + rc = MAPISTORE_SUCCESS; + } + } + + return rc; +} + +- (int) getAttachmentTable: (MAPIStoreAttachmentTable **) tablePtr + andRowCount: (uint32_t *) countPtr +{ + MAPIStoreAttachmentTable *attTable; + int rc = MAPISTORE_SUCCESS; + + attTable = [self attachmentTable]; + if (attTable) + { + *tablePtr = attTable; + *countPtr = [[self childKeysMatchingQualifier: nil + andSortOrderings: nil] + count]; + } + else + rc = MAPISTORE_ERR_NOT_FOUND; + + return rc; +} + +- (NSArray *) activeContainerMessageTables +{ + return [[MAPIStoreActiveTables activeTables] + activeTablesForFMID: [container objectId] + andType: MAPISTORE_MESSAGE_TABLE]; +} + +- (int) saveMessage +{ + NSArray *containerTables; + NSUInteger count, max; + struct mapistore_object_notification_parameters *notif_parameters; + uint64_t folderId; + struct mapistore_context *mstoreCtx; + + /* notifications */ + folderId = [(MAPIStoreFolder *) container objectId]; + mstoreCtx = [[self context] connectionInfo]->mstore_ctx; + + /* folder modified */ + notif_parameters + = talloc_zero(NULL, struct mapistore_object_notification_parameters); + notif_parameters->object_id = folderId; + if (isNew) + { + notif_parameters->tag_count = 3; + notif_parameters->tags = talloc_array (notif_parameters, + enum MAPITAGS, 3); + notif_parameters->tags[0] = PR_CONTENT_COUNT; + notif_parameters->tags[1] = PR_MESSAGE_SIZE; + notif_parameters->tags[2] = PR_NORMAL_MESSAGE_SIZE; + notif_parameters->new_message_count = true; + notif_parameters->message_count + = [[(MAPIStoreFolder *) container messageKeys] count] + 1; + } + mapistore_push_notification (mstoreCtx, + MAPISTORE_FOLDER, MAPISTORE_OBJECT_MODIFIED, + notif_parameters); + talloc_free (notif_parameters); + + /* message created */ + if (isNew) + { + notif_parameters + = talloc_zero(NULL, + struct mapistore_object_notification_parameters); + notif_parameters->object_id = [self objectId]; + notif_parameters->folder_id = folderId; + + notif_parameters->tag_count = 0xffff; + mapistore_push_notification (mstoreCtx, + MAPISTORE_MESSAGE, MAPISTORE_OBJECT_CREATED, + notif_parameters); + talloc_free (notif_parameters); + } + + /* we ensure the table caches are loaded so that old and new state + can be compared */ + containerTables = [self activeContainerMessageTables]; + max = [containerTables count]; + for (count = 0; count < max; count++) + [[containerTables objectAtIndex: count] restrictedChildKeys]; + + [self save]; + + /* table modified */ + for (count = 0; count < max; count++) + [[containerTables objectAtIndex: count] + notifyChangesForChild: self]; + [self setIsNew: NO]; + [self resetNewProperties]; + [container cleanupCaches]; + + return MAPISTORE_SUCCESS; } /* helper getters */ @@ -361,7 +608,7 @@ { NSURL *contextUrl; - contextUrl = [[self context] url]; + contextUrl = (NSURL *) [[self context] url]; *data = [[contextUrl user] asUnicodeInMemCtx: memCtx]; return MAPISTORE_SUCCESS; @@ -402,11 +649,6 @@ [self subclassResponsibility: _cmd]; } -- (void) submit -{ - [self subclassResponsibility: _cmd]; -} - - (MAPIStoreAttachment *) createAttachment { [self subclassResponsibility: _cmd]; diff --git a/OpenChange/MAPIStoreObject.m b/OpenChange/MAPIStoreObject.m index 422ac191a..da4179912 100644 --- a/OpenChange/MAPIStoreObject.m +++ b/OpenChange/MAPIStoreObject.m @@ -105,6 +105,8 @@ static Class NSExceptionK, MAPIStoreFolderK; isNew = NO; } + [self logWithFormat: @"-init"]; + return self; } @@ -122,6 +124,7 @@ static Class NSExceptionK, MAPIStoreFolderK; - (void) dealloc { + [self logWithFormat: @"-dealloc"]; [sogoObject release]; [newProperties release]; [parentContainersBag release]; diff --git a/OpenChange/MAPIStoreSOGo.m b/OpenChange/MAPIStoreSOGo.m index 8cd4bb300..82ed10966 100644 --- a/OpenChange/MAPIStoreSOGo.m +++ b/OpenChange/MAPIStoreSOGo.m @@ -33,6 +33,8 @@ #import "MAPIApplication.h" #import "MAPIStoreAttachment.h" #import "MAPIStoreContext.h" +#import "MAPIStoreDraftsMessage.h" +#import "MAPIStoreMessage.h" #import "MAPIStoreObject.h" #import "MAPIStoreTable.h" #import "NSObject+MAPIStore.h" @@ -406,11 +408,13 @@ sogo_op_openmessage(void *private_data, TALLOC_CTX *mem_ctx, uint64_t fid, uint64_t mid, - struct mapistore_message *msg) + void **message_object, + struct mapistore_message **msgp) { NSAutoreleasePool *pool; sogo_context *cContext; MAPIStoreContext *context; + MAPIStoreMessage *message; int rc; DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); @@ -423,9 +427,11 @@ sogo_op_openmessage(void *private_data, if (!context) DEBUG (5, (" context data is empty, failure ahead...")); - rc = [context openMessage: msg withMID: mid inFID: fid inMemCtx: mem_ctx]; + rc = [context openMessage: &message andMessageData: msgp withMID: mid inFID: fid inMemCtx: mem_ctx]; if (rc) DEBUG (5, (" failure opening message\n")); + else + *message_object = [message tallocWrapper: mem_ctx]; [context tearDownRequest]; [pool release]; @@ -433,16 +439,18 @@ sogo_op_openmessage(void *private_data, return rc; } - static int sogo_op_createmessage(void *private_data, + TALLOC_CTX *mem_ctx, uint64_t fid, uint64_t mid, - uint8_t associated) + uint8_t associated, + void **message_object) { NSAutoreleasePool *pool; sogo_context *cContext; MAPIStoreContext *context; + MAPIStoreMessage *message; int rc; DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); @@ -453,60 +461,11 @@ sogo_op_createmessage(void *private_data, context = cContext->objcContext; [context setupRequest]; - rc = [context createMessageWithMID: mid inFID: fid - isAssociated: associated]; - - [context tearDownRequest]; - [pool release]; - - return rc; -} - -static int -sogo_op_savechangesmessage(void *private_data, - uint64_t mid, - uint8_t flags) -{ - NSAutoreleasePool *pool; - sogo_context *cContext; - MAPIStoreContext *context; - int rc; - - DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); - - pool = [NSAutoreleasePool new]; - - cContext = private_data; - context = cContext->objcContext; - [context setupRequest]; - - rc = [context saveChangesInMessageWithMID: mid andFlags: flags]; - - [context tearDownRequest]; - [pool release]; - - return rc; -} - -static int -sogo_op_submitmessage(void *private_data, - uint64_t mid, - uint8_t flags) -{ - NSAutoreleasePool *pool; - sogo_context *cContext; - MAPIStoreContext *context; - int rc; - - DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); - - pool = [NSAutoreleasePool new]; - - cContext = private_data; - context = cContext->objcContext; - [context setupRequest]; - - rc = [context submitMessageWithMID: mid andFlags: flags]; + rc = [context createMessage: &message + withMID: mid inFID: fid + isAssociated: associated]; + if (!rc) + *message_object = [message tallocWrapper: mem_ctx]; [context tearDownRequest]; [pool release]; @@ -575,35 +534,6 @@ sogo_op_setprops(void *private_data, return rc; } -static int -sogo_op_modifyrecipients(void *private_data, - uint64_t mid, - struct ModifyRecipientRow *rows, - uint16_t count) -{ - NSAutoreleasePool *pool; - sogo_context *cContext; - MAPIStoreContext *context; - int rc; - - DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); - - pool = [NSAutoreleasePool new]; - - cContext = private_data; - context = cContext->objcContext; - [context setupRequest]; - - rc = [context modifyRecipientsWithMID: mid - inRows: rows - withCount: count]; - - [context tearDownRequest]; - [pool release]; - - return rc; -} - static int sogo_op_deletemessage(void *private_data, uint64_t fid, @@ -675,67 +605,93 @@ sogo_pocop_open_table(void *private_data, TALLOC_CTX *mem_ctx, } static int -sogo_pocop_get_attachment_table (void *private_data, TALLOC_CTX *mem_ctx, uint64_t mid, void **table_object, uint32_t *row_count) +sogo_pocop_create_attachment (void *message_object, TALLOC_CTX *mem_ctx, void **attachment_object, uint32_t *aidp) { + struct MAPIStoreTallocWrapper *wrapper; NSAutoreleasePool *pool; - sogo_context *cContext; - MAPIStoreContext *context; + MAPIStoreMessage *message; + MAPIStoreAttachment *attachment; + int rc; + + DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); + + if (message_object) + { + wrapper = message_object; + message = wrapper->MAPIStoreSOGoObject; + pool = [NSAutoreleasePool new]; + rc = [message createAttachment: &attachment inAID: aidp]; + if (rc == MAPISTORE_SUCCESS) + *attachment_object = [attachment tallocWrapper: mem_ctx]; + // [context tearDownRequest]; + [pool release]; + } + else + { + NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO OBJECT"); + rc = MAPI_E_NOT_FOUND; + } + + return rc; +} + +static int +sogo_pocop_get_attachment (void *message_object, TALLOC_CTX *mem_ctx, uint32_t aid, void **attachment_object) +{ + struct MAPIStoreTallocWrapper *wrapper; + NSAutoreleasePool *pool; + MAPIStoreMessage *message; + MAPIStoreAttachment *attachment; + int rc; + + DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); + + if (message_object) + { + wrapper = message_object; + message = wrapper->MAPIStoreSOGoObject; + pool = [NSAutoreleasePool new]; + rc = [message getAttachment: &attachment withAID: aid]; + if (rc == MAPISTORE_SUCCESS) + *attachment_object = [attachment tallocWrapper: mem_ctx]; + // [context tearDownRequest]; + [pool release]; + } + else + { + NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO OBJECT"); + rc = MAPI_E_NOT_FOUND; + } + + return rc; +} + +static int +sogo_pocop_get_attachment_table (void *message_object, TALLOC_CTX *mem_ctx, void **table_object, uint32_t *row_count) +{ + struct MAPIStoreTallocWrapper *wrapper; + NSAutoreleasePool *pool; + MAPIStoreMessage *message; MAPIStoreAttachmentTable *table; int rc; DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); - pool = [NSAutoreleasePool new]; - - cContext = private_data; - context = cContext->objcContext; - if (context) + if (message_object) { - [context setupRequest]; - rc = [context getAttachmentTable: &table - andRowCount: row_count - withMID: mid]; - *table_object = [table tallocWrapper: mem_ctx]; - [context tearDownRequest]; - } - else - { - NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO CONTEXT"); - rc = MAPI_E_NOT_FOUND; - } - - [pool release]; - - return rc; -} - -static int -sogo_pocop_get_attachment (void *private_data, TALLOC_CTX *mem_ctx, uint64_t mid, uint32_t aid, void **attachment_object) -{ - NSAutoreleasePool *pool; - sogo_context *cContext; - MAPIStoreContext *context; - MAPIStoreAttachment *attachment; - int rc; - - DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); - - pool = [NSAutoreleasePool new]; - - cContext = private_data; - context = cContext->objcContext; - if (context) - { - [context setupRequest]; - rc = [context getAttachment: &attachment withAID: aid inMID: mid]; + wrapper = message_object; + message = wrapper->MAPIStoreSOGoObject; + pool = [NSAutoreleasePool new]; + rc = [message getAttachmentTable: &table + andRowCount: row_count]; if (rc == MAPISTORE_SUCCESS) - *attachment_object = [attachment tallocWrapper: mem_ctx]; - [context tearDownRequest]; + *table_object = [table tallocWrapper: mem_ctx]; + // [context tearDownRequest]; [pool release]; } else { - NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO CONTEXT"); + NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO OBJECT"); rc = MAPI_E_NOT_FOUND; } @@ -743,33 +699,85 @@ sogo_pocop_get_attachment (void *private_data, TALLOC_CTX *mem_ctx, uint64_t mid } static int -sogo_pocop_create_attachment (void *private_data, TALLOC_CTX *mem_ctx, uint64_t mid, uint32_t *aid, void **attachment_object) +sogo_pocop_message_modify_recipients (void *message_object, + struct ModifyRecipientRow *recipients, + uint16_t count) { + struct MAPIStoreTallocWrapper *wrapper; NSAutoreleasePool *pool; - sogo_context *cContext; - MAPIStoreContext *context; - MAPIStoreAttachment *attachment; + MAPIStoreMessage *message; int rc; DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); - pool = [NSAutoreleasePool new]; - - cContext = private_data; - context = cContext->objcContext; - if (context) + if (message_object) { - [context setupRequest]; - rc = [context createAttachment: &attachment inAID: aid - withMessage: mid]; - if (rc == MAPISTORE_SUCCESS) - *attachment_object = [attachment tallocWrapper: mem_ctx]; - [context tearDownRequest]; + wrapper = message_object; + message = wrapper->MAPIStoreSOGoObject; + pool = [NSAutoreleasePool new]; + rc = [message modifyRecipientsWithRows: recipients andCount: count]; + // [context tearDownRequest]; [pool release]; } else { - NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO CONTEXT"); + NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO OBJECT"); + rc = MAPI_E_NOT_FOUND; + } + + return rc; +} + +static int +sogo_pocop_message_save (void *message_object) +{ + struct MAPIStoreTallocWrapper *wrapper; + NSAutoreleasePool *pool; + MAPIStoreMessage *message; + int rc; + + DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); + + if (message_object) + { + wrapper = message_object; + message = wrapper->MAPIStoreSOGoObject; + pool = [NSAutoreleasePool new]; + rc = [message saveMessage]; + // [context tearDownRequest]; + [pool release]; + } + else + { + NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO OBJECT"); + rc = MAPI_E_NOT_FOUND; + } + + return rc; +} + +static int +sogo_pocop_message_submit (void *message_object, enum SubmitFlags flags) +{ + struct MAPIStoreTallocWrapper *wrapper; + NSAutoreleasePool *pool; + MAPIStoreDraftsMessage *message; + int rc; + + DEBUG (5, ("[SOGo: %s:%d]\n", __FUNCTION__, __LINE__)); + + if (message_object) + { + wrapper = message_object; + message = wrapper->MAPIStoreSOGoObject; + pool = [NSAutoreleasePool new]; + rc = [message submitWithFlags: flags]; + // [context tearDownRequest]; + [pool release]; + } + else + { + NSLog (@" UNEXPECTED WEIRDNESS: RECEIVED NO OBJECT"); rc = MAPI_E_NOT_FOUND; } @@ -778,9 +786,9 @@ sogo_pocop_create_attachment (void *private_data, TALLOC_CTX *mem_ctx, uint64_t static int sogo_pocop_open_embedded_message (void *attachment_object, - TALLOC_CTX *mem_ctx, - uint64_t *mid, enum OpenEmbeddedMessage_OpenModeFlags flags, - struct mapistore_message *msg, void **message_object) + TALLOC_CTX *mem_ctx, void **message_object, + uint64_t *midP, + struct mapistore_message **msg) { struct MAPIStoreTallocWrapper *wrapper; NSAutoreleasePool *pool; @@ -798,8 +806,9 @@ sogo_pocop_open_embedded_message (void *attachment_object, attachment = wrapper->MAPIStoreSOGoObject; pool = [NSAutoreleasePool new]; rc = [attachment openEmbeddedMessage: &message - withMID: mid - withMAPIStoreMsg: msg andFlags: flags]; + withMID: midP + withMAPIStoreMsg: msg + inMemCtx: mem_ctx]; if (rc == MAPISTORE_SUCCESS) *message_object = [message tallocWrapper: mem_ctx]; [pool release]; @@ -1081,9 +1090,6 @@ int mapistore_init_backend(void) backend.op_readdir_count = sogo_op_readdir_count; backend.op_openmessage = sogo_op_openmessage; backend.op_createmessage = sogo_op_createmessage; - backend.op_modifyrecipients = sogo_op_modifyrecipients; - backend.op_savechangesmessage = sogo_op_savechangesmessage; - backend.op_submitmessage = sogo_op_submitmessage; backend.op_deletemessage = sogo_op_deletemessage; backend.op_setprops = sogo_op_setprops; @@ -1091,10 +1097,13 @@ int mapistore_init_backend(void) /* proof of concept */ backend.folder.open_table = sogo_pocop_open_table; + backend.message.create_attachment = sogo_pocop_create_attachment; backend.message.get_attachment_table = sogo_pocop_get_attachment_table; backend.message.get_attachment = sogo_pocop_get_attachment; - backend.message.create_attachment = sogo_pocop_create_attachment; backend.message.open_embedded_message = sogo_pocop_open_embedded_message; + backend.message.modify_recipients = sogo_pocop_message_modify_recipients; + backend.message.save = sogo_pocop_message_save; + backend.message.submit = sogo_pocop_message_submit; backend.table.get_available_properties = sogo_pocop_get_available_table_properties; backend.table.set_restrictions = sogo_pocop_set_table_restrictions; backend.table.set_sort_order = sogo_pocop_set_table_sort_order; diff --git a/OpenChange/MAPIStoreTable.m b/OpenChange/MAPIStoreTable.m index ead1eced6..917f86b67 100644 --- a/OpenChange/MAPIStoreTable.m +++ b/OpenChange/MAPIStoreTable.m @@ -303,6 +303,12 @@ static Class NSDataK, NSStringK; return self; } +- (id) retain +{ + [self logWithFormat: @"-retain"]; + return [super retain]; +} + - (void) dealloc { if (container)