Example #1
0
        protected SHARE_INFO_502_I GetShareInfo(string sharePath)
        {
            using (SrvsClient srvsClient = new SrvsClient(TestConfig.Timeout))
            {
                ClientSecurityContext securityContext =
                    new SspiClientSecurityContext(
                        TestConfig.DefaultSecurityPackage,
                        TestConfig.AccountCredential,
                        Smb2Utility.GetCifsServicePrincipalName(TestConfig.SutComputerName),
                        ClientSecurityContextAttribute.Connection
                        | ClientSecurityContextAttribute.DceStyle
                        | ClientSecurityContextAttribute.Integrity
                        | ClientSecurityContextAttribute.ReplayDetect
                        | ClientSecurityContextAttribute.SequenceDetect
                        | ClientSecurityContextAttribute.UseSessionKey,
                        SecurityTargetDataRepresentation.SecurityNativeDrep);

                srvsClient.Bind(TestConfig.SutComputerName, TestConfig.AccountCredential, securityContext);

                SHARE_INFO?shareInfo;
                uint       retVal = srvsClient.NetrShareGetInfo(@"\\" + TestConfig.SutComputerName, sharePath, SHARE_ENUM_STRUCT_LEVEL.Level502, out shareInfo);
                if (retVal != 0 || shareInfo == null || shareInfo.Value.ShareInfo502 == null)
                {
                    BaseTestSite.Assert.Fail("Fail to get share info through MS-SRVS.");
                }
                srvsClient.UnBind();
                return(shareInfo.Value.ShareInfo502.Value);
            }
        }
        /// <summary>
        /// Performs CredSSP authentication.
        /// </summary>
        /// <exception cref="IOException">Raised when attempting to read from/write to the remote connection which
        /// has been closed</exception>
        /// <exception cref="EndOfStreamException">Raised when the username or password doesn't match or authentication
        /// fails</exception>
        public void Authenticate()
        {
            // Authenticated already, do nothing
            if (isAuthenticated)
            {
                return;
            }

            credential = new AccountCredential(domain, userName, password);

            byte[] receivedBuffer = new byte[MaxBufferSize];
            int    bytesReceived  = 0;

            // Dispose the context as it may be timed out
            if (context != null)
            {
                context.Dispose();
            }
            context = new SspiClientSecurityContext(
                SecurityPackageType.CredSsp,
                credential,
                serverPrincipal,
                attribute,
                SecurityTargetDataRepresentation.SecurityNativeDrep);

            context.Initialize(null);
            // Get first token
            byte[] token = context.Token;
            // SSL handshake
            while (context.NeedContinueProcessing)
            {
                // Send handshake request
                clientStream.Write(token, 0, token.Length);
                // Get handshake resopnse
                bytesReceived = clientStream.Read(receivedBuffer, 0, receivedBuffer.Length);
                // The remote connection has been closed
                if (bytesReceived == 0)
                {
                    throw new EndOfStreamException("Authentication failed: remote connection has been closed.");
                }

                byte[] inToken = new byte[bytesReceived];
                Array.Copy(receivedBuffer, inToken, bytesReceived);
                // Get next token from response
                context.Initialize(inToken);
                token = context.Token;
            }
            // Send the last token, handshake over, CredSSP is established
            // Note if there're errors during authentication, an SSPIException will be raised
            // and isAuthentication will not be true.
            clientStream.Write(token, 0, token.Length);
            isAuthenticated = true;
        }
Example #3
0
        /// <summary>
        /// dispose the gssapi
        /// </summary>
        internal void DisposeGssApi()
        {
            if (this.GssApi == null)
            {
                return;
            }

            SspiClientSecurityContext sspiSecurityContext = this.GssApi as SspiClientSecurityContext;

            if (sspiSecurityContext != null)
            {
                sspiSecurityContext.Dispose();
            }
        }
        /// <summary>
        /// Implements IDisposable interface(from NetworkStream)
        /// </summary>
        /// <param name="disposing">Indicates if there's managed resource to release</param>
        protected override void Dispose(bool disposing)
        {
            if (!this.disposed)
            {
                if (disposing)
                {
                    // Clean managed resource
                    CloseClientStream();

                    if (context != null)
                    {
                        context.Dispose();
                        context = null;
                    }
                }
                this.disposed        = true;
                this.isAuthenticated = false;
            }

            base.Dispose(disposing);
        }
Example #5
0
        /// <summary>
        /// Connect to server.
        /// </summary>
        /// <param name="client">Fsrvp client.</param>
        /// <param name="server">The name of server.</param>
        /// <returns>Return true if success, otherwise return false.</returns>
        private bool ConnectServer(ref FsrvpClient client, string server)
        {
            AccountCredential accountCredential =
                new AccountCredential(TestConfig.DomainName, TestConfig.UserName, TestConfig.UserPassword);

            ClientSecurityContext securityContext =
                new SspiClientSecurityContext(
                    TestConfig.DefaultSecurityPackage,
                    accountCredential,
                    Smb2Utility.GetCifsServicePrincipalName(server),
                    ClientSecurityContextAttribute.Connection
                    | ClientSecurityContextAttribute.DceStyle
                    | ClientSecurityContextAttribute.Integrity
                    | ClientSecurityContextAttribute.ReplayDetect
                    | ClientSecurityContextAttribute.SequenceDetect
                    | ClientSecurityContextAttribute.UseSessionKey,
                    SecurityTargetDataRepresentation.SecurityNativeDrep);

            // This indicates that the RPC message is just integrity-protected.
            client.Context.AuthenticationLevel = TestConfig.DefaultRpceAuthenticationLevel;

            try
            {
                BaseTestSite.Log.Add(LogEntryKind.Debug, "Connect to server {0}.", server);
                client.BindOverNamedPipe(server, accountCredential, securityContext,
                                         new TimeSpan(0, 0, (int)FsrvpUtility.FSRVPTimeoutInSeconds));
            }
            catch (InvalidOperationException ex)
            {
                BaseTestSite.Log.Add(LogEntryKind.Debug,
                                     "Connect to server {0} failed. Exception: {1}",
                                     server,
                                     ex.Message);
                client.Unbind(TestConfig.Timeout);
                return(false);
            }

            BaseTestSite.Log.Add(LogEntryKind.Debug, "Connect to server {0} successfully.", server);
            return(true);
        }
Example #6
0
        /// <summary>
        /// Generate the Generic Security Service (GSS) Kerberos authentication token for a user.
        /// </summary>
        /// <param name="user">The user.</param>
        /// <returns>The GSS Kerberos authentication token in type of DRS_SecBuffer.</returns>
        public static DRS_SecBufferDesc GetAuthenticationToken(string account, string pwd, string domain, string spn)
        {
            ClientSecurityContextAttribute contextAttr =
                ClientSecurityContextAttribute.Connection |
                //ClientSecurityContextAttribute.Integrity |
                ClientSecurityContextAttribute.Confidentiality
                //|
                //ClientSecurityContextAttribute.UseSessionKey
                //|
                //ClientSecurityContextAttribute.Delegate
            ;

            SspiClientSecurityContext securityContext = new SspiClientSecurityContext(
                SecurityPackageType.Kerberos,
                new AccountCredential(domain, account, pwd),
                spn,
                contextAttr,
                SecurityTargetDataRepresentation.SecurityNativeDrep);

            //securityContext.Initialize(null);

            string kdcIpAddr = GetIPAddress(domain);

            byte[] token = GenerateGssApToken(kdcIpAddr, account, pwd, domain, spn, KerberosAccountType.User);

            DRS_SecBufferDesc pClientCreds = new DRS_SecBufferDesc();

            pClientCreds.ulVersion = ulVersion_Values.V1;
            //pClientCreds.Buffers = null;
            pClientCreds.cBuffers = 1;
            pClientCreds.Buffers  = new DRS_SecBuffer[1];
            DRS_SecBuffer secBuf = new DRS_SecBuffer();

            secBuf.BufferType       = BufferType_Values.SECBUFFER_TOKEN;
            secBuf.pvBuffer         = token;
            secBuf.cbBuffer         = (uint)secBuf.pvBuffer.Length;
            pClientCreds.Buffers[0] = secBuf;

            return(pClientCreds);
        }
Example #7
0
        public void UserLogon(
            DetectionInfo info,
            Smb2Client client,
            out ulong messageId,
            out ulong sessionId,
            out Guid clientGuid,
            out NEGOTIATE_Response negotiateResp,
            out bool encryptionRequired)
        {
            messageId = 1;
            sessionId = 0;
            logWriter.AddLog(LogLevel.Information, "Client connects to server");
            client.ConnectOverTCP(SUTIpAddress);

            #region Negotiate

            DialectRevision selectedDialect;
            byte[]          gssToken;
            Packet_Header   header;
            clientGuid = Guid.NewGuid();
            logWriter.AddLog(LogLevel.Information, "Client sends multi-protocol Negotiate to server");
            MultiProtocolNegotiate(
                client,
                1,
                1,
                Packet_Header_Flags_Values.NONE,
                messageId++,
                info.requestDialect,
                SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                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 | Capabilities_Values.GLOBAL_CAP_ENCRYPTION,
                clientGuid,
                out selectedDialect,
                out gssToken,
                out header,
                out negotiateResp);

            if (header.Status != Smb2Status.STATUS_SUCCESS)
            {
                LogFailedStatus("NEGOTIATE", header.Status);
                throw new Exception(string.Format("NEGOTIATE failed with {0}", Smb2Status.GetStatusCode(header.Status)));
            }

            #endregion

            #region Session Setup

            SESSION_SETUP_Response sessionSetupResp;

            SspiClientSecurityContext sspiClientGss =
                new SspiClientSecurityContext(
                    SecurityPackageType,
                    Credential,
                    Smb2Utility.GetCifsServicePrincipalName(SUTName),
                    ClientSecurityContextAttribute.None,
                    SecurityTargetDataRepresentation.SecurityNativeDrep);

            // Server GSS token is used only for Negotiate authentication when enabled
            if (SecurityPackageType == SecurityPackageType.Negotiate)
            {
                sspiClientGss.Initialize(gssToken);
            }
            else
            {
                sspiClientGss.Initialize(null);
            }

            do
            {
                logWriter.AddLog(LogLevel.Information, "Client sends SessionSetup to server");
                client.SessionSetup(
                    1,
                    64,
                    Packet_Header_Flags_Values.NONE,
                    messageId++,
                    sessionId,
                    SESSION_SETUP_Request_Flags.NONE,
                    SESSION_SETUP_Request_SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                    SESSION_SETUP_Request_Capabilities_Values.GLOBAL_CAP_DFS,
                    0,
                    sspiClientGss.Token,
                    out sessionId,
                    out gssToken,
                    out header,
                    out sessionSetupResp);

                if ((header.Status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED || header.Status == Smb2Status.STATUS_SUCCESS) && gssToken != null && gssToken.Length > 0)
                {
                    sspiClientGss.Initialize(gssToken);
                }
            } while (header.Status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED);

            if (header.Status != Smb2Status.STATUS_SUCCESS)
            {
                LogFailedStatus("SESSIONSETUP", header.Status);
                throw new Exception(string.Format("SESSIONSETUP failed with {0}", Smb2Status.GetStatusCode(header.Status)));
            }

            byte[] sessionKey;
            sessionKey         = sspiClientGss.SessionKey;
            encryptionRequired = sessionSetupResp.SessionFlags == SessionFlags_Values.SESSION_FLAG_ENCRYPT_DATA;
            client.GenerateCryptoKeys(
                sessionId,
                sessionKey,
                info.smb2Info.IsRequireMessageSigning, // Enable signing according to the configuration of SUT
                encryptionRequired,
                null,
                false);

            #endregion
        }
Example #8
0
        public uint Smb2AlternativeChannelSessionSetup(
            Smb2OverSmbdTestClient mainChannelClient,
            string domainName,
            string userName,
            string password,
            string serverName,
            SESSION_SETUP_Request_SecurityMode_Values securityMode = SESSION_SETUP_Request_SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
            SESSION_SETUP_Request_Capabilities_Values capabilities = SESSION_SETUP_Request_Capabilities_Values.GLOBAL_CAP_DFS,
            ushort creditRequest = 64)
        {
            sessionId  = mainChannelClient.sessionId;
            sessionKey = mainChannelClient.sessionKey;

            Smb2SetSessionSigningAndEncryption(true, false);

            Packet_Header          header;
            SESSION_SETUP_Response sessionSetupResponse;

            SspiClientSecurityContext sspiClientGss =
                new SspiClientSecurityContext(
                    SecurityPackageType.Negotiate,
                    new AccountCredential(domainName, userName, password),
                    Smb2Utility.GetCifsServicePrincipalName(serverName),
                    ClientSecurityContextAttribute.None,
                    SecurityTargetDataRepresentation.SecurityNativeDrep
                    );

            // Server GSS token is used only for Negotiate authentication
            sspiClientGss.Initialize(gssToken);


            uint status;

            do
            {
                status = SessionSetup(
                    1,
                    creditRequest,
                    Packet_Header_Flags_Values.FLAGS_SIGNED,
                    messageId,
                    sessionId,
                    SESSION_SETUP_Request_Flags.SESSION_FLAG_BINDING,
                    securityMode,
                    capabilities,
                    0,
                    sspiClientGss.Token,
                    out sessionId,
                    out gssToken,
                    out header,
                    out sessionSetupResponse
                    );

                CalculateSmb2AvailableCredits(1, packetHeader.CreditRequestResponse);

                if ((status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED || status == Smb2Status.STATUS_SUCCESS) &&
                    gssToken != null && gssToken.Length > 0)
                {
                    sspiClientGss.Initialize(gssToken);
                }
            } while (status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED);

            if (status == Smb2Status.STATUS_SUCCESS)
            {
                sessionKey = sspiClientGss.SessionKey;
                Smb2SetSessionSigningAndEncryption(true, false, true);
            }

            return(status);
        }
Example #9
0
        public uint Smb2SessionSetup(
            SecurityPackageType securityPackageType,
            string domainName,
            string userName,
            string password,
            string serverName)
        {
            uint status;
            SESSION_SETUP_Response sessionSetupResponse;

            SspiClientSecurityContext sspiClientGss =
                new SspiClientSecurityContext(
                    securityPackageType,
                    new AccountCredential(domainName, userName, password),
                    Smb2Utility.GetCifsServicePrincipalName(serverName),
                    ClientSecurityContextAttribute.None,
                    SecurityTargetDataRepresentation.SecurityNativeDrep
                    );

            // Server GSS token is used only for Negotiate authentication
            if (securityPackageType == SecurityPackageType.Negotiate)
            {
                sspiClientGss.Initialize(this.gssToken);
            }
            else
            {
                sspiClientGss.Initialize(null);
            }
            this.sessionId = 0;

            do
            {
                status = SessionSetup(
                    1,
                    64,
                    Packet_Header_Flags_Values.NONE,
                    this.messageId,
                    this.sessionId,
                    SESSION_SETUP_Request_Flags.NONE,
                    SESSION_SETUP_Request_SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                    SESSION_SETUP_Request_Capabilities_Values.GLOBAL_CAP_DFS,
                    0,
                    sspiClientGss.Token,
                    out sessionId,
                    out this.gssToken,
                    out packetHeader,
                    out sessionSetupResponse
                    );

                CalculateSmb2AvailableCredits(1, packetHeader.CreditRequestResponse);

                if ((status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED || status == Smb2Status.STATUS_SUCCESS) &&
                    this.gssToken != null && this.gssToken.Length > 0)
                {
                    sspiClientGss.Initialize(this.gssToken);
                }
            } while (status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED);

            if (status == Smb2Status.STATUS_SUCCESS)
            {
                sessionKey = sspiClientGss.SessionKey;
                GenerateCryptoKeys(sessionId, sessionKey, true, false);
            }

            return(status);
        }
Example #10
0
        /// <summary>
        /// Bind RPC server.
        /// </summary>
        /// <param name="swnClient">SWN rpc client</param>
        /// <param name="networkAddress">RPC network address</param>
        /// <param name="domainName">Domain name</param>
        /// <param name="userName">User name</param>
        /// <param name="password">Password</param>
        /// <param name="securityPackage">Security package</param>
        /// <param name="authLevel">Authentication level</param>
        /// <param name="timeout">Timeout</param>
        /// <param name="serverComputerName">ServerComputerName</param>
        /// <returns>Return true if success, otherwise return false</returns>
        public static bool BindServer(SwnClient swnClient, IPAddress networkAddress, string domainName, string userName, string password,
                                      SecurityPackageType securityPackage, RpceAuthenticationLevel authLevel, TimeSpan timeout, string serverComputerName = null)
        {
            AccountCredential accountCredential        = new AccountCredential(domainName, userName, password);
            string            cifsServicePrincipalName = string.Empty;

            if (!string.IsNullOrEmpty(serverComputerName))
            {
                cifsServicePrincipalName = "cifs/" + serverComputerName;
            }
            else
            {
                IPHostEntry hostEntry = null;
                try
                {
                    hostEntry = Dns.GetHostEntry(networkAddress);
                }
                catch (Exception ex)
                {
                    throw new Exception(string.Format("Failed to resolve network address {0} with exception: {1}", networkAddress.ToString(), ex.Message));
                }

                if (hostEntry != null && !string.IsNullOrEmpty(hostEntry.HostName))
                {
                    cifsServicePrincipalName = "cifs/" + hostEntry.HostName;
                }
                else
                {
                    throw new Exception("Failed to get HostName from network address " + networkAddress.ToString());
                }
            }
            ClientSecurityContext securityContext =
                new SspiClientSecurityContext(
                    securityPackage,
                    accountCredential,
                    cifsServicePrincipalName,
                    ClientSecurityContextAttribute.Connection
                    | ClientSecurityContextAttribute.DceStyle
                    | ClientSecurityContextAttribute.Integrity
                    | ClientSecurityContextAttribute.ReplayDetect
                    | ClientSecurityContextAttribute.SequenceDetect
                    | ClientSecurityContextAttribute.UseSessionKey,
                    SecurityTargetDataRepresentation.SecurityNativeDrep);

            try
            {
                //Bind
                BaseTestSite.Log.Add(LogEntryKind.Debug, "Start to Bind RPC to {0}.", networkAddress.ToString());
                swnClient.SwnBind(networkAddress.ToString(), accountCredential, securityContext, authLevel, timeout);
            }
            catch (Exception ex)
            {
                BaseTestSite.Log.Add(LogEntryKind.Debug,
                                     "Bind server {0} failed. Exception: {1}",
                                     networkAddress.ToString(),
                                     ex.Message);
                swnClient.SwnUnbind(timeout);
                return(false);
            }

            BaseTestSite.Log.Add(LogEntryKind.Debug, "Bind server {0} successfully.", networkAddress.ToString());
            return(true);
        }
Example #11
0
        /// <summary>
        /// Connect to the Server and establish the named pipe transport.
        /// </summary>
        private void ConnectToServer()
        {
            smb2Client = new Smb2Client(smb2ClientTimeout);

            if (IPAddress.TryParse(serverName, out var serverIp))
            {
                smb2Client.ConnectOverTCP(serverIp);
            }
            else
            {
                var serverHostEntry = Dns.GetHostEntry(serverName);
                smb2Client.ConnectOverTCP(serverHostEntry.AddressList[0]);
            }

            var validDialects = new DialectRevision[]
            {
                DialectRevision.Smb2002,
                DialectRevision.Smb21,
                DialectRevision.Smb30,
                DialectRevision.Smb302,
                DialectRevision.Smb311
            };

            var preauthIntegrityHashIDs = new PreauthIntegrityHashID[] { PreauthIntegrityHashID.SHA_512 };
            var encryptionAlgorithms    = new EncryptionAlgorithm[] { EncryptionAlgorithm.ENCRYPTION_AES128_GCM, EncryptionAlgorithm.ENCRYPTION_AES128_CCM };
            var status = smb2Client.Negotiate(
                creditCharge: 1,
                creditRequest: 1,
                flags: defaultFlags,
                messageId: messageId++,
                // Will negotiate highest dialect server supports
                dialects: validDialects,
                securityMode: SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                capabilities: Capabilities_Values.GLOBAL_CAP_DFS | Capabilities_Values.GLOBAL_CAP_ENCRYPTION | Capabilities_Values.GLOBAL_CAP_MULTI_CHANNEL | Capabilities_Values.GLOBAL_CAP_LARGE_MTU,
                clientGuid: Guid.NewGuid(),
                out var selectedDialect,
                out var serverGssToken,
                out Packet_Header _,
                out var negotiateResponse,
                preauthHashAlgs: preauthIntegrityHashIDs,
                encryptionAlgs: encryptionAlgorithms);

            CheckStatusCode(status, nameof(Smb2Client.Negotiate));

            var sessionSiginingRequired = negotiateResponse.SecurityMode.HasFlag(NEGOTIATE_Response_SecurityMode_Values.NEGOTIATE_SIGNING_REQUIRED);

            if (sessionSiginingRequired)
            {
                defaultFlags |= Packet_Header_Flags_Values.FLAGS_SIGNED;
            }

            var usedSecurityPackageType = (SecurityPackageType)Enum.Parse(typeof(SecurityPackageType), securityPackage);
            var sspiClientGss           = new SspiClientSecurityContext(
                usedSecurityPackageType,
                new AccountCredential(domainName, userName, password),
                Smb2Utility.GetCifsServicePrincipalName(serverName),
                ClientSecurityContextAttribute.None,
                SecurityTargetDataRepresentation.SecurityNativeDrep);

            if (usedSecurityPackageType == SecurityPackageType.Negotiate && useServerGssToken)
            {
                sspiClientGss.Initialize(serverGssToken);
            }
            else
            {
                sspiClientGss.Initialize(null);
            }

            do
            {
                status = smb2Client.SessionSetup(
                    creditCharge: 1,
                    creditRequest: 1,
                    flags: Packet_Header_Flags_Values.NONE,
                    messageId: messageId++,
                    sessionId: sessionId,
                    sessionSetupFlags: SESSION_SETUP_Request_Flags.NONE,
                    securityMode: SESSION_SETUP_Request_SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                    capabilities: SESSION_SETUP_Request_Capabilities_Values.GLOBAL_CAP_DFS,
                    previousSessionId: 0,
                    clientGssToken: sspiClientGss.Token,
                    out sessionId,
                    out serverGssToken,
                    out _,
                    out _);
                CheckStatusCode(status, nameof(Smb2Client.SessionSetup));

                if ((status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED || status == Smb2Status.STATUS_SUCCESS) &&
                    serverGssToken != null && serverGssToken.Length > 0)
                {
                    sspiClientGss.Initialize(serverGssToken);
                }
            } while (status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED);

            var treeConnectSigningRequired = sessionSiginingRequired || (selectedDialect >= DialectRevision.Smb311);

            smb2Client.GenerateCryptoKeys(
                sessionId,
                sspiClientGss.SessionKey,
                treeConnectSigningRequired,
                false);

            status = smb2Client.TreeConnect(
                creditCharge: 1,
                creditRequest: 1,
                flags: treeConnectSigningRequired ? defaultFlags | Packet_Header_Flags_Values.FLAGS_SIGNED : defaultFlags,
                messageId: messageId++,
                sessionId: sessionId,
                $"\\\\{serverName}\\IPC$",
                out treeId,
                out _,
                out _);
            CheckStatusCode(status, nameof(Smb2Client.TreeConnect));

            smb2Client.EnableSessionSigningAndEncryption(sessionId, sessionSiginingRequired, false);

            status = smb2Client.Create(
                creditCharge: 1,
                creditRequest: 1,
                flags: defaultFlags,
                messageId: messageId++,
                sessionId: sessionId,
                treeId: treeId,
                path: pipeName,
                desiredAccess: AccessMask.GENERIC_READ | AccessMask.GENERIC_WRITE,
                shareAccess: ShareAccess_Values.FILE_SHARE_READ,
                createOptions: CreateOptions_Values.NONE,
                createDispositions: CreateDisposition_Values.FILE_OPEN_IF,
                fileAttributes: File_Attributes.NONE,
                impersonationLevel: ImpersonationLevel_Values.Impersonation,
                securityFlag: SecurityFlags_Values.NONE,
                requestedOplockLevel: RequestedOplockLevel_Values.OPLOCK_LEVEL_NONE,
                createContexts: null,
                out fileId,
                out _,
                out _,
                out _);
            CheckStatusCode(status, nameof(Smb2Client.Create));
        }
Example #12
0
        private bool UserLogon(DetectionInfo info, Smb2Client client, out ulong messageId, out ulong sessionId, out Guid clientGuid, out NEGOTIATE_Response negotiateResp)
        {
            messageId = 0;
            sessionId = 0;
            client.ConnectOverTCP(Dns.GetHostAddresses(info.ContentServerName)[0]);

            #region Negotiate

            DialectRevision selectedDialect;
            byte[]          gssToken;
            Packet_Header   header;
            clientGuid = Guid.NewGuid();

            client.Negotiate(
                1,
                1,
                Packet_Header_Flags_Values.NONE,
                messageId++,
                new DialectRevision[] { DialectRevision.Smb30 },
                SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                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,
                clientGuid,
                out selectedDialect,
                out gssToken,
                out header,
                out negotiateResp);

            if (header.Status != Smb2Status.STATUS_SUCCESS)
            {
                LogFailedStatus("NEGOTIATE", header.Status);
                throw new Exception(string.Format("NEGOTIATE failed with {0}", Smb2Status.GetStatusCode(header.Status)));
            }

            #endregion

            #region Session Setup

            SESSION_SETUP_Response    sessionSetupResp;
            SspiClientSecurityContext sspiClientGss =
                new SspiClientSecurityContext(
                    SecurityPackageType,
                    Credential,
                    Smb2Utility.GetCifsServicePrincipalName(ContentServerName),
                    ClientSecurityContextAttribute.None,
                    SecurityTargetDataRepresentation.SecurityNativeDrep);

            // Server GSS token is used only for Negotiate authentication when enabled
            if (SecurityPackageType == SecurityPackageType.Negotiate)
            {
                sspiClientGss.Initialize(gssToken);
            }
            else
            {
                sspiClientGss.Initialize(null);
            }

            do
            {
                client.SessionSetup(
                    1,
                    64,
                    Packet_Header_Flags_Values.NONE,
                    messageId++,
                    sessionId,
                    SESSION_SETUP_Request_Flags.NONE,
                    SESSION_SETUP_Request_SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                    SESSION_SETUP_Request_Capabilities_Values.GLOBAL_CAP_DFS,
                    0,
                    sspiClientGss.Token,
                    out sessionId,
                    out gssToken,
                    out header,
                    out sessionSetupResp);

                if ((header.Status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED || header.Status == Smb2Status.STATUS_SUCCESS) && gssToken != null && gssToken.Length > 0)
                {
                    sspiClientGss.Initialize(gssToken);
                }
            } while (header.Status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED);

            if (header.Status != Smb2Status.STATUS_SUCCESS)
            {
                LogFailedStatus("SESSIONSETUP", header.Status);
                throw new Exception(string.Format("SESSIONSETUP failed with {0}", Smb2Status.GetStatusCode(header.Status)));
            }

            byte[] sessionKey;
            sessionKey = sspiClientGss.SessionKey;
            client.GenerateCryptoKeys(sessionId, sessionKey, true, false, null, false);

            #endregion

            return(true);
        }
        public void Smb2SessionSetup(SecurityPackageType authentication, string domain, string serverName, string userName, string password)
        {
            var sspiClientGss = new SspiClientSecurityContext(
                authentication,
                new AccountCredential(domain, userName, password),
                Smb2Utility.GetCifsServicePrincipalName(serverName),
                ClientSecurityContextAttribute.None,
                SecurityTargetDataRepresentation.SecurityNativeDrep
                );


            if (authentication == SecurityPackageType.Negotiate)
            {
                sspiClientGss.Initialize(serverGssToken);
            }
            else
            {
                sspiClientGss.Initialize(null);
            }

            Packet_Header packetHeader;

            SESSION_SETUP_Response sessionSetupResponse;

            uint status;

            while (true)
            {
                status = SessionSetup(
                    0,
                    RequestAndConsumeCredit(),
                    Packet_Header_Flags_Values.NONE,
                    GetMessageId(),
                    sessionId,
                    SESSION_SETUP_Request_Flags.NONE,
                    SESSION_SETUP_Request_SecurityMode_Values.NEGOTIATE_SIGNING_ENABLED,
                    SESSION_SETUP_Request_Capabilities_Values.NONE,
                    sessionId,
                    sspiClientGss.Token,
                    out sessionId,
                    out serverGssToken,
                    out packetHeader,
                    out sessionSetupResponse
                    );

                UpdateCredit(packetHeader);

                if ((status == Smb2Status.STATUS_MORE_PROCESSING_REQUIRED || status == Smb2Status.STATUS_SUCCESS) && serverGssToken != null && serverGssToken.Length > 0)
                {
                    sspiClientGss.Initialize(serverGssToken);
                }

                if (status != Smb2Status.STATUS_MORE_PROCESSING_REQUIRED)
                {
                    break;
                }
            }

            if (status != Smb2Status.STATUS_SUCCESS)
            {
                throw new InvalidOperationException(String.Format("SessionSetup failed with {0:X08}.", status));
            }

            encryptionEnabled = sessionSetupResponse.SessionFlags.HasFlag(SessionFlags_Values.SESSION_FLAG_ENCRYPT_DATA);


            GenerateCryptoKeys(
                sessionId,
                sspiClientGss.SessionKey,
                signingRequired,
                encryptionEnabled
                );

            if (!encryptionEnabled)
            {
                signingRequired = true;
            }

            EnableSessionSigningAndEncryption(sessionId, signingRequired, encryptionEnabled);
        }