summaryrefslogtreecommitdiff
path: root/monitor.c
diff options
context:
space:
mode:
authordjm@openbsd.org <djm@openbsd.org>2018-03-03 03:15:51 +0000
committerDamien Miller <djm@mindrot.org>2018-03-03 14:37:16 +1100
commit7c856857607112a3dfe6414696bf4c7ab7fb0cb3 (patch)
tree48c837fc9c9e11d64862d4f54c1a886b54d8721c /monitor.c
parent90c4bec8b5f9ec4c003ae4abdf13fc7766f00c8b (diff)
upstream: switch over to the new authorized_keys options API and
remove the legacy one. Includes a fairly big refactor of auth2-pubkey.c to retain less state between key file lines. feedback and ok markus@ OpenBSD-Commit-ID: dece6cae0f47751b9892080eb13d6625599573df
Diffstat (limited to 'monitor.c')
-rw-r--r--monitor.c70
1 files changed, 45 insertions, 25 deletions
diff --git a/monitor.c b/monitor.c
index e4ac3ccfd..c68e1b0d9 100644
--- a/monitor.c
+++ b/monitor.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: monitor.c,v 1.179 2018/02/05 05:37:46 tb Exp $ */ 1/* $OpenBSD: monitor.c,v 1.180 2018/03/03 03:15:51 djm Exp $ */
2/* 2/*
3 * Copyright 2002 Niels Provos <provos@citi.umich.edu> 3 * Copyright 2002 Niels Provos <provos@citi.umich.edu>
4 * Copyright 2002 Markus Friedl <markus@openbsd.org> 4 * Copyright 2002 Markus Friedl <markus@openbsd.org>
@@ -116,6 +116,7 @@ extern u_char session_id[];
116extern Buffer auth_debug; 116extern Buffer auth_debug;
117extern int auth_debug_init; 117extern int auth_debug_init;
118extern Buffer loginmsg; 118extern Buffer loginmsg;
119extern struct sshauthopt *auth_opts; /* XXX move to permanent ssh->authctxt? */
119 120
120/* State exported from the child */ 121/* State exported from the child */
121static struct sshbuf *child_state; 122static struct sshbuf *child_state;
@@ -172,6 +173,7 @@ static Authctxt *authctxt;
172static u_char *key_blob = NULL; 173static u_char *key_blob = NULL;
173static u_int key_bloblen = 0; 174static u_int key_bloblen = 0;
174static int key_blobtype = MM_NOKEY; 175static int key_blobtype = MM_NOKEY;
176static struct sshauthopt *key_opts = NULL;
175static char *hostbased_cuser = NULL; 177static char *hostbased_cuser = NULL;
176static char *hostbased_chost = NULL; 178static char *hostbased_chost = NULL;
177static char *auth_method = "unknown"; 179static char *auth_method = "unknown";
@@ -252,7 +254,6 @@ struct mon_table mon_dispatch_postauth20[] = {
252struct mon_table *mon_dispatch; 254struct mon_table *mon_dispatch;
253 255
254/* Specifies if a certain message is allowed at the moment */ 256/* Specifies if a certain message is allowed at the moment */
255
256static void 257static void
257monitor_permit(struct mon_table *ent, enum monitor_reqtype type, int permit) 258monitor_permit(struct mon_table *ent, enum monitor_reqtype type, int permit)
258{ 259{
@@ -297,6 +298,7 @@ monitor_child_preauth(Authctxt *_authctxt, struct monitor *pmonitor)
297 298
298 authctxt = _authctxt; 299 authctxt = _authctxt;
299 memset(authctxt, 0, sizeof(*authctxt)); 300 memset(authctxt, 0, sizeof(*authctxt));
301 ssh->authctxt = authctxt;
300 302
301 authctxt->loginmsg = &loginmsg; 303 authctxt->loginmsg = &loginmsg;
302 304
@@ -331,7 +333,7 @@ monitor_child_preauth(Authctxt *_authctxt, struct monitor *pmonitor)
331 fatal("%s: unexpected authentication from %d", 333 fatal("%s: unexpected authentication from %d",
332 __func__, ent->type); 334 __func__, ent->type);
333 if (authctxt->pw->pw_uid == 0 && 335 if (authctxt->pw->pw_uid == 0 &&
334 !auth_root_allowed(auth_method)) 336 !auth_root_allowed(ssh, auth_method))
335 authenticated = 0; 337 authenticated = 0;
336#ifdef USE_PAM 338#ifdef USE_PAM
337 /* PAM needs to perform account checks after auth */ 339 /* PAM needs to perform account checks after auth */
@@ -365,6 +367,7 @@ monitor_child_preauth(Authctxt *_authctxt, struct monitor *pmonitor)
365 367
366 debug("%s: %s has been authenticated by privileged process", 368 debug("%s: %s has been authenticated by privileged process",
367 __func__, authctxt->user); 369 __func__, authctxt->user);
370 ssh->authctxt = NULL;
368 ssh_packet_set_log_preamble(ssh, "user %s", authctxt->user); 371 ssh_packet_set_log_preamble(ssh, "user %s", authctxt->user);
369 372
370 mm_get_keystate(pmonitor); 373 mm_get_keystate(pmonitor);
@@ -413,7 +416,7 @@ monitor_child_postauth(struct monitor *pmonitor)
413 monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); 416 monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1);
414 monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1); 417 monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1);
415 418
416 if (!no_pty_flag) { 419 if (auth_opts->permit_pty_flag) {
417 monitor_permit(mon_dispatch, MONITOR_REQ_PTY, 1); 420 monitor_permit(mon_dispatch, MONITOR_REQ_PTY, 1);
418 monitor_permit(mon_dispatch, MONITOR_REQ_PTYCLEANUP, 1); 421 monitor_permit(mon_dispatch, MONITOR_REQ_PTYCLEANUP, 1);
419 } 422 }
@@ -558,9 +561,11 @@ monitor_reset_key_state(void)
558 free(key_blob); 561 free(key_blob);
559 free(hostbased_cuser); 562 free(hostbased_cuser);
560 free(hostbased_chost); 563 free(hostbased_chost);
564 sshauthopt_free(key_opts);
561 key_blob = NULL; 565 key_blob = NULL;
562 key_bloblen = 0; 566 key_bloblen = 0;
563 key_blobtype = MM_NOKEY; 567 key_blobtype = MM_NOKEY;
568 key_opts = NULL;
564 hostbased_cuser = NULL; 569 hostbased_cuser = NULL;
565 hostbased_chost = NULL; 570 hostbased_chost = NULL;
566} 571}
@@ -828,6 +833,7 @@ mm_answer_authserv(int sock, Buffer *m)
828int 833int
829mm_answer_authpassword(int sock, Buffer *m) 834mm_answer_authpassword(int sock, Buffer *m)
830{ 835{
836 struct ssh *ssh = active_state; /* XXX */
831 static int call_count; 837 static int call_count;
832 char *passwd; 838 char *passwd;
833 int authenticated; 839 int authenticated;
@@ -838,7 +844,7 @@ mm_answer_authpassword(int sock, Buffer *m)
838 passwd = buffer_get_string(m, &plen); 844 passwd = buffer_get_string(m, &plen);
839 /* Only authenticate if the context is valid */ 845 /* Only authenticate if the context is valid */
840 authenticated = options.password_authentication && 846 authenticated = options.password_authentication &&
841 auth_password(authctxt, passwd); 847 auth_password(ssh, passwd);
842 explicit_bzero(passwd, strlen(passwd)); 848 explicit_bzero(passwd, strlen(passwd));
843 free(passwd); 849 free(passwd);
844 850
@@ -1129,15 +1135,16 @@ mm_answer_pam_free_ctx(int sock, Buffer *m)
1129int 1135int
1130mm_answer_keyallowed(int sock, Buffer *m) 1136mm_answer_keyallowed(int sock, Buffer *m)
1131{ 1137{
1138 struct ssh *ssh = active_state; /* XXX */
1132 struct sshkey *key; 1139 struct sshkey *key;
1133 char *cuser, *chost; 1140 char *cuser, *chost;
1134 u_char *blob; 1141 u_char *blob;
1135 u_int bloblen, pubkey_auth_attempt; 1142 u_int bloblen, pubkey_auth_attempt;
1136 enum mm_keytype type = 0; 1143 enum mm_keytype type = 0;
1137 int allowed = 0; 1144 int r, allowed = 0;
1145 struct sshauthopt *opts = NULL;
1138 1146
1139 debug3("%s entering", __func__); 1147 debug3("%s entering", __func__);
1140
1141 type = buffer_get_int(m); 1148 type = buffer_get_int(m);
1142 cuser = buffer_get_string(m, NULL); 1149 cuser = buffer_get_string(m, NULL);
1143 chost = buffer_get_string(m, NULL); 1150 chost = buffer_get_string(m, NULL);
@@ -1156,28 +1163,31 @@ mm_answer_keyallowed(int sock, Buffer *m)
1156 1163
1157 switch (type) { 1164 switch (type) {
1158 case MM_USERKEY: 1165 case MM_USERKEY:
1159 allowed = options.pubkey_authentication &&
1160 !auth2_key_already_used(authctxt, key) &&
1161 match_pattern_list(sshkey_ssh_name(key),
1162 options.pubkey_key_types, 0) == 1 &&
1163 user_key_allowed(authctxt->pw, key,
1164 pubkey_auth_attempt);
1165 auth_method = "publickey"; 1166 auth_method = "publickey";
1166 if (options.pubkey_authentication && 1167 if (!options.pubkey_authentication)
1167 (!pubkey_auth_attempt || allowed != 1)) 1168 break;
1168 auth_clear_options(); 1169 if (auth2_key_already_used(authctxt, key))
1170 break;
1171 if (match_pattern_list(sshkey_ssh_name(key),
1172 options.pubkey_key_types, 0) != 1)
1173 break;
1174 allowed = user_key_allowed(ssh, authctxt->pw, key,
1175 pubkey_auth_attempt, &opts);
1169 break; 1176 break;
1170 case MM_HOSTKEY: 1177 case MM_HOSTKEY:
1171 allowed = options.hostbased_authentication && 1178 auth_method = "hostbased";
1172 !auth2_key_already_used(authctxt, key) && 1179 if (!options.hostbased_authentication)
1173 match_pattern_list(sshkey_ssh_name(key), 1180 break;
1174 options.hostbased_key_types, 0) == 1 && 1181 if (auth2_key_already_used(authctxt, key))
1175 hostbased_key_allowed(authctxt->pw, 1182 break;
1183 if (match_pattern_list(sshkey_ssh_name(key),
1184 options.hostbased_key_types, 0) != 1)
1185 break;
1186 allowed = hostbased_key_allowed(authctxt->pw,
1176 cuser, chost, key); 1187 cuser, chost, key);
1177 auth2_record_info(authctxt, 1188 auth2_record_info(authctxt,
1178 "client user \"%.100s\", client host \"%.100s\"", 1189 "client user \"%.100s\", client host \"%.100s\"",
1179 cuser, chost); 1190 cuser, chost);
1180 auth_method = "hostbased";
1181 break; 1191 break;
1182 default: 1192 default:
1183 fatal("%s: unknown key type %d", __func__, type); 1193 fatal("%s: unknown key type %d", __func__, type);
@@ -1185,7 +1195,10 @@ mm_answer_keyallowed(int sock, Buffer *m)
1185 } 1195 }
1186 } 1196 }
1187 1197
1188 debug3("%s: key is %s", __func__, allowed ? "allowed" : "not allowed"); 1198 debug3("%s: %s authentication%s: %s key is %s", __func__,
1199 auth_method, pubkey_auth_attempt ? "" : " test",
1200 (key == NULL || !authctxt->valid) ? "invalid" : sshkey_type(key),
1201 allowed ? "allowed" : "not allowed");
1189 1202
1190 auth2_record_key(authctxt, 0, key); 1203 auth2_record_key(authctxt, 0, key);
1191 sshkey_free(key); 1204 sshkey_free(key);
@@ -1198,6 +1211,7 @@ mm_answer_keyallowed(int sock, Buffer *m)
1198 key_blob = blob; 1211 key_blob = blob;
1199 key_bloblen = bloblen; 1212 key_bloblen = bloblen;
1200 key_blobtype = type; 1213 key_blobtype = type;
1214 key_opts = opts;
1201 hostbased_cuser = cuser; 1215 hostbased_cuser = cuser;
1202 hostbased_chost = chost; 1216 hostbased_chost = chost;
1203 } else { 1217 } else {
@@ -1210,10 +1224,13 @@ mm_answer_keyallowed(int sock, Buffer *m)
1210 1224
1211 buffer_clear(m); 1225 buffer_clear(m);
1212 buffer_put_int(m, allowed); 1226 buffer_put_int(m, allowed);
1213 buffer_put_int(m, forced_command != NULL); 1227 if (opts != NULL && (r = sshauthopt_serialise(opts, m, 1)) != 0)
1214 1228 fatal("%s: sshauthopt_serialise: %s", __func__, ssh_err(r));
1215 mm_request_send(sock, MONITOR_ANS_KEYALLOWED, m); 1229 mm_request_send(sock, MONITOR_ANS_KEYALLOWED, m);
1216 1230
1231 if (!allowed)
1232 sshauthopt_free(opts);
1233
1217 return (0); 1234 return (0);
1218} 1235}
1219 1236
@@ -1336,6 +1353,7 @@ monitor_valid_hostbasedblob(u_char *data, u_int datalen, char *cuser,
1336int 1353int
1337mm_answer_keyverify(int sock, struct sshbuf *m) 1354mm_answer_keyverify(int sock, struct sshbuf *m)
1338{ 1355{
1356 struct ssh *ssh = active_state; /* XXX */
1339 struct sshkey *key; 1357 struct sshkey *key;
1340 u_char *signature, *data, *blob; 1358 u_char *signature, *data, *blob;
1341 char *sigalg; 1359 char *sigalg;
@@ -1390,6 +1408,8 @@ mm_answer_keyverify(int sock, struct sshbuf *m)
1390 free(data); 1408 free(data);
1391 free(sigalg); 1409 free(sigalg);
1392 1410
1411 if (key_blobtype == MM_USERKEY)
1412 auth_activate_options(ssh, key_opts);
1393 monitor_reset_key_state(); 1413 monitor_reset_key_state();
1394 1414
1395 sshkey_free(key); 1415 sshkey_free(key);