private void GetMaxTokenSize() { int count; SafeContextBufferHandle secPkgInfos; if (Sspi.EnumerateSecurityPackages(out count, out secPkgInfos) != SecurityStatus.SEC_E_OK) { throw new Win32Exception("Failed to EnumerateSecurityPackages"); } for (int i = 0; i < count; i++) { var item = secPkgInfos.GetItem <SecPkgInfo>(i); if (string.Compare(item.GetName(), @"Schannel", true) == 0) { maxTokenSize = item.cbMaxToken; break; } } if (maxTokenSize == 0) { throw new Exception("Failed to retrive cbMaxToken for Schannel"); } }
public override void Start() { long num; Sspi.AcquireCredentialsHandle(CredentialUse.SECPKG_CRED_INBOUND, new SchannelCred(this.certificate, SchProtocols.TlsServer), out this.credential, out num); this.GetMaxTokenSize(); base.Start(); }
public SipMicrosoftAuthentication(AuthSchemes scheme, IAccounts accounts, IUserz userz) { this.scheme = scheme; this.accounts = accounts; this.userz = userz; this.connectingAssociations = new ThreadSafe.Dictionary <int, SecurityAssociation>(new Dictionary <int, SecurityAssociation>()); this.timer = new Timer(RemoveExpiredSecurityAssociationsTimer, null, 0, 60 * 1000); this.credHandle = Sspi.SafeAcquireCredentialsHandle(scheme.ToString(), CredentialUse.SECPKG_CRED_BOTH); }
public override void Start() { long expiry; Sspi.AcquireCredentialsHandle( CredentialUse.SECPKG_CRED_INBOUND, new SchannelCred(certificate, SchProtocols.TlsServer), out credential, out expiry); GetMaxTokenSize(); base.Start(); }
public bool Authentication(SafeCredHandle credHandle, Methods method, byte[] realm, byte[] inToken, out ArraySegment <byte> outToken) { //idleTime = DateTime.UtcNow.AddMinutes(IdleMinutes); InitializeThreadStaticVars(); secBufferDesc1.Buffers[0].SetBuffer(BufferType.SECBUFFER_TOKEN, inToken); secBufferDesc1.Buffers[1].SetBuffer(BufferType.SECBUFFER_PKG_PARAMS, method.ToByteArrayPart().Bytes); secBufferDesc1.Buffers[2].SetBuffer(BufferType.SECBUFFER_PKG_PARAMS, new byte[0]); secBufferDesc1.Buffers[3].SetBuffer(BufferType.SECBUFFER_PKG_PARAMS, new byte[0]); secBufferDesc1.Buffers[4].SetBuffer(BufferType.SECBUFFER_PKG_PARAMS, realm); secBufferDesc1.Buffers[5].SetBuffer(BufferType.SECBUFFER_CHANNEL_BINDINGS, new byte[0]); secBufferDesc2.Buffers[0].SetBuffer(BufferType.SECBUFFER_TOKEN, bytes1); secBufferDesc2.Buffers[1].SetBufferEmpty(); var newHandle = (contextHandle.IsInvalid) ? new SafeCtxtHandle() : contextHandle; var result = Sspi.SafeAcceptSecurityContext( ref credHandle, ref contextHandle, ref secBufferDesc1, 0, TargetDataRep.SECURITY_NETWORK_DREP, ref newHandle, ref secBufferDesc2); Tracer.WriteInformation("SSPI Digest Auth: " + result.ToString()); if (contextHandle.IsInvalid && newHandle.IsInvalid == false) { contextHandle = newHandle; } if (result == SecurityStatus.SEC_E_OK) { outToken = new ArraySegment <byte>(); isAuthenticationComplete = true; return(true); } else { outToken = new ArraySegment <byte>(); return(false); } }
public void SignMessage(SipMessageWriter writer) { outSnum++; int srand2 = Environment.TickCount; InitializeThreadStaticVars(); int length = SignatureBuffer.Generate(scheme, srand2, outSnum, targetname, writer, ref bytes1); if (bytes2.Length < maxSignatureSize) { bytes2 = new byte[maxSignatureSize]; } secBufferDesc1.Buffers[0].SetBuffer(BufferType.SECBUFFER_DATA, bytes1, 0, length); secBufferDesc1.Buffers[1].SetBuffer(BufferType.SECBUFFER_TOKEN, bytes2); var result = Sspi.SafeMakeSignature(contextHandle, ref secBufferDesc1, 100); Tracer.WriteInformation("Signature: " + result.ToString()); if (Sspi.Succeeded(result)) { writer.WriteAuthenticationInfo(true, scheme, targetname, realm, Opaque, outSnum, srand2, new ArraySegment <byte>(bytes2, 0, secBufferDesc1.Buffers[1].Size)); if (writer.IsResponse && writer.StatusCode >= 200 && writer.StatusCode <= 299) { if (writer.Method == Methods.Registerm && writer.Expires != int.MinValue) { idleTime = DateTime.UtcNow.AddSeconds(writer.Expires + 30); idleTimeUpdatedByExpires = true; } } else { // TODO: INVITE Session-Expires } } }
private void GetMaxTokenSize() { int num; SafeContextBufferHandle safeContextBufferHandle; if (Sspi.EnumerateSecurityPackages(out num, out safeContextBufferHandle) != SecurityStatus.SEC_E_OK) { throw new Win32Exception("Failed to EnumerateSecurityPackages"); } for (int i = 0; i < num; i++) { SecPkgInfo item = safeContextBufferHandle.GetItem <SecPkgInfo>(i); if (string.Compare(item.GetName(), "Schannel", true) == 0) { this.maxTokenSize = item.cbMaxToken; break; } } if (this.maxTokenSize == 0) { throw new Exception("Failed to retrive cbMaxToken for Schannel"); } }
private static MaxTokenSizes GetMaxTokenSizes() { int count; SafeContextBufferHandle secPkgInfos; if (Sspi.EnumerateSecurityPackages(out count, out secPkgInfos) != SecurityStatus.SEC_E_OK) { throw new Win32Exception("Failed to EnumerateSecurityPackages"); } int ntlm = 0, kerberos = 0; for (int i = 0; i < count; i++) { var item = secPkgInfos.GetItem <SecPkgInfo>(i); if (string.Compare(item.GetName(), @"NTLM", true) == 0) { ntlm = item.cbMaxToken; } if (string.Compare(item.GetName(), @"Kerberos", true) == 0) { kerberos = item.cbMaxToken; } } if (ntlm == 0) { throw new Exception(@"Failed to retrive cbMaxToken for NTLM"); } if (kerberos == 0) { throw new Exception(@"Failed to retrive cbMaxToken for Kerberos"); } return(new MaxTokenSizes(ntlm, kerberos)); }
public ErrorCodes Authentication(SafeCredHandle credHandle, byte[] inToken, out ArraySegment <byte> outToken) { idleTime = DateTime.UtcNow.AddMinutes(IdleMinutes); InitializeThreadStaticVars(); secBufferDesc1.Buffers[0].SetBuffer(BufferType.SECBUFFER_TOKEN, inToken); secBufferDesc1.Buffers[1].SetBufferEmpty(); secBufferDesc2.Buffers[0].SetBuffer(BufferType.SECBUFFER_TOKEN, bytes1); secBufferDesc2.Buffers[1].SetBufferEmpty(); var newHandle = (contextHandle.IsInvalid) ? new SafeCtxtHandle() : contextHandle; var result = Sspi.SafeAcceptSecurityContext( ref credHandle, ref contextHandle, ref secBufferDesc1, (int)(ContextReq.ASC_REQ_INTEGRITY | ContextReq.ASC_REQ_IDENTIFY | ((scheme == AuthSchemes.Ntlm) ? ContextReq.ASC_REQ_DATAGRAM : ContextReq.ASC_REQ_MUTUAL_AUTH)), TargetDataRep.SECURITY_NETWORK_DREP, ref newHandle, ref secBufferDesc2); Tracer.WriteInformation("Auth: " + result.ToString()); if (contextHandle.IsInvalid && newHandle.IsInvalid == false) { contextHandle = newHandle; } if (result == SecurityStatus.SEC_E_OK) { outToken = new ArraySegment <byte>(); isAuthenticationComplete = true; SecPkgContext_Sizes sizes; if (Sspi.Failed(Sspi.SafeQueryContextAttributes(ref contextHandle, out sizes))) { return(ErrorCodes.QueryContextAttributesForSizesFailed); } maxSignatureSize = sizes.cbMaxSignature; if (Sspi.Failed(Sspi.SafeQueryContextAttributes(ref contextHandle, out userName))) { return(ErrorCodes.QueryContextAttributesForUsernameFailed); } int slash = userName.IndexOf('\\'); if (slash >= 0) { userName = userName.Substring(slash + 1); } Tracer.WriteInformation("Username: " + userName); expireTime = DateTime.UtcNow.AddHours(ExpirationHours); return(ErrorCodes.Ok); } else if (result == SecurityStatus.SEC_I_CONTINUE_NEEDED) { outToken = new ArraySegment <byte>(bytes1, 0, secBufferDesc2.Buffers[0].Size); return(ErrorCodes.Continue); } else { outToken = new ArraySegment <byte>(); return(ErrorCodes.SecurityViolation); } }
public SspiDigestAuthorizationManager() { this.credHandle = Sspi.SafeAcquireCredentialsHandle(AuthSchemes.Digest.ToString(), CredentialUse.SECPKG_CRED_BOTH); }
public InitializeStep(string servicePrincipalName, string authorizationId, Sspi.SecurityContext context, byte[] bytesToSendToServer) { _servicePrincipalName = servicePrincipalName; _authorizationId = authorizationId; _context = context; _bytesToSendToServer = bytesToSendToServer ?? new byte[0]; }
private bool Handshake(ServerAsyncEventArgs ie, Server <C> .Connection <C> connection) { int num = 0; ServerAsyncEventArgs serverAsyncEventArgs = null; SspiContext sspiContext = connection.SspiContext; SecBufferDescEx secBufferDescEx = sspiContext.SecBufferDesc2[0]; SecBufferDescEx secBufferDescEx2 = sspiContext.SecBufferDesc2[1]; bool result; try { if (sspiContext.Buffer.IsValid && ie != null && !sspiContext.Buffer.CopyTransferredFrom(ie, 0)) { result = false; } else { while (true) { secBufferDescEx.Buffers[0].BufferType = BufferType.SECBUFFER_TOKEN; if (sspiContext.Buffer.IsValid) { this.SetSecBuffer(ref secBufferDescEx.Buffers[0], sspiContext); } else { this.SetSecBuffer(ref secBufferDescEx.Buffers[0], ie); } secBufferDescEx.Buffers[1].SetBufferEmpty(); if (serverAsyncEventArgs == null) { serverAsyncEventArgs = EventArgsManager.Get(); } serverAsyncEventArgs.AllocateBuffer(); secBufferDescEx2.Buffers[0].BufferType = BufferType.SECBUFFER_TOKEN; secBufferDescEx2.Buffers[0].Size = serverAsyncEventArgs.Count; secBufferDescEx2.Buffers[0].Buffer = serverAsyncEventArgs.Buffer; secBufferDescEx2.Buffers[0].Offset = serverAsyncEventArgs.Offset; secBufferDescEx2.Buffers[1].SetBufferEmpty(); int contextReq = 98332; SafeCtxtHandle handle = sspiContext.Handle.IsInvalid ? new SafeCtxtHandle() : sspiContext.Handle; long num2; SecurityStatus securityStatus = Sspi.SafeAcceptSecurityContext(ref this.credential, ref sspiContext.Handle, ref secBufferDescEx, contextReq, TargetDataRep.SECURITY_NATIVE_DREP, ref handle, ref secBufferDescEx2, out num, out num2); if (sspiContext.Handle.IsInvalid) { sspiContext.Handle = handle; } SecurityStatus securityStatus2 = securityStatus; if (securityStatus2 == (SecurityStatus)2148074264u) { break; } if (securityStatus2 != (SecurityStatus)2148074273u) { if ((securityStatus == SecurityStatus.SEC_I_CONTINUE_NEEDED || securityStatus == SecurityStatus.SEC_E_OK || (Sspi.Failed(securityStatus) && (num & 32768) != 0)) && secBufferDescEx2.Buffers[0].Size > 0) { serverAsyncEventArgs.Count = secBufferDescEx2.Buffers[0].Size; serverAsyncEventArgs.CopyAddressesFrom(ie); serverAsyncEventArgs.LocalEndPoint = base.GetLocalEndpoint(ie.RemoteEndPoint.Address); base.SendAsync(connection, serverAsyncEventArgs); serverAsyncEventArgs = null; } int bufferIndex = secBufferDescEx.GetBufferIndex(BufferType.SECBUFFER_EXTRA, 0); if (bufferIndex < 0) { sspiContext.Buffer.Free(); } else if (sspiContext.Buffer.IsInvalid) { if (!sspiContext.Buffer.CopyTransferredFrom(ie, ie.BytesTransferred - secBufferDescEx.Buffers[bufferIndex].Size)) { goto Block_21; } } else { sspiContext.Buffer.MoveToBegin(sspiContext.Buffer.BytesTransferred - secBufferDescEx.Buffers[bufferIndex].Size, secBufferDescEx.Buffers[bufferIndex].Size); } SecurityStatus securityStatus3 = securityStatus; if (securityStatus3 == SecurityStatus.SEC_E_OK) { goto IL_2FF; } if (securityStatus3 != SecurityStatus.SEC_I_CONTINUE_NEEDED) { goto Block_23; } if (bufferIndex < 0) { goto Block_25; } } else { if (serverAsyncEventArgs.Count >= this.maxTokenSize) { goto IL_1DC; } serverAsyncEventArgs.Count = this.maxTokenSize; serverAsyncEventArgs.ReAllocateBuffer(false); } } if (sspiContext.Buffer.IsInvalid && !sspiContext.Buffer.CopyTransferredFrom(ie, 0)) { result = false; return(result); } result = true; return(result); IL_1DC: result = false; return(result); Block_21: result = false; return(result); Block_23: result = false; return(result); IL_2FF: if (Sspi.SafeQueryContextAttributes(ref sspiContext.Handle, out sspiContext.StreamSizes) != SecurityStatus.SEC_E_OK) { result = false; return(result); } sspiContext.Connected = true; this.OnNewConnection(connection); result = true; return(result); Block_25: result = true; } } finally { if (serverAsyncEventArgs != null) { EventArgsManager.Put(ref serverAsyncEventArgs); } } return(result); }
private bool DecryptData(ref ServerAsyncEventArgs e, Server <C> .Connection <C> connection) { SspiContext sspiContext = connection.SspiContext; SecBufferDescEx secBufferDesc = sspiContext.SecBufferDesc5; if (sspiContext.Buffer.IsValid && e != null && !sspiContext.Buffer.CopyTransferredFrom(e, 0)) { return(false); } SecurityStatus securityStatus2; while (true) { secBufferDesc.Buffers[0].BufferType = BufferType.SECBUFFER_DATA; if (sspiContext.Buffer.IsValid) { this.SetSecBuffer(ref secBufferDesc.Buffers[0], sspiContext); } else { this.SetSecBuffer(ref secBufferDesc.Buffers[0], e); } secBufferDesc.Buffers[1].SetBufferEmpty(); secBufferDesc.Buffers[2].SetBufferEmpty(); secBufferDesc.Buffers[3].SetBufferEmpty(); secBufferDesc.Buffers[4].SetBufferEmpty(); SecurityStatus securityStatus = Sspi.SafeDecryptMessage(ref sspiContext.Handle, ref secBufferDesc, 0u, null); int bufferIndex = secBufferDesc.GetBufferIndex(BufferType.SECBUFFER_EXTRA, 0); int bufferIndex2 = secBufferDesc.GetBufferIndex(BufferType.SECBUFFER_DATA, 0); securityStatus2 = securityStatus; if (securityStatus2 != SecurityStatus.SEC_E_OK) { break; } if (bufferIndex2 < 0) { return(false); } if (sspiContext.Buffer.IsInvalid) { if (bufferIndex >= 0 && !sspiContext.Buffer.CopyFrom(secBufferDesc.Buffers[bufferIndex])) { return(false); } e.Offset = secBufferDesc.Buffers[bufferIndex2].Offset; e.BytesTransferred = secBufferDesc.Buffers[bufferIndex2].Size; e.SetMaxCount(); if (!this.OnReceived(connection, ref e)) { return(false); } } else { ArraySegment <byte> buffer = sspiContext.Buffer.Detach(); if (bufferIndex >= 0 && !sspiContext.Buffer.CopyFrom(secBufferDesc.Buffers[bufferIndex])) { return(false); } ServerAsyncEventArgs serverAsyncEventArgs = EventArgsManager.Get(); base.PrepareEventArgs(connection, serverAsyncEventArgs); serverAsyncEventArgs.AttachBuffer(buffer); serverAsyncEventArgs.Offset = secBufferDesc.Buffers[bufferIndex2].Offset; serverAsyncEventArgs.BytesTransferred = secBufferDesc.Buffers[bufferIndex2].Size; serverAsyncEventArgs.SetMaxCount(); bool flag = this.OnReceived(connection, ref serverAsyncEventArgs); if (serverAsyncEventArgs != null) { EventArgsManager.Put(serverAsyncEventArgs); } if (!flag) { return(false); } } if (bufferIndex < 0) { return(true); } } return(securityStatus2 != SecurityStatus.SEC_I_RENEGOTIATE && securityStatus2 == (SecurityStatus)2148074264u && (!sspiContext.Buffer.IsInvalid || sspiContext.Buffer.CopyTransferredFrom(e, 0))); }
public override unsafe void SendAsync(ServerAsyncEventArgs e) { try { var connection = GetTcpConnection(e.RemoteEndPoint); OnBeforeSend(connection, e); if (connection == null) { e.Completed = Send_Completed; e.SocketError = SocketError.NotConnected; e.OnCompleted(null); return; } var context = connection.SspiContext; var sizes = context.StreamSizes; var dataCount = e.Count; if (e.OffsetOffset >= sizes.cbHeader) { e.OffsetOffset -= sizes.cbHeader; e.Count = sizes.cbHeader + dataCount + sizes.cbTrailer; e.ReAllocateBuffer(true); } else { throw new NotImplementedException("Ineffective way not implemented. Need to move buffer for SECBUFFER_STREAM_HEADER."); } var message = new SecBufferDescEx( new SecBufferEx[] { new SecBufferEx() { BufferType = BufferType.SECBUFFER_STREAM_HEADER, Buffer = e.Buffer, Size = sizes.cbHeader, Offset = e.Offset, }, new SecBufferEx() { BufferType = BufferType.SECBUFFER_DATA, Buffer = e.Buffer, Size = dataCount, Offset = e.Offset + sizes.cbHeader, }, new SecBufferEx() { BufferType = BufferType.SECBUFFER_STREAM_TRAILER, Buffer = e.Buffer, Size = sizes.cbTrailer, Offset = e.Offset + sizes.cbHeader + dataCount, }, new SecBufferEx() { BufferType = BufferType.SECBUFFER_EMPTY, }, }); Sspi.EncryptMessage( ref context.Handle, ref message, 0, null); e.Count = message.Buffers[0].Size + message.Buffers[1].Size + message.Buffers[2].Size; e.ReAllocateBuffer(true); base.SendAsync(connection, e); } catch (SspiException ex) { e.SocketError = SocketError.Fault; OnFailed(new ServerInfoEventArgs(realEndPoint, ex)); } }
private unsafe bool Handshake(ServerAsyncEventArgs ie, Connection <C> connection) { int contextAttr = 0; ServerAsyncEventArgs oe = null; var context = connection.SspiContext; var input = context.SecBufferDesc2[0]; var output = context.SecBufferDesc2[1]; try { if (context.Buffer.IsValid && ie != null) { if (context.Buffer.CopyTransferredFrom(ie, 0) == false) { return(false); } } for (; ;) { // prepare input buffer // input.Buffers[0].BufferType = BufferType.SECBUFFER_TOKEN; if (context.Buffer.IsValid) { SetSecBuffer(ref input.Buffers[0], context); } else { SetSecBuffer(ref input.Buffers[0], ie); } input.Buffers[1].SetBufferEmpty(); // prepare output buffer // if (oe == null) { oe = EventArgsManager.Get(); } oe.AllocateBuffer(); output.Buffers[0].BufferType = BufferType.SECBUFFER_TOKEN; output.Buffers[0].Size = oe.Count; output.Buffers[0].Buffer = oe.Buffer; output.Buffers[0].Offset = oe.Offset; output.Buffers[1].SetBufferEmpty(); // prepare some args and call SSPI // int contextReq = (int)(ContextReq.ASC_REQ_SEQUENCE_DETECT | ContextReq.ASC_REQ_REPLAY_DETECT | ContextReq.ASC_REQ_CONFIDENTIALITY | ContextReq.ASC_REQ_EXTENDED_ERROR | ContextReq.ASC_REQ_STREAM); var newHandle = (context.Handle.IsInvalid) ? new SafeCtxtHandle() : context.Handle; long timeStamp; var result = Sspi.SafeAcceptSecurityContext( ref credential, ref context.Handle, ref input, contextReq, TargetDataRep.SECURITY_NATIVE_DREP, ref newHandle, ref output, out contextAttr, out timeStamp); if (context.Handle.IsInvalid) { context.Handle = newHandle; } // proccess non-critical errors // switch (result) { case SecurityStatus.SEC_E_INCOMPLETE_MESSAGE: if (context.Buffer.IsInvalid) { if (context.Buffer.CopyTransferredFrom(ie, 0) == false) { return(false); } } return(true); case SecurityStatus.SEC_E_BUFFER_TOO_SMALL: if (oe.Count < maxTokenSize) { oe.Count = maxTokenSize; oe.ReAllocateBuffer(false); continue; } return(false); } // send response to client // if (result == SecurityStatus.SEC_I_CONTINUE_NEEDED || result == SecurityStatus.SEC_E_OK || (Sspi.Failed(result) && (contextAttr & (int)ContextAttr.ASC_RET_EXTENDED_ERROR) != 0)) { if (output.Buffers[0].Size > 0) { oe.Count = output.Buffers[0].Size; oe.CopyAddressesFrom(ie); oe.LocalEndPoint = GetLocalEndpoint(ie.RemoteEndPoint.Address); base.SendAsync(connection, oe); oe = null; } } // move extra data to buffer // int extraIndex = input.GetBufferIndex(BufferType.SECBUFFER_EXTRA, 0); if (extraIndex < 0) { context.Buffer.Free(); } else { if (context.Buffer.IsInvalid) { if (context.Buffer.CopyTransferredFrom(ie, ie.BytesTransferred - input.Buffers[extraIndex].Size) == false) { return(false); } } else { context.Buffer.MoveToBegin(context.Buffer.BytesTransferred - input.Buffers[extraIndex].Size, input.Buffers[extraIndex].Size); } } // proccess error-codes // switch (result) { case SecurityStatus.SEC_E_OK: if (Sspi.SafeQueryContextAttributes(ref context.Handle, out context.StreamSizes) != SecurityStatus.SEC_E_OK) { return(false); } context.Connected = true; OnNewConnection(connection); return(true); case SecurityStatus.SEC_I_CONTINUE_NEEDED: if (extraIndex >= 0) { continue; } return(true); default: return(false); } } } finally { if (oe != null) { EventArgsManager.Put(ref oe); } } }
public bool VerifySignature(SipMessageReader reader, Credentials credentials) { bool result = false; InitializeThreadStaticVars(); int length = SignatureBuffer.Generate(scheme, credentials.Crand, credentials.Cnum, targetname, reader, ref bytes1); secBufferDesc1.Buffers[0].SetBuffer(BufferType.SECBUFFER_DATA, bytes1, 0, length); if (bytes2.Length < credentials.Response.Length / 2) { bytes2 = new byte[credentials.Response.Length]; } if (HexEncoding.TryParseHex(credentials.Response.ToArraySegment(), bytes2) >= 0) { secBufferDesc1.Buffers[1].SetBuffer(BufferType.SECBUFFER_TOKEN, bytes2, 0, credentials.Response.Length / 2); var result2 = Sspi.SafeVerifySignature(contextHandle, ref secBufferDesc1, 100); Tracer.WriteInformation("VerifySignature: " + result2.ToString()); result = Sspi.Succeeded(result2); } { //if (auth.Cnum > _LastCnum + SlidingWindowSize || auth.Cnum < _LastCnum - SlidingWindowSize || auth.Cnum == 0) // // cnum в не скользящего окна // throw new AuthenticationManager.MessageDiscardException(); //// индекс верхней границы скользящего окна //int index = auth.Cnum >= SlidingWindowSize ? (auth.Cnum - SlidingWindowSize) % SlidingWindowSize : auth.Cnum - 1; //if (auth.Cnum > _LastCnum) //{ // // индекс нижней границы скользящего окна // int lindex = _LastCnum >= SlidingWindowSize ? (_LastCnum - SlidingWindowSize + 1) % SlidingWindowSize : _LastCnum; // // смещение скользящего окна // if (lindex > index) // { // while (lindex < SlidingWindowSize) // _SlidingWindow[lindex++] = false; // lindex = 0; // } // while (lindex < index) // _SlidingWindow[lindex++] = false; // _LastCnum = auth.Cnum; //} //else //{ // if (_SlidingWindow[index] == true) // // дублирование cnum // throw new AuthenticationManager.MessageDiscardException(); //} //_SlidingWindow[index] = true; // удаление обработанного поля заголовка //message.Header.Headers[message.Header.FindHeaderIndex(auth_name, auth_index)].IsRemoved = true; //message.Verified = true; } if (idleTimeUpdatedByExpires == false) { idleTime = DateTime.UtcNow.AddMinutes(IdleMinutes); } return(result); }
public override void SendAsync(ServerAsyncEventArgs e) { try { Server <C> .Connection <C> tcpConnection = base.GetTcpConnection(e.RemoteEndPoint); base.OnBeforeSend(tcpConnection, e); if (tcpConnection == null) { e.Completed = new ServerAsyncEventArgs.CompletedEventHandler(base.Send_Completed); e.SocketError = SocketError.NotConnected; e.OnCompleted(null); } else { SspiContext sspiContext = tcpConnection.SspiContext; SecPkgContext_StreamSizes streamSizes = sspiContext.StreamSizes; int count = e.Count; if (e.OffsetOffset < streamSizes.cbHeader) { throw new NotImplementedException("Ineffective way not implemented. Need to move buffer for SECBUFFER_STREAM_HEADER."); } e.OffsetOffset -= streamSizes.cbHeader; e.Count = streamSizes.cbHeader + count + streamSizes.cbTrailer; e.ReAllocateBuffer(true); SecBufferDescEx secBufferDescEx = new SecBufferDescEx(new SecBufferEx[] { new SecBufferEx { BufferType = BufferType.SECBUFFER_STREAM_HEADER, Buffer = e.Buffer, Size = streamSizes.cbHeader, Offset = e.Offset }, new SecBufferEx { BufferType = BufferType.SECBUFFER_DATA, Buffer = e.Buffer, Size = count, Offset = e.Offset + streamSizes.cbHeader }, new SecBufferEx { BufferType = BufferType.SECBUFFER_STREAM_TRAILER, Buffer = e.Buffer, Size = streamSizes.cbTrailer, Offset = e.Offset + streamSizes.cbHeader + count }, new SecBufferEx { BufferType = BufferType.SECBUFFER_VERSION } }); Sspi.EncryptMessage(ref sspiContext.Handle, ref secBufferDescEx, 0u, null); e.Count = secBufferDescEx.Buffers[0].Size + secBufferDescEx.Buffers[1].Size + secBufferDescEx.Buffers[2].Size; e.ReAllocateBuffer(true); base.SendAsync(tcpConnection, e); } } catch (SspiException error) { e.SocketError = SocketError.Fault; this.OnFailed(new ServerInfoEventArgs(this.realEndPoint, error)); } }
public NegotiateStep(string authorizationId, Sspi.SecurityContext context, byte[] bytesToSendToServer) { _authorizationId = authorizationId; _context = context; _bytesToSendToServer = bytesToSendToServer ?? new byte[0]; }
unsafe private bool DecryptData(ref ServerAsyncEventArgs e, Connection <C> connection) { var context = connection.SspiContext; var message = context.SecBufferDesc5; if (context.Buffer.IsValid && e != null) { if (context.Buffer.CopyTransferredFrom(e, 0) == false) { return(false); } } for (; ;) { // prepare buffer // message.Buffers[0].BufferType = BufferType.SECBUFFER_DATA; if (context.Buffer.IsValid) { SetSecBuffer(ref message.Buffers[0], context); } else { SetSecBuffer(ref message.Buffers[0], e); } message.Buffers[1].SetBufferEmpty(); message.Buffers[2].SetBufferEmpty(); message.Buffers[3].SetBufferEmpty(); message.Buffers[4].SetBufferEmpty(); // call SSPI // var result = Sspi.SafeDecryptMessage(ref context.Handle, ref message, 0, null); // analize result // int extraIndex = message.GetBufferIndex(BufferType.SECBUFFER_EXTRA, 0); int dataIndex = message.GetBufferIndex(BufferType.SECBUFFER_DATA, 0); switch (result) { case SecurityStatus.SEC_E_OK: if (dataIndex >= 0) { if (context.Buffer.IsInvalid) { if (extraIndex >= 0) { if (context.Buffer.CopyFrom(message.Buffers[extraIndex]) == false) { return(false); } } e.Offset = message.Buffers[dataIndex].Offset; e.BytesTransferred = message.Buffers[dataIndex].Size; e.SetMaxCount(); if (OnReceived(connection, ref e) == false) { return(false); } } else { var buffer = context.Buffer.Detach(); if (extraIndex >= 0) { if (context.Buffer.CopyFrom(message.Buffers[extraIndex]) == false) { return(false); } } // create eventarg and call onreceived event // var e2 = EventArgsManager.Get(); base.PrepareEventArgs(connection, e2); e2.AttachBuffer(buffer); e2.Offset = message.Buffers[dataIndex].Offset; e2.BytesTransferred = message.Buffers[dataIndex].Size; e2.SetMaxCount(); bool continue1 = OnReceived(connection, ref e2); if (e2 != null) { EventArgsManager.Put(e2); } if (continue1 == false) { return(false); } } if (extraIndex >= 0) { continue; } return(true); } return(false); case SecurityStatus.SEC_E_INCOMPLETE_MESSAGE: if (context.Buffer.IsInvalid) { if (context.Buffer.CopyTransferredFrom(e, 0) == false) { return(false); } } return(true); case SecurityStatus.SEC_I_RENEGOTIATE: // MSDN: Renegotiation is not supported for Schannel kernel mode. The // caller should either ignore this return value or shut down the // connection. // If the value is ignored, either the client or the server might shut // down the connection as a result. return(false); default: return(false); } } }