]> git.ipfire.org Git - thirdparty/hostap.git/blame - src/utils/wpa_debug.c
Re-initialize hostapd/wpa_supplicant git repository based on 0.6.3 release
[thirdparty/hostap.git] / src / utils / wpa_debug.c
CommitLineData
6fc6879b
JM
1/*
2 * wpa_supplicant/hostapd / Debug prints
3 * Copyright (c) 2002-2007, Jouni Malinen <j@w1.fi>
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License version 2 as
7 * published by the Free Software Foundation.
8 *
9 * Alternatively, this software may be distributed under the terms of BSD
10 * license.
11 *
12 * See README and COPYING for more details.
13 */
14
15#include "includes.h"
16
17#include "common.h"
18
19
20#ifdef CONFIG_DEBUG_FILE
21static FILE *out_file = NULL;
22#endif /* CONFIG_DEBUG_FILE */
23int wpa_debug_level = MSG_INFO;
24int wpa_debug_show_keys = 0;
25int wpa_debug_timestamp = 0;
26
27
28#ifndef CONFIG_NO_STDOUT_DEBUG
29
30void wpa_debug_print_timestamp(void)
31{
32 struct os_time tv;
33
34 if (!wpa_debug_timestamp)
35 return;
36
37 os_get_time(&tv);
38#ifdef CONFIG_DEBUG_FILE
39 if (out_file) {
40 fprintf(out_file, "%ld.%06u: ", (long) tv.sec,
41 (unsigned int) tv.usec);
42 } else
43#endif /* CONFIG_DEBUG_FILE */
44 printf("%ld.%06u: ", (long) tv.sec, (unsigned int) tv.usec);
45}
46
47
48/**
49 * wpa_printf - conditional printf
50 * @level: priority level (MSG_*) of the message
51 * @fmt: printf format string, followed by optional arguments
52 *
53 * This function is used to print conditional debugging and error messages. The
54 * output may be directed to stdout, stderr, and/or syslog based on
55 * configuration.
56 *
57 * Note: New line '\n' is added to the end of the text when printing to stdout.
58 */
59void wpa_printf(int level, char *fmt, ...)
60{
61 va_list ap;
62
63 va_start(ap, fmt);
64 if (level >= wpa_debug_level) {
65 wpa_debug_print_timestamp();
66#ifdef CONFIG_DEBUG_FILE
67 if (out_file) {
68 vfprintf(out_file, fmt, ap);
69 fprintf(out_file, "\n");
70 } else {
71#endif /* CONFIG_DEBUG_FILE */
72 vprintf(fmt, ap);
73 printf("\n");
74#ifdef CONFIG_DEBUG_FILE
75 }
76#endif /* CONFIG_DEBUG_FILE */
77 }
78 va_end(ap);
79}
80
81
82static void _wpa_hexdump(int level, const char *title, const u8 *buf,
83 size_t len, int show)
84{
85 size_t i;
86 if (level < wpa_debug_level)
87 return;
88 wpa_debug_print_timestamp();
89#ifdef CONFIG_DEBUG_FILE
90 if (out_file) {
91 fprintf(out_file, "%s - hexdump(len=%lu):",
92 title, (unsigned long) len);
93 if (buf == NULL) {
94 fprintf(out_file, " [NULL]");
95 } else if (show) {
96 for (i = 0; i < len; i++)
97 fprintf(out_file, " %02x", buf[i]);
98 } else {
99 fprintf(out_file, " [REMOVED]");
100 }
101 fprintf(out_file, "\n");
102 } else {
103#endif /* CONFIG_DEBUG_FILE */
104 printf("%s - hexdump(len=%lu):", title, (unsigned long) len);
105 if (buf == NULL) {
106 printf(" [NULL]");
107 } else if (show) {
108 for (i = 0; i < len; i++)
109 printf(" %02x", buf[i]);
110 } else {
111 printf(" [REMOVED]");
112 }
113 printf("\n");
114#ifdef CONFIG_DEBUG_FILE
115 }
116#endif /* CONFIG_DEBUG_FILE */
117}
118
119void wpa_hexdump(int level, const char *title, const u8 *buf, size_t len)
120{
121 _wpa_hexdump(level, title, buf, len, 1);
122}
123
124
125void wpa_hexdump_key(int level, const char *title, const u8 *buf, size_t len)
126{
127 _wpa_hexdump(level, title, buf, len, wpa_debug_show_keys);
128}
129
130
131static void _wpa_hexdump_ascii(int level, const char *title, const u8 *buf,
132 size_t len, int show)
133{
134 size_t i, llen;
135 const u8 *pos = buf;
136 const size_t line_len = 16;
137
138 if (level < wpa_debug_level)
139 return;
140 wpa_debug_print_timestamp();
141#ifdef CONFIG_DEBUG_FILE
142 if (out_file) {
143 if (!show) {
144 fprintf(out_file,
145 "%s - hexdump_ascii(len=%lu): [REMOVED]\n",
146 title, (unsigned long) len);
147 return;
148 }
149 if (buf == NULL) {
150 fprintf(out_file,
151 "%s - hexdump_ascii(len=%lu): [NULL]\n",
152 title, (unsigned long) len);
153 return;
154 }
155 fprintf(out_file, "%s - hexdump_ascii(len=%lu):\n",
156 title, (unsigned long) len);
157 while (len) {
158 llen = len > line_len ? line_len : len;
159 fprintf(out_file, " ");
160 for (i = 0; i < llen; i++)
161 fprintf(out_file, " %02x", pos[i]);
162 for (i = llen; i < line_len; i++)
163 fprintf(out_file, " ");
164 fprintf(out_file, " ");
165 for (i = 0; i < llen; i++) {
166 if (isprint(pos[i]))
167 fprintf(out_file, "%c", pos[i]);
168 else
169 fprintf(out_file, "_");
170 }
171 for (i = llen; i < line_len; i++)
172 fprintf(out_file, " ");
173 fprintf(out_file, "\n");
174 pos += llen;
175 len -= llen;
176 }
177 } else {
178#endif /* CONFIG_DEBUG_FILE */
179 if (!show) {
180 printf("%s - hexdump_ascii(len=%lu): [REMOVED]\n",
181 title, (unsigned long) len);
182 return;
183 }
184 if (buf == NULL) {
185 printf("%s - hexdump_ascii(len=%lu): [NULL]\n",
186 title, (unsigned long) len);
187 return;
188 }
189 printf("%s - hexdump_ascii(len=%lu):\n", title, (unsigned long) len);
190 while (len) {
191 llen = len > line_len ? line_len : len;
192 printf(" ");
193 for (i = 0; i < llen; i++)
194 printf(" %02x", pos[i]);
195 for (i = llen; i < line_len; i++)
196 printf(" ");
197 printf(" ");
198 for (i = 0; i < llen; i++) {
199 if (isprint(pos[i]))
200 printf("%c", pos[i]);
201 else
202 printf("_");
203 }
204 for (i = llen; i < line_len; i++)
205 printf(" ");
206 printf("\n");
207 pos += llen;
208 len -= llen;
209 }
210#ifdef CONFIG_DEBUG_FILE
211 }
212#endif /* CONFIG_DEBUG_FILE */
213}
214
215
216void wpa_hexdump_ascii(int level, const char *title, const u8 *buf, size_t len)
217{
218 _wpa_hexdump_ascii(level, title, buf, len, 1);
219}
220
221
222void wpa_hexdump_ascii_key(int level, const char *title, const u8 *buf,
223 size_t len)
224{
225 _wpa_hexdump_ascii(level, title, buf, len, wpa_debug_show_keys);
226}
227
228
229int wpa_debug_open_file(const char *path)
230{
231#ifdef CONFIG_DEBUG_FILE
232 if (!path)
233 return 0;
234 out_file = fopen(path, "a");
235 if (out_file == NULL) {
236 wpa_printf(MSG_ERROR, "wpa_debug_open_file: Failed to open "
237 "output file, using standard output");
238 return -1;
239 }
240#ifndef _WIN32
241 setvbuf(out_file, NULL, _IOLBF, 0);
242#endif /* _WIN32 */
243#endif /* CONFIG_DEBUG_FILE */
244 return 0;
245}
246
247
248void wpa_debug_close_file(void)
249{
250#ifdef CONFIG_DEBUG_FILE
251 if (!out_file)
252 return;
253 fclose(out_file);
254 out_file = NULL;
255#endif /* CONFIG_DEBUG_FILE */
256}
257
258#endif /* CONFIG_NO_STDOUT_DEBUG */
259
260
261#ifndef CONFIG_NO_WPA_MSG
262static wpa_msg_cb_func wpa_msg_cb = NULL;
263
264void wpa_msg_register_cb(wpa_msg_cb_func func)
265{
266 wpa_msg_cb = func;
267}
268
269
270void wpa_msg(void *ctx, int level, char *fmt, ...)
271{
272 va_list ap;
273 char *buf;
274 const int buflen = 2048;
275 int len;
276
277 buf = os_malloc(buflen);
278 if (buf == NULL) {
279 wpa_printf(MSG_ERROR, "wpa_msg: Failed to allocate message "
280 "buffer");
281 return;
282 }
283 va_start(ap, fmt);
284 len = vsnprintf(buf, buflen, fmt, ap);
285 va_end(ap);
286 wpa_printf(level, "%s", buf);
287 if (wpa_msg_cb)
288 wpa_msg_cb(ctx, level, buf, len);
289 os_free(buf);
290}
291#endif /* CONFIG_NO_WPA_MSG */
292
293
294#ifndef CONFIG_NO_HOSTAPD_LOGGER
295static hostapd_logger_cb_func hostapd_logger_cb = NULL;
296
297void hostapd_logger_register_cb(hostapd_logger_cb_func func)
298{
299 hostapd_logger_cb = func;
300}
301
302
303void hostapd_logger(void *ctx, const u8 *addr, unsigned int module, int level,
304 const char *fmt, ...)
305{
306 va_list ap;
307 char *buf;
308 const int buflen = 2048;
309 int len;
310
311 buf = os_malloc(buflen);
312 if (buf == NULL) {
313 wpa_printf(MSG_ERROR, "hostapd_logger: Failed to allocate "
314 "message buffer");
315 return;
316 }
317 va_start(ap, fmt);
318 len = vsnprintf(buf, buflen, fmt, ap);
319 va_end(ap);
320 if (hostapd_logger_cb)
321 hostapd_logger_cb(ctx, addr, module, level, buf, len);
322 else
323 wpa_printf(MSG_DEBUG, "hostapd_logger: %s", buf);
324 os_free(buf);
325}
326#endif /* CONFIG_NO_HOSTAPD_LOGGER */