Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * Copyright (c) 2018-2021 Yubico AB. All rights reserved. |
3 | | * Use of this source code is governed by a BSD-style |
4 | | * license that can be found in the LICENSE file. |
5 | | * SPDX-License-Identifier: BSD-2-Clause |
6 | | */ |
7 | | |
8 | | #undef _GNU_SOURCE /* XSI strerror_r() */ |
9 | | |
10 | | #include <stdarg.h> |
11 | | #include <stdio.h> |
12 | | |
13 | | #include "fido.h" |
14 | | |
15 | | #ifndef FIDO_NO_DIAGNOSTIC |
16 | | |
17 | | #define XXDLEN 32 |
18 | | #define XXDROW 128 |
19 | | #define LINELEN 256 |
20 | | |
21 | | #ifndef TLS |
22 | | #define TLS |
23 | | #endif |
24 | | |
25 | | static TLS int logging; |
26 | | static TLS fido_log_handler_t *log_handler; |
27 | | |
28 | | static void |
29 | | log_on_stderr(const char *str) |
30 | 0 | { |
31 | 0 | fprintf(stderr, "%s", str); |
32 | 0 | } |
33 | | |
34 | | static void |
35 | | do_log(const char *suffix, const char *fmt, va_list args) |
36 | 15.9M | { |
37 | 15.9M | char line[LINELEN], body[LINELEN]; |
38 | | |
39 | 15.9M | vsnprintf(body, sizeof(body), fmt, args); |
40 | | |
41 | 15.9M | if (suffix != NULL) |
42 | 2.77M | snprintf(line, sizeof(line), "%.180s: %.70s\n", body, suffix); |
43 | 13.2M | else |
44 | 13.2M | snprintf(line, sizeof(line), "%.180s\n", body); |
45 | | |
46 | 15.9M | log_handler(line); |
47 | 15.9M | } |
48 | | |
49 | | void |
50 | | fido_log_init(void) |
51 | 30.1k | { |
52 | 30.1k | logging = 1; |
53 | 30.1k | log_handler = log_on_stderr; |
54 | 30.1k | } |
55 | | |
56 | | void |
57 | | fido_log_debug(const char *fmt, ...) |
58 | 13.2M | { |
59 | 13.2M | va_list args; |
60 | | |
61 | 13.2M | if (!logging || log_handler == NULL) |
62 | 0 | return; |
63 | | |
64 | 13.2M | va_start(args, fmt); |
65 | 13.2M | do_log(NULL, fmt, args); |
66 | 13.2M | va_end(args); |
67 | 13.2M | } |
68 | | |
69 | | void |
70 | | fido_log_xxd(const void *buf, size_t count, const char *fmt, ...) |
71 | 2.03M | { |
72 | 2.03M | const uint8_t *ptr = buf; |
73 | 2.03M | char row[XXDROW], xxd[XXDLEN]; |
74 | 2.03M | va_list args; |
75 | | |
76 | 2.03M | if (!logging || log_handler == NULL) |
77 | 0 | return; |
78 | | |
79 | 2.03M | snprintf(row, sizeof(row), "buf=%p, len=%zu", buf, count); |
80 | 2.03M | va_start(args, fmt); |
81 | 2.03M | do_log(row, fmt, args); |
82 | 2.03M | va_end(args); |
83 | 2.03M | *row = '\0'; |
84 | | |
85 | 72.4M | for (size_t i = 0; i < count; i++) { |
86 | 70.4M | *xxd = '\0'; |
87 | 70.4M | if (i % 16 == 0) |
88 | 5.19M | snprintf(xxd, sizeof(xxd), "%04zu: %02x", i, *ptr++); |
89 | 65.2M | else |
90 | 65.2M | snprintf(xxd, sizeof(xxd), " %02x", *ptr++); |
91 | 70.4M | strlcat(row, xxd, sizeof(row)); |
92 | 70.4M | if (i % 16 == 15 || i == count - 1) { |
93 | 5.19M | fido_log_debug("%s", row); |
94 | 5.19M | *row = '\0'; |
95 | 5.19M | } |
96 | 70.4M | } |
97 | 2.03M | } |
98 | | |
99 | | void |
100 | | fido_log_error(int errnum, const char *fmt, ...) |
101 | 734k | { |
102 | 734k | char errstr[LINELEN]; |
103 | 734k | va_list args; |
104 | | |
105 | 734k | if (!logging || log_handler == NULL) |
106 | 0 | return; |
107 | 734k | if (strerror_r(errnum, errstr, sizeof(errstr)) != 0) |
108 | 0 | snprintf(errstr, sizeof(errstr), "error %d", errnum); |
109 | | |
110 | 734k | va_start(args, fmt); |
111 | 734k | do_log(errstr, fmt, args); |
112 | 734k | va_end(args); |
113 | 734k | } |
114 | | |
115 | | void |
116 | | fido_set_log_handler(fido_log_handler_t *handler) |
117 | 30.1k | { |
118 | 30.1k | if (handler != NULL) |
119 | 30.1k | log_handler = handler; |
120 | 30.1k | } |
121 | | |
122 | | #endif /* !FIDO_NO_DIAGNOSTIC */ |