use new addr_families functions

git-svn-id: svn://svn.h5l.se/heimdal/trunk/heimdal@3517 ec53bebd-3082-4978-b11e-865c3cabbd6b
This commit is contained in:
Assar Westerlund
1997-09-21 13:24:31 +00:00
parent ebe1fa6374
commit 2ca944d2bc
5 changed files with 168 additions and 234 deletions

View File

@@ -132,81 +132,55 @@ krb5_auth_con_setaddrs(krb5_context context,
return 0;
}
static void
sockaddr2krb5_address (struct sockaddr *sa,
krb5_address *ka)
{
switch (sa->sa_family) {
case AF_INET: {
struct sockaddr_in *sin = (struct sockaddr_in *)sa;
ka->addr_type = AF_INET;
ka->address.length = sizeof(sin->sin_addr);
ka->address.data = &sin->sin_addr;
break;
}
#if defined(AF_INET6) && defined(HAVE_SOCKADDR_IN6)
case AF_INET6: {
struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)sa;
if (IN6_IS_ADDR_V4MAPPED(&sin6->sin6_addr)) {
ka->addr_type = AF_INET;
ka->address.length = sizeof(struct in_addr);
#ifndef IN6_ADDR_V6_TO_V4
#define IN6_ADDR_V6_TO_V4(x) (&IN6_EXTRACT_V4ADDR(x))
#endif
ka->address.data = IN6_ADDR_V6_TO_V4(&sin6->sin6_addr);
} else {
ka->addr_type = AF_INET6;
ka->address.length = sizeof(sin6->sin6_addr);
ka->address.data = &sin6->sin6_addr;
}
break;
}
#endif
default:
break;
}
}
krb5_error_code
krb5_auth_con_setaddrs_from_fd (krb5_context context,
krb5_auth_context auth_context,
int fd)
{
krb5_address *lptr = NULL, *rptr = NULL;
krb5_error_code ret;
krb5_address local_k_address, remote_k_address;
#if defined(AF_INET6) && defined(HAVE_SOCKADDR_IN6)
struct sockaddr_in6 local_addr, remote_addr;
#else
struct sockaddr_in local_addr, remote_addr;
#endif
krb5_address *lptr = NULL, *rptr = NULL;
size_t max_sz = krb5_max_sockaddr_size ();
char *buf1 = NULL, *buf2 = NULL;
struct sockaddr *local, *remote;
int len;
buf1 = malloc(max_sz);
if (buf1 == NULL) {
ret = ENOMEM;
goto out;
}
local = (struct sockaddr *)buf1;
buf2 = malloc(max_sz);
if (buf2 == NULL) {
ret = ENOMEM;
goto out;
}
remote = (struct sockaddr *)buf2;
if (auth_context->local_address == NULL) {
len = sizeof (local_addr);
if (getsockname (fd, (struct sockaddr *)&local_addr, &len) < 0)
return errno;
sockaddr2krb5_address((struct sockaddr *)&local_addr,
&local_k_address);
len = max_sz;
if(getsockname(fd, local, &len) < 0)
goto out;
krb5_sockaddr2address (local, &local_k_address);
lptr = &local_k_address;
}
if (auth_context->remote_address == NULL) {
len = sizeof (remote_addr);
if (getpeername (fd, (struct sockaddr *)&remote_addr, &len) < 0)
return errno;
sockaddr2krb5_address((struct sockaddr *)&remote_addr,
&remote_k_address);
len = max_sz;
if(getpeername(fd, remote, &len) < 0)
goto out;
krb5_sockaddr2address (remote, &remote_k_address);
rptr = &remote_k_address;
}
return krb5_auth_con_setaddrs (context,
auth_context,
lptr,
rptr);
ret = krb5_auth_con_setaddrs (context,
auth_context,
lptr,
rptr);
out:
free (buf1);
free (buf2);
return ret;
}
krb5_error_code

View File

@@ -174,52 +174,13 @@ find_all_addresses (krb5_addresses *res, int loop,
|| memcmp (sa, &sa_zero, sizeof(sa_zero)) == 0)
continue;
switch (sa->sa_family) {
#ifdef AF_INET
case AF_INET: {
unsigned char addr[4];
struct sockaddr_in *sin;
res->val[j].addr_type = AF_INET;
/* This is somewhat XXX */
sin = (struct sockaddr_in*)sa;
memcpy(addr, &sin->sin_addr, 4);
ret = krb5_data_copy(&res->val[j].address,
addr, 4);
if (ret)
goto error_out;
++j;
break;
}
#endif /* AF_INET */
#if defined(AF_INET6) && defined(HAVE_SOCKADDR_IN6)
case AF_INET6: {
struct in6_addr *sin6;
if (krb5_sockaddr_uninteresting (sa))
continue;
sin6 = &((struct sockaddr_in6 *)(&ifr->ifr_addr))->sin6_addr;
#ifndef IN6_IS_ADDR_LOOPBACK
#define IN6_IS_ADDR_LOOPBACK(x) IN6_IS_LOOPBACK(*x)
#endif
if (IN6_IS_ADDR_LOOPBACK(sin6)
|| IN6_IS_ADDR_LINKLOCAL(sin6)
|| IN6_IS_ADDR_V4COMPAT(sin6)) {
break;
} else {
res->val[j].addr_type = AF_INET6;
ret = krb5_data_copy(&res->val[j].address,
sin6,
sizeof(struct in6_addr));
}
if (ret)
goto error_out;
++j;
break;
}
#endif /* AF_INET6 */
default:
break;
}
ret = krb5_sockaddr2address (sa, &res->val[j]);
if (ret)
goto error_out;
++j;
}
if (j != num) {
void *tmp;

View File

@@ -138,26 +138,36 @@ krb5_sendto_kdc (krb5_context context,
const krb5_realm *realm,
krb5_data *receive)
{
krb5_error_code err;
krb5_error_code ret;
char **hostlist, **hp, *p;
struct hostent *hostent;
int fd;
int port;
int i;
char *buf;
struct sockaddr *sa;
port = krb5_getportbyname (context, "kerberos", "udp", 88);
err = krb5_get_krbhst (context, realm, &hostlist);
if (err) {
ret = krb5_get_krbhst (context, realm, &hostlist);
if (ret) {
close (fd);
return err;
return ret;
}
buf = malloc(krb5_max_sockaddr_size ());
if (buf == NULL) {
ret = ENOMEM;
goto out;
}
sa = (struct sockaddr *)buf;
for (i = 0; i < context->max_retries; ++i)
for (hp = hostlist; (p = *hp); ++hp) {
char *addr;
char *colon;
int http_flag = 0;
int sa_size;
if(strncmp(p, "http://", 7) == 0){
p += 7;
@@ -178,46 +188,24 @@ krb5_sendto_kdc (krb5_context context,
if (colon)
*colon++ = ':';
while ((addr = *hostent->h_addr_list++)) {
int ret;
int family;
struct sockaddr *sa;
int sa_size;
struct sockaddr_in sin;
#if defined(AF_INET6) && defined(HAVE_SOCKADDR_IN6)
struct sockaddr_in6 sin6;
#endif
family = hostent->h_addrtype;
int family = hostent->h_addrtype;
if(http_flag)
fd = socket(family, SOCK_STREAM, 0);
else
fd = socket(family, SOCK_DGRAM, 0);
if(fd < 0)
return errno;
switch (family) {
case AF_INET :
memset(&sin, 0, sizeof(sin));
sa_size = sizeof(sin);
sa = (struct sockaddr *)&sin;
sin.sin_family = family;
sin.sin_port = init_port(colon, port);
sin.sin_addr = *((struct in_addr *)addr);
break;
#if defined(AF_INET6) && defined(HAVE_SOCKADDR_IN6)
case AF_INET6:
memset(&sin6, 0, sizeof(sin6));
sa_size = sizeof(sin6);
sa = (struct sockaddr *)&sin6;
sin6.sin6_family = family;
sin6.sin6_port = init_port(colon, port);
sin6.sin6_addr = *((struct in6_addr *)addr);
break;
#endif
default:
continue;
if(fd < 0) {
ret = errno;
goto out;
}
ret = krb5_h_addr2sockaddr (family,
addr,
sa,
&sa_size,
init_port(colon, port));
if (ret)
continue;
if(connect(fd, sa, sa_size) < 0) {
close (fd);
@@ -232,12 +220,13 @@ krb5_sendto_kdc (krb5_context context,
ret = send_and_recv (fd, context->kdc_timeout, 1,
send, receive);
close (fd);
if(ret == 0){
krb5_free_krbhst (context, hostlist);
return 0;
}
if(ret == 0)
goto out;
}
}
ret = KRB5_KDC_UNREACH;
out:
krb5_free_krbhst (context, hostlist);
return KRB5_KDC_UNREACH;
free (buf);
return ret;
}

View File

@@ -48,34 +48,31 @@ krb5_sock_to_principal (krb5_context context,
krb5_principal *ret_princ)
{
krb5_error_code ret;
#if defined(AF_INET6) && defined(HAVE_SOCKADDR_IN6)
struct sockaddr_in6 addr;
#else
struct sockaddr_in addr;
#endif
int len = sizeof(addr);
krb5_address address;
int len = krb5_max_sockaddr_size ();
char *buf = malloc(len);
struct sockaddr *sa;
struct hostent *hostent;
int family;
if (getsockname (sock, (struct sockaddr *)&addr, &len) < 0)
if (buf == NULL)
return ENOMEM;
sa = (struct sockaddr *)buf;
if (getsockname (sock, sa, &len) < 0) {
free (buf);
return errno;
#if defined(AF_INET6) && defined(HAVE_SOCKADDR_IN6)
if(len == sizeof(struct sockaddr_in6))
hostent = gethostbyaddr ((const char *)&addr.sin6_addr,
sizeof(addr.sin6_addr),
addr.sin6_family);
else {
struct sockaddr_in *foo = (struct sockaddr_in *)&addr;
hostent = gethostbyaddr ((const char *)&foo->sin_addr,
sizeof(foo->sin_addr),
foo->sin_family);
}
#else
hostent = gethostbyaddr ((const char *)&addr.sin_addr,
sizeof(addr.sin_addr),
addr.sin_family);
#endif
family = sa->sa_family;
ret = krb5_sockaddr2address (sa, &address);
free (buf);
if (ret)
return ret;
hostent = gethostbyaddr (address.address.data,
address.address.length,
family);
if (hostent == NULL)
return h_errno;