Ejemplo n.º 1
0
        public static MessageObject CreateNewMessage(PSTFile file, FolderItemTypeName folderItemType, NodeID parentNodeID, Guid searchKey)
        {
            // [MS-PST] The following properties must be present in any valid Message object PC:
            PropertyContext pc = PropertyContext.CreateNewPropertyContext(file);

            pc.SetStringProperty(PropertyID.PidTagMessageClass, GetMessageClass(folderItemType));

            pc.SetInt32Property(PropertyID.PidTagMessageFlags, 0);
            pc.SetInt32Property(PropertyID.PidTagMessageStatus, 0);
            pc.SetDateTimeProperty(PropertyID.PidTagCreationTime, DateTime.UtcNow);
            pc.SetDateTimeProperty(PropertyID.PidTagLastModificationTime, DateTime.UtcNow);
            pc.SetDateTimeProperty(PropertyID.PidTagClientSubmitTime, DateTime.UtcNow);
            pc.SetDateTimeProperty(PropertyID.PidTagMessageDeliveryTime, DateTime.UtcNow);
            byte[] conversationIndex = ConversationIndexHeader.GenerateNewConversationIndex().GetBytes();
            pc.SetBytesProperty(PropertyID.PidTagConversationIndex, conversationIndex);

            // PidTagSearchKey is apparently a GUID
            pc.SetBytesProperty(PropertyID.PidTagSearchKey, LittleEndianConverter.GetBytes(searchKey));

            pc.SaveChanges();

            NodeID pcNodeID = file.Header.AllocateNextNodeID(NodeTypeName.NID_TYPE_NORMAL_MESSAGE);

            file.NodeBTree.InsertNodeEntry(pcNodeID, pc.DataTree, pc.SubnodeBTree, parentNodeID);

            // NOTE: According to [MS-PST], A Recipient Table MUST exist for any Message object,
            //       However, in practice even outlook itself does not always create it.
            PSTNode       pcNode  = new PSTNode(file, pcNodeID, pc.DataTree, pc.SubnodeBTree);
            MessageObject message = new MessageObject(pcNode);

            return(message);
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Caller must update its hierarchy table to include the new child
        /// </summary>
        public static PSTFolder CreateNewFolder(PSTFile file, string folderName, FolderItemTypeName folderItemType, NodeID parentNodeID)
        {
            // create the normal folder node
            PropertyContext pc = PropertyContext.CreateNewPropertyContext(file);

            pc.SetStringProperty(PropertyID.PidTagDisplayName, folderName);
            pc.SetInt32Property(PropertyID.PidTagContentCount, 0);
            pc.SetInt32Property(PropertyID.PidTagContentUnreadCount, 0);
            pc.SetBooleanProperty(PropertyID.PidTagSubfolders, false);
            pc.SetStringProperty(PropertyID.PidTagContainerClass, GetContainerClass(folderItemType));
            pc.SaveChanges();

            NodeID pcNodeID = file.Header.AllocateNextFolderNodeID();

            file.NodeBTree.InsertNodeEntry(pcNodeID, pc.DataTree, pc.SubnodeBTree, parentNodeID);
            PSTNode pcNode = new PSTNode(file, pcNodeID, pc.DataTree, pc.SubnodeBTree);

            // There is no need to create a new empty TC, we can simply point to the appropriate template
            // and only update the reference to another data tree during modification
            PSTNode hierarchyTableTemplateNode = file.GetNode(InternalNodeName.NID_HIERARCHY_TABLE_TEMPLATE);
            NodeID  hierarchyTableNodeID       = new NodeID(NodeTypeName.NID_TYPE_HIERARCHY_TABLE, pcNodeID.nidIndex);

            file.NodeBTree.InsertNodeEntry(hierarchyTableNodeID, hierarchyTableTemplateNode.DataTree, null, new NodeID(0));
            file.BlockBTree.IncrementBlockEntryReferenceCount(hierarchyTableTemplateNode.DataTree.RootBlock.BlockID);

            PSTNode contentsTableTemplateNode = file.GetNode(InternalNodeName.NID_CONTENTS_TABLE_TEMPLATE);
            NodeID  contentsTableNodeID       = new NodeID(NodeTypeName.NID_TYPE_CONTENTS_TABLE, pcNodeID.nidIndex);

            file.NodeBTree.InsertNodeEntry(contentsTableNodeID, contentsTableTemplateNode.DataTree, null, new NodeID(0));
            file.BlockBTree.IncrementBlockEntryReferenceCount(contentsTableTemplateNode.DataTree.RootBlock.BlockID);

            PSTNode associatedContentsTableTemplateNode = file.GetNode(InternalNodeName.NID_ASSOC_CONTENTS_TABLE_TEMPLATE);
            NodeID  associatedContentsTableNodeID       = new NodeID(NodeTypeName.NID_TYPE_ASSOC_CONTENTS_TABLE, pcNodeID.nidIndex);

            file.NodeBTree.InsertNodeEntry(associatedContentsTableNodeID, associatedContentsTableTemplateNode.DataTree, null, new NodeID(0));
            file.BlockBTree.IncrementBlockEntryReferenceCount(associatedContentsTableTemplateNode.DataTree.RootBlock.BlockID);

            PSTFolder folder = PSTFolder.GetFolder(pcNode);

            return(folder);
        }