*/
struct ctdb_context *ctdb_init(TALLOC_CTX *mem_ctx);
+/*
+ tell ctdb what address to listen on, in transport specific format
+*/
+int ctdb_set_address(struct ctdb_context *ctdb, const char *address);
+
/*
tell ctdb what nodes are available. This takes a filename, which will contain
1 node address per line, in a transport specific format
*/
int ctdb_set_nlist(struct ctdb_context *ctdb, const char *nlist);
+/*
+ start the ctdb protocol
+*/
+int ctdb_start(struct ctdb_context *ctdb);
/*
error string for last ctdb error
uint16_t flags, void *private)
{
struct ctdb_node *node = talloc_get_type(private, struct ctdb_node);
- printf("connection to node %s:%u is readable\n", node->address, node->port);
+ printf("connection to node %s:%u is readable\n",
+ node->address.address, node->address.port);
event_set_fd_flags(fde, 0);
}
return;
}
- printf("Established connection to %s:%u\n", node->address, node->port);
+ printf("Established connection to %s:%u\n",
+ node->address.address, node->address.port);
talloc_free(fde);
event_add_fd(node->ctdb->ev, node, node->fd, EVENT_FD_READ,
ctdb_node_read, node);
v = fcntl(node->fd, F_GETFL, 0);
fcntl(node->fd, F_SETFL, v | O_NONBLOCK);
- inet_pton(AF_INET, node->address, &sock_out.sin_addr);
- sock_out.sin_port = htons(node->port);
+ inet_pton(AF_INET, node->address.address, &sock_out.sin_addr);
+ sock_out.sin_port = htons(node->address.port);
sock_out.sin_family = PF_INET;
if (connect(node->fd, &sock_out, sizeof(sock_out)) != 0 &&
ctdb_node_connect_write, node);
}
+/*
+ parse a IP:port pair
+*/
+static int ctdb_parse_address(struct ctdb_context *ctdb,
+ TALLOC_CTX *mem_ctx, const char *str,
+ struct ctdb_address *address)
+{
+ char *p;
+ p = strchr(str, ':');
+ if (p == NULL) {
+ ctdb_set_error(ctdb, "Badly formed node '%s'\n", str);
+ return -1;
+ }
+
+ address->address = talloc_strndup(mem_ctx, str, p-str);
+ address->port = strtoul(p+1, NULL, 0);
+ return 0;
+}
+
/*
add a node to the list of active nodes
{
struct ctdb_node *node;
- /* expected to be in IP:port format */
- char *p;
- p = strchr(nstr, ':');
- if (p == NULL) {
- ctdb_set_error(ctdb, "Badly formed node '%s'\n", nstr);
+ node = talloc(ctdb, struct ctdb_node);
+ if (ctdb_parse_address(ctdb, node, nstr, &node->address) != 0) {
return -1;
}
- *p++ = 0;
-
- node = talloc(ctdb, struct ctdb_node);
- node->address = talloc_strdup(node, nstr);
- node->port = strtoul(p, NULL, 0);
node->fd = -1;
node->ctdb = ctdb;
DLIST_ADD(ctdb->nodes, node);
- event_add_timed(ctdb->ev, node, timeval_zero(), ctdb_node_connect, node);
return 0;
}
return 0;
}
+/*
+ setup the node list from a file
+*/
+int ctdb_set_address(struct ctdb_context *ctdb, const char *address)
+{
+ return ctdb_parse_address(ctdb, ctdb, address, &ctdb->address);
+}
+
/*
add a node to the list of active nodes
*/
{
struct ctdb_context *ctdb;
const char *nlist = NULL;
+ const char *myaddress = NULL;
+
struct poptOption popt_options[] = {
POPT_AUTOHELP
{ "nlist", 0, POPT_ARG_STRING, &nlist, 0, "node list file", "filename" },
+ { "listen", 0, POPT_ARG_STRING, &myaddress, 0, "address to listen on", "address" },
};
int opt;
const char **extra_argv;
while (extra_argv[extra_argc]) extra_argc++;
}
- if (nlist == NULL) {
- printf("You must provide a node list with --nlist\n");
+ if (nlist == NULL || myaddress == NULL) {
+ printf("You must provide a node list with --nlist and an address with --listen\n");
exit(1);
}
exit(1);
}
+ /* tell ctdb what address to listen on */
+ ret = ctdb_set_address(ctdb, myaddress);
+ if (ret == -1) {
+ printf("ctdb_set_address failed - %s\n", ctdb_errstr(ctdb));
+ exit(1);
+ }
+
/* tell ctdb what nodes are available */
ret = ctdb_set_nlist(ctdb, nlist);
if (ret == -1) {
/* setup a ctdb call function */
ret = ctdb_set_call(ctdb, sort_func, FUNC_SORT);
ret = ctdb_set_call(ctdb, fetch_func, FUNC_FETCH);
-
+
/* attach to a specific database */
ret = ctdb_attach(ctdb, "test.tdb", TDB_DEFAULT, O_RDWR|O_CREAT|O_TRUNC, 0666);
if (ret == -1) {
exit(1);
}
+ /* start the protocol running */
+ ret = ctdb_start(ctdb);
+
key.dptr = "test";
key.dsize = strlen("test")+1;