2 * PROJECT: ReactOS WLAN command-line configuration utility
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: base/applications/network/wlanconf/wlanconf.c
5 * PURPOSE: Allows WLAN configuration via the command prompt
6 * COPYRIGHT: Copyright 2012 Cameron Gutman (cameron.gutman@reactos.org)
18 BOOL bConnect
= FALSE
;
23 BOOL bDisconnect
= FALSE
;
25 DWORD
DoFormatMessage(DWORD ErrorCode
)
30 if ((RetVal
= FormatMessage(
31 FORMAT_MESSAGE_ALLOCATE_BUFFER
|
32 FORMAT_MESSAGE_FROM_SYSTEM
|
33 FORMAT_MESSAGE_IGNORE_INSERTS
,
36 MAKELANGID(LANG_NEUTRAL
, SUBLANG_DEFAULT
), /* Default language */
41 _tprintf(_T("%s"), (LPTSTR
)lpMsgBuf
);
45 /* return number of TCHAR's stored in output buffer
46 * excluding '\0' - as FormatMessage does*/
54 OpenDriverHandle(VOID
)
57 DWORD dwBytesReturned
;
60 /* Open a handle to the NDISUIO driver */
61 hDriver
= CreateFileW(NDISUIO_DEVICE_NAME
,
62 GENERIC_READ
| GENERIC_WRITE
,
66 FILE_ATTRIBUTE_NORMAL
,
68 if (hDriver
== INVALID_HANDLE_VALUE
)
69 return INVALID_HANDLE_VALUE
;
72 bSuccess
= DeviceIoControl(hDriver
,
73 IOCTL_NDISUIO_BIND_WAIT
,
83 return INVALID_HANDLE_VALUE
;
90 IsWlanAdapter(HANDLE hAdapter
)
93 DWORD dwBytesReturned
;
94 NDISUIO_QUERY_OID QueryOid
;
96 /* NDIS 5.1 WLAN drivers must support this OID */
97 QueryOid
.Oid
= OID_GEN_PHYSICAL_MEDIUM
;
99 bSuccess
= DeviceIoControl(hAdapter
,
100 IOCTL_NDISUIO_QUERY_OID_VALUE
,
107 if (!bSuccess
|| *(PULONG
)QueryOid
.Data
!= NdisPhysicalMediumWirelessLan
)
114 OpenAdapterHandle(DWORD Index
)
118 DWORD dwBytesReturned
;
119 DWORD QueryBindingSize
= sizeof(NDISUIO_QUERY_BINDING
) + (1024 * sizeof(WCHAR
));
120 PNDISUIO_QUERY_BINDING QueryBinding
;
122 /* Open the driver handle */
123 hDriver
= OpenDriverHandle();
124 if (hDriver
== INVALID_HANDLE_VALUE
)
125 return INVALID_HANDLE_VALUE
;
127 /* Allocate the binding struct */
128 QueryBinding
= HeapAlloc(GetProcessHeap(), 0, QueryBindingSize
);
131 CloseHandle(hDriver
);
132 return INVALID_HANDLE_VALUE
;
135 /* Query for bindable adapters */
136 QueryBinding
->BindingIndex
= 0;
138 bSuccess
= DeviceIoControl(hDriver
,
139 IOCTL_NDISUIO_QUERY_BINDING
,
146 if (QueryBinding
->BindingIndex
== Index
)
148 QueryBinding
->BindingIndex
++;
153 HeapFree(GetProcessHeap(), 0, QueryBinding
);
154 CloseHandle(hDriver
);
155 return INVALID_HANDLE_VALUE
;
158 /* Bind to the adapter */
159 bSuccess
= DeviceIoControl(hDriver
,
160 IOCTL_NDISUIO_OPEN_DEVICE
,
161 (PUCHAR
)QueryBinding
+ QueryBinding
->DeviceNameOffset
,
162 QueryBinding
->DeviceNameLength
,
167 HeapFree(GetProcessHeap(), 0, QueryBinding
);
171 CloseHandle(hDriver
);
172 return INVALID_HANDLE_VALUE
;
178 /* Only works with the first adapter for now */
180 OpenWlanAdapter(VOID
)
182 DWORD dwCurrentIndex
;
183 HANDLE hCurrentAdapter
;
185 for (dwCurrentIndex
= 0; ; dwCurrentIndex
++)
187 hCurrentAdapter
= OpenAdapterHandle(dwCurrentIndex
);
188 if (hCurrentAdapter
== INVALID_HANDLE_VALUE
)
191 if (IsWlanAdapter(hCurrentAdapter
))
192 return hCurrentAdapter
;
194 CloseHandle(hCurrentAdapter
);
197 return INVALID_HANDLE_VALUE
;
201 WlanDisconnect(HANDLE hAdapter
)
204 DWORD dwBytesReturned
;
205 NDISUIO_SET_OID SetOid
;
207 SetOid
.Oid
= OID_802_11_DISASSOCIATE
;
209 bSuccess
= DeviceIoControl(hAdapter
,
210 IOCTL_NDISUIO_SET_OID_VALUE
,
225 Char
= toupper(Char
);
267 WlanConnect(HANDLE hAdapter
)
270 DWORD dwBytesReturned
, SetOidSize
;
271 PNDISUIO_SET_OID SetOid
;
272 PNDIS_802_11_SSID Ssid
;
275 SetOidSize
= sizeof(NDISUIO_SET_OID
);
276 SetOid
= HeapAlloc(GetProcessHeap(), 0, SetOidSize
);
280 /* Set the network mode */
281 SetOid
->Oid
= OID_802_11_INFRASTRUCTURE_MODE
;
282 *(PULONG
)SetOid
->Data
= bAdhoc
? Ndis802_11IBSS
: Ndis802_11Infrastructure
;
284 bSuccess
= DeviceIoControl(hAdapter
,
285 IOCTL_NDISUIO_SET_OID_VALUE
,
294 HeapFree(GetProcessHeap(), 0, SetOid
);
298 /* Set the authentication mode */
299 SetOid
->Oid
= OID_802_11_AUTHENTICATION_MODE
;
300 *(PULONG
)SetOid
->Data
= sWepKey
? Ndis802_11AuthModeShared
: Ndis802_11AuthModeOpen
;
302 bSuccess
= DeviceIoControl(hAdapter
,
303 IOCTL_NDISUIO_SET_OID_VALUE
,
312 HeapFree(GetProcessHeap(), 0, SetOid
);
318 PNDIS_802_11_WEP WepData
;
320 HeapFree(GetProcessHeap(), 0, SetOid
);
322 SetOidSize
= sizeof(NDISUIO_SET_OID
) + FIELD_OFFSET(NDIS_802_11_WEP
, KeyMaterial
) +
323 (strlen(sWepKey
) >> 2);
324 SetOid
= HeapAlloc(GetProcessHeap(), 0, SetOidSize
);
328 /* Add the WEP key */
329 SetOid
->Oid
= OID_802_11_ADD_WEP
;
330 WepData
= (PNDIS_802_11_WEP
)SetOid
->Data
;
332 WepData
->KeyIndex
= 0x80000000;
333 WepData
->KeyLength
= strlen(sWepKey
) >> 2;
334 WepData
->Length
= FIELD_OFFSET(NDIS_802_11_WEP
, KeyMaterial
) + WepData
->KeyLength
;
336 /* Assemble the hex key */
338 while (sWepKey
[i
<< 2] != '\0')
340 WepData
->KeyMaterial
[i
] = CharToHex(sWepKey
[i
<< 2]) << 4;
341 WepData
->KeyMaterial
[i
] |= CharToHex(sWepKey
[(i
<< 2) + 1]);
345 bSuccess
= DeviceIoControl(hAdapter
,
346 IOCTL_NDISUIO_SET_OID_VALUE
,
355 HeapFree(GetProcessHeap(), 0, SetOid
);
360 /* Set the encryption status */
361 SetOid
->Oid
= OID_802_11_WEP_STATUS
;
362 *(PULONG
)SetOid
->Data
= sWepKey
? Ndis802_11WEPEnabled
: Ndis802_11WEPDisabled
;
364 bSuccess
= DeviceIoControl(hAdapter
,
365 IOCTL_NDISUIO_SET_OID_VALUE
,
374 HeapFree(GetProcessHeap(), 0, SetOid
);
378 HeapFree(GetProcessHeap(), 0, SetOid
);
379 SetOidSize
= sizeof(NDISUIO_SET_OID
) + sizeof(NDIS_802_11_MAC_ADDRESS
);
380 SetOid
= HeapAlloc(GetProcessHeap(), 0, SetOidSize
);
385 SetOid
->Oid
= OID_802_11_BSSID
;
386 RtlFillMemory(SetOid
->Data
, sizeof(NDIS_802_11_MAC_ADDRESS
), 0xFF);
388 bSuccess
= DeviceIoControl(hAdapter
,
389 IOCTL_NDISUIO_SET_OID_VALUE
,
398 HeapFree(GetProcessHeap(), 0, SetOid
);
402 HeapFree(GetProcessHeap(), 0, SetOid
);
403 SetOidSize
= sizeof(NDISUIO_SET_OID
) + sizeof(NDIS_802_11_SSID
);
404 SetOid
= HeapAlloc(GetProcessHeap(), 0, SetOidSize
);
408 /* Finally, set the SSID */
409 SetOid
->Oid
= OID_802_11_SSID
;
410 Ssid
= (PNDIS_802_11_SSID
)SetOid
->Data
;
412 RtlCopyMemory(Ssid
->Ssid
, sSsid
, strlen(sSsid
));
413 Ssid
->SsidLength
= strlen(sSsid
);
415 bSuccess
= DeviceIoControl(hAdapter
,
416 IOCTL_NDISUIO_SET_OID_VALUE
,
424 HeapFree(GetProcessHeap(), 0, SetOid
);
430 WlanScan(HANDLE hAdapter
)
433 DWORD dwBytesReturned
;
434 NDISUIO_SET_OID SetOid
;
435 PNDISUIO_QUERY_OID QueryOid
;
437 PNDIS_802_11_BSSID_LIST BssidList
;
440 SetOid
.Oid
= OID_802_11_BSSID_LIST_SCAN
;
442 /* Send the scan OID */
443 bSuccess
= DeviceIoControl(hAdapter
,
444 IOCTL_NDISUIO_SET_OID_VALUE
,
454 /* Allocate space for 15 networks to be returned */
455 QueryOidSize
= sizeof(NDISUIO_QUERY_OID
) + (sizeof(NDIS_WLAN_BSSID
) * 15);
456 QueryOid
= HeapAlloc(GetProcessHeap(), 0, QueryOidSize
);
460 QueryOid
->Oid
= OID_802_11_BSSID_LIST
;
461 BssidList
= (PNDIS_802_11_BSSID_LIST
)QueryOid
->Data
;
463 bSuccess
= DeviceIoControl(hAdapter
,
464 IOCTL_NDISUIO_QUERY_OID_VALUE
,
473 HeapFree(GetProcessHeap(), 0, QueryOid
);
477 if (BssidList
->NumberOfItems
== 0)
479 _tprintf(_T("No networks found in range\n"));
483 PNDIS_WLAN_BSSID BssidInfo
= BssidList
->Bssid
;
484 for (i
= 0; i
< BssidList
->NumberOfItems
; i
++)
486 PNDIS_802_11_SSID Ssid
= &BssidInfo
->Ssid
;
487 NDIS_802_11_RSSI Rssi
= BssidInfo
->Rssi
;
488 NDIS_802_11_NETWORK_INFRASTRUCTURE NetworkType
= BssidInfo
->InfrastructureMode
;
489 CHAR SsidBuffer
[NDIS_802_11_LENGTH_SSID
+ 1];
491 /* SSID member is a non-null terminated ASCII string */
492 RtlCopyMemory(SsidBuffer
, Ssid
->Ssid
, Ssid
->SsidLength
);
493 SsidBuffer
[Ssid
->SsidLength
] = 0;
495 _tprintf(_T("\nSSID: %s\n"
499 "Supported Rates (Mbps): "),
501 BssidInfo
->Privacy
== 0 ? "No" : "Yes",
502 NetworkType
== Ndis802_11IBSS
? "Adhoc" : "Infrastructure",
505 for (j
= 0; j
< NDIS_802_11_LENGTH_RATES
; j
++)
507 if (BssidInfo
->SupportedRates
[j
] != 0)
509 /* SupportedRates are in units of .5 */
510 _tprintf(_T("%d "), (BssidInfo
->SupportedRates
[j
] << 2));
515 /* Move to the next entry */
516 BssidInfo
= (PNDIS_WLAN_BSSID
)((PUCHAR
)BssidInfo
+ BssidInfo
->Length
);
520 HeapFree(GetProcessHeap(), 0, QueryOid
);
527 _tprintf(_T("\nConfigures a WLAN adapter.\n\n"
528 "WLANCONF [-c SSID [-w WEP] [-a]] [-d] [-s]\n\n"
529 " -c SSID Connects to a supplied SSID.\n"
530 " -w WEP Specifies a WEP key to use.\n"
531 " -a Specifies the target network is ad-hoc\n"
532 " -d Disconnects from the current AP.\n"
533 " -s Scans and displays a list of access points in range.\n"));
537 BOOL
ParseCmdline(int argc
, char* argv
[])
541 for (i
= 1; i
< argc
; i
++)
543 if ((argc
> 1) && (argv
[i
][0] == '-'))
547 while ((c
= *++argv
[i
]) != '\0')
575 if (!bScan
&& !bDisconnect
&& !bConnect
)
584 int main(int argc
, char* argv
[])
588 if (!ParseCmdline(argc
, argv
))
591 hAdapter
= OpenWlanAdapter();
592 if (hAdapter
== INVALID_HANDLE_VALUE
)
594 DoFormatMessage(GetLastError());
600 if (!WlanScan(hAdapter
))
602 DoFormatMessage(GetLastError());
603 CloseHandle(hAdapter
);
607 else if (bDisconnect
)
609 if (!WlanDisconnect(hAdapter
))
611 DoFormatMessage(GetLastError());
612 CloseHandle(hAdapter
);
618 if (!WlanConnect(hAdapter
))
620 DoFormatMessage(GetLastError());
621 CloseHandle(hAdapter
);
626 CloseHandle(hAdapter
);