diff --git a/src/backend/commands/dbcommands.c b/src/backend/commands/dbcommands.c index 7add59e2c39..ae4e52f42a4 100644 --- a/src/backend/commands/dbcommands.c +++ b/src/backend/commands/dbcommands.c @@ -9,7 +9,7 @@ * * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/commands/dbcommands.c,v 1.92 2002/05/25 16:30:59 tgl Exp $ + * $Header: /cvsroot/pgsql/src/backend/commands/dbcommands.c,v 1.93 2002/06/18 17:27:57 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -58,9 +58,7 @@ static bool remove_dbdirs(const char *real_loc, const char *altloc); */ void -createdb(const char *dbname, const char *dbowner, - const char *dbpath, const char *dbtemplate, - int encoding) +createdb(CreatedbStmt *stmt) { char *nominal_loc; char *alt_loc; @@ -82,6 +80,59 @@ createdb(const char *dbname, const char *dbowner, char new_record_nulls[Natts_pg_database]; Oid dboid; int32 datdba; + List *option; + DefElem *downer = NULL; + DefElem *dpath = NULL; + DefElem *dtemplate = NULL; + DefElem *dencoding = NULL; + char *dbname = stmt->dbname; + char *dbowner = NULL; + char *dbpath = NULL; + char *dbtemplate = NULL; + int encoding = -1; + + /* Extract options from the statement node tree */ + foreach(option, stmt->options) + { + DefElem *defel = (DefElem *) lfirst(option); + + if (strcmp(defel->defname, "owner") == 0) + { + if (downer) + elog(ERROR, "CREATE DATABASE: conflicting options"); + downer = defel; + } + else if (strcmp(defel->defname, "location") == 0) + { + if (dpath) + elog(ERROR, "CREATE DATABASE: conflicting options"); + dpath = defel; + } + else if (strcmp(defel->defname, "template") == 0) + { + if (dtemplate) + elog(ERROR, "CREATE DATABASE: conflicting options"); + dtemplate = defel; + } + else if (strcmp(defel->defname, "encoding") == 0) + { + if (dencoding) + elog(ERROR, "CREATE DATABASE: conflicting options"); + dencoding = defel; + } + else + elog(ERROR, "CREATE DATABASE: option \"%s\" not recognized", + defel->defname); + } + + if (downer) + dbowner = strVal(downer->arg); + if (dpath) + dbpath = strVal(dpath->arg); + if (dtemplate) + dbtemplate = strVal(dtemplate->arg); + if (dencoding) + encoding = intVal(dencoding->arg); /* obtain sysid of proposed owner */ if (dbowner) diff --git a/src/backend/nodes/copyfuncs.c b/src/backend/nodes/copyfuncs.c index 5bc16dc9b82..d2a3f40a348 100644 --- a/src/backend/nodes/copyfuncs.c +++ b/src/backend/nodes/copyfuncs.c @@ -15,7 +15,7 @@ * Portions Copyright (c) 1994, Regents of the University of California * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/nodes/copyfuncs.c,v 1.188 2002/05/22 17:20:58 petere Exp $ + * $Header: /cvsroot/pgsql/src/backend/nodes/copyfuncs.c,v 1.189 2002/06/18 17:27:57 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -2258,13 +2258,7 @@ _copyCreatedbStmt(CreatedbStmt *from) if (from->dbname) newnode->dbname = pstrdup(from->dbname); - if (from->dbowner) - newnode->dbowner = pstrdup(from->dbowner); - if (from->dbpath) - newnode->dbpath = pstrdup(from->dbpath); - if (from->dbtemplate) - newnode->dbtemplate = pstrdup(from->dbtemplate); - newnode->encoding = from->encoding; + Node_Copy(from, newnode, options); return newnode; } diff --git a/src/backend/nodes/equalfuncs.c b/src/backend/nodes/equalfuncs.c index b4f576fc881..85ff384479d 100644 --- a/src/backend/nodes/equalfuncs.c +++ b/src/backend/nodes/equalfuncs.c @@ -20,7 +20,7 @@ * Portions Copyright (c) 1994, Regents of the University of California * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/nodes/equalfuncs.c,v 1.135 2002/05/22 17:20:59 petere Exp $ + * $Header: /cvsroot/pgsql/src/backend/nodes/equalfuncs.c,v 1.136 2002/06/18 17:27:57 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -1085,13 +1085,7 @@ _equalCreatedbStmt(CreatedbStmt *a, CreatedbStmt *b) { if (!equalstr(a->dbname, b->dbname)) return false; - if (!equalstr(a->dbowner, b->dbowner)) - return false; - if (!equalstr(a->dbpath, b->dbpath)) - return false; - if (!equalstr(a->dbtemplate, b->dbtemplate)) - return false; - if (a->encoding != b->encoding) + if (!equal(a->options, b->options)) return false; return true; diff --git a/src/backend/parser/gram.y b/src/backend/parser/gram.y index 7106cfc1c28..8affd233ed9 100644 --- a/src/backend/parser/gram.y +++ b/src/backend/parser/gram.y @@ -11,7 +11,7 @@ * * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 2.328 2002/06/18 00:28:11 momjian Exp $ + * $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 2.329 2002/06/18 17:27:57 momjian Exp $ * * HISTORY * AUTHOR DATE MAJOR EVENT @@ -154,7 +154,8 @@ static void doNegateFloat(Value *v); %type alter_column_default %type add_drop, drop_behavior, opt_drop_behavior -%type createdb_opt_list, createdb_opt_item +%type createdb_opt_list +%type createdb_opt_item %type opt_equal %type opt_lock, lock_type @@ -3351,35 +3352,8 @@ CreatedbStmt: CREATE DATABASE database_name opt_with createdb_opt_list { CreatedbStmt *n = makeNode(CreatedbStmt); - List *l; - n->dbname = $3; - /* set default options */ - n->dbowner = NULL; - n->dbpath = NULL; - n->dbtemplate = NULL; - n->encoding = -1; - /* process additional options */ - foreach(l, $5) - { - List *optitem = (List *) lfirst(l); - - switch (lfirsti(optitem)) - { - case 1: - n->dbpath = (char *) lsecond(optitem); - break; - case 2: - n->dbtemplate = (char *) lsecond(optitem); - break; - case 3: - n->encoding = lfirsti(lnext(optitem)); - break; - case 4: - n->dbowner = (char *) lsecond(optitem); - break; - } - } + n->options = $5; $$ = (Node *)n; } ; @@ -3396,19 +3370,27 @@ createdb_opt_list: createdb_opt_item: LOCATION opt_equal Sconst { - $$ = lconsi(1, makeList1($3)); + $$ = makeNode(DefElem); + $$->defname = "location"; + $$->arg = (Node *)makeString($3); } | LOCATION opt_equal DEFAULT { - $$ = lconsi(1, makeList1(NULL)); + $$ = makeNode(DefElem); + $$->defname = "location"; + $$->arg = NULL; } | TEMPLATE opt_equal name { - $$ = lconsi(2, makeList1($3)); + $$ = makeNode(DefElem); + $$->defname = "template"; + $$->arg = (Node *)makeString($3); } | TEMPLATE opt_equal DEFAULT { - $$ = lconsi(2, makeList1(NULL)); + $$ = makeNode(DefElem); + $$->defname = "template"; + $$->arg = NULL; } | ENCODING opt_equal Sconst { @@ -3422,7 +3404,9 @@ createdb_opt_item: elog(ERROR, "Multi-byte support is not enabled"); encoding = GetStandardEncoding(); #endif - $$ = lconsi(3, makeListi1(encoding)); + $$ = makeNode(DefElem); + $$->defname = "encoding"; + $$->arg = (Node *)makeInteger(encoding); } | ENCODING opt_equal Iconst { @@ -3433,19 +3417,27 @@ createdb_opt_item: if ($3 != GetStandardEncoding()) elog(ERROR, "Multi-byte support is not enabled"); #endif - $$ = lconsi(3, makeListi1($3)); + $$ = makeNode(DefElem); + $$->defname = "encoding"; + $$->arg = (Node *)makeInteger($3); } | ENCODING opt_equal DEFAULT { - $$ = lconsi(3, makeListi1(-1)); + $$ = makeNode(DefElem); + $$->defname = "encoding"; + $$->arg = (Node *)makeInteger(-1); } | OWNER opt_equal name { - $$ = lconsi(4, makeList1($3)); + $$ = makeNode(DefElem); + $$->defname = "owner"; + $$->arg = (Node *)makeString($3); } | OWNER opt_equal DEFAULT { - $$ = lconsi(4, makeList1(NULL)); + $$ = makeNode(DefElem); + $$->defname = "owner"; + $$->arg = NULL; } ; diff --git a/src/backend/tcop/utility.c b/src/backend/tcop/utility.c index 36a3cb06dd4..4e23a6d9190 100644 --- a/src/backend/tcop/utility.c +++ b/src/backend/tcop/utility.c @@ -10,7 +10,7 @@ * * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.156 2002/05/21 22:18:08 tgl Exp $ + * $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.157 2002/06/18 17:27:58 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -630,10 +630,7 @@ ProcessUtility(Node *parsetree, case T_CreatedbStmt: { CreatedbStmt *stmt = (CreatedbStmt *) parsetree; - - createdb(stmt->dbname, stmt->dbowner, - stmt->dbpath, stmt->dbtemplate, - stmt->encoding); + createdb(stmt); } break; diff --git a/src/include/commands/dbcommands.h b/src/include/commands/dbcommands.h index 32c823e152c..1a99da6d4da 100644 --- a/src/include/commands/dbcommands.h +++ b/src/include/commands/dbcommands.h @@ -7,7 +7,7 @@ * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1994, Regents of the University of California * - * $Id: dbcommands.h,v 1.21 2002/03/01 22:45:17 petere Exp $ + * $Id: dbcommands.h,v 1.22 2002/06/18 17:27:58 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -16,9 +16,7 @@ #include -extern void createdb(const char *dbname, const char *dbowner, - const char *dbpath, const char *dbtemplate, - int encoding); +extern void createdb(CreatedbStmt *stmt); extern void dropdb(const char *dbname); extern void AlterDatabaseSet(AlterDatabaseSetStmt *stmt); diff --git a/src/include/nodes/parsenodes.h b/src/include/nodes/parsenodes.h index f7ea60ac802..01b90ce0285 100644 --- a/src/include/nodes/parsenodes.h +++ b/src/include/nodes/parsenodes.h @@ -7,7 +7,7 @@ * Portions Copyright (c) 1996-2001, PostgreSQL Global Development Group * Portions Copyright (c) 1994, Regents of the University of California * - * $Id: parsenodes.h,v 1.179 2002/05/22 17:21:01 petere Exp $ + * $Id: parsenodes.h,v 1.180 2002/06/18 17:27:58 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -1350,10 +1350,7 @@ typedef struct CreatedbStmt { NodeTag type; char *dbname; /* name of database to create */ - char *dbowner; /* name of owner (NULL = default) */ - char *dbpath; /* location of database (NULL = default) */ - char *dbtemplate; /* template to use (NULL = default) */ - int encoding; /* MULTIBYTE encoding (-1 = use default) */ + List *options; /* List of DefElem nodes */ } CreatedbStmt; /* ----------------------