Netduino home hardware projects downloads community

Jump to content


The Netduino forums have been replaced by new forums at community.wildernesslabs.co. This site has been preserved for archival purposes only and the ability to make new accounts or posts has been turned off.
Photo

Waiting for a network connection


  • Please log in to reply
2 replies to this topic

#1 ukkiwisurfer

ukkiwisurfer

    Advanced Member

  • Members
  • PipPipPip
  • 32 posts
  • LocationLondon

Posted 16 October 2015 - 11:43 AM

Following on from Chris' comments about waiting for a network connection on the Wifi version of the Netduino 3, I've written a Network helper class to use for both the Ethernet and Wifi boards:

 

 public NetworkInformation GetNetworkDetails(int interfaceIndex)
 {
     NetworkInformation information = null;
 
     NetworkChange.NetworkAvailabilityChanged += OnNetworkAvailabilityChanged;
     NetworkChange.NetworkAddressChanged += OnNetworkAddressChanged;
 
     // Wait for the network to become availableand for a DHCP address to be allocated.
     WaitHandle.WaitAll(new[] { m_WaitForAddressChange, m_WaitForNetwork });
....
}
 
The Ethernet version is configured to use DHCP. For reference the associated code to enable the WaitHandle.WaitAll() is below.
 
        /// <summary>
        /// Initialises an instance of the <see cref="NetworkHelper"/> class.
        /// </summary>
        public NetworkHelper()
        {
            m_WaitForNetwork = new AutoResetEvent(false);
            m_WaitForAddressChange = new AutoResetEvent(false);
        }
 
        /// <summary>
        /// Event handler to signal when the network address has changed.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="eventArgs"></param>
        private void OnNetworkAddressChanged(object sender, EventArgs eventArgs)
        {
            m_WaitForAddressChange.Set();
        }
 
        /// <summary>
        /// Event handler to signal that the network is now available.
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="networkAvailabilityEventArgs"></param>
        private void OnNetworkAvailabilityChanged(object sender, NetworkAvailabilityEventArgs eventArgs)
        {
            if (eventArgs.IsAvailable)
            {
                m_WaitForNetwork.Set();
            }
        }


#2 ukkiwisurfer

ukkiwisurfer

    Advanced Member

  • Members
  • PipPipPip
  • 32 posts
  • LocationLondon

Posted 22 October 2015 - 08:21 PM

In an interesting twist to this issue, running this code on a Netduino Plus 2 highlights a race condition. The issue is that the ethernet and Wifi networking capabilities on the Netduino 3 take a lot longer to initialise (3+ seconds) than the Netduino Plus 2's (4.3.2.1 Firmware) Ethernet does (milliseconds).

 

The consequence is, the above code will block indefinitely on Netduino Plus 2 at the WaitHandle.WaitAll() call because the NetworkChange event handlers never trigger. The network has already been initialised and configured (DHCP) even before the code has had a chance to set up the event handlers.

 

However the Netduino 3 (Ethernet and Wifi) take several seconds to initialise, allowing the NetworkChange event handlers to be set up and to fire.



#3 ukkiwisurfer

ukkiwisurfer

    Advanced Member

  • Members
  • PipPipPip
  • 32 posts
  • LocationLondon

Posted 22 October 2015 - 08:30 PM

The following code should remedy the above issue for the Netduino Plus 2 and will still work for the Netduino 3 (Ethernet and Wifi) boards. Short summary: specify a timeout in milliseconds and loop until the DHCP address has been assigned.

 

/// <summary>
/// Returns the IP address of the device.
/// </summary>

public NetworkInformation GetNetworkDetails(int interfaceIndex)
{
           NetworkInformation information = null;

           // Set up event handlers for network state changes.
           NetworkChange.NetworkAvailabilityChanged += OnInternalNetworkAvailabilityChanged;
           NetworkChange.NetworkAddressChanged += OnNetworkAddressChanged;

           try
           {
               // Wait for the network to become available and for a DHCP address to be allocated.
               bool isWaitingToInitialise = true;
               while (isWaitingToInitialise)
               {
                   var isSignalled = WaitHandle.WaitAll(new[] { m_WaitForAddressChange, m_WaitForNetwork }, m_WaitForNetworkEventInMilliseconds, false);
                   if (!isSignalled)
                   {
                       // Retrieve network interface details to see if the initialisation had already occurred.
                       information = QueryInterface(interfaceIndex);
                       if ((information.IsDHCPEnabled) && (information.IpAddress != "0.0.0.0"))
                       {
                           isWaitingToInitialise = false;
                       }
                   }
                   else isWaitingToInitialise = false;
               }

               information = QueryInterface(interfaceIndex);
           }
           finally
           {
               m_WaitForAddressChange.Reset();
               m_WaitForNetwork.Reset();
           }

           return information;
       }

       /// <summary>
       /// Queries a network device for details about its connection state.
       /// </summary>
       /// <param name="interfaceIndex">
       /// The index of the device to query.
       /// </param>
       /// <returns>
       /// The status information on the network device.
       /// </returns>
       public NetworkInformation QueryInterface(int interfaceIndex)
       {
           NetworkInformation information = null;

          
               var networkInterface = GetInterface(interfaceIndex);
               if (networkInterface != null)
               {
                   // Then capture the network details. 
                   information = new NetworkInformation();
                   information.IpAddress = networkInterface.IPAddress;
                   information.IsDHCPEnabled = networkInterface.IsDhcpEnabled;
                   information.SubnetMask = networkInterface.SubnetMask;
                   information.MacAddress = networkInterface.PhysicalAddress;
                   information.NetworkInterfaceType = networkInterface.NetworkInterfaceType.ToString();
               }

           return information;
       }






0 user(s) are reading this topic

0 members, 0 guests, 0 anonymous users

home    hardware    projects    downloads    community    where to buy    contact Copyright © 2016 Wilderness Labs Inc.  |  Legal   |   CC BY-SA
This webpage is licensed under a Creative Commons Attribution-ShareAlike License.