예제 #1
0
 public static void RopCopyToMethodForErrorCodeTable(CopyToCondition condition)
 {
     Condition.IsTrue(
         isInitialized &&
         isFirstObjectGot &&
         isSecondObjectGot &&
         (globalObj == ServerObjectType.Message ||
         globalObj == ServerObjectType.Attachment ||
         globalObj == ServerObjectType.Folder));
 }
        /// <summary>
        /// This method is used to copy or move properties from a source object to a destination object with error code returned. 
        /// </summary>
        /// <param name="condition">Specifies a special scenario of RopCopyTo.</param>
        public void RopCopyToMethodForErrorCodeTable(CopyToCondition condition)
        {
            // The source handle.
            uint sourceHandle = 0;

            // The destination handle.
            uint destHandle = 0;
            uint destMessageHandleFirst = 0;
            uint destMessageHandleSecond = 0;

            if ((condition == CopyToCondition.SourceMessageContainsDestMessage) || (condition == CopyToCondition.SourceMessageIndirectlyContainsDestMessage))
            {
                this.GetDestinationMessageHandle(cprptMessageHandle[0], out destMessageHandleFirst, out destMessageHandleSecond);
            }

            RopCreateFolderResponse createFolderResponse = new RopCreateFolderResponse();
            switch (condition)
            {
                case CopyToCondition.SourceDestNotCompatible:
                    sourceHandle = cprptMessageHandle[0];
                    destHandle = cprptFolderHandle[0];
                    break;
                case CopyToCondition.SourceContainsDest:
                    sourceHandle = cprptFolderHandle[2];
                    destHandle = this.RopCreateFolder(sourceHandle, out createFolderResponse, SubFolder, SubFolder, true);
                    break;
                case CopyToCondition.SourceDestHasSubObjWithSameDisplayName:
                    // Create sub folder for Folder1 and Folder2 with the same name.
                    this.RopCreateFolder(cprptFolderHandle[1], out createFolderResponse, SubFolder, SubFolder, true);
                    this.RopCreateFolder(cprptFolderHandle[2], out createFolderResponse, SubFolder, SubFolder, true);
                    sourceHandle = cprptFolderHandle[1];
                    destHandle = cprptFolderHandle[2];
                    break;
                case CopyToCondition.Normal:
                    sourceHandle = cprptMessageHandle[0];
                    destHandle = cprptMessageHandle[1];
                    break;
                case CopyToCondition.SourceMessageContainsDestMessage:
                    sourceHandle = cprptMessageHandle[0];
                    destHandle = destMessageHandleFirst;
                    break;
                case CopyToCondition.SourceMessageIndirectlyContainsDestMessage:
                    sourceHandle = cprptMessageHandle[0];
                    destHandle = destMessageHandleSecond;
                    break;
                default:
                    this.Site.Assert.Fail("Invalid CopyToCondition enum value {0}.", condition);
                    break;
            }

            // Copy subobject.
            byte wantSubObject = Convert.ToByte(true);

            RopCopyToResponse copyToRes = (RopCopyToResponse)this.RopCopyTo(sourceHandle, destHandle, (byte)HandleIndex.FirstIndex, (byte)HandleIndex.SecondIndex, 0, wantSubObject, (byte)RopCopyToCopyFlags.Move, null);

            this.VerifyRopCopyTo(copyToRes, condition, this.cprptCurrentType, CopyFlags.Move);
        }
예제 #3
0
        /// <summary>
        /// Verify the RopCopyTo operation related requirements.
        /// </summary>
        /// <param name="ropCopyToResponse">The RopCopyTo response buffer structure.</param>
        /// <param name="copyToCondition">The condition to generate the corresponding error codes.</param>
        /// <param name="objectType">Indicates which object type the RopCopyProperties operation is acting on.</param>
        /// <param name="copyFlags">Indicates the copy flags.</param>
        private void VerifyRopCopyTo(RopCopyToResponse ropCopyToResponse, CopyToCondition copyToCondition, ServerObjectType objectType, CopyFlags copyFlags)
        {
            // Since the RopCopyTo ROP response was parsed successfully, MS-OXCPRPT_R50702 can be captured directly.
            Site.CaptureRequirement(
                50702,
                @"[In Processing RopCopyTo] The server responds with a RopCopyTo ROP response buffer.");

            if (ropCopyToResponse.ReturnValue == (uint)CPRPTErrorCode.NotSupported)
            {
                // The parser has ensured the field satisfied the format, otherwise the response cannot be received.
                Site.CaptureRequirement(
                    "MS-OXCDATA",
                     928,
                     @"[In Error Codes] The numeric value (hex) for error code NotSupported is 0x80040102, %x02.01.04.80.");
            }

            if (ropCopyToResponse.ReturnValue == (uint)CPRPTErrorCode.None)
            {
                if (objectType == ServerObjectType.Message)
                {
                    // If the object type this operation acting on is Message object and this operation is performed successfully, then the following requirement can be captured.
                    Site.CaptureRequirement(
                        17201,
                        @"[In RopCopyTo ROP] This operation [RopCopyTo ROP] is valid on Message objects.");
                }

                if (objectType == ServerObjectType.Folder)
                {
                    if (copyFlags == CopyFlags.Move)
                    {
                        if (Common.IsRequirementEnabled(5070511, this.Site))
                        {
                            // If the implementation return a successful response, it means it doesn't return NotSupported error. So it can be capture directly.
                            Site.CaptureRequirement(
                                5070511,
                                @"[In Processing RopCopyTo] Implementation does not return a NotSupported error (0x80040102), if the original object is a Folder object and the CopyFlags field has the Move flag set. (Microsoft Exchange Server 2007 and above follow this behavior.)");
                        }
                    }

                    // If the object type this operation acting on is Folder object and this operation is performed successfully, then the following requirement can be captured.
                    Site.CaptureRequirement(
                        17203,
                        @"[In RopCopyTo ROP] This operation [RopCopyTo ROP] is valid on Folder objects.");
                }

                if (objectType == ServerObjectType.Attachment)
                {
                    // If the object type this operation acting on is Attachment object and this operation is performed successfully, then the following requirement can be captured.
                    Site.CaptureRequirement(
                        17202,
                        @"[In RopCopyTo ROP] This operation [RopCopyTo ROP] is valid on Attachment objects.");
                }

                // The parser has ensured the field satisfied the format, otherwise the response cannot be received.
                Site.CaptureRequirement(
                   192,
                   @"[In RopCopyTo ROP Response Buffer] propertyProblemCount: 2 bytes integer.");

                if (ropCopyToResponse.PropertyProblemCount != 0)
                {
                    for (int counter = 0; counter < ropCopyToResponse.PropertyProblems.Length; counter++) 
                    {
                        this.VerifyPropertyProblemSturctureInCDATA();
                    }

                    Site.CaptureRequirementIfAreEqual<ushort>(
                        ropCopyToResponse.PropertyProblemCount,
                        (ushort)ropCopyToResponse.PropertyProblems.Length,
                        19201,
                        @"[In RopCopyTo ROP Response Buffer] propertyProblemCount: An integer that specifies the number of elements contained in the PropertyProblems field. ");

                    // The parser has ensured the field satisfied the format, otherwise the response cannot be received.
                    Site.CaptureRequirement(
                        193,
                        @"[In RopCopyTo ROP Response Buffer] propertyProblems (variable): An array of PropertyProblem structures ([MS-OXCDATA] section 2.7).");
                }

                // The parser has ensured the field satisfied the format, otherwise the response cannot be received.
                Site.CaptureRequirement(
                    19601,
                    @"[In RopCopyTo ROP Response Buffer] DestHandleIndex (4 bytes):  An integer.");
            }

            if (ropCopyToResponse.ReturnValue.Equals((uint)CPRPTErrorCode.NullDestinationObject))
            {
                // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R195
                // The value of DestHandleIndex is not 0 means this field is present.
                Site.CaptureRequirementIfAreEqual<uint>(
                    1,
                    ropCopyToResponse.DestHandleIndex,
                    196,
                    @"[In RopCopyTo ROP Response Buffer] DestHandleIndex: The DestHandleIndex field MUST be set to the value of the DestHandleIndex field of the ROP request buffer");

                // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R739
                // The value of PropertyProblemCount is 0 means this field is not present.
                Site.CaptureRequirementIfAreEqual<ushort>(
                    0,
                    ropCopyToResponse.PropertyProblemCount,
                    739,
                    @"[In RopCopyTo ROP Response Buffer] PropertyProblemCount: This field MUST NOT be present if the ReturnValue field is set to NullDestinationObject (0x00000503).");

                // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R740
                // PropertyProblems is null means this field is not present.
                Site.CaptureRequirementIfIsNull(
                    ropCopyToResponse.PropertyProblems,
                    740,
                    @"[In RopCopyTo ROP Response Buffer] PropertyProblems: This field MUST NOT be present if the ReturnValue field is set to NullDestinationObject (0x00000503).");
            }
            else
            {
                // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R197
                // The value of DestHandleIndex is 0 means this field is not present.
                Site.CaptureRequirementIfAreEqual<uint>(
                     0,
                     ropCopyToResponse.DestHandleIndex,
                    197,
                    @"[In RopCopyTo ROP Response Buffer] DestHandleIndex: The DestHandleIndex field MUST NOT be present if the ReturnValue field is set to any value other than NullDestinationObject (0x00000503).");
            }

            if (copyToCondition == CopyToCondition.SourceContainsDest)
            {
                if (objectType == ServerObjectType.Folder)
                {
                    if (Common.IsRequirementEnabled(89603, this.Site))
                    {
                        Site.CaptureRequirementIfAreEqual<uint>(
                            (uint)CPRPTErrorCode.FolderCycle,
                            ropCopyToResponse.ReturnValue,
                            89603,
                            @"[In Processing RopCopyTo] Implementation does return error code ""0x8004060B"" with name ""FolderCycle"" when The source folder contains the destination folder.(Microsoft Exchange Server 2007 and above follow this behavior)");
                    }
                }
            }
            else if (copyToCondition == CopyToCondition.SourceDestNotCompatible)
            {
                // CopyToCondition.SourceDestNotCompatible means source object and destination object are not compatible with each other for the copy operation.
                bool isR890Satisfied = ropCopyToResponse.ReturnValue == (uint)CPRPTErrorCode.NotSupported;

                if (Common.IsRequirementEnabled(890, this.Site))
                {
                    // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R890
                    Site.CaptureRequirementIfIsTrue(
                        isR890Satisfied,
                        890,
                        @"[In Processing RopCopyTo] Implementation does return error code ""0x80040102"" with name ""NotSupported"",  when ""The source object and destination object are not compatible with each other for the copy operation."" (Microsoft Exchange Server 2007 and above follow this behavior)");

                    Site.CaptureRequirementIfIsTrue(
                        isR890Satisfied,
                        150,
                        @"[In RopCopyProperties ROP] Also, the source and destination object MUST be of the same type.");
                }
            }
            else if (copyToCondition == CopyToCondition.SourceDestHasSubObjWithSameDisplayName)
            {
                // CopyToCondition.SourceDestHasSubObjWithSameDisplayName means a sub-object cannot be copied because there is already a sub-object existing 
                // in the destination object with the same display name (PidTagDisplayName) as the sub-object to be copied.
                if (Common.IsRequirementEnabled(899, this.Site))
                {
                    // Add the debug information
                    Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCPRPT_R899, the return error code value is: {0}", ropCopyToResponse.ReturnValue);

                    // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R899
                    Site.CaptureRequirementIfAreEqual<uint>(
                        (uint)CPRPTErrorCode.CollidingNames,
                        ropCopyToResponse.ReturnValue,
                        899,
                        @"[In Processing RopCopyTo] Implementation does return error code ""0x80040604"" with name ""CollidingNames"", when a subobject cannot be copied because there is already a subobject existing in the destination object with the same display name, which is specified in the PidTagDisplayName property ([MS-OXCFOLD] section 2.2.2.2.2.4), as the subobject to be copied.(Microsoft Exchange Server 2007 and above follow this behavior)");
                }
            }
            else if (copyToCondition == CopyToCondition.SourceMessageContainsDestMessage && Common.IsRequirementEnabled(89601, this.Site))
            {
                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCPRPT_R89601, the return error code value is: {0}", ropCopyToResponse.ReturnValue);

                // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R89601
                Site.CaptureRequirementIfAreEqual<uint>(
                    (uint)CPRPTErrorCode.MessageCycle,
                    ropCopyToResponse.ReturnValue,
                    89601,
                    @"[In Appendix A: Product Behavior] Implementation does return error code ""0x00000504"" with name ""MessageCycle"" when the source message directly contains the destination message. (Exchange 2007 and above follow this behavior.)");
            }
            else if (copyToCondition == CopyToCondition.SourceMessageIndirectlyContainsDestMessage && Common.IsRequirementEnabled(89604, this.Site))
            {
                // Add the debug information
                Site.Log.Add(LogEntryKind.Debug, "Verify MS-OXCPRPT_R89604, the return error code value is: {0}", ropCopyToResponse.ReturnValue);

                // Verify MS-OXCPRPT requirement: MS-OXCPRPT_R89604
                Site.CaptureRequirementIfAreEqual<uint>(
                    (uint)CPRPTErrorCode.MessageCycle,
                    ropCopyToResponse.ReturnValue,
                    89604,
                    @"[In Appendix A: Product Behavior] Implementation does return error code ""0x00000504"" with name ""MessageCycle"" when the source message indirectly contains the destination message. (Exchange 2007 and above follow this behavior.)");            
            }
        }