|
@@ -481,6 +481,120 @@ static int get_cluster_mcast_addr (
|
|
|
return (err);
|
|
return (err);
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+static unsigned int generate_nodeid_for_duplicate_test(
|
|
|
|
|
+ struct totem_config *totem_config,
|
|
|
|
|
+ char *addr)
|
|
|
|
|
+{
|
|
|
|
|
+ unsigned int nodeid;
|
|
|
|
|
+ struct totem_ip_address totemip;
|
|
|
|
|
+
|
|
|
|
|
+ /* AF_INET hard-coded here because auto-generated nodeids
|
|
|
|
|
+ are only for IPv4 */
|
|
|
|
|
+ if (totemip_parse(&totemip, addr, AF_INET) != 0)
|
|
|
|
|
+ return -1;
|
|
|
|
|
+
|
|
|
|
|
+ memcpy (&nodeid, &totemip.addr, sizeof (unsigned int));
|
|
|
|
|
+
|
|
|
|
|
+#if __BYTE_ORDER == __LITTLE_ENDIAN
|
|
|
|
|
+ nodeid = swab32 (nodeid);
|
|
|
|
|
+#endif
|
|
|
|
|
+
|
|
|
|
|
+ if (totem_config->clear_node_high_bit) {
|
|
|
|
|
+ nodeid &= 0x7FFFFFFF;
|
|
|
|
|
+ }
|
|
|
|
|
+ return nodeid;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+static int check_for_duplicate_nodeids(
|
|
|
|
|
+ struct totem_config *totem_config,
|
|
|
|
|
+ const char **error_string)
|
|
|
|
|
+{
|
|
|
|
|
+ icmap_iter_t iter;
|
|
|
|
|
+ icmap_iter_t subiter;
|
|
|
|
|
+ const char *iter_key;
|
|
|
|
|
+ int res = 0;
|
|
|
|
|
+ int retval = 0;
|
|
|
|
|
+ char tmp_key[ICMAP_KEYNAME_MAXLEN];
|
|
|
|
|
+ char *ring0_addr=NULL;
|
|
|
|
|
+ char *ring0_addr1=NULL;
|
|
|
|
|
+ unsigned int node_pos;
|
|
|
|
|
+ unsigned int node_pos1;
|
|
|
|
|
+ unsigned int nodeid;
|
|
|
|
|
+ unsigned int nodeid1;
|
|
|
|
|
+ int autogenerated;
|
|
|
|
|
+
|
|
|
|
|
+ iter = icmap_iter_init("nodelist.node.");
|
|
|
|
|
+ while ((iter_key = icmap_iter_next(iter, NULL, NULL)) != NULL) {
|
|
|
|
|
+ res = sscanf(iter_key, "nodelist.node.%u.%s", &node_pos, tmp_key);
|
|
|
|
|
+ if (res != 2) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ if (strcmp(tmp_key, "ring0_addr") != 0) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ snprintf(tmp_key, ICMAP_KEYNAME_MAXLEN, "nodelist.node.%u.nodeid", node_pos);
|
|
|
|
|
+ autogenerated = 0;
|
|
|
|
|
+ if (icmap_get_uint32(tmp_key, &nodeid) != CS_OK) {
|
|
|
|
|
+
|
|
|
|
|
+ snprintf(tmp_key, ICMAP_KEYNAME_MAXLEN, "nodelist.node.%u.ring0_addr", node_pos);
|
|
|
|
|
+ if (icmap_get_string(tmp_key, &ring0_addr) != CS_OK) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* Generate nodeid so we can check that auto-generated nodeids don't clash either */
|
|
|
|
|
+ nodeid = generate_nodeid_for_duplicate_test(totem_config, ring0_addr);
|
|
|
|
|
+ if (nodeid == -1) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+ autogenerated = 1;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ node_pos1 = 0;
|
|
|
|
|
+ subiter = icmap_iter_init("nodelist.node.");
|
|
|
|
|
+ while (((iter_key = icmap_iter_next(subiter, NULL, NULL)) != NULL) && (node_pos1 < node_pos)) {
|
|
|
|
|
+ res = sscanf(iter_key, "nodelist.node.%u.%s", &node_pos1, tmp_key);
|
|
|
|
|
+ if ((res != 2) || (node_pos1 >= node_pos)) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ if (strcmp(tmp_key, "ring0_addr") != 0) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ snprintf(tmp_key, ICMAP_KEYNAME_MAXLEN, "nodelist.node.%u.nodeid", node_pos1);
|
|
|
|
|
+ if (icmap_get_uint32(tmp_key, &nodeid1) != CS_OK) {
|
|
|
|
|
+
|
|
|
|
|
+ snprintf(tmp_key, ICMAP_KEYNAME_MAXLEN, "nodelist.node.%u.ring0_addr", node_pos1);
|
|
|
|
|
+ if (icmap_get_string(tmp_key, &ring0_addr1) != CS_OK) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+ nodeid1 = generate_nodeid_for_duplicate_test(totem_config, ring0_addr1);
|
|
|
|
|
+ if (nodeid1 == -1) {
|
|
|
|
|
+ continue;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ if (nodeid == nodeid1) {
|
|
|
|
|
+ retval = -1;
|
|
|
|
|
+ snprintf (error_string_response, sizeof(error_string_response),
|
|
|
|
|
+ "Nodeid %u%s%s%s appears twice in corosync.conf", nodeid,
|
|
|
|
|
+ autogenerated?"(autogenerated from ":"",
|
|
|
|
|
+ autogenerated?ring0_addr:"",
|
|
|
|
|
+ autogenerated?")":"");
|
|
|
|
|
+ log_printf (LOGSYS_LEVEL_ERROR, error_string_response);
|
|
|
|
|
+ *error_string = error_string_response;
|
|
|
|
|
+ break;
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+ icmap_iter_finalize(subiter);
|
|
|
|
|
+ }
|
|
|
|
|
+ icmap_iter_finalize(iter);
|
|
|
|
|
+ return retval;
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+
|
|
|
static int find_local_node_in_nodelist(struct totem_config *totem_config)
|
|
static int find_local_node_in_nodelist(struct totem_config *totem_config)
|
|
|
{
|
|
{
|
|
|
icmap_iter_t iter;
|
|
icmap_iter_t iter;
|
|
@@ -1236,6 +1350,10 @@ int totem_config_validate (
|
|
|
return (-1);
|
|
return (-1);
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+ if (check_for_duplicate_nodeids(totem_config, error_string) == -1) {
|
|
|
|
|
+ return (-1);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
/*
|
|
/*
|
|
|
* RRP values validation
|
|
* RRP values validation
|
|
|
*/
|
|
*/
|