Пример #1
0
        public IAsyncResult BeginReceiveRecord(Stream record, AsyncCallback callback, object state)
        {
            if (context.ReceivedConnectionEnd)
            {
                throw new TlsException(AlertDescription.InternalError, "The session is finished and it's no longer valid.");
            }
            record_processing.Reset();
            byte[] initialBuffer = new byte[1];
            ReceiveRecordAsyncResult receiveRecordAsyncResult = new ReceiveRecordAsyncResult(callback, state, initialBuffer, record);

            record.BeginRead(receiveRecordAsyncResult.InitialBuffer, 0, receiveRecordAsyncResult.InitialBuffer.Length, InternalReceiveRecordCallback, receiveRecordAsyncResult);
            return(receiveRecordAsyncResult);
        }
Пример #2
0
        public byte[] EndReceiveRecord(IAsyncResult asyncResult)
        {
            ReceiveRecordAsyncResult receiveRecordAsyncResult = asyncResult as ReceiveRecordAsyncResult;

            if (receiveRecordAsyncResult == null)
            {
                throw new ArgumentException("Either the provided async result is null or was not created by this RecordProtocol.");
            }
            if (!receiveRecordAsyncResult.IsCompleted)
            {
                receiveRecordAsyncResult.AsyncWaitHandle.WaitOne();
            }
            if (receiveRecordAsyncResult.CompletedWithError)
            {
                throw receiveRecordAsyncResult.AsyncException;
            }
            byte[] resultingBuffer = receiveRecordAsyncResult.ResultingBuffer;
            record_processing.Set();
            return(resultingBuffer);
        }
		public IAsyncResult BeginReceiveRecord(Stream record, AsyncCallback callback, object state)
		{
			if (this.context.ConnectionEnd)
			{
				throw new TlsException(
					AlertDescription.InternalError,
					"The session is finished and it's no longer valid.");
			}

			record_processing.Reset ();
			byte[] recordTypeBuffer = new byte[1];

			ReceiveRecordAsyncResult internalResult = new ReceiveRecordAsyncResult(callback, state, recordTypeBuffer, record);

			record.BeginRead(internalResult.InitialBuffer, 0, internalResult.InitialBuffer.Length, new AsyncCallback(InternalReceiveRecordCallback), internalResult);

			return internalResult;
		}
Пример #4
0
        private void InternalReceiveRecordCallback(IAsyncResult asyncResult)
        {
            ReceiveRecordAsyncResult internalResult = asyncResult.AsyncState as ReceiveRecordAsyncResult;
            Stream record = internalResult.Record;

            try
            {
                int bytesRead = internalResult.Record.EndRead(asyncResult);

                //We're at the end of the stream. Time to bail.
                if (bytesRead == 0)
                {
                    internalResult.SetComplete((byte[])null);
                    return;
                }

                // Try to read the Record Content Type
                int type = internalResult.InitialBuffer[0];

                // Set last handshake message received to None
                this.context.LastHandshakeMsg = HandshakeType.ClientHello;

                ContentType contentType = (ContentType)type;
                byte[]      buffer      = this.ReadRecordBuffer(type, record);
                if (buffer == null)
                {
                    // record incomplete (at the moment)
                    internalResult.SetComplete((byte[])null);
                    return;
                }

                // Decrypt message contents if needed
                if (contentType == ContentType.Alert && buffer.Length == 2)
                {
                }
                else if ((this.Context.Read != null) && (this.Context.Read.Cipher != null))
                {
                    buffer = this.decryptRecordFragment(contentType, buffer);
                    DebugHelper.WriteLine("Decrypted record data", buffer);
                }

                // Process record
                switch (contentType)
                {
                case ContentType.Alert:
                    this.ProcessAlert((AlertLevel)buffer [0], (AlertDescription)buffer [1]);
                    if (record.CanSeek)
                    {
                        // don't reprocess that memory block
                        record.SetLength(0);
                    }
                    buffer = null;
                    break;

                case ContentType.ChangeCipherSpec:
                    this.ProcessChangeCipherSpec();
                    break;

                case ContentType.ApplicationData:
                    break;

                case ContentType.Handshake:
                    TlsStream message = new TlsStream(buffer);
                    while (!message.EOF)
                    {
                        this.ProcessHandshakeMessage(message);
                    }
                    break;

                case (ContentType)0x80:
                    this.context.HandshakeMessages.Write(buffer);
                    break;

                default:
                    throw new TlsException(
                              AlertDescription.UnexpectedMessage,
                              "Unknown record received from server.");
                }

                internalResult.SetComplete(buffer);
            }
            catch (Exception ex)
            {
                internalResult.SetComplete(ex);
            }
        }
Пример #5
0
        private void InternalReceiveRecordCallback(IAsyncResult asyncResult)
        {
            ReceiveRecordAsyncResult receiveRecordAsyncResult = asyncResult.AsyncState as ReceiveRecordAsyncResult;
            Stream record = receiveRecordAsyncResult.Record;

            try
            {
                if (receiveRecordAsyncResult.Record.EndRead(asyncResult) == 0)
                {
                    receiveRecordAsyncResult.SetComplete((byte[])null);
                }
                else
                {
                    int num = receiveRecordAsyncResult.InitialBuffer[0];
                    context.LastHandshakeMsg = HandshakeType.ClientHello;
                    ContentType contentType = (ContentType)num;
                    byte[]      array       = ReadRecordBuffer(num, record);
                    if (array == null)
                    {
                        receiveRecordAsyncResult.SetComplete((byte[])null);
                    }
                    else
                    {
                        if ((contentType != ContentType.Alert || array.Length != 2) && Context.Read != null && Context.Read.Cipher != null)
                        {
                            array = decryptRecordFragment(contentType, array);
                        }
                        switch (contentType)
                        {
                        case ContentType.Alert:
                            ProcessAlert((AlertLevel)array[0], (AlertDescription)array[1]);
                            if (record.CanSeek)
                            {
                                record.SetLength(0L);
                            }
                            array = null;
                            break;

                        case ContentType.ChangeCipherSpec:
                            ProcessChangeCipherSpec();
                            break;

                        case ContentType.Handshake:
                        {
                            TlsStream tlsStream = new TlsStream(array);
                            while (!tlsStream.EOF)
                            {
                                ProcessHandshakeMessage(tlsStream);
                            }
                            break;
                        }

                        case (ContentType)128:
                            context.HandshakeMessages.Write(array);
                            break;

                        default:
                            throw new TlsException(AlertDescription.UnexpectedMessage, "Unknown record received from server.");

                        case ContentType.ApplicationData:
                            break;
                        }
                        receiveRecordAsyncResult.SetComplete(array);
                    }
                }
            }
            catch (Exception complete)
            {
                receiveRecordAsyncResult.SetComplete(complete);
            }
        }