#include "xmalloc.h"
#include "ssh.h"
-/* Return the canonical name of the host at the other end of the socket.
- The caller should free the returned string with xfree. */
+/*
+ * Return the canonical name of the host at the other end of the socket. The
+ * caller should free the returned string with xfree.
+ */
char *
get_remote_hostname(int socket)
else
strlcpy(name, hp->h_name, sizeof(name));
- /* Convert it to all lowercase (which is expected by the
- rest of this software). */
+ /*
+ * Convert it to all lowercase (which is expected by the rest
+ * of this software).
+ */
for (i = 0; name[i]; i++)
if (isupper(name[i]))
name[i] = tolower(name[i]);
- /* Map it back to an IP address and check that the given
- address actually is an address of this host. This is
- necessary because anyone with access to a name server
- can define arbitrary names for an IP address. Mapping
- from name to IP address can be trusted better (but can
- still be fooled if the intruder has access to the name
- server of the domain). */
+ /*
+ * Map it back to an IP address and check that the given
+ * address actually is an address of this host. This is
+ * necessary because anyone with access to a name server can
+ * define arbitrary names for an IP address. Mapping from
+ * name to IP address can be trusted better (but can still be
+ * fooled if the intruder has access to the name server of
+ * the domain).
+ */
hp = gethostbyname(name);
if (!hp) {
log("reverse mapping checking gethostbyname for %.700s failed - POSSIBLE BREAKIN ATTEMPT!", name);
if (memcmp(hp->h_addr_list[i], &from.sin_addr, sizeof(from.sin_addr))
== 0)
break;
- /* If we reached the end of the list, the address was not
- there. */
+ /*
+ * If we reached the end of the list, the address was not
+ * there.
+ */
if (!hp->h_addr_list[i]) {
/* Address not found for the host name. */
log("Address %.100s maps to %.600s, but this does not map back to the address - POSSIBLE BREAKIN ATTEMPT!",
check_ip_options:
- /* If IP options are supported, make sure there are none (log and
- disconnect them if any are found). Basically we are worried
- about source routing; it can be used to pretend you are
- somebody (ip-address) you are not. That itself may be "almost
- acceptable" under certain circumstances, but rhosts
- autentication is useless if source routing is accepted. Notice
- also that if we just dropped source routing here, the other
- side could use IP spoofing to do rest of the interaction and
- could still bypass security. So we exit here if we detect any
- IP options. */
+ /*
+ * If IP options are supported, make sure there are none (log and
+ * disconnect them if any are found). Basically we are worried about
+ * source routing; it can be used to pretend you are somebody
+ * (ip-address) you are not. That itself may be "almost acceptable"
+ * under certain circumstances, but rhosts autentication is useless
+ * if source routing is accepted. Notice also that if we just dropped
+ * source routing here, the other side could use IP spoofing to do
+ * rest of the interaction and could still bypass security. So we
+ * exit here if we detect any IP options.
+ */
{
unsigned char options[200], *ucp;
char text[1024], *cp;
static char *canonical_host_name = NULL;
static char *canonical_host_ip = NULL;
-/* Return the canonical name of the host in the other side of the current
- connection. The host name is cached, so it is efficient to call this
- several times. */
+/* Returns 1 if remote host is connected via socket, 0 if not. */
+
+int
+peer_connection_is_on_socket()
+{
+ struct sockaddr_in from;
+ int fromlen;
+ int in = packet_get_connection_in();
+ int out = packet_get_connection_out();
+
+ /* filedescriptors in and out are the same, so it's a socket */
+ if (in == out)
+ return 1;
+ fromlen = sizeof(from);
+ memset(&from, 0, sizeof(from));
+ if (getpeername(in, (struct sockaddr *) & from, &fromlen) < 0)
+ return 0;
+ if (from.sin_family != AF_INET)
+ return 0;
+
+ return 1;
+}
+
+/*
+ * Return the canonical name of the host in the other side of the current
+ * connection. The host name is cached, so it is efficient to call this
+ * several times.
+ */
const char *
get_canonical_hostname()
return canonical_host_name;
/* Get the real hostname if socket; otherwise return UNKNOWN. */
- if (packet_get_connection_in() == packet_get_connection_out())
+ if (peer_connection_is_on_socket())
canonical_host_name = get_remote_hostname(packet_get_connection_in());
else
canonical_host_name = xstrdup("UNKNOWN");
return canonical_host_name;
}
-/* Returns the IP-address of the remote host as a string. The returned
- string need not be freed. */
+/*
+ * Returns the IP-address of the remote host as a string. The returned
+ * string need not be freed.
+ */
const char *
get_remote_ipaddr()
struct sockaddr_in from;
int fromlen, socket;
- /* Check if we have previously retrieved this same name. */
+ /* Check whether we have chached the name. */
if (canonical_host_ip != NULL)
return canonical_host_ip;
/* If not a socket, return UNKNOWN. */
- if (packet_get_connection_in() != packet_get_connection_out()) {
+ if (!peer_connection_is_on_socket()) {
canonical_host_ip = xstrdup("UNKNOWN");
return canonical_host_ip;
}
{
int socket;
- /* If the connection is not a socket, return 65535. This is
- intentionally chosen to be an unprivileged port number. */
- if (packet_get_connection_in() != packet_get_connection_out())
+ /*
+ * If the connection is not a socket, return 65535. This is
+ * intentionally chosen to be an unprivileged port number.
+ */
+ if (!peer_connection_is_on_socket())
return 65535;
/* Get client socket. */