diff options
Diffstat (limited to 'src/backend/utils/misc/guc.c')
-rw-r--r-- | src/backend/utils/misc/guc.c | 45 |
1 files changed, 27 insertions, 18 deletions
diff --git a/src/backend/utils/misc/guc.c b/src/backend/utils/misc/guc.c index 0c593b81b4e..13527fc258f 100644 --- a/src/backend/utils/misc/guc.c +++ b/src/backend/utils/misc/guc.c @@ -3324,10 +3324,12 @@ parse_and_validate_value(struct config_generic *record, * * Return value: * +1: the value is valid and was successfully applied. - * 0: the name or value is invalid (but see below). - * -1: the value was not applied because of context, priority, or changeVal. + * 0: the name or value is invalid, or it's invalid to try to set + * this GUC now; but elevel was less than ERROR (see below). + * -1: no error detected, but the value was not applied, either + * because changeVal is false or there is some overriding setting. * - * If there is an error (non-existing option, invalid value) then an + * If there is an error (non-existing option, invalid value, etc) then an * ereport(ERROR) is thrown *unless* this is called for a source for which * we don't want an ERROR (currently, those are defaults, the config file, * and per-database or per-user settings, as well as callers who specify @@ -3390,8 +3392,11 @@ set_config_option_ext(const char *name, const char *value, /* - * set_config_with_handle: takes an optional 'handle' argument, which can be - * obtained by the caller from get_config_handle(). + * set_config_with_handle: sets option `name' to given value. + * + * This API adds the ability to pass a 'handle' argument, which can be + * obtained by the caller from get_config_handle(). NULL has no effect, + * but a non-null value avoids the need to search the GUC tables. * * This should be used by callers which repeatedly set the same config * option(s), and want to avoid the overhead of a hash lookup each time. @@ -3428,6 +3433,16 @@ set_config_with_handle(const char *name, config_handle *handle, elevel = ERROR; } + /* if handle is specified, no need to look up option */ + if (!handle) + { + record = find_option(name, true, false, elevel); + if (record == NULL) + return 0; + } + else + record = handle; + /* * GUC_ACTION_SAVE changes are acceptable during a parallel operation, * because the current worker will also pop the change. We're probably @@ -3435,25 +3450,19 @@ set_config_with_handle(const char *name, config_handle *handle, * body should observe the change, and peer workers do not share in the * execution of a function call started by this worker. * + * Also allow normal setting if the GUC is marked GUC_ALLOW_IN_PARALLEL. + * * Other changes might need to affect other workers, so forbid them. */ - if (IsInParallelMode() && changeVal && action != GUC_ACTION_SAVE) + if (IsInParallelMode() && changeVal && action != GUC_ACTION_SAVE && + (record->flags & GUC_ALLOW_IN_PARALLEL) == 0) { ereport(elevel, (errcode(ERRCODE_INVALID_TRANSACTION_STATE), - errmsg("cannot set parameters during a parallel operation"))); - return -1; - } - - /* if handle is specified, no need to look up option */ - if (!handle) - { - record = find_option(name, true, false, elevel); - if (record == NULL) - return 0; + errmsg("parameter \"%s\" cannot be set during a parallel operation", + name))); + return 0; } - else - record = handle; /* * Check if the option can be set at this time. See guc.h for the precise |