[gnome-keyring/wip/dueno/ssh-agent: 24/24] ssh-agent: add test for ssh-agent interaction
- From: Daiki Ueno <dueno src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gnome-keyring/wip/dueno/ssh-agent: 24/24] ssh-agent: add test for ssh-agent interaction
- Date: Mon, 12 Feb 2018 17:02:42 +0000 (UTC)
commit 8c7ecaab0661bf3228f613281c4f4144b3283d7e
Author: Daiki Ueno <dueno src gnome org>
Date: Mon Feb 12 17:59:16 2018 +0100
ssh-agent: add test for ssh-agent interaction
daemon/ssh-agent/Makefile.am | 12 ++-
daemon/ssh-agent/gkd-ssh-agent-process.c | 126 ++++++++++++++++++++++---
daemon/ssh-agent/gkd-ssh-agent.c | 92 ------------------
daemon/ssh-agent/test-gkd-ssh-agent-process.c | 102 ++++++++++++++++++++
4 files changed, 225 insertions(+), 107 deletions(-)
---
diff --git a/daemon/ssh-agent/Makefile.am b/daemon/ssh-agent/Makefile.am
index 73a2edf..b58d465 100644
--- a/daemon/ssh-agent/Makefile.am
+++ b/daemon/ssh-agent/Makefile.am
@@ -28,15 +28,21 @@ ssh_agent_CFLAGS = \
$(DAEMON_CFLAGS)
ssh_agent_LIBS = \
- $(DAEMON_LIBS) \
- libgkd-ssh-agent.la
+ libgkd-ssh-agent.la \
+ libegg-buffer.la \
+ $(DAEMON_LIBS)
ssh_agent_TESTS = \
- test-gkd-ssh-openssh
+ test-gkd-ssh-openssh \
+ test-gkd-ssh-agent-process
test_gkd_ssh_openssh_SOURCES = daemon/ssh-agent/test-gkd-ssh-openssh.c
test_gkd_ssh_openssh_CFLAGS = $(ssh_agent_CFLAGS)
test_gkd_ssh_openssh_LDADD = $(ssh_agent_LIBS)
+test_gkd_ssh_agent_process_SOURCES = daemon/ssh-agent/test-gkd-ssh-agent-process.c
+test_gkd_ssh_agent_process_CFLAGS = $(ssh_agent_CFLAGS)
+test_gkd_ssh_agent_process_LDADD = $(ssh_agent_LIBS)
+
check_PROGRAMS += $(ssh_agent_TESTS)
TESTS += $(ssh_agent_TESTS)
diff --git a/daemon/ssh-agent/gkd-ssh-agent-process.c b/daemon/ssh-agent/gkd-ssh-agent-process.c
index 52ddc2e..03a9846 100644
--- a/daemon/ssh-agent/gkd-ssh-agent-process.c
+++ b/daemon/ssh-agent/gkd-ssh-agent-process.c
@@ -119,6 +119,65 @@ gkd_ssh_agent_process_class_init (GkdSshAgentProcessClass *klass)
G_PARAM_CONSTRUCT_ONLY | G_PARAM_WRITABLE));
}
+static gboolean
+read_all (int fd, guchar *buf, int len)
+{
+ int all = len;
+ int res;
+
+ while (len > 0) {
+
+ res = read (fd, buf, len);
+
+ if (res < 0) {
+ if (errno == EAGAIN || errno == EINTR)
+ continue;
+ g_warning ("couldn't read %u bytes from client: %s", all,
+ g_strerror (errno));
+ return FALSE;
+ } else if (res == 0) {
+ return FALSE;
+ } else {
+ len -= res;
+ buf += res;
+ }
+ }
+
+ return TRUE;
+}
+
+static gboolean
+write_all (int fd,
+ const guchar *buf,
+ int len,
+ const gchar *where)
+{
+ int all = len;
+ int res;
+
+ while (len > 0) {
+
+ res = write (fd, buf, len);
+ if (res < 0) {
+ if (errno == EAGAIN || errno == EINTR)
+ continue;
+ if (errno != EPIPE) {
+ g_warning ("couldn't write %u bytes to %s: %s", all,
+ where, g_strerror (errno));
+ }
+ return FALSE;
+ } else if (res == 0) {
+ g_warning ("couldn't write %u bytes to %s", all, where);
+ return FALSE;
+ } else {
+ len -= res;
+ buf += res;
+ }
+ }
+
+ return TRUE;
+}
+
static void
on_child_watch (GPid pid,
gint status,
@@ -160,7 +219,7 @@ on_output_watch (gint fd,
g_message ("couldn't read from ssh-agent stdout: %m");
condition |= G_IO_ERR;
} else if (len > 0) {
- gkd_ssh_agent_write_all (1, buf, len, "stdout");
+ write_all (1, buf, len, "stdout");
}
}
@@ -204,7 +263,7 @@ on_timeout (gpointer user_data)
}
gboolean
-gkd_ssh_agent_process_connect (GkdSshAgentProcess *self)
+gkd_ssh_agent_process_connect (GkdSshAgentProcess *self)
{
gboolean started = FALSE;
struct sockaddr_un addr;
@@ -214,11 +273,13 @@ gkd_ssh_agent_process_connect (GkdSshAgentProcess *self)
g_mutex_lock (&self->lock);
- if (self->pid == 0 || kill (self->pid, 0) != 0)
- started = agent_start_inlock (self);
-
- addr.sun_family = AF_UNIX;
- g_strlcpy (addr.sun_path, self->path, sizeof (addr.sun_path));
+ if (self->pid == 0 || kill (self->pid, 0) != 0) {
+ if (!agent_start_inlock (self)) {
+ g_mutex_unlock (&self->lock);
+ return FALSE;
+ }
+ started = TRUE;
+ }
if (started && !self->ready) {
source = g_timeout_add_seconds (5, on_timeout, &timedout);
@@ -227,24 +288,65 @@ gkd_ssh_agent_process_connect (GkdSshAgentProcess *self)
g_source_remove (source);
}
- if (!self->ready)
+ if (!self->ready) {
+ g_mutex_unlock (&self->lock);
return FALSE;
+ }
sock = socket (AF_UNIX, SOCK_STREAM, 0);
- g_return_val_if_fail (sock >= 0, -1);
+ if (sock < 0) {
+ g_mutex_unlock (&self->lock);
+ return FALSE;
+ }
+
+ addr.sun_family = AF_UNIX;
+ g_strlcpy (addr.sun_path, self->path, sizeof (addr.sun_path));
if (connect (sock, (struct sockaddr*) &addr, sizeof (addr)) < 0) {
g_message ("couldn't connect to ssh-agent socket at: %s: %s",
addr.sun_path, g_strerror (errno));
close (sock);
- sock = -1;
+ g_mutex_unlock (&self->lock);
+ return FALSE;
}
self->socket_fd = sock;
-
g_mutex_unlock (&self->lock);
- return sock != -1;
+ return TRUE;
+}
+
+gboolean
+gkd_ssh_agent_read_packet (gint fd,
+ EggBuffer *buffer)
+{
+ guint32 packet_size;
+
+ egg_buffer_reset (buffer);
+ egg_buffer_resize (buffer, 4);
+ if (!read_all (fd, buffer->buf, 4))
+ return FALSE;
+
+ if (!egg_buffer_get_uint32 (buffer, 0, NULL, &packet_size) ||
+ packet_size < 1) {
+ g_warning ("invalid packet size from client");
+ return FALSE;
+ }
+
+ egg_buffer_resize (buffer, packet_size + 4);
+ if (!read_all (fd, buffer->buf + 4, packet_size))
+ return FALSE;
+
+ return TRUE;
+}
+
+gboolean
+gkd_ssh_agent_write_packet (gint fd,
+ EggBuffer *buffer)
+{
+ if (!egg_buffer_set_uint32 (buffer, 0, buffer->len - 4))
+ g_return_val_if_reached (FALSE);
+ return write_all (fd, buffer->buf, buffer->len, "client");
}
gboolean
diff --git a/daemon/ssh-agent/gkd-ssh-agent.c b/daemon/ssh-agent/gkd-ssh-agent.c
index 6e31bc6..765ddf9 100644
--- a/daemon/ssh-agent/gkd-ssh-agent.c
+++ b/daemon/ssh-agent/gkd-ssh-agent.c
@@ -53,98 +53,6 @@ static char process_path[1024] = { 0, };
static GkdSshAgentProcess *process = NULL;
static gboolean
-read_all (int fd, guchar *buf, int len)
-{
- int all = len;
- int res;
-
- while (len > 0) {
-
- res = read (fd, buf, len);
-
- if (res < 0) {
- if (errno == EAGAIN || errno == EINTR)
- continue;
- g_warning ("couldn't read %u bytes from client: %s", all,
- g_strerror (errno));
- return FALSE;
- } else if (res == 0) {
- return FALSE;
- } else {
- len -= res;
- buf += res;
- }
- }
-
- return TRUE;
-}
-
-gboolean
-gkd_ssh_agent_write_all (int fd,
- const guchar *buf,
- int len,
- const gchar *where)
-{
- int all = len;
- int res;
-
- while (len > 0) {
-
- res = write (fd, buf, len);
- if (res < 0) {
- if (errno == EAGAIN || errno == EINTR)
- continue;
- if (errno != EPIPE) {
- g_warning ("couldn't write %u bytes to %s: %s", all,
- where, g_strerror (errno));
- }
- return FALSE;
- } else if (res == 0) {
- g_warning ("couldn't write %u bytes to %s", all, where);
- return FALSE;
- } else {
- len -= res;
- buf += res;
- }
- }
-
- return TRUE;
-}
-
-gboolean
-gkd_ssh_agent_read_packet (gint fd,
- EggBuffer *buffer)
-{
- guint32 packet_size;
-
- egg_buffer_reset (buffer);
- egg_buffer_resize (buffer, 4);
- if (!read_all (fd, buffer->buf, 4))
- return FALSE;
-
- if (!egg_buffer_get_uint32 (buffer, 0, NULL, &packet_size) ||
- packet_size < 1) {
- g_warning ("invalid packet size from client");
- return FALSE;
- }
-
- egg_buffer_resize (buffer, packet_size + 4);
- if (!read_all (fd, buffer->buf + 4, packet_size))
- return FALSE;
-
- return TRUE;
-}
-
-gboolean
-gkd_ssh_agent_write_packet (gint fd,
- EggBuffer *buffer)
-{
- if (!egg_buffer_set_uint32 (buffer, 0, buffer->len - 4))
- g_return_val_if_reached (FALSE);
- return gkd_ssh_agent_write_all (fd, buffer->buf, buffer->len, "client");
-}
-
-static gboolean
agent_relay (GkdSshAgentCall *call)
{
return gkd_ssh_agent_process_call (call->process, call->req, call->resp);
diff --git a/daemon/ssh-agent/test-gkd-ssh-agent-process.c b/daemon/ssh-agent/test-gkd-ssh-agent-process.c
new file mode 100644
index 0000000..165074b
--- /dev/null
+++ b/daemon/ssh-agent/test-gkd-ssh-agent-process.c
@@ -0,0 +1,102 @@
+/* -*- Mode: C; indent-tabs-mode: t; c-basic-offset: 8; tab-width: 8 -*- */
+/*
+ Copyright (C) 2008 Stefan Walter
+
+ The Gnome Keyring Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Library General Public License as
+ published by the Free Software Foundation; either version 2 of the
+ License, or (at your option) any later version.
+
+ The Gnome Keyring Library is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ Library General Public License for more details.
+
+ You should have received a copy of the GNU Library General Public
+ License along with the Gnome Library; see the file COPYING.LIB. If not,
+ <http://www.gnu.org/licenses/>.
+
+ Author: Stef Walter <stef memberwebs com>
+*/
+
+#include "config.h"
+
+#include "daemon/ssh-agent/gkd-ssh-agent-private.h"
+
+#include <glib.h>
+
+#include <fcntl.h>
+#include <stdlib.h>
+#include <stdio.h>
+#include <string.h>
+#include <unistd.h>
+
+typedef struct {
+ GkdSshAgentProcess *process;
+} Test;
+
+static void
+setup (Test *test, gconstpointer unused)
+{
+ unlink (BUILDDIR "/.ssh.sock");
+ test->process = gkd_ssh_agent_process_new (BUILDDIR "/.ssh.sock");
+ g_assert_nonnull (test->process);
+}
+
+static void
+teardown (Test *test, gconstpointer unused)
+{
+ g_clear_object (&test->process);
+ unlink (BUILDDIR "/.ssh.sock");
+}
+
+static void
+test_connect (Test *test, gconstpointer unused)
+{
+ gboolean ret = gkd_ssh_agent_process_connect (test->process);
+ g_assert_true (ret);
+}
+
+static void
+test_call (Test *test, gconstpointer unused)
+{
+ EggBuffer req;
+ EggBuffer resp;
+ uint32_t length;
+ unsigned char code;
+ size_t offset;
+ gboolean ret;
+
+ ret = gkd_ssh_agent_process_connect (test->process);
+ g_assert_true (ret);
+
+ egg_buffer_init_full (&req, 128, (EggBufferAllocator)g_realloc);
+ egg_buffer_init_full (&resp, 128, (EggBufferAllocator)g_realloc);
+
+ egg_buffer_add_uint32 (&req, 1);
+ egg_buffer_add_byte (&req, GKD_SSH_OP_REQUEST_IDENTITIES);
+ ret = gkd_ssh_agent_process_call (test->process, &req, &resp);
+ g_assert_true (ret);
+
+ offset = 0;
+ egg_buffer_get_uint32 (&resp, offset, &offset, &length);
+ g_assert_cmpint (length, >, 0);
+
+ code = 0;
+ egg_buffer_get_byte (&resp, offset, &offset, &code);
+ g_assert_cmpint (code, ==, GKD_SSH_RES_IDENTITIES_ANSWER);
+
+ egg_buffer_uninit (&req);
+ egg_buffer_uninit (&resp);
+}
+
+int
+main (int argc, char **argv)
+{
+ g_test_init (&argc, &argv, NULL);
+
+ g_test_add ("/ssh-agent/process/connect", Test, NULL, setup, test_connect, teardown);
+ g_test_add ("/ssh-agent/process/call", Test, NULL, setup, test_call, teardown);
+
+ return g_test_run ();
+}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]