public static PRUdpPacket Decode(byte[] bytes)
        {
            var    hex = bytes.ToHex();
            var    str = hex.Substring(4, 2);
            string sessionid = "", sig = "", seqnum = "", connsig = "", fragid = "", payload = "";
            var    typenflags = str.FromHexToBits();
            var    checksum   = hex.Substring(hex.Length - 8);

            int[] data = new int[typenflags.Count];
            for (int i = 0; i < typenflags.Count; i++)
            {
                if ((bool)typenflags[i])
                {
                    data[i] = 1;
                }
                else
                {
                    data[i] = 0;
                }
            }
            var flags  = Convert.ToString(data[0]) + Convert.ToString(data[1]) + Convert.ToString(data[2]) + Convert.ToString(data[3]) + Convert.ToString(data[4]);
            var type   = Convert.ToString(data[5]) + Convert.ToString(data[6]) + Convert.ToString(data[7]);
            var packet = new PRUdpPacket();

            packet.Type  = (PacketTypes)Convert.ToInt32(type, 2);
            packet.Flags = PFlags.ParseFlags(flags);
            if (packet.Type == PacketTypes.SYN || packet.Type == PacketTypes.CONNECT)
            {
                sessionid = hex.Substring(6, 2);
                sig       = hex.Substring(8, 8);
                seqnum    = hex.Substring(16, 4);
                connsig   = hex.Substring(20, 8);

                /*var f = connsig.Substring(0, 2);
                 * var ff = connsig.Substring(2, 2);
                 * var fff = connsig.Substring(4, 2);
                 * var ffff = connsig.Substring(6, 2);
                 * connsig = ffff + fff + ff + f;*/
            }
            else if (packet.Type == PacketTypes.DATA)
            {
                sessionid         = hex.Substring(6, 2);
                sig               = hex.Substring(8, 8);
                seqnum            = hex.Substring(16, 4);
                fragid            = hex.Substring(20, 2);
                payload           = PythonScript.DecompressPacketPayload(RC4.Decrypt(Encoding.ASCII.GetBytes("CD&ML"), hex.Substring(22, hex.Length - 30).FromHex()).ToHex().Substring(2)).Result;
                packet.RMCPayload = RMCPayload.Decode(payload);
            }
            else
            {
                sessionid = hex.Substring(6, 2);
                seqnum    = hex.Substring(8, 4);
            }
            packet.SessionId           = sessionid;
            packet.Signature           = sig;
            packet.Checksum            = checksum;
            packet.ConnectionSignature = connsig;
            packet.Payload             = payload;
            return(packet);
        }
        private void Handle(byte[] data, IPEndPoint endpoint)
        {
            var hex = data.ToHex();

            Console.WriteLine("Received: " + hex);
            if (hex.Equals("3f3120000000000000000000000034322000"))
            {
                //var packet = PRUdpPacket.Decode(data);
                var resp = "313f08000000000000000f8744db6a1b1887";
                //var packet1 = PRUdpPacket.Decode(resp.FromHex());
                Send(resp.FromHex(), endpoint);
            }
            else
            {
                var packet = PRUdpPacket.Decode(data);
                if (packet.Type == PacketTypes.PING)
                {
                    //todo, ping handling code
                }
                else if (packet.Type == PacketTypes.CONNECT)
                {
                    var response = new PRUdpPacket()
                    {
                        Flags               = new PacketFlags[] { PacketFlags.FLAG_ACK },
                        Type                = PacketTypes.CONNECT,
                        SessionId           = packet.SessionId,
                        Signature           = packet.Signature,
                        ConnectionSignature = packet.ConnectionSignature
                    };
                    var p = response.Encode();
                    Console.WriteLine("Sent: " + p.ToHex());
                    Send(p, endpoint);
                }
                else if (packet.Type == PacketTypes.DATA)
                {
                    var rvconndata = new RVConnectionData()
                    {
                        StationUrl = "prudps:/127.0.0.1:10264"
                    };
                    var rmc = new RMCPayload()
                    {
                        CallId     = packet.RMCPayload.CallId,
                        MethodId   = packet.RMCPayload.MethodId,
                        ProtocolId = packet.RMCPayload.ProtocolId,
                        Payload    = rvconndata.Encode()
                    };
                    var response = new PRUdpPacket()
                    {
                        Flags               = new PacketFlags[] { PacketFlags.FLAG_ACK, PacketFlags.FLAG_NEED_ACK },
                        Type                = PacketTypes.DATA,
                        SessionId           = packet.SessionId,
                        Signature           = packet.Signature,
                        Payload             = rmc.Encode(),
                        ConnectionSignature = packet.ConnectionSignature
                    };
                    var p = response.Encode().ToHex();
                    Console.WriteLine("Sent: " + p);
                    Send(p.FromHex(), endpoint);
                }
                else
                {
                    Console.WriteLine("Unknown packet: " + hex);
                }
            }
        }