Exemplo n.º 1
0
        /// <summary>
        /// Overrides TestClassBase's TestCleanup()
        /// </summary>
        protected override void TestCleanup()
        {
            bool transportIsMAPI = Common.GetConfigurationPropertyValue("TransportSeq", this.Site).ToLower() == "mapi_http";
            if (!transportIsMAPI || Common.IsRequirementEnabled(1340, this.Site))
            {
                if (!this.needCleanup)
                {
                    return;
                }

                #region Hard Delete Messages and Subfolders of Inbox
                if (this.isRootFolderCreated)
                {
                    RopDeleteFolderRequest deleteFolderRequest = new RopDeleteFolderRequest();
                    RopDeleteFolderResponse deleteFolderResponse;
                    deleteFolderRequest.RopId = (byte)RopId.RopDeleteFolder;
                    deleteFolderRequest.LogonId = Constants.CommonLogonId;
                    deleteFolderRequest.InputHandleIndex = Constants.CommonInputHandleIndex;

                    // Set the DeleteFolderFlags to indicate hard delete the common generic folder,
                    // including all folders and messages under the folder.
                    deleteFolderRequest.DeleteFolderFlags = (byte)DeleteFolderFlags.DelFolders
                        | (byte)DeleteFolderFlags.DelMessages
                        | (byte)DeleteFolderFlags.DeleteHardDelete;
                    deleteFolderRequest.FolderId = this.RootFolderId;

                    int count = 0;
                    bool rootFolderCleanUpSuccess = false;
                    do
                    {
                        deleteFolderResponse = this.Adapter.DeleteFolder(deleteFolderRequest, this.inboxFolderHandle, ref this.responseHandles);
                        if (deleteFolderResponse.ReturnValue == Constants.SuccessCode && deleteFolderResponse.PartialCompletion == 0)
                        {
                            rootFolderCleanUpSuccess = true;
                        }
                        else
                        {
                            Thread.Sleep(this.WaitTime);
                        }

                        if (count > this.RetryCount)
                        {
                            break;
                        }

                        count++;
                    }
                    while (!rootFolderCleanUpSuccess);

                    Site.Assert.IsTrue(rootFolderCleanUpSuccess, "Test case cleanup should succeed.");
                }               
                #endregion

                #region  RopRelease
                RopReleaseRequest releaseRequest = new RopReleaseRequest();
                object ropResponse = null;
                releaseRequest.RopId = (byte)RopId.RopRelease;
                releaseRequest.LogonId = Constants.CommonLogonId;
                releaseRequest.InputHandleIndex = Constants.CommonInputHandleIndex;
                this.Adapter.DoRopCall(releaseRequest, this.LogonHandle, ref ropResponse, ref this.responseHandles);
                #endregion

                this.logonHandle = 0;
                ropResponse = null;
                this.responseHandles = null;
                this.Adapter.DoDisconnect();
            }
        }
Exemplo n.º 2
0
        /// <summary>
        /// Create message each one loop In InBox
        /// </summary>
        /// <param name="logonResponse">the logon response be used to create message</param>
        /// <param name="tableHandle">The tableHanlder of the new folder</param>
        /// <param name="count">The count of created messages</param>
        /// <param name="createMessageRequest">The ROP CreateMessageRequest</param>
        /// <param name="saveChangesMessageRequest">The ROP SaveChangesMessageRequest</param>
        /// <param name="releaseRequest">The ROP ReleaseRequest</param>
        protected void CreateSingleProcessEachLoop(ref RopLogonResponse logonResponse, out uint tableHandle, int count, RopCreateMessageRequest createMessageRequest, RopSaveChangesMessageRequest saveChangesMessageRequest, RopReleaseRequest releaseRequest)
        {
            RopCreateMessageResponse createMessageResponse = new RopCreateMessageResponse();
            RopSaveChangesMessageResponse saveChangesMessageResponse = new RopSaveChangesMessageResponse();
            #region Preparing the table: CreateFolder

            // Open a folder first
            RopOpenFolderRequest openFolderRequest;
            RopOpenFolderResponse openFolderResponse;

            openFolderRequest.RopId = (byte)RopId.RopOpenFolder;

            openFolderRequest.LogonId = TestSuiteBase.LogonId;
            openFolderRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            openFolderRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex1;
            openFolderRequest.FolderId = logonResponse.FolderIds[4];
            openFolderRequest.OpenModeFlags = (byte)FolderOpenModeFlags.None;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the RopOpenFolder request.");

            this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                openFolderRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            openFolderResponse = (RopOpenFolderResponse)this.response;
            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                openFolderResponse.ReturnValue,
                "if ROP succeeds, the ReturnValue of its response is 0(success)");
            uint openedFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];

            // Create a new subfolder in the opened folder
            // The new subfolder will be used as target folder
            RopCreateFolderRequest createFolderRequest;
            RopCreateFolderResponse createFolderResponse;

            createFolderRequest.RopId = (byte)RopId.RopCreateFolder;
            createFolderRequest.LogonId = TestSuiteBase.LogonId;
            createFolderRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            createFolderRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex1;
            createFolderRequest.FolderType = (byte)FolderType.Genericfolder;
            createFolderRequest.UseUnicodeStrings = Convert.ToByte(TestSuiteBase.Zero);
            createFolderRequest.OpenExisting = TestSuiteBase.NonZero;
            createFolderRequest.Reserved = TestSuiteBase.Reserved;
            createFolderRequest.DisplayName = Encoding.ASCII.GetBytes(TestSuiteBase.DisplayNameAndCommentForNonSearchFolder + "\0");
            createFolderRequest.Comment = Encoding.ASCII.GetBytes(TestSuiteBase.DisplayNameAndCommentForNonSearchFolder + "\0");

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the RopCreateFolder request.");

            this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                createFolderRequest,
                openedFolderHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            createFolderResponse = (RopCreateFolderResponse)this.response;
            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                createFolderResponse.ReturnValue,
                "if ROP succeeds, the ReturnValue of its response is 0(success)");
            uint targetFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];
            tableHandle = this.GetContentsTableHandle(targetFolderHandle);
            ulong folderId = createFolderResponse.FolderId;

            #endregion

            #region Preparing the table: RopCreateAndSaveMessages

            int waitTime = int.Parse(Common.GetConfigurationPropertyValue("WaitTime", this.Site));
            int maxRetryCount = int.Parse(Common.GetConfigurationPropertyValue("RetryCount", this.Site));
            int retryCount;
            uint returnValue = 0;
            for (int i = 1; i < count; i++)
            {
                // If the RPC report error code reported by the following three ROP methods is 1726 (The remote procedure call failed), 
                // re-do the common steps of this case.
                if (returnValue == 1726)
                {
                    #region The common steps
                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "If RPC error code is 1726, re-connect to server.");
                    this.cropsAdapter.RpcConnect(
                        Common.GetConfigurationPropertyValue("SutComputerName", this.Site),
                        ConnectionType.PrivateMailboxServer,
                        Common.GetConfigurationPropertyValue("UserEssdn", this.Site),
                        Common.GetConfigurationPropertyValue("Domain", this.Site),
                        Common.GetConfigurationPropertyValue("AdminUserName", this.Site),
                        Common.GetConfigurationPropertyValue("PassWord", this.Site));
                    logonResponse = this.Logon(LogonType.Mailbox, this.userDN, out this.inputObjHandle);

                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopOpenFolder request.");

                    this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                        openFolderRequest,
                        this.inputObjHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.SuccessResponse);
                    openFolderResponse = (RopOpenFolderResponse)this.response;

                    Site.Assert.AreEqual<uint>(
                        TestSuiteBase.SuccessReturnValue,
                        openFolderResponse.ReturnValue,
                        "if ROP succeeds, the ReturnValue of its response is 0(success)");
                    openedFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];

                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopCreateFolder request.");

                    this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                        createFolderRequest,
                        openedFolderHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.SuccessResponse);
                    createFolderResponse = (RopCreateFolderResponse)this.response;
                    Site.Assert.AreEqual<uint>(
                        TestSuiteBase.SuccessReturnValue,
                        createFolderResponse.ReturnValue,
                        "if ROP succeeds, the ReturnValue of its response is 0(success)");
                    targetFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];
                    tableHandle = this.GetContentsTableHandle(targetFolderHandle);
                    folderId = createFolderResponse.FolderId;
                    #endregion
                }

                #region Create message
                createMessageRequest.FolderId = folderId;

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopCreateMessage request:loop counter i={0}", i);
                retryCount = maxRetryCount;

                do
                {
                    // Send the RopCreateMessage to create message.
                    this.responseSOHs = this.cropsAdapter.ProcessSingleRopWithReturnValue(
                        createMessageRequest,
                        this.inputObjHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.SuccessResponse,
                        out returnValue);
                    System.Threading.Thread.Sleep(waitTime);
                    retryCount--;
                }
                while (this.response is RopBackoffResponse && retryCount >= 0);

                Site.Assert.IsTrue(retryCount >= 0, "The case {0} failed since server is busy and always returns RopBackoff in the response, reduce your server load and try again.", this.TestContext.TestName);

                // If the error code is 1726, continue this loop.
                if (returnValue == 1726)
                {
                    continue;
                }

                createMessageResponse = (RopCreateMessageResponse)this.response;
                Site.Assert.AreEqual<uint>(
                    TestSuiteBase.SuccessReturnValue,
                    createMessageResponse.ReturnValue,
                "if ROP succeeds, the ReturnValue of its response is 0(success)");
                uint targetMessageHandle = this.responseSOHs[0][createMessageResponse.OutputHandleIndex];
                #endregion

                #region Save message
                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopSaveChangesMessage request:loop counter i={0}", i);

                retryCount = maxRetryCount;

                // Do the loop when response is RopBackoffResponse or saveChangesMessageResponse is 0x80040401 (ecTimeout).
                do
                {
                    // Send the RopSaveChangesMessage request to save the created message.
                    this.responseSOHs = this.cropsAdapter.ProcessSingleRopWithReturnValue(
                        saveChangesMessageRequest,
                        targetMessageHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.SuccessResponse,
                        out returnValue);

                    if (this.response is RopSaveChangesMessageResponse)
                    {
                        saveChangesMessageResponse = (RopSaveChangesMessageResponse)this.response;
                    }

                    System.Threading.Thread.Sleep(waitTime);
                    retryCount--;
                }
                while ((this.response is RopBackoffResponse || saveChangesMessageResponse.ReturnValue == 0x80040401) && retryCount >= 0);

                Site.Assert.IsTrue(retryCount >= 0, "The case {0} failed since server is busy and always returns RopBackoff in the response, reduce your server load and try again.", this.TestContext.TestName);

                // If the error code is 1726, continue this loop.
                if (returnValue == 1726)
                {
                    continue;
                }

                saveChangesMessageResponse = (RopSaveChangesMessageResponse)this.response;
                Site.Assert.AreEqual<uint>(
                    TestSuiteBase.SuccessReturnValue,
                    saveChangesMessageResponse.ReturnValue,
                "if ROP succeeds, the ReturnValue of its response is 0(success)");
                #endregion

                #region Release all resources
                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopRelease request.");

                retryCount = maxRetryCount;

                do
                {
                    this.responseSOHs = this.cropsAdapter.ProcessSingleRopWithReturnValue(
                        releaseRequest,
                        targetMessageHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.SuccessResponse,
                        out returnValue);
                    System.Threading.Thread.Sleep(waitTime);
                    retryCount--;
                }
                while (this.response is RopBackoffResponse && retryCount >= 0);

                Site.Assert.IsTrue(retryCount >= 0, "The case {0} failed since server is busy and always returns RopBackoff in the response, reduce your server load and try again.", this.TestContext.TestName);

                // If the error code is 1726, continue this loop.
                if (returnValue == 1726)
                {
                    continue;
                }
                #endregion
            }

            // If the error code 1726 occurs on the last time of the above "for" loop, re-do the common steps.
            if (returnValue == 1726)
            {
                #region The common steps
                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "If RPC error code is 1726, re-connect to server.");
                this.cropsAdapter.RpcConnect(
                    Common.GetConfigurationPropertyValue("SutComputerName", this.Site),
                    ConnectionType.PrivateMailboxServer,
                    Common.GetConfigurationPropertyValue("UserEssdn", this.Site),
                    Common.GetConfigurationPropertyValue("Domain", this.Site),
                    Common.GetConfigurationPropertyValue("AdminUserName", this.Site),
                    Common.GetConfigurationPropertyValue("PassWord", this.Site));
                logonResponse = this.Logon(LogonType.Mailbox, this.userDN, out this.inputObjHandle);

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopOpenFolder request.");

                this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                    openFolderRequest,
                    this.inputObjHandle,
                    ref this.response,
                    ref this.rawData,
                    RopResponseType.SuccessResponse);
                openFolderResponse = (RopOpenFolderResponse)this.response;

                Site.Assert.AreEqual<uint>(
                    TestSuiteBase.SuccessReturnValue,
                    openFolderResponse.ReturnValue,
                    "if ROP succeeds, the ReturnValue of its response is 0(success)");
                openedFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopCreateFolder request.");

                this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                    createFolderRequest,
                    openedFolderHandle,
                    ref this.response,
                    ref this.rawData,
                    RopResponseType.SuccessResponse);
                createFolderResponse = (RopCreateFolderResponse)this.response;
                Site.Assert.AreEqual<uint>(
                    TestSuiteBase.SuccessReturnValue,
                    createFolderResponse.ReturnValue,
                    "if ROP succeeds, the ReturnValue of its response is 0(success)");
                targetFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];
                tableHandle = this.GetContentsTableHandle(targetFolderHandle);
                folderId = createFolderResponse.FolderId;
                #endregion
            }

            #endregion
        }
Exemplo n.º 3
0
        /// <summary>
        /// Prepare the ROP request for RopCreateMessage, RopSaveChangesMessage and RopRelease.
        /// </summary>
        /// <param name="logonResponse">The response of RopLogon.</param>
        /// <param name="createMessageRequest">The request of RopCreateMessage.</param>
        /// <param name="saveChangesMessageRequest">The request of RopSaveChangesMessage.</param>
        /// <param name="releaseRequest">The request of RopRelease.</param>
        protected void PrepareRops(RopLogonResponse logonResponse, ref RopCreateMessageRequest createMessageRequest, ref RopSaveChangesMessageRequest saveChangesMessageRequest, ref RopReleaseRequest releaseRequest)
        {
            #region prepare rops for createmessage, savemessage and release
            createMessageRequest.RopId = (byte)RopId.RopCreateMessage;
            createMessageRequest.LogonId = TestSuiteBase.LogonId;
            createMessageRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            createMessageRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex1;

            // Set CodePageId to 0x0FFF, which specified the code page of Logon object will be used.
            createMessageRequest.CodePageId = TestSuiteBase.CodePageId;

            createMessageRequest.FolderId = logonResponse.FolderIds[4];
            createMessageRequest.AssociatedFlag = Convert.ToByte(TestSuiteBase.Zero);

            // Save message 
            saveChangesMessageRequest.RopId = (byte)RopId.RopSaveChangesMessage;
            saveChangesMessageRequest.LogonId = TestSuiteBase.LogonId;
            saveChangesMessageRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            saveChangesMessageRequest.ResponseHandleIndex = TestSuiteBase.ResponseHandleIndex1;
            saveChangesMessageRequest.SaveFlags = (byte)SaveFlags.ForceSave;

            releaseRequest.RopId = (byte)RopId.RopRelease;
            releaseRequest.LogonId = TestSuiteBase.LogonId;
            releaseRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            #endregion        
        }
Exemplo n.º 4
0
 /// <summary>
 ///  Release the folder handle
 /// </summary>
 /// <param name="objectHandle">The object handle to be released</param>
 protected void RopRelease(uint objectHandle)
 {
     RopReleaseRequest ropReleaseRequest = new RopReleaseRequest
     {
         RopId = 0x01,
         LogonId = 0x00,
         InputHandleIndex = 0x00
     };
     this.oxcstorAdapter.DoRopCall(ropReleaseRequest, objectHandle, ROPCommandType.Others, out this.outputBuffer);
 }
Exemplo n.º 5
0
        /// <summary>
        /// Create Vast Messages In InBox
        /// </summary>
        /// <param name="logonResponse">the logon response be used to create message</param>
        /// <param name="tableHandle">The tableHanlder of the new folder</param>
        /// <param name="count">The count of created messages</param>
        /// <param name="createMessageRequest">The ROP CreateMessageRequest</param>
        /// <param name="saveChangesMessageRequest">The ROP SaveChangesMessageRequest</param>
        /// <param name="releaseRequest">The ROP ReleaseRequest</param>
        protected void CreateVastMessages(ref RopLogonResponse logonResponse, out uint tableHandle, int count, RopCreateMessageRequest createMessageRequest, RopSaveChangesMessageRequest saveChangesMessageRequest, RopReleaseRequest releaseRequest)
        {
            RopCreateMessageResponse createMessageResponse;
            RopSaveChangesMessageResponse saveChangesMessageResponse;
            #region Preparing the table: CreateFolder

            // Open a folder first
            RopOpenFolderRequest openFolderRequest;
            RopOpenFolderResponse openFolderResponse;

            openFolderRequest.RopId = (byte)RopId.RopOpenFolder;

            openFolderRequest.LogonId = TestSuiteBase.LogonId;
            openFolderRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            openFolderRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex1;
            openFolderRequest.FolderId = logonResponse.FolderIds[4];
            openFolderRequest.OpenModeFlags = (byte)FolderOpenModeFlags.None;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the RopOpenFolder request.");

            this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                openFolderRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            openFolderResponse = (RopOpenFolderResponse)this.response;
            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                openFolderResponse.ReturnValue,
                "if ROP succeeds, the ReturnValue of its response is 0(success)");
            uint openedFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];

            // Create a new subfolder in the opened folder
            // The new subfolder will be used as target folder
            RopCreateFolderRequest createFolderRequest;
            RopCreateFolderResponse createFolderResponse;

            createFolderRequest.RopId = (byte)RopId.RopCreateFolder;
            createFolderRequest.LogonId = TestSuiteBase.LogonId;
            createFolderRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            createFolderRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex1;
            createFolderRequest.FolderType = (byte)FolderType.Genericfolder;
            createFolderRequest.UseUnicodeStrings = Convert.ToByte(TestSuiteBase.Zero);
            createFolderRequest.OpenExisting = TestSuiteBase.NonZero;
            createFolderRequest.Reserved = TestSuiteBase.Reserved;
            createFolderRequest.DisplayName = Encoding.ASCII.GetBytes(TestSuiteBase.DisplayNameAndCommentForNonSearchFolder + "\0");
            createFolderRequest.Comment = Encoding.ASCII.GetBytes(TestSuiteBase.DisplayNameAndCommentForNonSearchFolder + "\0");

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the RopCreateFolder request.");

            this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                createFolderRequest,
                openedFolderHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            createFolderResponse = (RopCreateFolderResponse)this.response;
            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                createFolderResponse.ReturnValue,
                "if ROP succeeds, the ReturnValue of its response is 0(success)");
            uint targetFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];
            tableHandle = this.GetContentsTableHandle(targetFolderHandle);
            ulong folderId = createFolderResponse.FolderId;

            #endregion

            int waitTime = int.Parse(Common.GetConfigurationPropertyValue("WaitTime", this.Site));
            int maxRetryCount = int.Parse(Common.GetConfigurationPropertyValue("RetryCount", this.Site));
            int retryCount;
            bool needRetry = false;
            uint returnValue = 0;
            int loopcount = 50;
            List<ISerializable> multipleRopRequests = new List<ISerializable>();
            List<IDeserializable> multipleRopResponses = new List<IDeserializable>();
            List<uint> multipleInputObjects = new List<uint>();
            List<uint> multipleOutputObjects = new List<uint>();

            for (int i = 0; i < count; i++)
            {
                // If the RPC report error code reported by the following three ROP methods is 1726 (The remote procedure call failed), 
                // re-do the common steps of this case.
                if (returnValue == 1726)
                {
                    // Step 1: Create a message.
                    #region Create message
                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "If RPC error code is 1726, re-connect to server.");
                    this.cropsAdapter.RpcConnect(
                        Common.GetConfigurationPropertyValue("SutComputerName", this.Site),
                        ConnectionType.PrivateMailboxServer,
                        Common.GetConfigurationPropertyValue("UserEssdn", this.Site),
                        Common.GetConfigurationPropertyValue("Domain", this.Site),
                        Common.GetConfigurationPropertyValue("AdminUserName", this.Site),
                        Common.GetConfigurationPropertyValue("PassWord", this.Site));
                    logonResponse = this.Logon(LogonType.Mailbox, this.userDN, out this.inputObjHandle);
                    #endregion

                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopOpenFolder request.");

                    this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                        openFolderRequest,
                        this.inputObjHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.SuccessResponse);
                    openFolderResponse = (RopOpenFolderResponse)this.response;

                    Site.Assert.AreEqual<uint>(
                        TestSuiteBase.SuccessReturnValue,
                        openFolderResponse.ReturnValue,
                        "if ROP succeeds, the ReturnValue of its response is 0(success)");
                    openedFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];

                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopCreateFolder request.");

                    this.responseSOHs = this.cropsAdapter.ProcessSingleRop(
                        createFolderRequest,
                        openedFolderHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.SuccessResponse);
                    createFolderResponse = (RopCreateFolderResponse)this.response;
                    Site.Assert.AreEqual<uint>(
                        TestSuiteBase.SuccessReturnValue,
                        createFolderResponse.ReturnValue,
                        "if ROP succeeds, the ReturnValue of its response is 0(success)");
                    targetFolderHandle = this.responseSOHs[0][openFolderResponse.OutputHandleIndex];
                    tableHandle = this.GetContentsTableHandle(targetFolderHandle);
                    folderId = createFolderResponse.FolderId;
                }

                // Step 1: Create a message.
                #region Create message

                createMessageRequest.FolderId = logonResponse.FolderIds[4];

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 1:Begin to send the RopCreateMessage request in CreateVastMessages method.");

                retryCount = maxRetryCount;
                do
                {
                    multipleRopRequests.Clear();
                    multipleRopResponses.Clear();
                    multipleOutputObjects.Clear();
                    multipleInputObjects.Clear();

                    // Send multiple RopCreateMessage to create messages.
                    for (int t = 0; t < loopcount; t++)
                    {
                        createMessageRequest.FolderId = folderId;
                        createMessageRequest.InputHandleIndex = 0;
                        createMessageRequest.OutputHandleIndex = Convert.ToByte(t + 1);
                        multipleRopRequests.Add(createMessageRequest);
                        if (t == 0)
                        {
                            multipleInputObjects.Add(this.inputObjHandle);
                        }
                        else
                        {
                            multipleInputObjects.Add(TestSuiteBase.DefaultFolderHandle);
                        }
                    }

                    // An additional default handle is needed since the output handle index is from 1 to t+1 in the above loop, and the last one is not added in the above loop.
                    multipleInputObjects.Add(TestSuiteBase.DefaultFolderHandle);

                    this.responseSOHs = this.cropsAdapter.ProcessMutipleRops(
                      multipleRopRequests,
                      multipleInputObjects,
                      ref multipleRopResponses,
                      ref this.rawData,
                      RopResponseType.SuccessResponse);

                    for (int t = 0; t < multipleRopResponses.Count; t++)
                    {
                        if (multipleRopResponses[t] is RopBackoffResponse)
                        {
                            needRetry = true;
                            break;
                        }
                    }

                    System.Threading.Thread.Sleep(waitTime);
                    retryCount--;
                }
                while (needRetry && retryCount >= 0);

                Site.Assert.IsTrue(retryCount >= 0, "The case {0} failed since server is busy, reduce your server load and try again.", this.TestContext.TestName);

                // If the error code is 1726, continue this loop.
                if (returnValue == 1726)
                {
                    continue;
                }

                for (int t = 0; t < multipleRopResponses.Count; t++)
                {
                    if (multipleRopResponses[t] is RopCreateMessageResponse)
                    {
                        createMessageResponse = (RopCreateMessageResponse)multipleRopResponses[t];
                        Site.Assert.AreEqual<uint>(
                            TestSuiteBase.SuccessReturnValue,
                            createMessageResponse.ReturnValue,
                            "if ROP succeeds, the ReturnValue of its response is 0(success)");
                        uint targetMessageHandle = this.responseSOHs[0][createMessageResponse.OutputHandleIndex];
                        multipleOutputObjects.Add(targetMessageHandle);
                    }
                }
                #endregion

                // Step 2: Save the created message.
                #region Save message

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopSaveChangesMessage request in CreateVastMessages method.");

                needRetry = false;
                retryCount = maxRetryCount;

                do
                {
                    multipleRopRequests.Clear();
                    multipleRopResponses.Clear();

                    // Send multiple RopSaveChangesMessage requests to save the created messages.
                    for (int t = 0; t < loopcount; t++)
                    {
                        saveChangesMessageRequest.InputHandleIndex = Convert.ToByte(t);
                        multipleRopRequests.Add(saveChangesMessageRequest);
                    }

                    this.responseSOHs = this.cropsAdapter.ProcessMutipleRops(
                     multipleRopRequests,
                     multipleOutputObjects,
                     ref multipleRopResponses,
                     ref this.rawData,
                     RopResponseType.SuccessResponse);

                    for (int t = 0; t < multipleRopResponses.Count; t++)
                    {
                        if (multipleRopResponses[t] is RopSaveChangesMessageResponse)
                        {
                            saveChangesMessageResponse = (RopSaveChangesMessageResponse)multipleRopResponses[t];
                            if (saveChangesMessageResponse.ReturnValue == 0x80040401)
                            {
                                needRetry = true;
                                break;
                            }
                        }
                        else if (this.response is RopBackoffResponse)
                        {
                            needRetry = false;
                            break;
                        }
                    }

                    System.Threading.Thread.Sleep(waitTime);
                    retryCount--;
                }
                while (this.response is RopBackoffResponse && retryCount >= 0);

                Site.Assert.IsTrue(retryCount >= 0, "The case {0} failed since server is busy, reduce your server load and try again.", this.TestContext.TestName);

                // If the error code is 1726, continue this loop.
                if (returnValue == 1726)
                {
                    continue;
                }

                for (int t = 0; t < multipleRopResponses.Count; t++)
                {
                    if (multipleRopResponses[t] is RopSaveChangesMessageResponse)
                    {
                        saveChangesMessageResponse = (RopSaveChangesMessageResponse)multipleRopResponses[t];
                        Site.Assert.AreEqual<uint>(
                            TestSuiteBase.SuccessReturnValue,
                            saveChangesMessageResponse.ReturnValue,
                        "if ROP succeeds, the ReturnValue of its response is 0(success)");
                    }
                }

                #endregion

                // Step 3: Send the RopRelease request to release all resources associated with a Server object.
                #region Release all resources

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2:Begin to send the RopRelease request in CreateVastMessages method.");
                needRetry = false;
                retryCount = maxRetryCount;

                do
                {
                    multipleRopRequests.Clear();
                    multipleRopResponses.Clear();
                    for (int t = 0; t < loopcount; t++)
                    {
                        releaseRequest.InputHandleIndex = Convert.ToByte(t);
                        multipleRopRequests.Add(releaseRequest);
                    }

                    this.responseSOHs = this.cropsAdapter.ProcessMutipleRops(
                     multipleRopRequests,
                     multipleOutputObjects,
                     ref multipleRopResponses,
                     ref this.rawData,
                     RopResponseType.SuccessResponse);

                    if (multipleRopResponses.Count != 0)
                    {
                        for (int t = 0; t < multipleRopResponses.Count; t++)
                        {
                            if (multipleRopResponses[t] is RopBackoffResponse)
                            {
                                needRetry = true;
                                break;
                            }
                        }
                    }

                    System.Threading.Thread.Sleep(waitTime);
                    retryCount--;
                }
                while (needRetry && retryCount >= 0);

                Site.Assert.IsTrue(retryCount >= 0, "The case {0} failed since server is busy, reduce your server load and try again.", this.TestContext.TestName);

                // If the error code is 1726, continue this loop.
                if (returnValue == 1726)
                {
                    continue;
                }
                #endregion
            }

            // If the error code 1726 occurs on the last time of the above "for" loop, re-do the common steps.
            if (returnValue == 1726)
            {
                #region The common steps
                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "If RPC error code is 1726, re-connect to server.");
                this.cropsAdapter.RpcConnect(
                    Common.GetConfigurationPropertyValue("SutComputerName", this.Site),
                    ConnectionType.PrivateMailboxServer,
                    Common.GetConfigurationPropertyValue("UserEssdn", this.Site),
                    Common.GetConfigurationPropertyValue("Domain", this.Site),
                    Common.GetConfigurationPropertyValue("AdminUserName", this.Site),
                    Common.GetConfigurationPropertyValue("PassWord", this.Site));
                logonResponse = this.Logon(LogonType.Mailbox, this.userDN, out this.inputObjHandle);
                #endregion
            }
        }
        /// <summary>
        /// This ROP releases all resources associated with a server object. 
        /// </summary>
        /// <param name="handle">The handle to operate.</param>
        private void RopRelease(uint handle)
        {
            this.rawDataValue = null;
            this.responseValue = null;
            this.responseSOHsValue = null;

            RopReleaseRequest releaseRequest = new RopReleaseRequest()
            {
                RopId = (byte)RopId.RopRelease,
                LogonId = LogonId,
                InputHandleIndex = (byte)HandleIndex.FirstIndex
            };

            // The RopRelease ROP doesn't return response from server.
            this.responseSOHsValue = this.ProcessSingleRop(releaseRequest, handle, ref this.responseValue, ref this.rawDataValue, RopResponseType.SuccessResponse);
        }
        /// <summary>
        /// Overrides TestClassBase's TestCleanup()
        /// </summary>
        protected override void TestCleanup()
        {
            if (this.NeedCleanup == false)
            {
                return;
            }

            // Reinitialize to connect to the server use administrator for test cleanup.
            this.Adapter.DoDisconnect();
            this.Adapter.DoConnect(ConnectionType.PrivateMailboxServer);
            uint logonHandle = 0;
            this.Logon(LogonFlags.Private, out logonHandle);
            ulong folderId = this.GetSubfolderIDByName(this.DefaultFolderIds[this.inboxIndex], logonHandle, this.RootFolder);

            if (folderId != 0)
            {
                uint inboxFolderHandle = 0;
                this.OpenFolder(logonHandle, this.DefaultFolderIds[this.inboxIndex], ref inboxFolderHandle);

                RopDeleteFolderRequest deleteFolderRequest = new RopDeleteFolderRequest();
                RopDeleteFolderResponse deleteFolderResponse;
                deleteFolderRequest.RopId = (byte)RopId.RopDeleteFolder;
                deleteFolderRequest.LogonId = Constants.CommonLogonId;
                deleteFolderRequest.InputHandleIndex = Constants.CommonInputHandleIndex;

                // Set the DeleteFolderFlags to indicate hard delete the common generic folder,
                // including all folders and messages under the folder.
                deleteFolderRequest.DeleteFolderFlags = (byte)DeleteFolderFlags.DelFolders
                    | (byte)DeleteFolderFlags.DelMessages
                    | (byte)DeleteFolderFlags.DeleteHardDelete;
                deleteFolderRequest.FolderId = this.RootFolderId;

                int count = 0;
                bool rootFolderCleanUpSuccess = false;
                do
                {
                    deleteFolderResponse = this.Adapter.DeleteFolder(deleteFolderRequest, inboxFolderHandle, ref this.responseHandles);
                    if (deleteFolderResponse.ReturnValue == Constants.SuccessCode && deleteFolderResponse.PartialCompletion == 0)
                    {
                        rootFolderCleanUpSuccess = true;
                    }
                    else
                    {
                        Thread.Sleep(this.WaitTime);
                    }

                    if (count > this.RetryCount)
                    {
                        break;
                    }

                    count++;
                }
                while (!rootFolderCleanUpSuccess);
            }

            #region  RopRelease
            RopReleaseRequest releaseRequest = new RopReleaseRequest();
            object ropResponse = null;
            releaseRequest.RopId = (byte)RopId.RopRelease;
            releaseRequest.LogonId = Constants.CommonLogonId;
            releaseRequest.InputHandleIndex = Constants.CommonInputHandleIndex;
            this.Adapter.DoRopCall(releaseRequest, this.LogonHandle, ref ropResponse, ref this.responseHandles);
            #endregion

            this.responseHandles = null;
            this.Adapter.DoDisconnect();
            this.Adapter.Reset();
        }
        public void MSOXCMSG_S03_TC03_RopSetReadFlagsAsyncDisable()
        {
            this.CheckMapiHttpIsSupported();
            this.ConnectToServer(ConnectionType.PrivateMailboxServer);

            List<PropertyTag> propertyTags = new List<PropertyTag>
            {
                PropertyHelper.PropertyTagDic[PropertyNames.PidTagMessageFlags]
            };
            List<PropertyObj> ps = new List<PropertyObj>();

            #region Call RopLogon to logon specific private mailbox and SUPPORT_PROGRESS flag is not set in the OpenFlags field.
            RopLogonResponse logonResponse = this.Logon(LogonType.Mailbox, out this.insideObjHandle);
            #endregion

            #region Call RopCreateMessage to create a new Message object.
            uint targetMessageHandle = this.CreatedMessage(logonResponse.FolderIds[4], this.insideObjHandle);
            #endregion

            #region Call RopSaveChangesMessage to save the Message object created step 2.
            RopSaveChangesMessageResponse saveChangesMessageResponse = this.SaveMessage(targetMessageHandle, (byte)SaveFlags.ForceSave);
            Site.Assert.AreEqual<uint>(TestSuiteBase.Success, saveChangesMessageResponse.ReturnValue, TestSuiteBase.ROPSucceedMsg);
            ulong[] messageIds = new ulong[1];
            messageIds[0] = saveChangesMessageResponse.MessageId;

            ps = this.GetSpecificPropertiesOfMessage(logonResponse.FolderIds[4], messageIds[0], this.insideObjHandle, propertyTags);
            PropertyObj pidTagMessageFlagsBeforeSet = PropertyHelper.GetPropertyByName(ps, PropertyNames.PidTagMessageFlags);
            #endregion

            #region Call RopOpenFolder to open inbox folder.
            uint folderHandle = this.OpenSpecificFolder(logonResponse.FolderIds[4], this.insideObjHandle);
            #endregion

            #region Call RopSetReadFlags to change the state of the PidTagMessageFlags property and the WantAsynchronous flag is set in RopSetReadFlags.
            // RopSetReadFlags
            RopSetReadFlagsRequest setReadFlagsRequet = new RopSetReadFlagsRequest()
            {
                RopId = (byte)RopId.RopSetReadFlags,
                LogonId = CommonLogonId,
                InputHandleIndex = CommonInputHandleIndex,
                WantAsynchronous = 0x01,
                ReadFlags = (byte)ReadFlags.ClearReadFlag,
                MessageIds = messageIds,
                MessageIdCount = Convert.ToUInt16(messageIds.Length)
            };
            this.ResponseSOHs = this.MSOXCMSGAdapter.DoRopCall(setReadFlagsRequet, folderHandle, ref this.response, ref this.rawData, GetPropertiesFlags.None);
            RopSetReadFlagsResponse setReadFlagesResponse = (RopSetReadFlagsResponse)this.response;
            Site.Assert.AreEqual<uint>(TestSuiteBase.Success, setReadFlagesResponse.ReturnValue, TestSuiteBase.ROPSucceedMsg);

            #region Verify MS-OXCMSG_R1510, MS-OXCMSG_R1512, MS-OXCMSG_R1917, MS-OXCMSG_R1918
            // Add the debug information
            this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCMSG_R1510");

            // Verify MS-OXCMSG requirement: MS-OXCMSG_R1510
            bool isVerifiedR1510 = this.response is RopSetReadFlagsResponse;

            this.Site.CaptureRequirementIfIsTrue(
                isVerifiedR1510,
                1510,
                @"[In Receiving a RopSetReadFlags ROP Request] If the server has not received a SUPPORT_PROGRESS flag in the request buffer of the RopLogon ROP ([MS-OXCROPS] section 2.2.3.1), the server MUST disable asynchronous processing for the RopSetReadFlags ROP ([MS-OXCROPS] section 2.2.6.10), overriding any value of the WantAsynchronous flag.");

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

                // Verify MS-OXCMSG requirement: MS-OXCMSG_R1917
                this.Site.CaptureRequirementIfIsNotInstanceOfType(
                    this.response,
                    typeof(RopProgressResponse),
                    1917,
                    @"[In Appendix A: Product Behavior] Implementation does support this behavior [disable asynchronous processing of the RopSetReadFlags ROP and doesn't return the RopProgress ROP whether or not the WantAsynchronous flag is set if the SUPPORT_PROGRESS flag is not set by the client in the OpenFlags field in the RopLogon ROP]. (Exchange 2010 SP2 and above follow this behavior.)");
            }
            
            ps = this.GetSpecificPropertiesOfMessage(logonResponse.FolderIds[4], messageIds[0], this.insideObjHandle, propertyTags);
            PropertyObj pidTagMessageFlagsAfterSet = PropertyHelper.GetPropertyByName(ps, PropertyNames.PidTagMessageFlags);

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

            // Verify MS-OXCMSG requirement: MS-OXCMSG_R1512
            this.Site.CaptureRequirementIfAreNotEqual<int>(
                (int)pidTagMessageFlagsBeforeSet.Value,
                (int)pidTagMessageFlagsAfterSet.Value,
                1512,
                @"[In Receiving a RopSetReadFlags ROP Request] If the client does not pass the SUPPORT_PROGRESS flag, the server will process the entire RopSetReadFlags ROP request before returning a response to the client.");
            #endregion
            #endregion

            #region Call RopRelease to release all resources.
            RopReleaseRequest releaseRequest = new RopReleaseRequest()
            {
                RopId = (byte)RopId.RopRelease, // RopId 0x01 indicates RopRelease
                LogonId = CommonLogonId, // The logonId 0x00 is associated with this operation.
                InputHandleIndex = CommonInputHandleIndex // This index specifies the location 0x00 in the Server Object Handle Table where the handle for the input Server Object is stored. 
            };
            this.ResponseSOHs = this.MSOXCMSGAdapter.DoRopCall(releaseRequest, targetMessageHandle, ref this.response, ref this.rawData, GetPropertiesFlags.None);

            releaseRequest = new RopReleaseRequest()
            {
                RopId = (byte)RopId.RopRelease, // RopId 0x01 indicates RopRelease
                LogonId = CommonLogonId, // The logonId 0x00 is associated with this operation.
                InputHandleIndex = CommonInputHandleIndex // This index specifies the location 0x00 in the Server Object Handle Table where the handle for the input Server Object is stored. 
            };
            this.ResponseSOHs = this.MSOXCMSGAdapter.DoRopCall(releaseRequest, folderHandle, ref this.response, ref this.rawData, GetPropertiesFlags.None);
            #endregion
        }
        /// <summary>
        /// Overrides TestClassBase's TestCleanup()
        /// </summary>
        protected override void TestCleanup()
        {
            if (this.NeedCleanup == true)
            {
                RopDeleteFolderRequest deleteFolderRequest = new RopDeleteFolderRequest
                {
                    RopId = (byte)RopId.RopDeleteFolder,
                    LogonId = Constants.CommonLogonId,
                    InputHandleIndex = Constants.CommonInputHandleIndex,
                    DeleteFolderFlags =
                        (byte)DeleteFolderFlags.DelMessages | (byte)DeleteFolderFlags.DelFolders |
                        (byte)DeleteFolderFlags.DeleteHardDelete,
                    FolderId = this.publicRootFolderId
                };
                RopDeleteFolderResponse deleteFolderResponse = this.Adapter.DeleteFolder(deleteFolderRequest, this.publicFoldersHandle, ref this.responseHandles);
                Site.Assert.AreEqual<uint>(0, deleteFolderResponse.ReturnValue, "RopDeleteFolderResponse ROP operation performs successfully!");

                #region  Roprelease
                RopReleaseRequest releaseRequest = new RopReleaseRequest();
                object ropResponse = null;
                releaseRequest.RopId = (byte)RopId.RopRelease;
                releaseRequest.LogonId = Constants.CommonLogonId;
                releaseRequest.InputHandleIndex = Constants.CommonInputHandleIndex;
                this.Adapter.DoRopCall(releaseRequest, this.LogonHandle, ref ropResponse, ref this.responseHandles);
                #endregion

                this.publicLogonHandle = 0;
                this.responseHandles = null;
                this.Adapter.DoDisconnect();
            }
        }
        public void MSOXCMSG_S03_TC08_RopSetReadFlagsWithPartialCompletion()
        {
            this.CheckMapiHttpIsSupported();
            this.ConnectToServer(ConnectionType.PrivateMailboxServer);

            #region Call RopLogon to logon the private mailbox.
            // Create a message
            RopLogonResponse logonResponse = this.Logon(LogonType.Mailbox, out this.insideObjHandle);
            #endregion

            #region Call RopCreateMessage to create Message object in inbox folder.
            uint targetMessageHandle = this.CreatedMessage(logonResponse.FolderIds[4], this.insideObjHandle);
            #endregion

            #region Call RopSaveChangesMessage to save created message.
            RopSaveChangesMessageResponse saveChangesMessageResponse = this.SaveMessage(targetMessageHandle, (byte)SaveFlags.ForceSave);
            ulong[] messageIds = new ulong[2];
            messageIds[0] = saveChangesMessageResponse.MessageId;
            messageIds[1] = saveChangesMessageResponse.MessageId + 1;

            Site.Assert.AreEqual<uint>(TestSuiteBase.Success, saveChangesMessageResponse.ReturnValue, TestSuiteBase.ROPSucceedMsg);
            #endregion

            #region Call RopOpenFolder to open inbox folder.
            uint folderHandle = this.OpenSpecificFolder(logonResponse.FolderIds[4], this.insideObjHandle);
            #endregion

            #region Call RopSetReadFlags to change the state of the PidTagMessageFlags property and the MessageIds contains a MessageId that the message does not exist.
            // RopSetReadFlags
            RopSetReadFlagsRequest setReadFlagsRequet = new RopSetReadFlagsRequest()
            {
                RopId = (byte)RopId.RopSetReadFlags,
                LogonId = CommonLogonId,
                InputHandleIndex = CommonInputHandleIndex,
                WantAsynchronous = 0x01,
                ReadFlags = (byte)ReadFlags.ClearReadFlag,
                MessageIds = messageIds,
                MessageIdCount = Convert.ToUInt16(messageIds.Length)
            };
            this.ResponseSOHs = this.MSOXCMSGAdapter.DoRopCall(setReadFlagsRequet, folderHandle, ref this.response, ref this.rawData, GetPropertiesFlags.None);
            RopSetReadFlagsResponse setReadFlagesResponse = (RopSetReadFlagsResponse)this.response;
            if(Common.IsRequirementEnabled(3021,this.Site))
            {
                // Add the debug information
                this.Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCMSG_R3021");

                // Verify MS-OXCMSG requirement: MS-OXCMSG_R3021
                this.Site.CaptureRequirementIfAreNotEqual<uint>(
                    0,
                    setReadFlagesResponse.PartialCompletion,
                    3021,
                    @"[In Appendix A: Product Behavior] [PartialCompletion] A nonzero value indicates the server was unable to modify one or more of the Message objects represented in the MessageIds field. (Exchange 2007 and exchange 2016 follow this behavior.)");

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

                // Verify MS-OXCMSG requirement: MS-OXCMSG_R1514
                this.Site.CaptureRequirementIfAreNotEqual<uint>(
                    0,
                    setReadFlagesResponse.PartialCompletion,
                    1514,
                    @"[In Receiving a RopSetReadFlags ROP Request] If the server is unable to modify one or more of the Message objects that are specified in the MessageIds field, as specified in section 2.2.3.10.1, of the request buffer, then the server returns the PartialCompletion flag, as specified in section 2.2.3.10.2, in the response buffer.");
            }
            #endregion

            #region Call RopRelease to release all resources.
            RopReleaseRequest releaseRequest = new RopReleaseRequest()
            {
                RopId = (byte)RopId.RopRelease, // RopId 0x01 indicates RopRelease
                LogonId = CommonLogonId, // The logonId 0x00 is associated with this operation.
                InputHandleIndex = CommonInputHandleIndex // This index specifies the location 0x00 in the Server Object Handle Table where the handle for the input Server Object is stored. 
            };
            this.ResponseSOHs = this.MSOXCMSGAdapter.DoRopCall(releaseRequest, targetMessageHandle, ref this.response, ref this.rawData, GetPropertiesFlags.None);

            releaseRequest = new RopReleaseRequest()
            {
                RopId = (byte)RopId.RopRelease, // RopId 0x01 indicates RopRelease
                LogonId = CommonLogonId, // The logonId 0x00 is associated with this operation.
                InputHandleIndex = CommonInputHandleIndex // This index specifies the location 0x00 in the Server Object Handle Table where the handle for the input Server Object is stored. 
            };
            this.ResponseSOHs = this.MSOXCMSGAdapter.DoRopCall(releaseRequest, folderHandle, ref this.response, ref this.rawData, GetPropertiesFlags.None);
            #endregion
        }
        public void MSOXCROPS_S06_TC03_TestRopProgress()
        {
            this.CheckTransportIsSupported();

            this.cropsAdapter.RpcConnect(
                Common.GetConfigurationPropertyValue("SutComputerName", this.Site),
                ConnectionType.PrivateMailboxServer,
                Common.GetConfigurationPropertyValue("UserEssdn", this.Site),
                Common.GetConfigurationPropertyValue("Domain", this.Site),
                Common.GetConfigurationPropertyValue("AdminUserName", this.Site),
                Common.GetConfigurationPropertyValue("PassWord", this.Site));

            // Refer to MS-OXCPRPT: The initial release version of Exchange 2010 does not implement the RopProgress ROP.
            if (Common.IsRequirementEnabled(86601, this.Site))
            {
                // Step 1: Preparations-Open a folder and construct emptyFolderRequest.
                #region Common methods

                // Log on to a private mailbox.
                RopLogonResponse logonResponse = Logon(LogonType.Mailbox, this.userDN, out inputObjHandle);
                RopCreateMessageRequest createMessageRequest = new RopCreateMessageRequest();
                RopSaveChangesMessageRequest saveChangesMessageRequest = new RopSaveChangesMessageRequest();
                RopReleaseRequest releaseRequest = new RopReleaseRequest();
                this.PrepareRops(logonResponse, ref createMessageRequest, ref saveChangesMessageRequest, ref releaseRequest);
                uint tableHandle;

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 1:Call CreateVastMessages method to create Vast Messages In InBox.");

                string transportSeq = Common.GetConfigurationPropertyValue("TransportSeq", this.Site).ToLower();
                if (transportSeq == "mapi_http")
                {
                    this.CreateVastMessages(ref logonResponse, out tableHandle, TestSuiteBase.MessagesCount / 50, createMessageRequest, saveChangesMessageRequest, releaseRequest);
                }
                else
                {
                    this.CreateSingleProcessEachLoop(ref logonResponse, out tableHandle, TestSuiteBase.MessagesCount, createMessageRequest, saveChangesMessageRequest, releaseRequest);
                }

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 1:Call CreateVastMessages method to create Vast Messages In InBox.");

                // Call GetOpenedFolderHandle to get the opened folder handle.
                uint openedFolderHandle = this.GetOpenedFolderHandle(logonResponse.FolderIds[4], inputObjHandle);

                #endregion

                // Step 2: Verify the RopProgress success response.
                #region RopProgress success response

                // Send the RopEmptyFolder request to delete all messages and subfolders from opened folder.
                #region RopEmptyFolder request

                RopProgressRequest progressRequest;
                RopEmptyFolderRequest emptyFolderRequest;

                emptyFolderRequest.RopId = (byte)RopId.RopEmptyFolder;
                emptyFolderRequest.LogonId = TestSuiteBase.LogonId;
                emptyFolderRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
                emptyFolderRequest.WantAsynchronous = TestSuiteBase.NonZero;
                emptyFolderRequest.WantDeleteAssociated = TestSuiteBase.NonZero;

                #endregion

                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the RopEmptyFolder request.");

                // Send the RopEmptyFolder request.
                this.responseSOHs = cropsAdapter.ProcessSingleRop(
                    emptyFolderRequest,
                    openedFolderHandle,
                    ref this.response,
                    ref this.rawData,
                    RopResponseType.SuccessResponse);

                if (response is RopProgressResponse)
                {
                    RopProgressResponse ropProgressResponse = (RopProgressResponse)response;

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

                    // Verify MS-OXCROPS requirement: MS-OXCROPS_R86601
                    Site.CaptureRequirementIfAreEqual<uint>(
                        TestSuiteBase.SuccessReturnValue,
                        ropProgressResponse.ReturnValue,
                        86601,
                        @"[In Appendix A: Product Behavior] Implementation does implement the RopProgress ROP ([MS-OXCROPS] section 2.2.8.13). (Exchange 2007 and Exchange 2013 follow this behavior.)");
                }

                #endregion

                if (Common.IsRequirementEnabled(3155, this.Site))
                {
                    // Step 3: Send the RopProgress request and verify the failure response.
                    #region Step 3: Send the RopProgress request and verify the failure response.

                    progressRequest.RopId = (byte)RopId.RopProgress;
                    progressRequest.LogonId = TestSuiteBase.LogonId;
                    progressRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex1;
                    progressRequest.WantCancel = Convert.ToByte(TestSuiteBase.Zero);

                    Site.Log.Add(LogEntryKind.Debug, "Step 3: Begin to send the RopProgress request.");

                    // Send the RopProgress request and verify the success response.
                    this.responseSOHs = cropsAdapter.ProcessSingleRop(
                        progressRequest,
                        this.inputObjHandle,
                        ref this.response,
                        ref this.rawData,
                        RopResponseType.FailureResponse);

                    #endregion
                }
            }
        }
        /// <summary>
        /// Release resources.
        /// </summary>
        /// <param name="handle">Unsigned integer value indicates the Server object Handle</param>
        protected void ReleaseRop(uint handle)
        {
            RopReleaseRequest relR = new RopReleaseRequest
            {
                InputHandleIndex = CommonInputHandleIndex,
                RopId = (byte)RopId.RopRelease,
                LogonId = CommonLogonId
            };

            this.ResponseSOHs = this.MSOXCMSGAdapter.DoRopCall(relR, handle, ref this.response, ref this.rawData, GetPropertiesFlags.None);
        }
        /// <summary>
        /// Release resources.
        /// </summary>
        /// <param name="handle">Unsigned integer value indicates the Server object Handle</param>
        public void ReleaseRop(uint handle)
        {
            RopReleaseRequest relR = new RopReleaseRequest
            {
                InputHandleIndex = 0x00,
                RopId = (byte)RopId.RopRelease,
                LogonId = 0x00
            };

            this.responseSOHs = this.DoRPCCall(relR, handle, ref this.response, ref this.rawData);
        }
        public void MSOXCROPS_S12_TC01_TestRopPending()
        {
            this.CheckTransportIsSupported();

            this.cropsAdapter.RpcConnect(
                Common.GetConfigurationPropertyValue("SutComputerName", this.Site),
                ConnectionType.PrivateMailboxServer,
                Common.GetConfigurationPropertyValue("UserEssdn", this.Site),
                Common.GetConfigurationPropertyValue("Domain", this.Site),
                Common.GetConfigurationPropertyValue("AdminUserName", this.Site),
                Common.GetConfigurationPropertyValue("PassWord", this.Site));

            // Step 1: Send the RopRegisterNotification request and verify the success response.
            #region RopRegisterNotification success response

            // Log on to the private mailbox.
            RopLogonResponse logonResponse = Logon(LogonType.Mailbox, this.userDN, out inputObjHandle);

            RopRegisterNotificationRequest registerNotificationRequest;
            RopRegisterNotificationResponse registerNotificationResponse;

            registerNotificationRequest.RopId = (byte)RopId.RopRegisterNotification;

            registerNotificationRequest.LogonId = TestSuiteBase.LogonId;
            registerNotificationRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            registerNotificationRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex0;

            // The server MUST send notifications to the client when CriticalError events occur within the scope of interest
            registerNotificationRequest.NotificationTypes = (byte)NotificationTypes.NewMail;
            registerNotificationRequest.Reserved = TestSuiteBase.Reserved;

            // TRUE: the scope for notifications is the entire database
            registerNotificationRequest.WantWholeStore = TestSuiteBase.NonZero;

            registerNotificationRequest.FolderId = logonResponse.FolderIds[4];
            registerNotificationRequest.MessageId = MS_OXCROPSAdapter.MessageIdForRops;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 1: Begin to send the RopRegisterNotification request:NotificationTypes=0x02.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                registerNotificationRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            registerNotificationResponse = (RopRegisterNotificationResponse)response;

            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                registerNotificationResponse.ReturnValue,
                "If ROP succeeds, the ReturnValue of its response is 0 (success)");

            // Set NotificationTypes to 0x04, which means the server sends notifications to the client when ObjectCreated events occur
            // within the scope of interest, as specified in [MS-OXCNOTIF].
            registerNotificationRequest.NotificationTypes = (byte)NotificationTypes.ObjectCreated;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 1: Begin to send the RopRegisterNotification request:NotificationTypes=0x04.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                registerNotificationRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            registerNotificationResponse = (RopRegisterNotificationResponse)response;

            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                registerNotificationResponse.ReturnValue,
                "If ROP succeeds, the ReturnValue of its response is 0 (success)");

            // Set NotificationTypes to 0x08, which means the server sends notifications to the client when ObjectDeleted events occur
            // within the scope of interest, as specified in [MS-OXCNOTIF].
            registerNotificationRequest.NotificationTypes = (byte)NotificationTypes.ObjectDeleted;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 1: Begin to send the RopRegisterNotification request:NotificationTypes=0x08.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                registerNotificationRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            registerNotificationResponse = (RopRegisterNotificationResponse)response;

            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                registerNotificationResponse.ReturnValue,
                "If ROP succeeds, the ReturnValue of its response is 0 (success)");

            // Set NotificationTypes to 0x10, which means the server sends notifications to the client when ObjectModified events occur
            // within the scope of interest, as specified in [MS-OXCNOTIF].
            registerNotificationRequest.NotificationTypes = (byte)NotificationTypes.ObjectModified;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 1: Begin to send the RopRegisterNotification request:NotificationTypes=0x10.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                registerNotificationRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            registerNotificationResponse = (RopRegisterNotificationResponse)response;

            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                registerNotificationResponse.ReturnValue,
                "If ROP succeeds, the ReturnValue of its response is 0 (success)");

            // Set NotificationTypes to 0x20, which means the server sends notifications to the client when ObjectMoved events occur
            // within the scope of interest, as specified in [MS-OXCNOTIF].
            registerNotificationRequest.NotificationTypes = (byte)NotificationTypes.ObjectMoved;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 1: Begin to send the RopRegisterNotification request:NotificationTypes=0x20.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                registerNotificationRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            registerNotificationResponse = (RopRegisterNotificationResponse)response;

            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                registerNotificationResponse.ReturnValue,
                "If ROP succeeds, the ReturnValue of its response is 0 (success)");

            // Set NotificationTypes to 0x40, which means the server sends notifications to the client when ObjectCopied events occur
            // within the scope of interest, as specified in [MS-OXCNOTIF].
            registerNotificationRequest.NotificationTypes = (byte)NotificationTypes.ObjectCopied;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 1: Begin to send the RopRegisterNotification request:NotificationTypes=0x40.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                registerNotificationRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            registerNotificationResponse = (RopRegisterNotificationResponse)response;

            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                registerNotificationResponse.ReturnValue,
                "If ROP succeeds, the ReturnValue of its response is 0 (success)");

            // Set NotificationTypes to 0x80, which means the server sends notifications to the client when SearchCompleted events occur
            // within the scope of interest, as specified in [MS-OXCNOTIF].
            registerNotificationRequest.NotificationTypes = (byte)NotificationTypes.SearchCompleted;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 1: Begin to send the RopRegisterNotification request:NotificationTypes=0x80.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                registerNotificationRequest,
                this.inputObjHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            registerNotificationResponse = (RopRegisterNotificationResponse)response;

            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                registerNotificationResponse.ReturnValue,
                "If ROP succeeds, the ReturnValue of its response is 0 (success)");

            #endregion

            // Step 2: Create message,Save message to test RopPending, RopNotify and RopBufferTooSmall
            #region RopRegisterNotification success response

            #region prepare rops for createmessage, savemessage and release
            RopCreateMessageRequest createMessageRequest = new RopCreateMessageRequest();
            RopSaveChangesMessageRequest saveChangesMessageRequest = new RopSaveChangesMessageRequest();
            RopReleaseRequest releaseRequest = new RopReleaseRequest();
            this.PrepareRops(logonResponse, ref createMessageRequest, ref saveChangesMessageRequest, ref releaseRequest);
            #endregion
            // Totally create message loop count.
            int loopCount;
            uint tableHandle = 0;

            string transportSeq = Common.GetConfigurationPropertyValue("TransportSeq", this.Site).ToLower();
            if (transportSeq == "mapi_http")
            {
                loopCount = 20;
                this.CreateVastMessages(ref logonResponse, out tableHandle, loopCount, createMessageRequest, saveChangesMessageRequest, releaseRequest);
            }
            else
            {
                loopCount = 1000;
                this.CreateSingleProcessEachLoop(ref logonResponse, out tableHandle, loopCount, createMessageRequest, saveChangesMessageRequest, releaseRequest);
            }

            #region RopBufferTooSmall response

            List<ISerializable> ropRequests1 = new List<ISerializable>();
            List<uint> inputObjects1 = new List<uint>
            {
                this.inputObjHandle
            };
            List<IDeserializable> ropResponses1 = new List<IDeserializable>();
            RopGetPropertiesAllRequest getPropertiesAllRequest;

            getPropertiesAllRequest.RopId = (byte)RopId.RopGetPropertiesAll;
            getPropertiesAllRequest.LogonId = TestSuiteBase.LogonId;
            getPropertiesAllRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;

            // Set PropertySizeLimit, which specifies the maximum size allowed for a property value returned.
            getPropertiesAllRequest.PropertySizeLimit = TestSuiteBase.PropertySizeLimit;

            getPropertiesAllRequest.WantUnicode = Convert.ToUInt16(TestSuiteBase.Zero);
            byte count = 255;
            for (byte i = 1; i < count; i++)
            {
                ropRequests1.Add(getPropertiesAllRequest);
            }

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the ProcessMutipleRops request to verify RopBufferTooSmall response.");

            // Verify the RopBufferTooSmall
            this.responseSOHs = cropsAdapter.ProcessMutipleRops(ropRequests1, inputObjects1, ref ropResponses1, ref this.rawData, RopResponseType.FailureResponse);

            #endregion

            List<IDeserializable> ropResponses4 = new List<IDeserializable>();

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to resubmit all the GetPropertiesAll request.");

            // All the requests are GetPropertiesAllRequest, resubmit the request in another call and get the responses in the ropResponses4
            this.responseSOHs = cropsAdapter.ProcessMutipleRops(ropRequests1, inputObjects1, ref ropResponses4, ref this.rawData, RopResponseType.SuccessResponse);

            #region RopSetColumns success response

            RopSetColumnsRequest setColumnsRequest;
            RopSetColumnsResponse setColumnsResponse;

            PropertyTag[] propertyTags = CreateSampleContentsTablePropertyTags();
            setColumnsRequest.RopId = (byte)RopId.RopSetColumns;
            setColumnsRequest.LogonId = TestSuiteBase.LogonId;
            setColumnsRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            setColumnsRequest.SetColumnsFlags = (byte)AsynchronousFlags.None;
            setColumnsRequest.PropertyTagCount = (ushort)propertyTags.Length;
            setColumnsRequest.PropertyTags = propertyTags;

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the RopSetColumns request.");

            this.responseSOHs = cropsAdapter.ProcessSingleRop(
                setColumnsRequest,
                tableHandle,
                ref this.response,
                ref this.rawData,
                RopResponseType.SuccessResponse);
            setColumnsResponse = (RopSetColumnsResponse)response;
            Site.Assert.AreEqual<uint>(
                TestSuiteBase.SuccessReturnValue,
                setColumnsResponse.ReturnValue,
                "if ROP succeeds, the ReturnValue of its response is 0(success)");

            #endregion

            #region RopQueryRows success response: send RopSetColumns and RopQueryRows in a request buffer
            RopQueryRowsRequest queryRowsRequest;

            queryRowsRequest.RopId = (byte)RopId.RopQueryRows;
            queryRowsRequest.LogonId = TestSuiteBase.LogonId;
            queryRowsRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex0;
            queryRowsRequest.QueryRowsFlags = (byte)QueryRowsFlags.Advance;
            queryRowsRequest.ForwardRead = TestSuiteBase.NonZero;

            // Set RowCount to 0x01, which the number of requested rows, as specified in [MS-OXCROPS].
            queryRowsRequest.RowCount = TestSuiteBase.RowCount;

            List<ISerializable> ropRequests = new List<ISerializable>
            {
                setColumnsRequest, queryRowsRequest
            };
            createMessageRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex2;
            createMessageRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex3;
            createMessageRequest.FolderId = logonResponse.FolderIds[4];
            ropRequests.Add(createMessageRequest);
            saveChangesMessageRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex3;
            ropRequests.Add(saveChangesMessageRequest);
            List<uint> inputObjects = new List<uint>
            {
                tableHandle,
                0xFFFF,
                this.inputObjHandle,
                0xFFFF
            };

            // 0xFFFF indicates a default input handle.
            List<IDeserializable> ropResponses = new List<IDeserializable>();

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the multiple ROPs request to verify the RopNotify response.");

            // Verify the RopNotify
            this.responseSOHs = cropsAdapter.ProcessMutipleRops(ropRequests, inputObjects, ref ropResponses, ref this.rawData, RopResponseType.SuccessResponse);

            // Set RowCount to 0x0600, which the number of requested rows, as specified in [MS-OXCROPS].
            queryRowsRequest.RowCount = TestSuiteBase.RowCount;

            List<ISerializable> ropRequests2 = new List<ISerializable>
            {
                setColumnsRequest, queryRowsRequest
            };
            createMessageRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex2;
            createMessageRequest.OutputHandleIndex = TestSuiteBase.OutputHandleIndex3;
            createMessageRequest.FolderId = logonResponse.FolderIds[4];
            ropRequests2.Add(createMessageRequest);
            saveChangesMessageRequest.InputHandleIndex = TestSuiteBase.InputHandleIndex3;
            ropRequests2.Add(saveChangesMessageRequest);
            List<uint> inputObjects2 = new List<uint>
            {
                tableHandle,
                0xFFFF,
                this.inputObjHandle,
                0xFFFF
            };

            // 0xFFFF indicates a default input handle.
            List<IDeserializable> ropResponses2 = new List<IDeserializable>();

            // Add the debug information
            Site.Log.Add(LogEntryKind.Debug, "Step 2: Begin to send the multiple ROPs request to verify the RopPending response.");

            // Verify the RopPending
            this.responseSOHs = cropsAdapter.ProcessMutipleRops(ropRequests2, inputObjects2, ref ropResponses2, ref this.rawData, RopResponseType.SuccessResponse);

            bool isContainedRopPending = false;
            for (int i = 1; i < ropResponses2.Count; i++)
            {
                if (ropResponses2[i] is RopPendingResponse)
                {
                    isContainedRopPending = true;
                    break;
                }
            }

            // Send an empty ROP to verify all queued RopNotify response have got in last step.
            List<ISerializable> ropRequestsEmpty = new List<ISerializable>(0x02);
            List<IDeserializable> ropResponsesNull = new List<IDeserializable>();

            this.responseSOHs = cropsAdapter.ProcessMutipleRops(ropRequestsEmpty, inputObjects, ref ropResponsesNull, ref this.rawData, RopResponseType.SuccessResponse);

            if (ropResponsesNull.Count == 0)
            {
                if (Common.IsRequirementEnabled(469303, this.Site))
                {
                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCROPS_R469303");

                    // Verify MS-OXCROPS requirement: MS-OXCROPS_R469303
                    Site.CaptureRequirementIfIsTrue(
                        isContainedRopPending,
                        469303,
                        @"[In Appendix B: Product Behavior] Implementation does include a RopPending ROP response (section 2.2.14.3) even though the ROP output buffer contains all queued RopNotify ROP responses (section 2.2.14.2). (<16> Section 3.1.5.1.3: Exchange 2007 follows this behavior.)");
                }

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

                    // Verify MS-OXCROPS requirement: MS-OXCROPS_R4693031
                    Site.CaptureRequirementIfIsFalse(
                        isContainedRopPending,
                        4693031,
                        @"[In Appendix B: Product Behavior] Implementation does not include a RopPending ROP response if the ROP output buffer contain all queued RopNotify ROP responses. (Exchange 2010 and above follow this behavior.)");
                }
            }
            #endregion

            #endregion
        }