public void MSOXCFOLD_S05_TC02_MessageDeletePartialCompleteValidation()
        {
            this.CheckWhetherSupportTransport();
            this.Adapter.DoConnect(ConnectionType.PrivateMailboxServer);
            uint logonHandle = 0;
            uint pidTagMemberRights = 0;

            this.GenericFolderInitialization();

            #region Step 1. Add permission entry for the user configured by "CommonUser" on the inbox and the root folder.
            uint inboxHandle = 0;
            this.OpenFolder(this.LogonHandle, this.DefaultFolderIds[this.inboxIndex], ref inboxHandle);

            // Add folder visible permission for the inbox.
            pidTagMemberRights = (uint)PidTagMemberRightsEnum.FolderVisible | (uint)PidTagMemberRightsEnum.ReadAny;
            this.AddPermission(this.commonUserEssdn, pidTagMemberRights, inboxHandle);

            // Add folder visible permission for the root folder.
            pidTagMemberRights = (uint)PidTagMemberRightsEnum.FolderVisible | (uint)PidTagMemberRightsEnum.ReadAny | (uint)PidTagMemberRightsEnum.EditOwned | (uint)PidTagMemberRightsEnum.Create | (uint)PidTagMemberRightsEnum.CreateSubFolder | (uint)PidTagMemberRightsEnum.DeleteOwned;
            this.AddPermission(this.commonUserEssdn, pidTagMemberRights, this.RootFolderHandle);
            #endregion

            #region Step 2. Create message and subfolder in the root folder.
            ulong messageId = 0;
            uint messageHandle = 0;
            this.CreateSaveMessage(this.RootFolderHandle, this.RootFolderId, ref messageId, ref messageHandle);

            uint subfolderHandle = 0;
            ulong subfolderId = 0;
            this.CreateFolder(this.RootFolderHandle, Constants.Subfolder1, ref subfolderId, ref subfolderHandle);
            #endregion

            #region Step 3. Logon the user configured by "CommonUser".
            this.Adapter.DoDisconnect();
            this.Adapter.DoConnect(this.sutServer, ConnectionType.PrivateMailboxServer, this.commonUserEssdn, this.domain, this.commonUser, this.commonUserPassword);
            this.Logon(LogonFlags.Private, out logonHandle, (uint)OpenFlags.UsePerMDBReplipMapping);
            #endregion

            #region Step 4. The "CommonUser" opens the root folder.
            this.OpenFolder(logonHandle, this.DefaultFolderIds[this.inboxIndex], ref inboxHandle);

            ulong rootFolderId = this.GetSubfolderIDByName(this.DefaultFolderIds[this.inboxIndex], logonHandle, this.RootFolder);
            uint rootFolderHandle = 0;
            RopOpenFolderResponse openFolderResponse = this.OpenFolder(logonHandle, rootFolderId, ref rootFolderHandle);

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R46202");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R46202
            Site.CaptureRequirementIfAreEqual<uint>(
                Constants.SuccessCode,
                openFolderResponse.ReturnValue,
                46202,
                @"[In Processing a RopOpenFolder ROP Request] If the folder with the specified ID actually exists and the client has sufficient access rights to view the folder, the RopOpenFolder ROP performs successfully.");

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R394");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R394.
            // MS-OXCFOLD_R462 was verified, MS-OXCFOLD_R462 can be verified directly.
            Site.CaptureRequirement(
                394,
                @"[In Opening a Folder] The client MUST have sufficient access rights to the folder for this operation to succeed.");

            ulong commonUserMessageId = 0;
            uint commonUserMessageHandle = 0;
            this.CreateSaveMessage(rootFolderHandle, rootFolderId, ref commonUserMessageId, ref commonUserMessageHandle);

            uint commonUserSubfolderHandle = 0;
            ulong commonUserSubfolderId = 0;
            this.CreateFolder(rootFolderHandle, Constants.Subfolder2, ref commonUserSubfolderId, ref commonUserSubfolderHandle);
            #endregion

            #region Step 5. The client calls RopDeleteMessages to delete the message created in step 2.

            ulong[] messageIds = new ulong[] { messageId, commonUserMessageId };
            RopDeleteMessagesRequest deleteMessagesRequest = new RopDeleteMessagesRequest();
            RopDeleteMessagesResponse deleteMessagesResponse = new RopDeleteMessagesResponse();
            deleteMessagesRequest.RopId = (byte)RopId.RopDeleteMessages;
            deleteMessagesRequest.LogonId = Constants.CommonLogonId;
            deleteMessagesRequest.InputHandleIndex = Constants.CommonInputHandleIndex;
            deleteMessagesRequest.WantAsynchronous = 0x00;

            // The server does not generate a non-read receipt for the deleted messages.
            deleteMessagesRequest.NotifyNonRead = 0x00;
            deleteMessagesRequest.MessageIdCount = (ushort)messageIds.Length;
            deleteMessagesRequest.MessageIds = messageIds;
            deleteMessagesResponse = this.Adapter.DeleteMessages(deleteMessagesRequest, rootFolderHandle, ref this.responseHandles);

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R991");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R991
            Site.CaptureRequirementIfAreNotEqual<byte>(
                0,
                deleteMessagesResponse.PartialCompletion,
                991,
                @"[In RopDeleteMessages ROP Response Buffer] PartialCompletion (1 byte): If the ROP [RopDeleteMessages] fails for a subset of targets, the value of this field is nonzero (TRUE).");

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R1147");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R1147
            Site.CaptureRequirementIfAreNotEqual<uint>(
                0,
                deleteMessagesResponse.PartialCompletion,
                1147,
                @"[In Processing a RopDeleteMessages ROP Request] If the server fails to delete any messages, it sets the PartialCompletion field of the RopDeleteMessages ROP response buffer to nonzero (TRUE), as specified in section 2.2.1.11.2.");
            #endregion

            #region Step 6. The client calls RopHardDeleteMessages to delete the message created in step 2.
            RopHardDeleteMessagesRequest hardDeleteMessagesRequest = new RopHardDeleteMessagesRequest
            {
                RopId = 0x91,
                LogonId = Constants.CommonLogonId,
                InputHandleIndex = Constants.CommonInputHandleIndex,
                WantAsynchronous = 0x00,
                NotifyNonRead = 0x00,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds
            };
            RopHardDeleteMessagesResponse hardDeleteMessagesResponse = this.Adapter.HardDeleteMessages(hardDeleteMessagesRequest, rootFolderHandle, ref this.responseHandles);

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R997");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R997.
            Site.CaptureRequirementIfAreNotEqual<byte>(
                0,
                hardDeleteMessagesResponse.PartialCompletion,
                997,
                @"[In RopHardDeleteMessages ROP Response Buffer] If the ROP [RopHardDeleteMessages] fails for a subset of targets, the value of this field is nonzero (TRUE).");

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R115602");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R115602
            Site.CaptureRequirementIfAreNotEqual<byte>(
                0,
                hardDeleteMessagesResponse.PartialCompletion,
                115602,
                @"[In Processing a RopHardDeleteMessages ROP Request] In the server behavior, if the server fails to delete any messages, it sets the PartialCompletion field of the RopDeleteMessages ROP response buffer to nonzero (TRUE), as specified in section 2.2.1.11.2.");
            #endregion

            #region Step 7. The client calls RopHardDeleteMessagesAndSubfolders to delete the message created in step 2.
            RopHardDeleteMessagesAndSubfoldersRequest hardDeleteMessagesAndSubfoldersRequest = new RopHardDeleteMessagesAndSubfoldersRequest
            {
                RopId = (byte)RopId.RopHardDeleteMessagesAndSubfolders,
                LogonId = Constants.CommonLogonId,
                InputHandleIndex = Constants.CommonInputHandleIndex,
                WantAsynchronous = 0x00,
                WantDeleteAssociated = 0xFF
            };
            RopHardDeleteMessagesAndSubfoldersResponse hardDeleteMessagesAndSubfoldersResponse = this.Adapter.HardDeleteMessagesAndSubfolders(hardDeleteMessagesAndSubfoldersRequest, rootFolderHandle, ref this.responseHandles);
            
            if (Common.IsRequirementEnabled(2721, this.Site))
            {
                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R2721");

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R2721
                Site.CaptureRequirementIfAreNotEqual<byte>(
                    0,
                    hardDeleteMessagesAndSubfoldersResponse.PartialCompletion,
                    2721,
                    @"[In RopHardDeleteMessagesAndSubfolders ROP Response Buffer] PartialCompletion (1 byte): If the ROP [RopHardDeleteMessagesAndSubfolders] fails for a subset of targets, the value of this field is nonzero (TRUE).");

                // Add the debug information.
                Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R113803");

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R113803.
                Site.CaptureRequirement(
                    113803,
                    @"[In Processing a RopHardDeleteMessagesAndSubfolders ROP Request] In the server behavior, if the server fails to delete any message or subfolder, it sets the PartialCompletion field of the RopHardDeleteMessagesAndSubfolders ROP response buffer to nonzero (TRUE), as specified in section 2.2.1.10.2.");
            }
            #endregion

            #region Step 8. The client calls RopMoveCopyMessages to move the message from the root folder to the inbox.
            List<uint> handleList = new List<uint>
            {
                rootFolderHandle, inboxHandle
            };

            RopMoveCopyMessagesRequest moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
            {
                RopId = (byte)RopId.RopMoveCopyMessages,
                LogonId = Constants.CommonLogonId,
                SourceHandleIndex = 0x00,
                DestHandleIndex = 0x01,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds,
                WantAsynchronous = 0x00,
                WantCopy = 0xFF
            };

            // WantCopy is nonzero (TRUE) indicates this is a copy operation.
            RopMoveCopyMessagesResponse moveCopyMessagesResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handleList, ref this.responseHandles);

            if (Common.IsRequirementEnabled(586, this.Site))
            {
                // Add the debug information.
                Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R10163");

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R10163.
                Site.CaptureRequirementIfAreNotEqual<byte>(
                    0,
                    moveCopyMessagesResponse.PartialCompletion,
                    10163,
                    @"[In RopMoveCopyMessages ROP Response Buffer] PartialCompletion (1 byte): If the ROP fails for a subset of targets, the value of this field is nonzero (TRUE).");

                // Add the debug information.
                Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R586");

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R586.
                // MS-OXCFOLD_R10163 is verified, MS-OXCFOLD_R586 can be verified directly.
                Site.CaptureRequirement(
                    586,
                    @"[In Processing a RopMoveCopyMessages ROP Request] If the server fails to move or copy any message, it sets the PartialCompletion field of the RopMoveCopyMessages ROP response buffer to nonzero (TRUE), as specified in section 2.2.1.6.2.");
            }
            #endregion
        }
        public void MSOXCFOLD_S04_TC04_RopMoveCopyMessagesInPublicFolderSuccess()
        {
            this.CheckWhetherSupportTransport();
            this.Logon();
            this.PublicFolderInitialization();

            #region Step 1. The client calls RopCreateFolder to create [MSOXCFOLDSubfolder1] under the root public folder.

            RopCreateFolderRequest createFolderRequest = new RopCreateFolderRequest
            {
                RopId = (byte)RopId.RopCreateFolder,
                LogonId = Constants.CommonLogonId,
                InputHandleIndex = Constants.CommonInputHandleIndex,
                OutputHandleIndex = Constants.CommonOutputHandleIndex,
                FolderType = (byte)FolderType.Genericfolder,
                UseUnicodeStrings = 0x0,
                OpenExisting = 0x01,
                Reserved = 0x0,
                DisplayName = Encoding.ASCII.GetBytes(Constants.Subfolder1),
                Comment = Encoding.ASCII.GetBytes(Constants.Subfolder1)
            };

            RopCreateFolderResponse createFolderResponse = this.Adapter.CreateFolder(createFolderRequest, this.publicRootFolderHandle, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(0, createFolderResponse.ReturnValue, "RopCreateFolder ROP operation performs should successfully.");
            uint subfolderHandle1 = this.responseHandles[0][createFolderResponse.OutputHandleIndex];

            #endregion

            #region Step 2. The client creates a message in the root public folder.

            uint messageHandle = 0;
            ulong messageId = 0;
            this.CreateSaveMessage(this.publicRootFolderHandle, this.publicRootFolderId, ref messageId, ref messageHandle);

            #endregion

            #region Step 3. The client calls RopMoveCopyMessages to copy the message from the root public folder to [MSOXCFOLDSubfolder1].

            ulong[] messageIds = new ulong[] { messageId };
            List<uint> handlelist = new List<uint>
            {
                this.publicRootFolderHandle, subfolderHandle1
            };

            RopMoveCopyMessagesRequest moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
            {
                RopId = (byte)RopId.RopMoveCopyMessages,
                LogonId = Constants.CommonLogonId,
                SourceHandleIndex = 0x00,
                DestHandleIndex = 0x01,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds,
                WantAsynchronous = 0x00,
                WantCopy = 0x01
            };

            // WantCopy is non-zero (TRUE) indicates this is a copy operation.
            RopMoveCopyMessagesResponse moveCopyMessagesResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(0, moveCopyMessagesResponse.ReturnValue, "The RopMoveCopyMessages ROP operation performs should successfully.");
            handlelist.Clear();

            #endregion

            #region Step 4. The client calls RopGetContentsTable to retrieve the contents table for [MSOXCFOLDSubfolder1] with 'ConversationMembers' flag.

            RopGetContentsTableRequest getContentsTableRequest = new RopGetContentsTableRequest
            {
                RopId = (byte)RopId.RopGetContentsTable,
                LogonId = Constants.CommonLogonId,
                InputHandleIndex = Constants.CommonInputHandleIndex,
                OutputHandleIndex = Constants.CommonOutputHandleIndex,
                TableFlags = (byte)FolderTableFlags.None
            };

            RopGetContentsTableResponse getContentsTableResponse = this.Adapter.GetContentsTable(getContentsTableRequest, this.publicRootFolderHandle, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(Constants.SuccessCode, getContentsTableResponse.ReturnValue, "RopGetContentsTable ROP operation performs should successfully.");

            #region Verify the requirement: MS-OXCFOLD_R14502 and MS-OXCFOLD_R10252.
            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R10252: the return value of the getContentsTableResponse is {0}", getContentsTableResponse.ReturnValue);

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R10252
            // The'ConversationMembers' flag is seted in the getContentsTableRequest, so if the getContentsTableResponse returns success. R10252 can be verified. 
            Site.CaptureRequirementIfAreEqual<uint>(
                0,
                getContentsTableResponse.ReturnValue,
                10252,
                @"[In RopGetContentsTable ROP Request Buffer] This bit [ConversationMembers] is supported on public folders.");

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R14502");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R14502
            Site.CaptureRequirementIfAreEqual<uint>(
                1,
                getContentsTableResponse.RowCount,
                14502,
                @"[In RopMoveCopyMessages ROP] This ROP applies to both public folders [and private mailboxes].");
            #endregion
            #endregion
         }
        public void MSOXCFOLD_S02_TC06_RopMoveCopyMessagesFailure()
        {
            this.CheckWhetherSupportTransport();
            this.Adapter.DoConnect(ConnectionType.PrivateMailboxServer);
            List<uint> handlelist;
            this.GenericFolderInitialization();

            #region Step 1. Create a message in the root folder.
            uint messageHandle = 0;
            ulong messageId = 0;
            this.CreateSaveMessage(this.RootFolderHandle, this.RootFolderId, ref messageId, ref messageHandle);
            #endregion

            #region Step 2. Call RopCreateFolder to create [MSOXCFOLDSubfolder1] under the root folder.
            uint subfolderHandle1 = 0;
            ulong subfolderId1 = 0;
            this.CreateFolder(this.RootFolderHandle, Constants.Subfolder1, ref subfolderId1, ref subfolderHandle1);
            #endregion

            #region Step 3. Call RopMoveCopyMessages using a logon object handle as a source folder handle to move the message created in step 2 to [MSOXCFOLDSubfolder1].
            ulong[] messageIds = new ulong[] { subfolderId1 };
            List<uint> handleList = new List<uint>
            {
                // Use logon object handle as a source handle for RopMoveCopyMessages in which case is purposed to get an error code ecNotSupported [0x80040102].  
                this.LogonHandle, subfolderHandle1
            };

            RopMoveCopyMessagesRequest moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
            {
                RopId = (byte)RopId.RopMoveCopyMessages,
                LogonId = Constants.CommonLogonId,
                SourceHandleIndex = 0x00,
                DestHandleIndex = 0x01,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds,
                WantAsynchronous = 0x00,
                WantCopy = 0
            };
            RopMoveCopyMessagesResponse moveCopyMessagesResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handleList, ref this.responseHandles);

            #region Verify MS-OXCFOLD_R589 and MS-OXCFOLD_R590.

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R589");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R589
            Site.CaptureRequirementIfAreEqual<uint>(
                0x80040102,
                moveCopyMessagesResponse.ReturnValue,
                589,
                @"[In Processing a RopMoveCopyMessages ROP Request]The value of error code ecNotSupported is 0x80040102.");

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R590");

            // The MS-OXCFOLD_R589 captured error code [ecNotSupported], using logon handle as a source folder handle, capture this requirement directly.
            Site.CaptureRequirement(
                590,
                @"[In Processing a RopMoveCopyMessages ROP Request] When the error code is ecNotSupported, it indicates that either the source object or the destination object is not a Folder object.");

            #endregion

            handleList.Clear();
            #endregion

            #region Step 4. Call RopMoveCopyMessages to move the message created in step 1 from the root folder to [MSOXCFOLDSubfolder1] synchronously.
            messageIds = new ulong[] { messageId };
            handlelist = new List<uint>
            {
                this.RootFolderHandle, subfolderHandle1
            };

            moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
            {
                RopId = (byte)RopId.RopMoveCopyMessages,
                LogonId = Constants.CommonLogonId,
                SourceHandleIndex = 0x00,
                DestHandleIndex = 0x01,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds,
                WantAsynchronous = 0x00,
                WantCopy = 0x00
            };

            // WantCopy is zero (FALSE) indicates this is a move operation.
            moveCopyMessagesResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(0, moveCopyMessagesResponse.ReturnValue, "The RopMoveCopyMessages ROP operation performs successfully.");
            Site.Assert.AreEqual<uint>(0, moveCopyMessagesResponse.PartialCompletion, "The ROP successes for all subsets of targets");
            #endregion
        }
        public void MSOXCFOLD_S02_TC01_RopMoveCopyMessagesSuccess()
        {
            this.CheckWhetherSupportTransport();
            this.Adapter.DoConnect(ConnectionType.PrivateMailboxServer);
            this.GenericFolderInitialization();

            bool sourceMessageExist;
            bool sourceMessageRemoved;
            bool destinationMessageExist;
            ulong[] messageIds;
            List<uint> handlelist;

            #region Step 1. Create a message in the root folder.
            ulong messageId = 0;
            uint messageHandle = 0;
            this.CreateSaveMessage(this.RootFolderHandle, this.RootFolderId, ref messageId, ref messageHandle);
            #endregion

            #region Step 2. Call RopCreateFolder to create [MSOXCFOLDSubfolder1] under the root folder.
            ulong subfolderId1 = 0;
            uint subfolderHandle1 = 0;
            this.CreateFolder(this.RootFolderHandle, Constants.Subfolder1, ref subfolderId1, ref subfolderHandle1);
            #endregion

            #region Step 3. Call RopMoveCopyMessages to copy the message created in step 1 from the root folder to [MSOXCFOLDSubfolder1] synchronously.
            messageIds = new ulong[1];
            messageIds[0] = messageId;
            handlelist = new List<uint>
            {
                this.RootFolderHandle, subfolderHandle1
            };

            RopMoveCopyMessagesRequest moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
            {
                RopId = (byte)RopId.RopMoveCopyMessages,
                LogonId = Constants.CommonLogonId,
                SourceHandleIndex = 0x00,
                DestHandleIndex = 0x01,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds,
                WantAsynchronous = 0x00,
                WantCopy = 0xFF
            };

            // WantCopy is nonzero (TRUE) indicates this is a copy operation.
            RopMoveCopyMessagesResponse moveCopyMessagesResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);

            Site.Assert.AreEqual<uint>(0, moveCopyMessagesResponse.ReturnValue, "The RopMoveCopyMessages ROP operation performs successfully.");
            Site.Assert.AreEqual<uint>(0, moveCopyMessagesResponse.PartialCompletion, "The ROP successes for all subsets of targets");
            handlelist.Clear();

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R1105");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R1105.
            // The return value 0 of MoveCopyMessages indicates that the server responds with a RopMoveCopyMessages ROP response buffer.
            Site.CaptureRequirement(
                1105,
                @"[In Processing a RopMoveCopyMessages ROP Request] The server responds with a RopMoveCopyMessages ROP response buffer.");

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R155");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R155.
            // The WantAsynchronous was set to zero and the server responds a RopMoveCopyMessages ROP response indicates the ROP is processed synchronously, MS-OXCFOLD_R155 can be verified directly.
            Site.CaptureRequirement(
                155,
                @"[In RopMoveCopyMessages ROP Request Buffer] WantAsynchronous (1 byte): [A Boolean value that is] zero (FALSE) if the ROP is to be processed synchronously.");

            #endregion

            #region Step 4. Validate the message is copied successfully in step 3.
            uint rootFolderContentsCountExpect = 1;
            uint rootFolderContentsCountActual = this.GetContentsTable(FolderTableFlags.None, this.RootFolderHandle);
            sourceMessageExist = rootFolderContentsCountExpect == rootFolderContentsCountActual;

            uint subfolderContentsCountExpect = 1;
            uint subfolderContentsCountActual = this.GetContentsTable(FolderTableFlags.None, subfolderHandle1);
            destinationMessageExist = subfolderContentsCountExpect == subfolderContentsCountActual;

            #region Verify MS-OXCFOLD_R159, MS-OXCFOLD_R14902, MS-OXCFOLD_R15102 and MS-OXCFOLD_R14501.
            // Add the debug information
            Site.Log.Add(
                LogEntryKind.Debug,
                @"Verify MS-OXCFOLD_R159:
                Expected contents count of the root folder is {0},
                Actual contents count of the root folder is {1};
                Expected contents count of the [MSOXCFOLDSubfolder1] is {2},
                Actual contents count of the [MSOXCFOLDSubfolder1] is {3};",
                rootFolderContentsCountExpect,
                rootFolderContentsCountActual,
                subfolderContentsCountExpect,
                subfolderContentsCountActual);

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R159.
            bool isVerifyR159 = sourceMessageExist && destinationMessageExist;

            Site.CaptureRequirementIfIsTrue(
                isVerifyR159,
                159,
                @"[In RopMoveCopyMessages ROP Request Buffer] WantCopy (1 byte): A Boolean value that is nonzero (TRUE) if this [RopMoveCopyMessages ROP] is a copy operation.");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R14902.
            bool isVerifyR14902 = sourceMessageExist && destinationMessageExist;

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R14902: expected contents count of the root folder is {0}, actual contents count of the root folder is {1}; expected contents count of the [MSOXCFOLDSubfolder1] is {2}, actual contents count of the [MSOXCFOLDSubfolder1] is {3};", rootFolderContentsCountExpect, rootFolderContentsCountActual, subfolderContentsCountExpect, subfolderContentsCountActual);

            // The source handle lists contain RootFolderHandle and subfolderHandle1, and the sourceHandleIndex is 0 and the destHandleIndex is 1 in the moveCopyMessage request, so if the message was copied successfully from root folder to the subfolder1, R14902 can be verified.
            Site.CaptureRequirementIfIsTrue(
                isVerifyR14902,
                14902,
                @"[In RopMoveCopyMessages ROP Request Buffer] SourceHandleIndex (1 byte): The source Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder from which the messages will be copied.");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R15102.
            bool isVerifyR15102 = sourceMessageExist && destinationMessageExist;

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R15102: expected contents count of the root folder is {0}, actual contents count of the root folder is {1}; expected contents count of the [MSOXCFOLDSubfolder1] is {2}, actual contents count of the [MSOXCFOLDSubfolder1] is {3};", rootFolderContentsCountExpect, rootFolderContentsCountActual, subfolderContentsCountExpect, subfolderContentsCountActual);

            // The source handle lists contain RootFolderHandle and subfolderHandle1, and the sourceHandleIndex is 0 and the destHandleIndex is 1 in the moveCopyMessage request, so if the message was copied successfully from root folder to the subfolder1, R15102 can be verified.
            Site.CaptureRequirementIfIsTrue(
                isVerifyR15102,
                15102,
                @"[In RopMoveCopyMessages ROP Request Buffer] DestHandleIndex (1 byte): The destination Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder to which the messages will be copied.");

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R14501");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R14501.
            // MS-OXCFOLD_R159 is verified and this scenario use private mailbox logon, MS-OXCFOLD_R14501 can be verified directly.
            Site.CaptureRequirement(
                14501,
                @"[In RopMoveCopyMessages ROP] This ROP applies to [both public folders and] private mailboxes.");
            #endregion
            #endregion

            #region Step 5. Call RopMoveCopyMessages to move the message created in step 1 from the root folder to [MSOXCFOLDSubfolder1] synchronously.
            messageIds = new ulong[] { messageId };
            handlelist = new List<uint>
            {
                this.RootFolderHandle, subfolderHandle1
            };

            moveCopyMessagesRequest = new RopMoveCopyMessagesRequest();
            moveCopyMessagesRequest.RopId = (byte)RopId.RopMoveCopyMessages;
            moveCopyMessagesRequest.LogonId = Constants.CommonLogonId;
            moveCopyMessagesRequest.SourceHandleIndex = 0x00;
            moveCopyMessagesRequest.DestHandleIndex = 0x01;
            moveCopyMessagesRequest.MessageIdCount = (ushort)messageIds.Length;
            moveCopyMessagesRequest.MessageIds = messageIds;
            moveCopyMessagesRequest.WantAsynchronous = 0x00;

            // WantCopy is zero (FALSE) indicates this is a move operation.
            moveCopyMessagesRequest.WantCopy = 0x00;
            moveCopyMessagesResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(0, moveCopyMessagesResponse.ReturnValue, "The RopMoveCopyMessages ROP operation performs successfully.");

            handlelist.Clear();

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R163");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R163.
            // According to the test case designing and open specification, the RopMoveCopyMessagesResponse operation here does not fail for a subset of targets, MS-OXCFOLD_R163 can be captured.
            Site.CaptureRequirementIfAreEqual<byte>(
                0x00,
                moveCopyMessagesResponse.PartialCompletion,
                163,
                @"[In RopMoveCopyMessages ROP Response Buffer]PartialCompletion (1 byte): Otherwise [if the ROP successes for a subset of targets], the value is zero (FALSE).");
            #endregion

            #region Step 6. Validate the message is moved successfully in step 5.
            rootFolderContentsCountExpect = 0;
            rootFolderContentsCountActual = this.GetContentsTable(FolderTableFlags.None, this.RootFolderHandle);
            sourceMessageRemoved = rootFolderContentsCountExpect == rootFolderContentsCountActual;

            subfolderContentsCountExpect = 2;
            subfolderContentsCountActual = this.GetContentsTable(FolderTableFlags.None, subfolderHandle1);
            destinationMessageExist = subfolderContentsCountExpect == subfolderContentsCountActual;

            #region Verify MS-OXCFOLD_R160, MS-OXCFOLD_R14901 and MS-OXCFOLD_R15101.
            // Add the debug information
            Site.Log.Add(
                LogEntryKind.Debug,
                @"Verify MS-OXCFOLD_R160: The validation result of whether the source message was removed is {0}, the validation result of whether the destination message is existed is {1}",
                sourceMessageRemoved,
                destinationMessageExist);

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R160.
            bool isVerifyR160 = sourceMessageRemoved && destinationMessageExist;

            Site.CaptureRequirementIfIsTrue(
                isVerifyR160,
                160,
                @"[In RopMoveCopyMessages ROP Request Buffer] WantCopy (1 byte): [A Boolean value that is] zero (FALSE) if this [RopMoveCopyMessages ROP] is a move operation.");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R14901.
            bool isVerifyR14901 = sourceMessageRemoved && destinationMessageExist;

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R14901: the validation result of whether the source message was removed is {0}, the validation result of whether the destination message is existed is {1}", sourceMessageRemoved, destinationMessageExist);

            // The source handle lists contain RootFolderHandle and subfolderHandle1, and the sourceHandleIndex is 0 and the destHandleIndex is 1 in the moveCopyMessage request, so if the message was moved successfully from root folder to the subfolder1, R14901 can be verified.
            Site.CaptureRequirementIfIsTrue(
                isVerifyR14901,
                14901,
                @"[In RopMoveCopyMessages ROP Request Buffer] SourceHandleIndex (1 byte): The source Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder from which the messages will be moved.");

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R15101.
            bool isVerifyR15101 = sourceMessageRemoved && destinationMessageExist;

            // Add the debug information.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R15101: the validation result of whether the source message was removed is {0}, the validation result of whether the destination message is existed is {1}", sourceMessageRemoved, destinationMessageExist);

            // The source handle lists contain RootFolderHandle and subfolderHandle1, and the sourceHandleIndex is 0 and the destHandleIndex is 1 in the moveCopyMessage request, so if the message was moved successfully from root folder to the subfolder1, R15101 can be verified.
            Site.CaptureRequirement(
                15101,
                @"[In RopMoveCopyMessages ROP Request Buffer] DestHandleIndex (1 byte): The destination Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder to which the messages will be moved.");
            #endregion
            #endregion
        }
        public void MSOXCFOLD_S02_TC11_RopMoveCopyMessagesUseSearchFolderSuccess()
        {
            this.Adapter.DoConnect(ConnectionType.PrivateMailboxServer);
            this.GenericFolderInitialization();

            #region Step 1. Call RopCreateFolder to create [MSOXCFOLDSubfolder1] under the root folder.
            ulong subfolderId1 = 0;
            uint subfolderHandle1 = 0;
            this.CreateFolder(this.RootFolderHandle, Constants.Subfolder1, ref subfolderId1, ref subfolderHandle1);
            #endregion

            #region Step 2. Create a message in the [MSOXCFOLDSubfolder1] folder created in step 1.

            uint messageHandle = 0;
            ulong messageId = 0;
            this.CreateSaveMessage(subfolderHandle1, subfolderId1, ref messageId, ref messageHandle);

            #endregion

            #region Step 3. Call RopCreateFolder to create [MSOXCFOLDSubfolder2] under the root folder.
            ulong subfolderId2 = 0;
            uint subfolderHandle2 = 0;
            this.CreateFolder(this.RootFolderHandle, Constants.Subfolder2, ref subfolderId2, ref subfolderHandle2);
            #endregion

            #region Step 4. Create a message in the [MSOXCFOLDSubfolder2] folder created in step 3.

            uint messageHandleInSubFolder2 = 0;
            ulong messageIdInSubFolder2 = 0;
            this.CreateSaveMessage(subfolderHandle2, subfolderId2, ref messageIdInSubFolder2, ref messageHandleInSubFolder2);
            #endregion

            #region Step 4. Call RopCreateFolder to create a search folder [MSOXCFOLDSearchFolder] under the root folder.
            RopCreateFolderRequest createFolderRequest = new RopCreateFolderRequest
            {
                RopId = (byte)RopId.RopCreateFolder,
                LogonId = Constants.CommonLogonId,
                InputHandleIndex = Constants.CommonInputHandleIndex,
                OutputHandleIndex = Constants.CommonOutputHandleIndex,
                FolderType = (byte)FolderType.Searchfolder,
                UseUnicodeStrings = 0x0,
                OpenExisting = 0x00,
                Reserved = 0x0,
                DisplayName = Encoding.ASCII.GetBytes(Constants.SearchFolder),
                Comment = Encoding.ASCII.GetBytes(Constants.SearchFolder)
            };
            RopCreateFolderResponse createFolderResponse = this.Adapter.CreateFolder(createFolderRequest, this.RootFolderHandle, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(Constants.SuccessCode, createFolderResponse.ReturnValue, "RopCreateFolder ROP operation performs successfully!");
            uint searchFolderHandle = this.responseHandles[0][createFolderResponse.OutputHandleIndex];

            #endregion

            #region Step 5. The client calls RopSetSearchCriteria to establish search criteria for [MSOXCFOLDSubFolder1].

            RopSetSearchCriteriaRequest setSearchCriteriaRequest = new RopSetSearchCriteriaRequest
            {
                RopId = (byte)RopId.RopSetSearchCriteria,
                LogonId = Constants.CommonLogonId,
                InputHandleIndex = Constants.CommonInputHandleIndex
            };
            PropertyTag propertyTag = new PropertyTag
            {
                PropertyId = (ushort)MessagePropertyId.PidTagMessageClass,
                PropertyType = (ushort)PropertyType.PtypString
            };
            ExistRestriction existRestriction = new ExistRestriction
            {
                PropTag = propertyTag
            };
            setSearchCriteriaRequest.RestrictionDataSize = (ushort)existRestriction.Size();
            setSearchCriteriaRequest.RestrictionData = existRestriction.Serialize();
            setSearchCriteriaRequest.FolderIds = new ulong[] { subfolderId1 };
            setSearchCriteriaRequest.FolderIdCount = (ushort)setSearchCriteriaRequest.FolderIds.Length;
            setSearchCriteriaRequest.SearchFlags = (uint)SetSearchFlags.ContentIndexedSearch | (uint)SetSearchFlags.StaticSearch | (uint)SetSearchFlags.RestartSearch;
            RopSetSearchCriteriaResponse setSearchCriteriaResponse = this.Adapter.SetSearchCriteria(setSearchCriteriaRequest, searchFolderHandle, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(Constants.SuccessCode, setSearchCriteriaResponse.ReturnValue, "RopSearchCriteria ROP operation performs successfully!");

            #endregion

            #region Step 6. The client calls RopGetSearchCriteria to obtain the search criteria and the status of the search folder [MSOXCFOLDSubFolder1].
            RopGetSearchCriteriaRequest getSearchCriteriaRequest = new RopGetSearchCriteriaRequest
            {
                RopId = (byte)RopId.RopGetSearchCriteria,
                LogonId = Constants.CommonLogonId,
                InputHandleIndex = Constants.CommonInputHandleIndex,
                UseUnicode = 0x00,
                IncludeRestriction = 0x01,
                IncludeFolders = 0x01
            };
            RopGetSearchCriteriaResponse getSearchCriteriaResponse = this.Adapter.GetSearchCriteria(getSearchCriteriaRequest, searchFolderHandle, ref this.responseHandles);
            Site.Assert.AreEqual<uint>(Constants.SuccessCode, getSearchCriteriaResponse.ReturnValue, "RopGetSearchCriteria ROP operation performs successfully!");

            #endregion

            #region Step 7. The client calls RopGetContentsTable to get handle of the contents table in the search folder [MSOXCFOLDSearchFolder].

            RopGetContentsTableRequest getContentsTableRequest = new RopGetContentsTableRequest();
            RopGetContentsTableResponse getContentsTableResponse;
            getContentsTableRequest.RopId = (byte)RopId.RopGetContentsTable;
            getContentsTableRequest.LogonId = Constants.CommonLogonId;
            getContentsTableRequest.InputHandleIndex = Constants.CommonInputHandleIndex;
            getContentsTableRequest.OutputHandleIndex = Constants.CommonOutputHandleIndex;
            getContentsTableRequest.TableFlags = (byte)FolderTableFlags.None;

            int count = 0;
            uint tableHandle;
            do
            {
                getContentsTableResponse = this.Adapter.GetContentsTable(getContentsTableRequest, searchFolderHandle, ref this.responseHandles);
                Site.Assert.AreEqual<uint>(Constants.SuccessCode, getContentsTableResponse.ReturnValue, "RopGetContentsTable ROP operation performs successfully!");
                tableHandle = this.responseHandles[0][getContentsTableResponse.OutputHandleIndex];
                if (getContentsTableResponse.RowCount != 1)
                {
                    Thread.Sleep(this.WaitTime);
                }
                else
                {
                    break;
                }

                count++;
            }
            while (count < this.RetryCount);

            #endregion

            #region Step 8. Sets the properties PidTagMid visible on the content table.

            RopSetColumnsRequest setColumnsRequest;
            PropertyTag[] propertyTags = new PropertyTag[1];
            propertyTags[0].PropertyId = (ushort)MessagePropertyId.PidTagMid;
            propertyTags[0].PropertyType = (ushort)PropertyType.PtypInteger64;

            setColumnsRequest.RopId = 0x12;
            setColumnsRequest.LogonId = 0x00;
            setColumnsRequest.InputHandleIndex = 0x00;
            setColumnsRequest.PropertyTagCount = (ushort)propertyTags.Length;
            setColumnsRequest.PropertyTags = propertyTags;
            setColumnsRequest.SetColumnsFlags = 0x00; // Sync

            object ropResponse = new object();
            this.Adapter.DoRopCall(setColumnsRequest, tableHandle, ref ropResponse, ref this.responseHandles);
            #endregion

            #region Step 9. Gets the message ID in the search folder [MSOXCFOLDSearchFolder].

            RopQueryRowsRequest queryRowsRequest;
            RopQueryRowsResponse queryRowsResponse;

            queryRowsRequest.RopId = 0x15;
            queryRowsRequest.LogonId = 0x00;
            queryRowsRequest.InputHandleIndex = 0x00;
            queryRowsRequest.QueryRowsFlags = 0x00;
            queryRowsRequest.ForwardRead = 0x01;
            queryRowsRequest.RowCount = 1;

            this.Adapter.DoRopCall(queryRowsRequest, tableHandle, ref ropResponse, ref this.responseHandles);
            queryRowsResponse = (RopQueryRowsResponse)ropResponse;
            ulong messageID = BitConverter.ToUInt64(queryRowsResponse.RowData.PropertyRows[0].PropertyValues[0].Value, 0);
            #endregion

            #region Step 10. Call RopMoveCopyMessages to copy the message in the [MSOXCFOLDSearchFolder] to root folder synchronously.
            ulong[] messageIds = new ulong[1];
            messageIds[0] = messageID;
            List<uint> handlelist = new List<uint>
            {
                searchFolderHandle, this.RootFolderHandle
            };

            RopMoveCopyMessagesRequest moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
            {
                RopId = (byte)RopId.RopMoveCopyMessages,
                LogonId = Constants.CommonLogonId,
                SourceHandleIndex = 0x00,
                DestHandleIndex = 0x01,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds,
                WantAsynchronous = 0x00,
                WantCopy = 0xFF
            };

            // WantCopy is nonzero (TRUE) indicates this is a copy operation.
            RopMoveCopyMessagesResponse copyMessagesFromSearchFolderResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);

            Site.Assert.AreEqual<uint>(0, copyMessagesFromSearchFolderResponse.ReturnValue, "The RopMoveCopyMessages ROP operation performs successfully.");
            Site.Assert.AreEqual<uint>(0, copyMessagesFromSearchFolderResponse.PartialCompletion, "The ROP successes for all subsets of targets");
            handlelist.Clear();
            #endregion

            #region Step 11. Validate the message is copied successfully in above step 9.
            uint rootFolderContentsCountActual = this.GetContentsTable(FolderTableFlags.None, this.RootFolderHandle);

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R121702.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R121702: expected contents count of the root folder is {0}, actual contents count of the root folder is {1};", 1, rootFolderContentsCountActual);

            // The source folder is a search folder, so if the message was copied successfully from MSOXCFOLDSearchFolder to root folder, R121702 can be verified.
            Site.CaptureRequirementIfAreEqual<uint>(
                1,
                rootFolderContentsCountActual,
                121702,
                @"[In RopMoveCopyMessages ROP Request Buffer] SourceHandleIndex (1 byte): [The source Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder from which the messages will be copied] This folder can be a search folder.");
            #endregion

            #region Step 12. Call RopMoveCopyMessages to move the message in the [MSOXCFOLDSearchFolder] to root folder synchronously.
            messageIds = new ulong[1];
            messageIds[0] = messageID;
            handlelist = new List<uint>
            {
                searchFolderHandle, this.RootFolderHandle
            };

            moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
            {
                RopId = (byte)RopId.RopMoveCopyMessages,
                LogonId = Constants.CommonLogonId,
                SourceHandleIndex = 0x00,
                DestHandleIndex = 0x01,
                MessageIdCount = (ushort)messageIds.Length,
                MessageIds = messageIds,
                WantAsynchronous = 0x00,
                WantCopy = 0x00
            };

            // WantCopy is zero (FALSE) indicates this is a move operation.
            RopMoveCopyMessagesResponse moveMessagesFromSearchFolderResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);

            Site.Assert.AreEqual<uint>(0, moveMessagesFromSearchFolderResponse.ReturnValue, "The RopMoveCopyMessages ROP operation performs successfully.");
            Site.Assert.AreEqual<uint>(0, moveMessagesFromSearchFolderResponse.PartialCompletion, "The ROP successes for all subsets of targets");
            handlelist.Clear();
            #endregion

            #region Step 13. Validate the message is moved successfully in above step 12.
            rootFolderContentsCountActual = this.GetContentsTable(FolderTableFlags.None, this.RootFolderHandle);

            // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R121701.
            Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R121701: expected contents count of the root folder is {0}, actual contents count of the root folder is {1};", 2, rootFolderContentsCountActual);

            // The source folder is a search folder, so if the message was moved successfully from MSOXCFOLDSearchFolder to root folder, R121701 can be verified.
            Site.CaptureRequirementIfAreEqual<uint>(
                2,
                rootFolderContentsCountActual,
                121701,
                @"[In RopMoveCopyMessages ROP Request Buffer] SourceHandleIndex (1 byte): [The source Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder from which the messages will be moved] This folder can be a search folder.");
            #endregion

            #region Step 14. Call RopMoveCopyMessages to copy the message in the [MSOXCFOLDSubfolder2] to the [MSOXCFOLDSearchFolder] synchronously.
            RopMoveCopyMessagesResponse copyMessagesToSearchFolderResponse = new RopMoveCopyMessagesResponse();
            if (Common.IsRequirementEnabled(1246, this.Site))
            {
                messageIds[0] = messageIdInSubFolder2;
                handlelist = new List<uint>
                {
                subfolderHandle2, searchFolderHandle
                };
                moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
                {
                    RopId = (byte)RopId.RopMoveCopyMessages,
                    LogonId = Constants.CommonLogonId,
                    SourceHandleIndex = 0x00,
                    DestHandleIndex = 0x01,
                    MessageIdCount = (ushort)messageIds.Length,
                    MessageIds = messageIds,
                    WantAsynchronous = 0x00,
                    WantCopy = 0xFF
                };

                // WantCopy is nonzero (TRUE) indicates this is a copy operation.
                copyMessagesToSearchFolderResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);

                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R121802: the PartialCompletion in the MoveCopyMessages response is {0}", copyMessagesToSearchFolderResponse.PartialCompletion);

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R121802
                // If the ROP RopMoveCopyMessages fails to copy message, the value of PartialCompletion field is nonzero.
                this.Site.CaptureRequirementIfAreNotEqual<uint>(
                    0x00000000,
                    copyMessagesToSearchFolderResponse.ReturnValue,
                    121802,
                    @"[In RopMoveCopyMessages ROP Request Buffer] DestHandleIndex (1 byte): [The destination Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder to which the messages will be copied.] This folder cannot be a search folder.");
            }
            #endregion

            #region Step 15. Call RopMoveCopyMessages to move the message in the [MSOXCFOLDSubfolder2] to the [MSOXCFOLDSearchFolder] synchronously.
            RopMoveCopyMessagesResponse moveMessagesToSearchFolderResponse;
            if (Common.IsRequirementEnabled(1246, this.Site))
            {
                messageIds[0] = messageIdInSubFolder2;
                handlelist = new List<uint>
                {
                subfolderHandle2, searchFolderHandle
                };
                moveCopyMessagesRequest = new RopMoveCopyMessagesRequest
                {
                    RopId = (byte)RopId.RopMoveCopyMessages,
                    LogonId = Constants.CommonLogonId,
                    SourceHandleIndex = 0x00,
                    DestHandleIndex = 0x01,
                    MessageIdCount = (ushort)messageIds.Length,
                    MessageIds = messageIds,
                    WantAsynchronous = 0x00,
                    WantCopy = 0x00
                };

                // WantCopy is zero (FLASE) indicates this is a move operation.
                 moveMessagesToSearchFolderResponse = this.Adapter.MoveCopyMessages(moveCopyMessagesRequest, handlelist, ref this.responseHandles);

                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R121801: the PartialCompletion in the MoveCopyMessages response is {0}", moveMessagesToSearchFolderResponse.PartialCompletion);

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R121801
                // If the ROP RopMoveCopyMessages fails to move message, the value of PartialCompletion field is nonzero.
                this.Site.CaptureRequirementIfAreNotEqual<uint>(
                    0x00000000,
                    moveMessagesToSearchFolderResponse.ReturnValue,
                    121801,
                    @"[In RopMoveCopyMessages ROP Request Buffer] DestHandleIndex (1 byte): [The destination Server object for this operation [RopMoveCopyMessages ROP] is a Folder object that represents the folder to which the messages will be moved.] This folder cannot be a search folder.");

                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R1216");

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R1216
                bool isVerifiedR1216 = copyMessagesFromSearchFolderResponse.ReturnValue == 0x00000000 &&
                                    moveMessagesFromSearchFolderResponse.ReturnValue == 0x00000000 &&
                                    copyMessagesToSearchFolderResponse.ReturnValue != 0x00000000 &&
                                    moveMessagesToSearchFolderResponse.ReturnValue != 0x00000000;

                this.Site.CaptureRequirementIfIsTrue(
                    isVerifiedR1216,
                    1216,
                    @"[In RopMoveCopyMessages ROP] The source folder can be a search folder, but the destination folder cannot.");

                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R1246: the return value is {0} when copy a message to a search folder and the return value is {1} when move a message to a search folder.", copyMessagesToSearchFolderResponse.ReturnValue, moveMessagesToSearchFolderResponse.ReturnValue);

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R1246
                bool isVerifiedR1246 = copyMessagesToSearchFolderResponse.ReturnValue == 0x00000460 && moveMessagesToSearchFolderResponse.ReturnValue == 0x00000460;

                this.Site.CaptureRequirementIfIsTrue(
                    isVerifiedR1246,
                    1246,
                    @"[In Processing a RopMoveCopyMessages ROP Request] When the error code is ecSearchFolder, it indicates the destination object is a search folder. ");

                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCFOLD_R1245");

                // Verify MS-OXCFOLD requirement: MS-OXCFOLD_R1245
                this.Site.CaptureRequirementIfAreEqual<uint>(
                    0x00000460,
                    copyMessagesToSearchFolderResponse.ReturnValue,
                    1245,
                    @"[In Processing a RopMoveCopyMessages ROP Request] The value of error code ecSearchFolder is 0x00000460.");
            }
            #endregion
        }
        /// <summary>
        /// Moves or copies messages from a source folder to a destination folder. 
        /// </summary>
        /// <param name="ropMoveCopyMessagesRequest">RopMoveCopyMessagesRequest object.</param>
        /// <param name="insideObjHandle">Server object handles in RopMoveCopyMessagesRequest.</param>
        /// <param name="responseSOHTable">Server objects handles in RopMoveCopyMessagesResponse.</param>
        /// <returns>RopMoveCopyMessagesResponse object.</returns>
        public RopMoveCopyMessagesResponse MoveCopyMessages(RopMoveCopyMessagesRequest ropMoveCopyMessagesRequest, List<uint> insideObjHandle, ref List<List<uint>> responseSOHTable)
        {
            object temp = new object();
            this.ExcuteRopCall((ISerializable)ropMoveCopyMessagesRequest, insideObjHandle, ref temp, ref responseSOHTable, ref this.rawData);
            RopMoveCopyMessagesResponse ropMoveCopyMessagesResponse = (RopMoveCopyMessagesResponse)temp;

            #region Capture Code
            // The ReturnValue equal to 0x00000000 indicate ROP operation success
            if (0x00000000 == ropMoveCopyMessagesResponse.ReturnValue)
            {
                this.VerifyRopMoveCopyMessages(ropMoveCopyMessagesResponse);
            }
            #endregion

            return ropMoveCopyMessagesResponse;
        }