public byte[] GetOutgoingBlob(byte[] incomingBlob, out bool handshakeComplete)
        {
            handshakeComplete = true;
            if (this.m_SecurityContext.Handle.Initialized && incomingBlob == null)
            {
                return(null);
            }
            SecurityBufferClass inputBuffer = null;

            if (incomingBlob != null)
            {
                inputBuffer = new SecurityBufferClass(incomingBlob, BufferType.Token);
            }
            SecurityBufferClass securityBufferClass = new SecurityBufferClass(this.m_TokenSize, BufferType.Token);
            int num  = SSPIWrapper.InitializeSecurityContext(ref this.m_CredentialsHandle.Handle, ref this.m_SecurityContext.Handle, this.m_RemotePeerId, (int)this.m_RequestedFlags, this.m_Endianness, inputBuffer, ref this.m_SecurityContext.Handle, securityBufferClass, ref this.m_ContextFlags, ref this.m_SecurityContext.TimeStamp);
            int num2 = num & -2147483648;

            if (num2 != 0)
            {
                throw new Win32Exception(num);
            }
            if (num != 0 && this.m_SecurityContext.Handle.Initialized)
            {
                handshakeComplete = false;
            }
            else
            {
                switch (this.m_SecurityContext.SecurityContextMode)
                {
                case SecurityContextMode.stream:
                    this.CheckIfFlagWasObtainedIfRequested(ContextFlags.Stream);
                    break;
                }
                this.CheckIfFlagWasObtainedIfRequested(ContextFlags.MutualAuth);
                this.CheckIfFlagWasObtainedIfRequested(ContextFlags.ReplayDetect);
                this.CheckIfFlagWasObtainedIfRequested(ContextFlags.SequenceDetect);
                this.CheckIfFlagWasObtainedIfRequested(ContextFlags.Confidentiality);
            }
            return(securityBufferClass.token);
        }
 private void WriteInBlockMode(byte[] buffer, int offset, int size)
 {
     for (int i = Math.Min(this.maxEncryptionBufferSize, size); i > 0; i = Math.Min(this.maxEncryptionBufferSize, size))
     {
         SecurityBufferClass securityBufferClass = this.securityBuffers[0];
         securityBufferClass.offset = offset;
         securityBufferClass.size   = i;
         securityBufferClass.token  = buffer;
         securityBufferClass.type   = 1;
         securityBufferClass        = this.securityBuffers[1];
         securityBufferClass.offset = 0;
         securityBufferClass.size   = this.maxTokenSize;
         securityBufferClass.token  = this.tokenBufferForWrite;
         securityBufferClass.type   = 2;
         int num = SSPIWrapper.EncryptMessage(ref this.securityContext.Handle, this.securityBuffers, ++this.sequenceNumberForWrite);
         if (num != 0)
         {
             throw new XmlaStreamException(new Win32Exception(num).Message);
         }
         base.Write();
         offset += i;
         size   -= i;
     }
 }
Example #3
0
        public override int Read(byte[] buffer, int offset, int size)
        {
            if (this.disposed)
            {
                throw new ObjectDisposedException(null);
            }
            int result;

            try
            {
                if (size == 0)
                {
                    result = 0;
                }
                else
                {
                    while (this.dataSizeForRead <= 0)
                    {
                        if (!this.Read())
                        {
                            result = 0;
                            return(result);
                        }
                        int num = SSPIWrapper.VerifySignature(ref this.securityContext.Handle, 0, this.securityBuffers, ++this.sequenceNumberForRead);
                        if (num != 0)
                        {
                            throw new XmlaStreamException(new Win32Exception(num).Message);
                        }
                        SecurityBufferClass securityBufferClass = this.securityBuffers[0];
                        if (securityBufferClass.offset + securityBufferClass.size > 65535)
                        {
                            throw new XmlaStreamException(XmlaSR.InternalError);
                        }
                        this.dataOffsetForRead = (ushort)securityBufferClass.offset;
                        this.dataSizeForRead   = (ushort)securityBufferClass.size;
                    }
                    ushort num2 = 0;
                    int    num3 = (int)this.dataOffsetForRead;
                    int    num4 = (int)(this.dataOffsetForRead + this.dataSizeForRead);
                    int    num5 = offset;
                    int    num6 = offset + size;
                    while (num3 < num4 && num5 < num6)
                    {
                        buffer[num5] = this.dataBufferForRead[num3];
                        num3++;
                        num5++;
                        num2 += 1;
                    }
                    this.dataSizeForRead   -= num2;
                    this.dataOffsetForRead += num2;
                    result = (int)num2;
                }
            }
            catch (XmlaStreamException)
            {
                throw;
            }
            catch (IOException innerException)
            {
                throw new XmlaStreamException(innerException);
            }
            catch (SocketException innerException2)
            {
                throw new XmlaStreamException(innerException2);
            }
            catch (Win32Exception innerException3)
            {
                throw new XmlaStreamException(innerException3);
            }
            return(result);
        }
        internal TcpSecureStream(TcpStream tcpStream, SecurityContext securityContext) : base(tcpStream)
        {
            if (securityContext == null)
            {
                throw new ArgumentNullException("securityContext");
            }
            this.securityContext = securityContext;
            try
            {
                switch (this.securityContext.SecurityContextMode)
                {
                case SecurityContextMode.block:
                {
                    Sizes sizes = (Sizes)SSPIWrapper.QueryContextAttributes(securityContext, ContextAttribute.Sizes);
                    this.maxTokenSize            = Math.Max(sizes.cbSecurityTrailer, sizes.cbMaxSignature);
                    this.maxEncryptionBufferSize = Math.Min(sizes.cbMaxToken, 65535);
                    if (this.maxTokenSize > 65535)
                    {
                        throw new XmlaStreamException(XmlaSR.TcpStream_MaxSignatureExceedsProtocolLimit);
                    }
                    this.tokenBufferForWrite = new byte[this.maxTokenSize];
                    this.tokenBufferForRead  = new byte[this.maxTokenSize];
                    this.securityBuffers     = new SecurityBufferClass[]
                    {
                        new SecurityBufferClass(null, BufferType.Data),
                        new SecurityBufferClass(this.tokenBufferForWrite, BufferType.Token)
                    };
                    break;
                }

                case SecurityContextMode.stream:
                {
                    this.streamSizes = (StreamSizes)SSPIWrapper.QueryContextAttributes(securityContext, ContextAttribute.StreamSizes);
                    if (this.streamSizes.cbMaxMessage > 65535)
                    {
                        throw new XmlaStreamException(XmlaSR.TcpStream_MaxSignatureExceedsProtocolLimit);
                    }
                    this.streamHeaderForWrite  = new ArraySegment <byte>(new byte[this.streamSizes.cbHeader]);
                    this.streamTrailerForWrite = new ArraySegment <byte>(new byte[this.streamSizes.cbTrailer]);
                    this.streamEncryptedDataAccumulatorForRead            = new List <ArraySegment <byte> >();
                    this.streamEncryptedDataAccumulatorForReadFreeBuffers = new List <ArraySegment <byte> >();
                    this.streamDecryptedDataForRead = new List <ArraySegment <byte> >();
                    SecurityBufferClass securityBufferClass  = new SecurityBufferClass(this.streamHeaderForWrite.Array, BufferType.Header);
                    SecurityBufferClass securityBufferClass2 = new SecurityBufferClass(null, BufferType.Data);
                    SecurityBufferClass securityBufferClass3 = new SecurityBufferClass(this.streamTrailerForWrite.Array, BufferType.Trailer);
                    SecurityBufferClass securityBufferClass4 = new SecurityBufferClass(null, BufferType.Empty);
                    this.securityBuffers = new SecurityBufferClass[]
                    {
                        securityBufferClass,
                        securityBufferClass2,
                        securityBufferClass3,
                        securityBufferClass4
                    };
                    break;
                }

                default:
                    throw new XmlaStreamException("SecurityContextMode " + this.securityContext.SecurityContextMode + " not configured!");
                }
            }
            catch (XmlaStreamException)
            {
                throw;
            }
            catch (IOException innerException)
            {
                throw new XmlaStreamException(innerException);
            }
            catch (SocketException innerException2)
            {
                throw new XmlaStreamException(innerException2);
            }
            catch (Win32Exception innerException3)
            {
                throw new XmlaStreamException(innerException3);
            }
        }
        private int ReadInStreamMode(byte[] buffer, int offset, int size)
        {
            if (this.disposed)
            {
                throw new ObjectDisposedException(null);
            }
            if (buffer == null)
            {
                throw new ArgumentNullException("buffer can't be null!");
            }
            if (offset < 0)
            {
                throw new ArgumentOutOfRangeException("offset can't be negative!");
            }
            if (size < 0)
            {
                throw new ArgumentOutOfRangeException("size can't be negative!");
            }
            if (size + offset > buffer.Length)
            {
                throw new ArgumentException(XmlaSR.InvalidArgument, "buffer is smaller than offset + size!");
            }
            if (this.streamDecryptedDataForRead.Count > 0)
            {
                return(this.ReturnAvailableDecryptedData(buffer, offset, size));
            }
            this.ReleaseEncryptedDataAccumulatorForReadFreeBuffers();
            int i = 0;

            for (int j = 0; j < this.streamEncryptedDataAccumulatorForRead.Count; j++)
            {
                i += this.streamEncryptedDataAccumulatorForRead[j].Count;
            }
            bool value;

            if (i < this.streamSizes.cbMaxMessage)
            {
                ArraySegment <byte> orCreateFreeEncryptedBuffer = this.GetOrCreateFreeEncryptedBuffer(this.streamSizes.cbMaxMessage);
                int num = base.Read(orCreateFreeEncryptedBuffer.Array, orCreateFreeEncryptedBuffer.Offset, orCreateFreeEncryptedBuffer.Count);
                if (num > 0)
                {
                    orCreateFreeEncryptedBuffer = new ArraySegment <byte>(orCreateFreeEncryptedBuffer.Array, orCreateFreeEncryptedBuffer.Offset, num);
                    this.streamEncryptedDataAccumulatorForRead.Add(orCreateFreeEncryptedBuffer);
                    i += num;
                }
                else
                {
                    this.streamEncryptedDataAccumulatorForReadFreeBuffers.Add(orCreateFreeEncryptedBuffer);
                }
                value = true;
                if (TcpStream.TRACESWITCH.TraceVerbose)
                {
                    StackTrace stackTrace = new StackTrace();
                    stackTrace.GetFrame(1).GetMethod();
                }
            }
            else
            {
                value = false;
                if (TcpStream.TRACESWITCH.TraceVerbose)
                {
                    StackTrace stackTrace2 = new StackTrace();
                    stackTrace2.GetFrame(1).GetMethod();
                }
            }
            while (i > 0)
            {
                TcpEncryptedStream.CleanSecurityBuffers(this.securityBuffers);
                byte[] array;
                if (this.contiguosEncryptedByteArrayCache != null && this.contiguosEncryptedByteArrayCache.Length >= i)
                {
                    array = this.contiguosEncryptedByteArrayCache;
                }
                else
                {
                    array = (this.contiguosEncryptedByteArrayCache = new byte[i]);
                }
                int k    = 0;
                int num2 = 0;
                while (k < this.streamEncryptedDataAccumulatorForRead.Count)
                {
                    ArraySegment <byte> arraySegment = this.streamEncryptedDataAccumulatorForRead[k];
                    Array.Copy(arraySegment.Array, arraySegment.Offset, array, num2, arraySegment.Count);
                    num2 += arraySegment.Count;
                    this.streamEncryptedDataAccumulatorForReadFreeBuffers.Add(new ArraySegment <byte>(arraySegment.Array));
                    k++;
                }
                this.streamEncryptedDataAccumulatorForRead.Clear();
                this.securityBuffers[0].token  = array;
                this.securityBuffers[0].offset = 0;
                this.securityBuffers[0].size   = i;
                this.securityBuffers[0].type   = 1;
                int num3 = SSPIWrapper.DecryptMessage(ref this.securityContext.Handle, this.securityBuffers, ++this.sequenceNumberForRead);
                if (num3 == -2146893032)
                {
                    if (TcpStream.TRACESWITCH.TraceVerbose)
                    {
                        StackTrace stackTrace3 = new StackTrace();
                        stackTrace3.GetFrame(1).GetMethod();
                    }
                    this.streamEncryptedDataAccumulatorForRead.Add(new ArraySegment <byte>(array, 0, i));
                    byte[] array2 = this.contiguosEncryptedByteArrayCache = null;
                }
                else
                {
                    if (num3 != 0)
                    {
                        throw new XmlaStreamException(new StringBuilder().Append("readFromTcp=").Append(value).Append("; ").Append("encryptedDataSz=").Append(i).ToString(), new Win32Exception(num3));
                    }
                    int num4 = this.ExtractDecryptedAndExtraData(this.securityBuffers, buffer, offset, size);
                    if (num4 > 0)
                    {
                        return(num4);
                    }
                }
                ArraySegment <byte> orCreateFreeEncryptedBuffer2 = this.GetOrCreateFreeEncryptedBuffer(this.streamSizes.cbMaxMessage);
                int num5 = base.Read(orCreateFreeEncryptedBuffer2.Array, orCreateFreeEncryptedBuffer2.Offset, orCreateFreeEncryptedBuffer2.Count);
                if (num5 > 0)
                {
                    orCreateFreeEncryptedBuffer2 = new ArraySegment <byte>(orCreateFreeEncryptedBuffer2.Array, orCreateFreeEncryptedBuffer2.Offset, num5);
                    this.streamEncryptedDataAccumulatorForRead.Add(orCreateFreeEncryptedBuffer2);
                }
                else
                {
                    this.streamEncryptedDataAccumulatorForReadFreeBuffers.Add(orCreateFreeEncryptedBuffer2);
                    if (num3 == -2146893032)
                    {
                        throw new XmlaStreamException("Not complete Encrypted stream received from underlying layer of type " + base.GetType().Name + "! DecryptMessage returned SEC_E_INCOMPLETE_MESSAGE while underlying stream reported all data was read.");
                    }
                }
                i = 0;
                for (int l = 0; l < this.streamEncryptedDataAccumulatorForRead.Count; l++)
                {
                    i += this.streamEncryptedDataAccumulatorForRead[l].Count;
                }
                if (TcpStream.TRACESWITCH.TraceVerbose)
                {
                    StackTrace stackTrace4 = new StackTrace();
                    stackTrace4.GetFrame(1).GetMethod();
                }
            }
            return(0);
        }