common.c revision 8d520ff1dc2da35cdca849e982051b86468016d8
18d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/* 28d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_supplicant/hostapd / common helper functions, etc. 38d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Copyright (c) 2002-2007, Jouni Malinen <j@w1.fi> 48d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 58d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This program is free software; you can redistribute it and/or modify 68d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * it under the terms of the GNU General Public License version 2 as 78d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * published by the Free Software Foundation. 88d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 98d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Alternatively, this software may be distributed under the terms of BSD 108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * license. 118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * See README and COPYING for more details. 138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "includes.h" 168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#include "common.h" 188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic int hex2num(char c) 218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (c >= '0' && c <= '9') 238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return c - '0'; 248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (c >= 'a' && c <= 'f') 258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return c - 'a' + 10; 268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (c >= 'A' && c <= 'F') 278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return c - 'A' + 10; 288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint hex2byte(const char *hex) 338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int a, b; 358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt a = hex2num(*hex++); 368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (a < 0) 378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt b = hex2num(*hex++); 398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (b < 0) 408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return (a << 4) | b; 428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * hwaddr_aton - Convert ASCII string to MAC address (colon-delimited format) 478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @txt: MAC address as a string (e.g., "00:11:22:33:44:55") 488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @addr: Buffer for the MAC address (ETH_ALEN = 6 bytes) 498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 on success, -1 on failure (e.g., string not a MAC address) 508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint hwaddr_aton(const char *txt, u8 *addr) 528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < 6; i++) { 568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int a, b; 578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt a = hex2num(*txt++); 598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (a < 0) 608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt b = hex2num(*txt++); 628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (b < 0) 638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *addr++ = (a << 4) | b; 658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (i < 5 && *txt++ != ':') 668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * hwaddr_compact_aton - Convert ASCII string to MAC address (no colon delimitors format) 748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @txt: MAC address as a string (e.g., "001122334455") 758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @addr: Buffer for the MAC address (ETH_ALEN = 6 bytes) 768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 on success, -1 on failure (e.g., string not a MAC address) 778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint hwaddr_compact_aton(const char *txt, u8 *addr) 798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < 6; i++) { 838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int a, b; 848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt a = hex2num(*txt++); 868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (a < 0) 878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt b = hex2num(*txt++); 898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (b < 0) 908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *addr++ = (a << 4) | b; 928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * hwaddr_aton2 - Convert ASCII string to MAC address (in any known format) 998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @txt: MAC address as a string (e.g., 00:11:22:33:44:55 or 0011.2233.4455) 1008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @addr: Buffer for the MAC address (ETH_ALEN = 6 bytes) 1018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Characters used (> 0) on success, -1 on failure 1028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 1038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint hwaddr_aton2(const char *txt, u8 *addr) 1048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int i; 1068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *pos = txt; 1078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < 6; i++) { 1098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int a, b; 1108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*pos == ':' || *pos == '.' || *pos == '-') 1128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos++; 1138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt a = hex2num(*pos++); 1158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (a < 0) 1168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 1178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt b = hex2num(*pos++); 1188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (b < 0) 1198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 1208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *addr++ = (a << 4) | b; 1218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return pos - txt; 1248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 1288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * hexstr2bin - Convert ASCII hex string into binary data 1298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @hex: ASCII hex string (e.g., "01ab") 1308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @buf: Buffer for the binary data 1318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @len: Length of the text to convert in bytes (of buf); hex will be double 1328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * this size 1338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: 0 on success, -1 on failure (invalid hex string) 1348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 1358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint hexstr2bin(const char *hex, u8 *buf, size_t len) 1368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t i; 1388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int a; 1398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt const char *ipos = hex; 1408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u8 *opos = buf; 1418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < len; i++) { 1438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt a = hex2byte(ipos); 1448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (a < 0) 1458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return -1; 1468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *opos++ = a; 1478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ipos += 2; 1488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 1508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 1548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * inc_byte_array - Increment arbitrary length byte array by one 1558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @counter: Pointer to byte array 1568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @len: Length of the counter in bytes 1578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 1588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function increments the last byte of the counter by one and continues 1598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * rolling over to more significant bytes if the byte was incremented from 1608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 0xff to 0x00. 1618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 1628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid inc_byte_array(u8 *counter, size_t len) 1638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int pos = len - 1; 1658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (pos >= 0) { 1668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt counter[pos]++; 1678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (counter[pos] != 0) 1688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt break; 1698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos--; 1708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 1718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_get_ntp_timestamp(u8 *buf) 1758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt struct os_time now; 1778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt u32 sec, usec; 1788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt be32 tmp; 1798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* 64-bit NTP timestamp (time from 1900-01-01 00:00:00) */ 1818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_get_time(&now); 1828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt sec = now.sec + 2208988800U; /* Epoch to 1900 */ 1838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Estimate 2^32/10^6 = 4295 - 1/32 - 1/512 */ 1848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt usec = now.usec; 1858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt usec = 4295 * usec - (usec >> 5) - (usec >> 9); 1868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tmp = host_to_be32(sec); 1878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(buf, (u8 *) &tmp, 4); 1888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt tmp = host_to_be32(usec); 1898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(buf + 4, (u8 *) &tmp, 4); 1908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 1918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 1938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtstatic inline int _wpa_snprintf_hex(char *buf, size_t buf_size, const u8 *data, 1948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t len, int uppercase) 1958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 1968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t i; 1978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *pos = buf, *end = buf + buf_size; 1988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt int ret; 1998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (buf_size == 0) 2008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return 0; 2018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (i = 0; i < len; i++) { 2028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ret = os_snprintf(pos, end - pos, uppercase ? "%02X" : "%02x", 2038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt data[i]); 2048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ret < 0 || ret >= end - pos) { 2058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end[-1] = '\0'; 2068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return pos - buf; 2078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt pos += ret; 2098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt end[-1] = '\0'; 2118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return pos - buf; 2128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 2158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_snprintf_hex - Print data as a hex string into a buffer 2168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @buf: Memory area to use as the output buffer 2178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @buf_size: Maximum buffer size in bytes (should be at least 2 * len + 1) 2188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @data: Data to be printed 2198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @len: Length of data in bytes 2208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Number of bytes written 2218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_snprintf_hex(char *buf, size_t buf_size, const u8 *data, size_t len) 2238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return _wpa_snprintf_hex(buf, buf_size, data, len, 0); 2258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 2298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_snprintf_hex_uppercase - Print data as a upper case hex string into buf 2308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @buf: Memory area to use as the output buffer 2318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @buf_size: Maximum buffer size in bytes (should be at least 2 * len + 1) 2328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @data: Data to be printed 2338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @len: Length of data in bytes 2348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Number of bytes written 2358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 2368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint wpa_snprintf_hex_uppercase(char *buf, size_t buf_size, const u8 *data, 2378d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt size_t len) 2388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return _wpa_snprintf_hex(buf, buf_size, data, len, 1); 2408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_ANSI_C_EXTRA 2448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef _WIN32_WCE 2468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid perror(const char *s) 2478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wpa_printf(MSG_ERROR, "%s: GetLastError: %d", 2498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt s, (int) GetLastError()); 2508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 2518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* _WIN32_WCE */ 2528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint optind = 1; 2558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint optopt; 2568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtchar *optarg; 2578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtint getopt(int argc, char *const argv[], const char *optstring) 2598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 2608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt static int optchr = 1; 2618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *cp; 2628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (optchr == 1) { 2648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (optind >= argc) { 2658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* all arguments processed */ 2668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return EOF; 2678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (argv[optind][0] != '-' || argv[optind][1] == '\0') { 2708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* no option characters */ 2718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return EOF; 2728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (os_strcmp(argv[optind], "--") == 0) { 2768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* no more options */ 2778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optind++; 2788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return EOF; 2798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optopt = argv[optind][optchr]; 2828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt cp = os_strchr(optstring, optopt); 2838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (cp == NULL || optopt == ':') { 2848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (argv[optind][++optchr] == '\0') { 2858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optchr = 1; 2868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optind++; 2878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2888d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return '?'; 2898d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 2908d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 2918d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (cp[1] == ':') { 2928d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Argument required */ 2938d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optchr = 1; 2948d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (argv[optind][optchr + 1]) { 2958d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* No space between option and argument */ 2968d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optarg = &argv[optind++][optchr + 1]; 2978d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else if (++optind >= argc) { 2988d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* option requires an argument */ 2998d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return '?'; 3008d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 3018d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* Argument in the next argv */ 3028d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optarg = argv[optind++]; 3038d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3048d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } else { 3058d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt /* No argument */ 3068d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (argv[optind][++optchr] == '\0') { 3078d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optchr = 1; 3088d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optind++; 3098d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3108d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt optarg = NULL; 3118d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3128d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return *cp; 3138d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3148d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_ANSI_C_EXTRA */ 3158d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3168d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3178d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef CONFIG_NATIVE_WINDOWS 3188d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 3198d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_unicode2ascii_inplace - Convert unicode string into ASCII 3208d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @str: Pointer to string to convert 3218d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 3228d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function converts a unicode string to ASCII using the same 3238d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * buffer for output. If UNICODE is not set, the buffer is not 3248d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * modified. 3258d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 3268d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid wpa_unicode2ascii_inplace(TCHAR *str) 3278d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3288d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef UNICODE 3298d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *dst = (char *) str; 3308d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt while (*str) 3318d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *dst++ = (char) *str++; 3328d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *dst = '\0'; 3338d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* UNICODE */ 3348d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3358d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3368d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3378d520ff1dc2da35cdca849e982051b86468016d8Dmitry ShmidtTCHAR * wpa_strdup_tchar(const char *str) 3388d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3398d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#ifdef UNICODE 3408d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt TCHAR *buf; 3418d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt buf = os_malloc((strlen(str) + 1) * sizeof(TCHAR)); 3428d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (buf == NULL) 3438d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return NULL; 3448d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt wsprintf(buf, L"%S", str); 3458d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return buf; 3468d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#else /* UNICODE */ 3478d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return os_strdup(str); 3488d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* UNICODE */ 3498d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3508d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt#endif /* CONFIG_NATIVE_WINDOWS */ 3518d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3528d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3538d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt/** 3548d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * wpa_ssid_txt - Convert SSID to a printable string 3558d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid: SSID (32-octet string) 3568d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * @ssid_len: Length of ssid in octets 3578d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * Returns: Pointer to a printable string 3588d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 3598d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function can be used to convert SSIDs into printable form. In most 3608d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * cases, SSIDs do not use unprintable characters, but IEEE 802.11 standard 3618d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * does not limit the used character set, so anything could be used in an SSID. 3628d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * 3638d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * This function uses a static buffer, so only one call can be used at the 3648d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * time, i.e., this is not re-entrant and the returned buffer must be used 3658d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt * before calling this again. 3668d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt */ 3678d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtconst char * wpa_ssid_txt(const u8 *ssid, size_t ssid_len) 3688d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3698d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt static char ssid_txt[33]; 3708d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt char *pos; 3718d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3728d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if (ssid_len > 32) 3738d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid_len = 32; 3748d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt os_memcpy(ssid_txt, ssid, ssid_len); 3758d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt ssid_txt[ssid_len] = '\0'; 3768d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt for (pos = ssid_txt; *pos != '\0'; pos++) { 3778d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt if ((u8) *pos < 32 || (u8) *pos >= 127) 3788d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt *pos = '_'; 3798d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt } 3808d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return ssid_txt; 3818d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 3828d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3838d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt 3848d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidtvoid * __hide_aliasing_typecast(void *foo) 3858d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt{ 3868d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt return foo; 3878d520ff1dc2da35cdca849e982051b86468016d8Dmitry Shmidt} 388