Просмотр исходного кода

corosync-quorumtool: add sort options

Adds a -o<a|i|n> option to corosync-votequorum so that the nodes list
can be sorted by Address, node Id or Name. The default remains IP
address.

Signed-Off-By: Christine Caulfield <ccaulfie@redhat.com>
Reviewed-by: Jan Friesse <jfriesse@redhat.com>
Christine Caulfield 11 лет назад
Родитель
Сommit
f53580c2c1
2 измененных файлов с 98 добавлено и 30 удалено
  1. 7 2
      man/corosync-quorumtool.8
  2. 91 28
      tools/corosync-quorumtool.c

+ 7 - 2
man/corosync-quorumtool.8

@@ -1,5 +1,5 @@
 .\"/*
 .\"/*
-.\" * Copyright (C) 2010,2012 Red Hat, Inc.
+.\" * Copyright (C) 2010,2014 Red Hat, Inc.
 .\" *
 .\" *
 .\" * All rights reserved.
 .\" * All rights reserved.
 .\" *
 .\" *
@@ -35,7 +35,7 @@
 .SH NAME
 .SH NAME
 corosync-quorumtool \- Set and display quorum settings.
 corosync-quorumtool \- Set and display quorum settings.
 .SH SYNOPSIS
 .SH SYNOPSIS
-.B "corosync-quorumtool [\-s] [\-m] [\-l] [\-p] [\-v votes] [\-n nodeid] [\-e expected] [\-h] [\-i] [\-V]"
+.B "corosync-quorumtool [\-s] [\-m] [\-l] [\-p] [\-v votes] [\-n nodeid] [\-e expected] [\-h] [\-i] [\-o <a|n|i>] [\-V]"
 .SH DESCRIPTION
 .SH DESCRIPTION
 Display the current state of quorum in the cluster and set vote quorum options.
 Display the current state of quorum in the cluster and set vote quorum options.
 .SH OPTIONS
 .SH OPTIONS
@@ -67,6 +67,11 @@ show node IP addresses instead of the resolved name
 .B -p
 .B -p
 when used with -s or -l, generates machine parsable output
 when used with -s or -l, generates machine parsable output
 .TP
 .TP
+.B -o <a|n|i>
+Orders the output of the nodes list. By default or with -oa nodes are listed in IP address
+order: as they come from corosync. -on will order the nodes based on their name,
+and -oi will order them based on their node ID.
+.TP
 .B  -h (if no other argument)
 .B  -h (if no other argument)
 show this help text
 show this help text
 .TP
 .TP

+ 91 - 28
tools/corosync-quorumtool.c

@@ -1,5 +1,5 @@
 /*
 /*
- * Copyright (c) 2009-2012 Red Hat, Inc.
+ * Copyright (c) 2009-2014 Red Hat, Inc.
  *
  *
  * All rights reserved.
  * All rights reserved.
  *
  *
@@ -69,6 +69,12 @@ typedef enum {
 	CMD_UNREGISTER_QDEVICE
 	CMD_UNREGISTER_QDEVICE
 } command_t;
 } command_t;
 
 
+typedef enum {
+	SORT_ADDR,
+	SORT_NODEID,
+	SORT_NODENAME
+} sorttype_t;
+
 /*
 /*
  * global vars
  * global vars
  */
  */
@@ -97,10 +103,18 @@ static quorum_callbacks_t q_callbacks = {
 /*
 /*
  * quorum call back vars
  * quorum call back vars
  */
  */
+
+/* Containing struct to keep votequorum & normal quorum bits together */
+typedef struct {
+      struct votequorum_info *vq_info; /* Might be NULL if votequorum not present */
+      char *name;  /* Might be IP address or NULL */
+      int node_id; /* Always present */
+} view_list_entry_t;
+
+static view_list_entry_t *g_view_list;
 static uint32_t g_quorate;
 static uint32_t g_quorate;
 static uint64_t g_ring_id;
 static uint64_t g_ring_id;
 static uint32_t g_view_list_entries;
 static uint32_t g_view_list_entries;
-static uint32_t *g_view_list = NULL;
 static uint32_t g_called;
 static uint32_t g_called;
 
 
 /*
 /*
@@ -142,6 +156,7 @@ static void show_usage(const char *name)
 	printf("  -e <expected>  change expected votes for the cluster (*)\n");
 	printf("  -e <expected>  change expected votes for the cluster (*)\n");
 	printf("  -H             show nodeids in hexadecimal rather than decimal\n");
 	printf("  -H             show nodeids in hexadecimal rather than decimal\n");
 	printf("  -i             show node IP addresses instead of the resolved name\n");
 	printf("  -i             show node IP addresses instead of the resolved name\n");
+	printf("  -o <a|i>       order by [a] IP address (default), [i] nodeid,\n");
 	printf("  -f             forcefully unregister a quorum device *DANGEROUS* (*)\n");
 	printf("  -f             forcefully unregister a quorum device *DANGEROUS* (*)\n");
 	printf("  -h             show this help text\n");
 	printf("  -h             show this help text\n");
 	printf("  -V             show version and exit\n");
 	printf("  -V             show version and exit\n");
@@ -335,6 +350,8 @@ static void quorum_notification_fn(
 	uint32_t view_list_entries,
 	uint32_t view_list_entries,
 	uint32_t *view_list)
 	uint32_t *view_list)
 {
 {
+        int i;
+
 	g_called = 1;
 	g_called = 1;
 	g_quorate = quorate;
 	g_quorate = quorate;
 	g_ring_id = ring_id;
 	g_ring_id = ring_id;
@@ -342,9 +359,13 @@ static void quorum_notification_fn(
 	if (g_view_list) {
 	if (g_view_list) {
 		free(g_view_list);
 		free(g_view_list);
 	}
 	}
-	g_view_list = malloc(sizeof(uint32_t) * view_list_entries);
+	g_view_list = malloc(sizeof(view_list_entry_t) * view_list_entries);
 	if (g_view_list) {
 	if (g_view_list) {
-		memcpy(g_view_list, view_list,sizeof(uint32_t) * view_list_entries);
+	        for (i=0; i< view_list_entries; i++) {
+		        g_view_list[i].node_id = view_list[i];
+			g_view_list[i].name = NULL;
+			g_view_list[i].vq_info = NULL;
+		}
 	}
 	}
 }
 }
 
 
@@ -369,10 +390,11 @@ static void print_uint32_padded(uint32_t value)
 	print_string_padded(buf);
 	print_string_padded(buf);
 }
 }
 
 
+/* for qsort */
 static int compare_nodeids(const void *one, const void *two)
 static int compare_nodeids(const void *one, const void *two)
 {
 {
-      const struct votequorum_info *info1 = one;
-      const struct votequorum_info *info2 = two;
+      const view_list_entry_t *info1 = one;
+      const view_list_entry_t *info2 = two;
 
 
       if (info1->node_id == info2->node_id) {
       if (info1->node_id == info2->node_id) {
 	  return 0;
 	  return 0;
@@ -383,25 +405,40 @@ static int compare_nodeids(const void *one, const void *two)
       return -1;
       return -1;
 }
 }
 
 
-static void display_nodes_data(nodeid_format_t nodeid_format, name_format_t name_format)
+static int compare_nodenames(const void *one, const void *two)
+{
+      const view_list_entry_t *info1 = one;
+      const view_list_entry_t *info2 = two;
+
+      return strcmp(info1->name, info2->name);
+}
+
+static void display_nodes_data(nodeid_format_t nodeid_format, name_format_t name_format, sorttype_t sort_type)
 {
 {
 	int i, display_qdevice = 0;
 	int i, display_qdevice = 0;
 	struct votequorum_info info[g_view_list_entries];
 	struct votequorum_info info[g_view_list_entries];
-
 	/*
 	/*
 	 * cache node info because we need to parse them twice
 	 * cache node info because we need to parse them twice
 	 */
 	 */
 	if (v_handle) {
 	if (v_handle) {
 		for (i=0; i < g_view_list_entries; i++) {
 		for (i=0; i < g_view_list_entries; i++) {
-			if (votequorum_getinfo(v_handle, g_view_list[i], &info[i]) != CS_OK) {
-				printf("Unable to get node %u info\n", g_view_list[i]);
+			if (votequorum_getinfo(v_handle, g_view_list[i].node_id, &info[i]) != CS_OK) {
+				printf("Unable to get node %u info\n", g_view_list[i].node_id);
 			}
 			}
+			g_view_list[i].vq_info = &info[i];
 			if (info[i].flags & VOTEQUORUM_INFO_QDEVICE_REGISTERED) {
 			if (info[i].flags & VOTEQUORUM_INFO_QDEVICE_REGISTERED) {
 				display_qdevice = 1;
 				display_qdevice = 1;
 			}
 			}
 		}
 		}
 	}
 	}
 
 
+	/* 
+	 * Get node names
+	 */
+	for (i=0; i < g_view_list_entries; i++) {
+	        g_view_list[i].name = strdup(node_name(g_view_list[i].node_id, name_format));
+	}
+
 	printf("\nMembership information\n");
 	printf("\nMembership information\n");
 	printf("----------------------\n");
 	printf("----------------------\n");
 
 
@@ -414,12 +451,18 @@ static void display_nodes_data(nodeid_format_t nodeid_format, name_format_t name
 	}
 	}
 	printf("Name\n");
 	printf("Name\n");
 
 
-	qsort(info, g_view_list_entries, sizeof(struct votequorum_info), compare_nodeids);
+	/* corosync sends them already sorted by address */
+	if (sort_type == SORT_NODEID) {
+		qsort(g_view_list, g_view_list_entries, sizeof(view_list_entry_t), compare_nodeids);
+	}
+	if (sort_type == SORT_NODENAME) {
+		qsort(g_view_list, g_view_list_entries, sizeof(view_list_entry_t), compare_nodenames);
+	}
 	for (i=0; i < g_view_list_entries; i++) {
 	for (i=0; i < g_view_list_entries; i++) {
 		if (nodeid_format == NODEID_FORMAT_DECIMAL) {
 		if (nodeid_format == NODEID_FORMAT_DECIMAL) {
-			print_uint32_padded(info[i].node_id);
+			print_uint32_padded(g_view_list[i].node_id);
 		} else {
 		} else {
-			printf("0x%08x ", info[i].node_id);
+			printf("0x%08x ", g_view_list[i].node_id);
 		}
 		}
 		if (v_handle) {
 		if (v_handle) {
 			int votes = -1;
 			int votes = -1;
@@ -442,14 +485,17 @@ static void display_nodes_data(nodeid_format_t nodeid_format, name_format_t name
 				}
 				}
 			}
 			}
 		}
 		}
-		printf("%s", node_name(info[i].node_id, name_format));
-		if (info[i].node_id == our_nodeid) {
+		printf("%s", g_view_list[i].name);
+		if (g_view_list[i].node_id == our_nodeid) {
 			printf(" (local)");
 			printf(" (local)");
 		}
 		}
 		printf("\n");
 		printf("\n");
 	}
 	}
 
 
 	if (g_view_list_entries) {
 	if (g_view_list_entries) {
+	        for (i=0; i < g_view_list_entries; i++) {
+		        free(g_view_list[i].name);
+		}
 		free(g_view_list);
 		free(g_view_list);
 		g_view_list = NULL;
 		g_view_list = NULL;
 	}
 	}
@@ -467,7 +513,7 @@ static void display_nodes_data(nodeid_format_t nodeid_format, name_format_t name
 }
 }
 
 
 static int display_quorum_data(int is_quorate,
 static int display_quorum_data(int is_quorate,
-			       nodeid_format_t nodeid_format, name_format_t name_format,
+			       nodeid_format_t nodeid_format, name_format_t name_format, sorttype_t sort_type,
 			       int loop)
 			       int loop)
 {
 {
 	struct votequorum_info info;
 	struct votequorum_info info;
@@ -520,7 +566,7 @@ static int display_quorum_data(int is_quorate,
 		fprintf(stderr, "Unable to get node info: %s\n", cs_strerror(err));
 		fprintf(stderr, "Unable to get node info: %s\n", cs_strerror(err));
 	}
 	}
 
 
-	display_nodes_data(nodeid_format, name_format);
+	display_nodes_data(nodeid_format, name_format, sort_type);
 
 
 	return err;
 	return err;
 }
 }
@@ -530,7 +576,7 @@ static int display_quorum_data(int is_quorate,
  *         0 if not quorate
  *         0 if not quorate
  *        -1 on error
  *        -1 on error
  */
  */
-static int show_status(nodeid_format_t nodeid_format, name_format_t name_format)
+static int show_status(nodeid_format_t nodeid_format, name_format_t name_format, sorttype_t sort_type)
 {
 {
 	int is_quorate;
 	int is_quorate;
 	int err;
 	int err;
@@ -564,7 +610,7 @@ quorum_err:
 		return -1;
 		return -1;
 	}
 	}
 
 
-	err = display_quorum_data(is_quorate, nodeid_format, name_format, 0);
+	err = display_quorum_data(is_quorate, nodeid_format, name_format, sort_type, 0);
 	if (err != CS_OK) {
 	if (err != CS_OK) {
 		return -1;
 		return -1;
 	}
 	}
@@ -572,13 +618,13 @@ quorum_err:
 	return is_quorate;
 	return is_quorate;
 }
 }
 
 
-static int monitor_status(nodeid_format_t nodeid_format, name_format_t name_format) {
+static int monitor_status(nodeid_format_t nodeid_format, name_format_t name_format, sorttype_t sort_type) {
 	int err;
 	int err;
 	int loop = 0;
 	int loop = 0;
 
 
 	if (q_type == QUORUM_FREE) {
 	if (q_type == QUORUM_FREE) {
 		printf("\nQuorum is not configured - cannot monitor\n");
 		printf("\nQuorum is not configured - cannot monitor\n");
-		return show_status(nodeid_format, name_format);
+		return show_status(nodeid_format, name_format, sort_type);
 	}
 	}
 
 
 	err=quorum_trackstart(q_handle, CS_TRACK_CHANGES);
 	err=quorum_trackstart(q_handle, CS_TRACK_CHANGES);
@@ -593,7 +639,7 @@ static int monitor_status(nodeid_format_t nodeid_format, name_format_t name_form
 			fprintf(stderr, "Unable to dispatch quorum status: %s\n", cs_strerror(err));
 			fprintf(stderr, "Unable to dispatch quorum status: %s\n", cs_strerror(err));
 			goto quorum_err;
 			goto quorum_err;
 		}
 		}
-		err = display_quorum_data(g_quorate, nodeid_format, name_format, loop);
+		err = display_quorum_data(g_quorate, nodeid_format, name_format, sort_type, loop);
 		printf("\n");
 		printf("\n");
 		loop = 1;
 		loop = 1;
 		if (err != CS_OK) {
 		if (err != CS_OK) {
@@ -606,7 +652,7 @@ quorum_err:
 	return -1;
 	return -1;
 }
 }
 
 
-static int show_nodes(nodeid_format_t nodeid_format, name_format_t name_format)
+static int show_nodes(nodeid_format_t nodeid_format, name_format_t name_format, sorttype_t sort_type)
 {
 {
 	int err;
 	int err;
 	int result = EXIT_FAILURE;
 	int result = EXIT_FAILURE;
@@ -626,7 +672,7 @@ static int show_nodes(nodeid_format_t nodeid_format, name_format_t name_format)
 		}
 		}
 	}
 	}
 
 
-	display_nodes_data(nodeid_format, name_format);
+	display_nodes_data(nodeid_format, name_format, sort_type);
 
 
 	result = EXIT_SUCCESS;
 	result = EXIT_SUCCESS;
 err_exit:
 err_exit:
@@ -721,7 +767,7 @@ static void close_all(void) {
 }
 }
 
 
 int main (int argc, char *argv[]) {
 int main (int argc, char *argv[]) {
-	const char *options = "VHslpmfe:v:hin:";
+	const char *options = "VHslpmfe:v:hin:o:";
 	char *endptr;
 	char *endptr;
 	int opt;
 	int opt;
 	int votes = 0;
 	int votes = 0;
@@ -731,6 +777,8 @@ int main (int argc, char *argv[]) {
 	nodeid_format_t nodeid_format = NODEID_FORMAT_DECIMAL;
 	nodeid_format_t nodeid_format = NODEID_FORMAT_DECIMAL;
 	name_format_t address_format = ADDRESS_FORMAT_NAME;
 	name_format_t address_format = ADDRESS_FORMAT_NAME;
 	command_t command_opt = CMD_SHOWSTATUS;
 	command_t command_opt = CMD_SHOWSTATUS;
+	sorttype_t sort_opt = SORT_ADDR;
+	char sortchar;
 	long int l;
 	long int l;
 
 
 	if (init_all()) {
 	if (init_all()) {
@@ -803,6 +851,21 @@ int main (int argc, char *argv[]) {
 				exit(2);
 				exit(2);
 			}
 			}
 			break;
 			break;
+		case 'o':
+			sortchar = optarg[0];
+			switch (sortchar) {
+			        case 'a': sort_opt = SORT_ADDR;
+					break;
+			        case 'i': sort_opt = SORT_NODEID;
+					break;
+			        case 'n': sort_opt = SORT_NODENAME;
+					break;
+			        default:
+					fprintf(stderr, "Invalid ordering option. valid orders are a(address), i(node ID) or n(name)\n");
+					exit(2);
+					break;
+			}
+			break;
 		case 'V':
 		case 'V':
 			printf("corosync-quorumtool version: %s\n", VERSION);
 			printf("corosync-quorumtool version: %s\n", VERSION);
 			exit(0);
 			exit(0);
@@ -821,10 +884,10 @@ int main (int argc, char *argv[]) {
 		ret = -1;
 		ret = -1;
 		break;
 		break;
 	case CMD_SHOWNODES:
 	case CMD_SHOWNODES:
-		ret = show_nodes(nodeid_format, address_format);
+		ret = show_nodes(nodeid_format, address_format, sort_opt);
 		break;
 		break;
 	case CMD_SHOWSTATUS:
 	case CMD_SHOWSTATUS:
-		ret = show_status(nodeid_format, address_format);
+		ret = show_status(nodeid_format, address_format, sort_opt);
 		break;
 		break;
 	case CMD_SETVOTES:
 	case CMD_SETVOTES:
 		if (!nodeid_set) {
 		if (!nodeid_set) {
@@ -836,7 +899,7 @@ int main (int argc, char *argv[]) {
 		ret = set_expected(votes);
 		ret = set_expected(votes);
 		break;
 		break;
 	case CMD_MONITOR:
 	case CMD_MONITOR:
-		ret = monitor_status(nodeid_format, address_format);
+		ret = monitor_status(nodeid_format, address_format, sort_opt);
 		break;
 		break;
 	case CMD_UNREGISTER_QDEVICE:
 	case CMD_UNREGISTER_QDEVICE:
 		ret = unregister_qdevice();
 		ret = unregister_qdevice();