static void ctdb_node_dead(struct ctdb_node *node)
{
node->ctdb->num_connected--;
+ node->flags &= ~NODE_FLAGS_CONNECTED;
DEBUG(1,("%s: node %s is dead: %d connected\n",
node->ctdb->name, node->name, node->ctdb->num_connected));
}
static void ctdb_node_connected(struct ctdb_node *node)
{
node->ctdb->num_connected++;
+ node->flags |= NODE_FLAGS_CONNECTED;
DEBUG(1,("%s: connected to %s - %d connected\n",
node->ctdb->name, node->name, node->ctdb->num_connected));
}
}
+/*
+ get a list of nodes (vnn and flags ) from a remote node
+ */
+int ctdb_getnodemap(struct ctdb_context *ctdb, uint32_t destnode, struct ctdb_node_map *nodemap)
+{
+ int ret;
+ TDB_DATA data, outdata;
+ int32_t i, res;
+
+ ZERO_STRUCT(data);
+ ret = ctdb_control(ctdb, destnode, 0,
+ CTDB_CONTROL_GET_NODEMAP, data,
+ ctdb, &outdata, &res);
+ if (ret != 0 || res != 0) {
+ DEBUG(0,(__location__ " ctdb_control for getnodes failed\n"));
+ return -1;
+ }
+
+ nodemap->num = ((uint32_t *)outdata.dptr)[0];
+ if (nodemap->nodes) {
+ talloc_free(nodemap->nodes);
+ nodemap->nodes=NULL;
+ }
+ nodemap->nodes=talloc_array(nodemap, struct ctdb_node_and_flags, nodemap->num);
+ if (!nodemap->nodes) {
+ DEBUG(0,(__location__ " failed to talloc nodemap\n"));
+ return -1;
+ }
+ for (i=0;i<nodemap->num;i++) {
+ nodemap->nodes[i].vnn = ((uint32_t *)outdata.dptr)[2*i+1];
+ nodemap->nodes[i].flags = ((uint32_t *)outdata.dptr)[2*i+2];
+ }
+
+ return 0;
+}
+
/*
set vnn map on a node
*/
return 0;
}
+ case CTDB_CONTROL_GET_NODEMAP: {
+ uint32_t num_nodes, i, len;
+ struct ctdb_node *node;
+
+ num_nodes = ctdb_get_num_nodes(ctdb);
+ len = 2*num_nodes + 1;
+
+ outdata->dsize = len*sizeof(uint32_t);
+ outdata->dptr = (unsigned char *)talloc_array(outdata, uint32_t, len);
+ if (!outdata->dptr) {
+ DEBUG(0, (__location__ "Failed to allocate node array\n"));
+ exit(1);
+ }
+
+
+ ((uint32_t *)outdata->dptr)[0] = num_nodes;
+ for (i=0; i<num_nodes; i++) {
+ node=ctdb->nodes[i];
+ ((uint32_t *)outdata->dptr)[i*2+1]=node->vnn;
+ ((uint32_t *)outdata->dptr)[i*2+2]=node->flags;
+ }
+
+ return 0;
+ }
+
case CTDB_CONTROL_SETVNNMAP: {
uint32_t *ptr, i;
struct ctdb_vnn_map;
int ctdb_getvnnmap(struct ctdb_context *ctdb, uint32_t destnode, struct ctdb_vnn_map *vnnmap);
int ctdb_setvnnmap(struct ctdb_context *ctdb, uint32_t destnode, struct ctdb_vnn_map *vnnmap);
-struct ctdb_dbid_map;
+
+/* table that contains a list of all dbids on a node
+ */
+struct ctdb_dbid_map {
+ uint32_t num;
+ uint32_t *dbids;
+};
int ctdb_getdbmap(struct ctdb_context *ctdb, uint32_t destnode, struct ctdb_dbid_map *dbmap);
+
+/* table that contains a list of all nodes a ctdb knows about and their
+ status
+ */
+struct ctdb_node_and_flags {
+ uint32_t vnn;
+ uint32_t flags;
+};
+struct ctdb_node_map {
+ uint32_t num;
+ struct ctdb_node_and_flags *nodes;
+};
+int ctdb_getnodemap(struct ctdb_context *ctdb, uint32_t destnode, struct ctdb_node_map *nodemap);
+
int ctdb_getdbpath(struct ctdb_context *ctdb, uint32_t dbid, TALLOC_CTX *mem_ctx, const char **path);
int ctdb_process_exists(struct ctdb_context *ctdb, uint32_t destnode, pid_t pid);
const char *name; /* for debug messages */
void *private_data; /* private to transport */
uint32_t vnn;
+#define NODE_FLAGS_CONNECTED 0x00000001
+ uint32_t flags;
};
/*
double max_lockwait_latency;
};
-/* table that contains a list of all dbids on a node
- */
-struct ctdb_dbid_map {
- uint32_t num;
- uint32_t *dbids;
-};
-
/* table that contains the mapping between a hash value and lmaster
*/
struct ctdb_vnn_map {
CTDB_CONTROL_SETVNNMAP,
CTDB_CONTROL_GET_DEBUG,
CTDB_CONTROL_SET_DEBUG,
- CTDB_CONTROL_GET_DBMAP};
+ CTDB_CONTROL_GET_DBMAP,
+ CTDB_CONTROL_GET_NODEMAP};
enum call_state {CTDB_CALL_WAIT, CTDB_CALL_DONE, CTDB_CALL_ERROR};
printf(" getvnnmap <vnn> display ctdb vnnmap\n");
printf(" setvnnmap <vnn> <generation> <numslots> <lmaster>*\n");
printf(" getdbmap <vnn> lists databases on a node\n");
+ printf(" getnodemap <vnn> lists nodes known to a ctdb daemon\n");
exit(1);
}
return 0;
}
+/*
+ display a list nodes known to a remote ctdb
+ */
+static int control_getnodemap(struct ctdb_context *ctdb, int argc, const char **argv)
+{
+ uint32_t vnn;
+ int i, ret;
+ struct ctdb_node_map *nodemap;
+
+ if (argc < 1) {
+ usage();
+ }
+
+ vnn = strtoul(argv[0], NULL, 0);
+
+ nodemap = talloc_zero(ctdb, struct ctdb_node_map);
+ ret = ctdb_getnodemap(ctdb, vnn, nodemap);
+ if (ret != 0) {
+ printf("Unable to get nodemap from node %u\n", vnn);
+ talloc_free(nodemap);
+ return ret;
+ }
+
+ printf("Number of nodes:%d\n", nodemap->num);
+ for(i=0;i<nodemap->num;i++){
+ printf("vnn:0x%08x %s\n", nodemap->nodes[i].vnn, nodemap->nodes[i].flags&NODE_FLAGS_CONNECTED?"UNAVAILABLE":"CONNECTED");
+ }
+ talloc_free(nodemap);
+ return 0;
+}
+
/*
set remote ctdb vnn map
*/
ret = control_getvnnmap(ctdb, extra_argc-1, extra_argv+1);
} else if (strcmp(control, "getdbmap") == 0) {
ret = control_getdbmap(ctdb, extra_argc-1, extra_argv+1);
+ } else if (strcmp(control, "getnodemap") == 0) {
+ ret = control_getnodemap(ctdb, extra_argc-1, extra_argv+1);
} else if (strcmp(control, "setvnnmap") == 0) {
ret = control_setvnnmap(ctdb, extra_argc-1, extra_argv+1);
} else if (strcmp(control, "ping") == 0) {