diff options
Diffstat (limited to 'monitor.c')
-rw-r--r-- | monitor.c | 108 |
1 files changed, 107 insertions, 1 deletions
@@ -158,6 +158,8 @@ int mm_answer_gss_setup_ctx(int, Buffer *); | |||
158 | int mm_answer_gss_accept_ctx(int, Buffer *); | 158 | int mm_answer_gss_accept_ctx(int, Buffer *); |
159 | int mm_answer_gss_userok(int, Buffer *); | 159 | int mm_answer_gss_userok(int, Buffer *); |
160 | int mm_answer_gss_checkmic(int, Buffer *); | 160 | int mm_answer_gss_checkmic(int, Buffer *); |
161 | int mm_answer_gss_sign(int, Buffer *); | ||
162 | int mm_answer_gss_updatecreds(int, Buffer *); | ||
161 | #endif | 163 | #endif |
162 | 164 | ||
163 | #ifdef SSH_AUDIT_EVENTS | 165 | #ifdef SSH_AUDIT_EVENTS |
@@ -235,11 +237,18 @@ struct mon_table mon_dispatch_proto20[] = { | |||
235 | {MONITOR_REQ_GSSSTEP, MON_ISAUTH, mm_answer_gss_accept_ctx}, | 237 | {MONITOR_REQ_GSSSTEP, MON_ISAUTH, mm_answer_gss_accept_ctx}, |
236 | {MONITOR_REQ_GSSUSEROK, MON_AUTH, mm_answer_gss_userok}, | 238 | {MONITOR_REQ_GSSUSEROK, MON_AUTH, mm_answer_gss_userok}, |
237 | {MONITOR_REQ_GSSCHECKMIC, MON_ISAUTH, mm_answer_gss_checkmic}, | 239 | {MONITOR_REQ_GSSCHECKMIC, MON_ISAUTH, mm_answer_gss_checkmic}, |
240 | {MONITOR_REQ_GSSSIGN, MON_ONCE, mm_answer_gss_sign}, | ||
238 | #endif | 241 | #endif |
239 | {0, 0, NULL} | 242 | {0, 0, NULL} |
240 | }; | 243 | }; |
241 | 244 | ||
242 | struct mon_table mon_dispatch_postauth20[] = { | 245 | struct mon_table mon_dispatch_postauth20[] = { |
246 | #ifdef GSSAPI | ||
247 | {MONITOR_REQ_GSSSETUP, 0, mm_answer_gss_setup_ctx}, | ||
248 | {MONITOR_REQ_GSSSTEP, 0, mm_answer_gss_accept_ctx}, | ||
249 | {MONITOR_REQ_GSSSIGN, 0, mm_answer_gss_sign}, | ||
250 | {MONITOR_REQ_GSSUPCREDS, 0, mm_answer_gss_updatecreds}, | ||
251 | #endif | ||
243 | #ifdef WITH_OPENSSL | 252 | #ifdef WITH_OPENSSL |
244 | {MONITOR_REQ_MODULI, 0, mm_answer_moduli}, | 253 | {MONITOR_REQ_MODULI, 0, mm_answer_moduli}, |
245 | #endif | 254 | #endif |
@@ -354,6 +363,10 @@ monitor_child_preauth(Authctxt *_authctxt, struct monitor *pmonitor) | |||
354 | /* Permit requests for moduli and signatures */ | 363 | /* Permit requests for moduli and signatures */ |
355 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); | 364 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); |
356 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); | 365 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); |
366 | #ifdef GSSAPI | ||
367 | /* and for the GSSAPI key exchange */ | ||
368 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSETUP, 1); | ||
369 | #endif | ||
357 | } else { | 370 | } else { |
358 | mon_dispatch = mon_dispatch_proto15; | 371 | mon_dispatch = mon_dispatch_proto15; |
359 | 372 | ||
@@ -462,6 +475,10 @@ monitor_child_postauth(struct monitor *pmonitor) | |||
462 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); | 475 | monitor_permit(mon_dispatch, MONITOR_REQ_MODULI, 1); |
463 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); | 476 | monitor_permit(mon_dispatch, MONITOR_REQ_SIGN, 1); |
464 | monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1); | 477 | monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1); |
478 | #ifdef GSSAPI | ||
479 | /* and for the GSSAPI key exchange */ | ||
480 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSETUP, 1); | ||
481 | #endif | ||
465 | } else { | 482 | } else { |
466 | mon_dispatch = mon_dispatch_postauth15; | 483 | mon_dispatch = mon_dispatch_postauth15; |
467 | monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1); | 484 | monitor_permit(mon_dispatch, MONITOR_REQ_TERM, 1); |
@@ -1876,6 +1893,13 @@ monitor_apply_keystate(struct monitor *pmonitor) | |||
1876 | # endif | 1893 | # endif |
1877 | #endif /* WITH_OPENSSL */ | 1894 | #endif /* WITH_OPENSSL */ |
1878 | kex->kex[KEX_C25519_SHA256] = kexc25519_server; | 1895 | kex->kex[KEX_C25519_SHA256] = kexc25519_server; |
1896 | #ifdef GSSAPI | ||
1897 | if (options.gss_keyex) { | ||
1898 | kex->kex[KEX_GSS_GRP1_SHA1] = kexgss_server; | ||
1899 | kex->kex[KEX_GSS_GRP14_SHA1] = kexgss_server; | ||
1900 | kex->kex[KEX_GSS_GEX_SHA1] = kexgss_server; | ||
1901 | } | ||
1902 | #endif | ||
1879 | kex->load_host_public_key=&get_hostkey_public_by_type; | 1903 | kex->load_host_public_key=&get_hostkey_public_by_type; |
1880 | kex->load_host_private_key=&get_hostkey_private_by_type; | 1904 | kex->load_host_private_key=&get_hostkey_private_by_type; |
1881 | kex->host_key_index=&get_hostkey_index; | 1905 | kex->host_key_index=&get_hostkey_index; |
@@ -1975,6 +1999,9 @@ mm_answer_gss_setup_ctx(int sock, Buffer *m) | |||
1975 | OM_uint32 major; | 1999 | OM_uint32 major; |
1976 | u_int len; | 2000 | u_int len; |
1977 | 2001 | ||
2002 | if (!options.gss_authentication && !options.gss_keyex) | ||
2003 | fatal("In GSSAPI monitor when GSSAPI is disabled"); | ||
2004 | |||
1978 | goid.elements = buffer_get_string(m, &len); | 2005 | goid.elements = buffer_get_string(m, &len); |
1979 | goid.length = len; | 2006 | goid.length = len; |
1980 | 2007 | ||
@@ -2002,6 +2029,9 @@ mm_answer_gss_accept_ctx(int sock, Buffer *m) | |||
2002 | OM_uint32 flags = 0; /* GSI needs this */ | 2029 | OM_uint32 flags = 0; /* GSI needs this */ |
2003 | u_int len; | 2030 | u_int len; |
2004 | 2031 | ||
2032 | if (!options.gss_authentication && !options.gss_keyex) | ||
2033 | fatal("In GSSAPI monitor when GSSAPI is disabled"); | ||
2034 | |||
2005 | in.value = buffer_get_string(m, &len); | 2035 | in.value = buffer_get_string(m, &len); |
2006 | in.length = len; | 2036 | in.length = len; |
2007 | major = ssh_gssapi_accept_ctx(gsscontext, &in, &out, &flags); | 2037 | major = ssh_gssapi_accept_ctx(gsscontext, &in, &out, &flags); |
@@ -2019,6 +2049,7 @@ mm_answer_gss_accept_ctx(int sock, Buffer *m) | |||
2019 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSTEP, 0); | 2049 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSTEP, 0); |
2020 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSUSEROK, 1); | 2050 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSUSEROK, 1); |
2021 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSCHECKMIC, 1); | 2051 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSCHECKMIC, 1); |
2052 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSSIGN, 1); | ||
2022 | } | 2053 | } |
2023 | return (0); | 2054 | return (0); |
2024 | } | 2055 | } |
@@ -2030,6 +2061,9 @@ mm_answer_gss_checkmic(int sock, Buffer *m) | |||
2030 | OM_uint32 ret; | 2061 | OM_uint32 ret; |
2031 | u_int len; | 2062 | u_int len; |
2032 | 2063 | ||
2064 | if (!options.gss_authentication && !options.gss_keyex) | ||
2065 | fatal("In GSSAPI monitor when GSSAPI is disabled"); | ||
2066 | |||
2033 | gssbuf.value = buffer_get_string(m, &len); | 2067 | gssbuf.value = buffer_get_string(m, &len); |
2034 | gssbuf.length = len; | 2068 | gssbuf.length = len; |
2035 | mic.value = buffer_get_string(m, &len); | 2069 | mic.value = buffer_get_string(m, &len); |
@@ -2056,7 +2090,11 @@ mm_answer_gss_userok(int sock, Buffer *m) | |||
2056 | { | 2090 | { |
2057 | int authenticated; | 2091 | int authenticated; |
2058 | 2092 | ||
2059 | authenticated = authctxt->valid && ssh_gssapi_userok(authctxt->user); | 2093 | if (!options.gss_authentication && !options.gss_keyex) |
2094 | fatal("In GSSAPI monitor when GSSAPI is disabled"); | ||
2095 | |||
2096 | authenticated = authctxt->valid && | ||
2097 | ssh_gssapi_userok(authctxt->user, authctxt->pw); | ||
2060 | 2098 | ||
2061 | buffer_clear(m); | 2099 | buffer_clear(m); |
2062 | buffer_put_int(m, authenticated); | 2100 | buffer_put_int(m, authenticated); |
@@ -2069,5 +2107,73 @@ mm_answer_gss_userok(int sock, Buffer *m) | |||
2069 | /* Monitor loop will terminate if authenticated */ | 2107 | /* Monitor loop will terminate if authenticated */ |
2070 | return (authenticated); | 2108 | return (authenticated); |
2071 | } | 2109 | } |
2110 | |||
2111 | int | ||
2112 | mm_answer_gss_sign(int socket, Buffer *m) | ||
2113 | { | ||
2114 | gss_buffer_desc data; | ||
2115 | gss_buffer_desc hash = GSS_C_EMPTY_BUFFER; | ||
2116 | OM_uint32 major, minor; | ||
2117 | u_int len; | ||
2118 | |||
2119 | if (!options.gss_authentication && !options.gss_keyex) | ||
2120 | fatal("In GSSAPI monitor when GSSAPI is disabled"); | ||
2121 | |||
2122 | data.value = buffer_get_string(m, &len); | ||
2123 | data.length = len; | ||
2124 | if (data.length != 20) | ||
2125 | fatal("%s: data length incorrect: %d", __func__, | ||
2126 | (int) data.length); | ||
2127 | |||
2128 | /* Save the session ID on the first time around */ | ||
2129 | if (session_id2_len == 0) { | ||
2130 | session_id2_len = data.length; | ||
2131 | session_id2 = xmalloc(session_id2_len); | ||
2132 | memcpy(session_id2, data.value, session_id2_len); | ||
2133 | } | ||
2134 | major = ssh_gssapi_sign(gsscontext, &data, &hash); | ||
2135 | |||
2136 | free(data.value); | ||
2137 | |||
2138 | buffer_clear(m); | ||
2139 | buffer_put_int(m, major); | ||
2140 | buffer_put_string(m, hash.value, hash.length); | ||
2141 | |||
2142 | mm_request_send(socket, MONITOR_ANS_GSSSIGN, m); | ||
2143 | |||
2144 | gss_release_buffer(&minor, &hash); | ||
2145 | |||
2146 | /* Turn on getpwnam permissions */ | ||
2147 | monitor_permit(mon_dispatch, MONITOR_REQ_PWNAM, 1); | ||
2148 | |||
2149 | /* And credential updating, for when rekeying */ | ||
2150 | monitor_permit(mon_dispatch, MONITOR_REQ_GSSUPCREDS, 1); | ||
2151 | |||
2152 | return (0); | ||
2153 | } | ||
2154 | |||
2155 | int | ||
2156 | mm_answer_gss_updatecreds(int socket, Buffer *m) { | ||
2157 | ssh_gssapi_ccache store; | ||
2158 | int ok; | ||
2159 | |||
2160 | store.filename = buffer_get_string(m, NULL); | ||
2161 | store.envvar = buffer_get_string(m, NULL); | ||
2162 | store.envval = buffer_get_string(m, NULL); | ||
2163 | |||
2164 | ok = ssh_gssapi_update_creds(&store); | ||
2165 | |||
2166 | free(store.filename); | ||
2167 | free(store.envvar); | ||
2168 | free(store.envval); | ||
2169 | |||
2170 | buffer_clear(m); | ||
2171 | buffer_put_int(m, ok); | ||
2172 | |||
2173 | mm_request_send(socket, MONITOR_ANS_GSSUPCREDS, m); | ||
2174 | |||
2175 | return(0); | ||
2176 | } | ||
2177 | |||
2072 | #endif /* GSSAPI */ | 2178 | #endif /* GSSAPI */ |
2073 | 2179 | ||