summaryrefslogtreecommitdiff
path: root/monitor.c
diff options
context:
space:
mode:
authorDamien Miller <djm@mindrot.org>2016-08-29 11:47:07 +1000
committerDamien Miller <djm@mindrot.org>2016-08-29 11:49:16 +1000
commitb38b95f5bcc52278feb839afda2987933f68ff96 (patch)
tree9e030baa90932b0b45178423d4ca1e6c1f966ab8 /monitor.c
parentdc664d1bd0fc91b24406a3e9575b81c285b8342b (diff)
Tighten monitor state-machine flow for PAM calls
(attack surface reduction)
Diffstat (limited to 'monitor.c')
-rw-r--r--monitor.c21
1 files changed, 17 insertions, 4 deletions
diff --git a/monitor.c b/monitor.c
index a86b77936..b255f273f 100644
--- a/monitor.c
+++ b/monitor.c
@@ -208,9 +208,9 @@ struct mon_table mon_dispatch_proto20[] = {
208#ifdef USE_PAM 208#ifdef USE_PAM
209 {MONITOR_REQ_PAM_START, MON_ONCE, mm_answer_pam_start}, 209 {MONITOR_REQ_PAM_START, MON_ONCE, mm_answer_pam_start},
210 {MONITOR_REQ_PAM_ACCOUNT, 0, mm_answer_pam_account}, 210 {MONITOR_REQ_PAM_ACCOUNT, 0, mm_answer_pam_account},
211 {MONITOR_REQ_PAM_INIT_CTX, MON_ISAUTH, mm_answer_pam_init_ctx}, 211 {MONITOR_REQ_PAM_INIT_CTX, MON_ONCE, mm_answer_pam_init_ctx},
212 {MONITOR_REQ_PAM_QUERY, MON_ISAUTH, mm_answer_pam_query}, 212 {MONITOR_REQ_PAM_QUERY, 0, mm_answer_pam_query},
213 {MONITOR_REQ_PAM_RESPOND, MON_ISAUTH, mm_answer_pam_respond}, 213 {MONITOR_REQ_PAM_RESPOND, MON_ONCE, mm_answer_pam_respond},
214 {MONITOR_REQ_PAM_FREE_CTX, MON_ONCE|MON_AUTHDECIDE, mm_answer_pam_free_ctx}, 214 {MONITOR_REQ_PAM_FREE_CTX, MON_ONCE|MON_AUTHDECIDE, mm_answer_pam_free_ctx},
215#endif 215#endif
216#ifdef SSH_AUDIT_EVENTS 216#ifdef SSH_AUDIT_EVENTS
@@ -990,6 +990,7 @@ mm_answer_pam_start(int sock, Buffer *m)
990 start_pam(authctxt); 990 start_pam(authctxt);
991 991
992 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_ACCOUNT, 1); 992 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_ACCOUNT, 1);
993 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_INIT_CTX, 1);
993 994
994 return (0); 995 return (0);
995} 996}
@@ -1019,11 +1020,14 @@ int
1019mm_answer_pam_init_ctx(int sock, Buffer *m) 1020mm_answer_pam_init_ctx(int sock, Buffer *m)
1020{ 1021{
1021 debug3("%s", __func__); 1022 debug3("%s", __func__);
1023 if (sshpam_ctxt != NULL)
1024 fatal("%s: already called", __func__);
1022 sshpam_ctxt = (sshpam_device.init_ctx)(authctxt); 1025 sshpam_ctxt = (sshpam_device.init_ctx)(authctxt);
1023 sshpam_authok = NULL; 1026 sshpam_authok = NULL;
1024 buffer_clear(m); 1027 buffer_clear(m);
1025 if (sshpam_ctxt != NULL) { 1028 if (sshpam_ctxt != NULL) {
1026 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_FREE_CTX, 1); 1029 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_FREE_CTX, 1);
1030 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_QUERY, 1);
1027 buffer_put_int(m, 1); 1031 buffer_put_int(m, 1);
1028 } else { 1032 } else {
1029 buffer_put_int(m, 0); 1033 buffer_put_int(m, 0);
@@ -1041,11 +1045,14 @@ mm_answer_pam_query(int sock, Buffer *m)
1041 1045
1042 debug3("%s", __func__); 1046 debug3("%s", __func__);
1043 sshpam_authok = NULL; 1047 sshpam_authok = NULL;
1048 if (sshpam_ctxt == NULL)
1049 fatal("%s: no context", __func__);
1044 ret = (sshpam_device.query)(sshpam_ctxt, &name, &info, &num, &prompts, &echo_on); 1050 ret = (sshpam_device.query)(sshpam_ctxt, &name, &info, &num, &prompts, &echo_on);
1045 if (ret == 0 && num == 0) 1051 if (ret == 0 && num == 0)
1046 sshpam_authok = sshpam_ctxt; 1052 sshpam_authok = sshpam_ctxt;
1047 if (num > 1 || name == NULL || info == NULL) 1053 if (num > 1 || name == NULL || info == NULL)
1048 ret = -1; 1054 fatal("sshpam_device.query failed");
1055 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_RESPOND, 1);
1049 buffer_clear(m); 1056 buffer_clear(m);
1050 buffer_put_int(m, ret); 1057 buffer_put_int(m, ret);
1051 buffer_put_cstring(m, name); 1058 buffer_put_cstring(m, name);
@@ -1075,6 +1082,8 @@ mm_answer_pam_respond(int sock, Buffer *m)
1075 int ret; 1082 int ret;
1076 1083
1077 debug3("%s", __func__); 1084 debug3("%s", __func__);
1085 if (sshpam_ctxt == NULL)
1086 fatal("%s: no context", __func__);
1078 sshpam_authok = NULL; 1087 sshpam_authok = NULL;
1079 num = buffer_get_int(m); 1088 num = buffer_get_int(m);
1080 if (num > 0) { 1089 if (num > 0) {
@@ -1104,10 +1113,14 @@ mm_answer_pam_free_ctx(int sock, Buffer *m)
1104 int r = sshpam_authok != NULL && sshpam_authok == sshpam_ctxt; 1113 int r = sshpam_authok != NULL && sshpam_authok == sshpam_ctxt;
1105 1114
1106 debug3("%s", __func__); 1115 debug3("%s", __func__);
1116 if (sshpam_ctxt == NULL)
1117 fatal("%s: no context", __func__);
1107 (sshpam_device.free_ctx)(sshpam_ctxt); 1118 (sshpam_device.free_ctx)(sshpam_ctxt);
1108 sshpam_ctxt = sshpam_authok = NULL; 1119 sshpam_ctxt = sshpam_authok = NULL;
1109 buffer_clear(m); 1120 buffer_clear(m);
1110 mm_request_send(sock, MONITOR_ANS_PAM_FREE_CTX, m); 1121 mm_request_send(sock, MONITOR_ANS_PAM_FREE_CTX, m);
1122 /* Allow another attempt */
1123 monitor_permit(mon_dispatch, MONITOR_REQ_PAM_INIT_CTX, 1);
1111 auth_method = "keyboard-interactive"; 1124 auth_method = "keyboard-interactive";
1112 auth_submethod = "pam"; 1125 auth_submethod = "pam";
1113 return r; 1126 return r;