[Openais] [PATCH 3/4] CTS: Add a condb test agent and python tests.

Steven Dake sdake at redhat.com
Wed Mar 24 14:06:01 PDT 2010


good for merge

On Thu, 2010-03-25 at 07:38 +1100, Angus Salkeld wrote:
> Signed-off-by: Angus Salkeld <asalkeld at redhat.com>
> ---
>  cts/agents/Makefile.am         |   10 +-
>  cts/agents/common_test_agent.c |  247 ++++++++++++++++++
>  cts/agents/common_test_agent.h |   43 +++
>  cts/agents/confdb_test_agent.c |  565 ++++++++++++++++++++++++++++++++++++++++
>  cts/agents/cpg_test_agent.c    |  195 +--------------
>  cts/corosync.py                |   48 +++-
>  cts/corotests.py               |   96 ++++++-
>  7 files changed, 988 insertions(+), 216 deletions(-)
>  create mode 100644 cts/agents/common_test_agent.c
>  create mode 100644 cts/agents/common_test_agent.h
>  create mode 100644 cts/agents/confdb_test_agent.c
> 
> diff --git a/cts/agents/Makefile.am b/cts/agents/Makefile.am
> index 8ae7ee7..19c6cc9 100644
> --- a/cts/agents/Makefile.am
> +++ b/cts/agents/Makefile.am
> @@ -32,7 +32,7 @@
>  MAINTAINERCLEANFILES = Makefile.in
>  INCLUDES = -I$(top_builddir)/include -I$(top_srcdir)/include
>  
> -TEST_AGENTS = cpg_test_agent
> +TEST_AGENTS = cpg_test_agent confdb_test_agent
>  
>  if INSTALL_TESTAGENTS
>  agentdir = $(datadir)/$(PACKAGE)/tests
> @@ -43,8 +43,14 @@ noinst_PROGRAMS = $(TEST_AGENTS)
>  noinst_SCRIPTS = mem_leak_test.sh net_breaker.sh
>  endif
>  
> +
> +cpg_test_agent_SOURCES = cpg_test_agent.c common_test_agent.c
>  cpg_test_agent_LDADD =  -lcpg -lcoroipcc ../../exec/coropoll.o ../../exec/crypto.o
> -cpg_test_agent_LDFLAGS =  -L../../lib
> +cpg_test_agent_LDFLAGS =  -L../../lib -L.
> +
> +confdb_test_agent_SOURCES = confdb_test_agent.c common_test_agent.c
> +confdb_test_agent_LDADD =  -lconfdb -lcoroipcc ../../exec/coropoll.o
> +confdb_test_agent_LDFLAGS =  -L../../lib 
>  
>  lint:
>  	-splint $(LINT_FLAGS) $(CFLAGS) *.c
> diff --git a/cts/agents/common_test_agent.c b/cts/agents/common_test_agent.c
> new file mode 100644
> index 0000000..6626103
> --- /dev/null
> +++ b/cts/agents/common_test_agent.c
> @@ -0,0 +1,247 @@
> +/*
> + * Copyright (c) 2010 Red Hat, Inc.
> + *
> + * All rights reserved.
> + *
> + * Author: Angus Salkeld (asalkeld at redhat.com)
> + *
> + * This software licensed under BSD license, the text of which follows:
> + *
> + * Redistribution and use in source and binary forms, with or without
> + * modification, are permitted provided that the following conditions are met:
> + *
> + * - Redistributions of source code must retain the above copyright notice,
> + *   this list of conditions and the following disclaimer.
> + * - Redistributions in binary form must reproduce the above copyright notice,
> + *   this list of conditions and the following disclaimer in the documentation
> + *   and/or other materials provided with the distribution.
> + * - Neither the name of the MontaVista Software, Inc. nor the names of its
> + *   contributors may be used to endorse or promote products derived from this
> + *   software without specific prior written permission.
> + *
> + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
> + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
> + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
> + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
> + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
> + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
> + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
> + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
> + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
> + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
> + * THE POSSIBILITY OF SUCH DAMAGE.
> + */
> +
> +#include <errno.h>
> +#include <unistd.h>
> +#include <stdio.h>
> +#include <stdlib.h>
> +#include <assert.h>
> +#include <string.h>
> +#include <sys/types.h>
> +#include <sys/socket.h>
> +#include <netinet/in.h>
> +#include <arpa/inet.h>
> +#include <netdb.h>
> +#include <syslog.h>
> +#include <poll.h>
> +#include <unistd.h>
> +#include <fcntl.h>
> +#include <corosync/hdb.h>
> +#include <corosync/totem/coropoll.h>
> +#include "common_test_agent.h"
> +
> +
> +int32_t parse_debug = 0;
> +static char big_and_buf_rx[HOW_BIG_AND_BUF];
> +ta_do_command_fn do_command;
> +static hdb_handle_t poll_handle;
> +
> +
> +hdb_handle_t ta_poll_handle_get(void)
> +{
> +	return poll_handle;
> +}
> +
> +static void ta_handle_command (int sock, char* msg)
> +{
> +	int num_args;
> +	char *saveptr = NULL;
> +	char *str = strdup (msg);
> +	char *str_len;
> +	char *str_arg;
> +	char *args[5];
> +	int i = 0;
> +	int a = 0;
> +	char* func = NULL;
> +
> +	if (parse_debug)
> +		syslog (LOG_DEBUG,"%s (MSG:%s)\n", __func__, msg);
> +
> +	str_len = strtok_r (str, ":", &saveptr);
> +	assert (str_len);
> +
> +	num_args = atoi (str_len) * 2;
> +	for (i = 0; i < num_args / 2; i++) {
> +		str_len = strtok_r (NULL, ":", &saveptr);
> +		str_arg = strtok_r (NULL, ":", &saveptr);
> +		if (func == NULL) {
> +			/* first "arg" is the function */
> +			if (parse_debug)
> +				syslog (LOG_DEBUG, "(LEN:%s, FUNC:%s)", str_len, str_arg);
> +			func = str_arg;
> +			a = 0;
> +		} else {
> +			args[a] = str_arg;
> +			a++;
> +			if (parse_debug)
> +				syslog (LOG_DEBUG, "(LEN:%s, ARG:%s)", str_len, str_arg);
> +		}
> +	}
> +	do_command (sock, func, args, a+1);
> +
> +	free (str);
> +}
> +
> +static int server_process_data_fn (hdb_handle_t handle,
> +	int fd,
> +	int revents,
> +	void *data)
> +{
> +	char *saveptr;
> +	char *msg;
> +	char *cmd;
> +	int32_t nbytes;
> +
> +	if ((nbytes = recv (fd, big_and_buf_rx, sizeof (big_and_buf_rx), 0)) <= 0) {
> +		/* got error or connection closed by client */
> +		if (nbytes == 0) {
> +			/* connection closed */
> +			syslog (LOG_WARNING, "socket %d hung up: exiting...\n", fd);
> +		} else {
> +			syslog (LOG_ERR,"recv() failed: %s", strerror(errno));
> +		}
> +		close (fd);
> +		poll_stop (handle);
> +	} else {
> +		big_and_buf_rx[nbytes] = '\0';
> +
> +		msg = strtok_r (big_and_buf_rx, ";", &saveptr);
> +		assert (msg);
> +		while (msg) {
> +			cmd = strdup (msg);
> +			ta_handle_command (fd, cmd);
> +			free (cmd);
> +			msg = strtok_r (NULL, ";", &saveptr);
> +		}
> +	}
> +
> +	return 0;
> +}
> +
> +static int server_accept_fn (hdb_handle_t handle,
> +	int fd, int revents, void *data)
> +{
> +	socklen_t addrlen;
> +	struct sockaddr_in in_addr;
> +	int new_fd;
> +	int res;
> +
> +	addrlen = sizeof (struct sockaddr_in);
> +
> +retry_accept:
> +	new_fd = accept (fd, (struct sockaddr *)&in_addr, &addrlen);
> +	if (new_fd == -1 && errno == EINTR) {
> +		goto retry_accept;
> +	}
> +
> +	if (new_fd == -1) {
> +		syslog (LOG_ERR,
> +			"Could not accept connection: %s\n", strerror (errno));
> +		return (0); /* This is an error, but -1 would indicate disconnect from poll loop */
> +	}
> +
> +	res = fcntl (new_fd, F_SETFL, O_NONBLOCK);
> +	if (res == -1) {
> +		syslog (LOG_ERR,
> +			"Could not set non-blocking operation on connection: %s\n",
> +			strerror (errno));
> +		close (new_fd);
> +		return (0); /* This is an error, but -1 would indicate disconnect from poll loop */
> +	}
> +
> +	poll_dispatch_add (poll_handle, new_fd, POLLIN|POLLNVAL, NULL, server_process_data_fn);
> +	return 0;
> +}
> +
> +
> +static int create_server_sockect (int server_port)
> +{
> +	int listener;
> +	int yes = 1;
> +	int rv;
> +	struct addrinfo hints, *ai, *p;
> +	char server_port_str[16];
> +
> +	/* get a socket and bind it
> +	 */
> +	sprintf(server_port_str, "%d", server_port);
> +	memset (&hints, 0, sizeof hints);
> +	hints.ai_family = AF_UNSPEC;
> +	hints.ai_socktype = SOCK_STREAM;
> +	hints.ai_flags = AI_PASSIVE;
> +	if ((rv = getaddrinfo (NULL, server_port_str, &hints, &ai)) != 0) {
> +		syslog (LOG_ERR, "%s\n", gai_strerror (rv));
> +		exit (1);
> +	}
> +
> +	for (p = ai; p != NULL; p = p->ai_next) {
> +		listener = socket (p->ai_family, p->ai_socktype, p->ai_protocol);
> +		if (listener < 0) {
> +			continue;
> +		}
> +
> +		/* lose the pesky "address already in use" error message
> +		 */
> +		if (setsockopt (listener, SOL_SOCKET, SO_REUSEADDR,
> +				&yes, sizeof(int)) < 0) {
> +			syslog (LOG_ERR, "setsockopt() failed: %s\n", strerror (errno));
> +		}
> +
> +		if (bind (listener, p->ai_addr, p->ai_addrlen) < 0) {
> +			syslog (LOG_ERR, "bind() failed: %s\n", strerror (errno));
> +			close (listener);
> +			continue;
> +		}
> +
> +		break;
> +	}
> +
> +	if (p == NULL) {
> +		syslog (LOG_ERR, "failed to bind\n");
> +		exit (2);
> +	}
> +
> +	freeaddrinfo (ai);
> +
> +	if (listen (listener, 10) == -1) {
> +		syslog (LOG_ERR, "listen() failed: %s", strerror(errno));
> +		exit (3);
> +	}
> +
> +	return listener;
> +}
> +
> +int test_agent_run(int server_port, ta_do_command_fn func)
> +{
> +	int listener;
> +
> +	do_command = func;
> +	poll_handle = poll_create ();
> +
> +	listener = create_server_sockect (server_port);
> +	poll_dispatch_add (poll_handle, listener, POLLIN|POLLNVAL, NULL, server_accept_fn);
> +
> +	return poll_run (poll_handle);
> +}
> +
> diff --git a/cts/agents/common_test_agent.h b/cts/agents/common_test_agent.h
> new file mode 100644
> index 0000000..fc8983c
> --- /dev/null
> +++ b/cts/agents/common_test_agent.h
> @@ -0,0 +1,43 @@
> +/*
> + * Copyright (c) 2010 Red Hat, Inc.
> + *
> + * All rights reserved.
> + *
> + * Author: Angus Salkeld (asalkeld at redhat.com)
> + *
> + * This software licensed under BSD license, the text of which follows:
> + *
> + * Redistribution and use in source and binary forms, with or without
> + * modification, are permitted provided that the following conditions are met:
> + *
> + * - Redistributions of source code must retain the above copyright notice,
> + *   this list of conditions and the following disclaimer.
> + * - Redistributions in binary form must reproduce the above copyright notice,
> + *   this list of conditions and the following disclaimer in the documentation
> + *   and/or other materials provided with the distribution.
> + * - Neither the name of the MontaVista Software, Inc. nor the names of its
> + *   contributors may be used to endorse or promote products derived from this
> + *   software without specific prior written permission.
> + *
> + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
> + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
> + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
> + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
> + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
> + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
> + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
> + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
> + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
> + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
> + * THE POSSIBILITY OF SUCH DAMAGE.
> + */
> +extern int32_t parse_debug;
> +#define HOW_BIG_AND_BUF 4096
> +
> +typedef void (*ta_do_command_fn) (int sock, char* func, char*args[], int num_args);
> +
> +int test_agent_run(int server_port, ta_do_command_fn func);
> +
> +hdb_handle_t ta_poll_handle_get(void);
> +
> +
> diff --git a/cts/agents/confdb_test_agent.c b/cts/agents/confdb_test_agent.c
> new file mode 100644
> index 0000000..6588526
> --- /dev/null
> +++ b/cts/agents/confdb_test_agent.c
> @@ -0,0 +1,565 @@
> +/*
> + * Copyright (c) 2008, 2009 Red Hat Inc
> + *
> + * All rights reserved.
> + *
> + * Author: Christine Caulfield <ccaulfie at redhat.com>
> + *
> + * This software licensed under BSD license, the text of which follows:
> + *
> + * Redistribution and use in source and binary forms, with or without
> + * modification, are permitted provided that the following conditions are met:
> + *
> + * - Redistributions of source code must retain the above copyright notice,
> + *   this list of conditions and the following disclaimer.
> + * - Redistributions in binary form must reproduce the above copyright notice,
> + *   this list of conditions and the following disclaimer in the documentation
> + *   and/or other materials provided with the distribution.
> + * - Neither the name of the MontaVista Software, Inc. nor the names of its
> + *   contributors may be used to endorse or promote products derived from this
> + *   software without specific prior written permission.
> + *
> + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
> + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
> + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
> + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
> + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
> + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
> + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
> + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
> + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
> + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
> + * THE POSSIBILITY OF SUCH DAMAGE.
> + */
> +
> +#include <config.h>
> +
> +#include <stdio.h>
> +#include <stdlib.h>
> +#include <errno.h>
> +#include <unistd.h>
> +#include <string.h>
> +#include <sys/types.h>
> +#include <sys/socket.h>
> +#include <netinet/in.h>
> +#include <arpa/inet.h>
> +#include <netdb.h>
> +#include <sys/un.h>
> +#include <syslog.h>
> +
> +#include <corosync/corotypes.h>
> +#include <corosync/confdb.h>
> +#include "common_test_agent.h"
> +
> +
> +#define OK_STR "OK"
> +#define FAIL_STR "FAIL"
> +#define NOT_SUPPORTED_STR "NOT_SUPPORTED"
> +
> +#define INCDEC_VALUE 45
> +
> +confdb_callbacks_t callbacks = {
> +	.confdb_key_change_notify_fn = NULL,
> +	.confdb_object_create_change_notify_fn = NULL,
> +	.confdb_object_delete_change_notify_fn = NULL
> +};
> +
> +typedef enum {
> +	NTF_OBJECT_CREATED,
> +	NTF_OBJECT_DELETED,
> +	NTF_KEY_CREATED,
> +	NTF_KEY_REPLACED,
> +	NTF_KEY_DELETED,
> +	NTF_NONE,
> +} ntf_callback_type_t;
> +
> +static ntf_callback_type_t callback_type;
> +static char ntf_object_name[256];
> +static size_t ntf_object_name_len;
> +static char ntf_key_name[256];
> +static size_t ntf_key_name_len;
> +static char ntf_key_value[256];
> +static size_t ntf_key_value_len;
> +
> +static void ta_key_change_notify (
> +	confdb_handle_t handle,
> +	confdb_change_type_t change_type,
> +	hdb_handle_t parent_object_handle,
> +	hdb_handle_t object_handle,
> +	const void *object_name,
> +	size_t  object_name_len,
> +	const void *key_name,
> +	size_t key_name_len,
> +	const void *key_value,
> +	size_t key_value_len)
> +{
> +	switch (change_type) {
> +	case OBJECT_KEY_CREATED:
> +		callback_type = NTF_KEY_CREATED;
> +		break;
> +	case OBJECT_KEY_DELETED:
> +		callback_type = NTF_KEY_DELETED;
> +		break;
> +	case OBJECT_KEY_REPLACED:
> +		callback_type = NTF_KEY_REPLACED;
> +		break;
> +	default:
> +		assert (0);
> +		break;
> +	}
> +	ntf_object_name_len = object_name_len;
> +	memcpy (ntf_object_name, object_name, object_name_len);
> +
> +	ntf_key_name_len = key_name_len;
> +	memcpy (ntf_key_name, key_name, key_name_len);
> +
> +	ntf_key_value_len = key_value_len;
> +	memcpy (ntf_key_value, key_value, key_value_len);
> +}
> +
> +static void ta_object_create_notify (
> +	confdb_handle_t handle,
> +	hdb_handle_t parent_object_handle,
> +	hdb_handle_t object_handle,
> +	const void *name_pt,
> +	size_t name_len)
> +{
> +	callback_type = NTF_OBJECT_CREATED;
> +	ntf_object_name_len = name_len;
> +	memcpy (ntf_object_name, name_pt, name_len);
> +}
> +
> +static void ta_object_delete_notify (
> +	confdb_handle_t handle,
> +	hdb_handle_t parent_object_handle,
> +	const void *name_pt,
> +	size_t name_len)
> +{
> +	callback_type = NTF_OBJECT_DELETED;
> +	ntf_object_name_len = name_len;
> +	memcpy (ntf_object_name, name_pt, name_len);
> +}
> +
> +confdb_callbacks_t valid_callbacks = {
> +	.confdb_key_change_notify_fn = ta_key_change_notify,
> +	.confdb_object_create_change_notify_fn = ta_object_create_notify,
> +	.confdb_object_delete_change_notify_fn = ta_object_delete_notify
> +};
> +
> +static void set_get_test (int sock)
> +{
> +	confdb_handle_t handle;
> +	char response[100];
> +	int res;
> +	hdb_handle_t object_handle;
> +	confdb_value_types_t type;
> +	char key_value[256];
> +	char key2_value[256];
> +	size_t value_len;
> +	size_t value2_len;
> +
> +	syslog (LOG_ERR, "%s START", __func__);
> +
> +	snprintf (response, 100, "%s", OK_STR);
> +
> +	res = confdb_initialize (&handle, &callbacks);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "Could not initialize confdb error %d", res);
> +		goto send_response;
> +	}
> +	/* Add a scratch object and put 2 keys into it */
> +	res = confdb_object_create (handle, OBJECT_PARENT_HANDLE,
> +		"testconfdb", strlen("testconfdb"), &object_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error creating 'testconfdb' object: %d", res);
> +		goto send_response;
> +	}
> +
> +	res = confdb_key_create (handle, object_handle,
> +	       "testkey", strlen ("testkey"),
> +		"one", strlen ("one"));
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error creating 'testconfdb' key 1: %d", res);
> +		goto send_response;
> +	}
> +
> +	res = confdb_key_replace (handle, object_handle,
> +		"testkey", strlen ("testkey"),
> +		"one", strlen ("one"),
> +		"newone", strlen ("newone"));
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error replace 'testconfdb' key 2: %d", res);
> +		goto send_response;
> +	}
> +
> +	res = confdb_key_get_typed (handle, object_handle,
> +		"testkey", key_value, &value_len, &type);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "Could not get \"testkey\" key: %d", res);
> +		goto send_response;
> +	}
> +	if (strcmp (key_value, "newone") != 0) {
> +		syslog (LOG_ERR, "Key not set correctly");
> +		goto send_response;
> +	}
> +	if (type != CONFDB_VALUETYPE_ANY) {
> +		syslog (LOG_ERR, "Key type not set correctly");
> +		goto send_response;
> +	}
> +	res = confdb_key_get (handle, object_handle,
> +		"testkey", strlen ("testkey"), key2_value, &value2_len);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "Could not get \"testkey\" key: %d", res);
> +		goto send_response;
> +	}
> +	if (value2_len != value_len) {
> +		syslog (LOG_ERR, "value length from confdb_key_get:%u and confdb_key_get_typed:%u differ.",
> +			(uint32_t)value_len, (uint32_t)value2_len);
> +		goto send_response;
> +	}
> +
> +	res = confdb_key_delete (handle, object_handle,
> +		"testkey", strlen ("testkey"), key2_value, value2_len);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "Could not get \"testkey\" key: %d", res);
> +		goto send_response;
> +	}
> +
> +	/* Remove it.
> +	   Check that it doesn't exist when the full tree dump runs next */
> +	res = confdb_object_destroy(handle, object_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error destroying 'testconfdb' object: %d", res);
> +		goto send_response;
> +	}
> +
> +	snprintf (response, 100, "%s", OK_STR);
> +
> +send_response:
> +	syslog (LOG_ERR, "%s %s", __func__, response);
> +	send (sock, response, strlen (response) + 1, 0);
> +	confdb_finalize (handle);
> +}
> +
> +static void increment_decrement_test (int sock)
> +{
> +	char response[100];
> +	int res;
> +	uint32_t incdec_value;
> +	hdb_handle_t object_handle;
> +	confdb_handle_t handle;
> +	confdb_handle_t par_handle;
> +
> +	snprintf (response, 100, "%s", FAIL_STR);
> +
> +	res = confdb_initialize (&handle, &callbacks);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "Could not initialize confdb error %d", res);
> +		goto send_response;
> +	}
> +	/* Add a scratch object and put 1 keys into it */
> +	res = confdb_object_create(handle, OBJECT_PARENT_HANDLE,
> +	       "testconfdb", strlen("testconfdb"), &object_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error creating 'testconfdb' object: %d", res);
> +		goto send_response;
> +	}
> +
> +	res = confdb_object_parent_get (handle, object_handle, &par_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error getting parent of 'testconfdb' object: %d", res);
> +		goto send_response;
> +	}
> +	if (par_handle != OBJECT_PARENT_HANDLE) {
> +		syslog (LOG_ERR, "wrong parent handle");
> +		goto send_response;
> +	}
> +
> +
> +	incdec_value = INCDEC_VALUE;
> +	res = confdb_key_create_typed (handle, object_handle, "incdec",
> +		&incdec_value, sizeof(incdec_value), CONFDB_VALUETYPE_UINT32);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error creating 'testconfdb' key 4: %d\n", res);
> +		goto send_response;
> +	}
> +	res = confdb_key_increment(handle, object_handle, "incdec", strlen("incdec"), &incdec_value);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error incrementing 'testconfdb' key 4: %d\n", res);
> +		goto send_response;
> +	}
> +	if (incdec_value == INCDEC_VALUE + 1) {
> +		syslog (LOG_INFO, "incremented value = %d\n", incdec_value);
> +	}
> +	else {
> +		syslog (LOG_ERR, "ERROR: incremented value = %d (should be %d)\n", incdec_value, INCDEC_VALUE+1);
> +		goto send_response;
> +	}
> +	res = confdb_key_decrement(handle, object_handle, "incdec", strlen("incdec"), &incdec_value);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error decrementing 'testconfdb' key 4: %d\n", res);
> +		goto send_response;
> +	}
> +	if (incdec_value == INCDEC_VALUE) {
> +		syslog (LOG_ERR, "decremented value = %d\n", incdec_value);
> +	}
> +	else {
> +		syslog (LOG_ERR, "ERROR: decremented value = %d (should be %d)\n", incdec_value, INCDEC_VALUE);
> +		goto send_response;
> +	}
> +	/* Remove it.
> +	   Check that it doesn't exist when the full tree dump runs next */
> +	res = confdb_object_destroy(handle, object_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error destroying 'testconfdb' object: %d\n", res);
> +		goto send_response;
> +	}
> +
> +	snprintf (response, 100, "%s", OK_STR);
> +
> +send_response:
> +	confdb_finalize (handle);
> +	send (sock, response, strlen (response) + 1, 0);
> +}
> +
> +
> +static void object_find_test (int sock)
> +{
> +	char response[100];
> +	confdb_handle_t handle;
> +	int result;
> +	hdb_handle_t totem_handle;
> +	char key_value[256];
> +	size_t value_len;
> +
> +	snprintf (response, 100, "%s", FAIL_STR);
> +
> +	result = confdb_initialize (&handle, &callbacks);
> +	if (result != CS_OK) {
> +		syslog (LOG_ERR, "Could not initialize confdb error %d\n", result);
> +		goto send_response;
> +	}
> +
> +	/* Find "totem" and dump bits of it again, to test the direct APIs */
> +	result = confdb_object_find_start(handle, OBJECT_PARENT_HANDLE);
> +	if (result != CS_OK) {
> +		syslog (LOG_ERR, "Could not start object_find %d\n", result);
> +		goto send_response;
> +	}
> +
> +	result = confdb_object_find(handle, OBJECT_PARENT_HANDLE, "totem", strlen("totem"), &totem_handle);
> +	if (result != CS_OK) {
> +		syslog (LOG_ERR, "Could not object_find \"totem\": %d\n", result);
> +		goto send_response;
> +	}
> +
> +	result = confdb_key_get(handle, totem_handle, "version", strlen("version"), key_value, &value_len);
> +	if (result != CS_OK) {
> +		syslog (LOG_ERR, "Could not get \"version\" key: %d\n", result);
> +		goto send_response;
> +	}
> +
> +	result = confdb_object_find_destroy (handle, OBJECT_PARENT_HANDLE);
> +	if (result != CS_OK) {
> +		syslog (LOG_ERR, "Could not destroy find object %d\n", result);
> +		goto send_response;
> +	}
> +
> +
> +	snprintf (response, 100, "%s", OK_STR);
> +
> +send_response:
> +	confdb_finalize (handle);
> +	send (sock, response, strlen (response) + 1, 0);
> +}
> +
> +static void notification_test (int sock)
> +{
> +	char response[100];
> +	confdb_handle_t handle;
> +	int res;
> +	hdb_handle_t object_handle;
> +	hdb_handle_t new_object_handle;
> +	uint16_t incdec_value;
> +	uint32_t incdec_value_out;
> +
> +	snprintf (response, 100, "%s", FAIL_STR);
> +
> +	res = confdb_initialize (&handle, &valid_callbacks);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "Could not initialize confdb error %d\n", res);
> +		goto send_response;
> +	}
> +
> +	/* Add a base scratch object (we don't want to track the parent object) */
> +	res = confdb_object_create(handle, OBJECT_PARENT_HANDLE,
> +	       "testconfdb", strlen("testconfdb"), &object_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error creating 'testconfdb' object: %d", res);
> +		goto send_response;
> +	}
> +
> +	res = confdb_track_changes (handle, object_handle, 1 /*OBJECT_TRACK_DEPTH_RECURSIVE*/);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "can't track changes on object: %d", res);
> +		goto send_response;
> +	}
> +
> +	/* Test 'object created' notification
> +	 */
> +	callback_type = NTF_NONE;
> +
> +	res = confdb_object_create(handle, object_handle,
> +	       "duck", strlen("duck"), &new_object_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error creating 'duck' object: %d", res);
> +		goto send_response;
> +	}
> +
> +	confdb_dispatch (handle, CS_DISPATCH_ALL);
> +
> +	if (callback_type != NTF_OBJECT_CREATED) {
> +		syslog (LOG_ERR, "no notification received for the creation of 'duck'");
> +		goto send_response;
> +	}
> +	if (strcmp ("duck", ntf_object_name) != 0) {
> +		syslog (LOG_ERR, "expected notification for 'duck' but got %s", ntf_object_name);
> +		goto send_response;
> +	}
> +
> +	/* Test 'key created' notification
> +	 */
> +	callback_type = NTF_NONE;
> +
> +	incdec_value = INCDEC_VALUE;
> +	res = confdb_key_create_typed (handle, new_object_handle, "incdec",
> +		&incdec_value, sizeof(incdec_value), CONFDB_VALUETYPE_UINT16);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error creating 'testconfdb' key 4: %d\n", res);
> +		goto send_response;
> +	}
> +
> +	confdb_dispatch (handle, CS_DISPATCH_ALL);
> +
> +	if (callback_type != NTF_KEY_CREATED) {
> +		syslog (LOG_ERR, "no notification received for the creation of key 'incdec'");
> +		goto send_response;
> +	}
> +	if (strcmp ("incdec", ntf_key_name) != 0) {
> +		syslog (LOG_ERR, "expected notification for 'incdec' but got %s", ntf_key_name);
> +		goto send_response;
> +	}
> +
> +	/* Test 'key replaced' notification
> +	 */
> +	callback_type = NTF_NONE;
> +
> +	res = confdb_key_increment(handle, new_object_handle, "incdec", strlen("incdec"), &incdec_value_out);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error incrementing 'testconfdb' key 4: %d\n", res);
> +		goto send_response;
> +	}
> +
> +	confdb_dispatch (handle, CS_DISPATCH_ALL);
> +
> +	if (callback_type != NTF_KEY_REPLACED) {
> +		syslog (LOG_ERR, "no notification received for the incrementing of key 'incdec'");
> +		goto send_response;
> +	}
> +	if (strcmp ("incdec", ntf_key_name) != 0) {
> +		syslog (LOG_ERR, "expected notification for 'incdec' but got %s", ntf_key_name);
> +		goto send_response;
> +	}
> +
> +	/* Test 'key destroyed' notification
> +	 */
> +	callback_type = NTF_NONE;
> +
> +	res = confdb_key_delete (handle, new_object_handle,
> +		"incdec", strlen ("incdec"), ntf_key_value, ntf_key_value_len);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "Could not delete \"incdec\" key: %d", res);
> +		goto send_response;
> +	}
> +
> +	confdb_dispatch (handle, CS_DISPATCH_ALL);
> +
> +	if (callback_type != NTF_KEY_DELETED) {
> +		syslog (LOG_ERR, "no notification received for the deletion of key 'incdec'");
> +		goto send_response;
> +	}
> +	if (strcmp ("incdec", ntf_key_name) != 0) {
> +		syslog (LOG_ERR, "expected notification for 'incdec' but got %s", ntf_key_name);
> +		goto send_response;
> +	}
> +
> +	/* Test 'object destroyed' notification
> +	 */
> +	callback_type = NTF_NONE;
> +
> +	res = confdb_object_destroy(handle, new_object_handle);
> +	if (res != CS_OK) {
> +		syslog (LOG_ERR, "error destroying 'testconfdb' object: %d", res);
> +		goto send_response;
> +	}
> +
> +	confdb_dispatch (handle, CS_DISPATCH_ALL);
> +
> +	if (callback_type != NTF_OBJECT_DELETED) {
> +		syslog (LOG_ERR, "no notification received for the deletion of 'duck'");
> +		goto send_response;
> +	}
> +	if (strcmp ("duck", ntf_object_name) != 0) {
> +		syslog (LOG_ERR, "expected notification for 'duck' but got %s", ntf_object_name);
> +		goto send_response;
> +	}
> +	confdb_stop_track_changes (handle);
> +	confdb_object_destroy(handle, object_handle);
> +
> +	snprintf (response, 100, "%s", OK_STR);
> +
> +send_response:
> +	send (sock, response, strlen (response) + 1, 0);
> +	confdb_finalize (handle);
> +}
> +
> +
> +
> +static void do_command (int sock, char* func, char*args[], int num_args)
> +{
> +	char response[100];
> +
> +	if (parse_debug)
> +		syslog (LOG_DEBUG,"RPC:%s() called.", func);
> +
> +	if (strcmp ("set_get_test", func) == 0) {
> +		set_get_test (sock);
> +	} else if (strcmp ("increment_decrement_test", func) == 0) {
> +		increment_decrement_test (sock);
> +	} else if (strcmp ("object_find_test", func) == 0) {
> +		object_find_test (sock);
> +	} else if (strcmp ("notification_test", func) == 0) {
> +		notification_test (sock);
> +	} else {
> +		syslog (LOG_ERR,"%s RPC:%s not supported!", __func__, func);
> +		snprintf (response, 100, "%s", NOT_SUPPORTED_STR);
> +		send (sock, response, strlen (response) + 1, 0);
> +	}
> +}
> +
> +
> +int main (int argc, char *argv[])
> +{
> +	int ret;
> +
> +	openlog (NULL, LOG_CONS|LOG_PID, LOG_DAEMON);
> +	syslog (LOG_ERR, "confdb_test_agent STARTING");
> +
> +	parse_debug = 1;
> +	ret = test_agent_run (9035, do_command);
> +	syslog (LOG_ERR, "confdb_test_agent EXITING");
> +
> +	return ret;
> +}
> +
> +
> diff --git a/cts/agents/cpg_test_agent.c b/cts/agents/cpg_test_agent.c
> index de47ca8..ac87af4 100644
> --- a/cts/agents/cpg_test_agent.c
> +++ b/cts/agents/cpg_test_agent.c
> @@ -51,10 +51,9 @@
>  #include <corosync/list.h>
>  #include <corosync/cpg.h>
>  #include "../../exec/crypto.h"
> +#include "common_test_agent.h"
>  
> 
> -#define SERVER_PORT "9034"
> -
>  typedef enum {
>  	MSG_OK,
>  	MSG_NODEID_ERR,
> @@ -79,10 +78,7 @@ typedef struct {
>  	struct list_head list;
>  } log_entry_t;
>  
> -#define HOW_BIG_AND_BUF 4096
>  static char big_and_buf[HOW_BIG_AND_BUF];
> -static char big_and_buf_rx[HOW_BIG_AND_BUF];
> -static int32_t parse_debug = 0;
>  static int32_t record_config_events_g = 0;
>  static int32_t record_messages_g = 0;
>  static cpg_handle_t cpg_handle = 0;
> @@ -94,7 +90,6 @@ static uint32_t my_nodeid;
>  static int32_t my_seq;
>  static int32_t my_msgs_to_send;
>  static int32_t total_stored_msgs = 0;
> -static hdb_handle_t poll_handle;
>  
> 
>  static void send_some_more_messages (void * unused);
> @@ -289,7 +284,7 @@ static void send_some_more_messages_later (void)
>  	poll_timer_handle timer_handle;
>  	cpg_dispatch (cpg_handle, CS_DISPATCH_ALL);
>  	poll_timer_add (
> -		poll_handle,
> +		ta_poll_handle_get(),
>  		100, NULL,
>  		send_some_more_messages,
>  		&timer_handle);
> @@ -384,7 +379,7 @@ static int cpg_dispatch_wrapper_fn (hdb_handle_t handle,
>  	cs_error_t error = cpg_dispatch (cpg_handle, CS_DISPATCH_ALL);
>  	if (error == CS_ERR_LIBRARY) {
>  		syslog (LOG_ERR, "%s() got LIB error disconnecting from corosync.", __func__);
> -		poll_dispatch_delete (poll_handle, cpg_fd);
> +		poll_dispatch_delete (ta_poll_handle_get(), cpg_fd);
>  		close (cpg_fd);
>  		cpg_fd = -1;
>  	}
> @@ -450,7 +445,7 @@ static void do_command (int sock, char* func, char*args[], int num_args)
>  		}
>  
>  		cpg_fd_get (cpg_handle, &cpg_fd);
> -		poll_dispatch_add (poll_handle, cpg_fd, POLLIN|POLLNVAL, NULL, cpg_dispatch_wrapper_fn);
> +		poll_dispatch_add (ta_poll_handle_get(), cpg_fd, POLLIN|POLLNVAL, NULL, cpg_dispatch_wrapper_fn);
>  
>  	} else if (strcmp ("cpg_local_get", func) == 0) {
>  		unsigned int local_nodeid;
> @@ -463,7 +458,7 @@ static void do_command (int sock, char* func, char*args[], int num_args)
>  	} else if (strcmp ("cpg_finalize",func) == 0) {
>  
>  		cpg_finalize (cpg_handle);
> -		poll_dispatch_delete (poll_handle, cpg_fd);
> +		poll_dispatch_delete (ta_poll_handle_get(), cpg_fd);
>  		cpg_fd = -1;
>  
>  	} else if (strcmp ("record_config_events",func) == 0) {
> @@ -491,192 +486,14 @@ static void do_command (int sock, char* func, char*args[], int num_args)
>  	}
>  }
>  
> -static void handle_command (int sock, char* msg)
> -{
> -	int num_args;
> -	char *saveptr = NULL;
> -	char *str = strdup (msg);
> -	char *str_len;
> -	char *str_arg;
> -	char *args[5];
> -	int i = 0;
> -	int a = 0;
> -	char* func = NULL;
> -
> -	if (parse_debug)
> -		syslog (LOG_DEBUG,"%s (MSG:%s)\n", __func__, msg);
> -
> -	str_len = strtok_r (str, ":", &saveptr);
> -	assert (str_len);
> -
> -	num_args = atoi (str_len) * 2;
> -	for (i = 0; i < num_args / 2; i++) {
> -		str_len = strtok_r (NULL, ":", &saveptr);
> -		str_arg = strtok_r (NULL, ":", &saveptr);
> -		if (func == NULL) {
> -			/* first "arg" is the function */
> -			if (parse_debug)
> -				syslog (LOG_DEBUG, "(LEN:%s, FUNC:%s)", str_len, str_arg);
> -			func = str_arg;
> -			a = 0;
> -		} else {
> -			args[a] = str_arg;
> -			a++;
> -			if (parse_debug)
> -				syslog (LOG_DEBUG, "(LEN:%s, ARG:%s)", str_len, str_arg);
> -		}
> -	}
> -	do_command (sock, func, args, a+1);
> -
> -	free (str);
> -}
> -
> -static int server_process_data_fn (hdb_handle_t handle,
> -	int fd,
> -	int revents,
> -	void *data)
> -{
> -	char *saveptr;
> -	char *msg;
> -	char *cmd;
> -	int32_t nbytes;
> -
> -	if ((nbytes = recv (fd, big_and_buf_rx, sizeof (big_and_buf_rx), 0)) <= 0) {
> -		/* got error or connection closed by client */
> -		if (nbytes == 0) {
> -			/* connection closed */
> -			syslog (LOG_WARNING, "socket %d hung up: exiting...\n", fd);
> -		} else {
> -			syslog (LOG_ERR,"recv() failed: %s", strerror(errno));
> -		}
> -		close (fd);
> -		exit (0);
> -	} else {
> -		if (my_msgs_to_send > 0)
> -			send_some_more_messages (NULL);
> -
> -		big_and_buf_rx[nbytes] = '\0';
> -
> -		msg = strtok_r (big_and_buf_rx, ";", &saveptr);
> -		assert (msg);
> -		while (msg) {
> -			cmd = strdup (msg);
> -			handle_command (fd, cmd);
> -			free (cmd);
> -			msg = strtok_r (NULL, ";", &saveptr);
> -		}
> -	}
> -
> -	return 0;
> -}
> -
> -static int server_accept_fn (hdb_handle_t handle,
> -	int fd,
> -	int revents,
> -	void *data)
> -{
> -	socklen_t addrlen;
> -	struct sockaddr_in in_addr;
> -	int new_fd;
> -	int res;
> -
> -	addrlen = sizeof (struct sockaddr_in);
> -
> -retry_accept:
> -	new_fd = accept (fd, (struct sockaddr *)&in_addr, &addrlen);
> -	if (new_fd == -1 && errno == EINTR) {
> -		goto retry_accept;
> -	}
> -
> -	if (new_fd == -1) {
> -		syslog (LOG_ERR,
> -			"Could not accept connection: %s\n", strerror (errno));
> -		return (0); /* This is an error, but -1 would indicate disconnect from poll loop */
> -	}
> -
> -	res = fcntl (new_fd, F_SETFL, O_NONBLOCK);
> -	if (res == -1) {
> -		syslog (LOG_ERR,
> -			"Could not set non-blocking operation on connection: %s\n",
> -			strerror (errno));
> -		close (new_fd);
> -		return (0); /* This is an error, but -1 would indicate disconnect from poll loop */
> -	}
> -
> -	poll_dispatch_add (poll_handle, new_fd, POLLIN|POLLNVAL, NULL, server_process_data_fn);
> -	return 0;
> -}
> -
> -static int create_server_sockect (void)
> -{
> -	int listener;
> -	int yes = 1;
> -	int rv;
> -	struct addrinfo hints, *ai, *p;
> -
> -	/* get a socket and bind it
> -	 */
> -	memset (&hints, 0, sizeof hints);
> -	hints.ai_family = AF_UNSPEC;
> -	hints.ai_socktype = SOCK_STREAM;
> -	hints.ai_flags = AI_PASSIVE;
> -	if ((rv = getaddrinfo (NULL, SERVER_PORT, &hints, &ai)) != 0) {
> -		syslog (LOG_ERR, "%s\n", gai_strerror (rv));
> -		exit (1);
> -	}
> -
> -	for (p = ai; p != NULL; p = p->ai_next) {
> -		listener = socket (p->ai_family, p->ai_socktype, p->ai_protocol);
> -		if (listener < 0) {
> -			continue;
> -		}
> -
> -		/* lose the pesky "address already in use" error message
> -		 */
> -		if (setsockopt (listener, SOL_SOCKET, SO_REUSEADDR,
> -				&yes, sizeof(int)) < 0) {
> -			syslog (LOG_ERR, "setsockopt() failed: %s\n", strerror (errno));
> -		}
> -
> -		if (bind (listener, p->ai_addr, p->ai_addrlen) < 0) {
> -			syslog (LOG_ERR, "bind() failed: %s\n", strerror (errno));
> -			close (listener);
> -			continue;
> -		}
> -
> -		break;
> -	}
> -
> -	if (p == NULL) {
> -		syslog (LOG_ERR, "failed to bind\n");
> -		exit (2);
> -	}
> -
> -	freeaddrinfo (ai);
> -
> -	if (listen (listener, 10) == -1) {
> -		syslog (LOG_ERR, "listen() failed: %s", strerror(errno));
> -		exit (3);
> -	}
> -
> -	return listener;
> -}
>  
>  int main (int argc, char *argv[])
>  {
> -	int listener;
> -
>  	openlog (NULL, LOG_CONS|LOG_PID, LOG_DAEMON);
>  
>  	list_init (&msg_log_head);
>  	list_init (&config_chg_log_head);
>  
> -	poll_handle = poll_create ();
> -
> -	listener = create_server_sockect ();
> -	poll_dispatch_add (poll_handle, listener, POLLIN|POLLNVAL, NULL, server_accept_fn);
> -
> -	poll_run (poll_handle);
> -	return -1;
> +	return test_agent_run (9034, do_command);
>  }
>  
> diff --git a/cts/corosync.py b/cts/corosync.py
> index 9455a36..f54af4d 100644
> --- a/cts/corosync.py
> +++ b/cts/corosync.py
> @@ -135,7 +135,8 @@ class corosync_flatiron(ClusterManager):
>              ),
>              "LogFileName"    : Environment["LogFileName"],
>              })
> -        self.agent={}
> +        self.cpg_agent={}
> +        self.confdb_agent={}
>          self.config = CoroConfig ()
>          self.node_to_ip = {}
>          
> @@ -209,8 +210,10 @@ class corosync_flatiron(ClusterManager):
>  
>          self.debug('starting corosync on : ' + node)
>          ret = ClusterManager.StartaCM(self, node)
> -        if self.agent.has_key(node):
> -            self.agent[node].restart()
> +        if self.cpg_agent.has_key(node):
> +            self.cpg_agent[node].restart()
> +        if self.confdb_agent.has_key(node):
> +            self.confdb_agent[node].restart()
>          return ret
>  
>      def StopaCM(self, node):
> @@ -218,8 +221,10 @@ class corosync_flatiron(ClusterManager):
>              return 1
>  
>          self.debug('stoping corosync on : ' + node)
> -        if self.agent.has_key(node):
> -            self.agent[node].stop()
> +        if self.cpg_agent.has_key(node):
> +            self.cpg_agent[node].stop()
> +        if self.confdb_agent.has_key(node):
> +            self.confdb_agent[node].stop()
>          return ClusterManager.StopaCM(self, node)
>  
>      def test_node_CM(self, node):
> @@ -318,15 +323,18 @@ class TestAgentComponent(ScenarioComponent):
>              if not CM.StataCM(node):
>                  raise RuntimeError ("corosync not up")
>  
> -            self.CM.agent[node] = CpgTestAgent(node, CM.Env)
> -            self.CM.agent[node].start()
> +            self.CM.cpg_agent[node] = CpgTestAgent(node, CM.Env)
> +            self.CM.cpg_agent[node].start()
> +            self.CM.confdb_agent[node] = ConfdbTestAgent(node, CM.Env)
> +            self.CM.confdb_agent[node].start()
>          return 1
>  
>      def TearDown(self, CM):
>          '''Tear down (undo) the given ScenarioComponent'''
>          self.CM = CM
>          for node in self.Env["nodes"]:
> -            self.CM.agent[node].stop()
> +            self.CM.cpg_agent[node].stop()
> +            self.CM.confdb_agent[node].stop()
>  
>  ###################################################################
>  class TestAgent(object):
> @@ -342,6 +350,7 @@ class TestAgent(object):
>          self.func_name = None
>          self.used = False
>          self.env = env
> +        self.send_recv = False
>  
>      def restart(self):
>          self.stop()
> @@ -416,7 +425,14 @@ class TestAgent(object):
>              return object.__getattribute__(self, name)
>          except:
>              self.func_name = name
> -            return self.send_dynamic
> +            if self.send_recv:
> +                return self.send_recv_dynamic
> +            else:
> +                return self.send_dynamic
> +
> +    def send_recv_dynamic (self, *args):
> +        self.send_dynamic (args)
> +        return self.read()
>  
>      def send_dynamic (self, *args):
>          if not self.started:
> @@ -484,7 +500,7 @@ class CpgTestAgent(TestAgent):
>          try:
>              self.send(["cpg_finalize"])
>          except RuntimeError, msg:
> -            # if agent is down, we are not going to stress
> +            # if cpg_agent is down, we are not going to stress
>              print msg
>  
>          TestAgent.stop(self)
> @@ -519,3 +535,15 @@ class CpgTestAgent(TestAgent):
>          else:
>              return msg
>  
> +###################################################################
> +class ConfdbTestAgent(TestAgent):
> +
> +    def __init__(self, node, Env=None):
> +        TestAgent.__init__(self, "confdb_test_agent", node, 9035, env=Env)
> +        self.initialized = False
> +        self.nodeid = None
> +        self.send_recv = True
> +
> +    def cpg_local_get(self):
> +        return 1
> +
> diff --git a/cts/corotests.py b/cts/corotests.py
> index fb28fc5..8fe5149 100644
> --- a/cts/corotests.py
> +++ b/cts/corotests.py
> @@ -97,15 +97,15 @@ class CpgConfigChangeBase(CoroTest):
>          self.listener = None
>          self.wobbly = None
>          for n in self.CM.Env["nodes"]:
> -            self.CM.agent[n].clean_start()
> -            self.CM.agent[n].cpg_join(self.name)
> +            self.CM.cpg_agent[n].clean_start()
> +            self.CM.cpg_agent[n].cpg_join(self.name)
>              if self.listener is None:
>                  self.listener = n
>              elif self.wobbly is None:
>                  self.wobbly = n
>  
> -        self.wobbly_id = self.CM.agent[self.wobbly].cpg_local_get()
> -        self.CM.agent[self.listener].record_config_events(truncate=True)
> +        self.wobbly_id = self.CM.cpg_agent[self.wobbly].cpg_local_get()
> +        self.CM.cpg_agent[self.listener].record_config_events(truncate=True)
>  
>          return ret
>  
> @@ -117,9 +117,9 @@ class CpgConfigChangeBase(CoroTest):
>          self.CM.log("Waiting for config change on " + self.listener)
>          while not found:
>              try:
> -                event = self.CM.agent[self.listener].read_config_event()
> +                event = self.CM.cpg_agent[self.listener].read_config_event()
>              except:
> -                return self.failure('connection to test agent failed.')
> +                return self.failure('connection to test cpg_agent failed.')
>              if not event == None:
>                  self.CM.debug("RECEIVED: " + str(event))
>              if event == None:
> @@ -155,7 +155,7 @@ class CpgCfgChgOnGroupLeave(CpgConfigChangeBase):
>  
>      def failure_action(self):
>          self.CM.log("calling cpg_leave() on " + self.wobbly)
> -        self.CM.agent[self.wobbly].cpg_leave(self.name)
> +        self.CM.cpg_agent[self.wobbly].cpg_leave(self.name)
>  
>      def __call__(self, node):
>          self.incr("calls")
> @@ -230,16 +230,16 @@ class CpgMsgOrderBase(CoroTest):
>  
>          for n in self.CM.Env["nodes"]:
>              self.total_num_msgs = self.total_num_msgs + self.num_msgs_per_node
> -            self.CM.agent[n].clean_start()
> -            self.CM.agent[n].cpg_join(self.name)
> -            self.CM.agent[n].record_messages()
> +            self.CM.cpg_agent[n].clean_start()
> +            self.CM.cpg_agent[n].cpg_join(self.name)
> +            self.CM.cpg_agent[n].record_messages()
>  
>          time.sleep(1)
>          return ret
>  
>      def cpg_msg_blaster(self):
>          for n in self.CM.Env["nodes"]:
> -            self.CM.agent[n].msg_blaster(self.num_msgs_per_node)
> +            self.CM.cpg_agent[n].msg_blaster(self.num_msgs_per_node)
>          
>      def wait_and_validate_order(self):
>          msgs = {}
> @@ -251,7 +251,7 @@ class CpgMsgOrderBase(CoroTest):
>  
>              while len(msgs[n]) < self.total_num_msgs and waited < 60:
>  
> -                msg = self.CM.agent[n].read_messages(25)
> +                msg = self.CM.cpg_agent[n].read_messages(25)
>                  if not msg == None:
>                      msgl = msg.split(";")
>  
> @@ -428,6 +428,67 @@ class ServiceLoadTest(CoroTest):
>  
>          return self.success()
>  
> +
> +###################################################################
> +class ConfdbReplaceTest(CoroTest):
> +    def __init__(self, cm):
> +        CoroTest.__init__(self, cm)
> +        self.name="ConfdbReplaceTest"
> +
> +    def __call__(self, node):
> +        self.incr("calls")
> +        res = self.CM.confdb_agent[node].set_get_test()
> +        if 'OK' in res:
> +            return self.success()
> +        else:
> +            return self.failure('set_get_test failed')
> +
> +
> +###################################################################
> +class ConfdbIncrementTest(CoroTest):
> +    def __init__(self, cm):
> +        CoroTest.__init__(self, cm)
> +        self.name="ConfdbIncrementTest"
> +
> +    def __call__(self, node):
> +        self.incr("calls")
> +        res = self.CM.confdb_agent[node].increment_decrement_test()
> +        if 'OK' in res:
> +            return self.success()
> +        else:
> +            return self.failure('increment_decrement_test failed')
> +
> +
> +###################################################################
> +class ConfdbObjectFindTest(CoroTest):
> +    def __init__(self, cm):
> +        CoroTest.__init__(self, cm)
> +        self.name="ConfdbObjectFindTest"
> +
> +    def __call__(self, node):
> +        self.incr("calls")
> +        res = self.CM.confdb_agent[node].object_find_test()
> +        if 'OK' in res:
> +            return self.success()
> +        else:
> +            return self.failure('object_find_test failed')
> +
> +
> +###################################################################
> +class ConfdbNotificationTest(CoroTest):
> +    def __init__(self, cm):
> +        CoroTest.__init__(self, cm)
> +        self.name="ConfdbNotificationTest"
> +
> +    def __call__(self, node):
> +        self.incr("calls")
> +        res = self.CM.confdb_agent[node].notification_test()
> +        if 'OK' in res:
> +            return self.success()
> +        else:
> +            return self.failure('notification_test failed')
> +
> +
>  GenTestClasses = []
>  GenTestClasses.append(CpgMsgOrderBasic)
>  GenTestClasses.append(CpgCfgChgOnExecCrash)
> @@ -436,6 +497,11 @@ GenTestClasses.append(CpgCfgChgOnNodeLeave)
>  GenTestClasses.append(CpgCfgChgOnNodeIsolate)
>  
>  AllTestClasses = []
> +AllTestClasses.append(ConfdbReplaceTest)
> +AllTestClasses.append(ConfdbIncrementTest)
> +AllTestClasses.append(ConfdbObjectFindTest)
> +AllTestClasses.append(ConfdbNotificationTest)
> +
>  AllTestClasses.append(ServiceLoadTest)
>  AllTestClasses.append(MemLeakObject)
>  AllTestClasses.append(MemLeakSession)
> @@ -488,9 +554,9 @@ def CoroTestList(cm, audits):
>      configs.append(e)
>  
>      #quorum/provider=
> -    f = {}
> -    f['quorum/provider'] = 'corosync_quorum_ykd'
> -    configs.append(f)
> +    #f = {}
> +    #f['quorum/provider'] = 'corosync_quorum_ykd'
> +    #configs.append(f)
>  
>      num=1
>      for cfg in configs:



More information about the Openais mailing list