summaryrefslogtreecommitdiff
path: root/tests/fdpassing.c
diff options
context:
space:
mode:
Diffstat (limited to 'tests/fdpassing.c')
-rw-r--r--tests/fdpassing.c222
1 files changed, 170 insertions, 52 deletions
diff --git a/tests/fdpassing.c b/tests/fdpassing.c
index 9e1b6e9..a98f8a2 100644
--- a/tests/fdpassing.c
+++ b/tests/fdpassing.c
@@ -25,6 +25,15 @@
#include <string.h>
#include <assert.h>
#include <sys/stat.h>
+#if HAVE_W32_SYSTEM
+# define WIN32_LEAN_AND_MEAN
+# include <windows.h>
+# include <wincrypt.h>
+# include <io.h>
+#else
+# include <sys/socket.h>
+# include <sys/un.h>
+#endif
#include <unistd.h>
#include <errno.h>
@@ -98,20 +107,9 @@ register_commands (assuan_context_t ctx)
static void
-server (void)
+server_common (assuan_context_t ctx)
{
int rc;
- assuan_context_t ctx;
-
- log_info ("server started\n");
-
- rc = assuan_new (&ctx);
- if (rc)
- log_fatal ("assuan_new failed: %s\n", gpg_strerror (rc));
-
- rc = assuan_init_pipe_server (ctx, NULL);
- if (rc)
- log_fatal ("assuan_init_pipe_server failed: %s\n", gpg_strerror (rc));
rc = register_commands (ctx);
if (rc)
@@ -140,8 +138,87 @@ server (void)
assuan_release (ctx);
}
+static void
+server_pipe (void)
+{
+ int rc;
+ assuan_context_t ctx;
+
+ log_info ("server started\n");
+ rc = assuan_new (&ctx);
+ if (rc)
+ log_fatal ("assuan_new failed: %s\n", gpg_strerror (rc));
+ rc = assuan_init_pipe_server (ctx, NULL);
+ if (rc)
+ log_fatal ("assuan_init_pipe_server failed: %s\n", gpg_strerror (rc));
+
+ server_common (ctx);
+}
+
+static assuan_sock_nonce_t socket_nonce;
+
+static void
+server_socket (const char *socketname)
+{
+ int rc;
+ assuan_context_t ctx;
+ assuan_fd_t fd;
+ struct sockaddr_un unaddr_struct;
+ struct sockaddr *addr;
+ socklen_t len;
+
+ log_info ("server on socket started\n");
+
+ fd = assuan_sock_new (AF_UNIX, SOCK_STREAM, 0);
+ if (fd == ASSUAN_INVALID_FD)
+ log_fatal ("assuan_sock_new failed\n");
+
+ addr = (struct sockaddr *)&unaddr_struct;
+ rc = assuan_sock_set_sockaddr_un (socketname, addr, NULL);
+ if (rc)
+ {
+ assuan_sock_close (fd);
+ log_fatal ("assuan_sock_set_sockaddr_un failed: %s\n", gpg_strerror (rc));
+ }
+
+ len = offsetof (struct sockaddr_un, sun_path)
+ + strlen (unaddr_struct.sun_path);
+ rc = assuan_sock_bind (fd, addr, len);
+ if (rc)
+ {
+ assuan_sock_close (fd);
+ log_fatal ("assuan_sock_bind failed: %s\n", gpg_strerror (rc));
+ }
+
+ rc = assuan_sock_get_nonce (addr, len, &socket_nonce);
+ if (rc)
+ {
+ assuan_sock_close (fd);
+ log_fatal ("assuan_sock_get_nonce failed: %s\n", gpg_strerror (rc));
+ }
+
+ rc = listen (HANDLE2SOCKET (fd), 5);
+ if (rc < 0)
+ {
+ assuan_sock_close (fd);
+ log_fatal ("listen failed: %s\n",
+ gpg_strerror (gpg_error_from_syserror ()));
+ }
+
+ rc = assuan_new (&ctx);
+ if (rc)
+ log_fatal ("assuan_new failed: %s\n", gpg_strerror (rc));
+
+ rc = assuan_init_socket_server (ctx, fd, ASSUAN_SOCKET_SERVER_FDPASSING);
+ if (rc)
+ log_fatal ("assuan_init_socket_server failed: %s\n", gpg_strerror (rc));
+
+ assuan_set_sock_nonce (ctx, &socket_nonce);
+
+ server_common (ctx);
+}
/*
@@ -217,11 +294,9 @@ main (int argc, char **argv)
int last_argc = -1;
assuan_context_t ctx;
gpg_error_t err;
- assuan_fd_t no_close_fds[2];
- const char *arglist[10];
int is_server = 0;
int with_exec = 0;
- char *fname = prepend_srcdir ("motd");
+ const char *socketname = NULL;
if (argc)
{
@@ -239,6 +314,7 @@ main (int argc, char **argv)
"Options:\n"
" --verbose Show what is going on\n"
" --with-exec Exec the child. Default is just a fork on POSIX machine\n"
+" --socketname Specify the socket path\n"
);
exit (0);
}
@@ -262,71 +338,113 @@ main (int argc, char **argv)
with_exec = 1;
argc--; argv++;
}
+ else if (!strcmp (*argv, "--socketname"))
+ {
+ argc--; argv++;
+ if (argc)
+ {
+ socketname = *argv++;
+ argc--;
+ }
+ }
}
+ if (socketname)
+ assuan_sock_init ();
+ else
+ {
#ifdef HAVE_W32_SYSTEM
- with_exec = 1;
+ with_exec = 1;
+#else
+ ;
#endif
+ }
assuan_set_assuan_log_prefix (log_prefix);
if (is_server)
{
- server ();
+ if (socketname)
+ server_socket (socketname);
+ else
+ server_pipe ();
log_info ("server finished\n");
}
else
{
- const char *loc;
- const char *program_name;
-
-#ifdef HAVE_W32_SYSTEM
- program_name = "fdpassing.exe";
-#else
- program_name = "fdpassing";
-#endif
-
- no_close_fds[0] = verbose? assuan_fd_from_posix_fd (2): (assuan_fd_t)-1;
- no_close_fds[1] = (assuan_fd_t)-1;
- if (with_exec)
- {
- arglist[0] = program_name;
- arglist[1] = "--server";
- arglist[2] = verbose? "--verbose":NULL;
- arglist[3] = NULL;
- }
+ char *fname;
err = assuan_new (&ctx);
if (err)
log_fatal ("assuan_new failed: %s\n", gpg_strerror (err));
- err = assuan_pipe_connect (ctx, with_exec? program_name : NULL,
- with_exec ? arglist : &loc,
- no_close_fds, NULL, NULL, 1);
- if (err)
- {
- log_error ("assuan_pipe_connect failed: %s\n", gpg_strerror (err));
- assuan_release (ctx);
- errorcount++;
- }
- else if (!with_exec && loc[0] == 's')
+ if (socketname)
{
- server ();
- assuan_release (ctx);
- log_info ("server finished\n");
+ err = assuan_socket_connect (ctx, socketname, 0,
+ ASSUAN_SOCKET_CONNECT_FDPASSING);
+ if (err)
+ {
+ log_error ("assuan_socket_connect failed: %s\n",
+ gpg_strerror (err));
+ assuan_release (ctx);
+ errorcount++;
+ goto done;
+ }
}
else
{
- if (client (ctx, fname))
+ assuan_fd_t no_close_fds[2];
+ const char *arglist[10];
+ const char *loc;
+ const char *program_name;
+
+#ifdef HAVE_W32_SYSTEM
+ program_name = "fdpassing.exe";
+#else
+ program_name = "fdpassing";
+#endif
+
+ no_close_fds[0] = verbose?
+ assuan_fd_from_posix_fd (2): (assuan_fd_t)-1;
+ no_close_fds[1] = (assuan_fd_t)-1;
+ if (with_exec)
+ {
+ arglist[0] = program_name;
+ arglist[1] = "--server";
+ arglist[2] = verbose? "--verbose":NULL;
+ arglist[3] = NULL;
+ }
+
+ err = assuan_pipe_connect (ctx, with_exec? program_name : NULL,
+ with_exec ? arglist : &loc,
+ no_close_fds, NULL, NULL, 1);
+ if (err)
+ {
+ log_error ("assuan_pipe_connect failed: %s\n",
+ gpg_strerror (err));
+ assuan_release (ctx);
+ errorcount++;
+ }
+ else if (!with_exec && loc[0] == 's')
{
- log_info ("waiting for server to terminate...\n");
+ server_pipe ();
assuan_release (ctx);
+ log_info ("server finished\n");
+ goto done;
}
- log_info ("client finished\n");
}
+
+ fname = prepend_srcdir ("motd");
+ if (client (ctx, fname))
+ {
+ log_info ("waiting for server to terminate...\n");
+ assuan_release (ctx);
+ }
+ log_info ("client finished\n");
+ xfree (fname);
}
- xfree (fname);
+ done:
return errorcount ? 1 : 0;
}