dirmngr: Use Assuan socket wrappers for http.c

* dirmngr/http.c: Include assuan.h.  Changed all code taking a socket
descriptor from int to assuan_fd_t.
(my_unprotect, my_protect): New.
(my_connect): Remove.
(_my_socket_new, _my_socket_unref): use assuan_sock_close.
(connect_server): Use assuan_sock_connect, assuan_sock_new, and
assuan_sock_close.
* dirmngr/Makefile.am (t_common_ldadd): Add LIBASSUAN_LIBS.
--

This change prepares for the use of SOCKS5 with http.

Signed-off-by: Werner Koch <wk@gnupg.org>
This commit is contained in:
Werner Koch 2015-10-19 12:43:22 +02:00
parent 253afa2444
commit 8c609eaf35
No known key found for this signature in database
GPG Key ID: E3FDFF218E45B72B
2 changed files with 74 additions and 56 deletions

View File

@ -109,7 +109,7 @@ no-libgcrypt.c : $(top_srcdir)/tools/no-libgcrypt.c
t_common_src = t-support.h
t_common_ldadd = $(libcommon) no-libgcrypt.o \
t_common_ldadd = $(libcommon) no-libgcrypt.o $(LIBASSUAN_LIBS) \
$(GPG_ERROR_LIBS) $(NETLIBS) \
$(NTBTLS_LIBS) $(LIBGNUTLS_LIBS) \
$(DNSLIBS) $(LIBINTL) $(LIBICONV)

View File

@ -94,6 +94,7 @@
# include <gnutls/x509.h>
#endif /*HTTP_USE_GNUTLS*/
#include <assuan.h> /* We need the socket wrapper. */
#include "util.h"
#include "i18n.h"
@ -119,12 +120,14 @@ struct srventry
#ifdef USE_NPTH
# define my_select(a,b,c,d,e) npth_select ((a), (b), (c), (d), (e))
# define my_connect(a,b,c) npth_connect ((a), (b), (c))
# define my_accept(a,b,c) npth_accept ((a), (b), (c))
# define my_unprotect() npth_unprotect ()
# define my_protect() npth_protect ()
#else
# define my_select(a,b,c,d,e) select ((a), (b), (c), (d), (e))
# define my_connect(a,b,c) connect ((a), (b), (c))
# define my_accept(a,b,c) accept ((a), (b), (c))
# define my_unprotect() do { } while(0)
# define my_protect() do { } while(0)
#endif
#ifdef HAVE_W32_SYSTEM
@ -181,9 +184,9 @@ static gpg_error_t send_request (http_t hd, const char *httphost,
static char *build_rel_path (parsed_uri_t uri);
static gpg_error_t parse_response (http_t hd);
static int connect_server (const char *server, unsigned short port,
unsigned int flags, const char *srvtag,
int *r_host_not_found);
static assuan_fd_t connect_server (const char *server, unsigned short port,
unsigned int flags, const char *srvtag,
int *r_host_not_found);
static gpg_error_t write_server (int sock, const char *data, size_t length);
static ssize_t cookie_read (void *cookie, void *buffer, size_t size);
@ -194,8 +197,8 @@ static int cookie_close (void *cookie);
/* A socket object used to a allow ref counting of sockets. */
struct my_socket_s
{
int fd; /* The actual socket - shall never be -1. */
int refcount; /* Number of references to this socket. */
assuan_fd_t fd; /* The actual socket - shall never be ASSUAN_INVALID_FD. */
int refcount; /* Number of references to this socket. */
};
typedef struct my_socket_s *my_socket_t;
@ -338,7 +341,7 @@ init_sockets (void)
/* Create a new socket object. Returns NULL and closes FD if not
enough memory is available. */
static my_socket_t
_my_socket_new (int lnr, int fd)
_my_socket_new (int lnr, assuan_fd_t fd)
{
my_socket_t so;
@ -346,7 +349,7 @@ _my_socket_new (int lnr, int fd)
if (!so)
{
int save_errno = errno;
sock_close (fd);
assuan_sock_close (fd);
gpg_err_set_errno (save_errno);
return NULL;
}
@ -389,7 +392,7 @@ _my_socket_unref (int lnr, my_socket_t so,
{
if (preclose)
preclose (preclosearg);
sock_close (so->fd);
assuan_sock_close (so->fd);
xfree (so);
}
}
@ -740,7 +743,6 @@ http_raw_connect (http_t *r_hd, const char *server, unsigned short port,
unsigned int flags, const char *srvtag)
{
gpg_error_t err = 0;
int sock;
http_t hd;
cookie_t cookie;
int hnf;
@ -761,22 +763,26 @@ http_raw_connect (http_t *r_hd, const char *server, unsigned short port,
hd->flags = flags;
/* Connect. */
sock = connect_server (server, port, hd->flags, srvtag, &hnf);
if (sock == -1)
{
err = gpg_err_make (default_errsource,
(hnf? GPG_ERR_UNKNOWN_HOST
: gpg_err_code_from_syserror ()));
xfree (hd);
return err;
}
hd->sock = my_socket_new (sock);
if (!hd->sock)
{
err = gpg_err_make (default_errsource, gpg_err_code_from_syserror ());
xfree (hd);
return err;
}
{
assuan_fd_t sock;
sock = connect_server (server, port, hd->flags, srvtag, &hnf);
if (sock == ASSUAN_INVALID_FD)
{
err = gpg_err_make (default_errsource,
(hnf? GPG_ERR_UNKNOWN_HOST
: gpg_err_code_from_syserror ()));
xfree (hd);
return err;
}
hd->sock = my_socket_new (sock);
if (!hd->sock)
{
err = gpg_err_make (default_errsource, gpg_err_code_from_syserror ());
xfree (hd);
return err;
}
}
/* Setup estreams for reading and writing. */
cookie = xtrycalloc (1, sizeof *cookie);
@ -1560,7 +1566,7 @@ send_request (http_t hd, const char *httphost, const char *auth,
hd->flags, srvtag, &hnf);
save_errno = errno;
http_release_parsed_uri (uri);
if (sock == -1)
if (sock == ASSUAN_INVALID_FD)
gpg_err_set_errno (save_errno);
}
else
@ -1568,7 +1574,7 @@ send_request (http_t hd, const char *httphost, const char *auth,
sock = connect_server (server, port, hd->flags, srvtag, &hnf);
}
if (sock == -1)
if (sock == ASSUAN_INVALID_FD)
{
xfree (proxy_authstr);
return gpg_err_make (default_errsource,
@ -2183,11 +2189,11 @@ start_server ()
/* Actually connect to a server. Returns the file descriptor or -1 on
error. ERRNO is set on error. */
static int
static assuan_fd_t
connect_server (const char *server, unsigned short port,
unsigned int flags, const char *srvtag, int *r_host_not_found)
{
int sock = -1;
assuan_fd_t sock = ASSUAN_INVALID_FD;
int srvcount = 0;
int hostfound = 0;
int anyhostaddr = 0;
@ -2197,6 +2203,7 @@ connect_server (const char *server, unsigned short port,
#ifdef HAVE_W32_SYSTEM
unsigned long inaddr;
#endif
int ret;
*r_host_not_found = 0;
#ifdef HAVE_W32_SYSTEM
@ -2213,21 +2220,24 @@ connect_server (const char *server, unsigned short port,
memset(&addr,0,sizeof(addr));
sock = socket(AF_INET,SOCK_STREAM,0);
if ( sock==INVALID_SOCKET )
sock = assuan_sock_socket (AF_INET, SOCK_STREAM, 0);
if (sock == ASSUAN_INVALID_FD)
{
log_error("error creating socket: ec=%d\n",(int)WSAGetLastError());
return -1;
log_error ("error creating socket: %s\n", strerror (errno));
return ASSUAN_INVALID_FD;
}
addr.sin_family = AF_INET;
addr.sin_port = htons(port);
memcpy (&addr.sin_addr,&inaddr,sizeof(inaddr));
if (!my_connect (sock,(struct sockaddr *)&addr,sizeof(addr)) )
my_unprotect ();
ret = assuan_sock_connect (sock,(struct sockaddr *)&addr,sizeof(addr));
my_protect ();
if (!ret)
return sock;
sock_close(sock);
return -1;
assuan_sock_close (sock);
return ASSUAN_INVALID_FD;
}
#endif /*HAVE_W32_SYSTEM*/
@ -2284,21 +2294,25 @@ connect_server (const char *server, unsigned short port,
if (ai->ai_family == AF_INET6 && (flags & HTTP_FLAG_IGNORE_IPv6))
continue;
if (sock != -1)
sock_close (sock);
sock = socket (ai->ai_family, ai->ai_socktype, ai->ai_protocol);
if (sock == -1)
if (sock != ASSUAN_INVALID_FD)
assuan_sock_close (sock);
sock = assuan_sock_new (ai->ai_family, ai->ai_socktype,
ai->ai_protocol);
if (sock == ASSUAN_INVALID_FD)
{
int save_errno = errno;
log_error ("error creating socket: %s\n", strerror (errno));
freeaddrinfo (res);
xfree (serverlist);
errno = save_errno;
return -1;
return ASSUAN_INVALID_FD;
}
anyhostaddr = 1;
if (my_connect (sock, ai->ai_addr, ai->ai_addrlen))
my_unprotect ();
ret = assuan_sock_connect (sock, ai->ai_addr, ai->ai_addrlen);
my_protect ();
if (ret)
last_errno = errno;
else
connected = 1;
@ -2321,14 +2335,14 @@ connect_server (const char *server, unsigned short port,
continue;
hostfound = 1;
if (sock != -1)
sock_close (sock);
sock = socket (host->h_addrtype, SOCK_STREAM, 0);
if (sock == -1)
if (sock != ASSUAN_INVALID_FD)
assuan_sock_close (sock);
sock = assuan_sock_new (host->h_addrtype, SOCK_STREAM, 0);
if (sock == ASSUAN_INVALID_FD)
{
log_error ("error creating socket: %s\n", strerror (errno));
xfree (serverlist);
return -1;
return ASSUAN_INVALID_FD;
}
addr.sin_family = host->h_addrtype;
@ -2337,7 +2351,7 @@ connect_server (const char *server, unsigned short port,
log_error ("unknown address family for '%s'\n",
serverlist[srv].target);
xfree (serverlist);
return -1;
return ASSUAN_INVALID_FD;
}
addr.sin_port = htons (serverlist[srv].port);
if (host->h_length != 4)
@ -2345,7 +2359,7 @@ connect_server (const char *server, unsigned short port,
log_error ("illegal address length for '%s'\n",
serverlist[srv].target);
xfree (serverlist);
return -1;
return ASSUAN_INVALID_FD;
}
/* Try all A records until one responds. */
@ -2353,7 +2367,11 @@ connect_server (const char *server, unsigned short port,
{
anyhostaddr = 1;
memcpy (&addr.sin_addr, host->h_addr_list[i], host->h_length);
if (my_connect (sock, (struct sockaddr *) &addr, sizeof (addr)))
my_unprotect ();
ret = assuan_sock_connect (sock,
(struct sockaddr *) &addr, sizeof (addr));
my_protect ();
if (ret)
last_errno = errno;
else
{
@ -2386,10 +2404,10 @@ connect_server (const char *server, unsigned short port,
}
if (!hostfound || (hostfound && !anyhostaddr))
*r_host_not_found = 1;
if (sock != -1)
sock_close (sock);
if (sock != ASSUAN_INVALID_FD)
assuan_sock_close (sock);
gpg_err_set_errno (last_errno);
return -1;
return ASSUAN_INVALID_FD;
}
return sock;
}