Rilevare nome e stato della scheda WIFI con Microsoft .Net

Un esempio pratico di come rilevare le informazioni sulla scheda WiFi e verificare lo stato.

il
Sviluppatore Microsoft .Net, Collaboratore di IProgrammatori

In questo articolo vedremo come rilevare il nome della scheda WiFi e verificare lo stato, ossia connesso, disconnesso o altro.
Utilizzeremo le API di Windows per gestire la periferica.


Stesura del codice


Si crea un nuovo progetto di tipo “Windows Application” utilizzando il linguaggio di programmazione di programmazione  VB.Net o C# in base alla conoscenza del lettore.
Aggiungiamo nella form un pulsante il quale visualizzerà in una casella di testo il nome della scheda e lo stato.
Passiamo in visualizzazione codice.
Aggiungiamo lo spazio dei nomi per gestire l’interoperabilità, ossia l’utilizzo delle API.

VB.Net
Imports System.Runtime.InteropServices
C#
using System.Runtime.InteropServices;

Si creano due costanti le quali saranno utilizzate nelle funzioni API per verificare se le chiamate sono andate a buon fine oppure no.
Qui di seguito il frammento di codice delle suddette operazioni.

VB.Net
Private Const WLAN_API_VERSION_2_0 As Integer = 2
Private Const ERROR_SUCCESS As Integer = 0
C#
private const int WLAN_API_VERSION_2_0 = 2;
private const int ERROR_SUCCESS = 0;

A questo punto non ci resta che aggiungere le funzioni API di Windows, per rilevare le informazioni della scheda.

Qui di seguito i frammenti di codice per entrambi i linguaggi.

VB.Net
''' <summary >
''' Apertura alla connessione al server
''' </summary >
<DllImport("wlanapi.dll", SetLastError:=True)> _
Private Shared Function WlanOpenHandle(dwClientVersion As UInt32, pReserved As IntPtr, ByRef pdwNegotiatedVersion As UInt32, ByRef phClientHandle As IntPtr) As UInt32
End Function
''' <summary >
''' Chiusura connessione al server
''' </summary >
<DllImport("wlanapi.dll", SetLastError:=True)> _
Private Shared Function WlanCloseHandle(hClientHandle As IntPtr, pReserved As IntPtr) As UInt32
End Function
''' <summary >
''' Lista di tutte le interfacce Wireless
''' </summary >
<DllImport("wlanapi.dll", SetLastError:=True)> _
Private Shared Function WlanEnumInterfaces(hClientHandle As IntPtr, pReserved As IntPtr, ByRef ppInterfaceList As IntPtr) As UInt32
End Function
''' <summary >
'''
''' </summary >
<DllImport("wlanapi.dll", SetLastError:=True)> _
Private Shared Sub WlanFreeMemory(pmemory As IntPtr)
End Sub
''' <summary >
'''
''' </summary >
Public Enum WLAN_INTERFACE_STATE As Integer
wlan_interface_state_not_ready = 0
wlan_interface_state_connected
wlan_interface_state_ad_hoc_network_formed
wlan_interface_state_disconnecting
wlan_interface_state_disconnected
wlan_interface_state_associating
wlan_interface_state_discovering
wlan_interface_state_authenticating
End Enum
''' <summary >
'''
''' </summary >
<StructLayout(LayoutKind.Sequential, CharSet:=CharSet.Unicode)> _
Public Structure WLAN_INTERFACE_INFO
''' GUID->_GUID
Public InterfaceGuid As Guid
''' WCHAR[256]
<MarshalAs(UnmanagedType.ByValTStr, SizeConst:=256)> _
Public strInterfaceDescription As String
''' WLAN_INTERFACE_STATE->_WLAN_INTERFACE_STATE
Public isState As WLAN_INTERFACE_STATE
End Structure
''' <summary >
'''
''' </summary >
<StructLayout(LayoutKind.Sequential)> _
Public Structure WLAN_INTERFACE_INFO_LIST
Public dwNumberofItems As Int32
Public dwIndex As Int32
Public InterfaceInfo As WLAN_INTERFACE_INFO()
Public Sub New(pList As IntPtr)
dwNumberofItems = Marshal.ReadInt32(pList, 0)
dwIndex = Marshal.ReadInt32(pList, 4)
InterfaceInfo = New WLAN_INTERFACE_INFO(dwNumberofItems - 1) {}
For i As Integer = 0 To dwNumberofItems - 1
Dim pItemList As New IntPtr(pList.ToInt32() + (i * 532) + 8)
Dim wii As New WLAN_INTERFACE_INFO()
wii = CType(Marshal.PtrToStructure(pItemList, GetType(WLAN_INTERFACE_INFO)), WLAN_INTERFACE_INFO)
InterfaceInfo(i) = wii
Next
End Sub
End Structure
Private Function getStateDescription(state As WLAN_INTERFACE_STATE) As String
Dim stateDescription As String = String.Empty
Select Case state
Case WLAN_INTERFACE_STATE.wlan_interface_state_not_ready
stateDescription = "Non presente"
Exit Select
Case WLAN_INTERFACE_STATE.wlan_interface_state_connected
stateDescription = "Connesso"
Exit Select
Case WLAN_INTERFACE_STATE.wlan_interface_state_ad_hoc_network_formed
stateDescription = "first node in an adhoc network"
Exit Select
Case WLAN_INTERFACE_STATE.wlan_interface_state_disconnecting
stateDescription = "In fase di disconnessione"
Exit Select
Case WLAN_INTERFACE_STATE.wlan_interface_state_disconnected
stateDescription = "Disconesso"
Exit Select
Case WLAN_INTERFACE_STATE.wlan_interface_state_associating
stateDescription = "Associato"
Exit Select
Case WLAN_INTERFACE_STATE.wlan_interface_state_discovering
stateDescription = "discovering"
Exit Select
Case WLAN_INTERFACE_STATE.wlan_interface_state_authenticating
stateDescription = "Autenticazione"
Exit Select
End Select
Return stateDescription
End Function
C#
/// <summary >
/// Apertura alla connessione al server
/// </summary >
[DllImport("wlanapi.dll", SetLastError = true)]
private static extern UInt32 WlanOpenHandle(UInt32 dwClientVersion,
IntPtr pReserved, out UInt32 pdwNegotiatedVersion,
out IntPtr phClientHandle);
/// <summary >
/// Chiusura connessione al server
/// </summary >
[DllImport("wlanapi.dll", SetLastError = true)]
private static extern UInt32 WlanCloseHandle(IntPtr hClientHandle,
IntPtr pReserved);
/// <summary >
/// Lista di tutte le interfacce Wireless
/// </summary >
[DllImport("wlanapi.dll", SetLastError = true)]
private static extern UInt32 WlanEnumInterfaces(IntPtr hClientHandle,
IntPtr pReserved, out IntPtr ppInterfaceList);
/// <summary >
///
/// </summary >
[DllImport("wlanapi.dll", SetLastError = true)]
private static extern void WlanFreeMemory(IntPtr pmemory);
/// <summary >
///
/// </summary >
public enum WLAN_INTERFACE_STATE : int
{
wlan_interface_state_not_ready = 0,
wlan_interface_state_connected,
wlan_interface_state_ad_hoc_network_formed,
wlan_interface_state_disconnecting,
wlan_interface_state_disconnected,
wlan_interface_state_associating,
wlan_interface_state_discovering,
wlan_interface_state_authenticating
};
/// <summary >
///
/// </summary >
[StructLayout(LayoutKind.Sequential, CharSet = CharSet.Unicode)]
public struct WLAN_INTERFACE_INFO
{
/// GUID->_GUID
public Guid InterfaceGuid;
/// WCHAR[256]
[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)]
public string strInterfaceDescription;
/// WLAN_INTERFACE_STATE->_WLAN_INTERFACE_STATE
public WLAN_INTERFACE_STATE isState;
}
/// <summary >
///
/// </summary >
[StructLayout(LayoutKind.Sequential)]
public struct WLAN_INTERFACE_INFO_LIST
{
public Int32 dwNumberofItems;
public Int32 dwIndex;
public WLAN_INTERFACE_INFO[] InterfaceInfo;
public WLAN_INTERFACE_INFO_LIST(IntPtr pList)
{
dwNumberofItems = Marshal.ReadInt32(pList, 0);
dwIndex = Marshal.ReadInt32(pList, 4);
InterfaceInfo = new WLAN_INTERFACE_INFO[dwNumberofItems];
for (int i = 0; i < dwNumberofItems; i++)
{
IntPtr pItemList = new IntPtr(pList.ToInt32() + (i * 532) + 8);
WLAN_INTERFACE_INFO wii = new WLAN_INTERFACE_INFO();
wii = (WLAN_INTERFACE_INFO)Marshal.PtrToStructure(pItemList,
typeof(WLAN_INTERFACE_INFO));
InterfaceInfo[i] = wii;
}
}
}
private string getStateDescription(WLAN_INTERFACE_STATE state)
{
string stateDescription=string.Empty;
switch (state)
{
case WLAN_INTERFACE_STATE.wlan_interface_state_not_ready:
stateDescription = "Non presente";
break;
case WLAN_INTERFACE_STATE.wlan_interface_state_connected:
stateDescription = "Connesso";
break;
case WLAN_INTERFACE_STATE.wlan_interface_state_ad_hoc_network_formed:
stateDescription = "first node in an adhoc network";
break;
case WLAN_INTERFACE_STATE.wlan_interface_state_disconnecting:
stateDescription = "In fase di disconnessione";
break;
case WLAN_INTERFACE_STATE.wlan_interface_state_disconnected:
stateDescription = "Disconesso";
break;
case WLAN_INTERFACE_STATE.wlan_interface_state_associating:
stateDescription = "Associato";
break;
case WLAN_INTERFACE_STATE.wlan_interface_state_discovering:
stateDescription = "discovering";
break;
case WLAN_INTERFACE_STATE.wlan_interface_state_authenticating:
stateDescription = "Autenticazione";
break;
}
return stateDescription;
}

Ora dobbiamo scrivere la funzione che verrà richiamata nell’evento click del pulsante e che dovrà visualizzare le informazioni della scheda tramite l’utilizzo delle API.
Qui di seguito il frammento di codice per il codice VB.Net e C#.

VB.Net
Private Sub OttieniListaWifi()
Dim serviceVersion As UInteger = 0
Dim handle As IntPtr = IntPtr.Zero
If WlanOpenHandle(WLAN_API_VERSION_2_0, IntPtr.Zero, serviceVersion, handle) = ERROR_SUCCESS Then
Dim ppInterfaceList As IntPtr = IntPtr.Zero
Dim interfaceList As WLAN_INTERFACE_INFO_LIST
If WlanEnumInterfaces(handle, IntPtr.Zero, ppInterfaceList) = ERROR_SUCCESS Then
interfaceList = New WLAN_INTERFACE_INFO_LIST(ppInterfaceList)
For i As Integer = 0 To interfaceList.dwNumberofItems - 1
txtLista.Text = interfaceList.InterfaceInfo(i).strInterfaceDescription + " " + getStateDescription(interfaceList.InterfaceInfo(i).isState)
Next
If ppInterfaceList <> IntPtr.Zero Then
WlanFreeMemory(ppInterfaceList)
End If
End If
WlanCloseHandle(handle, IntPtr.Zero)
End If
End Sub
C#
private void OttieniListaWifi()
{
uint serviceVersion = 0;
IntPtr handle = IntPtr.Zero;
if(WlanOpenHandle(WLAN_API_VERSION_2_0, IntPtr.Zero,
out serviceVersion, out handle) == ERROR_SUCCESS)
{
IntPtr ppInterfaceList = IntPtr.Zero;
WLAN_INTERFACE_INFO_LIST interfaceList;
if (WlanEnumInterfaces(handle, IntPtr.Zero,
out ppInterfaceList) == ERROR_SUCCESS)
{
interfaceList = new WLAN_INTERFACE_INFO_LIST(ppInterfaceList);
for (int i = 0; i < interfaceList.dwNumberofItems; i++)
txtLista.Text = interfaceList.InterfaceInfo[i].strInterfaceDescription + " " + getStateDescription(interfaceList.InterfaceInfo[i].isState);
if (ppInterfaceList != IntPtr.Zero)
WlanFreeMemory(ppInterfaceList);
}
WlanCloseHandle(handle, IntPtr.Zero);
}
}

Siamo giunti alla fine dell'articolo ora dovremmo scrivere il codice per l’evento click del pulsante che permetterà di avere informazioni sulla scheda.

VB.Net
Private Sub BtnVisualizza_Click(sender As System.Object, e As System.EventArgs) Handles BtnVisualizza.Click
OttieniListaWifi()
End Sub
C#
private void BtnVisualizza_Click(object sender, EventArgs e)
{
OttieniListaWifi();
}

Conclusioni


L’articolo ha voluto fornire al lettore l’utilizzo delle API per rilevare informazioni sulla scheda WiFi. Sempre più negli ultimi anni la scheda WiFi è divenuto un componente indispensabile al punto che si possono realizzare tools e programmi di sicurezza.