示例#1
0
        private void Constructor(string sendingPacketTypeStr, string requestReturnPacketTypeStr, object packetObject, SendReceiveOptions options)
        {
            if (sendingPacketTypeStr == null || sendingPacketTypeStr == "")
            {
                throw new ArgumentNullException("sendingPacketTypeStr", "The provided string can not be null or zero length.");
            }
            if (options == null)
            {
                throw new ArgumentNullException("options", "The provided SendReceiveOptions cannot be null.");
            }

            if (packetObject == null)
            {
                this.packetData = new StreamSendWrapper(new ThreadSafeStream(new MemoryStream(new byte[0], 0, 0, false, true), true));
            }
            else
            {
                if (options.DataSerializer == null)
                {
                    throw new ArgumentNullException("options", "The provided SendReceiveOptions.DataSerializer cannot be null.");
                }
                this.packetData = options.DataSerializer.SerialiseDataObject(packetObject, options.DataProcessors, options.Options);
            }

            //We only calculate the checkSum if we are going to use it
            string hashStr = null;

            if (NetworkComms.EnablePacketCheckSumValidation)
            {
                hashStr = NetworkComms.MD5Bytes(packetData.ThreadSafeStream.ToArray(packetData.Start, packetData.Length));
            }

            this.packetHeader = new PacketHeader(sendingPacketTypeStr, packetData.Length, requestReturnPacketTypeStr,
                                                 options.Options.ContainsKey("ReceiveConfirmationRequired"),
                                                 hashStr,
                                                 options.Options.ContainsKey("IncludePacketConstructionTime"));

            //Add an identifier specifying the serializers and processors we have used
            this.packetHeader.SetOption(PacketHeaderLongItems.SerializerProcessors, DPSManager.CreateSerializerDataProcessorIdentifier(options.DataSerializer, options.DataProcessors));

            if (NetworkComms.LoggingEnabled)
            {
                NetworkComms.Logger.Trace(" ... creating comms packet. PacketObject data size is " + packetData.Length.ToString() + " bytes");
            }
        }
示例#2
0
        private void Constructor <payloadObjectType>(string sendingPacketTypeStr, string requestReturnPacketTypeStr, payloadObjectType payloadObject, SendReceiveOptions options, bool isNested)
        {
            if (sendingPacketTypeStr == null || sendingPacketTypeStr == "")
            {
                throw new ArgumentNullException("sendingPacketTypeStr", "The provided string can not be null or zero length.");
            }
            if (options == null)
            {
                throw new ArgumentNullException("options", "The provided SendReceiveOptions cannot be null.");
            }
            if (options.DataSerializer == null)
            {
                throw new ArgumentNullException("options", "The provided SendReceiveOptions.DataSerializer cannot be null. Consider using NullSerializer instead.");
            }

            //Check for security critical data processors
            //There may be performance issues here
            bool containsSecurityCritialDataProcessors = false;

            if (!options.Options.ContainsKey("UseNestedPacketType") && //We only need to perform this check if we are not already using a nested packet
                !isNested)                                             //We do not perform this check within a nested packet
            {
                foreach (DataProcessor processor in options.DataProcessors)
                {
                    if (processor.IsSecurityCritical)
                    {
                        containsSecurityCritialDataProcessors = true;
                        break;
                    }
                }
            }

            //By default the object to serialise will be the payloadObject
            object objectToSerialise       = payloadObject;
            bool   objectToSerialiseIsNull = false;

            //We only replace the null with an empty stream if this is either in the nested packet
            //or we will not be nesting
            if (objectToSerialise == null &&
                ((!options.Options.ContainsKey("UseNestedPacketType") &&
                  !containsSecurityCritialDataProcessors) || isNested))
            {
#if NETFX_CORE
                var emptyStream = new MemoryStream(new byte[0], 0, 0, false);
#else
                var emptyStream = new MemoryStream(new byte[0], 0, 0, false, true);
#endif
                //If the sending object is null we set objectToSerialiseIsNull and create a zero length StreamSendWrapper
                //The zero length StreamSendWrapper can then be passed to any data serializers
                objectToSerialiseIsNull = true;
                objectToSerialise       = new StreamTools.StreamSendWrapper(new StreamTools.ThreadSafeStream(emptyStream, true));
            }

            //If we need to nest this packet
            if ((containsSecurityCritialDataProcessors || options.Options.ContainsKey("UseNestedPacketType")) && !isNested)
            {
                //We set the objectToSerialise to a nested packet
                objectToSerialise = new Packet(sendingPacketTypeStr, requestReturnPacketTypeStr, payloadObject, options, true);
            }
            else if (isNested)
            {
                //Serialise the payload object into byte[]
                //We do not use any data processors at this stage as the object will be processed again one level higher.
#if NETFX_CORE
                _payloadObjectBytes = options.DataSerializer.SerialiseDataObject(payloadObject).ThreadSafeStream.ToArray();
                _payloadSize        = _payloadObjectBytes.Length;
#else
                NetworkCommsDotNet.Tools.StreamTools.ThreadSafeStream tempStream = options.DataSerializer.SerialiseDataObject(objectToSerialise).ThreadSafeStream;
                _payloadObjectBytes = tempStream.GetBuffer();
                _payloadSize        = (int)tempStream.Length;
#endif
                //Set the packet header
                //THe nulls represent internal SendReceiveOptions and no checksum
                this._packetHeader = new PacketHeader(sendingPacketTypeStr, _payloadSize, null, requestReturnPacketTypeStr, null);

                //Set the deserialiser information in the nested packet header, excluding data processors
                this._packetHeader.SetOption(PacketHeaderLongItems.SerializerProcessors, DPSManager.CreateSerializerDataProcessorIdentifier(options.DataSerializer, null));
            }

            //If we are at the top level packet we can finish off the serialisation
            if (!isNested)
            {
                //Set the payload stream data.
                if (objectToSerialiseIsNull && options.DataProcessors.Count == 0)
                {
                    //Only if there are no data processors can we use a zero length array for nulls
                    //This ensures that should there be any required padding we can include it
                    this.payloadStream = (StreamTools.StreamSendWrapper)objectToSerialise;
                }
                else
                {
                    if (objectToSerialise is Packet)
                    {
                        //We have to use the internal explicit serializer for nested packets (the nested data is already byte[])
                        this.payloadStream = NetworkComms.InternalFixedSendReceiveOptions.DataSerializer.SerialiseDataObject(objectToSerialise, options.DataProcessors, options.Options);
                    }
                    else
                    {
                        this.payloadStream = options.DataSerializer.SerialiseDataObject(objectToSerialise, options.DataProcessors, options.Options);
                    }
                }

                //We only calculate the checkSum if we are going to use it
                string hashStr = null;
                if (NetworkComms.EnablePacketCheckSumValidation)
                {
                    hashStr = StreamTools.MD5(payloadStream.ThreadSafeStream.ToArray(payloadStream.Start, payloadStream.Length));
                }

                //Choose the sending and receiving packet type depending on if it is being used with a nested packet
                string _sendingPacketTypeStr;
                string _requestReturnPacketTypeStr = null;
                if (containsSecurityCritialDataProcessors || options.Options.ContainsKey("UseNestedPacketType"))
                {
                    _sendingPacketTypeStr = Enum.GetName(typeof(ReservedPacketType), ReservedPacketType.NestedPacket);
                }
                else
                {
                    _sendingPacketTypeStr       = sendingPacketTypeStr;
                    _requestReturnPacketTypeStr = requestReturnPacketTypeStr;
                }

                this._packetHeader = new PacketHeader(_sendingPacketTypeStr, payloadStream.Length, options, _requestReturnPacketTypeStr, hashStr);

                //Add an identifier specifying the serialisers and processors we have used
                if (objectToSerialise is Packet)
                {
                    this._packetHeader.SetOption(PacketHeaderLongItems.SerializerProcessors, DPSManager.CreateSerializerDataProcessorIdentifier(NetworkComms.InternalFixedSendReceiveOptions.DataSerializer, options.DataProcessors));
                }
                else
                {
                    this._packetHeader.SetOption(PacketHeaderLongItems.SerializerProcessors, DPSManager.CreateSerializerDataProcessorIdentifier(options.DataSerializer, options.DataProcessors));
                }
            }

            //Set the null data header section if required
            if (objectToSerialiseIsNull &&
                ((!containsSecurityCritialDataProcessors && !options.Options.ContainsKey("UseNestedPacketType")) || isNested))
            {
                this._packetHeader.SetOption(PacketHeaderStringItems.NullDataSection, "");
            }

            if (NetworkComms.LoggingEnabled)
            {
                if (isNested)
                {
                    NetworkComms.Logger.Trace(" ... created nested packet of type " + sendingPacketTypeStr);
                }
                else
                {
                    NetworkComms.Logger.Trace(" ... created packet of type " + sendingPacketTypeStr + ". PacketObject data size is " + payloadStream.Length.ToString() + " bytes");
                }
            }
        }