Пример #1
0
        private static void RunAsClient()
        {
            GonzoNet.PacketHandlers.Register(0x02, false, 0, new OnPacketReceive(PacketHandlers.HandleServerChallenge));
            //GonzoNet requires a log output stream to function correctly. This is built in behavior.
            GonzoNet.Logger.OnMessageLogged += new MessageLoggedDelegate(Logger_OnMessageLogged);

            StaticStaticDiffieHellman.ExportKey("ClientPublic.dat", PacketHandlers.ClientKey.PublicKey);

            m_Client              = new NetworkClient("127.0.0.1", 12345);
            m_Client.OnConnected += new OnConnectedDelegate(m_Client_OnConnected);

            LoginArgsContainer LoginArgs = new LoginArgsContainer();

            LoginArgs.Enc      = new GonzoNet.Encryption.ARC4Encryptor("test");
            LoginArgs.Username = "******";
            LoginArgs.Password = "******";
            LoginArgs.Client   = m_Client;

            PacketHandlers.GenerateClientIV();

            m_Client.Connect(LoginArgs);

            while (true)
            {
                Thread.Sleep(1000);
            }
        }
Пример #2
0
        /// <summary>
        /// A client requested login.
        /// </summary>
        /// <param name="Client">NetworkClient instance.</param>
        /// <param name="Packet">ProcessedPacket instance.</param>
        public static void InitialClientConnect(NetworkClient Client, ProcessedPacket Packet)
        {
            Console.WriteLine("Server receives data - test 1");

            PacketStream EncryptedPacket = new PacketStream(0x02, 0);

            EncryptedPacket.WriteHeader();

            ClientPublicKey = Packet.ReadBytes((Packet.ReadByte()));

            AESEncryptor Enc = (AESEncryptor)Client.ClientEncryptor;

            Enc.NOnce              = Packet.ReadBytes((Packet.ReadByte()));
            Enc.PublicKey          = ClientPublicKey;
            Enc.PrivateKey         = ServerPrivateKey;
            Client.ClientEncryptor = Enc;

            //THIS IS IMPORTANT - public key must be derived from private!
            ServerPublicKey = ServerPrivateKey.PublicKey.ToByteArray();

            ChallengeResponse = new byte[16];
            m_Random.GetNonZeroBytes(ChallengeResponse);

            MemoryStream StreamToEncrypt = new MemoryStream();
            BinaryWriter Writer          = new BinaryWriter(StreamToEncrypt);

            Writer.Write(ChallengeResponse, 0, ChallengeResponse.Length);
            Writer.Flush();

            byte[] EncryptedData = StaticStaticDiffieHellman.Encrypt(ServerPrivateKey,
                                                                     ECDiffieHellmanCngPublicKey.FromByteArray(ClientPublicKey, CngKeyBlobFormat.EccPublicBlob), Enc.NOnce,
                                                                     StreamToEncrypt.ToArray());

            EncryptedPacket.WriteUInt16((ushort)(PacketHeaders.UNENCRYPTED +
                                                 (1 + ServerPublicKey.Length) +
                                                 (1 + EncryptedData.Length)));

            EncryptedPacket.WriteByte((byte)ServerPublicKey.Length);
            EncryptedPacket.WriteBytes(ServerPublicKey);
            EncryptedPacket.WriteByte((byte)EncryptedData.Length);
            EncryptedPacket.WriteBytes(EncryptedData);

            Client.Send(EncryptedPacket.ToArray());

            NetworkFacade.Listener.UpdateClient(Client);

            Console.WriteLine("Test 1: passed!");
        }
Пример #3
0
        private static void RunAsServer()
        {
            GonzoNet.PacketHandlers.Register(0x01, false, 0, new OnPacketReceive(PacketHandlers.InitialClientConnect));
            GonzoNet.PacketHandlers.Register(0x03, false, 0, new OnPacketReceive(PacketHandlers.HandleChallengeResponse));
            //GonzoNet requires a log output stream to function correctly. This is built in behavior.
            GonzoNet.Logger.OnMessageLogged += new MessageLoggedDelegate(Logger_OnMessageLogged);

            StaticStaticDiffieHellman.ExportKey("ServerPublic.dat", PacketHandlers.ClientKey.PublicKey);

            m_Listener.Initialize(new IPEndPoint(IPAddress.Parse("127.0.0.1"), 12345));

            while (true)
            {
                Thread.Sleep(1000);
            }
        }
Пример #4
0
        /// <summary>
        /// A client requested login.
        /// </summary>
        /// <param name="Client">NetworkClient instance.</param>
        /// <param name="Packet">ProcessedPacket instance.</param>
        public static void InitialClientConnect(NetworkClient Client, ProcessedPacket Packet)
        {
            Console.WriteLine("Server receives data - test 1");

            //AES is used to encrypt all further communication between client and server.
            AesCryptoServiceProvider AesCrypto = new AesCryptoServiceProvider();

            AesCrypto.GenerateKey();
            AesCrypto.GenerateIV();
            AES AesEncryptor = new AES(AesCrypto.Key, AesCrypto.IV);

            SessionKey = AesCrypto.Key;
            IV         = AesCrypto.IV;

            Guid Nonce = new Guid(Packet.ReadPascalString());

            //Username would normally be used to lookup client's public key in DB (only time such a use is valid).
            string Username = Packet.ReadPascalString();
            ECDiffieHellmanPublicKey ClientPub = StaticStaticDiffieHellman.ImportKey("ClientPublic.dat");

            PacketStream EncryptedPacket = new PacketStream(0x02, 0);

            EncryptedPacket.WriteHeader();

            MemoryStream StreamToEncrypt = new MemoryStream();
            BinaryWriter Writer          = new BinaryWriter(StreamToEncrypt);

            Writer.Write((byte)ChallengeResponse.ToByteArray().Length);
            Writer.Write(ChallengeResponse.ToByteArray(), 0, ChallengeResponse.ToByteArray().Length);
            Writer.Write((byte)SessionKey.Length);
            Writer.Write(SessionKey, 0, SessionKey.Length);
            Writer.Write((byte)IV.Length);
            Writer.Write(IV, 0, IV.Length);
            Writer.Flush();

            byte[] EncryptedData = StaticStaticDiffieHellman.Encrypt(ServerKey, ClientPub, Nonce.ToByteArray(),
                                                                     StreamToEncrypt.ToArray());

            EncryptedPacket.WriteUInt16((ushort)(PacketHeaders.UNENCRYPTED + 1 + EncryptedData.Length));

            EncryptedPacket.WriteByte((byte)EncryptedData.Length);
            EncryptedPacket.Write(EncryptedData, 0, EncryptedData.Length);

            Client.Send(EncryptedPacket.ToArray());

            Console.WriteLine("Test 1: passed!");
        }
Пример #5
0
        /// <summary>
        /// Initial response from server to client.
        /// </summary>
        /// <param name="Client">A NetworkClient instance.</param>
        /// <param name="Packet">A ProcessedPacket instance.</param>
        public static void HandleServerChallenge(NetworkClient Client, ProcessedPacket Packet)
        {
            Console.WriteLine("Client receives encrypted data - test 2");

            byte[] PacketBuf = new byte[Packet.ReadByte()];
            Packet.Read(PacketBuf, 0, (int)PacketBuf.Length);

            ECDiffieHellmanPublicKey ServerPub = StaticStaticDiffieHellman.ImportKey("ServerPublic.dat");

            MemoryStream DecryptedStream = new MemoryStream(StaticStaticDiffieHellman.Decrypt(ClientKey, ServerPub,
                                                                                              ClientNOnce.ToByteArray(), PacketBuf));
            BinaryReader Reader = new BinaryReader(DecryptedStream);

            Guid ChallengeResponse = new Guid(Reader.ReadBytes(Reader.ReadByte()));

            SessionKey = Reader.ReadBytes(Reader.ReadByte());
            IV         = Reader.ReadBytes(Reader.ReadByte());

            //Yay, we have key and IV, we can now start encryption with AES!
            AES AesEncryptor = new AES(SessionKey, IV);

            PacketStream EncryptedPacket = new PacketStream(0x03, 0);

            EncryptedPacket.WriteHeader();

            MemoryStream StreamToEncrypt = new MemoryStream();
            BinaryWriter Writer          = new BinaryWriter(StreamToEncrypt);

            Writer.Write((byte)ChallengeResponse.ToByteArray().Length);
            Writer.Write(ChallengeResponse.ToByteArray(), 0, ChallengeResponse.ToByteArray().Length);

            //Encrypt data using key and IV from server, hoping that it'll be decrypted correctly at the other end...
            byte[] EncryptedData = AesEncryptor.Encrypt(StreamToEncrypt.ToArray());

            EncryptedPacket.WriteUInt16((ushort)(PacketHeaders.UNENCRYPTED + EncryptedData.Length + 1));
            EncryptedPacket.WriteByte((byte)EncryptedData.Length);
            EncryptedPacket.Write(EncryptedData, 0, EncryptedData.Length);

            Client.Send(EncryptedPacket.ToArray());

            Console.WriteLine("Test 2: passed!");
        }
Пример #6
0
        /// <summary>
        /// Initial response from server to client.
        /// </summary>
        /// <param name="Client">A NetworkClient instance.</param>
        /// <param name="Packet">A ProcessedPacket instance.</param>
        public static void HandleServerChallenge(NetworkClient Client, ProcessedPacket Packet)
        {
            Console.WriteLine("Client receives encrypted data - test 2");

            ServerPublicKey = Packet.ReadBytes(Packet.ReadByte());
            byte[] EncryptedData = Packet.ReadBytes(Packet.ReadByte());

            AESEncryptor Enc = (AESEncryptor)Client.ClientEncryptor;

            Enc.PublicKey          = ServerPublicKey;
            Client.ClientEncryptor = Enc;
            NetworkFacade.Client.ClientEncryptor = Enc;

            ECDiffieHellmanCng PrivateKey = Client.ClientEncryptor.GetDecryptionArgsContainer().AESDecryptArgs.PrivateKey;

            byte[] NOnce = Client.ClientEncryptor.GetDecryptionArgsContainer().AESDecryptArgs.NOnce;

            byte[] ChallengeResponse = StaticStaticDiffieHellman.Decrypt(PrivateKey,
                                                                         ECDiffieHellmanCngPublicKey.FromByteArray(ServerPublicKey, CngKeyBlobFormat.EccPublicBlob),
                                                                         NOnce, EncryptedData);

            MemoryStream StreamToEncrypt = new MemoryStream();
            BinaryWriter Writer          = new BinaryWriter(StreamToEncrypt);

            Writer.Write((byte)ChallengeResponse.Length);
            Writer.Write(ChallengeResponse, 0, ChallengeResponse.Length);

            Writer.Write(Client.ClientEncryptor.Username);
            Writer.Write((byte)PasswordHash.Length);
            Writer.Write(PasswordHash);
            Writer.Flush();

            Client.SendEncrypted(0x03, StreamToEncrypt.ToArray());

            Console.WriteLine("Test 2: passed!");
        }