static internal extern int AcquireCredentialsHandle( string pszPrincipal, string pszPackage, int fCredentialUse, IntPtr pvLogonID, IntPtr pAuthData, int pGetKeyFn, IntPtr pvGetKeyArgument, ref SecurityHandle phCredential, ref SecurityInteger ptsExpiry);
static internal extern int InitializeSecurityContext(ref SecurityHandle phCredential, IntPtr phContext, string pszTargetName, uint fContextReq, int Reserved1, uint TargetDataRep, IntPtr pInput, int Reserved2, out SecurityHandle phNewContext, out SecBufferDesc pOutput, out uint pfContextAttr, out SecurityInteger ptsTimeStamp);
internal static extern int InitializeSecurityContext(ref SecurityHandle phCredential, IntPtr phContext, string pszTargetName, uint fContextReq, int Reserved1, uint TargetDataRep, IntPtr pInput, int Reserved2, out SecurityHandle phNewContext, out SecBufferDesc pOutput, out uint pfContextAttr, out SecurityInteger ptsTimeStamp);
/// <summary> /// Initialize authentication sequence for the client /// </summary> /// <returns>Token to be sent to the server</returns> public SSPIResponse StartClientAuthentication(string targetMachine, uint targetPort) { // Save the server we're authenticating against _targetMachineSPN = string.Format("MSSQLSvc/{0}:{1}", targetMachine, targetPort); // Allocate a new instance of the client security buffer of the specified size SecBufferDesc clientSecBuffer = new SecBufferDesc(_maxTokenBufferSize); try { // Return code from the security API call int secReturnCode = 0; // New context attribute uint contextAttribute = 0; // Initialize token lifetime container SecurityInteger lifeTime = new SecurityInteger(); // Delegate into security API secReturnCode = SecurityWrapper.InitializeSecurityContext(ref _outboundCredential, IntPtr.Zero, _targetMachineSPN, (int)(SecContextRequirements.MutualAuthentication | SecContextRequirements.Delegate | SecContextRequirements.ExtendedError), 0, (int)SecDataRepresentation.Native, IntPtr.Zero, 0, out _clientContext, out clientSecBuffer, out contextAttribute, out lifeTime); // Check the return code if (secReturnCode != (int)SecResult.Ok && secReturnCode != (int)SecResult.ContinueNeeded) { // Operation failed throw new Win32Exception(secReturnCode, "Failed to generate initial security context"); } // Convert to byte array and indication whether this is a last call return(new SSPIResponse(clientSecBuffer.ToArray(), secReturnCode != (int)SecResult.ContinueNeeded && secReturnCode != (int)SecResult.CompleteAndContinue)); } finally { // Dispose server security buffer clientSecBuffer.Dispose(); } }
/// <summary> /// Create SSPI context for client /// </summary> public static SSPIContext CreateClient() { // Create an instance of the context SSPIContext context = new SSPIContext(); // Initialize token lifetime container SecurityInteger lifeTime = new SecurityInteger(); // Delegate into security API int secReturnCode = SecurityWrapper.AcquireCredentialsHandle(null, SecConstants.Negotiate, (int)SecPgkCredentials.Outbound, IntPtr.Zero, IntPtr.Zero, 0, IntPtr.Zero, ref context._outboundCredential, ref lifeTime); // Check if we succeeded if (secReturnCode != (int)SecResult.Ok) { // We couldn't obtain server credentials handle throw new Win32Exception(secReturnCode, "Failed to acquire client credentials handle"); } return(context); }
static internal extern int AcceptSecurityContext(ref SecurityHandle phCredential, ref SecurityHandle phContext, ref SecBufferDesc pInput, uint fContextReq, uint TargetDataRep, out SecurityHandle phNewContext, out SecBufferDesc pOutput, out uint pfContextAttr, out SecurityInteger ptsTimeStamp);
/// <summary> /// Initialize authentication sequence for the client /// </summary> /// <param name="clientToken">Payload received from the server</param> /// <returns>Token to be sent to the server</returns> public SSPIResponse ContinueClientAuthentication(byte[] clientToken) { // Wrap client token with the security buffer SecBufferDesc serverSecBuffer = new SecBufferDesc(clientToken); try { // Allocate a new instance of the client security buffer of the specified size SecBufferDesc clientSecBuffer = new SecBufferDesc(_maxTokenBufferSize); try { // Return code from the security API call int secReturnCode = 0; // New context attribute uint contextAttribute = 0; // Initialize token lifetime container SecurityInteger lifeTime = new SecurityInteger(); // Delegate into security API secReturnCode = SecurityWrapper.InitializeSecurityContext(ref _outboundCredential, ref _clientContext, _targetMachineSPN, (int)(SecContextRequirements.MutualAuthentication | SecContextRequirements.Delegate | SecContextRequirements.ExtendedError), 0, (int)SecDataRepresentation.Native, ref serverSecBuffer, 0, out _clientContext, out clientSecBuffer, out contextAttribute, out lifeTime); // Check the return code if (secReturnCode != (int)SecResult.Ok && secReturnCode != (int)SecResult.ContinueNeeded && secReturnCode != (int)SecResult.CompleteAndContinue) { // Operation failed throw new Win32Exception(secReturnCode, "Failed to generate security context"); } // NOTE: Digest SSP call to "CompleteAuthToken" is intentionally omitted because we don't support Digest today. // Convert to byte array and indication whether this is a last call return new SSPIResponse(clientSecBuffer.ToArray(), secReturnCode != (int)SecResult.ContinueNeeded && secReturnCode != (int)SecResult.CompleteAndContinue); } finally { // Dispose client security buffer clientSecBuffer.Dispose(); } } finally { // Dispose server security buffer serverSecBuffer.Dispose(); } }
/// <summary> /// Initialize authentication sequence for the client /// </summary> /// <returns>Token to be sent to the server</returns> public SSPIResponse StartClientAuthentication(string targetMachine, uint targetPort) { // Save the server we're authenticating against _targetMachineSPN = string.Format("MSSQLSvc/{0}:{1}", targetMachine, targetPort); // Allocate a new instance of the client security buffer of the specified size SecBufferDesc clientSecBuffer = new SecBufferDesc(_maxTokenBufferSize); try { // Return code from the security API call int secReturnCode = 0; // New context attribute uint contextAttribute = 0; // Initialize token lifetime container SecurityInteger lifeTime = new SecurityInteger(); // Delegate into security API secReturnCode = SecurityWrapper.InitializeSecurityContext(ref _outboundCredential, IntPtr.Zero, _targetMachineSPN, (int)(SecContextRequirements.MutualAuthentication | SecContextRequirements.Delegate | SecContextRequirements.ExtendedError), 0, (int)SecDataRepresentation.Native, IntPtr.Zero, 0, out _clientContext, out clientSecBuffer, out contextAttribute, out lifeTime); // Check the return code if (secReturnCode != (int)SecResult.Ok && secReturnCode != (int)SecResult.ContinueNeeded) { // Operation failed throw new Win32Exception(secReturnCode, "Failed to generate initial security context"); } // Convert to byte array and indication whether this is a last call return new SSPIResponse(clientSecBuffer.ToArray(), secReturnCode != (int)SecResult.ContinueNeeded && secReturnCode != (int)SecResult.CompleteAndContinue); } finally { // Dispose server security buffer clientSecBuffer.Dispose(); } }
/// <summary> /// Continue authentication sequence for the server /// </summary> /// <param name="clientToken">Token received from the client</param> /// <returns>Token to be sent to the client in response</returns> public SSPIResponse ContinueServerAuthentication(byte[] clientToken) { // Wrap client token with the security buffer SecBufferDesc clientSecBuffer = new SecBufferDesc(clientToken); try { // Allocate a new instance of the server security buffer of the specified size SecBufferDesc serverSecBuffer = new SecBufferDesc(_maxTokenBufferSize); try { // Return code from the security API call int secReturnCode = 0; // New context attribute uint contextAttribute = 0; // Initialize token lifetime container SecurityInteger lifeTime = new SecurityInteger(); // Delegate into security API secReturnCode = SecurityWrapper.AcceptSecurityContext(ref _inboundCredential, ref _serverContext, ref clientSecBuffer, (int)SecContextRequirements.MutualAuthentication, (int)SecDataRepresentation.Native, out _serverContext, out serverSecBuffer, out contextAttribute, out lifeTime); // Check the return code if (secReturnCode != (int)SecResult.Ok && secReturnCode != (int)SecResult.ContinueNeeded) { // Operation failed throw new Win32Exception(secReturnCode, "Failed to accept security context"); } // Convert to byte array and indication whether this is a last call return new SSPIResponse(serverSecBuffer.ToArray(), secReturnCode != (int)SecResult.ContinueNeeded); } finally { // Dispose server security buffer serverSecBuffer.Dispose(); } } finally { // Dispose client security buffer clientSecBuffer.Dispose(); } }
/// <summary> /// Create SSPI context for client /// </summary> public static SSPIContext CreateClient() { // Create an instance of the context SSPIContext context = new SSPIContext(); // Initialize token lifetime container SecurityInteger lifeTime = new SecurityInteger(); // Delegate into security API int secReturnCode = SecurityWrapper.AcquireCredentialsHandle(null, SecConstants.Negotiate, (int)SecPgkCredentials.Outbound, IntPtr.Zero, IntPtr.Zero, 0, IntPtr.Zero, ref context._outboundCredential, ref lifeTime); // Check if we succeeded if (secReturnCode != (int)SecResult.Ok) { // We couldn't obtain server credentials handle throw new Win32Exception(secReturnCode, "Failed to acquire client credentials handle"); } return context; }