X-Git-Url: https://git.gag.com/?a=blobdiff_plain;f=common-src%2Fbsd-security.c;h=2d4304e64212f9909e13316c8697e2f2da33fcfb;hb=c4f19a4c1ce2b200d4e18c880257a4389bd5368c;hp=4be79482bb6bc036871bcc539bab6b8c6d133dd2;hpb=e442edb4d5816c4ad107ad9e71164f845eba70ad;p=debian%2Famanda diff --git a/common-src/bsd-security.c b/common-src/bsd-security.c index 4be7948..2d4304e 100644 --- a/common-src/bsd-security.c +++ b/common-src/bsd-security.c @@ -39,7 +39,6 @@ #include "security-util.h" #include "sockaddr-util.h" #include "stream.h" -#include "version.h" #ifndef SO_RCVBUF #undef DUMPER_SOCKET_BUFFERING @@ -74,6 +73,7 @@ const security_driver_t bsd_security_driver = { "BSD", bsd_connect, bsd_accept, + sec_get_authenticated_peer_name_hostname, bsd_close, udpbsd_sendpkt, udp_recvpkt, @@ -124,7 +124,6 @@ bsd_connect( void * datap) { struct sec_handle *bh; - struct servent *se; in_port_t port = 0; struct timeval sequence_time; int sequence; @@ -133,13 +132,14 @@ bsd_connect( struct addrinfo *res, *res_addr; char *canonname; int result_bind; + char *service; assert(hostname != NULL); (void)conf_fn; /* Quiet unused parameter warning */ (void)datap; /* Quiet unused parameter warning */ - bh = alloc(SIZEOF(*bh)); + bh = g_new0(struct sec_handle, 1); bh->proto_handle=NULL; security_handleinit(&bh->sech, &bsd_security_driver); @@ -156,15 +156,16 @@ bsd_connect( security_seterror(&bh->sech, _("resolve_hostname(%s) did not return a canonical name\n"), hostname); (*fn)(arg, &bh->sech, S_ERROR); - return; + if (res) freeaddrinfo(res); + return; } if (res == NULL) { dbprintf(_("resolve_hostname(%s): no results\n"), hostname); security_seterror(&bh->sech, _("resolve_hostname(%s): no results\n"), hostname); (*fn)(arg, &bh->sech, S_ERROR); - amfree(canonname); - return; + amfree(canonname); + return; } for (res_addr = res; res_addr != NULL; res_addr = res_addr->ai_next) { @@ -177,10 +178,8 @@ bsd_connect( * Only init the IPv6 socket once */ if (res_addr->ai_addr->sa_family == AF_INET6 && not_init6 == 1) { - uid_t euid; dgram_zero(&netfd6.dgram); - euid = geteuid(); set_root_privs(1); result_bind = dgram_bind(&netfd6.dgram, res_addr->ai_addr->sa_family, &port); @@ -219,10 +218,8 @@ bsd_connect( * Only init the IPv4 socket once */ if (res_addr->ai_addr->sa_family == AF_INET && not_init4 == 1) { - uid_t euid; dgram_zero(&netfd4.dgram); - euid = geteuid(); set_root_privs(1); result_bind = dgram_bind(&netfd4.dgram, res_addr->ai_addr->sa_family, &port); @@ -269,10 +266,22 @@ bsd_connect( bh->udp = &netfd4; auth_debug(1, _("Resolved hostname=%s\n"), canonname); - if ((se = getservbyname(AMANDA_SERVICE_NAME, "udp")) == NULL) - port = AMANDA_SERVICE_DEFAULT; - else - port = (in_port_t)ntohs(se->s_port); + + if (conf_fn) { + service = conf_fn("client_port", datap); + if (!service || strlen(service) <= 1) + service = "amanda"; + } else { + service = "amanda"; + } + port = find_port_for_service(service, "udp"); + if (port == 0) { + security_seterror(&bh->sech, _("%s/udp unknown protocol"), service); + (*fn)(arg, &bh->sech, S_ERROR); + amfree(canonname); + return; + } + amanda_gettimeofday(&sequence_time); sequence = (int)sequence_time.tv_sec ^ (int)sequence_time.tv_usec; handle=alloc(15); @@ -304,6 +313,7 @@ bsd_accept( void (*fn)(security_handle_t *, pkt_t *), void *datap) { + struct stat sbuf; assert(in >= 0 && out >= 0); assert(fn != NULL); @@ -330,7 +340,13 @@ bsd_accept( netfd4.prefix_packet = &bsd_prefix_packet; netfd4.driver = &bsd_security_driver; - udp_addref(&netfd4, &udp_netfd_read_callback); + /* check if in is a socket */ + fstat(in, &sbuf); + if (S_ISSOCK(sbuf.st_mode)) { + udp_addref(&netfd4, &udp_netfd_read_callback); + } else { + g_warning("input file descriptor is not a socket; cannot use BSD auth"); + } } /* @@ -386,7 +402,7 @@ bsd_stream_server( assert(bh != NULL); - bs = alloc(SIZEOF(*bs)); + bs = g_new0(struct sec_stream, 1); security_streaminit(&bs->secstr, &bsd_security_driver); bs->socket = stream_server(SU_GET_FAMILY(&bh->udp->peer), &bs->port, (size_t)STREAM_BUFSIZE, (size_t)STREAM_BUFSIZE, @@ -441,7 +457,7 @@ bsd_stream_client( assert(bh != NULL); - bs = alloc(SIZEOF(*bs)); + bs = g_new0(struct sec_stream, 1); security_streaminit(&bs->secstr, &bsd_security_driver); bs->fd = stream_client(bh->hostname, (in_port_t)id, STREAM_BUFSIZE, STREAM_BUFSIZE, &bs->port, 0); @@ -528,6 +544,10 @@ bsd_stream_read( bs->arg = arg; } +/* buffer for bsd_stream_read_sync function */ +static ssize_t sync_pktlen; +static void *sync_pkt; + /* * Read a chunk of data to a stream. Blocks until completion. */ @@ -546,11 +566,13 @@ bsd_stream_read_sync( if(bs->ev_read != NULL) { return -1; } + sync_pktlen = 0; + sync_pkt = NULL; bs->ev_read = event_register((event_id_t)bs->fd, EV_READFD, stream_read_sync_callback, bs); event_wait(bs->ev_read); - *buf = bs->databuf; - return (bs->len); + *buf = sync_pkt; + return (sync_pktlen); } @@ -576,8 +598,11 @@ stream_read_sync_callback( n = read(bs->fd, bs->databuf, sizeof(bs->databuf)); } while ((n < 0) && ((errno == EINTR) || (errno == EAGAIN))); if (n < 0) - security_stream_seterror(&bs->secstr, strerror(errno)); + security_stream_seterror(&bs->secstr, "%s", strerror(errno)); bs->len = n; + sync_pktlen = bs->len; + sync_pkt = malloc(sync_pktlen); + memcpy(sync_pkt, bs->databuf, sync_pktlen); } /* @@ -618,7 +643,7 @@ stream_read_callback( } while ((n < 0) && ((errno == EINTR) || (errno == EAGAIN))); if (n < 0) - security_stream_seterror(&bs->secstr, strerror(errno)); + security_stream_seterror(&bs->secstr, "%s", strerror(errno)); (*bs->fn)(bs->arg, bs->databuf, n); }