mirror of
https://git.proxmox.com/git/mirror_corosync
synced 2025-10-04 00:31:15 +00:00
Report crypto errors back to cfg reload
Because crypto changing happens in the 'commit' phase of the reload and we can't get sure that knet will allow the new parameters, the result gets ignored. This can happen in FIPS mode if a non-FIPS cipher is requested. This patch reports the errors back in a cmap key so that the command-line can spot those errors and report them back to the user. It also restores the internal values for crypto so that subsequent attempts to change things have predictable results. Otherwise further attempts can do nothing but not report any errors back. I've also added some error reporting back for the knet ping counters using this mechanism. The alternative to all of this would be to check for FIPS in totemconfig.c and then exclude certain options, but this would be duplicating code that could easily get out of sync. This system could also be a useful mechanism for reporting back other 'impossible' errors. Signed-off-by: Christine Caulfield <ccaulfie@redhat.com> Reviewed-by: Jan Friesse <jfriesse@redhat.com>
This commit is contained in:
parent
8d46eb0127
commit
ce03c68394
@ -722,6 +722,9 @@ static void message_handler_req_exec_cfg_reload_config (
|
||||
|
||||
log_printf(LOGSYS_LEVEL_NOTICE, "Config reload requested by node " CS_PRI_NODE_ID, nodeid);
|
||||
|
||||
// Clear this out in case it all goes well
|
||||
icmap_delete("config.reload_error_message");
|
||||
|
||||
icmap_set_uint8("config.totemconfig_reload_in_progress", 1);
|
||||
|
||||
/* Make sure there is no rubbish in this that might be checked, even on error */
|
||||
|
@ -2439,7 +2439,13 @@ int totemconfig_commit_new_params(
|
||||
totempg_reconfigure();
|
||||
|
||||
free(new_interfaces);
|
||||
return res; /* On a reload this is ignored */
|
||||
|
||||
/*
|
||||
* On a reload this return is ignored because it's too late to do anything about it,
|
||||
* but errors are reported back via cmap.
|
||||
*/
|
||||
return res;
|
||||
|
||||
}
|
||||
|
||||
static void add_totem_config_notification(struct totem_config *totem_config)
|
||||
|
@ -93,6 +93,8 @@ static int setup_nozzle(void *knet_context);
|
||||
struct totemknet_instance {
|
||||
struct crypto_instance *crypto_inst;
|
||||
|
||||
struct knet_handle_crypto_cfg last_good_crypto_cfg;
|
||||
|
||||
qb_loop_t *poll_handle;
|
||||
|
||||
knet_handle_t knet_handle;
|
||||
@ -995,6 +997,7 @@ static void totemknet_refresh_config(
|
||||
}
|
||||
|
||||
for (i=0; i<num_nodes; i++) {
|
||||
int linkerr = 0;
|
||||
for (link_no = 0; link_no < INTERFACE_MAX; link_no++) {
|
||||
if (host_ids[i] == instance->our_nodeid || !instance->totem_config->interfaces[link_no].configured) {
|
||||
continue;
|
||||
@ -1006,19 +1009,25 @@ static void totemknet_refresh_config(
|
||||
instance->totem_config->interfaces[link_no].knet_ping_precision);
|
||||
if (err) {
|
||||
KNET_LOGSYS_PERROR(errno, LOGSYS_LEVEL_ERROR, "knet_link_set_ping_timers for node " CS_PRI_NODE_ID " link %d failed", host_ids[i], link_no);
|
||||
linkerr = err;
|
||||
}
|
||||
err = knet_link_set_pong_count(instance->knet_handle, host_ids[i], link_no,
|
||||
instance->totem_config->interfaces[link_no].knet_pong_count);
|
||||
if (err) {
|
||||
KNET_LOGSYS_PERROR(errno, LOGSYS_LEVEL_ERROR, "knet_link_set_pong_count for node " CS_PRI_NODE_ID " link %d failed",host_ids[i], link_no);
|
||||
linkerr = err;
|
||||
}
|
||||
err = knet_link_set_priority(instance->knet_handle, host_ids[i], link_no,
|
||||
instance->totem_config->interfaces[link_no].knet_link_priority);
|
||||
if (err) {
|
||||
KNET_LOGSYS_PERROR(errno, LOGSYS_LEVEL_ERROR, "knet_link_set_priority for node " CS_PRI_NODE_ID " link %d failed", host_ids[i], link_no);
|
||||
linkerr = err;
|
||||
}
|
||||
|
||||
}
|
||||
if (linkerr) {
|
||||
icmap_set_string("config.reload_error_message", "Failed to set knet ping timers(2)");
|
||||
}
|
||||
}
|
||||
|
||||
/* Log levels get reconfigured from logconfig.c as that happens last in the reload */
|
||||
@ -1086,6 +1095,10 @@ static int totemknet_set_knet_crypto(struct totemknet_instance *instance)
|
||||
|
||||
/* use_config will be called later when all nodes are synced */
|
||||
res = knet_handle_crypto_set_config(instance->knet_handle, &crypto_cfg, instance->totem_config->crypto_index);
|
||||
if (res == 0) {
|
||||
/* Keep a copy in case it fails in future */
|
||||
memcpy(&instance->last_good_crypto_cfg, &crypto_cfg, sizeof(crypto_cfg));
|
||||
}
|
||||
if (res == -1) {
|
||||
knet_log_printf(LOGSYS_LEVEL_ERROR, "knet_handle_crypto_set_config (index %d) failed: %s", instance->totem_config->crypto_index, strerror(errno));
|
||||
goto exit_error;
|
||||
@ -1112,8 +1125,24 @@ static int totemknet_set_knet_crypto(struct totemknet_instance *instance)
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
exit_error:
|
||||
#ifdef HAVE_KNET_CRYPTO_RECONF
|
||||
if (res) {
|
||||
icmap_set_string("config.reload_error_message", "Failed to set crypto parameters");
|
||||
|
||||
/* Restore the old values in cmap & totem_config */
|
||||
icmap_set_string("totem.crypto_cipher", instance->last_good_crypto_cfg.crypto_cipher_type);
|
||||
icmap_set_string("totem.crypto_hash", instance->last_good_crypto_cfg.crypto_hash_type);
|
||||
icmap_set_string("totem.crypto_model", instance->last_good_crypto_cfg.crypto_model);
|
||||
|
||||
memcpy(instance->totem_config->crypto_hash_type, instance->last_good_crypto_cfg.crypto_hash_type,
|
||||
sizeof(instance->last_good_crypto_cfg.crypto_hash_type));
|
||||
memcpy(instance->totem_config->crypto_cipher_type, instance->last_good_crypto_cfg.crypto_cipher_type,
|
||||
sizeof(instance->last_good_crypto_cfg.crypto_cipher_type));
|
||||
memcpy(instance->totem_config->crypto_model, instance->last_good_crypto_cfg.crypto_model,
|
||||
sizeof(instance->last_good_crypto_cfg.crypto_model));
|
||||
}
|
||||
#endif
|
||||
return res;
|
||||
}
|
||||
|
||||
@ -1656,6 +1685,9 @@ int totemknet_member_add (
|
||||
log_flush_messages(instance);
|
||||
errno = saved_errno;
|
||||
KNET_LOGSYS_PERROR(errno, LOGSYS_LEVEL_ERROR, "knet_link_set_ping_timers for nodeid " CS_PRI_NODE_ID ", link %d failed", member->nodeid, link_no);
|
||||
|
||||
icmap_set_string("config.reload_error_message", "Failed to set knet ping timers");
|
||||
|
||||
return -1;
|
||||
}
|
||||
err = knet_link_set_pong_count(instance->knet_handle, member->nodeid, link_no,
|
||||
@ -1666,6 +1698,7 @@ int totemknet_member_add (
|
||||
log_flush_messages(instance);
|
||||
errno = saved_errno;
|
||||
KNET_LOGSYS_PERROR(errno, LOGSYS_LEVEL_ERROR, "knet_link_set_pong_count for nodeid " CS_PRI_NODE_ID ", link %d failed", member->nodeid, link_no);
|
||||
icmap_set_string("config.reload_error_message", "Failed to set knet pong count");
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
@ -1774,11 +1807,14 @@ int totemknet_reconfigure (
|
||||
/* Flip crypto_index */
|
||||
totem_config->crypto_index = 3-totem_config->crypto_index;
|
||||
res = totemknet_set_knet_crypto(instance);
|
||||
|
||||
knet_log_printf(LOG_INFO, "kronosnet crypto reconfigured on index %d: %s/%s/%s", totem_config->crypto_index,
|
||||
totem_config->crypto_model,
|
||||
totem_config->crypto_cipher_type,
|
||||
totem_config->crypto_hash_type);
|
||||
if (res == 0) {
|
||||
knet_log_printf(LOG_INFO, "kronosnet crypto reconfigured on index %d: %s/%s/%s", totem_config->crypto_index,
|
||||
totem_config->crypto_model,
|
||||
totem_config->crypto_cipher_type,
|
||||
totem_config->crypto_hash_type);
|
||||
} else {
|
||||
icmap_set_string("config.reload_error_message", "Failed to set knet crypto");
|
||||
}
|
||||
}
|
||||
return (res);
|
||||
}
|
||||
|
@ -332,6 +332,33 @@ nodestatusget_do (enum user_action action, int brief)
|
||||
return rc;
|
||||
}
|
||||
|
||||
|
||||
static int check_for_reload_errors(void)
|
||||
{
|
||||
cmap_handle_t cmap_handle;
|
||||
cs_error_t result;
|
||||
char *str;
|
||||
int res;
|
||||
|
||||
result = cmap_initialize (&cmap_handle);
|
||||
if (result != CS_OK) {
|
||||
fprintf (stderr, "Could not initialize corosync cmap API error %d\n", result);
|
||||
exit (EXIT_FAILURE);
|
||||
}
|
||||
|
||||
result = cmap_get_string(cmap_handle, "config.reload_error_message", &str);
|
||||
if (result == CS_OK) {
|
||||
printf("ERROR from reload: %s - see syslog for more information\n", str);
|
||||
free(str);
|
||||
res = 1;
|
||||
}
|
||||
else {
|
||||
res = 0;
|
||||
}
|
||||
cmap_finalize(cmap_handle);
|
||||
return res;
|
||||
}
|
||||
|
||||
static int reload_config_do (void)
|
||||
{
|
||||
cs_error_t result;
|
||||
@ -358,6 +385,10 @@ static int reload_config_do (void)
|
||||
|
||||
(void)corosync_cfg_finalize (handle);
|
||||
|
||||
if ((rc = check_for_reload_errors())) {
|
||||
fprintf(stderr, "Errors in appying config, corosync.conf might not match the running system\n");
|
||||
}
|
||||
|
||||
return (rc);
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user