Directory: | ./ |
---|---|
File: | pdserv/src/Session.cpp |
Date: | 2024-11-17 04:08:36 |
Exec | Total | Coverage | |
---|---|---|---|
Lines: | 212 | 290 | 73.1% |
Branches: | 274 | 851 | 32.2% |
Line | Branch | Exec | Source |
---|---|---|---|
1 | /***************************************************************************** | ||
2 | * | ||
3 | * $Id$ | ||
4 | * | ||
5 | * Copyright 2010 Richard Hacker (lerichi at gmx dot net) | ||
6 | * | ||
7 | * This file is part of the pdserv library. | ||
8 | * | ||
9 | * The pdserv library is free software: you can redistribute it and/or modify | ||
10 | * it under the terms of the GNU Lesser General Public License as published | ||
11 | * by the Free Software Foundation, either version 3 of the License, or (at | ||
12 | * your option) any later version. | ||
13 | * | ||
14 | * The pdserv library is distributed in the hope that it will be useful, but | ||
15 | * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY | ||
16 | * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public | ||
17 | * License for more details. | ||
18 | * | ||
19 | * You should have received a copy of the GNU Lesser General Public License | ||
20 | * along with the pdserv library. If not, see <http://www.gnu.org/licenses/>. | ||
21 | * | ||
22 | *****************************************************************************/ | ||
23 | |||
24 | #include "Session.h" | ||
25 | #include "Main.h" | ||
26 | #include "Debug.h" | ||
27 | |||
28 | #include <sasl/saslutil.h> | ||
29 | #include <cerrno> | ||
30 | #include <cstring> // strerror() | ||
31 | #include <log4cplus/logger.h> | ||
32 | #include <log4cplus/loggingmacros.h> | ||
33 | |||
34 | #ifdef GNUTLS_FOUND | ||
35 | # include <gnutls/x509.h> | ||
36 | # include "TLS.h" | ||
37 | #endif | ||
38 | |||
39 | using namespace PdServ; | ||
40 | |||
41 | // Initialize SASL server. There are no callbacks, as well as an | ||
42 | // empty name so that no default configuration file is searched for | ||
43 | 3 | const int Session::saslServerInit = sasl_server_init(NULL, NULL); | |
44 | |||
45 | ///////////////////////////////////////////////////////////////////////////// | ||
46 | 148 | Session::Session(const Main *m, log4cplus::Logger& log, size_t bufsize) | |
47 | 148 | : main(m), log(log) | |
48 | { | ||
49 | 148 | conn = 0; | |
50 | 148 | p_eof = false; | |
51 | 148 | p_loggedIn = false; | |
52 | |||
53 |
1/2✓ Branch 24 taken 148 times.
✗ Branch 25 not taken.
|
148 | main->gettime(&connectedTime); |
54 |
1/2✓ Branch 24 taken 148 times.
✗ Branch 25 not taken.
|
148 | main->prepare(this); |
55 | |||
56 |
1/2✓ Branch 1 taken 148 times.
✗ Branch 2 not taken.
|
148 | char* buf = new char[bufsize]; |
57 |
1/2✓ Branch 4 taken 148 times.
✗ Branch 5 not taken.
|
148 | setp(buf, buf + bufsize); |
58 | 148 | } | |
59 | |||
60 | ///////////////////////////////////////////////////////////////////////////// | ||
61 | 296 | Session::~Session() | |
62 | { | ||
63 | 148 | saslDispose(); | |
64 | |||
65 | 148 | main->cleanup(this); | |
66 |
1/2✓ Branch 4 taken 148 times.
✗ Branch 5 not taken.
|
148 | delete[] pbase(); |
67 | 148 | } | |
68 | |||
69 | ///////////////////////////////////////////////////////////////////////////// | ||
70 | 30 | bool Session::saslInit() | |
71 | { | ||
72 |
1/2✓ Branch 4 taken 30 times.
✗ Branch 5 not taken.
|
60 | std::string remoteip = peerAddr(';'); |
73 |
1/2✓ Branch 4 taken 30 times.
✗ Branch 5 not taken.
|
60 | std::string localip = localAddr(';'); |
74 | |||
75 |
9/18✓ Branch 8 taken 30 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 30 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 30 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 30 times.
✗ Branch 18 not taken.
✓ Branch 20 taken 30 times.
✗ Branch 21 not taken.
✓ Branch 23 taken 30 times.
✗ Branch 24 not taken.
✓ Branch 26 taken 30 times.
✗ Branch 27 not taken.
✓ Branch 30 taken 30 times.
✗ Branch 31 not taken.
✓ Branch 34 taken 30 times.
✗ Branch 35 not taken.
|
30 | LOG4CPLUS_DEBUG(log, |
76 | LOG4CPLUS_TEXT("Creating new login session for remoteip=") | ||
77 | << LOG4CPLUS_STRING_TO_TSTRING(remoteip) | ||
78 | << LOG4CPLUS_TEXT(" localip=") | ||
79 | << LOG4CPLUS_STRING_TO_TSTRING(localip)); | ||
80 | |||
81 | // Make sure sasl_server_init() was successful | ||
82 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 30 times.
|
30 | if (saslServerInit != SASL_OK) { |
83 | ✗ | LOG4CPLUS_ERROR(log, | |
84 | LOG4CPLUS_TEXT("Could not initialize SASL server: ") | ||
85 | << LOG4CPLUS_C_STR_TO_TSTRING( | ||
86 | sasl_errstring(saslServerInit, NULL, NULL))); | ||
87 | ✗ | return true; | |
88 | } | ||
89 | |||
90 | // Setup callbacks. Only use SASL_CB_GETOPT | ||
91 | typedef int (*cb_t)(void); | ||
92 | static const sasl_callback_t _cb[CB_SIZE] = { | ||
93 | {SASL_CB_LOG, cb_t((void*)sasl_log), 0}, | ||
94 | {SASL_CB_GETOPT, cb_t((void*)sasl_getopt), 0}, | ||
95 | {SASL_CB_LIST_END, 0, 0}, | ||
96 | }; | ||
97 |
2/2✓ Branch 0 taken 60 times.
✓ Branch 1 taken 30 times.
|
90 | for (size_t i = 0; i < CB_SIZE-1; ++i) { |
98 | 60 | sasl_callbacks[i] = _cb[i]; | |
99 | 60 | sasl_callbacks[i].context = this; | |
100 | } | ||
101 | 30 | sasl_callbacks[0].context = const_cast<log4cplus::Logger*>(&log); | |
102 | 30 | const std::string default_realm = | |
103 |
4/8✓ Branch 15 taken 30 times.
✗ Branch 16 not taken.
✓ Branch 18 taken 30 times.
✗ Branch 19 not taken.
✓ Branch 21 taken 30 times.
✗ Branch 22 not taken.
✓ Branch 27 taken 30 times.
✗ Branch 28 not taken.
|
60 | main->config("access")["sasl"]["default_realm"].toString(); |
104 | |||
105 | 30 | const std::string service_name = | |
106 |
5/10✓ Branch 15 taken 30 times.
✗ Branch 16 not taken.
✓ Branch 18 taken 30 times.
✗ Branch 19 not taken.
✓ Branch 21 taken 30 times.
✗ Branch 22 not taken.
✓ Branch 27 taken 30 times.
✗ Branch 28 not taken.
✓ Branch 31 taken 30 times.
✗ Branch 32 not taken.
|
60 | main->config("access")["sasl"]["service_name"].toString("pdserv"); |
107 | |||
108 | // Create a new login session | ||
109 |
2/2✓ Branch 2 taken 2 times.
✓ Branch 3 taken 28 times.
|
60 | int result = sasl_server_new(service_name.c_str(), |
110 | NULL, /* serverFQDN; null = use gethostname() */ | ||
111 | /* user realm, null = use gethostname() */ | ||
112 | 30 | default_realm.empty() ? nullptr : default_realm.c_str(), | |
113 | localip.c_str(), /* Local IP */ | ||
114 | remoteip.c_str(), /* Remote IP */ | ||
115 | sasl_callbacks, | ||
116 | SASL_SUCCESS_DATA, | ||
117 |
1/2✓ Branch 1 taken 30 times.
✗ Branch 2 not taken.
|
30 | &conn); |
118 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 30 times.
|
30 | if (result != SASL_OK) { |
119 | ✗ | LOG4CPLUS_ERROR(log, | |
120 | LOG4CPLUS_TEXT("Could not create new SASL server instance: ") | ||
121 | << LOG4CPLUS_C_STR_TO_TSTRING(sasl_errstring(result,0,0))); | ||
122 | ✗ | return true; | |
123 | } | ||
124 | |||
125 | 30 | return false; | |
126 | } | ||
127 | |||
128 | ///////////////////////////////////////////////////////////////////////////// | ||
129 | 32 | const char* Session::saslMechanisms() | |
130 | { | ||
131 |
5/8✓ Branch 3 taken 30 times.
✓ Branch 4 taken 2 times.
✓ Branch 9 taken 30 times.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
✓ Branch 12 taken 30 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 32 times.
|
32 | if (!conn and saslInit()) |
132 | ✗ | return 0; | |
133 | |||
134 | // Send the mechanisms back. | ||
135 | // This is a space separated list of words, no prefix or suffix | ||
136 | 32 | const char* mechanisms; | |
137 | 32 | int result = sasl_listmech(conn, | |
138 | NULL, // user | ||
139 | NULL, // prefix | ||
140 | NULL, // space | ||
141 | NULL, // suffix | ||
142 | &mechanisms, | ||
143 | NULL, // plen | ||
144 |
1/2✓ Branch 1 taken 32 times.
✗ Branch 2 not taken.
|
32 | NULL); // pcount |
145 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 32 times.
|
32 | if (SASL_OK != result) { |
146 | ✗ | LOG4CPLUS_ERROR(log, | |
147 | LOG4CPLUS_TEXT("Could not create new SASL server instance: ") | ||
148 | << LOG4CPLUS_C_STR_TO_TSTRING(sasl_errstring(result,0,0))); | ||
149 | ✗ | return NULL; | |
150 | } | ||
151 |
8/16✓ Branch 8 taken 32 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 32 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 32 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 32 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 32 times.
✗ Branch 24 not taken.
✓ Branch 27 taken 32 times.
✗ Branch 28 not taken.
✓ Branch 35 taken 32 times.
✗ Branch 36 not taken.
✓ Branch 39 taken 32 times.
✗ Branch 40 not taken.
|
32 | LOG4CPLUS_DEBUG(log, |
152 | LOG4CPLUS_TEXT("Available SASL authentication mechanisms: ") | ||
153 | << LOG4CPLUS_C_STR_TO_TSTRING(mechanisms)); | ||
154 | |||
155 | 32 | return mechanisms; | |
156 | } | ||
157 | |||
158 | ///////////////////////////////////////////////////////////////////////////// | ||
159 | 149 | void Session::saslDispose() | |
160 | { | ||
161 | 149 | sasl_dispose(&conn); | |
162 | 149 | p_loggedIn = false; | |
163 | 149 | conn = 0; | |
164 | 149 | } | |
165 | |||
166 | ///////////////////////////////////////////////////////////////////////////// | ||
167 | 59 | bool Session::saslProcess( | |
168 | const char* mech, const char* response, const std::string** serverout) | ||
169 | { | ||
170 | int result; | ||
171 | 59 | const char* out; | |
172 | 59 | unsigned int outlen; | |
173 | |||
174 |
3/4✓ Branch 0 taken 28 times.
✓ Branch 1 taken 31 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 28 times.
|
59 | unsigned int inlen = response ? strlen(response) : 0; |
175 | 59 | unsigned int buflen = inlen/4*3 + 1; | |
176 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 59 times.
|
59 | char clientout[buflen]; |
177 | 59 | unsigned int clientoutlen; | |
178 | |||
179 | 59 | *serverout = NULL; | |
180 | |||
181 |
1/2✗ Branch 3 not taken.
✓ Branch 4 taken 59 times.
|
59 | if (!conn) { |
182 | ✗ | p_loggedIn = false; | |
183 | |||
184 | ✗ | if (saslInit()) | |
185 | ✗ | return false; | |
186 | } | ||
187 | |||
188 | // First decode client base64 coded response | ||
189 |
1/2✓ Branch 1 taken 59 times.
✗ Branch 2 not taken.
|
59 | result = sasl_decode64(response, inlen, clientout, buflen, &clientoutlen); |
190 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 59 times.
|
59 | if (SASL_OK != result) { |
191 | ✗ | LOG4CPLUS_ERROR(log, | |
192 | LOG4CPLUS_TEXT("Could not decode client base64 coded string: ") | ||
193 | << LOG4CPLUS_C_STR_TO_TSTRING(sasl_errstring(result,0,0))); | ||
194 | ✗ | return false; | |
195 | } | ||
196 | |||
197 | 59 | if (clientoutlen) | |
198 | LOG4CPLUS_TRACE(log, | ||
199 | LOG4CPLUS_TEXT("SASL: Receive client reply: ") | ||
200 | << LOG4CPLUS_STRING_TO_TSTRING( | ||
201 | std::string(clientout,clientoutlen))); | ||
202 | |||
203 | // If mech is not null, this is the first step in authentication | ||
204 | // otherwise it is another step | ||
205 |
2/2✓ Branch 0 taken 31 times.
✓ Branch 1 taken 28 times.
|
59 | if (mech) { |
206 |
8/16✓ Branch 8 taken 31 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 31 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 31 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 31 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 31 times.
✗ Branch 24 not taken.
✓ Branch 27 taken 31 times.
✗ Branch 28 not taken.
✓ Branch 35 taken 31 times.
✗ Branch 36 not taken.
✓ Branch 39 taken 31 times.
✗ Branch 40 not taken.
|
31 | LOG4CPLUS_DEBUG(log, |
207 | LOG4CPLUS_TEXT("Login: using mechanism ") | ||
208 | << LOG4CPLUS_C_STR_TO_TSTRING(mech)); | ||
209 |
2/4✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
✓ Branch 6 taken 31 times.
✗ Branch 7 not taken.
|
31 | result = sasl_server_start(conn, mech, |
210 | response ? clientout : 0, clientoutlen, | ||
211 | &out, &outlen); | ||
212 | } | ||
213 | else { | ||
214 |
1/2✓ Branch 4 taken 28 times.
✗ Branch 5 not taken.
|
28 | result = sasl_server_step(conn, |
215 | clientout, clientoutlen, | ||
216 | &out, &outlen); | ||
217 | } | ||
218 | |||
219 |
11/22✓ Branch 8 taken 59 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 59 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 59 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 59 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 59 times.
✗ Branch 24 not taken.
✓ Branch 26 taken 59 times.
✗ Branch 27 not taken.
✓ Branch 32 taken 59 times.
✗ Branch 33 not taken.
✓ Branch 36 taken 59 times.
✗ Branch 37 not taken.
✓ Branch 42 taken 59 times.
✗ Branch 43 not taken.
✓ Branch 46 taken 59 times.
✗ Branch 47 not taken.
✓ Branch 50 taken 59 times.
✗ Branch 51 not taken.
|
59 | LOG4CPLUS_DEBUG(log, |
220 | LOG4CPLUS_TEXT("Login: result ") | ||
221 | << result << ' ' << (void*)out << ' ' << outlen); | ||
222 | |||
223 |
2/2✓ Branch 0 taken 24 times.
✓ Branch 1 taken 35 times.
|
59 | if (result == SASL_OK) { |
224 | 24 | const char* str; | |
225 | 24 | const void** strp = (const void**)&str; | |
226 | |||
227 | const char* userName = | ||
228 |
2/4✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 24 times.
✗ Branch 7 not taken.
|
48 | (SASL_OK == sasl_getprop(conn, SASL_USERNAME, strp) and str) |
229 |
1/2✓ Branch 0 taken 24 times.
✗ Branch 1 not taken.
|
48 | ? str : "unknown_user"; |
230 | |||
231 |
8/16✓ Branch 8 taken 24 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 24 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 24 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 24 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 24 times.
✗ Branch 24 not taken.
✓ Branch 27 taken 24 times.
✗ Branch 28 not taken.
✓ Branch 35 taken 24 times.
✗ Branch 36 not taken.
✓ Branch 39 taken 24 times.
✗ Branch 40 not taken.
|
24 | LOG4CPLUS_INFO(log, |
232 | LOG4CPLUS_TEXT("Successfully logged in ") | ||
233 | << LOG4CPLUS_C_STR_TO_TSTRING(userName)); | ||
234 | |||
235 |
2/4✓ Branch 7 taken 24 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 24 times.
✗ Branch 10 not taken.
|
24 | if (log.isEnabledFor(log4cplus::DEBUG_LOG_LEVEL)) { |
236 |
1/2✓ Branch 2 taken 24 times.
✗ Branch 3 not taken.
|
48 | std::ostringstream os; |
237 | |||
238 |
4/8✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 24 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 24 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 24 times.
✗ Branch 11 not taken.
|
24 | if (SASL_OK == sasl_getprop(conn, SASL_AUTHUSER, strp) and str) |
239 |
2/4✓ Branch 1 taken 24 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
|
24 | os << " authname=" << str; |
240 | |||
241 |
4/8✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 24 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 24 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 24 times.
✗ Branch 11 not taken.
|
24 | if (SASL_OK == sasl_getprop(conn, SASL_MECHNAME, strp) and str) |
242 |
2/4✓ Branch 1 taken 24 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
|
24 | os << " mechanism=" << str; |
243 | |||
244 |
6/8✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 24 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 23 times.
✓ Branch 9 taken 1 times.
✓ Branch 10 taken 23 times.
✓ Branch 11 taken 1 times.
|
24 | if (SASL_OK == sasl_getprop(conn, SASL_DEFUSERREALM, strp) and str) |
245 |
2/4✓ Branch 1 taken 23 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 23 times.
✗ Branch 5 not taken.
|
23 | os << " realm=" << str; |
246 | |||
247 |
4/8✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 24 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 24 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 24 times.
✗ Branch 11 not taken.
|
24 | if (SASL_OK == sasl_getprop(conn, SASL_IPREMOTEPORT, strp) and str) |
248 |
2/4✓ Branch 1 taken 24 times.
✗ Branch 2 not taken.
✓ Branch 4 taken 24 times.
✗ Branch 5 not taken.
|
24 | os << " remoteip=" << str; |
249 | |||
250 |
1/2✓ Branch 9 taken 24 times.
✗ Branch 10 not taken.
|
48 | log.forcedLog(log4cplus::DEBUG_LOG_LEVEL, |
251 |
1/2✓ Branch 1 taken 24 times.
✗ Branch 2 not taken.
|
48 | LOG4CPLUS_STRING_TO_TSTRING(os.str())); |
252 | } | ||
253 | |||
254 | 24 | p_loggedIn = true; | |
255 | } | ||
256 |
2/2✓ Branch 0 taken 4 times.
✓ Branch 1 taken 31 times.
|
35 | else if (result != SASL_CONTINUE) { |
257 | 4 | const char* str; | |
258 | 4 | const void** sptr = (const void**)&str; | |
259 | |||
260 | const char* userName = | ||
261 |
2/4✓ Branch 4 taken 4 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 4 times.
✗ Branch 7 not taken.
|
8 | (SASL_OK == sasl_getprop(conn, SASL_USERNAME, sptr) and str) |
262 |
1/2✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
|
8 | ? str : "unknown_user"; |
263 | |||
264 | const char* authSrc = | ||
265 |
2/4✓ Branch 4 taken 4 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 4 times.
✗ Branch 7 not taken.
|
8 | (SASL_OK == sasl_getprop(conn, SASL_AUTHSOURCE, sptr) and str) |
266 |
1/2✓ Branch 0 taken 4 times.
✗ Branch 1 not taken.
|
8 | ? str : "unknown"; |
267 | |||
268 |
15/30✓ Branch 8 taken 4 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 4 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 4 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 4 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 4 times.
✗ Branch 24 not taken.
✓ Branch 27 taken 4 times.
✗ Branch 28 not taken.
✓ Branch 30 taken 4 times.
✗ Branch 31 not taken.
✓ Branch 36 taken 4 times.
✗ Branch 37 not taken.
✓ Branch 40 taken 4 times.
✗ Branch 41 not taken.
✓ Branch 43 taken 4 times.
✗ Branch 44 not taken.
✓ Branch 52 taken 4 times.
✗ Branch 53 not taken.
✓ Branch 55 taken 4 times.
✗ Branch 56 not taken.
✓ Branch 59 taken 4 times.
✗ Branch 60 not taken.
✓ Branch 75 taken 4 times.
✗ Branch 76 not taken.
✓ Branch 79 taken 4 times.
✗ Branch 80 not taken.
|
4 | LOG4CPLUS_ERROR(log, |
269 | LOG4CPLUS_TEXT("Login failed for user ") | ||
270 | << LOG4CPLUS_C_STR_TO_TSTRING(userName) | ||
271 | << LOG4CPLUS_TEXT(" using ") | ||
272 | << LOG4CPLUS_C_STR_TO_TSTRING(authSrc) | ||
273 | << LOG4CPLUS_TEXT(": ") | ||
274 | << LOG4CPLUS_C_STR_TO_TSTRING(sasl_errdetail(conn))); | ||
275 | 4 | return false; | |
276 | } | ||
277 | |||
278 |
2/2✓ Branch 0 taken 31 times.
✓ Branch 1 taken 24 times.
|
55 | if (outlen) { |
279 | 31 | buflen = (outlen+2)/3*4 + 1; | |
280 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
|
31 | char outbuf[buflen]; |
281 |
1/2✓ Branch 1 taken 31 times.
✗ Branch 2 not taken.
|
31 | int rv = sasl_encode64(out, outlen, outbuf, buflen, &buflen); |
282 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 31 times.
|
31 | if (rv != SASL_OK) { |
283 | ✗ | LOG4CPLUS_ERROR(log, | |
284 | LOG4CPLUS_TEXT("Could not base64-encode string: ") | ||
285 | << LOG4CPLUS_C_STR_TO_TSTRING(sasl_errstring(rv,0,0))); | ||
286 | ✗ | return false; | |
287 | } | ||
288 |
1/2✓ Branch 2 taken 31 times.
✗ Branch 3 not taken.
|
31 | sasl_reply.assign(outbuf, buflen); |
289 | 31 | *serverout = &sasl_reply; | |
290 | LOG4CPLUS_TRACE(log, | ||
291 | LOG4CPLUS_TEXT("SASL: Sending challenge ") | ||
292 | 31 | << LOG4CPLUS_STRING_TO_TSTRING(std::string(out,outlen))); | |
293 | } | ||
294 | |||
295 | 114 | return result == SASL_OK; | |
296 | } | ||
297 | |||
298 | /////////////////////////////////////////////////////////////////////////// | ||
299 | // man: sasl_log_t | ||
300 | 3 | int Session::sasl_log(void *context, int level, | |
301 | const char *message) | ||
302 | { | ||
303 | log4cplus::LogLevel log4cpluslevel; | ||
304 |
1/7✗ Branch 0 not taken.
✗ Branch 1 not taken.
✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
|
3 | switch (level) { |
305 | ✗ | case SASL_LOG_NONE: /* don't log anything */ | |
306 | ✗ | log4cpluslevel = log4cplus::OFF_LOG_LEVEL; | |
307 | ✗ | break; | |
308 | |||
309 | ✗ | case SASL_LOG_ERR: /* log unusual errors (default) */ | |
310 | ✗ | log4cpluslevel = log4cplus::FATAL_LOG_LEVEL; | |
311 | ✗ | break; | |
312 | |||
313 | 3 | case SASL_LOG_FAIL: /* log all authentication failures */ | |
314 | 3 | log4cpluslevel = log4cplus::ERROR_LOG_LEVEL; | |
315 | 3 | break; | |
316 | |||
317 | ✗ | case SASL_LOG_WARN: /* log non-fatal warnings */ | |
318 | ✗ | log4cpluslevel = log4cplus::WARN_LOG_LEVEL; | |
319 | ✗ | break; | |
320 | |||
321 | ✗ | case SASL_LOG_NOTE: /* more verbose than LOG_WARN */ | |
322 | ✗ | log4cpluslevel = log4cplus::INFO_LOG_LEVEL; | |
323 | ✗ | break; | |
324 | |||
325 | ✗ | case SASL_LOG_DEBUG: /* more verbose than LOG_NOTE */ | |
326 | ✗ | log4cpluslevel = log4cplus::DEBUG_LOG_LEVEL; | |
327 | ✗ | break; | |
328 | |||
329 | ✗ | case SASL_LOG_TRACE: /* traces of internal protocols */ | |
330 | case SASL_LOG_PASS: /* traces of internal protocols, including | ||
331 | * passwords */ | ||
332 | default: | ||
333 | ✗ | log4cpluslevel = log4cplus::TRACE_LOG_LEVEL; | |
334 | ✗ | break; | |
335 | } | ||
336 | |||
337 | 3 | log4cplus::Logger* logger = reinterpret_cast<log4cplus::Logger*>(context); | |
338 |
3/6✓ Branch 0 taken 3 times.
✗ Branch 1 not taken.
✓ Branch 6 taken 3 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 3 times.
✗ Branch 9 not taken.
|
3 | if (logger and logger->isEnabledFor(log4cpluslevel)) { |
339 |
1/2✓ Branch 2 taken 3 times.
✗ Branch 3 not taken.
|
6 | log4cplus::tostringstream os; |
340 | os << LOG4CPLUS_TEXT("SASL: ") | ||
341 |
3/6✓ Branch 1 taken 3 times.
✗ Branch 2 not taken.
✓ Branch 7 taken 3 times.
✗ Branch 8 not taken.
✓ Branch 11 taken 3 times.
✗ Branch 12 not taken.
|
3 | << LOG4CPLUS_C_STR_TO_TSTRING(message); |
342 |
2/4✓ Branch 5 taken 3 times.
✗ Branch 6 not taken.
✓ Branch 9 taken 3 times.
✗ Branch 10 not taken.
|
3 | logger->forcedLog(log4cpluslevel, os.str(), __FILE__, __LINE__); |
343 | } | ||
344 | |||
345 | 3 | return SASL_OK; | |
346 | } | ||
347 | |||
348 | /////////////////////////////////////////////////////////////////////////// | ||
349 | // man: sasl_getopt_t | ||
350 | 230 | int Session::sasl_getopt(void *context, const char* /*plugin_name*/, | |
351 | const char *option, const char **result, unsigned *len) | ||
352 | { | ||
353 | 230 | int rv = SASL_BADPARAM; | |
354 | log_debug("context=%p, option=%s, result=%p len=%p", | ||
355 | context, option, result, len); | ||
356 | 230 | Session* session = reinterpret_cast<Session*>(context); | |
357 | |||
358 |
2/4✓ Branch 0 taken 230 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 230 times.
✗ Branch 3 not taken.
|
230 | if (session and option) { |
359 |
2/4✓ Branch 5 taken 230 times.
✗ Branch 6 not taken.
✓ Branch 9 taken 230 times.
✗ Branch 10 not taken.
|
460 | SaslParam::iterator it = session->saslParam.find(option); |
360 |
2/2✓ Branch 6 taken 172 times.
✓ Branch 7 taken 58 times.
|
230 | if (it == session->saslParam.end()) { |
361 |
3/6✓ Branch 15 taken 172 times.
✗ Branch 16 not taken.
✓ Branch 18 taken 172 times.
✗ Branch 19 not taken.
✓ Branch 21 taken 172 times.
✗ Branch 22 not taken.
|
344 | Config param = session->main->config("access")["sasl"][option]; |
362 |
3/4✓ Branch 1 taken 172 times.
✗ Branch 2 not taken.
✓ Branch 3 taken 114 times.
✓ Branch 4 taken 58 times.
|
172 | if (param) |
363 |
1/2✓ Branch 3 taken 114 times.
✗ Branch 4 not taken.
|
342 | it = session->saslParam.insert( |
364 |
3/6✓ Branch 5 taken 114 times.
✗ Branch 6 not taken.
✓ Branch 12 taken 114 times.
✗ Branch 13 not taken.
✓ Branch 16 taken 114 times.
✗ Branch 17 not taken.
|
228 | std::make_pair(std::string(option), param.toString())) |
365 | 228 | .first; | |
366 | else { | ||
367 |
8/16✓ Branch 8 taken 58 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 58 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 58 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 58 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 58 times.
✗ Branch 24 not taken.
✓ Branch 27 taken 58 times.
✗ Branch 28 not taken.
✓ Branch 35 taken 58 times.
✗ Branch 36 not taken.
✓ Branch 39 taken 58 times.
✗ Branch 40 not taken.
|
58 | LOG4CPLUS_DEBUG(session->log, |
368 | LOG4CPLUS_TEXT("SASL parameter not specified: ") | ||
369 | << LOG4CPLUS_C_STR_TO_TSTRING(option)); | ||
370 | } | ||
371 | } | ||
372 |
2/2✓ Branch 6 taken 172 times.
✓ Branch 7 taken 58 times.
|
230 | if (it != session->saslParam.end()) { |
373 | 172 | *result = it->second.c_str(); | |
374 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 172 times.
|
172 | if (len) |
375 | ✗ | *len = it->second.size(); | |
376 | 172 | rv = SASL_OK; | |
377 | } | ||
378 | } | ||
379 | |||
380 | //#define STR(x) #x | ||
381 | //#define QUOTE(x) STR(x) | ||
382 | // if (!strcmp(option, "log_level") and rv != SASL_OK) { | ||
383 | // *result = QUOTE(SASL_LOG_PASS); | ||
384 | // log_debug("setting log level rv=%s", *result); | ||
385 | // rv = SASL_OK; | ||
386 | // } | ||
387 | |||
388 | 230 | return rv; | |
389 | } | ||
390 | |||
391 | ///////////////////////////////////////////////////////////////////////////// | ||
392 | 105 | bool Session::eof() const | |
393 | { | ||
394 |
1/2✗ Branch 3 not taken.
✓ Branch 4 taken 105 times.
|
105 | return p_eof; |
395 | } | ||
396 | |||
397 | ///////////////////////////////////////////////////////////////////////////// | ||
398 | 606 | bool Session::loggedIn() const | |
399 | { | ||
400 |
5/6✓ Branch 3 taken 142 times.
✓ Branch 4 taken 464 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 142 times.
✓ Branch 10 taken 81 times.
✓ Branch 11 taken 61 times.
|
606 | return conn and p_loggedIn; |
401 | } | ||
402 | |||
403 | ///////////////////////////////////////////////////////////////////////////// | ||
404 | ✗ | int Session::overflow(int value) | |
405 | { | ||
406 | ✗ | char c = value; | |
407 | ✗ | return xsputn(&c, 1) ? c : traits_type::eof(); | |
408 | } | ||
409 | |||
410 | ///////////////////////////////////////////////////////////////////////////// | ||
411 | 72792 | std::streamsize Session::xsputn(const char * buf, std::streamsize count) | |
412 | { | ||
413 | 72792 | const char* ptr = buf; | |
414 | |||
415 | ✗ | do { | |
416 | // Put data into buffer | ||
417 | 72792 | size_t n = std::min(epptr() - pptr(), count); | |
418 | 72792 | std::copy(ptr, ptr + n, pptr()); | |
419 | |||
420 | // Update pointers | ||
421 | 72792 | pbump(n); | |
422 | 72792 | ptr += n; | |
423 | 72792 | count -= n; | |
424 | |||
425 |
5/8✓ Branch 8 taken 2 times.
✓ Branch 9 taken 72790 times.
✓ Branch 14 taken 2 times.
✗ Branch 15 not taken.
✗ Branch 16 not taken.
✓ Branch 17 taken 72792 times.
✗ Branch 18 not taken.
✓ Branch 19 taken 72792 times.
|
72792 | } while (!(pptr() == epptr() and flush(true)) and count); |
426 | |||
427 | 72792 | return ptr - buf; | |
428 | } | ||
429 | |||
430 | ///////////////////////////////////////////////////////////////////////////// | ||
431 | 9723 | int Session::sync() | |
432 | { | ||
433 | 9723 | return flush(false); | |
434 | } | ||
435 | |||
436 | ///////////////////////////////////////////////////////////////////////////// | ||
437 | // Flush output buffer. | ||
438 | // | ||
439 | // partial: true: do only one flush pass | ||
440 | 9725 | int Session::flush(bool partial) | |
441 | { | ||
442 | 9725 | const char* buf = pbase(); | |
443 | 9725 | size_t count = pptr() - buf; | |
444 | |||
445 |
2/4✗ Branch 3 not taken.
✓ Branch 4 taken 9725 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 9725 times.
|
9725 | if (p_eof) |
446 | ✗ | return -1; | |
447 |
2/2✓ Branch 0 taken 8678 times.
✓ Branch 1 taken 1047 times.
|
9725 | else if (!count) |
448 | 8678 | return 0; | |
449 | |||
450 | // log_debug("flushing %i %zu", partial, count); | ||
451 | 1047 | ssize_t result = 0; | |
452 | ✗ | do { | |
453 | |||
454 | 1047 | result = write(buf, count); | |
455 | |||
456 | // log_debug("flushing result %i", result); | ||
457 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 1047 times.
|
1047 | if (result <= 0) |
458 | ✗ | break; | |
459 | |||
460 | 1047 | buf += result; | |
461 | 1047 | count -= result; | |
462 | |||
463 |
1/4✗ Branch 0 not taken.
✓ Branch 1 taken 1047 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
|
1047 | } while (count and !partial); |
464 | |||
465 | // Copy remaining data to buffer start and | ||
466 | // update std::streambuf's current put pointer pptr() | ||
467 | 1047 | std::copy(buf, const_cast<const char*>(pptr()), pbase()); | |
468 | 1047 | pbump(pbase() - buf); | |
469 | |||
470 | // Calculate EOF | ||
471 |
1/2✗ Branch 3 not taken.
✓ Branch 4 taken 1047 times.
|
2094 | p_eof |= !result |
472 |
2/6✓ Branch 0 taken 1047 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 1047 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
|
1047 | or (result < 0 and (result != -EAGAIN)); |
473 | |||
474 |
1/2✓ Branch 0 taken 1047 times.
✗ Branch 1 not taken.
|
1047 | if (result > 0) |
475 | 1047 | return 0; | |
476 | |||
477 | // Interpret EOF | ||
478 | ✗ | if (!result) | |
479 | ✗ | LOG4CPLUS_INFO_STR(log, | |
480 | LOG4CPLUS_TEXT("Client closed connection")); | ||
481 | ✗ | else if (result != -EAGAIN) | |
482 | ✗ | LOG4CPLUS_ERROR(log, | |
483 | LOG4CPLUS_TEXT("Network write() error: ") | ||
484 | << LOG4CPLUS_C_STR_TO_TSTRING(strerror(-result))); | ||
485 | |||
486 | ✗ | return -1; | |
487 | } | ||
488 | |||
489 | ///////////////////////////////////////////////////////////////////////////// | ||
490 | ✗ | int Session::underflow() | |
491 | { | ||
492 | ✗ | char c; | |
493 | ✗ | return xsgetn(&c, 1) == 1 ? c : traits_type::eof(); | |
494 | } | ||
495 | |||
496 | ///////////////////////////////////////////////////////////////////////////// | ||
497 | 8913 | std::streamsize Session::xsgetn(char* s, std::streamsize n) | |
498 | { | ||
499 | 8913 | const ssize_t result = read(s, n); | |
500 | |||
501 |
2/2✓ Branch 0 taken 8808 times.
✓ Branch 1 taken 105 times.
|
8913 | if (result > 0) |
502 | 8808 | return result; | |
503 | |||
504 | // Calculate EOF | ||
505 |
2/4✓ Branch 0 taken 105 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 105 times.
✗ Branch 3 not taken.
|
105 | if (!result and result != -EAGAIN) |
506 | 105 | p_eof = true; | |
507 | |||
508 | // Interpret EOF | ||
509 |
2/4✗ Branch 3 not taken.
✓ Branch 4 taken 105 times.
✓ Branch 5 taken 105 times.
✗ Branch 6 not taken.
|
105 | if (p_eof) { |
510 |
1/2✓ Branch 0 taken 105 times.
✗ Branch 1 not taken.
|
105 | if (!result) |
511 |
3/6✓ Branch 8 taken 105 times.
✗ Branch 9 not taken.
✓ Branch 14 taken 105 times.
✗ Branch 15 not taken.
✓ Branch 18 taken 105 times.
✗ Branch 19 not taken.
|
105 | LOG4CPLUS_INFO_STR(log, |
512 | LOG4CPLUS_TEXT("Client closed connection")); | ||
513 | ✗ | else if (result != -EAGAIN) | |
514 | ✗ | LOG4CPLUS_ERROR(log, | |
515 | LOG4CPLUS_TEXT("Network error: ") | ||
516 | << LOG4CPLUS_C_STR_TO_TSTRING(strerror(-result))); | ||
517 | } | ||
518 | |||
519 | 105 | return 0; | |
520 | } | ||
521 | |||
522 | ///////////////////////////////////////////////////////////////////////////// | ||
523 | ///////////////////////////////////////////////////////////////////////////// | ||
524 | #ifdef GNUTLS_FOUND | ||
525 | ///////////////////////////////////////////////////////////////////////////// | ||
526 | 27 | int Session::gnutls_verify_client(gnutls_session_t tls_session) | |
527 | { | ||
528 | int result; | ||
529 | Session* session = | ||
530 |
1/2✓ Branch 1 taken 27 times.
✗ Branch 2 not taken.
|
27 | reinterpret_cast<Session*>(gnutls_session_get_ptr(tls_session)); |
531 | 27 | const Blacklist& blacklist = session->main->getBlacklist(); | |
532 | |||
533 | 27 | unsigned int list_size = ~0U; | |
534 | const gnutls_datum_t* certs = | ||
535 |
1/2✓ Branch 1 taken 27 times.
✗ Branch 2 not taken.
|
27 | gnutls_certificate_get_peers (tls_session, &list_size); |
536 |
3/6✓ Branch 0 taken 27 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 27 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 27 times.
|
27 | if (list_size == ~0U or !certs or !list_size) { |
537 | ✗ | LOG4CPLUS_FATAL_STR(session->log, | |
538 | LOG4CPLUS_TEXT( | ||
539 | "gnutls_certificate_get_peers() failed: " | ||
540 | "Client did not send a certificate or " | ||
541 | "there was an error retrieving it")); | ||
542 | ✗ | return -1; | |
543 | } | ||
544 | else { | ||
545 |
8/16✓ Branch 8 taken 27 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 27 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 27 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 27 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 27 times.
✗ Branch 24 not taken.
✓ Branch 27 taken 27 times.
✗ Branch 28 not taken.
✓ Branch 31 taken 27 times.
✗ Branch 32 not taken.
✓ Branch 35 taken 27 times.
✗ Branch 36 not taken.
|
27 | LOG4CPLUS_INFO(session->log, |
546 | LOG4CPLUS_TEXT("Received ") | ||
547 | << list_size | ||
548 | << LOG4CPLUS_TEXT(" certificates from peer")); | ||
549 | } | ||
550 | |||
551 | 27 | gnutls_x509_crt_t raw_crt = nullptr; | |
552 |
1/2✓ Branch 1 taken 27 times.
✗ Branch 2 not taken.
|
27 | result = gnutls_x509_crt_init (&raw_crt); |
553 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 27 times.
|
27 | if (result) { |
554 | ✗ | LOG4CPLUS_FATAL(session->log, | |
555 | LOG4CPLUS_TEXT("gnutls_x509_crt_init() failed: ") | ||
556 | << LOG4CPLUS_C_STR_TO_TSTRING(gnutls_strerror(result)) | ||
557 | << LOG4CPLUS_TEXT(" (") | ||
558 | << LOG4CPLUS_C_STR_TO_TSTRING( | ||
559 | gnutls_strerror_name(result)) | ||
560 | << LOG4CPLUS_TEXT(")")); | ||
561 | ✗ | return -1; | |
562 | } | ||
563 | 54 | std::unique_ptr<gnutls_x509_crt_int, TlsDeleter> crt(raw_crt); | |
564 | |||
565 |
3/4✓ Branch 0 taken 79 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 52 times.
✓ Branch 3 taken 27 times.
|
79 | for (unsigned int i = 0; !result and i < list_size; ++i) { |
566 |
1/2✓ Branch 2 taken 52 times.
✗ Branch 3 not taken.
|
52 | result = gnutls_x509_crt_import (crt.get(), certs++, GNUTLS_X509_FMT_DER); |
567 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 52 times.
|
52 | if (result) { |
568 | ✗ | LOG4CPLUS_FATAL(session->log, | |
569 | LOG4CPLUS_TEXT("gnutls_x509_crt_import(") | ||
570 | << i | ||
571 | << LOG4CPLUS_TEXT(") failed: ") | ||
572 | << LOG4CPLUS_C_STR_TO_TSTRING(gnutls_strerror(result)) | ||
573 | << LOG4CPLUS_TEXT(" (") | ||
574 | << LOG4CPLUS_C_STR_TO_TSTRING( | ||
575 | gnutls_strerror_name(result)) | ||
576 | << LOG4CPLUS_TEXT(")")); | ||
577 | ✗ | break; | |
578 | } | ||
579 | |||
580 | 52 | gnutls_datum_t cinfo = { NULL, 0 }; | |
581 |
1/2✓ Branch 2 taken 52 times.
✗ Branch 3 not taken.
|
52 | result = gnutls_x509_crt_print( |
582 | crt.get(), GNUTLS_CRT_PRINT_ONELINE, &cinfo); | ||
583 |
1/2✓ Branch 0 taken 52 times.
✗ Branch 1 not taken.
|
52 | if (result == GNUTLS_E_SUCCESS) { |
584 |
10/20✓ Branch 8 taken 52 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 52 times.
✗ Branch 11 not taken.
✓ Branch 13 taken 52 times.
✗ Branch 14 not taken.
✓ Branch 17 taken 52 times.
✗ Branch 18 not taken.
✓ Branch 23 taken 52 times.
✗ Branch 24 not taken.
✓ Branch 27 taken 52 times.
✗ Branch 28 not taken.
✓ Branch 33 taken 52 times.
✗ Branch 34 not taken.
✓ Branch 37 taken 52 times.
✗ Branch 38 not taken.
✓ Branch 45 taken 52 times.
✗ Branch 46 not taken.
✓ Branch 49 taken 52 times.
✗ Branch 50 not taken.
|
52 | LOG4CPLUS_INFO(session->log, |
585 | LOG4CPLUS_TEXT("Certificate[") | ||
586 | << i | ||
587 | << LOG4CPLUS_TEXT("].info: ") | ||
588 | << LOG4CPLUS_C_STR_TO_TSTRING((const char*)cinfo.data)); | ||
589 | } | ||
590 | else { | ||
591 | ✗ | LOG4CPLUS_INFO(session->log, | |
592 | LOG4CPLUS_TEXT("gnutls_x509_crt_print(") | ||
593 | << i | ||
594 | << LOG4CPLUS_TEXT(") failed: ") | ||
595 | << LOG4CPLUS_C_STR_TO_TSTRING(gnutls_strerror(result)) | ||
596 | << LOG4CPLUS_TEXT(" (") | ||
597 | << LOG4CPLUS_C_STR_TO_TSTRING( | ||
598 | gnutls_strerror_name(result)) | ||
599 | << LOG4CPLUS_TEXT(")")); | ||
600 | } | ||
601 |
1/2✓ Branch 1 taken 52 times.
✗ Branch 2 not taken.
|
52 | gnutls_free(cinfo.data); |
602 | |||
603 |
1/2✗ Branch 2 not taken.
✓ Branch 3 taken 52 times.
|
52 | if (!blacklist.empty()) { |
604 | ✗ | unsigned char buf[100]; | |
605 | ✗ | size_t len = sizeof(buf); | |
606 | ✗ | result = gnutls_x509_crt_get_key_id(crt.get(), 0, buf, &len); | |
607 | ✗ | if (result or !len) { | |
608 | ✗ | LOG4CPLUS_FATAL(session->log, | |
609 | LOG4CPLUS_TEXT("gnutls_x509_crt_get_key_id(") | ||
610 | << i | ||
611 | << LOG4CPLUS_TEXT(") failed: ") | ||
612 | << LOG4CPLUS_C_STR_TO_TSTRING(gnutls_strerror(result)) | ||
613 | << LOG4CPLUS_TEXT(" (") | ||
614 | << LOG4CPLUS_C_STR_TO_TSTRING( | ||
615 | gnutls_strerror_name(result)) | ||
616 | << LOG4CPLUS_TEXT(")")); | ||
617 | ✗ | result = -1; | |
618 | ✗ | break; | |
619 | } | ||
620 | else { | ||
621 | ✗ | Blacklist::const_iterator it = | |
622 | ✗ | blacklist.find(datum_string(buf, len)); | |
623 | ✗ | if (it != blacklist.end()) { | |
624 | ✗ | LOG4CPLUS_FATAL(session->log, | |
625 | LOG4CPLUS_TEXT( | ||
626 | "Certificate is blacklisted. Public Key Id = ") | ||
627 | << LOG4CPLUS_STRING_TO_TSTRING(std::string(*it))); | ||
628 | ✗ | result = -1; | |
629 | ✗ | break; | |
630 | } | ||
631 | } | ||
632 | } | ||
633 | } | ||
634 | |||
635 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 27 times.
|
27 | if (result) |
636 | ✗ | return result; | |
637 | |||
638 | 27 | unsigned int status; | |
639 |
1/2✓ Branch 1 taken 27 times.
✗ Branch 2 not taken.
|
27 | result = gnutls_certificate_verify_peers2(tls_session, &status); |
640 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 27 times.
|
27 | if (result) { |
641 | // Complain | ||
642 | ✗ | LOG4CPLUS_FATAL(session->log, | |
643 | LOG4CPLUS_TEXT("gnutls_certificate_verify_peers2() failed: ") | ||
644 | << LOG4CPLUS_C_STR_TO_TSTRING(gnutls_strerror(result)) | ||
645 | << LOG4CPLUS_TEXT(" (") | ||
646 | << LOG4CPLUS_C_STR_TO_TSTRING( | ||
647 | gnutls_strerror_name(result)) | ||
648 | << LOG4CPLUS_TEXT(")")); | ||
649 | ✗ | return -1; | |
650 | } | ||
651 |
2/2✓ Branch 0 taken 1 times.
✓ Branch 1 taken 26 times.
|
27 | else if (status) { |
652 |
1/2✓ Branch 2 taken 1 times.
✗ Branch 3 not taken.
|
2 | std::ostringstream os; |
653 |
1/2✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
|
1 | os << "Verification of peer's certificate failed: "; |
654 |
1/2✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
|
1 | if (status & GNUTLS_CERT_INVALID) |
655 |
1/2✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
|
1 | os << "Certificate is invalid"; |
656 | |||
657 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
|
1 | if (status & GNUTLS_CERT_REVOKED) |
658 | ✗ | os << "Certificate is revoked"; | |
659 | |||
660 |
1/2✓ Branch 0 taken 1 times.
✗ Branch 1 not taken.
|
1 | if (status & GNUTLS_CERT_SIGNER_NOT_FOUND) |
661 |
1/2✓ Branch 1 taken 1 times.
✗ Branch 2 not taken.
|
1 | os << "Certificate signer is not found"; |
662 | |||
663 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
|
1 | if (status & GNUTLS_CERT_SIGNER_NOT_CA) |
664 | ✗ | os << "Certificate signer is not a certification authority"; | |
665 | |||
666 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
|
1 | if (status & GNUTLS_CERT_INSECURE_ALGORITHM) |
667 | ✗ | os << "Certificate uses an insecure algorithm"; | |
668 | |||
669 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
|
1 | if (status & GNUTLS_CERT_NOT_ACTIVATED) |
670 | ✗ | os << "Certificate is not activated"; | |
671 | |||
672 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 1 times.
|
1 | if (status & GNUTLS_CERT_EXPIRED) |
673 | ✗ | os << "Certificate expired"; | |
674 | |||
675 |
4/8✓ Branch 8 taken 1 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 1 times.
✗ Branch 11 not taken.
✓ Branch 14 taken 1 times.
✗ Branch 15 not taken.
✓ Branch 18 taken 1 times.
✗ Branch 19 not taken.
|
1 | LOG4CPLUS_FATAL_STR(session->log, |
676 | LOG4CPLUS_STRING_TO_TSTRING(os.str())); | ||
677 | |||
678 | 1 | return -1; | |
679 | } | ||
680 | |||
681 | 26 | return 0; | |
682 | 9 | } | |
683 | |||
684 | #endif | ||
685 |