summaryrefslogtreecommitdiff
path: root/sshd.c
diff options
context:
space:
mode:
authorSimon Wilkinson <simon@sxw.org.uk>2014-02-09 16:09:48 +0000
committerColin Watson <cjwatson@debian.org>2015-11-29 17:36:18 +0000
commit09c4d9b7d41ab3c9973f07e0109e931f57c59c43 (patch)
tree238d7d86bfd8c0080d01fb55cef2ad37df46bd2e /sshd.c
parent651211fd4a199b299540c00c54a46e27fadb04be (diff)
GSSAPI key exchange support
This patch has been rejected upstream: "None of the OpenSSH developers are in favour of adding this, and this situation has not changed for several years. This is not a slight on Simon's patch, which is of fine quality, but just that a) we don't trust GSSAPI implementations that much and b) we don't like adding new KEX since they are pre-auth attack surface. This one is particularly scary, since it requires hooks out to typically root-owned system resources." However, quite a lot of people rely on this in Debian, and it's better to have it merged into the main openssh package rather than having separate -krb5 packages (as we used to have). It seems to have a generally good security history. Bug: https://bugzilla.mindrot.org/show_bug.cgi?id=1242 Last-Updated: 2015-11-29 Patch-Name: gssapi.patch
Diffstat (limited to 'sshd.c')
-rw-r--r--sshd.c110
1 files changed, 110 insertions, 0 deletions
diff --git a/sshd.c b/sshd.c
index 65ef7e850..839c2e02d 100644
--- a/sshd.c
+++ b/sshd.c
@@ -126,6 +126,10 @@
126#include "version.h" 126#include "version.h"
127#include "ssherr.h" 127#include "ssherr.h"
128 128
129#ifdef USE_SECURITY_SESSION_API
130#include <Security/AuthSession.h>
131#endif
132
129#ifndef O_NOCTTY 133#ifndef O_NOCTTY
130#define O_NOCTTY 0 134#define O_NOCTTY 0
131#endif 135#endif
@@ -1827,10 +1831,13 @@ main(int ac, char **av)
1827 logit("Disabling protocol version 1. Could not load host key"); 1831 logit("Disabling protocol version 1. Could not load host key");
1828 options.protocol &= ~SSH_PROTO_1; 1832 options.protocol &= ~SSH_PROTO_1;
1829 } 1833 }
1834#ifndef GSSAPI
1835 /* The GSSAPI key exchange can run without a host key */
1830 if ((options.protocol & SSH_PROTO_2) && !sensitive_data.have_ssh2_key) { 1836 if ((options.protocol & SSH_PROTO_2) && !sensitive_data.have_ssh2_key) {
1831 logit("Disabling protocol version 2. Could not load host key"); 1837 logit("Disabling protocol version 2. Could not load host key");
1832 options.protocol &= ~SSH_PROTO_2; 1838 options.protocol &= ~SSH_PROTO_2;
1833 } 1839 }
1840#endif
1834 if (!(options.protocol & (SSH_PROTO_1|SSH_PROTO_2))) { 1841 if (!(options.protocol & (SSH_PROTO_1|SSH_PROTO_2))) {
1835 logit("sshd: no hostkeys available -- exiting."); 1842 logit("sshd: no hostkeys available -- exiting.");
1836 exit(1); 1843 exit(1);
@@ -2145,6 +2152,60 @@ main(int ac, char **av)
2145 remote_ip, remote_port, laddr, get_local_port()); 2152 remote_ip, remote_port, laddr, get_local_port());
2146 free(laddr); 2153 free(laddr);
2147 2154
2155#ifdef USE_SECURITY_SESSION_API
2156 /*
2157 * Create a new security session for use by the new user login if
2158 * the current session is the root session or we are not launched
2159 * by inetd (eg: debugging mode or server mode). We do not
2160 * necessarily need to create a session if we are launched from
2161 * inetd because Panther xinetd will create a session for us.
2162 *
2163 * The only case where this logic will fail is if there is an
2164 * inetd running in a non-root session which is not creating
2165 * new sessions for us. Then all the users will end up in the
2166 * same session (bad).
2167 *
2168 * When the client exits, the session will be destroyed for us
2169 * automatically.
2170 *
2171 * We must create the session before any credentials are stored
2172 * (including AFS pags, which happens a few lines below).
2173 */
2174 {
2175 OSStatus err = 0;
2176 SecuritySessionId sid = 0;
2177 SessionAttributeBits sattrs = 0;
2178
2179 err = SessionGetInfo(callerSecuritySession, &sid, &sattrs);
2180 if (err)
2181 error("SessionGetInfo() failed with error %.8X",
2182 (unsigned) err);
2183 else
2184 debug("Current Session ID is %.8X / Session Attributes are %.8X",
2185 (unsigned) sid, (unsigned) sattrs);
2186
2187 if (inetd_flag && !(sattrs & sessionIsRoot))
2188 debug("Running in inetd mode in a non-root session... "
2189 "assuming inetd created the session for us.");
2190 else {
2191 debug("Creating new security session...");
2192 err = SessionCreate(0, sessionHasTTY | sessionIsRemote);
2193 if (err)
2194 error("SessionCreate() failed with error %.8X",
2195 (unsigned) err);
2196
2197 err = SessionGetInfo(callerSecuritySession, &sid,
2198 &sattrs);
2199 if (err)
2200 error("SessionGetInfo() failed with error %.8X",
2201 (unsigned) err);
2202 else
2203 debug("New Session ID is %.8X / Session Attributes are %.8X",
2204 (unsigned) sid, (unsigned) sattrs);
2205 }
2206 }
2207#endif
2208
2148 /* 2209 /*
2149 * We don't want to listen forever unless the other side 2210 * We don't want to listen forever unless the other side
2150 * successfully authenticates itself. So we set up an alarm which is 2211 * successfully authenticates itself. So we set up an alarm which is
@@ -2563,6 +2624,48 @@ do_ssh2_kex(void)
2563 myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS] = compat_pkalg_proposal( 2624 myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS] = compat_pkalg_proposal(
2564 list_hostkey_types()); 2625 list_hostkey_types());
2565 2626
2627#ifdef GSSAPI
2628 {
2629 char *orig;
2630 char *gss = NULL;
2631 char *newstr = NULL;
2632 orig = myproposal[PROPOSAL_KEX_ALGS];
2633
2634 /*
2635 * If we don't have a host key, then there's no point advertising
2636 * the other key exchange algorithms
2637 */
2638
2639 if (strlen(myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS]) == 0)
2640 orig = NULL;
2641
2642 if (options.gss_keyex)
2643 gss = ssh_gssapi_server_mechanisms();
2644 else
2645 gss = NULL;
2646
2647 if (gss && orig)
2648 xasprintf(&newstr, "%s,%s", gss, orig);
2649 else if (gss)
2650 newstr = gss;
2651 else if (orig)
2652 newstr = orig;
2653
2654 /*
2655 * If we've got GSSAPI mechanisms, then we've got the 'null' host
2656 * key alg, but we can't tell people about it unless its the only
2657 * host key algorithm we support
2658 */
2659 if (gss && (strlen(myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS])) == 0)
2660 myproposal[PROPOSAL_SERVER_HOST_KEY_ALGS] = "null";
2661
2662 if (newstr)
2663 myproposal[PROPOSAL_KEX_ALGS] = newstr;
2664 else
2665 fatal("No supported key exchange algorithms");
2666 }
2667#endif
2668
2566 /* start key exchange */ 2669 /* start key exchange */
2567 if ((r = kex_setup(active_state, myproposal)) != 0) 2670 if ((r = kex_setup(active_state, myproposal)) != 0)
2568 fatal("kex_setup: %s", ssh_err(r)); 2671 fatal("kex_setup: %s", ssh_err(r));
@@ -2577,6 +2680,13 @@ do_ssh2_kex(void)
2577# endif 2680# endif
2578#endif 2681#endif
2579 kex->kex[KEX_C25519_SHA256] = kexc25519_server; 2682 kex->kex[KEX_C25519_SHA256] = kexc25519_server;
2683#ifdef GSSAPI
2684 if (options.gss_keyex) {
2685 kex->kex[KEX_GSS_GRP1_SHA1] = kexgss_server;
2686 kex->kex[KEX_GSS_GRP14_SHA1] = kexgss_server;
2687 kex->kex[KEX_GSS_GEX_SHA1] = kexgss_server;
2688 }
2689#endif
2580 kex->server = 1; 2690 kex->server = 1;
2581 kex->client_version_string=client_version_string; 2691 kex->client_version_string=client_version_string;
2582 kex->server_version_string=server_version_string; 2692 kex->server_version_string=server_version_string;