X-Git-Url: https://git.gag.com/?a=blobdiff_plain;f=common-src%2Fsecurity-util.c;h=bc108cdd0fbfcd4747579ce02ce4f933bdd728c9;hb=b116e9366c7b2ea2c2eb53b0a13df4090e176235;hp=77e5d0c8c914a8daac3996b5ffb0797e20d582f5;hpb=fb2bd066c2f8b34addafe48d62550e3033a59431;p=debian%2Famanda diff --git a/common-src/security-util.c b/common-src/security-util.c index 77e5d0c..bc108cd 100644 --- a/common-src/security-util.c +++ b/common-src/security-util.c @@ -37,25 +37,15 @@ #include "util.h" #include "event.h" #include "packet.h" -#include "queue.h" #include "security.h" #include "security-util.h" #include "stream.h" -#include "version.h" #include "sockaddr-util.h" -/* - * Magic values for sec_conn->handle - */ -#define H_TAKEN -1 /* sec_conn->tok was already read */ -#define H_EOF -2 /* this connection has been shut down */ - /* * This is a queue of open connections */ -struct connq_s connq = { - TAILQ_HEAD_INITIALIZER(connq.tailq), 0 -}; +GSList *connq = NULL; static int newhandle = 1; static int newevent = 1; @@ -112,7 +102,7 @@ sec_accept( { struct tcp_conn *rc; - rc = sec_tcp_conn_get("unknown",0); + rc = sec_tcp_conn_get("",0); /* no hostname yet */ rc->read = in; rc->write = out; rc->accept_fn = fn; @@ -229,7 +219,8 @@ stream_sendpkt( pkt_type2str(pkt->type), pkt->type, strlen(pkt->body), pkt->body); if (security_stream_write(&rh->rs->secstr, buf, len) < 0) { - security_seterror(&rh->sech, security_stream_geterror(&rh->rs->secstr)); + security_seterror(&rh->sech, "%s", security_stream_geterror(&rh->rs->secstr)); + amfree(buf); return (-1); } amfree(buf); @@ -330,7 +321,7 @@ tcpm_stream_write( if (tcpm_send_token(rs->rc, rs->rc->write, rs->handle, &rs->rc->errmsg, buf, size)) { - security_stream_seterror(&rs->secstr, rs->rc->errmsg); + security_stream_seterror(&rs->secstr, "%s", rs->rc->errmsg); return (-1); } return (0); @@ -354,7 +345,7 @@ tcpm_stream_read( * Only one read request can be active per stream. */ if (rs->ev_read == NULL) { - rs->ev_read = event_register((event_id_t)rs->rc, EV_WAIT, + rs->ev_read = event_register((event_id_t)rs->rc->event_id, EV_WAIT, stream_read_callback, rs); sec_tcp_conn_read(rs->rc); } @@ -362,6 +353,10 @@ tcpm_stream_read( rs->arg = arg; } +/* buffer for tcpm_stream_read_sync function */ +static ssize_t sync_pktlen; +static void *sync_pkt; + /* * Write a chunk of data to a stream. Blocks until completion. */ @@ -380,12 +375,15 @@ tcpm_stream_read_sync( if (rs->ev_read != NULL) { return -1; } - rs->ev_read = event_register((event_id_t)rs->rc, EV_WAIT, + sync_pktlen = 0; + sync_pkt = NULL; + rs->ev_read = event_register((event_id_t)rs->rc->event_id, EV_WAIT, stream_read_sync_callback, rs); sec_tcp_conn_read(rs->rc); event_wait(rs->ev_read); - *buf = rs->rc->pkt; - return (rs->rc->pktlen); + /* Can't use rs or rc, they can be freed */ + *buf = sync_pkt; + return (sync_pktlen); } /* @@ -427,11 +425,19 @@ tcpm_send_token( int rval; char *encbuf; ssize_t encsize; + int save_errno; + time_t logtime; assert(SIZEOF(netlength) == 4); + logtime = time(NULL); + if (rc && logtime > rc->logstamp + 10) { + g_debug("tcpm_send_token: data is still flowing"); + rc->logstamp = logtime; + } + auth_debug(1, "tcpm_send_token: write %zd bytes to handle %d\n", - len, handle); + len, handle); /* * Format is: * 32 bit length (network byte order) @@ -466,7 +472,8 @@ tcpm_send_token( nb_iov = 3; } - rval = net_writev(fd, iov, nb_iov); + rval = full_writev(fd, iov, nb_iov); + save_errno = errno; if (len != 0 && rc->driver->data_encrypt != NULL && buf != encbuf) { amfree(encbuf); } @@ -474,13 +481,14 @@ tcpm_send_token( if (rval < 0) { if (errmsg) *errmsg = newvstrallocf(*errmsg, _("write error to: %s"), - strerror(errno)); + strerror(save_errno)); return (-1); } return (0); } /* + * return -2 for incomplete packet * return -1 on error * return 0 on EOF: *handle = H_EOF && *size = 0 if socket closed * return 0 on EOF: *handle = handle && *size = 0 if stream closed @@ -494,93 +502,118 @@ tcpm_recv_token( int * handle, char ** errmsg, char ** buf, - ssize_t * size, - int timeout) + ssize_t * size) { - unsigned int netint[2]; - - assert(SIZEOF(netint) == 8); - - switch (net_read(fd, &netint, SIZEOF(netint), timeout)) { - case -1: - if (errmsg) - *errmsg = newvstrallocf(*errmsg, _("recv error: %s"), strerror(errno)); - auth_debug(1, _("tcpm_recv_token: A return(-1)\n")); - return (-1); - case 0: - *size = 0; - *handle = H_EOF; - *errmsg = newvstrallocf(*errmsg, _("SOCKET_EOF")); - auth_debug(1, _("tcpm_recv_token: A return(0)\n")); - return (0); - default: - break; - } - - *size = (ssize_t)ntohl(netint[0]); - *handle = (int)ntohl(netint[1]); - /* amanda protocol packet can be above NETWORK_BLOCK_BYTES */ - if (*size > 128*NETWORK_BLOCK_BYTES || *size < 0) { - if (isprint((int)(*size ) & 0xFF) && - isprint((int)(*size >> 8 ) & 0xFF) && - isprint((int)(*size >> 16) & 0xFF) && - isprint((int)(*size >> 24) & 0xFF) && - isprint((*handle ) & 0xFF) && - isprint((*handle >> 8 ) & 0xFF) && - isprint((*handle >> 16) & 0xFF) && - isprint((*handle >> 24) & 0xFF)) { - char s[101]; - int i; - s[0] = ((int)(*size) >> 24) & 0xFF; - s[1] = ((int)(*size) >> 16) & 0xFF; - s[2] = ((int)(*size) >> 8) & 0xFF; - s[3] = ((int)(*size) ) & 0xFF; - s[4] = (*handle >> 24) & 0xFF; - s[5] = (*handle >> 16) & 0xFF; - s[6] = (*handle >> 8 ) & 0xFF; - s[7] = (*handle ) & 0xFF; - i = 8; s[i] = ' '; - while(i<100 && isprint((int)s[i]) && s[i] != '\n') { - switch(net_read(fd, &s[i], 1, 0)) { - case -1: s[i] = '\0'; break; - case 0: s[i] = '\0'; break; - default: + ssize_t rval; + + assert(SIZEOF(rc->netint) == 8); + if (rc->size_header_read < (ssize_t)SIZEOF(rc->netint)) { + rval = read(fd, ((char *)&rc->netint) + rc->size_header_read, + SIZEOF(rc->netint) - rc->size_header_read); + if (rval == -1) { + if (errmsg) + *errmsg = newvstrallocf(*errmsg, _("recv error: %s"), + strerror(errno)); + auth_debug(1, _("tcpm_recv_token: A return(-1)\n")); + return(-1); + } else if (rval == 0) { + *size = 0; + *handle = H_EOF; + *errmsg = newvstrallocf(*errmsg, _("SOCKET_EOF")); + auth_debug(1, _("tcpm_recv_token: A return(0)\n")); + return(0); + } else if (rval < (ssize_t)SIZEOF(rc->netint) - rc->size_header_read) { + rc->size_header_read += rval; + return(-2); + } + rc->size_header_read += rval; + amfree(rc->buffer); + *size = (ssize_t)ntohl(rc->netint[0]); + *handle = (int)ntohl(rc->netint[1]); + rc->buffer = NULL; + rc->size_buffer_read = 0; + + /* amanda protocol packet can be above NETWORK_BLOCK_BYTES */ + if (*size > 128*NETWORK_BLOCK_BYTES || *size < 0) { + if (isprint((int)(*size ) & 0xFF) && + isprint((int)(*size >> 8 ) & 0xFF) && + isprint((int)(*size >> 16) & 0xFF) && + isprint((int)(*size >> 24) & 0xFF) && + isprint((*handle ) & 0xFF) && + isprint((*handle >> 8 ) & 0xFF) && + isprint((*handle >> 16) & 0xFF) && + isprint((*handle >> 24) & 0xFF)) { + char s[201]; + char *s1; + int i; + s[0] = ((int)(*size) >> 24) & 0xFF; + s[1] = ((int)(*size) >> 16) & 0xFF; + s[2] = ((int)(*size) >> 8) & 0xFF; + s[3] = ((int)(*size) ) & 0xFF; + s[4] = (*handle >> 24) & 0xFF; + s[5] = (*handle >> 16) & 0xFF; + s[6] = (*handle >> 8 ) & 0xFF; + s[7] = (*handle ) & 0xFF; + i = 8; s[i] = ' '; + while(i<200 && isprint((int)s[i]) && s[i] != '\n') { + switch(net_read(fd, &s[i], 1, 0)) { + case -1: s[i] = '\0'; break; + case 0: s[i] = '\0'; break; + default: dbprintf(_("read: %c\n"), s[i]); i++; s[i]=' '; break; + } } + s[i] = '\0'; + s1 = quote_string(s); + *errmsg = newvstrallocf(*errmsg, + _("tcpm_recv_token: invalid size: %s"), s1); + dbprintf(_("tcpm_recv_token: invalid size %s\n"), s1); + amfree(s1); + } else { + *errmsg = newvstrallocf(*errmsg, + _("tcpm_recv_token: invalid size")); + dbprintf(_("tcpm_recv_token: invalid size %zd\n"), *size); } - s[i] = '\0'; - *errmsg = newvstrallocf(*errmsg, _("tcpm_recv_token: invalid size: %s"), s); - dbprintf(_("tcpm_recv_token: invalid size %s\n"), s); - } else { - *errmsg = newvstrallocf(*errmsg, _("tcpm_recv_token: invalid size")); - dbprintf(_("tcpm_recv_token: invalid size %zd\n"), *size); + *size = -1; + return -1; } - *size = -1; - return -1; - } - amfree(*buf); - *buf = alloc((size_t)*size); + rc->buffer = alloc((size_t)*size); - if(*size == 0) { - auth_debug(1, _("tcpm_recv_token: read EOF from %d\n"), *handle); - *errmsg = newvstrallocf(*errmsg, _("EOF")); - return 0; + if (*size == 0) { + auth_debug(1, _("tcpm_recv_token: read EOF from %d\n"), *handle); + *errmsg = newvstrallocf(*errmsg, _("EOF")); + rc->size_header_read = 0; + return 0; + } } - switch (net_read(fd, *buf, (size_t)*size, timeout)) { - case -1: + + *size = (ssize_t)ntohl(rc->netint[0]); + *handle = (int)ntohl(rc->netint[1]); + + rval = read(fd, rc->buffer + rc->size_buffer_read, + (size_t)*size - rc->size_buffer_read); + if (rval == -1) { if (errmsg) - *errmsg = newvstrallocf(*errmsg, _("recv error: %s"), strerror(errno)); + *errmsg = newvstrallocf(*errmsg, _("recv error: %s"), + strerror(errno)); auth_debug(1, _("tcpm_recv_token: B return(-1)\n")); return (-1); - case 0: + } else if (rval == 0) { *size = 0; *errmsg = newvstrallocf(*errmsg, _("SOCKET_EOF")); auth_debug(1, _("tcpm_recv_token: B return(0)\n")); return (0); - default: - break; + } else if (rval < (ssize_t)*size - rc->size_buffer_read) { + rc->size_buffer_read += rval; + return (-2); } + rc->size_buffer_read += rval; + amfree(*buf); + *buf = rc->buffer; + rc->size_header_read = 0; + rc->size_buffer_read = 0; + rc->buffer = NULL; auth_debug(1, _("tcpm_recv_token: read %zd bytes from %d\n"), *size, *handle); @@ -607,7 +640,7 @@ tcpm_close_connection( (void)hostname; - if (rh && rh->rc && rh->rc->toclose == 0) { + if (rh && rh->rc && rh->rc->read >= 0 && rh->rc->toclose == 0) { rh->rc->toclose = 1; sec_tcp_conn_put(rh->rc); } @@ -648,7 +681,7 @@ tcpma_stream_client( return (NULL); } - rs = alloc(SIZEOF(*rs)); + rs = g_new0(struct sec_stream, 1); security_streaminit(&rs->secstr, rh->sech.driver); rs->handle = id; rs->ev_read = NULL; @@ -682,7 +715,7 @@ tcpma_stream_server( assert(rh != NULL); - rs = alloc(SIZEOF(*rs)); + rs = g_new0(struct sec_stream, 1); security_streaminit(&rs->secstr, rh->sech.driver); rs->closed_by_me = 0; rs->closed_by_network = 0; @@ -734,6 +767,7 @@ tcpma_stream_close( security_stream_read_cancel(&rs->secstr); if(rs->closed_by_network == 0) sec_tcp_conn_put(rs->rc); + amfree(((security_stream_t *)rs)->error); amfree(rs); } @@ -750,7 +784,7 @@ tcp1_stream_server( assert(rh != NULL); - rs = alloc(SIZEOF(*rs)); + rs = g_new0(struct sec_stream, 1); security_streaminit(&rs->secstr, rh->sech.driver); rs->closed_by_me = 0; rs->closed_by_network = 0; @@ -822,7 +856,7 @@ tcp1_stream_client( assert(rh != NULL); - rs = alloc(SIZEOF(*rs)); + rs = g_new0(struct sec_stream, 1); security_streaminit(&rs->secstr, rh->sech.driver); rs->handle = id; rs->ev_read = NULL; @@ -859,10 +893,17 @@ tcp_stream_write( size_t size) { struct sec_stream *rs = s; + time_t logtime; assert(rs != NULL); - if (fullwrite(rs->fd, buf, size) < 0) { + logtime = time(NULL); + if (rs && rs->rc && logtime > rs->rc->logstamp + 10) { + g_debug("tcp_stream_write: data is still flowing"); + rs->rc->logstamp = logtime; + } + + if (full_write(rs->fd, buf, size) < size) { security_stream_seterror(&rs->secstr, _("write error on stream %d: %s"), rs->port, strerror(errno)); return (-1); @@ -882,11 +923,11 @@ bsd_prefix_packet( if (pkt->type != P_REQ) return ""; - if ((pwd = getpwuid(getuid())) == NULL) { + if ((pwd = getpwuid(geteuid())) == NULL) { security_seterror(&rh->sech, _("can't get login name for my uid %ld"), - (long)getuid()); - return(NULL); + (long)geteuid()); + return ""; } buf = alloc(16+strlen(pwd->pw_name)); strncpy(buf, "SECURITY USER ", (16 + strlen(pwd->pw_name))); @@ -1016,6 +1057,7 @@ bsd_recv_security_ok( if ((tok = strtok(NULL, "")) == NULL) { security_seterror(&rh->sech, _("SECURITY line: %s"), security_line); + amfree(service); amfree(security_line); return (-1); /* default errmsg */ } @@ -1063,7 +1105,7 @@ udpbsd_sendpkt( * Initialize this datagram, and add the header */ dgram_zero(&rh->udp->dgram); - dgram_cat(&rh->udp->dgram, pkthdr2str(rh, pkt)); + dgram_cat(&rh->udp->dgram, "%s", pkthdr2str(rh, pkt)); /* * Add the security info. This depends on which kind of packet we're @@ -1089,7 +1131,7 @@ udpbsd_sendpkt( /* * Add the body, and send it */ - dgram_cat(&rh->udp->dgram, pkt->body); + dgram_cat(&rh->udp->dgram, "%s", pkt->body); auth_debug(1, _("sec: udpbsd_sendpkt: %s (%d) pkt_t (len %zu) contains:\n\n\"%s\"\n\n"), @@ -1372,7 +1414,7 @@ udp_netfd_read_callback( return; } - rh = alloc(SIZEOF(*rh)); + rh = g_new0(struct sec_handle, 1); rh->proto_handle=NULL; rh->udp = udp; rh->rc = NULL; @@ -1428,17 +1470,19 @@ sec_tcp_conn_get( const char *hostname, int want_new) { - struct tcp_conn *rc; + GSList *iter; + struct tcp_conn *rc = NULL; auth_debug(1, _("sec_tcp_conn_get: %s\n"), hostname); if (want_new == 0) { - for (rc = connq_first(); rc != NULL; rc = connq_next(rc)) { + for (iter = connq; iter != NULL; iter = iter->next) { + rc = (struct tcp_conn *)iter->data; if (strcasecmp(hostname, rc->hostname) == 0) break; } - if (rc != NULL) { + if (iter != NULL) { rc->refcnt++; auth_debug(1, _("sec_tcp_conn_get: exists, refcnt to %s is now %d\n"), @@ -1451,7 +1495,7 @@ sec_tcp_conn_get( /* * We can't be creating a new handle if we are the client */ - rc = alloc(SIZEOF(*rc)); + rc = g_new0(struct tcp_conn, 1); rc->read = rc->write = -1; rc->driver = NULL; rc->pid = -1; @@ -1470,7 +1514,8 @@ sec_tcp_conn_get( rc->auth = 0; rc->conf_fn = NULL; rc->datap = NULL; - connq_append(rc); + rc->event_id = newevent++; + connq = g_slist_append(connq, rc); return (rc); } @@ -1503,12 +1548,15 @@ sec_tcp_conn_put( event_release(rc->ev_read); if (rc->errmsg != NULL) amfree(rc->errmsg); - connq_remove(rc); + connq = g_slist_remove(connq, rc); amfree(rc->pkt); - if(!rc->donotclose) - amfree(rc); /* someone might still use it */ - /* eg. in sec_tcp_conn_read_callback if */ - /* event_wakeup call us. */ + if(!rc->donotclose) { + /* amfree(rc) */ + /* a memory leak occurs, but freeing it lead to memory + * corruption because it can still be used. + * We need to find a good place to free 'rc'. + */ + } } /* @@ -1583,7 +1631,7 @@ recvpkt_callback( (*rh->fn.recvpkt)(rh->arg, NULL, S_ERROR); return; case -1: - security_seterror(&rh->sech, security_stream_geterror(&rh->rs->secstr)); + security_seterror(&rh->sech, "%s", security_stream_geterror(&rh->rs->secstr)); (*rh->fn.recvpkt)(rh->arg, NULL, S_ERROR); return; default: @@ -1635,9 +1683,13 @@ stream_read_sync_callback( */ tcpm_stream_read_cancel(rs); + sync_pktlen = rs->rc->pktlen; + sync_pkt = malloc(sync_pktlen); + memcpy(sync_pkt, rs->rc->pkt, sync_pktlen); + if (rs->rc->pktlen <= 0) { auth_debug(1, _("sec: stream_read_sync_callback: %s\n"), rs->rc->errmsg); - security_stream_seterror(&rs->secstr, rs->rc->errmsg); + security_stream_seterror(&rs->secstr, "%s", rs->rc->errmsg); if(rs->closed_by_me == 0 && rs->closed_by_network == 0) sec_tcp_conn_put(rs->rc); rs->closed_by_network = 1; @@ -1656,8 +1708,15 @@ stream_read_callback( void * arg) { struct sec_stream *rs = arg; + time_t logtime; + assert(rs != NULL); + logtime = time(NULL); + if (rs && rs->rc && logtime > rs->rc->logstamp + 10) { + g_debug("stream_read_callback: data is still flowing"); + rs->rc->logstamp = logtime; + } auth_debug(1, _("sec: stream_read_callback: handle %d\n"), rs->handle); /* @@ -1683,7 +1742,7 @@ stream_read_callback( if (rs->rc->pktlen <= 0) { auth_debug(1, _("sec: stream_read_callback: %s\n"), rs->rc->errmsg); - security_stream_seterror(&rs->secstr, rs->rc->errmsg); + security_stream_seterror(&rs->secstr, "%s", rs->rc->errmsg); if(rs->closed_by_me == 0 && rs->closed_by_network == 0) sec_tcp_conn_put(rs->rc); rs->closed_by_network = 1; @@ -1717,13 +1776,18 @@ sec_tcp_conn_read_callback( /* Read the data off the wire. If we get errors, shut down. */ rval = tcpm_recv_token(rc, rc->read, &rc->handle, &rc->errmsg, &rc->pkt, - &rc->pktlen, 60); + &rc->pktlen); auth_debug(1, _("sec: conn_read_callback: tcpm_recv_token returned %zd\n"), rval); + + if (rval == -2) { + return; + } + if (rval < 0 || rc->handle == H_EOF) { rc->pktlen = rval; rc->handle = H_EOF; - revent = event_wakeup((event_id_t)rc); + revent = event_wakeup((event_id_t)rc->event_id); auth_debug(1, _("sec: conn_read_callback: event_wakeup return %d\n"), revent); /* delete our 'accept' reference */ @@ -1741,7 +1805,7 @@ sec_tcp_conn_read_callback( if(rval == 0) { rc->pktlen = 0; - revent = event_wakeup((event_id_t)rc); + revent = event_wakeup((event_id_t)rc->event_id); auth_debug(1, _("sec: conn_read_callback: event_wakeup return %d\n"), revent); return; @@ -1749,8 +1813,8 @@ sec_tcp_conn_read_callback( /* If there are events waiting on this handle, we're done */ rc->donotclose = 1; - revent = event_wakeup((event_id_t)rc); - auth_debug(1, _("sec: conn_read_callback: event_wakeup return %zd\n"), rval); + revent = event_wakeup((event_id_t)rc->event_id); + auth_debug(1, _("sec: conn_read_callback: event_wakeup return %d\n"), revent); rc->donotclose = 0; if (rc->handle == H_TAKEN || rc->pktlen == 0) { if(rc->refcnt == 0) amfree(rc); @@ -1760,10 +1824,14 @@ sec_tcp_conn_read_callback( assert(rc->refcnt > 0); /* If there is no accept fn registered, then drop the packet */ - if (rc->accept_fn == NULL) + if (rc->accept_fn == NULL) { + g_warning( + _("sec: conn_read_callback: %zd bytes for handle %d went unclaimed!"), + rc->pktlen, rc->handle); return; + } - rh = alloc(SIZEOF(*rh)); + rh = g_new0(struct sec_handle, 1); security_handleinit(&rh->sech, rc->driver); rh->hostname = stralloc(rc->hostname); rh->ev_timeout = NULL; @@ -2237,7 +2305,7 @@ check_user_amandahosts( if (! found) { if (strcmp(service, "amindexd") == 0 || strcmp(service, "amidxtaped") == 0) { - result = vstrallocf(_("Please add the line \"%s %s amindexd amidxtaped\" to %s on the client"), host, remoteuser, ptmp); + result = vstrallocf(_("Please add the line \"%s %s amindexd amidxtaped\" to %s on the server"), host, remoteuser, ptmp); } else if (strcmp(service, "amdump") == 0 || strcmp(service, "noop") == 0 || strcmp(service, "selfcheck") == 0 || @@ -2365,57 +2433,6 @@ check_security( return *errstr == NULL; } -/* - * Writes out the entire iovec - */ -ssize_t -net_writev( - int fd, - struct iovec * iov, - int iovcnt) -{ - ssize_t delta, n, total; - - assert(iov != NULL); - - total = 0; - while (iovcnt > 0) { - /* - * Write the iovec - */ - n = writev(fd, iov, iovcnt); - if (n < 0) { - if (errno != EINTR) - return (-1); - auth_debug(1, _("net_writev got EINTR\n")); - } - else if (n == 0) { - errno = EIO; - return (-1); - } else { - total += n; - /* - * Iterate through each iov. Figure out what we still need - * to write out. - */ - for (; n > 0; iovcnt--, iov++) { - /* 'delta' is the bytes written from this iovec */ - delta = ((size_t)n < (size_t)iov->iov_len) ? n : (ssize_t)iov->iov_len; - /* subtract from the total num bytes written */ - n -= delta; - assert(n >= 0); - /* subtract from this iovec */ - iov->iov_len -= delta; - iov->iov_base = (char *)iov->iov_base + delta; - /* if this iovec isn't empty, run the writev again */ - if (iov->iov_len > 0) - break; - } - } - } - return (total); -} - /* * Like read(), but waits until the entire buffer has been filled. */ @@ -2602,7 +2619,7 @@ check_name_give_sockaddr( } } - dbprintf(_("%s doesn't resolve to %s"), + g_debug("%s doesn't resolve to %s", hostname, str_sockaddr((sockaddr_union *)addr)); *errstr = newvstrallocf(*errstr, "%s doesn't resolve to %s", @@ -2612,3 +2629,50 @@ error: amfree(canonname); return -1; } + +in_port_t +find_port_for_service( + char *service, + char *proto) +{ + in_port_t port; + char *s; + int all_numeric = 1; + + for (s=service; *s != '\0'; s++) { + if (!isdigit((int)*s)) { + all_numeric = 0; + } + } + + if (all_numeric == 1) { + port = atoi(service); + } else { + struct servent *sp; + + if ((sp = getservbyname(service, proto)) == NULL) { + port = 0; + } else { + port = (in_port_t)(ntohs((in_port_t)sp->s_port)); + } + } + + return port; +} + +char * +sec_get_authenticated_peer_name_localhost( + security_handle_t *hdl G_GNUC_UNUSED) +{ + return "localhost"; +} + +char * +sec_get_authenticated_peer_name_hostname( + security_handle_t *hdl) +{ + char *hostname = ((struct sec_handle *)hdl)->hostname; + if (!hostname) + hostname = ""; + return hostname; +}