]> git.deb.at Git - rhonda/impostor.hazel.git/commitdiff
Make disconnect send synchronous so it's more likely to actually send
authorForest <chocozilla@gmail.com>
Thu, 9 Aug 2018 18:29:04 +0000 (11:29 -0700)
committerForest <chocozilla@gmail.com>
Thu, 9 Aug 2018 18:29:04 +0000 (11:29 -0700)
Hazel/Connection.cs
Hazel/NetworkConnection.cs
Hazel/Udp/UdpClientConnection.cs
Hazel/Udp/UdpConnection.cs
Hazel/Udp/UdpConnectionListener.cs
Hazel/Udp/UdpServerConnection.cs

index 5b59197f20cf4b823e7215655d69e86a14a4da7e..05f451303783731557fb13b6b3b1ce09f60c6c3b 100644 (file)
@@ -225,7 +225,12 @@ namespace Hazel
         ///     <see cref="HazelException"/> if there is a problem connecting.
         /// </remarks>
         public abstract void ConnectAsync(byte[] bytes = null, int timeout = 5000);
-        
+
+        /// <summary>
+        ///     Sends a disconnect message to the end point.
+        /// </summary>
+        public abstract void SendDisconnect();
+
         /// <summary>
         ///     Invokes the DataReceived event.
         /// </summary>
index 7aef3e4f96e17bff4dc6d14b48ecce6b93bda38e..21f2f45b3568b1136b6579100bb0e8cd1439d6cf 100644 (file)
@@ -26,5 +26,10 @@ namespace Hazel
         ///     The <see cref="IPMode">IPMode</see> the client is connected using.
         /// </summary>
         public IPMode IPMode { get; protected set; }
+
+        public long GetIP4Address()
+        {
+            return ((IPEndPoint)this.RemoteEndPoint).Address.Address;
+        }
     }
 }
index 89f408cab9ccf762c7dc21abd4a8d93a06423279..32fa7c3b7e827b4c51b3938f3a1506c710138564 100644 (file)
@@ -109,6 +109,40 @@ namespace Hazel.Udp
             }
         }
 
+        /// <inheritdoc />
+        protected override void WriteBytesToConnectionSync(byte[] bytes, int length)
+        {
+            InvokeDataSentRaw(bytes, length);
+
+            lock (stateLock)
+            {
+                if (State != ConnectionState.Connected && State != ConnectionState.Connecting)
+                    throw new InvalidOperationException("Could not send data as this Connection is not connected and is not connecting. Did you disconnect?");
+            }
+
+            try
+            {
+                socket.SendTo(
+                    bytes,
+                    0,
+                    length,
+                    SocketFlags.None,
+                    RemoteEndPoint
+                );
+            }
+            catch (ObjectDisposedException)
+            {
+                //User probably called Disconnect in between this method starting and here so report the issue
+                throw new InvalidOperationException("Could not send data as this Connection is not connected. Did you disconnect?");
+            }
+            catch (SocketException e)
+            {
+                HazelException he = new HazelException("Could not send data as a SocketException occured.", e);
+                HandleDisconnect(he);
+                throw he;
+            }
+        }
+
         /// <inheritdoc />
         public override void Connect(byte[] bytes = null, int timeout = 5000)
         {
index f705bffb11bee9e16c87ed9e1b98b5165c5ac02a..d18c03e7669743cfb092b90bc8fe43650b80c8f7 100644 (file)
@@ -29,6 +29,12 @@ namespace Hazel.Udp
         /// <param name="bytes">The bytes to write.</param>
         protected abstract void WriteBytesToConnection(byte[] bytes, int length);
 
+        /// <summary>
+        ///     Writes the given bytes to the connection synchronously.
+        /// </summary>
+        /// <param name="bytes">The bytes to write.</param>
+        protected abstract void WriteBytesToConnectionSync(byte[] bytes, int length);
+
         /// <inheritdoc/>
         public override void Send(MessageWriter msg)
         {
@@ -282,9 +288,9 @@ namespace Hazel.Udp
         /// <summary>
         ///     Sends a disconnect message to the end point.
         /// </summary>
-        protected void SendDisconnect()
+        public override void SendDisconnect()
         {
-            HandleSend(new byte[0], (byte)UdpSendOption.Disconnect);       //TODO Should disconnect wait for an ack?
+            WriteBytesToConnectionSync(new byte[] { (byte)UdpSendOption.Disconnect }, 1);
         }
 
         /// <inheritdoc/>
index e1cacd6f17ccea581ab15c22fb9585975ee3ddbe..26d95eea3d612b10af5c98d4d141744935cfcf20 100644 (file)
@@ -216,6 +216,34 @@ namespace Hazel.Udp
             }
         }
 
+        /// <summary>
+        ///     Sends data from the listener socket.
+        /// </summary>
+        /// <param name="bytes">The bytes to send.</param>
+        /// <param name="endPoint">The endpoint to send to.</param>
+        internal void SendDataSync(byte[] bytes, int length, EndPoint endPoint)
+        {
+            try
+            {
+                listener.SendTo(
+                    bytes,
+                    0,
+                    length,
+                    SocketFlags.None,
+                    endPoint
+                );
+            }
+            catch (SocketException e)
+            {
+                throw new HazelException("Could not send data as a SocketException occured.", e);
+            }
+            catch (ObjectDisposedException)
+            {
+                //Keep alive timer probably ran, ignore
+                return;
+            }
+        }
+
         /// <summary>
         ///     Removes a virtual connection from the list.
         /// </summary>
index 3bfae30a4502c1ec93e3c8e043d4853ce4c63eed..85b6e22b67c3a4e36c1d4b5cbdaaa43993b4798e 100644 (file)
@@ -58,6 +58,20 @@ namespace Hazel.Udp
             Listener.SendData(bytes, length, RemoteEndPoint);
         }
 
+        /// <inheritdoc />
+        protected override void WriteBytesToConnectionSync(byte[] bytes, int length)
+        {
+            InvokeDataSentRaw(bytes, length);
+
+            lock (stateLock)
+            {
+                if (State != ConnectionState.Connected)
+                    throw new InvalidOperationException("Could not send data as this Connection is not connected. Did you disconnect?");
+            }
+
+            Listener.SendDataSync(bytes, length, RemoteEndPoint);
+        }
+
         /// <inheritdoc />
         /// <remarks>
         ///     This will always throw a HazelException.