public void BVT_ResilientHandle_Reconnect() { #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb21); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_LMR_REQUEST_RESILIENCY); TestConfig.CheckCreateContext(CreateContextTypeValue.SMB2_CREATE_DURABLE_HANDLE_RECONNECT); #endregion Guid clientGuid = Guid.NewGuid(); #region clientBeforeDisconnection Create a File BaseTestSite.Log.Add(LogEntryKind.TestStep, "Start the first client to create a file by sending the following requests: NEGOTIATE; SESSION_SETUP; TREE_CONNECT"); clientBeforeDisconnection.Negotiate(TestConfig.RequestDialects, TestConfig.IsSMB1NegotiateEnabled, clientGuid: clientGuid); clientBeforeDisconnection.SessionSetup(TestConfig.DefaultSecurityPackage, TestConfig.SutComputerName, TestConfig.AccountCredential, false); uint treeId; clientBeforeDisconnection.TreeConnect(sharePath, out treeId); FILEID fileId; Smb2CreateContextResponse[] createContextResponse; clientBeforeDisconnection.Create(treeId, fileName, CreateOptions_Values.FILE_NON_DIRECTORY_FILE, out fileId, out createContextResponse); #endregion #region Request Resilient Handle IOCTL_Response IOCTLResponse; byte[] inputInResponse; byte[] outputInResponse; Packet_Header packetHeader; BaseTestSite.Log.Add(LogEntryKind.TestStep, "The first client sends an IOCTL FSCTL_LMR_REQUEST_RESILLIENCY request."); clientBeforeDisconnection.ResiliencyRequest(treeId, fileId, TestConfig.MaxResiliencyTimeoutInSecond * 1000, NETWORK_RESILIENCY_REQUEST_SIZE, out packetHeader, out IOCTLResponse, out inputInResponse, out outputInResponse); #endregion BaseTestSite.Log.Add(LogEntryKind.TestStep, "Tear down the first client by sending DISCONNECT request."); clientBeforeDisconnection.Disconnect(); #region ClientAfterDisconnection Opens the Previously Created File with DurableHandleReconnect BaseTestSite.Log.Add(LogEntryKind.TestStep, "Start a second client by sending the following requests: NEGOTIATE; SESSION_SETUP; TREE_CONNECT"); clientAfterDisconnection.Negotiate(TestConfig.RequestDialects, TestConfig.IsSMB1NegotiateEnabled, clientGuid: clientGuid); clientAfterDisconnection.ReconnectSessionSetup(clientBeforeDisconnection, TestConfig.DefaultSecurityPackage, TestConfig.SutComputerName, TestConfig.AccountCredential, false); clientAfterDisconnection.TreeConnect(sharePath, out treeId); BaseTestSite.Log.Add(LogEntryKind.TestStep, "The second client sends CREATE request with SMB2_CREATE_DURABLE_HANDLE_RECONNECT create context to open the same file created by the first client."); clientAfterDisconnection.Create(treeId, fileName, CreateOptions_Values.FILE_NON_DIRECTORY_FILE, out fileId, out createContextResponse, RequestedOplockLevel_Values.OPLOCK_LEVEL_BATCH, new Smb2CreateContextRequest[] { new Smb2CreateDurableHandleReconnect { Data = fileId } }); #endregion #region Tear Down Client BaseTestSite.Log.Add(LogEntryKind.TestStep, "Tear down the second client by sending the following requests: CLOSE; TREE_DISCONNECT; LOG_OFF"); clientAfterDisconnection.Close(treeId, fileId); clientAfterDisconnection.TreeDisconnect(treeId); clientAfterDisconnection.LogOff(); #endregion }
public void ResilientOpenScavengerTimer_ReconnectBeforeTimeout() { /// 1. Open Resilient Handle with specific timeout. /// 2. Disconnect to start the Resilient Timer. /// 3. Wait for specific timeout - 1 seconds. /// 4. Reconnect the resilient handle and expect the result is success. #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb21); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_LMR_REQUEST_RESILIENCY); TestConfig.CheckCreateContext(CreateContextTypeValue.SMB2_CREATE_DURABLE_HANDLE_RECONNECT); #endregion Smb2FunctionalClient prepareClient = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite); uint timeoutInSecond = testConfig.MaxResiliencyTimeoutInSecond / 2; Guid clientGuid = Guid.NewGuid(); string fileName = "ResilientHandle_" + Guid.NewGuid() + ".txt"; FILEID fileId; // Open file & Resiliency request BaseTestSite.Log.Add( LogEntryKind.TestStep, "Create resilient handle to file '{0}' and timeout is {1} seconds", fileName, timeoutInSecond); OpenFileAndResilientRequest( prepareClient, clientGuid, fileName, timeoutInSecond * 1000, // convert second to millisecond out fileId); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Disconnect the client to start the Resilient Open Scavenger Timer on server"); prepareClient.Disconnect(); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Wait {0} seconds before Resilient Open Scavenger Timer expired.", timeoutInSecond - 1); Thread.Sleep(TimeSpan.FromSeconds(timeoutInSecond - 1)); Smb2FunctionalClient reconnectClient = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Re-establish Resilient Open, verify the returned status is STATUS_SUCCESS."); ReconnectResilientHandle( reconnectClient, clientGuid, fileName, fileId, NtStatus.STATUS_SUCCESS, "Reconnect resilient handle should be successful."); // clean reconnectClient.Disconnect(); }
protected override void TestInitialize() { base.TestInitialize(); #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb30); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_OFFLOAD_READ, CtlCode_Values.FSCTL_OFFLOAD_WRITE); #endregion client = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite); }
private void PrepareFileForTrimming(out uint treeId, out FILEID fileId) { #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb30); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_FILE_LEVEL_TRIM); #endregion string uncSharePath = Smb2Utility.GetUncPath(TestConfig.SutComputerName, TestConfig.BasicFileShare); string fileName = GetTestFileName(uncSharePath); string contentWrite = Smb2Utility.CreateRandomString(TestConfig.WriteBufferLengthInKb); smb2Functionalclient.ConnectToServer(TestConfig.UnderlyingTransport, TestConfig.SutComputerName, TestConfig.SutIPAddress); uint status = smb2Functionalclient.Negotiate( TestConfig.RequestDialects, TestConfig.IsSMB1NegotiateEnabled, checker: (Packet_Header header, NEGOTIATE_Response response) => { BaseTestSite.Assert.AreEqual( Smb2Status.STATUS_SUCCESS, header.Status, "CREATE should succeed, actually server returns {0}.", Smb2Status.GetStatusCode(header.Status)); TestConfig.CheckNegotiateDialect(DialectRevision.Smb30, response); }); status = smb2Functionalclient.SessionSetup( TestConfig.DefaultSecurityPackage, TestConfig.SutComputerName, TestConfig.AccountCredential, TestConfig.UseServerGssToken); status = smb2Functionalclient.TreeConnect(uncSharePath, out treeId); Smb2CreateContextResponse[] serverCreateContexts; status = smb2Functionalclient.Create( treeId, fileName, CreateOptions_Values.FILE_NON_DIRECTORY_FILE, out fileId, out serverCreateContexts); status = smb2Functionalclient.Write(treeId, fileId, contentWrite); status = smb2Functionalclient.Close(treeId, fileId); status = smb2Functionalclient.Create( treeId, fileName, CreateOptions_Values.FILE_NON_DIRECTORY_FILE, out fileId, out serverCreateContexts); }
private void TestValidateNegotiateInfo(Smb2FunctionalClient client, ValidateNegotiateInfoRequestType requestType, DialectRevision[] invalidDialects = null) { #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb30); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_VALIDATE_NEGOTIATE_INFO); TestConfig.CheckDialectIOCTLCompatibility(CtlCode_Values.FSCTL_VALIDATE_NEGOTIATE_INFO); // Server will terminate connection if Validate Negotiate Info Request is not signed. TestConfig.CheckSigning(); #endregion BaseTestSite.Log.Add(LogEntryKind.TestStep, "Start a client by sending the following requests: NEGOTIATE; SESSION_SETUP; TREE_CONNECT"); Guid clientGuid = Guid.NewGuid(); DialectRevision[] requestDialects = TestConfig.RequestDialects; Capabilities_Values clientCapabilities = Capabilities_Values.GLOBAL_CAP_DFS | Capabilities_Values.GLOBAL_CAP_DIRECTORY_LEASING | Capabilities_Values.GLOBAL_CAP_LARGE_MTU | Capabilities_Values.GLOBAL_CAP_LEASING | Capabilities_Values.GLOBAL_CAP_MULTI_CHANNEL | Capabilities_Values.GLOBAL_CAP_PERSISTENT_HANDLES; SecurityMode_Values clientSecurityMode = SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED; NEGOTIATE_Response? negotiateResponse = null; status = client.Negotiate( requestDialects, TestConfig.IsSMB1NegotiateEnabled, clientSecurityMode, clientCapabilities, clientGuid, (Packet_Header header, NEGOTIATE_Response response) => { BaseTestSite.Assert.AreEqual( Smb2Status.STATUS_SUCCESS, header.Status, "Negotiation should succeed, actually server returns {0}.", Smb2Status.GetStatusCode(header.Status)); TestConfig.CheckNegotiateDialect(DialectRevision.Smb30, response); negotiateResponse = response; }); status = client.SessionSetup( TestConfig.DefaultSecurityPackage, TestConfig.SutComputerName, TestConfig.AccountCredential, TestConfig.UseServerGssToken); uint treeId; string ipcPath = Smb2Utility.GetIPCPath(TestConfig.SutComputerName); status = client.TreeConnect(ipcPath, out treeId); VALIDATE_NEGOTIATE_INFO_Request validateNegotiateInfoReq; switch (requestType) { case ValidateNegotiateInfoRequestType.None: case ValidateNegotiateInfoRequestType.InvalidMaxOutputResponse: validateNegotiateInfoReq.Guid = clientGuid; validateNegotiateInfoReq.Capabilities = clientCapabilities; validateNegotiateInfoReq.SecurityMode = clientSecurityMode; validateNegotiateInfoReq.DialectCount = (ushort)requestDialects.Length; validateNegotiateInfoReq.Dialects = requestDialects; break; case ValidateNegotiateInfoRequestType.InvalidDialects: validateNegotiateInfoReq.Guid = clientGuid; validateNegotiateInfoReq.Capabilities = clientCapabilities; validateNegotiateInfoReq.SecurityMode = clientSecurityMode; validateNegotiateInfoReq.DialectCount = (ushort)invalidDialects.Length; validateNegotiateInfoReq.Dialects = invalidDialects; break; case ValidateNegotiateInfoRequestType.InvalidGuid: validateNegotiateInfoReq.Guid = Guid.NewGuid(); validateNegotiateInfoReq.Capabilities = clientCapabilities; validateNegotiateInfoReq.SecurityMode = clientSecurityMode; validateNegotiateInfoReq.DialectCount = (ushort)requestDialects.Length; validateNegotiateInfoReq.Dialects = requestDialects; break; case ValidateNegotiateInfoRequestType.InvalidSecurityMode: validateNegotiateInfoReq.Guid = clientGuid; validateNegotiateInfoReq.Capabilities = clientCapabilities; validateNegotiateInfoReq.SecurityMode = SecurityMode_Values.NONE; validateNegotiateInfoReq.DialectCount = (ushort)requestDialects.Length; validateNegotiateInfoReq.Dialects = requestDialects; break; case ValidateNegotiateInfoRequestType.InvalidCapabilities: validateNegotiateInfoReq.Guid = clientGuid; validateNegotiateInfoReq.Capabilities = Capabilities_Values.NONE; validateNegotiateInfoReq.SecurityMode = clientSecurityMode; validateNegotiateInfoReq.DialectCount = (ushort)requestDialects.Length; validateNegotiateInfoReq.Dialects = requestDialects; break; default: throw new InvalidOperationException("Unexpected ValidateNegotiateInfo request type " + requestType); } byte[] inputBuffer = TypeMarshal.ToBytes <VALIDATE_NEGOTIATE_INFO_Request>(validateNegotiateInfoReq); byte[] outputBuffer; VALIDATE_NEGOTIATE_INFO_Response validateNegotiateInfoResp; BaseTestSite.Log.Add( LogEntryKind.TestStep, "Attempt to validate negotiate info with info Guid: {0}, Capabilities: {1}, SecurityMode: {2}, DialectCount: {3}, Dialects: {4}", validateNegotiateInfoReq.Guid, validateNegotiateInfoReq.Capabilities, validateNegotiateInfoReq.SecurityMode, validateNegotiateInfoReq.DialectCount, Smb2Utility.GetArrayString(validateNegotiateInfoReq.Dialects)); if (requestType == ValidateNegotiateInfoRequestType.None) { status = client.ValidateNegotiateInfo(treeId, inputBuffer, out outputBuffer, checker: (header, response) => { }); BaseTestSite.Assert.AreEqual(Smb2Status.STATUS_SUCCESS, status, "ValidateNegotiateInfo should succeed "); validateNegotiateInfoResp = TypeMarshal.ToStruct <VALIDATE_NEGOTIATE_INFO_Response>(outputBuffer); BaseTestSite.Log.Add( LogEntryKind.Debug, "Capabilities returned in ValidateNegotiateInfo response: {0}", validateNegotiateInfoResp.Capabilities); BaseTestSite.Assert.AreEqual( (Capabilities_Values)negotiateResponse.Value.Capabilities, validateNegotiateInfoResp.Capabilities, "Capabilities returned in ValidateNegotiateInfo response should be equal to server capabilities in original Negotiate response"); BaseTestSite.Log.Add( LogEntryKind.Debug, "Guid returned in ValidateNegotiateInfo response: {0}", validateNegotiateInfoResp.Guid); BaseTestSite.Assert.AreEqual( negotiateResponse.Value.ServerGuid, validateNegotiateInfoResp.Guid, "ServerGuid returned in ValidateNegotiateInfo response should be equal to server ServerGuid in original Negotiate response"); BaseTestSite.Log.Add( LogEntryKind.Debug, "SecurityMode returned in ValidateNegotiateInfo response: {0}", validateNegotiateInfoResp.SecurityMode); BaseTestSite.Assert.AreEqual( (SecurityMode_Values)negotiateResponse.Value.SecurityMode, validateNegotiateInfoResp.SecurityMode, "SecurityMode returned in ValidateNegotiateInfo response should be equal to server SecurityMode in original Negotiate response"); BaseTestSite.Log.Add( LogEntryKind.Debug, "Dialect returned in ValidateNegotiateInfo response: {0}", validateNegotiateInfoResp.Dialect); BaseTestSite.Assert.AreEqual( negotiateResponse.Value.DialectRevision, validateNegotiateInfoResp.Dialect, "DialectRevision returned in ValidateNegotiateInfo response should be equal to server DialectRevision in original Negotiate response"); client.TreeDisconnect(treeId); client.LogOff(); return; } uint maxOutputResponse = (requestType == ValidateNegotiateInfoRequestType.InvalidMaxOutputResponse) ? (uint)0: 64 * 1024; try { client.ValidateNegotiateInfo(treeId, inputBuffer, out outputBuffer, maxOutputResponse, (header, response) => { }); client.TreeDisconnect(treeId); client.LogOff(); return; } catch { } string errCondition = requestType == ValidateNegotiateInfoRequestType.InvalidMaxOutputResponse ? "MaxOutputResponse in the request is less than the size of a VALIDATE_NEGOTIATE_INFO Response" : "there's invalid info in the request"; BaseTestSite.Assert.IsTrue(client.Smb2Client.IsServerDisconnected, "Transport connection should be terminated when {0}", errCondition); }
public void BVT_EnumerateSnapShots() { #region Check Applicability TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_SRV_ENUMERATE_SNAPSHOTS); #endregion uint treeId; FILEID fileId; OpenFile(out treeId, out fileId); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Enumerate snapshots by sending the first IOCTL request: FSCTL_SRV_ENUMERATE_SNAPSHOTS, with MaxOutputResponse set to 16."); SRV_SNAPSHOT_ARRAY snapShotArray; client.EnumerateSnapShots( treeId, fileId, SizeOfEmptySnapShotArray, out snapShotArray, checker: (Packet_Header header, IOCTL_Response response) => { BaseTestSite.Assert.AreEqual( Smb2Status.STATUS_SUCCESS, header.Status, "FSCTL_SRV_ENUMERATE_SNAPSHOTS should succeed, actually server returns {0}.", Smb2Status.GetStatusCode(header.Status)); }); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Verify SRV_SNAPSHOT_ARRAY returned in response."); BaseTestSite.Assert.AreEqual( TestConfig.NumberOfPreviousVersions, snapShotArray.NumberOfSnapShots, "NumberOfSnapShots should be {0}.", TestConfig.NumberOfPreviousVersions); BaseTestSite.Assert.AreEqual( (uint)0, snapShotArray.NumberOfSnapShotsReturned, "NumberOfSnapShotsReturned should be 0."); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Enumerate snapshots by sending the second IOCTL request: FSCTL_SRV_ENUMERATE_SNAPSHOTS, with MaxOutputResponse set to 65536."); client.EnumerateSnapShots( treeId, fileId, Smb2FunctionalClient.DefaultMaxOutputResponse, out snapShotArray, checker: (Packet_Header header, IOCTL_Response response) => { BaseTestSite.Assert.AreEqual( Smb2Status.STATUS_SUCCESS, header.Status, "FSCTL_SRV_ENUMERATE_SNAPSHOTS should succeed, actually server returns {0}.", Smb2Status.GetStatusCode(header.Status)); }); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Verify SRV_SNAPSHOT_ARRAY returned in response."); BaseTestSite.Assert.AreEqual( TestConfig.NumberOfPreviousVersions, snapShotArray.NumberOfSnapShots, "NumberOfSnapShots should be {0}.", TestConfig.NumberOfPreviousVersions); BaseTestSite.Log.Add(LogEntryKind.Debug, "NumberOfSnapShotsReturned is {0}.", snapShotArray.NumberOfSnapShotsReturned); string[] versionArray = System.Text.Encoding.Unicode.GetString(snapShotArray.SnapShots).Split('\0'); BaseTestSite.Assert.AreEqual( snapShotArray.NumberOfSnapShotsReturned + 2, (uint)versionArray.Length, "The field \"SnapShots\" should be separated by UNICODE null characters and terminated by two UNICODE null characters."); DateTime dt; for (int i = 0; i < snapShotArray.NumberOfSnapShotsReturned; ++i) { BaseTestSite.Assert.IsTrue( DateTime.TryParseExact(versionArray[i], "@GMT-yyyy.MM.dd-HH.mm.ss", System.Globalization.CultureInfo.InvariantCulture, System.Globalization.DateTimeStyles.None, out dt), "This SnapShot is {0}. The format of each SnapShot should be \"@GMT-YYYY.MM.DD-HH.MM.SS\". ", versionArray[i]); } BaseTestSite.Log.Add(LogEntryKind.TestStep, "Tear down client by sending the following requests: CLOSE; TREE_DISCONNECT; LOG_OFF"); client.Close(treeId, fileId); client.TreeDisconnect(treeId); client.LogOff(); }
public void ResilientOpenScavengerTimer_ReconnectBeforeTimeout_Zero() { /// 1. Open Resilient Handle with timeout = 0. When server receive resilient handle with timeout = 0, /// it will set the Open.ResilientTimeout as implementation-specific value. /// 2. Disconnect to start the Resilient Timer. /// 3. Wait for specific timeout - 1 seconds. /// 4. Reconnect the resilient handle and expect the result is success. #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb21); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_LMR_REQUEST_RESILIENCY); TestConfig.CheckCreateContext(CreateContextTypeValue.SMB2_CREATE_DURABLE_HANDLE_RECONNECT); #endregion Smb2FunctionalClient prepareClient = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite); Guid clientGuid = Guid.NewGuid(); string fileName = "ResilientHandle_" + Guid.NewGuid() + ".txt"; FILEID fileId; // Open file & Resiliency request BaseTestSite.Log.Add( LogEntryKind.TestStep, "Create resilient handle to file '{0}' and timeout is {1} seconds", fileName, 0); OpenFileAndResilientRequest( prepareClient, clientGuid, fileName, 0, // convert second to millisecond out fileId); /// Open.ResiliencyTimeout SHOULD be set to an implementation-specific value.<294> uint timeout = DEFAULT_RESILIENT_TIMEOUT_IN_SECONDS; if (TestConfig.Platform == Platform.WindowsServer2012) { /// <294> Section 3.3.5.15.9: Windows 7 and Windows Server 2008 R2 servers keep the resilient /// handle open indefinitely when the requested Timeout value is equal to zero. /// Windows 8 and Windows Server 2012 servers set a constant value of 120 seconds. timeout = DEFAULT_RESILIENT_TIMEOUT_IN_SECONDS; } else { timeout = testConfig.DefaultResiliencyTimeoutInSecond; } BaseTestSite.Log.Add( LogEntryKind.Debug, "Server should set the timeout of resilient handle to implementation-specific timeout {0} seconds", timeout); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Disconnect the client to start the Resilient Open Scavenger Timer on server"); prepareClient.Disconnect(); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Wait {0} seconds before Resilient Open Scavenger Timer expired.", timeout - 1); Thread.Sleep(TimeSpan.FromSeconds(timeout - 1)); Smb2FunctionalClient reconnectClient = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Re-establish Resilient Open, verify the returned status is STATUS_SUCCESS."); ReconnectResilientHandle( reconnectClient, clientGuid, fileName, fileId, NtStatus.STATUS_SUCCESS, "Reconnect resilient handle should be successful."); // clean reconnectClient.Disconnect(); }
public void BVT_ResilientHandle_LockSequence() { #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb21); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_LMR_REQUEST_RESILIENCY); TestConfig.CheckCreateContext(CreateContextTypeValue.SMB2_CREATE_DURABLE_HANDLE_RECONNECT); #endregion Guid clientGuid = Guid.NewGuid(); #region clientBeforeDisconnection Create a File BaseTestSite.Log.Add( LogEntryKind.TestStep, "Start the first client to create a file by sending the following requests: NEGOTIATE; SESSION_SETUP; TREE_CONNECT; CREATE."); clientBeforeDisconnection.Negotiate(TestConfig.RequestDialects, TestConfig.IsSMB1NegotiateEnabled, clientGuid: clientGuid); clientBeforeDisconnection.SessionSetup(TestConfig.DefaultSecurityPackage, TestConfig.SutComputerName, TestConfig.AccountCredential, false); uint treeId; clientBeforeDisconnection.TreeConnect(sharePath, out treeId); FILEID fileId; Smb2CreateContextResponse[] createContextResponse; clientBeforeDisconnection.Create(treeId, fileName, CreateOptions_Values.FILE_NON_DIRECTORY_FILE, out fileId, out createContextResponse); #endregion #region Request Resilient Handle IOCTL_Response IOCTLResponse; byte[] inputInResponse; byte[] outputInResponse; Packet_Header packetHeader; BaseTestSite.Log.Add( LogEntryKind.TestStep, "The first client sends an IOCTL FSCTL_LMR_REQUEST_RESILLIENCY request."); clientBeforeDisconnection.ResiliencyRequest(treeId, fileId, TestConfig.MaxResiliencyTimeoutInSecond * 1000, NETWORK_RESILIENCY_REQUEST_SIZE, out packetHeader, out IOCTLResponse, out inputInResponse, out outputInResponse); BaseTestSite.Log.Add(LogEntryKind.TestStep, "The first client sends WRITE request."); clientBeforeDisconnection.Write(treeId, fileId, "12345678"); BaseTestSite.Log.Add(LogEntryKind.TestStep, "The first client sends Flush request."); clientBeforeDisconnection.Flush(treeId, fileId); #endregion //The LockSequence field of the SMB2 lock request MUST be set to (BucketNumber<< 4) + BucketSequence. int bucketNum = 1; int bucketSeq = 1; uint lockSequence = (uint)bucketNum << 4 + bucketSeq; BaseTestSite.Log.Add( LogEntryKind.TestStep, "The first client sends LOCK request with LockSequence set to (BucketNumber<< 4) + BucketSequence"); clientBeforeDisconnection.Lock(treeId, lockSequence, fileId, new LOCK_ELEMENT[] { new LOCK_ELEMENT { Flags = LOCK_ELEMENT_Flags_Values.LOCKFLAG_EXCLUSIVE_LOCK | LOCK_ELEMENT_Flags_Values.LOCKFLAG_FAIL_IMMEDIATELY, Offset = 0, Length = 4 } }); clientBeforeDisconnection.Disconnect(); #region clientAfterDisconnection Opens the Previously Created File BaseTestSite.Log.Add( LogEntryKind.TestStep, "Start the second client to reconnect to the file created by the first client by sending the following requests: NEGOTIATE; SESSION_SETUP; TREE_CONNECT; CREATE (with SMB2_CREATE_DURABLE_HANDLE_RECONNECT Create Context)."); clientAfterDisconnection.Negotiate(TestConfig.RequestDialects, TestConfig.IsSMB1NegotiateEnabled, clientGuid: clientGuid); clientAfterDisconnection.ReconnectSessionSetup(clientBeforeDisconnection, TestConfig.DefaultSecurityPackage, TestConfig.SutComputerName, TestConfig.AccountCredential, false); clientAfterDisconnection.TreeConnect(sharePath, out treeId); clientAfterDisconnection.Create(treeId, fileName, CreateOptions_Values.FILE_NON_DIRECTORY_FILE, out fileId, out createContextResponse, RequestedOplockLevel_Values.OPLOCK_LEVEL_BATCH, new Smb2CreateContextRequest[] { new Smb2CreateDurableHandleReconnect { Data = fileId } }); #endregion //If the sequence numbers are equal, the server MUST complete the lock/unlock request with success. BaseTestSite.Log.Add(LogEntryKind.TestStep, "The second client sends LOCK request with the same LockSequence with the first client."); clientAfterDisconnection.Lock(treeId, lockSequence, //Using same Lock Sequence fileId, new LOCK_ELEMENT[] { new LOCK_ELEMENT { Flags = LOCK_ELEMENT_Flags_Values.LOCKFLAG_EXCLUSIVE_LOCK | LOCK_ELEMENT_Flags_Values.LOCKFLAG_FAIL_IMMEDIATELY, Offset = 0, Length = 4 } }); clientAfterDisconnection.Lock(treeId, lockSequence + 1, //Using different Lock Sequence fileId, new LOCK_ELEMENT[] { new LOCK_ELEMENT { Flags = LOCK_ELEMENT_Flags_Values.LOCKFLAG_EXCLUSIVE_LOCK | LOCK_ELEMENT_Flags_Values.LOCKFLAG_FAIL_IMMEDIATELY, Offset = 0, Length = 4 } }, (header, response) => { BaseTestSite.Assert.AreEqual( Smb2Status.STATUS_LOCK_NOT_GRANTED, header.Status, "If the range being locked is already locked by another open in a way that does not allow this open to take a lock on the range, " + "and if SMB2_LOCKFLAG_FAIL_IMMEDIATELY is set, the server MUST fail the request with STATUS_LOCK_NOT_GRANTED. " + "Actually server returns {0}.", Smb2Status.GetStatusCode(header.Status)); }); #region Tear Down Client BaseTestSite.Log.Add(LogEntryKind.TestStep, "Tear down the second client by sending the following requests: CLOSE; TREE_DISCONNECT; LOG_OFF"); clientAfterDisconnection.Close(treeId, fileId); clientAfterDisconnection.TreeDisconnect(treeId); clientAfterDisconnection.LogOff(); #endregion }
public void BVT_SetGetIntegrityInfo() { #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb30); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_SET_INTEGRITY_INFORMATION, CtlCode_Values.FSCTL_GET_INTEGRITY_INFORMATION); #endregion client.ConnectToServer(TestConfig.UnderlyingTransport, TestConfig.SutComputerName, TestConfig.SutIPAddress); BaseTestSite.Log.Add(LogEntryKind.TestStep, "Client creates a file by sending the following requests: NEGOTIATE; SESSION_SETUP; TREE_CONNECT; CREATE"); status = client.Negotiate( TestConfig.RequestDialects, TestConfig.IsSMB1NegotiateEnabled, checker: (Packet_Header header, NEGOTIATE_Response response) => { BaseTestSite.Assert.AreEqual( Smb2Status.STATUS_SUCCESS, header.Status, "Negotiation should succeed, actually server returns {0}.", Smb2Status.GetStatusCode(header.Status)); TestConfig.CheckNegotiateDialect(DialectRevision.Smb30, response); }); status = client.SessionSetup( TestConfig.DefaultSecurityPackage, TestConfig.SutComputerName, TestConfig.AccountCredential, TestConfig.UseServerGssToken); uint treeId; string uncSharePath = Smb2Utility.GetUncPath(TestConfig.SutComputerName, TestConfig.FileShareSupportingIntegrityInfo); status = client.TreeConnect(uncSharePath, out treeId); FILEID fileId; Smb2CreateContextResponse[] serverCreateContexts; status = client.Create( treeId, GetTestFileName(uncSharePath), CreateOptions_Values.FILE_NON_DIRECTORY_FILE, out fileId, out serverCreateContexts); FSCTL_GET_INTEGRITY_INFO_OUTPUT getIntegrityInfo; BaseTestSite.Log.Add(LogEntryKind.TestStep, "Client sends IOCTL request with FSCTL_GET_INTEGRITY_INFORMATION."); status = client.GetIntegrityInfo(treeId, fileId, out getIntegrityInfo); BaseTestSite.Log.Add( LogEntryKind.Debug, "Integrity info returned in FSCTL_GET_INTEGRITY_INFO request: ChecksumAlgorithm {0}, Flags {1}, ChecksumChunkSizeInBytes {2}, ClusterSizeInBytes {3}", getIntegrityInfo.ChecksumAlgorithm, getIntegrityInfo.Flags, getIntegrityInfo.ChecksumChunkSizeInBytes, getIntegrityInfo.ClusterSizeInBytes); FSCTL_SET_INTEGRIY_INFO_INPUT setIntegrityInfo; setIntegrityInfo.ChecksumAlgorithm = FSCTL_SET_INTEGRITY_INFO_INPUT_CHECKSUMALGORITHM.CHECKSUM_TYPE_CRC64; setIntegrityInfo.Flags = FSCTL_SET_INTEGRITY_INFO_INPUT_FLAGS.FSCTL_INTEGRITY_FLAG_CHECKSUM_ENFORCEMENT_OFF; setIntegrityInfo.Reserved = FSCTL_SET_INTEGRITY_INFO_INPUT_RESERVED.V1; byte[] buffer = TypeMarshal.ToBytes <FSCTL_SET_INTEGRIY_INFO_INPUT>(setIntegrityInfo); BaseTestSite.Log.Add( LogEntryKind.Debug, "Attempt to set integrity info with ChecksumAlgrithm {0}, Flags {1}", setIntegrityInfo.ChecksumAlgorithm, setIntegrityInfo.Flags); BaseTestSite.Log.Add(LogEntryKind.TestStep, "Client sends IOCTL request with FSCTL_SET_INTEGRITY_INFORMATION after changed the value of the following fields in FSCTL_SET_INTEGRIY_INFO_INPUT: ChecksumAlgorithm, Flags, Reserved."); status = client.SetIntegrityInfo(treeId, fileId, buffer); BaseTestSite.Log.Add(LogEntryKind.TestStep, "Client sends IOCTL request with FSCTL_GET_INTEGRITY_INFORMATION."); status = client.GetIntegrityInfo(treeId, fileId, out getIntegrityInfo); BaseTestSite.Log.Add( LogEntryKind.Debug, "Current ChecksumAlgorithm is " + getIntegrityInfo.ChecksumAlgorithm); BaseTestSite.Assert.AreEqual( (ushort)setIntegrityInfo.ChecksumAlgorithm, (ushort)getIntegrityInfo.ChecksumAlgorithm, "ChecksumAlgorithm field after set should be {0}, actual value is {1}", setIntegrityInfo.ChecksumAlgorithm, getIntegrityInfo.ChecksumAlgorithm); BaseTestSite.Log.Add( LogEntryKind.Debug, "Current Flags is " + getIntegrityInfo.Flags); BaseTestSite.Assert.AreEqual( (uint)setIntegrityInfo.Flags, (uint)getIntegrityInfo.Flags, "Flags field after set should be {0}, actual value is {1}", setIntegrityInfo.Flags, getIntegrityInfo.Flags); BaseTestSite.Log.Add(LogEntryKind.TestStep, "Tear down the client by sending the following requests: CLOSE; TREE_DISCONNECT; LOG_OFF."); status = client.Close(treeId, fileId); status = client.TreeDisconnect(treeId); status = client.LogOff(); }
public void ResilientOpenScavengerTimer_ReconnectAfterTimeout() { /// 1. Wait for MaxResiliencyTimeoutInSecond seconds to expire the Resilient Timer and make sure that the Timer is not started. /// 2. Open Resilient Handle with specific timeout. /// 3. Disconnect to start the Resilient Timer. /// 4. Wait for specific timeout + 1 seconds. /// 5. Reconnect the resilient handle and expect the handle is terminated. #region Check Applicability TestConfig.CheckDialect(DialectRevision.Smb21); TestConfig.CheckIOCTL(CtlCode_Values.FSCTL_LMR_REQUEST_RESILIENCY); TestConfig.CheckCreateContext(CreateContextTypeValue.SMB2_CREATE_DURABLE_HANDLE_RECONNECT); #endregion BaseTestSite.Log.Add( LogEntryKind.TestStep, "Wait {0} seconds to make sure Resilient Timer is not started.", testConfig.MaxResiliencyTimeoutInSecond); Thread.Sleep(TimeSpan.FromSeconds((int)testConfig.MaxResiliencyTimeoutInSecond)); Smb2FunctionalClient prepareClient = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite); uint timeoutInSecond = testConfig.MaxResiliencyTimeoutInSecond / 2; Guid clientGuid = Guid.NewGuid(); string fileName = GetTestFileName(Smb2Utility.GetUncPath(testConfig.SutComputerName, testConfig.BasicFileShare)); FILEID fileId; // Open file & Resiliency request BaseTestSite.Log.Add( LogEntryKind.TestStep, "Create resilient handle to file '{0}' and timeout is {1} seconds", fileName, timeoutInSecond); OpenFileAndResilientRequest( prepareClient, clientGuid, fileName, timeoutInSecond * 1000, // convert second to millisecond out fileId); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Disconnect the client to start the Resilient Open Scavenger Timer on server"); prepareClient.Disconnect(); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Wait {0} seconds before Resilient Open Scavenger Timer expired.", timeoutInSecond + 10); Thread.Sleep(TimeSpan.FromSeconds(timeoutInSecond + 10)); Smb2FunctionalClient reconnectClient = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite); BaseTestSite.Log.Add( LogEntryKind.TestStep, "Re-establish Resilient Open, verify the returned status is STATUS_OBJECT_NAME_NOT_FOUND."); ReconnectResilientHandle( reconnectClient, clientGuid, fileName, fileId, NtStatus.STATUS_OBJECT_NAME_NOT_FOUND, "Resilient handle should be terminated."); // clean reconnectClient.Disconnect(); }