Mercurial > dropbear
comparison svr-auth.c @ 1641:a2bbc22ea1e6 coverity
merge coverity
author | Matt Johnston <matt@ucc.asn.au> |
---|---|
date | Thu, 21 Mar 2019 00:14:38 +0800 |
parents | 592a18dac250 |
children | 7c17995bcdfb |
comparison
equal
deleted
inserted
replaced
1610:96e4c9b2cc00 | 1641:a2bbc22ea1e6 |
---|---|
77 unsigned int userlen, servicelen, methodlen; | 77 unsigned int userlen, servicelen, methodlen; |
78 int valid_user = 0; | 78 int valid_user = 0; |
79 | 79 |
80 TRACE(("enter recv_msg_userauth_request")) | 80 TRACE(("enter recv_msg_userauth_request")) |
81 | 81 |
82 /* for compensating failure delay */ | |
83 gettime_wrapper(&ses.authstate.auth_starttime); | |
84 | |
82 /* ignore packets if auth is already done */ | 85 /* ignore packets if auth is already done */ |
83 if (ses.authstate.authdone == 1) { | 86 if (ses.authstate.authdone == 1) { |
84 TRACE(("leave recv_msg_userauth_request: authdone already")) | 87 TRACE(("leave recv_msg_userauth_request: authdone already")) |
85 return; | 88 return; |
86 } | 89 } |
147 !(svr_opts.norootpass && ses.authstate.pw_uid == 0) ) { | 150 !(svr_opts.norootpass && ses.authstate.pw_uid == 0) ) { |
148 /* user wants to try password auth */ | 151 /* user wants to try password auth */ |
149 if (methodlen == AUTH_METHOD_PASSWORD_LEN && | 152 if (methodlen == AUTH_METHOD_PASSWORD_LEN && |
150 strncmp(methodname, AUTH_METHOD_PASSWORD, | 153 strncmp(methodname, AUTH_METHOD_PASSWORD, |
151 AUTH_METHOD_PASSWORD_LEN) == 0) { | 154 AUTH_METHOD_PASSWORD_LEN) == 0) { |
152 if (valid_user) { | 155 svr_auth_password(valid_user); |
153 svr_auth_password(); | 156 goto out; |
154 goto out; | |
155 } | |
156 } | 157 } |
157 } | 158 } |
158 #endif | 159 #endif |
159 | 160 |
160 #if DROPBEAR_SVR_PAM_AUTH | 161 #if DROPBEAR_SVR_PAM_AUTH |
162 !(svr_opts.norootpass && ses.authstate.pw_uid == 0) ) { | 163 !(svr_opts.norootpass && ses.authstate.pw_uid == 0) ) { |
163 /* user wants to try password auth */ | 164 /* user wants to try password auth */ |
164 if (methodlen == AUTH_METHOD_PASSWORD_LEN && | 165 if (methodlen == AUTH_METHOD_PASSWORD_LEN && |
165 strncmp(methodname, AUTH_METHOD_PASSWORD, | 166 strncmp(methodname, AUTH_METHOD_PASSWORD, |
166 AUTH_METHOD_PASSWORD_LEN) == 0) { | 167 AUTH_METHOD_PASSWORD_LEN) == 0) { |
167 if (valid_user) { | 168 svr_auth_pam(valid_user); |
168 svr_auth_pam(); | 169 goto out; |
169 goto out; | |
170 } | |
171 } | 170 } |
172 } | 171 } |
173 #endif | 172 #endif |
174 | 173 |
175 #if DROPBEAR_SVR_PUBKEY_AUTH | 174 #if DROPBEAR_SVR_PUBKEY_AUTH |
176 /* user wants to try pubkey auth */ | 175 /* user wants to try pubkey auth */ |
177 if (methodlen == AUTH_METHOD_PUBKEY_LEN && | 176 if (methodlen == AUTH_METHOD_PUBKEY_LEN && |
178 strncmp(methodname, AUTH_METHOD_PUBKEY, | 177 strncmp(methodname, AUTH_METHOD_PUBKEY, |
179 AUTH_METHOD_PUBKEY_LEN) == 0) { | 178 AUTH_METHOD_PUBKEY_LEN) == 0) { |
180 if (valid_user) { | 179 svr_auth_pubkey(valid_user); |
181 svr_auth_pubkey(); | |
182 } else { | |
183 /* pubkey has no failure delay */ | |
184 send_msg_userauth_failure(0, 0); | |
185 } | |
186 goto out; | 180 goto out; |
187 } | 181 } |
188 #endif | 182 #endif |
189 | 183 |
190 /* nothing matched, we just fail with a delay */ | 184 /* nothing matched, we just fail with a delay */ |
280 return DROPBEAR_FAILURE; | 274 return DROPBEAR_FAILURE; |
281 } | 275 } |
282 | 276 |
283 /* check if we are running as non-root, and login user is different from the server */ | 277 /* check if we are running as non-root, and login user is different from the server */ |
284 uid = geteuid(); | 278 uid = geteuid(); |
285 if (uid != 0 && uid != ses.authstate.pw_uid) { | 279 if (!(DROPBEAR_SVR_MULTIUSER && uid == 0) && uid != ses.authstate.pw_uid) { |
286 TRACE(("running as nonroot, only server uid is allowed")) | 280 TRACE(("running as nonroot, only server uid is allowed")) |
287 dropbear_log(LOG_WARNING, | 281 dropbear_log(LOG_WARNING, |
288 "Login attempt with wrong user %s from %s", | 282 "Login attempt with wrong user %s from %s", |
289 ses.authstate.pw_name, | 283 ses.authstate.pw_name, |
290 svr_ses.addrstring); | 284 svr_ses.addrstring); |
389 | 383 |
390 buf_putbyte(ses.writepayload, partial ? 1 : 0); | 384 buf_putbyte(ses.writepayload, partial ? 1 : 0); |
391 encrypt_packet(); | 385 encrypt_packet(); |
392 | 386 |
393 if (incrfail) { | 387 if (incrfail) { |
394 unsigned int delay; | 388 /* The SSH_MSG_AUTH_FAILURE response is delayed to attempt to |
395 genrandom((unsigned char*)&delay, sizeof(delay)); | 389 avoid user enumeration and slow brute force attempts. |
396 /* We delay for 300ms +- 50ms */ | 390 The delay is adjusted by the time already spent in processing |
397 delay = 250000 + (delay % 100000); | 391 authentication (ses.authstate.auth_starttime timestamp). */ |
392 | |
393 /* Desired total delay 300ms +-50ms (in nanoseconds). | |
394 Beware of integer overflow if increasing these values */ | |
395 const unsigned int mindelay = 250000000; | |
396 const unsigned int vardelay = 100000000; | |
397 unsigned int rand_delay; | |
398 struct timespec delay; | |
399 | |
400 gettime_wrapper(&delay); | |
401 delay.tv_sec -= ses.authstate.auth_starttime.tv_sec; | |
402 delay.tv_nsec -= ses.authstate.auth_starttime.tv_nsec; | |
403 | |
404 /* carry */ | |
405 if (delay.tv_nsec < 0) { | |
406 delay.tv_nsec += 1000000000; | |
407 delay.tv_sec -= 1; | |
408 } | |
409 | |
410 genrandom((unsigned char*)&rand_delay, sizeof(rand_delay)); | |
411 rand_delay = mindelay + (rand_delay % vardelay); | |
412 | |
413 if (delay.tv_sec == 0 && delay.tv_nsec <= mindelay) { | |
414 /* Compensate for elapsed time */ | |
415 delay.tv_nsec = rand_delay - delay.tv_nsec; | |
416 } else { | |
417 /* No time left or time went backwards, just delay anyway */ | |
418 delay.tv_sec = 0; | |
419 delay.tv_nsec = rand_delay; | |
420 } | |
421 | |
422 | |
398 #if DROPBEAR_FUZZ | 423 #if DROPBEAR_FUZZ |
399 if (!fuzz.fuzzing) | 424 if (!fuzz.fuzzing) |
400 #endif | 425 #endif |
401 { | 426 { |
402 usleep(delay); | 427 while (nanosleep(&delay, &delay) == -1 && errno == EINTR) { /* Go back to sleep */ } |
403 } | 428 } |
429 | |
404 ses.authstate.failcount++; | 430 ses.authstate.failcount++; |
405 } | 431 } |
406 | 432 |
407 if (ses.authstate.failcount >= svr_opts.maxauthtries) { | 433 if (ses.authstate.failcount >= svr_opts.maxauthtries) { |
408 char * userstr; | 434 char * userstr; |