summaryrefslogtreecommitdiff
path: root/auth.c
diff options
context:
space:
mode:
authorSimon Wilkinson <simon@sxw.org.uk>2014-02-09 16:09:48 +0000
committerColin Watson <cjwatson@debian.org>2017-10-04 13:54:43 +0100
commit4e70490950e5c5134df48848affaf73685bf0284 (patch)
tree59de097e770693fb1f81268e85f7802df32cb58e /auth.c
parent62f54f20bf351468e0124f63cc2902ee40d9b0e9 (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: 2017-10-04 Patch-Name: gssapi.patch
Diffstat (limited to 'auth.c')
-rw-r--r--auth.c96
1 files changed, 2 insertions, 94 deletions
diff --git a/auth.c b/auth.c
index a44906174..6aec36052 100644
--- a/auth.c
+++ b/auth.c
@@ -395,7 +395,8 @@ auth_root_allowed(const char *method)
395 case PERMIT_NO_PASSWD: 395 case PERMIT_NO_PASSWD:
396 if (strcmp(method, "publickey") == 0 || 396 if (strcmp(method, "publickey") == 0 ||
397 strcmp(method, "hostbased") == 0 || 397 strcmp(method, "hostbased") == 0 ||
398 strcmp(method, "gssapi-with-mic") == 0) 398 strcmp(method, "gssapi-with-mic") == 0 ||
399 strcmp(method, "gssapi-keyex") == 0)
399 return 1; 400 return 1;
400 break; 401 break;
401 case PERMIT_FORCED_ONLY: 402 case PERMIT_FORCED_ONLY:
@@ -728,99 +729,6 @@ fakepw(void)
728} 729}
729 730
730/* 731/*
731 * Returns the remote DNS hostname as a string. The returned string must not
732 * be freed. NB. this will usually trigger a DNS query the first time it is
733 * called.
734 * This function does additional checks on the hostname to mitigate some
735 * attacks on legacy rhosts-style authentication.
736 * XXX is RhostsRSAAuthentication vulnerable to these?
737 * XXX Can we remove these checks? (or if not, remove RhostsRSAAuthentication?)
738 */
739
740static char *
741remote_hostname(struct ssh *ssh)
742{
743 struct sockaddr_storage from;
744 socklen_t fromlen;
745 struct addrinfo hints, *ai, *aitop;
746 char name[NI_MAXHOST], ntop2[NI_MAXHOST];
747 const char *ntop = ssh_remote_ipaddr(ssh);
748
749 /* Get IP address of client. */
750 fromlen = sizeof(from);
751 memset(&from, 0, sizeof(from));
752 if (getpeername(ssh_packet_get_connection_in(ssh),
753 (struct sockaddr *)&from, &fromlen) < 0) {
754 debug("getpeername failed: %.100s", strerror(errno));
755 return strdup(ntop);
756 }
757
758 ipv64_normalise_mapped(&from, &fromlen);
759 if (from.ss_family == AF_INET6)
760 fromlen = sizeof(struct sockaddr_in6);
761
762 debug3("Trying to reverse map address %.100s.", ntop);
763 /* Map the IP address to a host name. */
764 if (getnameinfo((struct sockaddr *)&from, fromlen, name, sizeof(name),
765 NULL, 0, NI_NAMEREQD) != 0) {
766 /* Host name not found. Use ip address. */
767 return strdup(ntop);
768 }
769
770 /*
771 * if reverse lookup result looks like a numeric hostname,
772 * someone is trying to trick us by PTR record like following:
773 * 1.1.1.10.in-addr.arpa. IN PTR 2.3.4.5
774 */
775 memset(&hints, 0, sizeof(hints));
776 hints.ai_socktype = SOCK_DGRAM; /*dummy*/
777 hints.ai_flags = AI_NUMERICHOST;
778 if (getaddrinfo(name, NULL, &hints, &ai) == 0) {
779 logit("Nasty PTR record \"%s\" is set up for %s, ignoring",
780 name, ntop);
781 freeaddrinfo(ai);
782 return strdup(ntop);
783 }
784
785 /* Names are stored in lowercase. */
786 lowercase(name);
787
788 /*
789 * Map it back to an IP address and check that the given
790 * address actually is an address of this host. This is
791 * necessary because anyone with access to a name server can
792 * define arbitrary names for an IP address. Mapping from
793 * name to IP address can be trusted better (but can still be
794 * fooled if the intruder has access to the name server of
795 * the domain).
796 */
797 memset(&hints, 0, sizeof(hints));
798 hints.ai_family = from.ss_family;
799 hints.ai_socktype = SOCK_STREAM;
800 if (getaddrinfo(name, NULL, &hints, &aitop) != 0) {
801 logit("reverse mapping checking getaddrinfo for %.700s "
802 "[%s] failed.", name, ntop);
803 return strdup(ntop);
804 }
805 /* Look for the address from the list of addresses. */
806 for (ai = aitop; ai; ai = ai->ai_next) {
807 if (getnameinfo(ai->ai_addr, ai->ai_addrlen, ntop2,
808 sizeof(ntop2), NULL, 0, NI_NUMERICHOST) == 0 &&
809 (strcmp(ntop, ntop2) == 0))
810 break;
811 }
812 freeaddrinfo(aitop);
813 /* If we reached the end of the list, the address was not there. */
814 if (ai == NULL) {
815 /* Address not found for the host name. */
816 logit("Address %.100s maps to %.600s, but this does not "
817 "map back to the address.", ntop, name);
818 return strdup(ntop);
819 }
820 return strdup(name);
821}
822
823/*
824 * Return the canonical name of the host in the other side of the current 732 * Return the canonical name of the host in the other side of the current
825 * connection. The host name is cached, so it is efficient to call this 733 * connection. The host name is cached, so it is efficient to call this
826 * several times. 734 * several times.