diff --git a/doc/src/sgml/runtime.sgml b/doc/src/sgml/runtime.sgml index 1f28e21559f283dfa5e8c36188276f55ef5f488f..d5598cd0b967674bf91a6bc1708ae41a2b2e2c68 100644 --- a/doc/src/sgml/runtime.sgml +++ b/doc/src/sgml/runtime.sgml @@ -1,5 +1,5 @@ <!-- -$Header: /cvsroot/pgsql/doc/src/sgml/runtime.sgml,v 1.195 2003/07/23 20:30:35 momjian Exp $ +$Header: /cvsroot/pgsql/doc/src/sgml/runtime.sgml,v 1.196 2003/07/27 04:35:53 momjian Exp $ --> <Chapter Id="runtime"> @@ -571,14 +571,45 @@ SET ENABLE_SEQSCAN TO OFF; <row> <entry><literal>name</literal></entry> <entry><type>text</type></entry> - <entry>The name of the run-time configuration parameter</entry> + <entry>run-time configuration parameter name</entry> </row> <row> <entry><literal>setting</literal></entry> <entry><type>text</type></entry> - <entry>The current value of the run-time configuration parameter</entry> + <entry>current value of the parameter</entry> </row> + + <row> + <entry><literal>context</literal></entry> + <entry><type>text</type></entry> + <entry>context required to set the parameter's value</entry> + </row> + + <row> + <entry><literal>vartype</literal></entry> + <entry><type>text</type></entry> + <entry>parameter type</entry> + </row> + + <row> + <entry><literal>source</literal></entry> + <entry><type>text</type></entry> + <entry>source of the current parameter value</entry> + </row> + + <row> + <entry><literal>min_val</literal></entry> + <entry><type>text</type></entry> + <entry>minimum allowed value of the parameter</entry> + </row> + + <row> + <entry><literal>max_val</literal></entry> + <entry><type>text</type></entry> + <entry>maximum allowed value of the parameter</entry> + </row> + </tbody> </tgroup> </table> diff --git a/src/backend/utils/misc/guc.c b/src/backend/utils/misc/guc.c index de1fd50d20379a081b01229e5dbbb21571d990c9..ef6053f3286ec4ee204f79576f4a9e6925300d57 100644 --- a/src/backend/utils/misc/guc.c +++ b/src/backend/utils/misc/guc.c @@ -10,7 +10,7 @@ * Written by Peter Eisentraut <peter_e@gmx.net>. * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/utils/misc/guc.c,v 1.139 2003/07/25 20:17:56 tgl Exp $ + * $Header: /cvsroot/pgsql/src/backend/utils/misc/guc.c,v 1.140 2003/07/27 04:35:53 momjian Exp $ * *-------------------------------------------------------------------- */ @@ -155,6 +155,47 @@ static char *timezone_string; static char *XactIsoLevel_string; +/* + * Used for pg_settings. Keep in sync with config_type enum above + */ +static char *config_type_name[] = +{ + "bool", + "integer", + "real", + "string" +}; + +/* + * Used for pg_settings. Keep in sync with GucContext enum in guc.h + */ +static char *GucContextName[] = +{ + "internal", + "postmaster", + "sighup", + "backend", + "super-user", + "user" +}; + +/* + * Used for pg_settings. Keep in sync with GucSource enum in guc.h + */ +static char *GucSourceName[] = +{ + "default", + "environment variable", + "configuration file", + "command line", + "database", + "user", + "client", + "override", + "session" +}; + + /* Macros for freeing malloc'd pointers only if appropriate to do so */ /* Some of these tests are probably redundant, but be safe ... */ #define SET_STRING_VARIABLE(rec, newval) \ @@ -3323,23 +3364,102 @@ GetConfigOptionByName(const char *name, const char **varname) * Return GUC variable value by variable number; optionally return canonical * form of name. Return value is palloc'd. */ -char * -GetConfigOptionByNum(int varnum, const char **varname, bool *noshow) +void +GetConfigOptionByNum(int varnum, const char **values, bool *noshow) { - struct config_generic *conf; + char buffer[256]; + struct config_generic *conf; /* check requested variable number valid */ Assert((varnum >= 0) && (varnum < num_guc_variables)); conf = guc_variables[varnum]; - if (varname) - *varname = conf->name; - if (noshow) *noshow = (conf->flags & GUC_NO_SHOW_ALL) ? true : false; - return _ShowOption(conf); + /* first get the generic attributes */ + + /* name */ + values[0] = conf->name; + + /* setting : use _ShowOption in order to avoid duplicating the logic */ + values[1] = _ShowOption(conf); + + /* context */ + values[2] = GucContextName[conf->context]; + + /* vartype */ + values[3] = config_type_name[conf->vartype]; + + /* source */ + values[4] = GucSourceName[conf->source]; + + /* now get the type specifc attributes */ + switch (conf->vartype) + { + case PGC_BOOL: + { + /* min_val */ + values[5] = NULL; + + /* max_val */ + values[6] = NULL; + } + break; + + case PGC_INT: + { + struct config_int *lconf = (struct config_int *) conf; + + /* min_val */ + snprintf(buffer, sizeof(buffer), "%d", lconf->min); + values[5] = pstrdup(buffer); + + /* max_val */ + snprintf(buffer, sizeof(buffer), "%d", lconf->max); + values[6] = pstrdup(buffer); + } + break; + + case PGC_REAL: + { + struct config_real *lconf = (struct config_real *) conf; + + /* min_val */ + snprintf(buffer, sizeof(buffer), "%g", lconf->min); + values[5] = pstrdup(buffer); + + /* max_val */ + snprintf(buffer, sizeof(buffer), "%g", lconf->max); + values[6] = pstrdup(buffer); + } + break; + + case PGC_STRING: + { + /* min_val */ + values[5] = NULL; + + /* max_val */ + values[6] = NULL; + } + break; + + default: + { + /* + * should never get here, but in case we do, set 'em to NULL + */ + + /* min_val */ + values[5] = NULL; + + /* max_val */ + values[6] = NULL; + } + break; + } } /* @@ -3379,6 +3499,8 @@ show_config_by_name(PG_FUNCTION_ARGS) * show_all_settings - equiv to SHOW ALL command but implemented as * a Table Function. */ +#define NUM_PG_SETTINGS_ATTS 7 + Datum show_all_settings(PG_FUNCTION_ARGS) { @@ -3402,12 +3524,25 @@ show_all_settings(PG_FUNCTION_ARGS) */ oldcontext = MemoryContextSwitchTo(funcctx->multi_call_memory_ctx); - /* need a tuple descriptor representing two TEXT columns */ - tupdesc = CreateTemplateTupleDesc(2, false); + /* + * need a tuple descriptor representing NUM_PG_SETTINGS_ATTS columns + * of the appropriate types + */ + tupdesc = CreateTemplateTupleDesc(NUM_PG_SETTINGS_ATTS, false); TupleDescInitEntry(tupdesc, (AttrNumber) 1, "name", TEXTOID, -1, 0, false); TupleDescInitEntry(tupdesc, (AttrNumber) 2, "setting", TEXTOID, -1, 0, false); + TupleDescInitEntry(tupdesc, (AttrNumber) 3, "context", + TEXTOID, -1, 0, false); + TupleDescInitEntry(tupdesc, (AttrNumber) 4, "vartype", + TEXTOID, -1, 0, false); + TupleDescInitEntry(tupdesc, (AttrNumber) 5, "source", + TEXTOID, -1, 0, false); + TupleDescInitEntry(tupdesc, (AttrNumber) 6, "min_val", + TEXTOID, -1, 0, false); + TupleDescInitEntry(tupdesc, (AttrNumber) 7, "max_val", + TEXTOID, -1, 0, false); /* allocate a slot for a tuple with this tupdesc */ slot = TupleDescGetSlot(tupdesc); @@ -3438,9 +3573,7 @@ show_all_settings(PG_FUNCTION_ARGS) if (call_cntr < max_calls) /* do when there is more left to send */ { - char *values[2]; - char *varname; - char *varval; + char *values[NUM_PG_SETTINGS_ATTS]; bool noshow; HeapTuple tuple; Datum result; @@ -3450,15 +3583,9 @@ show_all_settings(PG_FUNCTION_ARGS) */ do { - varval = GetConfigOptionByNum(call_cntr, - (const char **) &varname, - &noshow); + GetConfigOptionByNum(call_cntr, (const char **) values, &noshow); if (noshow) { - /* varval is a palloc'd copy, so free it */ - if (varval != NULL) - pfree(varval); - /* bump the counter and get the next config setting */ call_cntr = ++funcctx->call_cntr; @@ -3468,24 +3595,12 @@ show_all_settings(PG_FUNCTION_ARGS) } } while (noshow); - /* - * Prepare a values array for storage in our slot. This should be - * an array of C strings which will be processed later by the - * appropriate "in" functions. - */ - values[0] = varname; - values[1] = varval; - /* build a tuple */ tuple = BuildTupleFromCStrings(attinmeta, values); /* make the tuple into a datum */ result = TupleGetDatum(slot, tuple); - /* Clean up */ - if (varval != NULL) - pfree(varval); - SRF_RETURN_NEXT(funcctx, result); } else diff --git a/src/bin/initdb/initdb.sh b/src/bin/initdb/initdb.sh index 62d1a8039ac46d81df70f030cf7a462640d8b83c..5908416ce40dc1bb620b45bd527fe860bd736479 100644 --- a/src/bin/initdb/initdb.sh +++ b/src/bin/initdb/initdb.sh @@ -27,7 +27,7 @@ # Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group # Portions Copyright (c) 1994, Regents of the University of California # -# $Header: /cvsroot/pgsql/src/bin/initdb/Attic/initdb.sh,v 1.198 2003/07/23 08:46:54 petere Exp $ +# $Header: /cvsroot/pgsql/src/bin/initdb/Attic/initdb.sh,v 1.199 2003/07/27 04:35:53 momjian Exp $ # #------------------------------------------------------------------------- @@ -1000,7 +1000,9 @@ CREATE VIEW pg_locks AS \ CREATE VIEW pg_settings AS \ SELECT * \ - FROM pg_show_all_settings() AS A(name text, setting text); + FROM pg_show_all_settings() AS A \ + (name text, setting text, context text, vartype text, \ + source text, min_val text, max_val text); CREATE RULE pg_settings_u AS \ ON UPDATE TO pg_settings \ diff --git a/src/include/utils/guc.h b/src/include/utils/guc.h index 7199a6e2ea2eae479ccbb9dc4a7b0ae00218a1f0..02d2a01d8bf9a20907369021170a049e422d6cab 100644 --- a/src/include/utils/guc.h +++ b/src/include/utils/guc.h @@ -7,7 +7,7 @@ * Copyright 2000-2003 by PostgreSQL Global Development Group * Written by Peter Eisentraut <peter_e@gmx.net>. * - * $Id: guc.h,v 1.35 2003/07/21 21:02:12 momjian Exp $ + * $Id: guc.h,v 1.36 2003/07/27 04:35:54 momjian Exp $ *-------------------------------------------------------------------- */ #ifndef GUC_H @@ -55,13 +55,13 @@ */ typedef enum { - PGC_INTERNAL, - PGC_POSTMASTER, - PGC_SIGHUP, - PGC_BACKEND, - PGC_SUSET, - PGC_USERLIMIT, - PGC_USERSET + PGC_INTERNAL = 0, + PGC_POSTMASTER = 1, + PGC_SIGHUP = 2, + PGC_BACKEND = 3, + PGC_SUSET = 4, + PGC_USERLIMIT = 5, + PGC_USERSET = 6 } GucContext; /* @@ -73,6 +73,8 @@ typedef enum * Sources <= PGC_S_OVERRIDE will set the default used by RESET, as well * as the current value. Note that source == PGC_S_OVERRIDE should be * used when setting a PGC_INTERNAL option. + * + * Keep in sync with GucSourceName in guc.c */ typedef enum { @@ -92,7 +94,6 @@ typedef enum PGC_S_SESSION = 9 /* SET command */ } GucSource; - /* GUC vars that are actually declared in guc.c, rather than elsewhere */ extern bool log_statement; extern bool log_duration; @@ -132,7 +133,7 @@ extern bool set_config_option(const char *name, const char *value, extern void ShowGUCConfigOption(const char *name, DestReceiver *dest); extern void ShowAllGUCConfig(DestReceiver *dest); extern char *GetConfigOptionByName(const char *name, const char **varname); -extern char *GetConfigOptionByNum(int varnum, const char **varname, bool *noshow); +extern void GetConfigOptionByNum(int varnum, const char **values, bool *noshow); extern int GetNumConfigOptions(void); extern void SetPGVariable(const char *name, List *args, bool is_local); diff --git a/src/include/utils/guc_tables.h b/src/include/utils/guc_tables.h index e8ccfeefd00fd7d59ae76cb6dd0ddd7868a984d6..0eb9376dd573857cf04c345bf8f98f0d429af4fa 100644 --- a/src/include/utils/guc_tables.h +++ b/src/include/utils/guc_tables.h @@ -7,7 +7,7 @@ * * Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group * - * $Id: guc_tables.h,v 1.1 2003/07/04 16:41:22 tgl Exp $ + * $Id: guc_tables.h,v 1.2 2003/07/27 04:35:54 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -61,10 +61,10 @@ enum config_group */ enum config_type { - PGC_BOOL, - PGC_INT, - PGC_REAL, - PGC_STRING + PGC_BOOL = 0, + PGC_INT = 1, + PGC_REAL = 2, + PGC_STRING = 3 }; /* diff --git a/src/test/regress/expected/rangefuncs.out b/src/test/regress/expected/rangefuncs.out index 2790790717aeb1844738f2ee0c8924581d44d59f..7acbbe9bc608d3e6093cd47c4bc7f7baf43c6d19 100644 --- a/src/test/regress/expected/rangefuncs.out +++ b/src/test/regress/expected/rangefuncs.out @@ -1,4 +1,4 @@ -SELECT * FROM pg_settings WHERE name LIKE 'enable%'; +SELECT name, setting FROM pg_settings WHERE name LIKE 'enable%'; name | setting ------------------+--------- enable_hashagg | on diff --git a/src/test/regress/expected/rules.out b/src/test/regress/expected/rules.out index 75e8a676d316b588582e982abb8ad02a130abcfc..a00959e0f70b0ca6109eecb8f6dc306d3ccf3e4b 100644 --- a/src/test/regress/expected/rules.out +++ b/src/test/regress/expected/rules.out @@ -1273,7 +1273,7 @@ SELECT viewname, definition FROM pg_views WHERE schemaname <> 'information_schem pg_indexes | SELECT n.nspname AS schemaname, c.relname AS tablename, i.relname AS indexname, pg_get_indexdef(i.oid) AS indexdef FROM (((pg_index x JOIN pg_class c ON ((c.oid = x.indrelid))) JOIN pg_class i ON ((i.oid = x.indexrelid))) LEFT JOIN pg_namespace n ON ((n.oid = c.relnamespace))) WHERE ((c.relkind = 'r'::"char") AND (i.relkind = 'i'::"char")); pg_locks | SELECT l.relation, l."database", l."transaction", l.pid, l."mode", l.granted FROM pg_lock_status() l(relation oid, "database" oid, "transaction" xid, pid integer, "mode" text, granted boolean); pg_rules | SELECT n.nspname AS schemaname, c.relname AS tablename, r.rulename, pg_get_ruledef(r.oid) AS definition FROM ((pg_rewrite r JOIN pg_class c ON ((c.oid = r.ev_class))) LEFT JOIN pg_namespace n ON ((n.oid = c.relnamespace))) WHERE (r.rulename <> '_RETURN'::name); - pg_settings | SELECT a.name, a.setting FROM pg_show_all_settings() a(name text, setting text); + pg_settings | SELECT a.name, a.setting, a.context, a.vartype, a.source, a.min_val, a.max_val FROM pg_show_all_settings() a(name text, setting text, context text, vartype text, source text, min_val text, max_val text); pg_stat_activity | SELECT d.oid AS datid, d.datname, pg_stat_get_backend_pid(s.backendid) AS procpid, pg_stat_get_backend_userid(s.backendid) AS usesysid, u.usename, pg_stat_get_backend_activity(s.backendid) AS current_query, pg_stat_get_backend_activity_start(s.backendid) AS query_start FROM pg_database d, (SELECT pg_stat_get_backend_idset() AS backendid) s, pg_shadow u WHERE ((pg_stat_get_backend_dbid(s.backendid) = d.oid) AND (pg_stat_get_backend_userid(s.backendid) = u.usesysid)); pg_stat_all_indexes | SELECT c.oid AS relid, i.oid AS indexrelid, n.nspname AS schemaname, c.relname, i.relname AS indexrelname, pg_stat_get_numscans(i.oid) AS idx_scan, pg_stat_get_tuples_returned(i.oid) AS idx_tup_read, pg_stat_get_tuples_fetched(i.oid) AS idx_tup_fetch FROM (((pg_class c JOIN pg_index x ON ((c.oid = x.indrelid))) JOIN pg_class i ON ((i.oid = x.indexrelid))) LEFT JOIN pg_namespace n ON ((n.oid = c.relnamespace))) WHERE (c.relkind = 'r'::"char"); pg_stat_all_tables | SELECT c.oid AS relid, n.nspname AS schemaname, c.relname, pg_stat_get_numscans(c.oid) AS seq_scan, pg_stat_get_tuples_returned(c.oid) AS seq_tup_read, sum(pg_stat_get_numscans(i.indexrelid)) AS idx_scan, sum(pg_stat_get_tuples_fetched(i.indexrelid)) AS idx_tup_fetch, pg_stat_get_tuples_inserted(c.oid) AS n_tup_ins, pg_stat_get_tuples_updated(c.oid) AS n_tup_upd, pg_stat_get_tuples_deleted(c.oid) AS n_tup_del FROM ((pg_class c LEFT JOIN pg_index i ON ((c.oid = i.indrelid))) LEFT JOIN pg_namespace n ON ((n.oid = c.relnamespace))) WHERE (c.relkind = 'r'::"char") GROUP BY c.oid, n.nspname, c.relname; diff --git a/src/test/regress/sql/rangefuncs.sql b/src/test/regress/sql/rangefuncs.sql index 6522fdda10d96ea651d63a5caf166c8e06edf688..2f1c8e75130b07dc7207691c28da659a63981869 100644 --- a/src/test/regress/sql/rangefuncs.sql +++ b/src/test/regress/sql/rangefuncs.sql @@ -1,4 +1,4 @@ -SELECT * FROM pg_settings WHERE name LIKE 'enable%'; +SELECT name, setting FROM pg_settings WHERE name LIKE 'enable%'; CREATE TABLE foo2(fooid int, f2 int); INSERT INTO foo2 VALUES(1, 11);