]> granicus.if.org Git - postgresql/commitdiff
Now we are able to CREATE PROCEDURAL LANGUAGE (Thanks, Jan).
authorVadim B. Mikheev <vadim4o@yahoo.com>
Tue, 28 Oct 1997 15:11:45 +0000 (15:11 +0000)
committerVadim B. Mikheev <vadim4o@yahoo.com>
Tue, 28 Oct 1997 15:11:45 +0000 (15:11 +0000)
16 files changed:
src/backend/commands/Makefile
src/backend/commands/define.c
src/backend/commands/proclang.c [new file with mode: 0644]
src/backend/commands/trigger.c
src/backend/parser/gram.y
src/backend/parser/keywords.c
src/backend/tcop/utility.c
src/backend/utils/Gen_fmgrtab.sh.in
src/backend/utils/cache/syscache.c
src/backend/utils/fmgr/fmgr.c
src/include/catalog/pg_language.h
src/include/commands/proclang.h [new file with mode: 0644]
src/include/nodes/nodes.h
src/include/nodes/parsenodes.h
src/include/utils/rel.h
src/include/utils/syscache.h

index 5d8e945a66ad19c20febb800d142d4a6897fdd81..c65f04da402cca9e5c7d4116f71f06ed747c00d9 100644 (file)
@@ -4,7 +4,7 @@
 #    Makefile for commands
 #
 # IDENTIFICATION
-#    $Header: /cvsroot/pgsql/src/backend/commands/Makefile,v 1.4 1997/08/31 11:40:12 vadim Exp $
+#    $Header: /cvsroot/pgsql/src/backend/commands/Makefile,v 1.5 1997/10/28 14:54:43 vadim Exp $
 #
 #-------------------------------------------------------------------------
 
@@ -19,7 +19,7 @@ CFLAGS+=$(INCLUDE_OPT)
 
 OBJS = async.o creatinh.o command.o copy.o defind.o define.o \
        purge.o remove.o rename.o vacuum.o version.o view.o cluster.o \
-       recipe.o explain.o sequence.o trigger.o
+       recipe.o explain.o sequence.o trigger.o proclang.o
 
 all: SUBSYS.o
 
index 903bb5164953f71bc757fef085b4265c1867767b..9aa8c09897329c5e3fa27017fecb9b4040f80429 100644 (file)
@@ -9,7 +9,7 @@
  *
  *
  * IDENTIFICATION
- *       $Header: /cvsroot/pgsql/src/backend/commands/define.c,v 1.16 1997/09/08 21:42:38 momjian Exp $
+ *       $Header: /cvsroot/pgsql/src/backend/commands/define.c,v 1.17 1997/10/28 14:54:46 vadim Exp $
  *
  * DESCRIPTION
  *       The "DefineFoo" routines take the parse tree and pick out the
@@ -45,6 +45,7 @@
 #include <catalog/pg_operator.h>
 #include <catalog/pg_proc.h>
 #include <catalog/pg_type.h>
+#include <catalog/pg_language.h>
 #include <utils/syscache.h>
 #include <fmgr.h>                              /* for fmgr */
 #include <utils/builtins.h>            /* prototype for textin() */
@@ -239,6 +240,8 @@ CreateFunction(ProcedureStmt *stmt, CommandDest dest)
        bool            canCache;
        bool            returnsSet;
 
+       bool            lanisPL = false;
+
        /* The function returns a set of values, as opposed to a singleton. */
 
 
@@ -262,19 +265,59 @@ CreateFunction(ProcedureStmt *stmt, CommandDest dest)
        }
        else
        {
-               elog(WARN,
+               HeapTuple               languageTuple;
+               Form_pg_language        languageStruct;
+
+               /* Lookup the language in the system cache */
+               languageTuple = SearchSysCacheTuple(LANNAME,
+                       PointerGetDatum(languageName),
+                       0, 0, 0);
+               
+               if (!HeapTupleIsValid(languageTuple)) {
+
+                   elog(WARN,
                         "Unrecognized language specified in a CREATE FUNCTION: "
-                        "'%s'.  Recognized languages are sql, C, and internal.",
+                        "'%s'.  Recognized languages are sql, C, internal "
+                        "and the created procedural languages.",
                         languageName);
+               }
+
+               /* Check that this language is a PL */
+               languageStruct = (Form_pg_language) GETSTRUCT(languageTuple);
+               if (!(languageStruct->lanispl)) {
+                   elog(WARN,
+                       "Language '%s' isn't defined as PL", languageName);
+               }
+
+               /*
+                * Functions in untrusted procedural languages are
+                * restricted to be defined by postgres superusers only
+                */
+               if (languageStruct->lanpltrusted == false && !superuser()) {
+                   elog(WARN, "Only users with Postgres superuser privilege "
+                       "are permitted to create a function in the '%s' "
+                       "language.",
+                       languageName);
+               }
+
+               lanisPL = true;
+
+               /*
+                * These are meaningless
+                */
+               perbyte_cpu = percall_cpu = 0;
+               byte_pct = outin_ratio = 100;
+               canCache = false;
        }
 
        interpret_AS_clause(languageName, stmt->as, &prosrc_str, &probin_str);
 
-       if (strcmp(languageName, "sql") != 0 && !superuser())
+       if (strcmp(languageName, "sql") != 0 && lanisPL == false && !superuser())
                elog(WARN,
                         "Only users with Postgres superuser privilege are permitted "
                         "to create a function "
-                        "in the '%s' language.  Others may use the 'sql' language.",
+                        "in the '%s' language.  Others may use the 'sql' language "
+                        "or the created procedural languages.",
                         languageName);
        /* Above does not return. */
        else
diff --git a/src/backend/commands/proclang.c b/src/backend/commands/proclang.c
new file mode 100644 (file)
index 0000000..2b8836b
--- /dev/null
@@ -0,0 +1,205 @@
+/*-------------------------------------------------------------------------
+ *
+ * proclang.c--
+ *       PostgreSQL PROCEDURAL LANGUAGE support code.
+ *
+ *-------------------------------------------------------------------------
+ */
+#include <ctype.h>
+#include <string.h>
+#include "postgres.h"
+
+#include "access/heapam.h"
+#include "catalog/catname.h"
+#include "catalog/pg_user.h"
+#include "catalog/pg_proc.h"
+#include "catalog/pg_language.h"
+#include "utils/syscache.h"
+#include "commands/proclang.h"
+#include "fmgr.h"
+
+
+static void
+case_translate_language_name(const char *input, char *output)
+{
+/*-------------------------------------------------------------------------
+  Translate the input language name to lower case, except if it's C,
+  translate to upper case.
+--------------------------------------------------------------------------*/
+       int                     i;
+
+       for (i = 0; i < NAMEDATALEN && input[i] != '\0'; ++i)
+               output[i] = tolower(input[i]);
+
+       output[i] = '\0';
+
+       if (strcmp(output, "c") == 0)
+               output[0] = 'C';
+}
+
+
+/* ---------------------------------------------------------------------
+ * CREATE PROCEDURAL LANGUAGE
+ * ---------------------------------------------------------------------
+ */
+void
+CreateProceduralLanguage(CreatePLangStmt * stmt)
+{
+       char            languageName[NAMEDATALEN];
+       HeapTuple       langTup;
+       HeapTuple       procTup;
+
+       Oid                     typev[8];
+       char            nulls[Natts_pg_language];
+       Datum           values[Natts_pg_language];
+       Relation        rdesc;
+       HeapTuple       tup;
+       TupleDesc       tupDesc;
+
+       int                     i;
+
+       /* ----------------
+        * Check permission
+        * ----------------
+        */
+       if (!superuser())
+       {
+               elog(WARN, "Only users with Postgres superuser privilege are "
+                        "permitted to create procedural languages");
+       }
+
+       /* ----------------
+        * Translate the language name and check that
+        * this language doesn't already exist
+        * ----------------
+        */
+       case_translate_language_name(stmt->plname, languageName);
+
+       langTup = SearchSysCacheTuple(LANNAME,
+                                                                 PointerGetDatum(languageName),
+                                                                 0, 0, 0);
+       if (HeapTupleIsValid(langTup))
+       {
+               elog(WARN, "Language %s already exists", languageName);
+       }
+
+       /* ----------------
+        * Lookup the PL handler function and check that it is
+        * of return type Opaque
+        * ----------------
+        */
+       memset(typev, 0, sizeof(typev));
+       procTup = SearchSysCacheTuple(PRONAME,
+                                                                 PointerGetDatum(stmt->plhandler),
+                                                                 UInt16GetDatum(0),
+                                                                 PointerGetDatum(typev),
+                                                                 0);
+       if (!HeapTupleIsValid(procTup))
+       {
+               elog(WARN, "PL handler function %s() doesn't exist",
+                        stmt->plhandler);
+       }
+       if (((Form_pg_proc) GETSTRUCT(procTup))->prorettype != InvalidOid)
+       {
+               elog(WARN, "PL handler function %s() isn't of return type Opaque",
+                        stmt->plhandler);
+       }
+
+       /* ----------------
+        * Insert the new language into pg_language
+        * ----------------
+        */
+       for (i = 0; i < Natts_pg_language; i++)
+       {
+               nulls[i] = ' ';
+               values[i] = (Datum) NULL;
+       }
+
+       i = 0;
+       values[i++] = PointerGetDatum(languageName);
+       values[i++] = Int8GetDatum((bool) 1);
+       values[i++] = Int8GetDatum(stmt->pltrusted);
+       values[i++] = ObjectIdGetDatum(procTup->t_oid);
+       values[i++] = (Datum) fmgr(TextInRegProcedure, stmt->plcompiler);
+
+       rdesc = heap_openr(LanguageRelationName);
+
+       tupDesc = rdesc->rd_att;
+       tup = heap_formtuple(tupDesc, values, nulls);
+
+       heap_insert(rdesc, tup);
+
+       heap_close(rdesc);
+       return;
+}
+
+
+/* ---------------------------------------------------------------------
+ * DROP PROCEDURAL LANGUAGE
+ * ---------------------------------------------------------------------
+ */
+void
+DropProceduralLanguage(DropPLangStmt * stmt)
+{
+       char            languageName[NAMEDATALEN];
+       HeapTuple       langTup;
+
+       Relation        rdesc;
+       HeapScanDesc scanDesc;
+       ScanKeyData scanKeyData;
+       HeapTuple       tup;
+
+       /* ----------------
+        * Check permission
+        * ----------------
+        */
+       if (!superuser())
+       {
+               elog(WARN, "Only users with Postgres superuser privilege are "
+                        "permitted to drop procedural languages");
+       }
+
+       /* ----------------
+        * Translate the language name, check that
+        * this language exist and is a PL
+        * ----------------
+        */
+       case_translate_language_name(stmt->plname, languageName);
+
+       langTup = SearchSysCacheTuple(LANNAME,
+                                                                 PointerGetDatum(languageName),
+                                                                 0, 0, 0);
+       if (!HeapTupleIsValid(langTup))
+       {
+               elog(WARN, "Language %s doesn't exist", languageName);
+       }
+
+       if (!((Form_pg_language) GETSTRUCT(langTup))->lanispl)
+       {
+               elog(WARN, "Language %s isn't a created procedural language",
+                        languageName);
+       }
+
+       /* ----------------
+        * Now scan pg_language and delete the PL tuple
+        * ----------------
+        */
+       rdesc = heap_openr(LanguageRelationName);
+
+       ScanKeyEntryInitialize(&scanKeyData, 0, Anum_pg_language_lanname,
+                                                  F_NAMEEQ, PointerGetDatum(languageName));
+
+       scanDesc = heap_beginscan(rdesc, 0, NowTimeQual, 1, &scanKeyData);
+
+       tup = heap_getnext(scanDesc, 0, (Buffer *) NULL);
+
+       if (!HeapTupleIsValid(tup))
+       {
+               elog(WARN, "Language with name '%s' not found", languageName);
+       }
+
+       heap_delete(rdesc, &(tup->t_ctid));
+
+       heap_endscan(scanDesc);
+       heap_close(rdesc);
+}
index 9215f41055596fd433bc0bd2f6b3d124983e58cc..273136b29233811edc59c54b790ef261fd657c10 100644 (file)
 #include "utils/mcxt.h"
 #include "utils/inval.h"
 #include "utils/builtins.h"
+#include "utils/syscache.h"
 
 #ifndef NO_SECURITY
 #include "miscadmin.h"
 #include "utils/acl.h"
-#include "utils/syscache.h"
 #endif
 
 TriggerData *CurrentTriggerData = NULL;
@@ -87,8 +87,8 @@ CreateTrigger(CreateTrigStmt * stmt)
        if (stmt->row)
                TRIGGER_SETT_ROW(tgtype);
        else
-               elog (WARN, "CreateTrigger: STATEMENT triggers are unimplemented, yet");
-       
+               elog(WARN, "CreateTrigger: STATEMENT triggers are unimplemented, yet");
+
        for (i = 0; i < 3 && stmt->actions[i]; i++)
        {
                switch (stmt->actions[i])
@@ -142,7 +142,22 @@ CreateTrigger(CreateTrigStmt * stmt)
                elog(WARN, "CreateTrigger: function %s () does not exist", stmt->funcname);
 
        if (((Form_pg_proc) GETSTRUCT(tuple))->prolang != ClanguageId)
-               elog(WARN, "CreateTrigger: only C functions are supported");
+       {
+               HeapTuple       langTup;
+
+               langTup = SearchSysCacheTuple(LANOID,
+                       ObjectIdGetDatum(((Form_pg_proc) GETSTRUCT(tuple))->prolang),
+                                                                         0, 0, 0);
+               if (!HeapTupleIsValid(langTup))
+               {
+                       elog(WARN, "CreateTrigger: cache lookup for PL failed");
+               }
+
+               if (((Form_pg_language) GETSTRUCT(langTup))->lanispl == false)
+               {
+                       elog(WARN, "CreateTrigger: only C and PL functions are supported");
+               }
+       }
 
        MemSet(nulls, ' ', Natts_pg_trigger * sizeof(char));
 
@@ -159,10 +174,10 @@ CreateTrigger(CreateTrigStmt * stmt)
 
                foreach(le, stmt->args)
                {
-                       char   *ar = (char *) lfirst(le);
+                       char       *ar = (char *) lfirst(le);
 
                        len += strlen(ar) + 4;
-                       for ( ; *ar; ar++)
+                       for (; *ar; ar++)
                        {
                                if (*ar == '\\')
                                        len++;
@@ -172,9 +187,9 @@ CreateTrigger(CreateTrigStmt * stmt)
                args[0] = 0;
                foreach(le, stmt->args)
                {
-                       char   *s = (char *) lfirst(le);
-                       char   *d = args + strlen(args);
-                       
+                       char       *s = (char *) lfirst(le);
+                       char       *d = args + strlen(args);
+
                        while (*s)
                        {
                                if (*s == '\\')
@@ -399,6 +414,7 @@ RelationBuildTriggers(Relation relation)
                build->tgname = nameout(&(pg_trigger->tgname));
                build->tgfoid = pg_trigger->tgfoid;
                build->tgfunc = NULL;
+               build->tgplfunc = NULL;
                build->tgtype = pg_trigger->tgtype;
                build->tgnargs = pg_trigger->tgnargs;
                memcpy(build->tgattr, &(pg_trigger->tgattr), 8 * sizeof(int16));
@@ -578,6 +594,54 @@ DescribeTrigger(TriggerDesc * trigdesc, Trigger * trigger)
 
 }
 
+static HeapTuple
+ExecCallTriggerFunc(Trigger * trigger)
+{
+
+       if (trigger->tgfunc != NULL)
+       {
+               return (HeapTuple) ((*(trigger->tgfunc)) ());
+       }
+
+       if (trigger->tgplfunc == NULL)
+       {
+               HeapTuple       procTuple;
+               HeapTuple       langTuple;
+               Form_pg_proc procStruct;
+               Form_pg_language langStruct;
+               int                     nargs;
+
+               procTuple = SearchSysCacheTuple(PROOID,
+                                                                               ObjectIdGetDatum(trigger->tgfoid),
+                                                                               0, 0, 0);
+               if (!HeapTupleIsValid(procTuple))
+               {
+                       elog(WARN, "ExecCallTriggerFunc(): Cache lookup for proc %ld failed",
+                                ObjectIdGetDatum(trigger->tgfoid));
+               }
+               procStruct = (Form_pg_proc) GETSTRUCT(procTuple);
+
+               langTuple = SearchSysCacheTuple(LANOID,
+                                                                  ObjectIdGetDatum(procStruct->prolang),
+                                                                               0, 0, 0);
+               if (!HeapTupleIsValid(langTuple))
+               {
+                       elog(WARN, "ExecCallTriggerFunc(): Cache lookup for language %ld failed",
+                                ObjectIdGetDatum(procStruct->prolang));
+               }
+               langStruct = (Form_pg_language) GETSTRUCT(langTuple);
+
+               if (langStruct->lanispl == false)
+               {
+                       fmgr_info(trigger->tgfoid, &(trigger->tgfunc), &nargs);
+                       return (HeapTuple) ((*(trigger->tgfunc)) ());
+               }
+               fmgr_info(langStruct->lanplcallfoid, &(trigger->tgplfunc), &nargs);
+       }
+
+       return (HeapTuple) ((*(trigger->tgplfunc)) (trigger->tgfoid));
+}
+
 HeapTuple
 ExecBRInsertTriggers(Relation rel, HeapTuple trigtuple)
 {
@@ -586,7 +650,6 @@ ExecBRInsertTriggers(Relation rel, HeapTuple trigtuple)
        Trigger   **trigger = rel->trigdesc->tg_before_row[TRIGGER_EVENT_INSERT];
        HeapTuple       newtuple = trigtuple;
        HeapTuple       oldtuple;
-       int                     nargs;
        int                     i;
 
        SaveTriggerData = (TriggerData *) palloc(sizeof(TriggerData));
@@ -599,9 +662,7 @@ ExecBRInsertTriggers(Relation rel, HeapTuple trigtuple)
                CurrentTriggerData = SaveTriggerData;
                CurrentTriggerData->tg_trigtuple = oldtuple = newtuple;
                CurrentTriggerData->tg_trigger = trigger[i];
-               if (trigger[i]->tgfunc == NULL)
-                       fmgr_info(trigger[i]->tgfoid, &(trigger[i]->tgfunc), &nargs);
-               newtuple = (HeapTuple) ((*(trigger[i]->tgfunc)) ());
+               newtuple = ExecCallTriggerFunc(trigger[i]);
                if (newtuple == NULL)
                        break;
                else if (oldtuple != newtuple && oldtuple != trigtuple)
@@ -618,7 +679,6 @@ ExecARInsertTriggers(Relation rel, HeapTuple trigtuple)
        TriggerData *SaveTriggerData;
        int                     ntrigs = rel->trigdesc->n_after_row[TRIGGER_EVENT_INSERT];
        Trigger   **trigger = rel->trigdesc->tg_after_row[TRIGGER_EVENT_INSERT];
-       int                     nargs;
        int                     i;
 
        SaveTriggerData = (TriggerData *) palloc(sizeof(TriggerData));
@@ -630,9 +690,7 @@ ExecARInsertTriggers(Relation rel, HeapTuple trigtuple)
                CurrentTriggerData = SaveTriggerData;
                CurrentTriggerData->tg_trigtuple = trigtuple;
                CurrentTriggerData->tg_trigger = trigger[i];
-               if (trigger[i]->tgfunc == NULL)
-                       fmgr_info(trigger[i]->tgfoid, &(trigger[i]->tgfunc), &nargs);
-               (void) ((*(trigger[i]->tgfunc)) ());
+               ExecCallTriggerFunc(trigger[i]);
        }
        CurrentTriggerData = NULL;
        pfree(SaveTriggerData);
@@ -647,7 +705,6 @@ ExecBRDeleteTriggers(Relation rel, ItemPointer tupleid)
        Trigger   **trigger = rel->trigdesc->tg_before_row[TRIGGER_EVENT_DELETE];
        HeapTuple       trigtuple;
        HeapTuple       newtuple = NULL;
-       int                     nargs;
        int                     i;
 
        trigtuple = GetTupleForTrigger(rel, tupleid, true);
@@ -664,9 +721,7 @@ ExecBRDeleteTriggers(Relation rel, ItemPointer tupleid)
                CurrentTriggerData = SaveTriggerData;
                CurrentTriggerData->tg_trigtuple = trigtuple;
                CurrentTriggerData->tg_trigger = trigger[i];
-               if (trigger[i]->tgfunc == NULL)
-                       fmgr_info(trigger[i]->tgfoid, &(trigger[i]->tgfunc), &nargs);
-               newtuple = (HeapTuple) ((*(trigger[i]->tgfunc)) ());
+               newtuple = ExecCallTriggerFunc(trigger[i]);
                if (newtuple == NULL)
                        break;
        }
@@ -684,7 +739,6 @@ ExecARDeleteTriggers(Relation rel, ItemPointer tupleid)
        int                     ntrigs = rel->trigdesc->n_after_row[TRIGGER_EVENT_DELETE];
        Trigger   **trigger = rel->trigdesc->tg_after_row[TRIGGER_EVENT_DELETE];
        HeapTuple       trigtuple;
-       int                     nargs;
        int                     i;
 
        trigtuple = GetTupleForTrigger(rel, tupleid, false);
@@ -700,9 +754,7 @@ ExecARDeleteTriggers(Relation rel, ItemPointer tupleid)
                CurrentTriggerData = SaveTriggerData;
                CurrentTriggerData->tg_trigtuple = trigtuple;
                CurrentTriggerData->tg_trigger = trigger[i];
-               if (trigger[i]->tgfunc == NULL)
-                       fmgr_info(trigger[i]->tgfoid, &(trigger[i]->tgfunc), &nargs);
-               (void) ((*(trigger[i]->tgfunc)) ());
+               ExecCallTriggerFunc(trigger[i]);
        }
        CurrentTriggerData = NULL;
        pfree(SaveTriggerData);
@@ -719,7 +771,6 @@ ExecBRUpdateTriggers(Relation rel, ItemPointer tupleid, HeapTuple newtuple)
        HeapTuple       trigtuple;
        HeapTuple       oldtuple;
        HeapTuple       intuple = newtuple;
-       int                     nargs;
        int                     i;
 
        trigtuple = GetTupleForTrigger(rel, tupleid, true);
@@ -736,9 +787,7 @@ ExecBRUpdateTriggers(Relation rel, ItemPointer tupleid, HeapTuple newtuple)
                CurrentTriggerData->tg_trigtuple = trigtuple;
                CurrentTriggerData->tg_newtuple = oldtuple = newtuple;
                CurrentTriggerData->tg_trigger = trigger[i];
-               if (trigger[i]->tgfunc == NULL)
-                       fmgr_info(trigger[i]->tgfoid, &(trigger[i]->tgfunc), &nargs);
-               newtuple = (HeapTuple) ((*(trigger[i]->tgfunc)) ());
+               newtuple = ExecCallTriggerFunc(trigger[i]);
                if (newtuple == NULL)
                        break;
                else if (oldtuple != newtuple && oldtuple != intuple)
@@ -757,7 +806,6 @@ ExecARUpdateTriggers(Relation rel, ItemPointer tupleid, HeapTuple newtuple)
        int                     ntrigs = rel->trigdesc->n_after_row[TRIGGER_EVENT_UPDATE];
        Trigger   **trigger = rel->trigdesc->tg_after_row[TRIGGER_EVENT_UPDATE];
        HeapTuple       trigtuple;
-       int                     nargs;
        int                     i;
 
        trigtuple = GetTupleForTrigger(rel, tupleid, false);
@@ -773,9 +821,7 @@ ExecARUpdateTriggers(Relation rel, ItemPointer tupleid, HeapTuple newtuple)
                CurrentTriggerData->tg_trigtuple = trigtuple;
                CurrentTriggerData->tg_newtuple = newtuple;
                CurrentTriggerData->tg_trigger = trigger[i];
-               if (trigger[i]->tgfunc == NULL)
-                       fmgr_info(trigger[i]->tgfoid, &(trigger[i]->tgfunc), &nargs);
-               (void) ((*(trigger[i]->tgfunc)) ());
+               ExecCallTriggerFunc(trigger[i]);
        }
        CurrentTriggerData = NULL;
        pfree(SaveTriggerData);
index 8132cc34d4837d9ce32b46204a322615931821c6..7eb361d3a93e21541479b3785d9a1560980fd1f5 100644 (file)
@@ -10,7 +10,7 @@
  *
  *
  * IDENTIFICATION
- *       $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 1.58 1997/10/25 05:56:41 thomas Exp $
+ *       $Header: /cvsroot/pgsql/src/backend/parser/gram.y,v 1.59 1997/10/28 14:56:08 vadim Exp $
  *
  * HISTORY
  *       AUTHOR                        DATE                    MAJOR EVENT
@@ -109,6 +109,7 @@ static char *FlattenStringList(List *list);
                AddAttrStmt, ClosePortalStmt,
                CopyStmt, CreateStmt, CreateSeqStmt, DefineStmt, DestroyStmt,
                ExtendStmt, FetchStmt,  GrantStmt, CreateTrigStmt, DropTrigStmt,
+               CreatePLangStmt, DropPLangStmt,
                IndexStmt, ListenStmt, OptimizableStmt,
                ProcedureStmt, PurgeStmt,
                RecipeStmt, RemoveAggrStmt, RemoveOperStmt, RemoveFuncStmt, RemoveStmt,
@@ -119,7 +120,7 @@ static char *FlattenStringList(List *list);
 
 %type <node>   SubSelect
 %type <str>            join_expr, join_outer, join_spec
-%type <boolean> TriggerActionTime, TriggerForSpec
+%type <boolean> TriggerActionTime, TriggerForSpec, PLangTrusted
 
 %type <str>            TriggerEvents, TriggerFuncArg
 
@@ -225,9 +226,9 @@ static char *FlattenStringList(List *list);
 /* Keywords (in SQL92 reserved words) */
 %token ACTION, ADD, ALL, ALTER, AND, AS, ASC,
                BEGIN_TRANS, BETWEEN, BOTH, BY,
-               CASCADE, CAST, CHAR, CHARACTER, CHECK, CLOSE,
-               COLLATE, COLUMN, COMMIT, CONSTRAINT, CREATE, CROSS,
-               CURRENT, CURRENT_DATE, CURRENT_TIME, CURRENT_TIMESTAMP, CURRENT_USER, CURSOR,
+               CASCADE, CAST, CHAR, CHARACTER, CHECK, CLOSE, COLLATE, COLUMN, COMMIT, 
+               CONSTRAINT, CREATE, CROSS, CURRENT, CURRENT_DATE, CURRENT_TIME, 
+               CURRENT_TIMESTAMP, CURRENT_USER, CURSOR,
                DAY_P, DECIMAL, DECLARE, DEFAULT, DELETE, DESC, DISTINCT, DOUBLE, DROP,
                END_TRANS, EXECUTE, EXISTS, EXTRACT,
                FETCH, FLOAT, FOR, FOREIGN, FROM, FULL,
@@ -256,12 +257,12 @@ static char *FlattenStringList(List *list);
                APPEND, ARCHIVE, ARCH_STORE,
                BACKWARD, BEFORE, BINARY, CHANGE, CLUSTER, COPY,
                DATABASE, DELIMITERS, DO, EXPLAIN, EXTEND,
-               FORWARD, FUNCTION, HEAVY,
+               FORWARD, FUNCTION, HANDLER, HEAVY,
                INDEX, INHERITS, INSTEAD, ISNULL,
-               LIGHT, LISTEN, LOAD, MERGE, MOVE,
-               NEW, NONE, NOTHING, OIDS, OPERATOR, PURGE,
+               LANCOMPILER, LIGHT, LISTEN, LOAD, MERGE, MOVE,
+               NEW, NONE, NOTHING, OIDS, OPERATOR, PROCEDURAL, PURGE,
                RECIPE, RENAME, REPLACE, RESET, RETRIEVE, RETURNS, RULE,
-               SEQUENCE, SETOF, SHOW, STDIN, STDOUT, STORE,
+               SEQUENCE, SETOF, SHOW, STDIN, STDOUT, STORE, TRUSTED, 
                VACUUM, VERBOSE, VERSION
 
 /* Special keywords, not in the query language - see the "lex" file */
@@ -318,10 +319,12 @@ stmt :      AddAttrStmt
                | CopyStmt
                | CreateStmt
                | CreateSeqStmt
+               | CreatePLangStmt
                | CreateTrigStmt
                | ClusterStmt
                | DefineStmt
                | DestroyStmt
+               | DropPLangStmt
                | DropTrigStmt
                | ExtendStmt
                | ExplainStmt
@@ -857,6 +860,36 @@ OptSeqElem:                IDENT NumConst
                                }
                ;
 
+/*****************************************************************************
+ *
+ *             QUERIES :
+ *                             CREATE PROCEDURAL LANGUAGE ...
+ *                             DROP PROCEDURAL LANGUAGE ...
+ *
+ *****************************************************************************/
+
+CreatePLangStmt: CREATE PLangTrusted PROCEDURAL LANGUAGE Sconst 
+                       HANDLER def_name LANCOMPILER Sconst
+                       {
+                               CreatePLangStmt *n = makeNode(CreatePLangStmt);
+                               n->plname = $5;
+                               n->plhandler = $7;
+                               n->plcompiler = $9;
+                               n->pltrusted = $2;
+                               $$ = (Node *)n;
+                       }
+               ;
+
+PLangTrusted:          TRUSTED { $$ = TRUE; }
+                       |       { $$ = FALSE; }
+
+DropPLangStmt: DROP PROCEDURAL LANGUAGE Sconst
+                       {
+                               DropPLangStmt *n = makeNode(DropPLangStmt);
+                               n->plname = $4;
+                               $$ = (Node *)n;
+                       }
+               ;
 
 /*****************************************************************************
  *
index f3f957dbb0f8896ea7a756675e1102ddfca210f5..b2bcce32d1e9fc59ab9cd979ad73f32651fa6cf6 100644 (file)
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *       $Header: /cvsroot/pgsql/src/backend/parser/keywords.c,v 1.20 1997/10/25 05:44:11 thomas Exp $
+ *       $Header: /cvsroot/pgsql/src/backend/parser/keywords.c,v 1.21 1997/10/28 14:56:10 vadim Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -104,6 +104,7 @@ static ScanKeyword ScanKeywords[] = {
        {"function", FUNCTION},
        {"grant", GRANT},
        {"group", GROUP},
+       {"handler", HANDLER},
        {"having", HAVING},
        {"heavy", HEAVY},
        {"hour", HOUR_P},
@@ -119,6 +120,7 @@ static ScanKeyword ScanKeywords[] = {
        {"isnull", ISNULL},
        {"join", JOIN},
        {"key", KEY},
+       {"lancompiler", LANCOMPILER},
        {"language", LANGUAGE},
        {"leading", LEADING},
        {"left", LEFT},
@@ -156,6 +158,7 @@ static ScanKeyword ScanKeywords[] = {
        {"precision", PRECISION},
        {"primary", PRIMARY},
        {"privileges", PRIVILEGES},
+       {"procedural", PROCEDURAL},
        {"procedure", PROCEDURE},
        {"public", PUBLIC},
        {"purge", PURGE},
@@ -188,6 +191,7 @@ static ScanKeyword ScanKeywords[] = {
        {"trigger", TRIGGER},
        {"trim", TRIM},
        {"true", TRUE_P},
+       {"trusted", TRUSTED},
        {"type", TYPE_P},
        {"union", UNION},
        {"unique", UNIQUE},
index 50013c8f7f1ca2901022a04029a0b77438d6030b..1fd20eb986a9c66d87736be6dc1301ee57395e1b 100644 (file)
@@ -9,7 +9,7 @@
  *
  *
  * IDENTIFICATION
- *       $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.26 1997/10/25 05:34:07 thomas Exp $
+ *       $Header: /cvsroot/pgsql/src/backend/tcop/utility.c,v 1.27 1997/10/28 14:57:24 vadim Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -35,6 +35,7 @@
 #include "commands/recipe.h"
 #include "commands/explain.h"
 #include "commands/trigger.h"
+#include "commands/proclang.h"
 
 #include "nodes/parsenodes.h"
 #include "../backend/parser/parse.h"
@@ -75,7 +76,7 @@
  * ----------------
  */
 void
-ProcessUtility(Node *parsetree,
+ProcessUtility(Node * parsetree,
                           CommandDest dest)
 {
        char       *commandTag = NULL;
@@ -149,8 +150,8 @@ ProcessUtility(Node *parsetree,
                                 */
 
                                count = stmt->howMany;
-                               PerformPortalFetch(portalName, forward, count, commandTag, 
-                                       (stmt->ismove) ? None : dest);  /* /dev/null for MOVE */
+                               PerformPortalFetch(portalName, forward, count, commandTag,
+                                                                  (stmt->ismove) ? None : dest);               /* /dev/null for MOVE */
                        }
                        break;
 
@@ -718,6 +719,23 @@ ProcessUtility(Node *parsetree,
                        DropTrigger((DropTrigStmt *) parsetree);
                        break;
 
+                       /*
+                        * ************* PROCEDURAL LANGUAGE statements *****************
+                        */
+               case T_CreatePLangStmt:
+                       commandTag = "CREATE";
+                       CHECK_IF_ABORTED();
+
+                       CreateProceduralLanguage((CreatePLangStmt *) parsetree);
+                       break;
+
+               case T_DropPLangStmt:
+                       commandTag = "DROP";
+                       CHECK_IF_ABORTED();
+
+                       DropProceduralLanguage((DropPLangStmt *) parsetree);
+                       break;
+
                        /*
                         * ******************************** default ********************************
                         *
index 1d7c8d23568ef95c5564fd4445a71fc4f8beab87..409372e8ce2f1a41346246bed0b2aa4c2bc632fb 100644 (file)
@@ -8,7 +8,7 @@
 #
 #
 # IDENTIFICATION
-#    $Header: /cvsroot/pgsql/src/backend/utils/Attic/Gen_fmgrtab.sh.in,v 1.4 1997/07/28 00:55:41 momjian Exp $
+#    $Header: /cvsroot/pgsql/src/backend/utils/Attic/Gen_fmgrtab.sh.in,v 1.5 1997/10/28 15:02:24 vadim Exp $
 #
 # NOTES
 #    Passes any -D options on to cpp prior to generating the list
@@ -81,7 +81,7 @@ cat > $HFILE <<FuNkYfMgRsTuFf
  *
  * Copyright (c) 1994, Regents of the University of California
  *
- * $Id: Gen_fmgrtab.sh.in,v 1.4 1997/07/28 00:55:41 momjian Exp $
+ * $Id: Gen_fmgrtab.sh.in,v 1.5 1997/10/28 15:02:24 vadim Exp $
  *
  * NOTES
  *     ******************************
@@ -114,6 +114,8 @@ typedef struct {
 /*
  * defined in fmgr.c
  */
+extern char *fmgr_pl(Oid func_id, int n_arguments, FmgrValues *values,
+       bool *isNull);
 extern char *fmgr_c(func_ptr user_fn, Oid func_id, int n_arguments,
        FmgrValues *values, bool *isNull);
 extern void fmgr_info(Oid procedureId, func_ptr *function, int *nargs);
@@ -175,7 +177,7 @@ cat > $TABCFILE <<FuNkYfMgRtAbStUfF
  *
  *
  * IDENTIFICATION
- *    $Header: /cvsroot/pgsql/src/backend/utils/Attic/Gen_fmgrtab.sh.in,v 1.4 1997/07/28 00:55:41 momjian Exp $
+ *    $Header: /cvsroot/pgsql/src/backend/utils/Attic/Gen_fmgrtab.sh.in,v 1.5 1997/10/28 15:02:24 vadim Exp $
  *
  * NOTES
  *
index 149e99888ea5de1922104e6f0be793ca084d7c14..f12e17f03d8163a9e12d4288d2549b36d4c5b510 100644 (file)
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *       $Header: /cvsroot/pgsql/src/backend/utils/cache/syscache.c,v 1.9 1997/09/18 20:22:25 momjian Exp $
+ *       $Header: /cvsroot/pgsql/src/backend/utils/cache/syscache.c,v 1.10 1997/10/28 15:03:06 vadim Exp $
  *
  * NOTES
  *       These routines allow the parser/planner/executor to perform
@@ -57,7 +57,7 @@ extern bool AMI_OVERRIDE;             /* XXX style */
 #include "utils/syscache.h"
 #include "catalog/indexing.h"
 
-typedef HeapTuple (*ScanFunc) ();
+typedef                HeapTuple(*ScanFunc) ();
 
 /* ----------------
  *             Warning:  cacheinfo[] below is changed, then be sure and
@@ -179,7 +179,7 @@ static struct cachedesc cacheinfo[] = {
                        0,
                        0,
                0},
-               offsetof(TypeTupleFormData, typalign) +sizeof(char),
+               offsetof(TypeTupleFormData, typalign) + sizeof(char),
                TypeNameIndex,
        TypeNameIndexScan},
        {TypeRelationName,                      /* TYPOID */
@@ -316,7 +316,16 @@ static struct cachedesc cacheinfo[] = {
                0},
                sizeof(FormData_pg_opclass),
                NULL,
-       (ScanFunc) NULL}
+       (ScanFunc) NULL},
+       {LanguageRelationName,          /* LANOID */
+               1,
+               {ObjectIdAttributeNumber,
+                       0,
+                       0,
+               0},
+               offsetof(FormData_pg_language, lancompiler),
+               NULL,
+       NULL}
 };
 
 static struct catcache *SysCache[
@@ -383,7 +392,7 @@ InitCatalogCache()
  * XXX The tuple that is returned is NOT supposed to be pfree'd!
  */
 HeapTuple
-SearchSysCacheTuple(int cacheId,/* cache selection code */
+SearchSysCacheTuple(int cacheId,               /* cache selection code */
                                        Datum key1,
                                        Datum key2,
                                        Datum key3,
@@ -562,7 +571,7 @@ SearchSysCacheGetAttribute(int cacheId,
                : attributeLength;              /* fixed length */
 
                tmp = (char *) palloc(size);
-               memmove(tmp, (void *)attributeValue, size);
+               memmove(tmp, (void *) attributeValue, size);
                returnValue = (void *) tmp;
        }
 
index 939341a3ded4eb535dc35618aaf55a759f4b362f..a225c982555e3589e93c52c7f6a73e5f462a1cd1 100644 (file)
@@ -7,7 +7,7 @@
  *
  *
  * IDENTIFICATION
- *       $Header: /cvsroot/pgsql/src/backend/utils/fmgr/fmgr.c,v 1.6 1997/09/08 21:49:07 momjian Exp $
+ *       $Header: /cvsroot/pgsql/src/backend/utils/fmgr/fmgr.c,v 1.7 1997/10/28 15:05:32 vadim Exp $
  *
  *-------------------------------------------------------------------------
  */
 
 #include "utils/elog.h"
 
+#include "nodes/parsenodes.h"
+#include "commands/trigger.h"
+
+
+char      *
+fmgr_pl(Oid func_id,
+               int n_arguments,
+               FmgrValues * values,
+               bool * isNull)
+{
+       HeapTuple       procedureTuple;
+       HeapTuple       languageTuple;
+       Form_pg_proc procedureStruct;
+       Form_pg_language languageStruct;
+       func_ptr        plcall_fn;
+       int                     plcall_nargs;
+
+       /* Fetch the pg_proc tuple from the syscache */
+       procedureTuple = SearchSysCacheTuple(PROOID,
+                                                                                ObjectIdGetDatum(func_id),
+                                                                                0, 0, 0);
+       if (!HeapTupleIsValid(procedureTuple))
+       {
+               elog(WARN, "fmgr_pl(): Cache lookup of procedure %ld failed.",
+                        ObjectIdGetDatum(func_id));
+       }
+       procedureStruct = (Form_pg_proc) GETSTRUCT(procedureTuple);
+
+       /* Fetch the pg_language tuple from the syscache */
+       languageTuple = SearchSysCacheTuple(LANOID,
+                                                         ObjectIdGetDatum(procedureStruct->prolang),
+                                                                               0, 0, 0);
+       if (!HeapTupleIsValid(languageTuple))
+       {
+               elog(WARN, "fmgr_pl(): Cache lookup of language %ld for procedure %ld failed.",
+                        ObjectIdGetDatum(procedureStruct->prolang),
+                        ObjectIdGetDatum(func_id));
+       }
+       languageStruct = (Form_pg_language) GETSTRUCT(languageTuple);
+
+       /* Get the function pointer for the PL call handler */
+       fmgr_info(languageStruct->lanplcallfoid, &plcall_fn, &plcall_nargs);
+       if (plcall_fn == NULL)
+       {
+               elog(WARN, "fmgr_pl(): failed to load PL handler for procedure %ld.",
+                        ObjectIdGetDatum(func_id));
+       }
+
+       /* Call the PL handler */
+       CurrentTriggerData = NULL;
+       return (*plcall_fn) (func_id,
+                                                n_arguments,
+                                                values,
+                                                isNull);
+}
+
 
 char      *
 fmgr_c(func_ptr user_fn,
           Oid func_id,
           int n_arguments,
-          FmgrValues *values,
-          bool *isNull)
+          FmgrValues * values,
+          bool * isNull)
 {
        char       *returnValue = (char *) NULL;
 
@@ -43,11 +99,11 @@ fmgr_c(func_ptr user_fn,
        {
 
                /*
-                * a NULL func_ptr denotes untrusted function (in postgres 4.2).
-                * Untrusted functions have very limited use and is clumsy. We
-                * just get rid of it.
+                * a NULL func_ptr denotet untrusted function (in postgres 4.2).
+                * Untrusted functions have very limited use and is clumsy. We now
+                * use this feature for procedural languages.
                 */
-               elog(WARN, "internal error: untrusted function not supported.");
+               return fmgr_pl(func_id, n_arguments, values, isNull);
        }
 
        switch (n_arguments)
@@ -115,12 +171,14 @@ fmgr_c(func_ptr user_fn,
 }
 
 void
-fmgr_info(Oid procedureId, func_ptr *function, int *nargs)
+fmgr_info(Oid procedureId, func_ptr * function, int *nargs)
 {
        func_ptr        user_fn = NULL;
        FmgrCall   *fcp;
        HeapTuple       procedureTuple;
        FormData_pg_proc *procedureStruct;
+       HeapTuple       languageTuple;
+       Form_pg_language languageStruct;
        Oid                     language;
 
        if (!(fcp = fmgr_isbuiltin(procedureId)))
@@ -158,8 +216,35 @@ fmgr_info(Oid procedureId, func_ptr *function, int *nargs)
                                *nargs = procedureStruct->pronargs;
                                break;
                        default:
-                               elog(WARN, "fmgr_info: function %d: unknown language %d",
-                                        procedureId, language);
+
+                               /*
+                                * Might be a created procedural language Lookup the
+                                * syscache for the language and check the lanispl flag If
+                                * this is the case, we return a NULL function pointer and
+                                * the number of arguments from the procedure.
+                                */
+                               languageTuple = SearchSysCacheTuple(LANOID,
+                                                         ObjectIdGetDatum(procedureStruct->prolang),
+                                                                                                       0, 0, 0);
+                               if (!HeapTupleIsValid(languageTuple))
+                               {
+                                       elog(WARN, "fmgr_info: %s %ld",
+                                                "Cache lookup for language %d failed",
+                                                ObjectIdGetDatum(procedureStruct->prolang));
+                               }
+                               languageStruct = (Form_pg_language)
+                                       GETSTRUCT(languageTuple);
+                               if (languageStruct->lanispl)
+                               {
+                                       user_fn = (func_ptr) NULL;
+                                       *nargs = procedureStruct->pronargs;
+                               }
+                               else
+                               {
+                                       elog(WARN, "fmgr_info: function %d: unknown language %d",
+                                                procedureId, language);
+                               }
+                               break;
                }
        }
        else
@@ -252,7 +337,7 @@ fmgr_ptr(func_ptr user_fn, Oid func_id,...)
  * to fmgr_c().
  */
 char      *
-fmgr_array_args(Oid procedureId, int nargs, char *args[], bool *isNull)
+fmgr_array_args(Oid procedureId, int nargs, char *args[], bool * isNull)
 {
        func_ptr        user_fn;
        int                     true_arguments;
index 8c8490b4861d43aa09ee8e5a78a01ddcb1758c2d..d666688cb40cfced76127a85c85a9daaa880a293 100644 (file)
@@ -7,7 +7,7 @@
  *
  * Copyright (c) 1994, Regents of the University of California
  *
- * $Id: pg_language.h,v 1.4 1997/09/08 02:35:16 momjian Exp $
+ * $Id: pg_language.h,v 1.5 1997/10/28 15:08:05 vadim Exp $
  *
  * NOTES
  *       the genbki.sh script reads this file and generates .bki
@@ -33,6 +33,9 @@
 CATALOG(pg_language)
 {
        NameData        lanname;
+       bool            lanispl;                /* Is a procedural language */
+       bool            lanpltrusted;   /* PL is trusted */
+       Oid                     lanplcallfoid;  /* Call handler for PL */
        text            lancompiler;    /* VARIABLE LENGTH FIELD */
 } FormData_pg_language;
 
@@ -47,21 +50,24 @@ typedef FormData_pg_language *Form_pg_language;
  *             compiler constants for pg_language
  * ----------------
  */
-#define Natts_pg_language                              2
+#define Natts_pg_language                              5
 #define Anum_pg_language_lanname               1
-#define Anum_pg_language_lancompiler   2
+#define Anum_pg_language_lanispl               2
+#define Anum_pg_language_lanpltrusted          3
+#define Anum_pg_language_lanplcallfoid         4
+#define Anum_pg_language_lancompiler           5
 
 /* ----------------
  *             initial contents of pg_language
  * ----------------
  */
 
-DATA(insert OID = 11 ( internal "n/a" ));
+DATA(insert OID = 11 ( internal f 0 0 "n/a" ));
 #define INTERNALlanguageId 11
-DATA(insert OID = 12 ( lisp "/usr/ucb/liszt" ));
-DATA(insert OID = 13 ( "C" "/bin/cc" ));
+DATA(insert OID = 12 ( lisp f 0 0 "/usr/ucb/liszt" ));
+DATA(insert OID = 13 ( "C" f 0 0 "/bin/cc" ));
 #define ClanguageId 13
-DATA(insert OID = 14 ( "sql" "postgres"));
+DATA(insert OID = 14 ( "sql" f 0 0 "postgres"));
 #define SQLlanguageId 14
 
 
diff --git a/src/include/commands/proclang.h b/src/include/commands/proclang.h
new file mode 100644 (file)
index 0000000..af6182c
--- /dev/null
@@ -0,0 +1,17 @@
+/*-------------------------------------------------------------------------
+ *
+ * proclang.h--
+ *       prototypes for proclang.c.
+ *
+ *
+ *-------------------------------------------------------------------------
+ */
+#ifndef PROCLANG_H
+#define PROCLANG_H
+
+#include <nodes/parsenodes.h>
+
+extern void CreateProceduralLanguage(CreatePLangStmt * stmt);
+extern void DropProceduralLanguage(DropPLangStmt * stmt);
+
+#endif                                                 /* PROCLANG_H */
index f60e39d79143084840d7b228aefe8b01e1432091..152a1cdd28e2ed548233f8ed815a33c485b4fb72 100644 (file)
@@ -6,7 +6,7 @@
  *
  * Copyright (c) 1994, Regents of the University of California
  *
- * $Id: nodes.h,v 1.15 1997/09/29 06:01:44 vadim Exp $
+ * $Id: nodes.h,v 1.16 1997/10/28 15:10:37 vadim Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -185,6 +185,8 @@ typedef enum NodeTag
        T_VariableResetStmt,
        T_CreateTrigStmt,
        T_DropTrigStmt,
+       T_CreatePLangStmt,
+       T_DropPLangStmt,
 
        T_A_Expr = 700,
        T_Attr,
index 0bff16711c83bed18c26bf886a6dc98ca941542f..6e9e49b1c016fa2285bc724220976e99ff87fba2 100644 (file)
@@ -6,7 +6,7 @@
  *
  * Copyright (c) 1994, Regents of the University of California
  *
- * $Id: parsenodes.h,v 1.28 1997/09/29 06:01:46 vadim Exp $
+ * $Id: parsenodes.h,v 1.29 1997/10/28 15:10:39 vadim Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -64,7 +64,7 @@ typedef struct Query
        List       *join_relation_list_;        /* list of relations generated by
                                                                                 * joins */
        bool            query_is_archival_;             /* archival query flag */
-} Query;
+}                      Query;
 
 
 /*****************************************************************************
@@ -98,7 +98,7 @@ typedef struct ChangeACLStmt
        struct AclItem *aclitem;
        unsigned        modechg;
        List       *relNames;
-} ChangeACLStmt;
+}                      ChangeACLStmt;
 
 /* ----------------------
  *             Close Portal Statement
@@ -108,7 +108,7 @@ typedef struct ClosePortalStmt
 {
        NodeTag         type;
        char       *portalname;         /* name of the portal (cursor) */
-} ClosePortalStmt;
+}                      ClosePortalStmt;
 
 /* ----------------------
  *             Copy Statement
@@ -123,7 +123,7 @@ typedef struct CopyStmt
        int                     direction;              /* TO or FROM */
        char       *filename;           /* if NULL, use stdin/stdout */
        char       *delimiter;          /* delimiter character, \t by default */
-} CopyStmt;
+}                      CopyStmt;
 
 /* ----------------------
  *             Create Table Statement
@@ -145,19 +145,19 @@ typedef struct CreateStmt
        int                     location;               /* smgrid (-1 if none) */
        int                     archiveLoc;             /* smgrid (-1 if none) */
        List       *constraints;        /* list of constraints (ConstaintDef) */
-} CreateStmt;
+}                      CreateStmt;
 
 typedef enum ConstrType
 {
        CONSTR_NONE, CONSTR_CHECK       /* type of constaints */
-} ConstrType;
+}                      ConstrType;
 
 typedef struct ConstraintDef
 {
        ConstrType      type;
        char       *name;                       /* name */
        void       *def;                        /* definition */
-} ConstraintDef;
+}                      ConstraintDef;
 
 /* ----------------------
  *             Create/Drop TRIGGER Statements
@@ -178,14 +178,35 @@ typedef struct CreateTrigStmt
        char       *text;                       /* AS 'text' */
        List       *attr;                       /* UPDATE OF a, b,... (NI) or NULL */
        char       *when;                       /* WHEN 'a > 10 ...' (NI) or NULL */
-} CreateTrigStmt;
+}                      CreateTrigStmt;
 
 typedef struct DropTrigStmt
 {
        NodeTag         type;
        char       *trigname;           /* TRIGGER' name */
        char       *relname;            /* triggered relation */
-} DropTrigStmt;
+}                      DropTrigStmt;
+
+
+/* ----------------------
+ *             Create/Drop PROCEDURAL LANGUAGE Statement
+ * ----------------------
+ */
+typedef struct CreatePLangStmt
+{
+       NodeTag         type;
+       char       *plname;                     /* PL name */
+       char       *plhandler;          /* PL call handler function */
+       char       *plcompiler;         /* lancompiler text */
+       bool            pltrusted;              /* PL is trusted */
+}                      CreatePLangStmt;
+
+typedef struct DropPLangStmt
+{
+       NodeTag         type;
+       char       *plname;                     /* PL name */
+}                      DropPLangStmt;
+
 
 /* ----------------------
  *             Create SEQUENCE Statement
@@ -197,7 +218,7 @@ typedef struct CreateSeqStmt
        NodeTag         type;
        char       *seqname;            /* the relation to create */
        List       *options;
-} CreateSeqStmt;
+}                      CreateSeqStmt;
 
 /* ----------------------
  *             Create Version Statement
@@ -210,7 +231,7 @@ typedef struct VersionStmt
        int                     direction;              /* FORWARD | BACKWARD */
        char       *fromRelname;        /* relation to create a version */
        char       *date;                       /* date of the snapshot */
-} VersionStmt;
+}                      VersionStmt;
 
 /* ----------------------
  *             Create {Operator|Type|Aggregate} Statement
@@ -222,7 +243,7 @@ typedef struct DefineStmt
        int                     defType;                /* OPERATOR|P_TYPE|AGGREGATE */
        char       *defname;
        List       *definition;         /* a list of DefElem */
-} DefineStmt;
+}                      DefineStmt;
 
 /* ----------------------
  *             Drop Table Statement
@@ -233,7 +254,7 @@ typedef struct DestroyStmt
        NodeTag         type;
        List       *relNames;           /* relations to be dropped */
        bool            sequence;
-} DestroyStmt;
+}                      DestroyStmt;
 
 /* ----------------------
  *             Extend Index Statement
@@ -246,7 +267,7 @@ typedef struct ExtendStmt
        Node       *whereClause;        /* qualifications */
        List       *rangetable;         /* range table, filled in by
                                                                 * transformStmt() */
-} ExtendStmt;
+}                      ExtendStmt;
 
 /* ----------------------
  *             Begin Recipe Statement
@@ -256,7 +277,7 @@ typedef struct RecipeStmt
 {
        NodeTag         type;
        char       *recipeName;         /* name of the recipe */
-} RecipeStmt;
+}                      RecipeStmt;
 
 /* ----------------------
  *             Fetch Statement
@@ -269,7 +290,7 @@ typedef struct FetchStmt
        int                     howMany;                /* amount to fetch ("ALL" --> 0) */
        char       *portalname;         /* name of portal (cursor) */
        bool            ismove;                 /* TRUE if MOVE */
-} FetchStmt;
+}                      FetchStmt;
 
 /* ----------------------
  *             Create Index Statement
@@ -288,7 +309,7 @@ typedef struct IndexStmt
                                                                 * transformStmt() */
        bool       *lossy;                      /* is index lossy? */
        bool            unique;                 /* is index unique? */
-} IndexStmt;
+}                      IndexStmt;
 
 /* ----------------------
  *             Create Function Statement
@@ -305,7 +326,7 @@ typedef struct ProcedureStmt
        List       *withClause;         /* a list of ParamString */
        char       *as;                         /* the SQL statement or filename */
        char       *language;           /* C or SQL */
-} ProcedureStmt;
+}                      ProcedureStmt;
 
 /* ----------------------
  *             Purge Statement
@@ -317,7 +338,7 @@ typedef struct PurgeStmt
        char       *relname;            /* relation to purge */
        char       *beforeDate;         /* purge before this date */
        char       *afterDate;          /* purge after this date */
-} PurgeStmt;
+}                      PurgeStmt;
 
 /* ----------------------
  *             Drop Aggregate Statement
@@ -328,7 +349,7 @@ typedef struct RemoveAggrStmt
        NodeTag         type;
        char       *aggname;            /* aggregate to drop */
        char       *aggtype;            /* for this type */
-} RemoveAggrStmt;
+}                      RemoveAggrStmt;
 
 /* ----------------------
  *             Drop Function Statement
@@ -339,7 +360,7 @@ typedef struct RemoveFuncStmt
        NodeTag         type;
        char       *funcname;           /* function to drop */
        List       *args;                       /* types of the arguments */
-} RemoveFuncStmt;
+}                      RemoveFuncStmt;
 
 /* ----------------------
  *             Drop Operator Statement
@@ -350,7 +371,7 @@ typedef struct RemoveOperStmt
        NodeTag         type;
        char       *opname;                     /* operator to drop */
        List       *args;                       /* types of the arguments */
-} RemoveOperStmt;
+}                      RemoveOperStmt;
 
 /* ----------------------
  *             Drop {Type|Index|Rule|View} Statement
@@ -361,7 +382,7 @@ typedef struct RemoveStmt
        NodeTag         type;
        int                     removeType;             /* P_TYPE|INDEX|RULE|VIEW */
        char       *name;                       /* name to drop */
-} RemoveStmt;
+}                      RemoveStmt;
 
 /* ----------------------
  *             Alter Table Statement
@@ -376,7 +397,7 @@ typedef struct RenameStmt
                                                                 * the new name. Otherwise, rename this
                                                                 * column name. */
        char       *newname;            /* the new name */
-} RenameStmt;
+}                      RenameStmt;
 
 /* ----------------------
  *             Create Rule Statement
@@ -391,7 +412,7 @@ typedef struct RuleStmt
        struct Attr *object;            /* object affected */
        bool            instead;                /* is a 'do instead'? */
        List       *actions;            /* the action statements */
-} RuleStmt;
+}                      RuleStmt;
 
 /* ----------------------
  *             Notify Statement
@@ -401,7 +422,7 @@ typedef struct NotifyStmt
 {
        NodeTag         type;
        char       *relname;            /* relation to notify */
-} NotifyStmt;
+}                      NotifyStmt;
 
 /* ----------------------
  *             Listen Statement
@@ -411,7 +432,7 @@ typedef struct ListenStmt
 {
        NodeTag         type;
        char       *relname;            /* relation to listen on */
-} ListenStmt;
+}                      ListenStmt;
 
 /* ----------------------
  *             {Begin|Abort|End} Transaction Statement
@@ -421,7 +442,7 @@ typedef struct TransactionStmt
 {
        NodeTag         type;
        int                     command;                /* BEGIN|END|ABORT */
-} TransactionStmt;
+}                      TransactionStmt;
 
 /* ----------------------
  *             Create View Statement
@@ -432,7 +453,7 @@ typedef struct ViewStmt
        NodeTag         type;
        char       *viewname;           /* name of the view */
        Query      *query;                      /* the SQL statement */
-} ViewStmt;
+}                      ViewStmt;
 
 /* ----------------------
  *             Load Statement
@@ -442,7 +463,7 @@ typedef struct LoadStmt
 {
        NodeTag         type;
        char       *filename;           /* file to load */
-} LoadStmt;
+}                      LoadStmt;
 
 /* ----------------------
  *             Createdb Statement
@@ -452,7 +473,7 @@ typedef struct CreatedbStmt
 {
        NodeTag         type;
        char       *dbname;                     /* database to create */
-} CreatedbStmt;
+}                      CreatedbStmt;
 
 /* ----------------------
  *             Destroydb Statement
@@ -462,7 +483,7 @@ typedef struct DestroydbStmt
 {
        NodeTag         type;
        char       *dbname;                     /* database to drop */
-} DestroydbStmt;
+}                      DestroydbStmt;
 
 /* ----------------------
  *             Cluster Statement (support pbrown's cluster index implementation)
@@ -473,7 +494,7 @@ typedef struct ClusterStmt
        NodeTag         type;
        char       *relname;            /* relation being indexed */
        char       *indexname;          /* original index defined */
-} ClusterStmt;
+}                      ClusterStmt;
 
 /* ----------------------
  *             Vacuum Statement
@@ -486,7 +507,7 @@ typedef struct VacuumStmt
        bool            analyze;                /* analyze data */
        char       *vacrel;                     /* table to vacuum */
        List       *va_spec;            /* columns to analyse */
-} VacuumStmt;
+}                      VacuumStmt;
 
 /* ----------------------
  *             Explain Statement
@@ -497,7 +518,7 @@ typedef struct ExplainStmt
        NodeTag         type;
        Query      *query;                      /* the query */
        bool            verbose;                /* print plan info */
-} ExplainStmt;
+}                      ExplainStmt;
 
 /* ----------------------
  * Set Statement
@@ -509,7 +530,7 @@ typedef struct VariableSetStmt
        NodeTag         type;
        char       *name;
        char       *value;
-} VariableSetStmt;
+}                      VariableSetStmt;
 
 /* ----------------------
  * Show Statement
@@ -520,7 +541,7 @@ typedef struct VariableShowStmt
 {
        NodeTag         type;
        char       *name;
-} VariableShowStmt;
+}                      VariableShowStmt;
 
 /* ----------------------
  * Reset Statement
@@ -531,7 +552,7 @@ typedef struct VariableResetStmt
 {
        NodeTag         type;
        char       *name;
-} VariableResetStmt;
+}                      VariableResetStmt;
 
 
 /*****************************************************************************
@@ -561,7 +582,7 @@ typedef struct DeleteStmt
        NodeTag         type;
        char       *relname;            /* relation to delete from */
        Node       *whereClause;        /* qualifications */
-} DeleteStmt;
+}                      DeleteStmt;
 
 /* ----------------------
  *             Update Statement
@@ -574,7 +595,7 @@ typedef struct ReplaceStmt
        List       *targetList;         /* the target list (of ResTarget) */
        Node       *whereClause;        /* qualifications */
        List       *fromClause;         /* the from clause */
-} ReplaceStmt;
+}                      ReplaceStmt;
 
 /* ----------------------
  *             Create Cursor Statement
@@ -591,7 +612,7 @@ typedef struct CursorStmt
        Node       *whereClause;        /* qualifications */
        List       *groupClause;        /* group by clause */
        List       *sortClause;         /* sort clause (a list of SortGroupBy's) */
-} CursorStmt;
+}                      CursorStmt;
 
 /* ----------------------
  *             Select Statement
@@ -609,7 +630,7 @@ typedef struct RetrieveStmt
        Node       *havingClause;       /* having conditional-expression */
        List       *selectClause;       /* subselect parameters */
        List       *sortClause;         /* sort clause (a list of SortGroupBy's) */
-} RetrieveStmt;
+}                      RetrieveStmt;
 
 
 /****************************************************************************
@@ -628,7 +649,7 @@ typedef struct SubSelect
        Node       *whereClause;        /* qualifications */
        List       *groupClause;        /* group by clause */
        Node       *havingClause;       /* having conditional-expression */
-} SubSelect;
+}                      SubSelect;
 
 /*
  * TypeName - specifies a type in definitions
@@ -641,7 +662,7 @@ typedef struct TypeName
        bool            setof;                  /* is a set? */
        List       *arrayBounds;        /* array bounds */
        int                     typlen;                 /* length for char() and varchar() */
-} TypeName;
+}                      TypeName;
 
 /*
  * ParamNo - specifies a parameter reference
@@ -651,7 +672,7 @@ typedef struct ParamNo
        NodeTag         type;
        int                     number;                 /* the number of the parameter */
        TypeName   *typename;           /* the typecast */
-} ParamNo;
+}                      ParamNo;
 
 /*
  * A_Expr - binary expressions
@@ -702,7 +723,7 @@ typedef struct ColumnDef
        TypeName   *typename;           /* type of column */
        bool            is_not_null;    /* flag to NOT NULL constraint */
        char       *defval;                     /* default value of column */
-} ColumnDef;
+}                      ColumnDef;
 
 /*
  * Ident -
@@ -718,7 +739,7 @@ typedef struct Ident
        List       *indirection;        /* array references */
        bool            isRel;                  /* is a relation - filled in by
                                                                 * transformExpr() */
-} Ident;
+}                      Ident;
 
 /*
  * FuncCall - a function/aggregate invocation
@@ -728,7 +749,7 @@ typedef struct FuncCall
        NodeTag         type;
        char       *funcname;           /* name of function */
        List       *args;                       /* the arguments (list of exprs) */
-} FuncCall;
+}                      FuncCall;
 
 /*
  * A_Indices - array reference or bounds ([lidx:uidx] or [uidx])
@@ -751,7 +772,7 @@ typedef struct ResTarget
        List       *indirection;        /* array references */
        Node       *val;                        /* the value of the result (A_Expr or
                                                                 * Attr) (or A_Const) */
-} ResTarget;
+}                      ResTarget;
 
 /*
  * ParamString - used in with clauses
@@ -761,7 +782,7 @@ typedef struct ParamString
        NodeTag         type;
        char       *name;
        char       *val;
-} ParamString;
+}                      ParamString;
 
 /*
  * TimeRange - specifies a time range
@@ -771,7 +792,7 @@ typedef struct TimeRange
        NodeTag         type;
        char       *startDate;
        char       *endDate;            /* snapshot if NULL */
-} TimeRange;
+}                      TimeRange;
 
 /*
  * RelExpr - relation expressions
@@ -782,7 +803,7 @@ typedef struct RelExpr
        char       *relname;            /* the relation name */
        bool            inh;                    /* inheritance query */
        TimeRange  *timeRange;          /* the time range */
-} RelExpr;
+}                      RelExpr;
 
 /*
  * SortGroupBy - for order by clause
@@ -794,7 +815,7 @@ typedef struct SortGroupBy
        char       *range;
        char       *name;                       /* name of column to sort on */
        char       *useOp;                      /* operator to use */
-} SortGroupBy;
+}                      SortGroupBy;
 
 /*
  * RangeVar - range variable, used in from clauses
@@ -804,7 +825,7 @@ typedef struct RangeVar
        NodeTag         type;
        RelExpr    *relExpr;            /* the relation expression */
        char       *name;                       /* the name to be referenced (optional) */
-} RangeVar;
+}                      RangeVar;
 
 /*
  * IndexElem - index parameters (used in create index)
@@ -816,7 +837,7 @@ typedef struct IndexElem
        List       *args;                       /* if not NULL, function index */
        char       *class;
        TypeName   *tname;                      /* type of index's keys (optional) */
-} IndexElem;
+}                      IndexElem;
 
 /*
  * DefElem -
@@ -827,7 +848,7 @@ typedef struct DefElem
        NodeTag         type;
        char       *defname;
        Node       *arg;                        /* a (Value *) or a (TypeName *) */
-} DefElem;
+}                      DefElem;
 
 
 /****************************************************************************
@@ -847,7 +868,7 @@ typedef struct TargetEntry
        Resdom     *resdom;                     /* fjoin overload this to be a list?? */
        Fjoin      *fjoin;
        Node       *expr;                       /* can be a list too */
-} TargetEntry;
+}                      TargetEntry;
 
 /*
  * RangeTblEntry -
@@ -873,7 +894,7 @@ typedef struct RangeTblEntry
        bool            archive;                /* filled in by plan_archive */
        bool            inFromCl;               /* comes from From Clause */
        TimeQual        timeQual;               /* filled in by pg_plan */
-} RangeTblEntry;
+}                      RangeTblEntry;
 
 /*
  * SortClause -
@@ -884,7 +905,7 @@ typedef struct SortClause
        NodeTag         type;
        Resdom     *resdom;                     /* attributes in tlist to be sorted */
        Oid                     opoid;                  /* sort operators */
-} SortClause;
+}                      SortClause;
 
 /*
  * GroupClause -
@@ -895,6 +916,6 @@ typedef struct GroupClause
        NodeTag         type;
        TargetEntry *entry;                     /* attributes to group on */
        Oid                     grpOpoid;               /* the sort operator to use */
-} GroupClause;
+}                      GroupClause;
 
 #endif                                                 /* PARSENODES_H */
index 0dbf0e1c397337d1e07d3151b2bf315fe5cc60a2..951e12d6f3040aa1c81fa05a093e10558ff62b25 100644 (file)
@@ -6,7 +6,7 @@
  *
  * Copyright (c) 1994, Regents of the University of California
  *
- * $Id: rel.h,v 1.12 1997/09/08 21:55:16 momjian Exp $
+ * $Id: rel.h,v 1.13 1997/10/28 15:11:43 vadim Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -25,6 +25,7 @@ typedef struct Trigger
        char       *tgname;
        Oid                     tgfoid;
        func_ptr        tgfunc;
+       func_ptr        tgplfunc;
        int16           tgtype;
        int16           tgnargs;
        int16           tgattr[8];
index 54c42a198444d90c296d72f0f3c2412508caf08d..0e37771a67ea591753a5e137243d4d13bcffa80c 100644 (file)
@@ -6,7 +6,7 @@
  *
  * Copyright (c) 1994, Regents of the University of California
  *
- * $Id: syscache.h,v 1.7 1997/09/08 21:55:17 momjian Exp $
+ * $Id: syscache.h,v 1.8 1997/10/28 15:11:45 vadim Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -59,6 +59,7 @@
 #define REWRITENAME            25
 #define PROSRC                 26
 #define CLADEFTYPE             27
+#define LANOID                 28
 
 /* ----------------
  *             struct cachedesc:               information needed for a call to InitSysCache()