]> granicus.if.org Git - postgresql/blob - src/pl/plpython/plpython.c
Improve the recently-added support for properly pluralized error messages
[postgresql] / src / pl / plpython / plpython.c
1 /**********************************************************************
2  * plpython.c - python as a procedural language for PostgreSQL
3  *
4  *      $PostgreSQL: pgsql/src/pl/plpython/plpython.c,v 1.121 2009/06/04 18:33:08 tgl Exp $
5  *
6  *********************************************************************
7  */
8
9 #if defined(_MSC_VER) && defined(_DEBUG)
10 /* Python uses #pragma to bring in a non-default libpython on VC++ if
11  * _DEBUG is defined */
12 #undef _DEBUG
13 /* Also hide away errcode, since we load Python.h before postgres.h */
14 #define errcode __msvc_errcode
15 #include <Python.h>
16 #undef errcode
17 #define _DEBUG
18 #elif defined (_MSC_VER)
19 #define errcode __msvc_errcode
20 #include <Python.h>
21 #undef errcode
22 #else
23 #include <Python.h>
24 #endif
25
26 /*
27  * Py_ssize_t compat for Python <= 2.4
28  */
29 #if PY_VERSION_HEX < 0x02050000 && !defined(PY_SSIZE_T_MIN)
30 typedef int Py_ssize_t;
31
32 #define PY_SSIZE_T_MAX INT_MAX
33 #define PY_SSIZE_T_MIN INT_MIN
34 #endif
35
36 /*
37  * PyBool_FromLong is supported from 2.3.
38  */
39 #if PY_VERSION_HEX < 0x02030000
40 #define PyBool_FromLong(x) PyInt_FromLong(x)
41 #endif
42
43
44 #include "postgres.h"
45
46 /* system stuff */
47 #include <unistd.h>
48 #include <fcntl.h>
49
50 /* postgreSQL stuff */
51 #include "catalog/pg_proc.h"
52 #include "catalog/pg_type.h"
53 #include "commands/trigger.h"
54 #include "executor/spi.h"
55 #include "funcapi.h"
56 #include "fmgr.h"
57 #include "miscadmin.h"
58 #include "nodes/makefuncs.h"
59 #include "parser/parse_type.h"
60 #include "tcop/tcopprot.h"
61 #include "utils/builtins.h"
62 #include "utils/lsyscache.h"
63 #include "utils/memutils.h"
64 #include "utils/syscache.h"
65 #include "utils/typcache.h"
66
67 /* define our text domain for translations */
68 #undef TEXTDOMAIN
69 #define TEXTDOMAIN PG_TEXTDOMAIN("plpython")
70
71 #include <compile.h>
72 #include <eval.h>
73
74 PG_MODULE_MAGIC;
75
76 /* convert Postgresql Datum or tuple into a PyObject.
77  * input to Python.  Tuples are converted to dictionary
78  * objects.
79  */
80
81 typedef PyObject *(*PLyDatumToObFunc) (const char *);
82
83 typedef struct PLyDatumToOb
84 {
85         PLyDatumToObFunc func;
86         FmgrInfo        typfunc;                /* The type's output function */
87         Oid                     typoid;                 /* The OID of the type */
88         Oid                     typioparam;
89         bool            typbyval;
90 }       PLyDatumToOb;
91
92 typedef struct PLyTupleToOb
93 {
94         PLyDatumToOb *atts;
95         int                     natts;
96 }       PLyTupleToOb;
97
98 typedef union PLyTypeInput
99 {
100         PLyDatumToOb d;
101         PLyTupleToOb r;
102 }       PLyTypeInput;
103
104 /* convert PyObject to a Postgresql Datum or tuple.
105  * output from Python
106  */
107 typedef struct PLyObToDatum
108 {
109         FmgrInfo        typfunc;                /* The type's input function */
110         Oid                     typoid;                 /* The OID of the type */
111         Oid                     typioparam;
112         bool            typbyval;
113 }       PLyObToDatum;
114
115 typedef struct PLyObToTuple
116 {
117         PLyObToDatum *atts;
118         int                     natts;
119 }       PLyObToTuple;
120
121 typedef union PLyTypeOutput
122 {
123         PLyObToDatum d;
124         PLyObToTuple r;
125 }       PLyTypeOutput;
126
127 /* all we need to move Postgresql data to Python objects,
128  * and vis versa
129  */
130 typedef struct PLyTypeInfo
131 {
132         PLyTypeInput in;
133         PLyTypeOutput out;
134         int                     is_rowtype;
135
136         /*
137          * is_rowtype can be: -1  not known yet (initial state) 0  scalar datatype
138          * 1  rowtype 2  rowtype, but I/O functions not set up yet
139          */
140 }       PLyTypeInfo;
141
142
143 /* cached procedure data */
144 typedef struct PLyProcedure
145 {
146         char       *proname;            /* SQL name of procedure */
147         char       *pyname;                     /* Python name of procedure */
148         TransactionId fn_xmin;
149         ItemPointerData fn_tid;
150         bool            fn_readonly;
151         PLyTypeInfo result;                     /* also used to store info for trigger tuple
152                                                                  * type */
153         bool            is_setof;               /* true, if procedure returns result set */
154         PyObject   *setof;                      /* contents of result set. */
155         char      **argnames;           /* Argument names */
156         PLyTypeInfo args[FUNC_MAX_ARGS];
157         int                     nargs;
158         PyObject   *code;                       /* compiled procedure code */
159         PyObject   *statics;            /* data saved across calls, local scope */
160         PyObject   *globals;            /* data saved across calls, global scope */
161         PyObject   *me;                         /* PyCObject containing pointer to this
162                                                                  * PLyProcedure */
163 }       PLyProcedure;
164
165
166 /* Python objects */
167 typedef struct PLyPlanObject
168 {
169         PyObject_HEAD
170         void       *plan;                       /* return of an SPI_saveplan */
171         int                     nargs;
172         Oid                *types;
173         Datum      *values;
174         PLyTypeInfo *args;
175 }       PLyPlanObject;
176
177 typedef struct PLyResultObject
178 {
179         PyObject_HEAD
180         /* HeapTuple *tuples; */
181         PyObject * nrows;                       /* number of rows returned by query */
182         PyObject   *rows;                       /* data rows, or None if no data returned */
183         PyObject   *status;                     /* query status, SPI_OK_*, or SPI_ERR_* */
184 }       PLyResultObject;
185
186
187 /* function declarations */
188
189 /* Two exported functions: first is the magic telling Postgresql
190  * what function call interface it implements. Second is for
191  * initialization of the interpreter during library load.
192  */
193 Datum           plpython_call_handler(PG_FUNCTION_ARGS);
194 void            _PG_init(void);
195
196 PG_FUNCTION_INFO_V1(plpython_call_handler);
197
198 /* most of the remaining of the declarations, all static */
199
200 /* these should only be called once at the first call
201  * of plpython_call_handler.  initialize the python interpreter
202  * and global data.
203  */
204 static void PLy_init_interp(void);
205 static void PLy_init_plpy(void);
206
207 /* call PyErr_SetString with a vprint interface and translation support */
208 static void PLy_exception_set(PyObject *, const char *,...)
209 __attribute__((format(printf, 2, 3)));
210 /* same, with pluralized message */
211 static void PLy_exception_set_plural(PyObject *, const char *, const char *,
212                                                                          unsigned long n,...)
213 __attribute__((format(printf, 2, 5)))
214 __attribute__((format(printf, 3, 5)));
215
216 /* Get the innermost python procedure called from the backend */
217 static char *PLy_procedure_name(PLyProcedure *);
218
219 /* some utility functions */
220 static void PLy_elog(int, const char *,...)
221 __attribute__((format(printf, 2, 3)));
222 static char *PLy_traceback(int *);
223
224 static void *PLy_malloc(size_t);
225 static void *PLy_malloc0(size_t);
226 static char *PLy_strdup(const char *);
227 static void PLy_free(void *);
228
229 /* sub handlers for functions and triggers */
230 static Datum PLy_function_handler(FunctionCallInfo fcinfo, PLyProcedure *);
231 static HeapTuple PLy_trigger_handler(FunctionCallInfo fcinfo, PLyProcedure *);
232
233 static PyObject *PLy_function_build_args(FunctionCallInfo fcinfo, PLyProcedure *);
234 static void PLy_function_delete_args(PLyProcedure *);
235 static PyObject *PLy_trigger_build_args(FunctionCallInfo fcinfo, PLyProcedure *,
236                                            HeapTuple *);
237 static HeapTuple PLy_modify_tuple(PLyProcedure *, PyObject *,
238                                  TriggerData *, HeapTuple);
239
240 static PyObject *PLy_procedure_call(PLyProcedure *, char *, PyObject *);
241
242 static PLyProcedure *PLy_procedure_get(FunctionCallInfo fcinfo,
243                                   Oid tgreloid);
244
245 static PLyProcedure *PLy_procedure_create(HeapTuple procTup, Oid tgreloid,
246                                                                                   char *key);
247
248 static void PLy_procedure_compile(PLyProcedure *, const char *);
249 static char *PLy_procedure_munge_source(const char *, const char *);
250 static void PLy_procedure_delete(PLyProcedure *);
251
252 static void PLy_typeinfo_init(PLyTypeInfo *);
253 static void PLy_typeinfo_dealloc(PLyTypeInfo *);
254 static void PLy_output_datum_func(PLyTypeInfo *, HeapTuple);
255 static void PLy_output_datum_func2(PLyObToDatum *, HeapTuple);
256 static void PLy_input_datum_func(PLyTypeInfo *, Oid, HeapTuple);
257 static void PLy_input_datum_func2(PLyDatumToOb *, Oid, HeapTuple);
258 static void PLy_output_tuple_funcs(PLyTypeInfo *, TupleDesc);
259 static void PLy_input_tuple_funcs(PLyTypeInfo *, TupleDesc);
260
261 /* conversion functions */
262 static PyObject *PLyDict_FromTuple(PLyTypeInfo *, HeapTuple, TupleDesc);
263 static PyObject *PLyBool_FromString(const char *);
264 static PyObject *PLyFloat_FromString(const char *);
265 static PyObject *PLyInt_FromString(const char *);
266 static PyObject *PLyLong_FromString(const char *);
267 static PyObject *PLyString_FromString(const char *);
268
269 static HeapTuple PLyMapping_ToTuple(PLyTypeInfo *, PyObject *);
270 static HeapTuple PLySequence_ToTuple(PLyTypeInfo *, PyObject *);
271 static HeapTuple PLyObject_ToTuple(PLyTypeInfo *, PyObject *);
272
273 /*
274  * Currently active plpython function
275  */
276 static PLyProcedure *PLy_curr_procedure = NULL;
277
278 /*
279  * When a callback from Python into PG incurs an error, we temporarily store
280  * the error information here, and return NULL to the Python interpreter.
281  * Any further callback attempts immediately fail, and when the Python
282  * interpreter returns to the calling function, we re-throw the error (even if
283  * Python thinks it trapped the error and doesn't return NULL).  Eventually
284  * this ought to be improved to let Python code really truly trap the error,
285  * but that's more of a change from the pre-8.0 semantics than I have time for
286  * now --- it will only be possible if the callback query is executed inside a
287  * subtransaction.
288  */
289 static ErrorData *PLy_error_in_progress = NULL;
290
291 static PyObject *PLy_interp_globals = NULL;
292 static PyObject *PLy_interp_safe_globals = NULL;
293 static PyObject *PLy_procedure_cache = NULL;
294
295 /* Python exceptions */
296 static PyObject *PLy_exc_error = NULL;
297 static PyObject *PLy_exc_fatal = NULL;
298 static PyObject *PLy_exc_spi_error = NULL;
299
300 /* some globals for the python module */
301 static char PLy_plan_doc[] = {
302         "Store a PostgreSQL plan"
303 };
304
305 static char PLy_result_doc[] = {
306         "Results of a PostgreSQL query"
307 };
308
309
310 /*
311  * the function definitions
312  */
313
314 /*
315  * This routine is a crock, and so is everyplace that calls it.  The problem
316  * is that the cached form of plpython functions/queries is allocated permanently
317  * (mostly via malloc()) and never released until backend exit.  Subsidiary
318  * data structures such as fmgr info records therefore must live forever
319  * as well.  A better implementation would store all this stuff in a per-
320  * function memory context that could be reclaimed at need.  In the meantime,
321  * fmgr_info_cxt must be called specifying TopMemoryContext so that whatever
322  * it might allocate, and whatever the eventual function might allocate using
323  * fn_mcxt, will live forever too.
324  */
325 static void
326 perm_fmgr_info(Oid functionId, FmgrInfo *finfo)
327 {
328         fmgr_info_cxt(functionId, finfo, TopMemoryContext);
329 }
330
331 Datum
332 plpython_call_handler(PG_FUNCTION_ARGS)
333 {
334         Datum           retval;
335         PLyProcedure *save_curr_proc;
336         PLyProcedure *volatile proc = NULL;
337
338         if (SPI_connect() != SPI_OK_CONNECT)
339                 elog(ERROR, "SPI_connect failed");
340
341         save_curr_proc = PLy_curr_procedure;
342
343         PG_TRY();
344         {
345                 if (CALLED_AS_TRIGGER(fcinfo))
346                 {
347                         TriggerData *tdata = (TriggerData *) fcinfo->context;
348                         HeapTuple       trv;
349
350                         proc = PLy_procedure_get(fcinfo,
351                                                                          RelationGetRelid(tdata->tg_relation));
352                         PLy_curr_procedure = proc;
353                         trv = PLy_trigger_handler(fcinfo, proc);
354                         retval = PointerGetDatum(trv);
355                 }
356                 else
357                 {
358                         proc = PLy_procedure_get(fcinfo, InvalidOid);
359                         PLy_curr_procedure = proc;
360                         retval = PLy_function_handler(fcinfo, proc);
361                 }
362         }
363         PG_CATCH();
364         {
365                 PLy_curr_procedure = save_curr_proc;
366                 if (proc)
367                 {
368                         /* note: Py_DECREF needs braces around it, as of 2003/08 */
369                         Py_DECREF(proc->me);
370                 }
371                 PyErr_Clear();
372                 PG_RE_THROW();
373         }
374         PG_END_TRY();
375
376         PLy_curr_procedure = save_curr_proc;
377
378         Py_DECREF(proc->me);
379
380         return retval;
381 }
382
383 /* trigger and function sub handlers
384  *
385  * the python function is expected to return Py_None if the tuple is
386  * acceptable and unmodified.  Otherwise it should return a PyString
387  * object who's value is SKIP, or MODIFY.  SKIP means don't perform
388  * this action.  MODIFY means the tuple has been modified, so update
389  * tuple and perform action.  SKIP and MODIFY assume the trigger fires
390  * BEFORE the event and is ROW level.  postgres expects the function
391  * to take no arguments and return an argument of type trigger.
392  */
393 static HeapTuple
394 PLy_trigger_handler(FunctionCallInfo fcinfo, PLyProcedure * proc)
395 {
396         HeapTuple       rv = NULL;
397         PyObject   *volatile plargs = NULL;
398         PyObject   *volatile plrv = NULL;
399
400         PG_TRY();
401         {
402                 plargs = PLy_trigger_build_args(fcinfo, proc, &rv);
403                 plrv = PLy_procedure_call(proc, "TD", plargs);
404
405                 Assert(plrv != NULL);
406                 Assert(!PLy_error_in_progress);
407
408                 /*
409                  * Disconnect from SPI manager
410                  */
411                 if (SPI_finish() != SPI_OK_FINISH)
412                         elog(ERROR, "SPI_finish failed");
413
414                 /*
415                  * return of None means we're happy with the tuple
416                  */
417                 if (plrv != Py_None)
418                 {
419                         char       *srv;
420
421                         if (!PyString_Check(plrv))
422                                 ereport(ERROR,
423                                                 (errcode(ERRCODE_DATA_EXCEPTION),
424                                         errmsg("unexpected return value from trigger procedure"),
425                                                  errdetail("Expected None or a string.")));
426
427                         srv = PyString_AsString(plrv);
428                         if (pg_strcasecmp(srv, "SKIP") == 0)
429                                 rv = NULL;
430                         else if (pg_strcasecmp(srv, "MODIFY") == 0)
431                         {
432                                 TriggerData *tdata = (TriggerData *) fcinfo->context;
433
434                                 if (TRIGGER_FIRED_BY_INSERT(tdata->tg_event) ||
435                                         TRIGGER_FIRED_BY_UPDATE(tdata->tg_event))
436                                         rv = PLy_modify_tuple(proc, plargs, tdata, rv);
437                                 else
438                                         ereport(WARNING,
439                                                         (errmsg("PL/Python trigger function returned \"MODIFY\" in a DELETE trigger -- ignored")));
440                         }
441                         else if (pg_strcasecmp(srv, "OK") != 0)
442                         {
443                                 /*
444                                  * accept "OK" as an alternative to None; otherwise, raise an
445                                  * error
446                                  */
447                                 ereport(ERROR,
448                                                 (errcode(ERRCODE_DATA_EXCEPTION),
449                                         errmsg("unexpected return value from trigger procedure"),
450                                                  errdetail("Expected None, \"OK\", \"SKIP\", or \"MODIFY\".")));
451                         }
452                 }
453         }
454         PG_CATCH();
455         {
456                 Py_XDECREF(plargs);
457                 Py_XDECREF(plrv);
458
459                 PG_RE_THROW();
460         }
461         PG_END_TRY();
462
463         Py_DECREF(plargs);
464         Py_DECREF(plrv);
465
466         return rv;
467 }
468
469 static HeapTuple
470 PLy_modify_tuple(PLyProcedure * proc, PyObject * pltd, TriggerData *tdata,
471                                  HeapTuple otup)
472 {
473         PyObject   *volatile plntup;
474         PyObject   *volatile plkeys;
475         PyObject   *volatile platt;
476         PyObject   *volatile plval;
477         PyObject   *volatile plstr;
478         HeapTuple       rtup;
479         int                     natts,
480                                 i,
481                                 attn,
482                                 atti;
483         int                *volatile modattrs;
484         Datum      *volatile modvalues;
485         char       *volatile modnulls;
486         TupleDesc       tupdesc;
487
488         plntup = plkeys = platt = plval = plstr = NULL;
489         modattrs = NULL;
490         modvalues = NULL;
491         modnulls = NULL;
492
493         PG_TRY();
494         {
495                 if ((plntup = PyDict_GetItemString(pltd, "new")) == NULL)
496                         ereport(ERROR, 
497                                         (errmsg("TD[\"new\"] deleted, cannot modify row")));
498                 if (!PyDict_Check(plntup))
499                         ereport(ERROR,
500                                         (errmsg("TD[\"new\"] is not a dictionary")));
501                 Py_INCREF(plntup);
502
503                 plkeys = PyDict_Keys(plntup);
504                 natts = PyList_Size(plkeys);
505
506                 modattrs = (int *) palloc(natts * sizeof(int));
507                 modvalues = (Datum *) palloc(natts * sizeof(Datum));
508                 modnulls = (char *) palloc(natts * sizeof(char));
509
510                 tupdesc = tdata->tg_relation->rd_att;
511
512                 for (i = 0; i < natts; i++)
513                 {
514                         char       *src;
515
516                         platt = PyList_GetItem(plkeys, i);
517                         if (!PyString_Check(platt))
518                                 ereport(ERROR,
519                                                 (errmsg("name of TD[\"new\"] attribute at ordinal position %d is not a string", i)));
520                         attn = SPI_fnumber(tupdesc, PyString_AsString(platt));
521                         if (attn == SPI_ERROR_NOATTRIBUTE)
522                                 ereport(ERROR,
523                                                 (errmsg("key \"%s\" found in TD[\"new\"] does not exist as a column in the triggering row",
524                                                                 PyString_AsString(platt))));
525                         atti = attn - 1;
526
527                         plval = PyDict_GetItem(plntup, platt);
528                         if (plval == NULL)
529                                 elog(FATAL, "Python interpreter is probably corrupted");
530
531                         Py_INCREF(plval);
532
533                         modattrs[i] = attn;
534
535                         if (tupdesc->attrs[atti]->attisdropped)
536                         {
537                                 modvalues[i] = (Datum) 0;
538                                 modnulls[i] = 'n';
539                         }
540                         else if (plval != Py_None)
541                         {
542                                 plstr = PyObject_Str(plval);
543                                 if (!plstr)
544                                         PLy_elog(ERROR, "could not compute string representation of Python object in PL/Python function \"%s\" while modifying trigger row",
545                                                          proc->proname);
546                                 src = PyString_AsString(plstr);
547
548                                 modvalues[i] =
549                                         InputFunctionCall(&proc->result.out.r.atts[atti].typfunc,
550                                                                           src,
551                                                                         proc->result.out.r.atts[atti].typioparam,
552                                                                           tupdesc->attrs[atti]->atttypmod);
553                                 modnulls[i] = ' ';
554
555                                 Py_DECREF(plstr);
556                                 plstr = NULL;
557                         }
558                         else
559                         {
560                                 modvalues[i] =
561                                         InputFunctionCall(&proc->result.out.r.atts[atti].typfunc,
562                                                                           NULL,
563                                                                         proc->result.out.r.atts[atti].typioparam,
564                                                                           tupdesc->attrs[atti]->atttypmod);
565                                 modnulls[i] = 'n';
566                         }
567
568                         Py_DECREF(plval);
569                         plval = NULL;
570                 }
571
572                 rtup = SPI_modifytuple(tdata->tg_relation, otup, natts,
573                                                            modattrs, modvalues, modnulls);
574                 if (rtup == NULL)
575                         elog(ERROR, "SPI_modifytuple failed: error %d", SPI_result);
576         }
577         PG_CATCH();
578         {
579                 Py_XDECREF(plntup);
580                 Py_XDECREF(plkeys);
581                 Py_XDECREF(plval);
582                 Py_XDECREF(plstr);
583
584                 if (modnulls)
585                         pfree(modnulls);
586                 if (modvalues)
587                         pfree(modvalues);
588                 if (modattrs)
589                         pfree(modattrs);
590
591                 PG_RE_THROW();
592         }
593         PG_END_TRY();
594
595         Py_DECREF(plntup);
596         Py_DECREF(plkeys);
597
598         pfree(modattrs);
599         pfree(modvalues);
600         pfree(modnulls);
601
602         return rtup;
603 }
604
605 static PyObject *
606 PLy_trigger_build_args(FunctionCallInfo fcinfo, PLyProcedure * proc, HeapTuple *rv)
607 {
608         TriggerData *tdata = (TriggerData *) fcinfo->context;
609         PyObject   *pltname,
610                            *pltevent,
611                            *pltwhen,
612                            *pltlevel,
613                            *pltrelid,
614                            *plttablename,
615                            *plttableschema;
616         PyObject   *pltargs,
617                            *pytnew,
618                            *pytold;
619         PyObject   *volatile pltdata = NULL;
620         char       *stroid;
621
622         PG_TRY();
623         {
624                 pltdata = PyDict_New();
625                 if (!pltdata)
626                         PLy_elog(ERROR, "could not create new dictionary while building trigger arguments");
627
628                 pltname = PyString_FromString(tdata->tg_trigger->tgname);
629                 PyDict_SetItemString(pltdata, "name", pltname);
630                 Py_DECREF(pltname);
631
632                 stroid = DatumGetCString(DirectFunctionCall1(oidout,
633                                                            ObjectIdGetDatum(tdata->tg_relation->rd_id)));
634                 pltrelid = PyString_FromString(stroid);
635                 PyDict_SetItemString(pltdata, "relid", pltrelid);
636                 Py_DECREF(pltrelid);
637                 pfree(stroid);
638
639                 stroid = SPI_getrelname(tdata->tg_relation);
640                 plttablename = PyString_FromString(stroid);
641                 PyDict_SetItemString(pltdata, "table_name", plttablename);
642                 Py_DECREF(plttablename);
643                 pfree(stroid);
644
645                 stroid = SPI_getnspname(tdata->tg_relation);
646                 plttableschema = PyString_FromString(stroid);
647                 PyDict_SetItemString(pltdata, "table_schema", plttableschema);
648                 Py_DECREF(plttableschema);
649                 pfree(stroid);
650
651
652                 if (TRIGGER_FIRED_BEFORE(tdata->tg_event))
653                         pltwhen = PyString_FromString("BEFORE");
654                 else if (TRIGGER_FIRED_AFTER(tdata->tg_event))
655                         pltwhen = PyString_FromString("AFTER");
656                 else
657                 {
658                         elog(ERROR, "unrecognized WHEN tg_event: %u", tdata->tg_event);
659                         pltwhen = NULL;         /* keep compiler quiet */
660                 }
661                 PyDict_SetItemString(pltdata, "when", pltwhen);
662                 Py_DECREF(pltwhen);
663
664                 if (TRIGGER_FIRED_FOR_ROW(tdata->tg_event))
665                 {
666                         pltlevel = PyString_FromString("ROW");
667                         PyDict_SetItemString(pltdata, "level", pltlevel);
668                         Py_DECREF(pltlevel);
669
670                         if (TRIGGER_FIRED_BY_INSERT(tdata->tg_event))
671                         {
672                                 pltevent = PyString_FromString("INSERT");
673
674                                 PyDict_SetItemString(pltdata, "old", Py_None);
675                                 pytnew = PLyDict_FromTuple(&(proc->result), tdata->tg_trigtuple,
676                                                                                    tdata->tg_relation->rd_att);
677                                 PyDict_SetItemString(pltdata, "new", pytnew);
678                                 Py_DECREF(pytnew);
679                                 *rv = tdata->tg_trigtuple;
680                         }
681                         else if (TRIGGER_FIRED_BY_DELETE(tdata->tg_event))
682                         {
683                                 pltevent = PyString_FromString("DELETE");
684
685                                 PyDict_SetItemString(pltdata, "new", Py_None);
686                                 pytold = PLyDict_FromTuple(&(proc->result), tdata->tg_trigtuple,
687                                                                                    tdata->tg_relation->rd_att);
688                                 PyDict_SetItemString(pltdata, "old", pytold);
689                                 Py_DECREF(pytold);
690                                 *rv = tdata->tg_trigtuple;
691                         }
692                         else if (TRIGGER_FIRED_BY_UPDATE(tdata->tg_event))
693                         {
694                                 pltevent = PyString_FromString("UPDATE");
695
696                                 pytnew = PLyDict_FromTuple(&(proc->result), tdata->tg_newtuple,
697                                                                                    tdata->tg_relation->rd_att);
698                                 PyDict_SetItemString(pltdata, "new", pytnew);
699                                 Py_DECREF(pytnew);
700                                 pytold = PLyDict_FromTuple(&(proc->result), tdata->tg_trigtuple,
701                                                                                    tdata->tg_relation->rd_att);
702                                 PyDict_SetItemString(pltdata, "old", pytold);
703                                 Py_DECREF(pytold);
704                                 *rv = tdata->tg_newtuple;
705                         }
706                         else
707                         {
708                                 elog(ERROR, "unrecognized OP tg_event: %u", tdata->tg_event);
709                                 pltevent = NULL;        /* keep compiler quiet */
710                         }
711
712                         PyDict_SetItemString(pltdata, "event", pltevent);
713                         Py_DECREF(pltevent);
714                 }
715                 else if (TRIGGER_FIRED_FOR_STATEMENT(tdata->tg_event))
716                 {
717                         pltlevel = PyString_FromString("STATEMENT");
718                         PyDict_SetItemString(pltdata, "level", pltlevel);
719                         Py_DECREF(pltlevel);
720
721                         PyDict_SetItemString(pltdata, "old", Py_None);
722                         PyDict_SetItemString(pltdata, "new", Py_None);
723                         *rv = NULL;
724
725                         if (TRIGGER_FIRED_BY_INSERT(tdata->tg_event))
726                                 pltevent = PyString_FromString("INSERT");
727                         else if (TRIGGER_FIRED_BY_DELETE(tdata->tg_event))
728                                 pltevent = PyString_FromString("DELETE");
729                         else if (TRIGGER_FIRED_BY_UPDATE(tdata->tg_event))
730                                 pltevent = PyString_FromString("UPDATE");
731                         else if (TRIGGER_FIRED_BY_TRUNCATE(tdata->tg_event))
732                                 pltevent = PyString_FromString("TRUNCATE");
733                         else
734                         {
735                                 elog(ERROR, "unrecognized OP tg_event: %u", tdata->tg_event);
736                                 pltevent = NULL;        /* keep compiler quiet */
737                         }
738
739                         PyDict_SetItemString(pltdata, "event", pltevent);
740                         Py_DECREF(pltevent);
741                 }
742                 else
743                         elog(ERROR, "unrecognized LEVEL tg_event: %u", tdata->tg_event);
744
745                 if (tdata->tg_trigger->tgnargs)
746                 {
747                         /*
748                          * all strings...
749                          */
750                         int                     i;
751                         PyObject   *pltarg;
752
753                         pltargs = PyList_New(tdata->tg_trigger->tgnargs);
754                         for (i = 0; i < tdata->tg_trigger->tgnargs; i++)
755                         {
756                                 pltarg = PyString_FromString(tdata->tg_trigger->tgargs[i]);
757
758                                 /*
759                                  * stolen, don't Py_DECREF
760                                  */
761                                 PyList_SetItem(pltargs, i, pltarg);
762                         }
763                 }
764                 else
765                 {
766                         Py_INCREF(Py_None);
767                         pltargs = Py_None;
768                 }
769                 PyDict_SetItemString(pltdata, "args", pltargs);
770                 Py_DECREF(pltargs);
771         }
772         PG_CATCH();
773         {
774                 Py_XDECREF(pltdata);
775                 PG_RE_THROW();
776         }
777         PG_END_TRY();
778
779         return pltdata;
780 }
781
782
783
784 /* function handler and friends */
785 static Datum
786 PLy_function_handler(FunctionCallInfo fcinfo, PLyProcedure * proc)
787 {
788         Datum           rv;
789         PyObject   *volatile plargs = NULL;
790         PyObject   *volatile plrv = NULL;
791         PyObject   *volatile plrv_so = NULL;
792         char       *plrv_sc;
793
794         PG_TRY();
795         {
796                 if (!proc->is_setof || proc->setof == NULL)
797                 {
798                         /* Simple type returning function or first time for SETOF function */
799                         plargs = PLy_function_build_args(fcinfo, proc);
800                         plrv = PLy_procedure_call(proc, "args", plargs);
801                         if (!proc->is_setof)
802
803                                 /*
804                                  * SETOF function parameters will be deleted when last row is
805                                  * returned
806                                  */
807                                 PLy_function_delete_args(proc);
808                         Assert(plrv != NULL);
809                         Assert(!PLy_error_in_progress);
810                 }
811
812                 /*
813                  * Disconnect from SPI manager and then create the return values datum
814                  * (if the input function does a palloc for it this must not be
815                  * allocated in the SPI memory context because SPI_finish would free
816                  * it).
817                  */
818                 if (SPI_finish() != SPI_OK_FINISH)
819                         elog(ERROR, "SPI_finish failed");
820
821                 if (proc->is_setof)
822                 {
823                         bool            has_error = false;
824                         ReturnSetInfo *rsi = (ReturnSetInfo *) fcinfo->resultinfo;
825
826                         if (proc->setof == NULL)
827                         {
828                                 /* first time -- do checks and setup */
829                                 if (!rsi || !IsA(rsi, ReturnSetInfo) ||
830                                         (rsi->allowedModes & SFRM_ValuePerCall) == 0)
831                                 {
832                                         ereport(ERROR,
833                                                         (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
834                                                          errmsg("unsupported set function return mode"),
835                                                          errdetail("PL/Python set-returning functions only support returning only value per call.")));
836                                 }
837                                 rsi->returnMode = SFRM_ValuePerCall;
838
839                                 /* Make iterator out of returned object */
840                                 proc->setof = PyObject_GetIter(plrv);
841                                 Py_DECREF(plrv);
842                                 plrv = NULL;
843
844                                 if (proc->setof == NULL)
845                                         ereport(ERROR,
846                                                         (errcode(ERRCODE_DATATYPE_MISMATCH),
847                                                          errmsg("returned object cannot be iterated"),
848                                         errdetail("PL/Python set-returning functions must return an iterable object.")));
849                         }
850
851                         /* Fetch next from iterator */
852                         plrv = PyIter_Next(proc->setof);
853                         if (plrv)
854                                 rsi->isDone = ExprMultipleResult;
855                         else
856                         {
857                                 rsi->isDone = ExprEndResult;
858                                 has_error = PyErr_Occurred() != NULL;
859                         }
860
861                         if (rsi->isDone == ExprEndResult)
862                         {
863                                 /* Iterator is exhausted or error happened */
864                                 Py_DECREF(proc->setof);
865                                 proc->setof = NULL;
866
867                                 Py_XDECREF(plargs);
868                                 Py_XDECREF(plrv);
869                                 Py_XDECREF(plrv_so);
870
871                                 PLy_function_delete_args(proc);
872
873                                 if (has_error)
874                                         ereport(ERROR,
875                                                         (errcode(ERRCODE_DATA_EXCEPTION),
876                                                   errmsg("error fetching next item from iterator")));
877
878                                 fcinfo->isnull = true;
879                                 return (Datum) NULL;
880                         }
881                 }
882
883                 /*
884                  * If the function is declared to return void, the Python return value
885                  * must be None. For void-returning functions, we also treat a None
886                  * return value as a special "void datum" rather than NULL (as is the
887                  * case for non-void-returning functions).
888                  */
889                 if (proc->result.out.d.typoid == VOIDOID)
890                 {
891                         if (plrv != Py_None)
892                                 ereport(ERROR,
893                                                 (errcode(ERRCODE_DATATYPE_MISMATCH),
894                                            errmsg("PL/Python function with return type \"void\" did not return None")));
895
896                         fcinfo->isnull = false;
897                         rv = (Datum) 0;
898                 }
899                 else if (plrv == Py_None)
900                 {
901                         fcinfo->isnull = true;
902                         if (proc->result.is_rowtype < 1)
903                                 rv = InputFunctionCall(&proc->result.out.d.typfunc,
904                                                                            NULL,
905                                                                            proc->result.out.d.typioparam,
906                                                                            -1);
907                         else
908                                 /* Tuple as None */
909                                 rv = (Datum) NULL;
910                 }
911                 else if (proc->result.is_rowtype >= 1)
912                 {
913                         HeapTuple       tuple = NULL;
914
915                         if (PySequence_Check(plrv))
916                                 /* composite type as sequence (tuple, list etc) */
917                                 tuple = PLySequence_ToTuple(&proc->result, plrv);
918                         else if (PyMapping_Check(plrv))
919                                 /* composite type as mapping (currently only dict) */
920                                 tuple = PLyMapping_ToTuple(&proc->result, plrv);
921                         else
922                                 /* returned as smth, must provide method __getattr__(name) */
923                                 tuple = PLyObject_ToTuple(&proc->result, plrv);
924
925                         if (tuple != NULL)
926                         {
927                                 fcinfo->isnull = false;
928                                 rv = HeapTupleGetDatum(tuple);
929                         }
930                         else
931                         {
932                                 fcinfo->isnull = true;
933                                 rv = (Datum) NULL;
934                         }
935                 }
936                 else
937                 {
938                         fcinfo->isnull = false;
939                         plrv_so = PyObject_Str(plrv);
940                         if (!plrv_so)
941                                 PLy_elog(ERROR, "could not create string representation of Python object in PL/Python function \"%s\" while creating return value", proc->proname);
942                         plrv_sc = PyString_AsString(plrv_so);
943                         rv = InputFunctionCall(&proc->result.out.d.typfunc,
944                                                                    plrv_sc,
945                                                                    proc->result.out.d.typioparam,
946                                                                    -1);
947                 }
948         }
949         PG_CATCH();
950         {
951                 Py_XDECREF(plargs);
952                 Py_XDECREF(plrv);
953                 Py_XDECREF(plrv_so);
954
955                 PG_RE_THROW();
956         }
957         PG_END_TRY();
958
959         Py_XDECREF(plargs);
960         Py_DECREF(plrv);
961         Py_XDECREF(plrv_so);
962
963         return rv;
964 }
965
966 static PyObject *
967 PLy_procedure_call(PLyProcedure * proc, char *kargs, PyObject * vargs)
968 {
969         PyObject   *rv;
970
971         PyDict_SetItemString(proc->globals, kargs, vargs);
972         rv = PyEval_EvalCode((PyCodeObject *) proc->code,
973                                                  proc->globals, proc->globals);
974
975         /*
976          * If there was an error in a PG callback, propagate that no matter what
977          * Python claims about its success.
978          */
979         if (PLy_error_in_progress)
980         {
981                 ErrorData  *edata = PLy_error_in_progress;
982
983                 PLy_error_in_progress = NULL;
984                 ReThrowError(edata);
985         }
986
987         if (rv == NULL || PyErr_Occurred())
988         {
989                 Py_XDECREF(rv);
990                 PLy_elog(ERROR, "PL/Python function \"%s\" failed", proc->proname);
991         }
992
993         return rv;
994 }
995
996 static PyObject *
997 PLy_function_build_args(FunctionCallInfo fcinfo, PLyProcedure * proc)
998 {
999         PyObject   *volatile arg = NULL;
1000         PyObject   *volatile args = NULL;
1001         int                     i;
1002
1003         PG_TRY();
1004         {
1005                 args = PyList_New(proc->nargs);
1006                 for (i = 0; i < proc->nargs; i++)
1007                 {
1008                         if (proc->args[i].is_rowtype > 0)
1009                         {
1010                                 if (fcinfo->argnull[i])
1011                                         arg = NULL;
1012                                 else
1013                                 {
1014                                         HeapTupleHeader td;
1015                                         Oid                     tupType;
1016                                         int32           tupTypmod;
1017                                         TupleDesc       tupdesc;
1018                                         HeapTupleData tmptup;
1019
1020                                         td = DatumGetHeapTupleHeader(fcinfo->arg[i]);
1021                                         /* Extract rowtype info and find a tupdesc */
1022                                         tupType = HeapTupleHeaderGetTypeId(td);
1023                                         tupTypmod = HeapTupleHeaderGetTypMod(td);
1024                                         tupdesc = lookup_rowtype_tupdesc(tupType, tupTypmod);
1025
1026                                         /* Set up I/O funcs if not done yet */
1027                                         if (proc->args[i].is_rowtype != 1)
1028                                                 PLy_input_tuple_funcs(&(proc->args[i]), tupdesc);
1029
1030                                         /* Build a temporary HeapTuple control structure */
1031                                         tmptup.t_len = HeapTupleHeaderGetDatumLength(td);
1032                                         tmptup.t_data = td;
1033
1034                                         arg = PLyDict_FromTuple(&(proc->args[i]), &tmptup, tupdesc);
1035                                         ReleaseTupleDesc(tupdesc);
1036                                 }
1037                         }
1038                         else
1039                         {
1040                                 if (fcinfo->argnull[i])
1041                                         arg = NULL;
1042                                 else
1043                                 {
1044                                         char       *ct;
1045
1046                                         ct = OutputFunctionCall(&(proc->args[i].in.d.typfunc),
1047                                                                                         fcinfo->arg[i]);
1048                                         arg = (proc->args[i].in.d.func) (ct);
1049                                         pfree(ct);
1050                                 }
1051                         }
1052
1053                         if (arg == NULL)
1054                         {
1055                                 Py_INCREF(Py_None);
1056                                 arg = Py_None;
1057                         }
1058
1059                         if (PyList_SetItem(args, i, arg) == -1)
1060                                 PLy_elog(ERROR, "PyList_SetItem() failed for PL/Python function \"%s\" while setting up arguments", proc->proname);
1061
1062                         if (proc->argnames && proc->argnames[i] &&
1063                                 PyDict_SetItemString(proc->globals, proc->argnames[i], arg) == -1)
1064                                 PLy_elog(ERROR, "PyDict_SetItemString() failed for PL/Python function \"%s\" while setting up arguments", proc->proname);
1065                         arg = NULL;
1066                 }
1067         }
1068         PG_CATCH();
1069         {
1070                 Py_XDECREF(arg);
1071                 Py_XDECREF(args);
1072
1073                 PG_RE_THROW();
1074         }
1075         PG_END_TRY();
1076
1077         return args;
1078 }
1079
1080
1081 static void
1082 PLy_function_delete_args(PLyProcedure * proc)
1083 {
1084         int                     i;
1085
1086         if (!proc->argnames)
1087                 return;
1088
1089         for (i = 0; i < proc->nargs; i++)
1090                 if (proc->argnames[i])
1091                         PyDict_DelItemString(proc->globals, proc->argnames[i]);
1092 }
1093
1094
1095 /*
1096  * PLyProcedure functions
1097  */
1098
1099 /* PLy_procedure_get: returns a cached PLyProcedure, or creates, stores and
1100  * returns a new PLyProcedure.  fcinfo is the call info, tgreloid is the
1101  * relation OID when calling a trigger, or InvalidOid (zero) for ordinary
1102  * function calls.
1103  */
1104 static PLyProcedure *
1105 PLy_procedure_get(FunctionCallInfo fcinfo, Oid tgreloid)
1106 {
1107         Oid                     fn_oid;
1108         HeapTuple       procTup;
1109         char            key[128];
1110         PyObject   *plproc;
1111         PLyProcedure *proc = NULL;
1112         int                     rv;
1113
1114         fn_oid = fcinfo->flinfo->fn_oid;
1115         procTup = SearchSysCache(PROCOID,
1116                                                          ObjectIdGetDatum(fn_oid),
1117                                                          0, 0, 0);
1118         if (!HeapTupleIsValid(procTup))
1119                 elog(ERROR, "cache lookup failed for function %u", fn_oid);
1120
1121         rv = snprintf(key, sizeof(key), "%u_%u", fn_oid, tgreloid);
1122         if (rv >= sizeof(key) || rv < 0)
1123                 elog(ERROR, "key too long");
1124
1125         plproc = PyDict_GetItemString(PLy_procedure_cache, key);
1126
1127         if (plproc != NULL)
1128         {
1129                 Py_INCREF(plproc);
1130                 if (!PyCObject_Check(plproc))
1131                         elog(FATAL, "expected a PyCObject, didn't get one");
1132
1133                 proc = PyCObject_AsVoidPtr(plproc);
1134                 if (proc->me != plproc)
1135                         elog(FATAL, "proc->me != plproc");
1136                 /* did we find an up-to-date cache entry? */
1137                 if (proc->fn_xmin != HeapTupleHeaderGetXmin(procTup->t_data) ||
1138                         !ItemPointerEquals(&proc->fn_tid, &procTup->t_self))
1139                 {
1140                         Py_DECREF(plproc);
1141                         proc = NULL;
1142                 }
1143         }
1144
1145         if (proc == NULL)
1146                 proc = PLy_procedure_create(procTup, tgreloid, key);
1147
1148         if (OidIsValid(tgreloid))
1149         {
1150                 /*
1151                  * Input/output conversion for trigger tuples.  Use the result
1152                  * TypeInfo variable to store the tuple conversion info.  We
1153                  * do this over again on each call to cover the possibility that
1154                  * the relation's tupdesc changed since the trigger was last called.
1155                  * PLy_input_tuple_funcs and PLy_output_tuple_funcs are responsible
1156                  * for not doing repetitive work.
1157                  */
1158                 TriggerData *tdata = (TriggerData *) fcinfo->context;
1159
1160                 Assert(CALLED_AS_TRIGGER(fcinfo));
1161                 PLy_input_tuple_funcs(&(proc->result), tdata->tg_relation->rd_att);
1162                 PLy_output_tuple_funcs(&(proc->result), tdata->tg_relation->rd_att);
1163         }
1164
1165         ReleaseSysCache(procTup);
1166
1167         return proc;
1168 }
1169
1170 static PLyProcedure *
1171 PLy_procedure_create(HeapTuple procTup, Oid tgreloid, char *key)
1172 {
1173         char            procName[NAMEDATALEN + 256];
1174         Form_pg_proc procStruct;
1175         PLyProcedure *volatile proc;
1176         char       *volatile procSource = NULL;
1177         Datum           prosrcdatum;
1178         bool            isnull;
1179         int                     i,
1180                                 rv;
1181
1182         procStruct = (Form_pg_proc) GETSTRUCT(procTup);
1183
1184         if (OidIsValid(tgreloid))
1185                 rv = snprintf(procName, sizeof(procName),
1186                                           "__plpython_procedure_%s_%u_trigger_%u",
1187                                           NameStr(procStruct->proname),
1188                                           HeapTupleGetOid(procTup),
1189                                           tgreloid);
1190         else
1191                 rv = snprintf(procName, sizeof(procName),
1192                                           "__plpython_procedure_%s_%u",
1193                                           NameStr(procStruct->proname),
1194                                           HeapTupleGetOid(procTup));
1195         if (rv >= sizeof(procName) || rv < 0)
1196                 elog(ERROR, "procedure name would overrun buffer");
1197
1198         proc = PLy_malloc(sizeof(PLyProcedure));
1199         proc->proname = PLy_strdup(NameStr(procStruct->proname));
1200         proc->pyname = PLy_strdup(procName);
1201         proc->fn_xmin = HeapTupleHeaderGetXmin(procTup->t_data);
1202         proc->fn_tid = procTup->t_self;
1203         /* Remember if function is STABLE/IMMUTABLE */
1204         proc->fn_readonly =
1205                 (procStruct->provolatile != PROVOLATILE_VOLATILE);
1206         PLy_typeinfo_init(&proc->result);
1207         for (i = 0; i < FUNC_MAX_ARGS; i++)
1208                 PLy_typeinfo_init(&proc->args[i]);
1209         proc->nargs = 0;
1210         proc->code = proc->statics = NULL;
1211         proc->globals = proc->me = NULL;
1212         proc->is_setof = procStruct->proretset;
1213         proc->setof = NULL;
1214         proc->argnames = NULL;
1215
1216         PG_TRY();
1217         {
1218                 /*
1219                  * get information required for output conversion of the return value,
1220                  * but only if this isn't a trigger.
1221                  */
1222                 if (!OidIsValid(tgreloid))
1223                 {
1224                         HeapTuple       rvTypeTup;
1225                         Form_pg_type rvTypeStruct;
1226
1227                         rvTypeTup = SearchSysCache(TYPEOID,
1228                                                                         ObjectIdGetDatum(procStruct->prorettype),
1229                                                                            0, 0, 0);
1230                         if (!HeapTupleIsValid(rvTypeTup))
1231                                 elog(ERROR, "cache lookup failed for type %u",
1232                                          procStruct->prorettype);
1233                         rvTypeStruct = (Form_pg_type) GETSTRUCT(rvTypeTup);
1234
1235                         /* Disallow pseudotype result, except for void */
1236                         if (rvTypeStruct->typtype == TYPTYPE_PSEUDO &&
1237                                 procStruct->prorettype != VOIDOID)
1238                         {
1239                                 if (procStruct->prorettype == TRIGGEROID)
1240                                         ereport(ERROR,
1241                                                         (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1242                                                          errmsg("trigger functions can only be called as triggers")));
1243                                 else
1244                                         ereport(ERROR,
1245                                                         (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1246                                                    errmsg("PL/Python functions cannot return type %s",
1247                                                                   format_type_be(procStruct->prorettype))));
1248                         }
1249
1250                         if (rvTypeStruct->typtype == TYPTYPE_COMPOSITE)
1251                         {
1252                                 /*
1253                                  * Tuple: set up later, during first call to
1254                                  * PLy_function_handler
1255                                  */
1256                                 proc->result.out.d.typoid = procStruct->prorettype;
1257                                 proc->result.is_rowtype = 2;
1258                         }
1259                         else
1260                                 PLy_output_datum_func(&proc->result, rvTypeTup);
1261
1262                         ReleaseSysCache(rvTypeTup);
1263                 }
1264
1265                 /*
1266                  * Now get information required for input conversion of the
1267                  * procedure's arguments.  Note that we ignore output arguments
1268                  * here --- since we don't support returning record, and that was
1269                  * already checked above, there's no need to worry about multiple
1270                  * output arguments.
1271                  */
1272                 if (procStruct->pronargs)
1273                 {
1274                         Oid             *types;
1275                         char   **names,
1276                                         *modes;
1277                         int              i,
1278                                          pos,
1279                                          total;
1280
1281                         /* extract argument type info from the pg_proc tuple */
1282                         total = get_func_arg_info(procTup, &types, &names, &modes);
1283
1284                         /* count number of in+inout args into proc->nargs */
1285                         if (modes == NULL)
1286                                 proc->nargs = total;
1287                         else
1288                         {
1289                                 /* proc->nargs was initialized to 0 above */
1290                                 for (i = 0; i < total; i++)
1291                                 {
1292                                         if (modes[i] != PROARGMODE_OUT &&
1293                                                 modes[i] != PROARGMODE_TABLE)
1294                                                 (proc->nargs)++;
1295                                 }
1296                         }
1297
1298                         proc->argnames = (char **) PLy_malloc0(sizeof(char *) * proc->nargs);
1299                         for (i = pos = 0; i < total; i++)
1300                         {
1301                                 HeapTuple       argTypeTup;
1302                                 Form_pg_type argTypeStruct;
1303
1304                                 if (modes &&
1305                                         (modes[i] == PROARGMODE_OUT ||
1306                                          modes[i] == PROARGMODE_TABLE))
1307                                         continue;       /* skip OUT arguments */
1308
1309                                 Assert(types[i] == procStruct->proargtypes.values[pos]);
1310
1311                                 argTypeTup = SearchSysCache(TYPEOID,
1312                                                                                         ObjectIdGetDatum(types[i]),
1313                                                                                         0, 0, 0);
1314                                 if (!HeapTupleIsValid(argTypeTup))
1315                                         elog(ERROR, "cache lookup failed for type %u", types[i]);
1316                                 argTypeStruct = (Form_pg_type) GETSTRUCT(argTypeTup);
1317
1318                                 /* check argument type is OK, set up I/O function info */
1319                                 switch (argTypeStruct->typtype)
1320                                 {
1321                                         case TYPTYPE_PSEUDO:
1322                                                 /* Disallow pseudotype argument */
1323                                                 ereport(ERROR,
1324                                                                 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
1325                                                                  errmsg("PL/Python functions cannot accept type %s",
1326                                                                  format_type_be(types[i]))));
1327                                                 break;
1328                                         case TYPTYPE_COMPOSITE:
1329                                                 /* we'll set IO funcs at first call */
1330                                                 proc->args[pos].is_rowtype = 2;
1331                                                 break;
1332                                         default:
1333                                                 PLy_input_datum_func(&(proc->args[pos]),
1334                                                                                          types[i],
1335                                                                                          argTypeTup);
1336                                                 break;
1337                                 }
1338
1339                                 /* get argument name */
1340                                 proc->argnames[pos] = names ? PLy_strdup(names[i]) : NULL;
1341
1342                                 ReleaseSysCache(argTypeTup);
1343
1344                                 pos++;
1345                         }
1346                 }
1347
1348                 /*
1349                  * get the text of the function.
1350                  */
1351                 prosrcdatum = SysCacheGetAttr(PROCOID, procTup,
1352                                                                           Anum_pg_proc_prosrc, &isnull);
1353                 if (isnull)
1354                         elog(ERROR, "null prosrc");
1355                 procSource = TextDatumGetCString(prosrcdatum);
1356
1357                 PLy_procedure_compile(proc, procSource);
1358
1359                 pfree(procSource);
1360
1361                 proc->me = PyCObject_FromVoidPtr(proc, NULL);
1362                 PyDict_SetItemString(PLy_procedure_cache, key, proc->me);
1363         }
1364         PG_CATCH();
1365         {
1366                 PLy_procedure_delete(proc);
1367                 if (procSource)
1368                         pfree(procSource);
1369
1370                 PG_RE_THROW();
1371         }
1372         PG_END_TRY();
1373
1374         return proc;
1375 }
1376
1377 static void
1378 PLy_procedure_compile(PLyProcedure * proc, const char *src)
1379 {
1380         PyObject   *crv = NULL;
1381         char       *msrc;
1382
1383         proc->globals = PyDict_Copy(PLy_interp_globals);
1384
1385         /*
1386          * SD is private preserved data between calls. GD is global data shared by
1387          * all functions
1388          */
1389         proc->statics = PyDict_New();
1390         PyDict_SetItemString(proc->globals, "SD", proc->statics);
1391
1392         /*
1393          * insert the function code into the interpreter
1394          */
1395         msrc = PLy_procedure_munge_source(proc->pyname, src);
1396         crv = PyRun_String(msrc, Py_file_input, proc->globals, NULL);
1397         free(msrc);
1398
1399         if (crv != NULL && (!PyErr_Occurred()))
1400         {
1401                 int                     clen;
1402                 char            call[NAMEDATALEN + 256];
1403
1404                 Py_DECREF(crv);
1405
1406                 /*
1407                  * compile a call to the function
1408                  */
1409                 clen = snprintf(call, sizeof(call), "%s()", proc->pyname);
1410                 if (clen < 0 || clen >= sizeof(call))
1411                         elog(ERROR, "string would overflow buffer");
1412                 proc->code = Py_CompileString(call, "<string>", Py_eval_input);
1413                 if (proc->code != NULL && (!PyErr_Occurred()))
1414                         return;
1415         }
1416         else
1417                 Py_XDECREF(crv);
1418
1419         PLy_elog(ERROR, "could not compile PL/Python function \"%s\"", proc->proname);
1420 }
1421
1422 static char *
1423 PLy_procedure_munge_source(const char *name, const char *src)
1424 {
1425         char       *mrc,
1426                            *mp;
1427         const char *sp;
1428         size_t          mlen,
1429                                 plen;
1430
1431         /*
1432          * room for function source and the def statement
1433          */
1434         mlen = (strlen(src) * 2) + strlen(name) + 16;
1435
1436         mrc = PLy_malloc(mlen);
1437         plen = snprintf(mrc, mlen, "def %s():\n\t", name);
1438         Assert(plen >= 0 && plen < mlen);
1439
1440         sp = src;
1441         mp = mrc + plen;
1442
1443         while (*sp != '\0')
1444         {
1445                 if (*sp == '\r' && *(sp + 1) == '\n')
1446                         sp++;
1447
1448                 if (*sp == '\n' || *sp == '\r')
1449                 {
1450                         *mp++ = '\n';
1451                         *mp++ = '\t';
1452                         sp++;
1453                 }
1454                 else
1455                         *mp++ = *sp++;
1456         }
1457         *mp++ = '\n';
1458         *mp++ = '\n';
1459         *mp = '\0';
1460
1461         if (mp > (mrc + mlen))
1462                 elog(FATAL, "buffer overrun in PLy_munge_source");
1463
1464         return mrc;
1465 }
1466
1467 static void
1468 PLy_procedure_delete(PLyProcedure * proc)
1469 {
1470         int                     i;
1471
1472         Py_XDECREF(proc->code);
1473         Py_XDECREF(proc->statics);
1474         Py_XDECREF(proc->globals);
1475         Py_XDECREF(proc->me);
1476         if (proc->proname)
1477                 PLy_free(proc->proname);
1478         if (proc->pyname)
1479                 PLy_free(proc->pyname);
1480         for (i = 0; i < proc->nargs; i++)
1481         {
1482                 if (proc->args[i].is_rowtype == 1)
1483                 {
1484                         if (proc->args[i].in.r.atts)
1485                                 PLy_free(proc->args[i].in.r.atts);
1486                         if (proc->args[i].out.r.atts)
1487                                 PLy_free(proc->args[i].out.r.atts);
1488                 }
1489                 if (proc->argnames && proc->argnames[i])
1490                         PLy_free(proc->argnames[i]);
1491         }
1492         if (proc->argnames)
1493                 PLy_free(proc->argnames);
1494 }
1495
1496 /*
1497  * Conversion functions.  Remember output from Python is input to
1498  * PostgreSQL, and vice versa.
1499  */
1500 static void
1501 PLy_input_tuple_funcs(PLyTypeInfo * arg, TupleDesc desc)
1502 {
1503         int                     i;
1504
1505         if (arg->is_rowtype == 0)
1506                 elog(ERROR, "PLyTypeInfo struct is initialized for a Datum");
1507         arg->is_rowtype = 1;
1508
1509         if (arg->in.r.natts != desc->natts)
1510         {
1511                 if (arg->in.r.atts)
1512                         PLy_free(arg->in.r.atts);
1513                 arg->in.r.natts = desc->natts;
1514                 arg->in.r.atts = PLy_malloc0(desc->natts * sizeof(PLyDatumToOb));
1515         }
1516
1517         for (i = 0; i < desc->natts; i++)
1518         {
1519                 HeapTuple       typeTup;
1520
1521                 if (desc->attrs[i]->attisdropped)
1522                         continue;
1523
1524                 if (arg->in.r.atts[i].typoid == desc->attrs[i]->atttypid)
1525                         continue;                       /* already set up this entry */
1526
1527                 typeTup = SearchSysCache(TYPEOID,
1528                                                                  ObjectIdGetDatum(desc->attrs[i]->atttypid),
1529                                                                  0, 0, 0);
1530                 if (!HeapTupleIsValid(typeTup))
1531                         elog(ERROR, "cache lookup failed for type %u",
1532                                  desc->attrs[i]->atttypid);
1533
1534                 PLy_input_datum_func2(&(arg->in.r.atts[i]),
1535                                                           desc->attrs[i]->atttypid,
1536                                                           typeTup);
1537
1538                 ReleaseSysCache(typeTup);
1539         }
1540 }
1541
1542 static void
1543 PLy_output_tuple_funcs(PLyTypeInfo * arg, TupleDesc desc)
1544 {
1545         int                     i;
1546
1547         if (arg->is_rowtype == 0)
1548                 elog(ERROR, "PLyTypeInfo struct is initialized for a Datum");
1549         arg->is_rowtype = 1;
1550
1551         if (arg->out.r.natts != desc->natts)
1552         {
1553                 if (arg->out.r.atts)
1554                         PLy_free(arg->out.r.atts);
1555                 arg->out.r.natts = desc->natts;
1556                 arg->out.r.atts = PLy_malloc0(desc->natts * sizeof(PLyDatumToOb));
1557         }
1558
1559         for (i = 0; i < desc->natts; i++)
1560         {
1561                 HeapTuple       typeTup;
1562
1563                 if (desc->attrs[i]->attisdropped)
1564                         continue;
1565
1566                 if (arg->out.r.atts[i].typoid == desc->attrs[i]->atttypid)
1567                         continue;                       /* already set up this entry */
1568
1569                 typeTup = SearchSysCache(TYPEOID,
1570                                                                  ObjectIdGetDatum(desc->attrs[i]->atttypid),
1571                                                                  0, 0, 0);
1572                 if (!HeapTupleIsValid(typeTup))
1573                         elog(ERROR, "cache lookup failed for type %u",
1574                                  desc->attrs[i]->atttypid);
1575
1576                 PLy_output_datum_func2(&(arg->out.r.atts[i]), typeTup);
1577
1578                 ReleaseSysCache(typeTup);
1579         }
1580 }
1581
1582 static void
1583 PLy_output_datum_func(PLyTypeInfo * arg, HeapTuple typeTup)
1584 {
1585         if (arg->is_rowtype > 0)
1586                 elog(ERROR, "PLyTypeInfo struct is initialized for a Tuple");
1587         arg->is_rowtype = 0;
1588         PLy_output_datum_func2(&(arg->out.d), typeTup);
1589 }
1590
1591 static void
1592 PLy_output_datum_func2(PLyObToDatum * arg, HeapTuple typeTup)
1593 {
1594         Form_pg_type typeStruct = (Form_pg_type) GETSTRUCT(typeTup);
1595
1596         perm_fmgr_info(typeStruct->typinput, &arg->typfunc);
1597         arg->typoid = HeapTupleGetOid(typeTup);
1598         arg->typioparam = getTypeIOParam(typeTup);
1599         arg->typbyval = typeStruct->typbyval;
1600 }
1601
1602 static void
1603 PLy_input_datum_func(PLyTypeInfo * arg, Oid typeOid, HeapTuple typeTup)
1604 {
1605         if (arg->is_rowtype > 0)
1606                 elog(ERROR, "PLyTypeInfo struct is initialized for Tuple");
1607         arg->is_rowtype = 0;
1608         PLy_input_datum_func2(&(arg->in.d), typeOid, typeTup);
1609 }
1610
1611 static void
1612 PLy_input_datum_func2(PLyDatumToOb * arg, Oid typeOid, HeapTuple typeTup)
1613 {
1614         Form_pg_type typeStruct = (Form_pg_type) GETSTRUCT(typeTup);
1615
1616         /* Get the type's conversion information */
1617         perm_fmgr_info(typeStruct->typoutput, &arg->typfunc);
1618         arg->typoid = HeapTupleGetOid(typeTup);
1619         arg->typioparam = getTypeIOParam(typeTup);
1620         arg->typbyval = typeStruct->typbyval;
1621
1622         /* Determine which kind of Python object we will convert to */
1623         switch (typeOid)
1624         {
1625                 case BOOLOID:
1626                         arg->func = PLyBool_FromString;
1627                         break;
1628                 case FLOAT4OID:
1629                 case FLOAT8OID:
1630                 case NUMERICOID:
1631                         arg->func = PLyFloat_FromString;
1632                         break;
1633                 case INT2OID:
1634                 case INT4OID:
1635                         arg->func = PLyInt_FromString;
1636                         break;
1637                 case INT8OID:
1638                         arg->func = PLyLong_FromString;
1639                         break;
1640                 default:
1641                         arg->func = PLyString_FromString;
1642                         break;
1643         }
1644 }
1645
1646 static void
1647 PLy_typeinfo_init(PLyTypeInfo * arg)
1648 {
1649         arg->is_rowtype = -1;
1650         arg->in.r.natts = arg->out.r.natts = 0;
1651         arg->in.r.atts = NULL;
1652         arg->out.r.atts = NULL;
1653 }
1654
1655 static void
1656 PLy_typeinfo_dealloc(PLyTypeInfo * arg)
1657 {
1658         if (arg->is_rowtype == 1)
1659         {
1660                 if (arg->in.r.atts)
1661                         PLy_free(arg->in.r.atts);
1662                 if (arg->out.r.atts)
1663                         PLy_free(arg->out.r.atts);
1664         }
1665 }
1666
1667 /* assumes that a bool is always returned as a 't' or 'f' */
1668 static PyObject *
1669 PLyBool_FromString(const char *src)
1670 {
1671         /*
1672          * We would like to use Py_RETURN_TRUE and Py_RETURN_FALSE here for
1673          * generating SQL from trigger functions, but those are only supported in
1674          * Python >= 2.3, and we support older versions.
1675          * http://docs.python.org/api/boolObjects.html
1676          */
1677         if (src[0] == 't')
1678                 return PyBool_FromLong(1);
1679         return PyBool_FromLong(0);
1680 }
1681
1682 static PyObject *
1683 PLyFloat_FromString(const char *src)
1684 {
1685         double          v;
1686         char       *eptr;
1687
1688         errno = 0;
1689         v = strtod(src, &eptr);
1690         if (*eptr != '\0' || errno)
1691                 return NULL;
1692         return PyFloat_FromDouble(v);
1693 }
1694
1695 static PyObject *
1696 PLyInt_FromString(const char *src)
1697 {
1698         long            v;
1699         char       *eptr;
1700
1701         errno = 0;
1702         v = strtol(src, &eptr, 0);
1703         if (*eptr != '\0' || errno)
1704                 return NULL;
1705         return PyInt_FromLong(v);
1706 }
1707
1708 static PyObject *
1709 PLyLong_FromString(const char *src)
1710 {
1711         return PyLong_FromString((char *) src, NULL, 0);
1712 }
1713
1714 static PyObject *
1715 PLyString_FromString(const char *src)
1716 {
1717         return PyString_FromString(src);
1718 }
1719
1720 static PyObject *
1721 PLyDict_FromTuple(PLyTypeInfo * info, HeapTuple tuple, TupleDesc desc)
1722 {
1723         PyObject   *volatile dict;
1724         int                     i;
1725
1726         if (info->is_rowtype != 1)
1727                 elog(ERROR, "PLyTypeInfo structure describes a datum");
1728
1729         dict = PyDict_New();
1730         if (dict == NULL)
1731                 PLy_elog(ERROR, "could not create new dictionary");
1732
1733         PG_TRY();
1734         {
1735                 for (i = 0; i < info->in.r.natts; i++)
1736                 {
1737                         char       *key,
1738                                            *vsrc;
1739                         Datum           vattr;
1740                         bool            is_null;
1741                         PyObject   *value;
1742
1743                         if (desc->attrs[i]->attisdropped)
1744                                 continue;
1745
1746                         key = NameStr(desc->attrs[i]->attname);
1747                         vattr = heap_getattr(tuple, (i + 1), desc, &is_null);
1748
1749                         if (is_null || info->in.r.atts[i].func == NULL)
1750                                 PyDict_SetItemString(dict, key, Py_None);
1751                         else
1752                         {
1753                                 vsrc = OutputFunctionCall(&info->in.r.atts[i].typfunc,
1754                                                                                   vattr);
1755
1756                                 /*
1757                                  * no exceptions allowed
1758                                  */
1759                                 value = info->in.r.atts[i].func(vsrc);
1760                                 pfree(vsrc);
1761                                 PyDict_SetItemString(dict, key, value);
1762                                 Py_DECREF(value);
1763                         }
1764                 }
1765         }
1766         PG_CATCH();
1767         {
1768                 Py_DECREF(dict);
1769                 PG_RE_THROW();
1770         }
1771         PG_END_TRY();
1772
1773         return dict;
1774 }
1775
1776
1777 static HeapTuple
1778 PLyMapping_ToTuple(PLyTypeInfo * info, PyObject * mapping)
1779 {
1780         TupleDesc       desc;
1781         HeapTuple       tuple;
1782         Datum      *values;
1783         bool       *nulls;
1784         volatile int i;
1785
1786         Assert(PyMapping_Check(mapping));
1787
1788         desc = lookup_rowtype_tupdesc(info->out.d.typoid, -1);
1789         if (info->is_rowtype == 2)
1790                 PLy_output_tuple_funcs(info, desc);
1791         Assert(info->is_rowtype == 1);
1792
1793         /* Build tuple */
1794         values = palloc(sizeof(Datum) * desc->natts);
1795         nulls = palloc(sizeof(bool) * desc->natts);
1796         for (i = 0; i < desc->natts; ++i)
1797         {
1798                 char       *key;
1799                 PyObject   *volatile value,
1800                                    *volatile so;
1801
1802                 key = NameStr(desc->attrs[i]->attname);
1803                 value = so = NULL;
1804                 PG_TRY();
1805                 {
1806                         value = PyMapping_GetItemString(mapping, key);
1807                         if (value == Py_None)
1808                         {
1809                                 values[i] = (Datum) NULL;
1810                                 nulls[i] = true;
1811                         }
1812                         else if (value)
1813                         {
1814                                 char       *valuestr;
1815
1816                                 so = PyObject_Str(value);
1817                                 if (so == NULL)
1818                                         PLy_elog(ERROR, "could not compute string representation of Python object");
1819                                 valuestr = PyString_AsString(so);
1820
1821                                 values[i] = InputFunctionCall(&info->out.r.atts[i].typfunc
1822                                                                                           ,valuestr
1823                                                                                           ,info->out.r.atts[i].typioparam
1824                                                                                           ,-1);
1825                                 Py_DECREF(so);
1826                                 so = NULL;
1827                                 nulls[i] = false;
1828                         }
1829                         else
1830                                 ereport(ERROR,
1831                                                 (errcode(ERRCODE_UNDEFINED_COLUMN),
1832                                                  errmsg("key \"%s\" not found in mapping", key),
1833                                                  errhint("To return null in a column, "
1834                                           "add the value None to the mapping with the key named after the column.")));
1835
1836                         Py_XDECREF(value);
1837                         value = NULL;
1838                 }
1839                 PG_CATCH();
1840                 {
1841                         Py_XDECREF(so);
1842                         Py_XDECREF(value);
1843                         PG_RE_THROW();
1844                 }
1845                 PG_END_TRY();
1846         }
1847
1848         tuple = heap_form_tuple(desc, values, nulls);
1849         ReleaseTupleDesc(desc);
1850         pfree(values);
1851         pfree(nulls);
1852
1853         return tuple;
1854 }
1855
1856
1857 static HeapTuple
1858 PLySequence_ToTuple(PLyTypeInfo * info, PyObject * sequence)
1859 {
1860         TupleDesc       desc;
1861         HeapTuple       tuple;
1862         Datum      *values;
1863         bool       *nulls;
1864         volatile int i;
1865
1866         Assert(PySequence_Check(sequence));
1867
1868         /*
1869          * Check that sequence length is exactly same as PG tuple's. We actually
1870          * can ignore exceeding items or assume missing ones as null but to avoid
1871          * plpython developer's errors we are strict here
1872          */
1873         desc = lookup_rowtype_tupdesc(info->out.d.typoid, -1);
1874         if (PySequence_Length(sequence) != desc->natts)
1875                 ereport(ERROR,
1876                                 (errcode(ERRCODE_DATATYPE_MISMATCH),
1877                 errmsg("length of returned sequence did not match number of columns in row")));
1878
1879         if (info->is_rowtype == 2)
1880                 PLy_output_tuple_funcs(info, desc);
1881         Assert(info->is_rowtype == 1);
1882
1883         /* Build tuple */
1884         values = palloc(sizeof(Datum) * desc->natts);
1885         nulls = palloc(sizeof(bool) * desc->natts);
1886         for (i = 0; i < desc->natts; ++i)
1887         {
1888                 PyObject   *volatile value,
1889                                    *volatile so;
1890
1891                 value = so = NULL;
1892                 PG_TRY();
1893                 {
1894                         value = PySequence_GetItem(sequence, i);
1895                         Assert(value);
1896                         if (value == Py_None)
1897                         {
1898                                 values[i] = (Datum) NULL;
1899                                 nulls[i] = true;
1900                         }
1901                         else if (value)
1902                         {
1903                                 char       *valuestr;
1904
1905                                 so = PyObject_Str(value);
1906                                 if (so == NULL)
1907                                         PLy_elog(ERROR, "could not compute string representation of Python object");
1908                                 valuestr = PyString_AsString(so);
1909                                 values[i] = InputFunctionCall(&info->out.r.atts[i].typfunc
1910                                                                                           ,valuestr
1911                                                                                           ,info->out.r.atts[i].typioparam
1912                                                                                           ,-1);
1913                                 Py_DECREF(so);
1914                                 so = NULL;
1915                                 nulls[i] = false;
1916                         }
1917
1918                         Py_XDECREF(value);
1919                         value = NULL;
1920                 }
1921                 PG_CATCH();
1922                 {
1923                         Py_XDECREF(so);
1924                         Py_XDECREF(value);
1925                         PG_RE_THROW();
1926                 }
1927                 PG_END_TRY();
1928         }
1929
1930         tuple = heap_form_tuple(desc, values, nulls);
1931         ReleaseTupleDesc(desc);
1932         pfree(values);
1933         pfree(nulls);
1934
1935         return tuple;
1936 }
1937
1938
1939 static HeapTuple
1940 PLyObject_ToTuple(PLyTypeInfo * info, PyObject * object)
1941 {
1942         TupleDesc       desc;
1943         HeapTuple       tuple;
1944         Datum      *values;
1945         bool       *nulls;
1946         volatile int i;
1947
1948         desc = lookup_rowtype_tupdesc(info->out.d.typoid, -1);
1949         if (info->is_rowtype == 2)
1950                 PLy_output_tuple_funcs(info, desc);
1951         Assert(info->is_rowtype == 1);
1952
1953         /* Build tuple */
1954         values = palloc(sizeof(Datum) * desc->natts);
1955         nulls = palloc(sizeof(bool) * desc->natts);
1956         for (i = 0; i < desc->natts; ++i)
1957         {
1958                 char       *key;
1959                 PyObject   *volatile value,
1960                                    *volatile so;
1961
1962                 key = NameStr(desc->attrs[i]->attname);
1963                 value = so = NULL;
1964                 PG_TRY();
1965                 {
1966                         value = PyObject_GetAttrString(object, key);
1967                         if (value == Py_None)
1968                         {
1969                                 values[i] = (Datum) NULL;
1970                                 nulls[i] = true;
1971                         }
1972                         else if (value)
1973                         {
1974                                 char       *valuestr;
1975
1976                                 so = PyObject_Str(value);
1977                                 if (so == NULL)
1978                                         PLy_elog(ERROR, "could not compute string representation of Python object");
1979                                 valuestr = PyString_AsString(so);
1980                                 values[i] = InputFunctionCall(&info->out.r.atts[i].typfunc
1981                                                                                           ,valuestr
1982                                                                                           ,info->out.r.atts[i].typioparam
1983                                                                                           ,-1);
1984                                 Py_DECREF(so);
1985                                 so = NULL;
1986                                 nulls[i] = false;
1987                         }
1988                         else
1989                                 ereport(ERROR,
1990                                                 (errcode(ERRCODE_UNDEFINED_COLUMN),
1991                                                  errmsg("attribute \"%s\" does not exist in Python object", key),
1992                                                  errhint("To return null in a column, "
1993                                                                  "let the returned object have an attribute named "
1994                                                                  "after column with value None.")));
1995
1996                         Py_XDECREF(value);
1997                         value = NULL;
1998                 }
1999                 PG_CATCH();
2000                 {
2001                         Py_XDECREF(so);
2002                         Py_XDECREF(value);
2003                         PG_RE_THROW();
2004                 }
2005                 PG_END_TRY();
2006         }
2007
2008         tuple = heap_form_tuple(desc, values, nulls);
2009         ReleaseTupleDesc(desc);
2010         pfree(values);
2011         pfree(nulls);
2012
2013         return tuple;
2014 }
2015
2016
2017 /* initialization, some python variables function declared here */
2018
2019 /* interface to postgresql elog */
2020 static PyObject *PLy_debug(PyObject *, PyObject *);
2021 static PyObject *PLy_log(PyObject *, PyObject *);
2022 static PyObject *PLy_info(PyObject *, PyObject *);
2023 static PyObject *PLy_notice(PyObject *, PyObject *);
2024 static PyObject *PLy_warning(PyObject *, PyObject *);
2025 static PyObject *PLy_error(PyObject *, PyObject *);
2026 static PyObject *PLy_fatal(PyObject *, PyObject *);
2027
2028 /* PLyPlanObject, PLyResultObject and SPI interface */
2029 #define is_PLyPlanObject(x) ((x)->ob_type == &PLy_PlanType)
2030 static PyObject *PLy_plan_new(void);
2031 static void PLy_plan_dealloc(PyObject *);
2032 static PyObject *PLy_plan_getattr(PyObject *, char *);
2033 static PyObject *PLy_plan_status(PyObject *, PyObject *);
2034
2035 static PyObject *PLy_result_new(void);
2036 static void PLy_result_dealloc(PyObject *);
2037 static PyObject *PLy_result_getattr(PyObject *, char *);
2038 static PyObject *PLy_result_nrows(PyObject *, PyObject *);
2039 static PyObject *PLy_result_status(PyObject *, PyObject *);
2040 static Py_ssize_t PLy_result_length(PyObject *);
2041 static PyObject *PLy_result_item(PyObject *, Py_ssize_t);
2042 static PyObject *PLy_result_slice(PyObject *, Py_ssize_t, Py_ssize_t);
2043 static int      PLy_result_ass_item(PyObject *, Py_ssize_t, PyObject *);
2044 static int      PLy_result_ass_slice(PyObject *, Py_ssize_t, Py_ssize_t, PyObject *);
2045
2046
2047 static PyObject *PLy_spi_prepare(PyObject *, PyObject *);
2048 static PyObject *PLy_spi_execute(PyObject *, PyObject *);
2049 static PyObject *PLy_spi_execute_query(char *query, long limit);
2050 static PyObject *PLy_spi_execute_plan(PyObject *, PyObject *, long);
2051 static PyObject *PLy_spi_execute_fetch_result(SPITupleTable *, int, int);
2052
2053
2054 static PyTypeObject PLy_PlanType = {
2055         PyObject_HEAD_INIT(NULL)
2056         0,                                                      /* ob_size */
2057         "PLyPlan",                                      /* tp_name */
2058         sizeof(PLyPlanObject),          /* tp_size */
2059         0,                                                      /* tp_itemsize */
2060
2061         /*
2062          * methods
2063          */
2064         PLy_plan_dealloc,                       /* tp_dealloc */
2065         0,                                                      /* tp_print */
2066         PLy_plan_getattr,                       /* tp_getattr */
2067         0,                                                      /* tp_setattr */
2068         0,                                                      /* tp_compare */
2069         0,                                                      /* tp_repr */
2070         0,                                                      /* tp_as_number */
2071         0,                                                      /* tp_as_sequence */
2072         0,                                                      /* tp_as_mapping */
2073         0,                                                      /* tp_hash */
2074         0,                                                      /* tp_call */
2075         0,                                                      /* tp_str */
2076         0,                                                      /* tp_getattro */
2077         0,                                                      /* tp_setattro */
2078         0,                                                      /* tp_as_buffer */
2079         Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,       /* tp_flags */
2080         PLy_plan_doc,                           /* tp_doc */
2081 };
2082
2083 static PyMethodDef PLy_plan_methods[] = {
2084         {"status", PLy_plan_status, METH_VARARGS, NULL},
2085         {NULL, NULL, 0, NULL}
2086 };
2087
2088 static PySequenceMethods PLy_result_as_sequence = {
2089         PLy_result_length,                      /* sq_length */
2090         NULL,                                           /* sq_concat */
2091         NULL,                                           /* sq_repeat */
2092         PLy_result_item,                        /* sq_item */
2093         PLy_result_slice,                       /* sq_slice */
2094         PLy_result_ass_item,            /* sq_ass_item */
2095         PLy_result_ass_slice,           /* sq_ass_slice */
2096 };
2097
2098 static PyTypeObject PLy_ResultType = {
2099         PyObject_HEAD_INIT(NULL)
2100         0,                                                      /* ob_size */
2101         "PLyResult",                            /* tp_name */
2102         sizeof(PLyResultObject),        /* tp_size */
2103         0,                                                      /* tp_itemsize */
2104
2105         /*
2106          * methods
2107          */
2108         PLy_result_dealloc,                     /* tp_dealloc */
2109         0,                                                      /* tp_print */
2110         PLy_result_getattr,                     /* tp_getattr */
2111         0,                                                      /* tp_setattr */
2112         0,                                                      /* tp_compare */
2113         0,                                                      /* tp_repr */
2114         0,                                                      /* tp_as_number */
2115         &PLy_result_as_sequence,        /* tp_as_sequence */
2116         0,                                                      /* tp_as_mapping */
2117         0,                                                      /* tp_hash */
2118         0,                                                      /* tp_call */
2119         0,                                                      /* tp_str */
2120         0,                                                      /* tp_getattro */
2121         0,                                                      /* tp_setattro */
2122         0,                                                      /* tp_as_buffer */
2123         Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE,       /* tp_flags */
2124         PLy_result_doc,                         /* tp_doc */
2125 };
2126
2127 static PyMethodDef PLy_result_methods[] = {
2128         {"nrows", PLy_result_nrows, METH_VARARGS, NULL},
2129         {"status", PLy_result_status, METH_VARARGS, NULL},
2130         {NULL, NULL, 0, NULL}
2131 };
2132
2133 static PyMethodDef PLy_methods[] = {
2134         /*
2135          * logging methods
2136          */
2137         {"debug", PLy_debug, METH_VARARGS, NULL},
2138         {"log", PLy_log, METH_VARARGS, NULL},
2139         {"info", PLy_info, METH_VARARGS, NULL},
2140         {"notice", PLy_notice, METH_VARARGS, NULL},
2141         {"warning", PLy_warning, METH_VARARGS, NULL},
2142         {"error", PLy_error, METH_VARARGS, NULL},
2143         {"fatal", PLy_fatal, METH_VARARGS, NULL},
2144
2145         /*
2146          * create a stored plan
2147          */
2148         {"prepare", PLy_spi_prepare, METH_VARARGS, NULL},
2149
2150         /*
2151          * execute a plan or query
2152          */
2153         {"execute", PLy_spi_execute, METH_VARARGS, NULL},
2154
2155         {NULL, NULL, 0, NULL}
2156 };
2157
2158
2159 /* plan object methods */
2160 static PyObject *
2161 PLy_plan_new(void)
2162 {
2163         PLyPlanObject *ob;
2164
2165         if ((ob = PyObject_NEW(PLyPlanObject, &PLy_PlanType)) == NULL)
2166                 return NULL;
2167
2168         ob->plan = NULL;
2169         ob->nargs = 0;
2170         ob->types = NULL;
2171         ob->args = NULL;
2172
2173         return (PyObject *) ob;
2174 }
2175
2176
2177 static void
2178 PLy_plan_dealloc(PyObject * arg)
2179 {
2180         PLyPlanObject *ob = (PLyPlanObject *) arg;
2181
2182         if (ob->plan)
2183                 SPI_freeplan(ob->plan);
2184         if (ob->types)
2185                 PLy_free(ob->types);
2186         if (ob->args)
2187         {
2188                 int                     i;
2189
2190                 for (i = 0; i < ob->nargs; i++)
2191                         PLy_typeinfo_dealloc(&ob->args[i]);
2192                 PLy_free(ob->args);
2193         }
2194
2195         arg->ob_type->tp_free(arg);
2196 }
2197
2198
2199 static PyObject *
2200 PLy_plan_getattr(PyObject * self, char *name)
2201 {
2202         return Py_FindMethod(PLy_plan_methods, self, name);
2203 }
2204
2205 static PyObject *
2206 PLy_plan_status(PyObject * self, PyObject * args)
2207 {
2208         if (PyArg_ParseTuple(args, ""))
2209         {
2210                 Py_INCREF(Py_True);
2211                 return Py_True;
2212                 /* return PyInt_FromLong(self->status); */
2213         }
2214         PLy_exception_set(PLy_exc_error, "plan.status takes no arguments");
2215         return NULL;
2216 }
2217
2218
2219
2220 /* result object methods */
2221
2222 static PyObject *
2223 PLy_result_new(void)
2224 {
2225         PLyResultObject *ob;
2226
2227         if ((ob = PyObject_NEW(PLyResultObject, &PLy_ResultType)) == NULL)
2228                 return NULL;
2229
2230         /* ob->tuples = NULL; */
2231
2232         Py_INCREF(Py_None);
2233         ob->status = Py_None;
2234         ob->nrows = PyInt_FromLong(-1);
2235         ob->rows = PyList_New(0);
2236
2237         return (PyObject *) ob;
2238 }
2239
2240 static void
2241 PLy_result_dealloc(PyObject * arg)
2242 {
2243         PLyResultObject *ob = (PLyResultObject *) arg;
2244
2245         Py_XDECREF(ob->nrows);
2246         Py_XDECREF(ob->rows);
2247         Py_XDECREF(ob->status);
2248
2249         arg->ob_type->tp_free(arg);
2250 }
2251
2252 static PyObject *
2253 PLy_result_getattr(PyObject * self, char *name)
2254 {
2255         return Py_FindMethod(PLy_result_methods, self, name);
2256 }
2257
2258 static PyObject *
2259 PLy_result_nrows(PyObject * self, PyObject * args)
2260 {
2261         PLyResultObject *ob = (PLyResultObject *) self;
2262
2263         Py_INCREF(ob->nrows);
2264         return ob->nrows;
2265 }
2266
2267 static PyObject *
2268 PLy_result_status(PyObject * self, PyObject * args)
2269 {
2270         PLyResultObject *ob = (PLyResultObject *) self;
2271
2272         Py_INCREF(ob->status);
2273         return ob->status;
2274 }
2275
2276 static Py_ssize_t
2277 PLy_result_length(PyObject * arg)
2278 {
2279         PLyResultObject *ob = (PLyResultObject *) arg;
2280
2281         return PyList_Size(ob->rows);
2282 }
2283
2284 static PyObject *
2285 PLy_result_item(PyObject * arg, Py_ssize_t idx)
2286 {
2287         PyObject   *rv;
2288         PLyResultObject *ob = (PLyResultObject *) arg;
2289
2290         rv = PyList_GetItem(ob->rows, idx);
2291         if (rv != NULL)
2292                 Py_INCREF(rv);
2293         return rv;
2294 }
2295
2296 static int
2297 PLy_result_ass_item(PyObject * arg, Py_ssize_t idx, PyObject * item)
2298 {
2299         int                     rv;
2300         PLyResultObject *ob = (PLyResultObject *) arg;
2301
2302         Py_INCREF(item);
2303         rv = PyList_SetItem(ob->rows, idx, item);
2304         return rv;
2305 }
2306
2307 static PyObject *
2308 PLy_result_slice(PyObject * arg, Py_ssize_t lidx, Py_ssize_t hidx)
2309 {
2310         PyObject   *rv;
2311         PLyResultObject *ob = (PLyResultObject *) arg;
2312
2313         rv = PyList_GetSlice(ob->rows, lidx, hidx);
2314         if (rv == NULL)
2315                 return NULL;
2316         Py_INCREF(rv);
2317         return rv;
2318 }
2319
2320 static int
2321 PLy_result_ass_slice(PyObject * arg, Py_ssize_t lidx, Py_ssize_t hidx, PyObject * slice)
2322 {
2323         int                     rv;
2324         PLyResultObject *ob = (PLyResultObject *) arg;
2325
2326         rv = PyList_SetSlice(ob->rows, lidx, hidx, slice);
2327         return rv;
2328 }
2329
2330 /* SPI interface */
2331 static PyObject *
2332 PLy_spi_prepare(PyObject * self, PyObject * args)
2333 {
2334         PLyPlanObject *plan;
2335         PyObject   *list = NULL;
2336         PyObject   *volatile optr = NULL;
2337         char       *query;
2338         void       *tmpplan;
2339         MemoryContext oldcontext;
2340
2341         /* Can't execute more if we have an unhandled error */
2342         if (PLy_error_in_progress)
2343         {
2344                 PLy_exception_set(PLy_exc_error, "transaction aborted");
2345                 return NULL;
2346         }
2347
2348         if (!PyArg_ParseTuple(args, "s|O", &query, &list))
2349         {
2350                 PLy_exception_set(PLy_exc_spi_error,
2351                                                   "invalid arguments for plpy.prepare");
2352                 return NULL;
2353         }
2354
2355         if (list && (!PySequence_Check(list)))
2356         {
2357                 PLy_exception_set(PLy_exc_spi_error,
2358                                                   "second argument of plpy.prepare must be a sequence");
2359                 return NULL;
2360         }
2361
2362         if ((plan = (PLyPlanObject *) PLy_plan_new()) == NULL)
2363                 return NULL;
2364
2365         oldcontext = CurrentMemoryContext;
2366         PG_TRY();
2367         {
2368                 if (list != NULL)
2369                 {
2370                         int                     nargs,
2371                                                 i;
2372
2373                         nargs = PySequence_Length(list);
2374                         if (nargs > 0)
2375                         {
2376                                 plan->nargs = nargs;
2377                                 plan->types = PLy_malloc(sizeof(Oid) * nargs);
2378                                 plan->values = PLy_malloc(sizeof(Datum) * nargs);
2379                                 plan->args = PLy_malloc(sizeof(PLyTypeInfo) * nargs);
2380
2381                                 /*
2382                                  * the other loop might throw an exception, if PLyTypeInfo
2383                                  * member isn't properly initialized the Py_DECREF(plan) will
2384                                  * go boom
2385                                  */
2386                                 for (i = 0; i < nargs; i++)
2387                                 {
2388                                         PLy_typeinfo_init(&plan->args[i]);
2389                                         plan->values[i] = PointerGetDatum(NULL);
2390                                 }
2391
2392                                 for (i = 0; i < nargs; i++)
2393                                 {
2394                                         char       *sptr;
2395                                         HeapTuple       typeTup;
2396                                         Oid                     typeId;
2397                                         int32           typmod;
2398                                         Form_pg_type typeStruct;
2399
2400                                         optr = PySequence_GetItem(list, i);
2401                                         if (!PyString_Check(optr))
2402                                                 ereport(ERROR,
2403                                                                 (errmsg("plpy.prepare: type name at ordinal position %d is not a string", i)));
2404                                         sptr = PyString_AsString(optr);
2405
2406                                         /********************************************************
2407                                          * Resolve argument type names and then look them up by
2408                                          * oid in the system cache, and remember the required
2409                                          *information for input conversion.
2410                                          ********************************************************/
2411
2412                                         parseTypeString(sptr, &typeId, &typmod);
2413
2414                                         typeTup = SearchSysCache(TYPEOID,
2415                                                                                          ObjectIdGetDatum(typeId),
2416                                                                                          0, 0, 0);
2417                                         if (!HeapTupleIsValid(typeTup))
2418                                                 elog(ERROR, "cache lookup failed for type %u", typeId);
2419
2420                                         Py_DECREF(optr);
2421                                         optr = NULL;    /* this is important */
2422
2423                                         plan->types[i] = typeId;
2424                                         typeStruct = (Form_pg_type) GETSTRUCT(typeTup);
2425                                         if (typeStruct->typtype != TYPTYPE_COMPOSITE)
2426                                                 PLy_output_datum_func(&plan->args[i], typeTup);
2427                                         else
2428                                                 ereport(ERROR,
2429                                                                 (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
2430                                                                  errmsg("plpy.prepare does not support composite types")));
2431                                         ReleaseSysCache(typeTup);
2432                                 }
2433                         }
2434                 }
2435
2436                 plan->plan = SPI_prepare(query, plan->nargs, plan->types);
2437                 if (plan->plan == NULL)
2438                         elog(ERROR, "SPI_prepare failed: %s",
2439                                  SPI_result_code_string(SPI_result));
2440
2441                 /* transfer plan from procCxt to topCxt */
2442                 tmpplan = plan->plan;
2443                 plan->plan = SPI_saveplan(tmpplan);
2444                 SPI_freeplan(tmpplan);
2445                 if (plan->plan == NULL)
2446                         elog(ERROR, "SPI_saveplan failed: %s",
2447                                  SPI_result_code_string(SPI_result));
2448         }
2449         PG_CATCH();
2450         {
2451                 MemoryContextSwitchTo(oldcontext);
2452                 PLy_error_in_progress = CopyErrorData();
2453                 FlushErrorState();
2454                 Py_DECREF(plan);
2455                 Py_XDECREF(optr);
2456                 if (!PyErr_Occurred())
2457                         PLy_exception_set(PLy_exc_spi_error,
2458                                                           "unrecognized error in PLy_spi_prepare");
2459                 /* XXX this oughta be replaced with errcontext mechanism */
2460                 PLy_elog(WARNING, "in PL/Python function \"%s\"",
2461                                  PLy_procedure_name(PLy_curr_procedure));
2462                 return NULL;
2463         }
2464         PG_END_TRY();
2465
2466         return (PyObject *) plan;
2467 }
2468
2469 /* execute(query="select * from foo", limit=5)
2470  * execute(plan=plan, values=(foo, bar), limit=5)
2471  */
2472 static PyObject *
2473 PLy_spi_execute(PyObject * self, PyObject * args)
2474 {
2475         char       *query;
2476         PyObject   *plan;
2477         PyObject   *list = NULL;
2478         long            limit = 0;
2479
2480         /* Can't execute more if we have an unhandled error */
2481         if (PLy_error_in_progress)
2482         {
2483                 PLy_exception_set(PLy_exc_error, "transaction aborted");
2484                 return NULL;
2485         }
2486
2487         if (PyArg_ParseTuple(args, "s|l", &query, &limit))
2488                 return PLy_spi_execute_query(query, limit);
2489
2490         PyErr_Clear();
2491
2492         if (PyArg_ParseTuple(args, "O|Ol", &plan, &list, &limit) &&
2493                 is_PLyPlanObject(plan))
2494                 return PLy_spi_execute_plan(plan, list, limit);
2495
2496         PLy_exception_set(PLy_exc_error, "plpy.execute expected a query or a plan");
2497         return NULL;
2498 }
2499
2500 static PyObject *
2501 PLy_spi_execute_plan(PyObject * ob, PyObject * list, long limit)
2502 {
2503         volatile int nargs;
2504         int                     i,
2505                                 rv;
2506         PLyPlanObject *plan;
2507         MemoryContext oldcontext;
2508
2509         if (list != NULL)
2510         {
2511                 if (!PySequence_Check(list) || PyString_Check(list))
2512                 {
2513                         PLy_exception_set(PLy_exc_spi_error, "plpy.execute takes a sequence as its second argument");
2514                         return NULL;
2515                 }
2516                 nargs = PySequence_Length(list);
2517         }
2518         else
2519                 nargs = 0;
2520
2521         plan = (PLyPlanObject *) ob;
2522
2523         if (nargs != plan->nargs)
2524         {
2525                 char       *sv;
2526                 PyObject   *so = PyObject_Str(list);
2527
2528                 if (!so)
2529                         PLy_elog(ERROR, "PL/Python function \"%s\" could not execute plan",
2530                                          PLy_procedure_name(PLy_curr_procedure));
2531                 sv = PyString_AsString(so);
2532                 PLy_exception_set_plural(PLy_exc_spi_error,
2533                                                                  "Expected sequence of %d argument, got %d: %s",
2534                                                                  "Expected sequence of %d arguments, got %d: %s",
2535                                                                  plan->nargs,
2536                                                                  plan->nargs, nargs, sv);
2537                 Py_DECREF(so);
2538
2539                 return NULL;
2540         }
2541
2542         oldcontext = CurrentMemoryContext;
2543         PG_TRY();
2544         {
2545                 char       *nulls = palloc(nargs * sizeof(char));
2546                 volatile int j;
2547
2548                 for (j = 0; j < nargs; j++)
2549                 {
2550                         PyObject   *elem,
2551                                            *so;
2552
2553                         elem = PySequence_GetItem(list, j);
2554                         if (elem != Py_None)
2555                         {
2556                                 so = PyObject_Str(elem);
2557                                 if (!so)
2558                                         PLy_elog(ERROR, "PL/Python function \"%s\" could not execute plan",
2559                                                          PLy_procedure_name(PLy_curr_procedure));
2560                                 Py_DECREF(elem);
2561
2562                                 PG_TRY();
2563                                 {
2564                                         char       *sv = PyString_AsString(so);
2565
2566                                         plan->values[j] =
2567                                                 InputFunctionCall(&(plan->args[j].out.d.typfunc),
2568                                                                                   sv,
2569                                                                                   plan->args[j].out.d.typioparam,
2570                                                                                   -1);
2571                                 }
2572                                 PG_CATCH();
2573                                 {
2574                                         Py_DECREF(so);
2575                                         PG_RE_THROW();
2576                                 }
2577                                 PG_END_TRY();
2578
2579                                 Py_DECREF(so);
2580                                 nulls[j] = ' ';
2581                         }
2582                         else
2583                         {
2584                                 Py_DECREF(elem);
2585                                 plan->values[j] =
2586                                         InputFunctionCall(&(plan->args[j].out.d.typfunc),
2587                                                                           NULL,
2588                                                                           plan->args[j].out.d.typioparam,
2589                                                                           -1);
2590                                 nulls[j] = 'n';
2591                         }
2592                 }
2593
2594                 rv = SPI_execute_plan(plan->plan, plan->values, nulls,
2595                                                           PLy_curr_procedure->fn_readonly, limit);
2596
2597                 pfree(nulls);
2598         }
2599         PG_CATCH();
2600         {
2601                 int                     k;
2602
2603                 MemoryContextSwitchTo(oldcontext);
2604                 PLy_error_in_progress = CopyErrorData();
2605                 FlushErrorState();
2606
2607                 /*
2608                  * cleanup plan->values array
2609                  */
2610                 for (k = 0; k < nargs; k++)
2611                 {
2612                         if (!plan->args[k].out.d.typbyval &&
2613                                 (plan->values[k] != PointerGetDatum(NULL)))
2614                         {
2615                                 pfree(DatumGetPointer(plan->values[k]));
2616                                 plan->values[k] = PointerGetDatum(NULL);
2617                         }
2618                 }
2619
2620                 if (!PyErr_Occurred())
2621                         PLy_exception_set(PLy_exc_error,
2622                                                           "unrecognized error in PLy_spi_execute_plan");
2623                 /* XXX this oughta be replaced with errcontext mechanism */
2624                 PLy_elog(WARNING, "in PL/Python function \"%s\"",
2625                                  PLy_procedure_name(PLy_curr_procedure));
2626                 return NULL;
2627         }
2628         PG_END_TRY();
2629
2630         for (i = 0; i < nargs; i++)
2631         {
2632                 if (!plan->args[i].out.d.typbyval &&
2633                         (plan->values[i] != PointerGetDatum(NULL)))
2634                 {
2635                         pfree(DatumGetPointer(plan->values[i]));
2636                         plan->values[i] = PointerGetDatum(NULL);
2637                 }
2638         }
2639
2640         if (rv < 0)
2641         {
2642                 PLy_exception_set(PLy_exc_spi_error,
2643                                                   "SPI_execute_plan failed: %s",
2644                                                   SPI_result_code_string(rv));
2645                 return NULL;
2646         }
2647
2648         return PLy_spi_execute_fetch_result(SPI_tuptable, SPI_processed, rv);
2649 }
2650
2651 static PyObject *
2652 PLy_spi_execute_query(char *query, long limit)
2653 {
2654         int                     rv;
2655         MemoryContext oldcontext;
2656
2657         oldcontext = CurrentMemoryContext;
2658         PG_TRY();
2659         {
2660                 rv = SPI_execute(query, PLy_curr_procedure->fn_readonly, limit);
2661         }
2662         PG_CATCH();
2663         {
2664                 MemoryContextSwitchTo(oldcontext);
2665                 PLy_error_in_progress = CopyErrorData();
2666                 FlushErrorState();
2667                 if (!PyErr_Occurred())
2668                         PLy_exception_set(PLy_exc_spi_error,
2669                                                           "unrecognized error in PLy_spi_execute_query");
2670                 /* XXX this oughta be replaced with errcontext mechanism */
2671                 PLy_elog(WARNING, "in PL/Python function \"%s\"",
2672                                  PLy_procedure_name(PLy_curr_procedure));
2673                 return NULL;
2674         }
2675         PG_END_TRY();
2676
2677         if (rv < 0)
2678         {
2679                 PLy_exception_set(PLy_exc_spi_error,
2680                                                   "SPI_execute failed: %s",
2681                                                   SPI_result_code_string(rv));
2682                 return NULL;
2683         }
2684
2685         return PLy_spi_execute_fetch_result(SPI_tuptable, SPI_processed, rv);
2686 }
2687
2688 static PyObject *
2689 PLy_spi_execute_fetch_result(SPITupleTable *tuptable, int rows, int status)
2690 {
2691         PLyResultObject *result;
2692         MemoryContext oldcontext;
2693
2694         result = (PLyResultObject *) PLy_result_new();
2695         Py_DECREF(result->status);
2696         result->status = PyInt_FromLong(status);
2697
2698         if (status > 0 && tuptable == NULL)
2699         {
2700                 Py_DECREF(result->nrows);
2701                 result->nrows = PyInt_FromLong(rows);
2702         }
2703         else if (status > 0 && tuptable != NULL)
2704         {
2705                 PLyTypeInfo args;
2706                 int                     i;
2707
2708                 Py_DECREF(result->nrows);
2709                 result->nrows = PyInt_FromLong(rows);
2710                 PLy_typeinfo_init(&args);
2711
2712                 oldcontext = CurrentMemoryContext;
2713                 PG_TRY();
2714                 {
2715                         if (rows)
2716                         {
2717                                 Py_DECREF(result->rows);
2718                                 result->rows = PyList_New(rows);
2719
2720                                 PLy_input_tuple_funcs(&args, tuptable->tupdesc);
2721                                 for (i = 0; i < rows; i++)
2722                                 {
2723                                         PyObject   *row = PLyDict_FromTuple(&args, tuptable->vals[i],
2724                                                                                                                 tuptable->tupdesc);
2725
2726                                         PyList_SetItem(result->rows, i, row);
2727                                 }
2728                                 PLy_typeinfo_dealloc(&args);
2729
2730                                 SPI_freetuptable(tuptable);
2731                         }
2732                 }
2733                 PG_CATCH();
2734                 {
2735                         MemoryContextSwitchTo(oldcontext);
2736                         PLy_error_in_progress = CopyErrorData();
2737                         FlushErrorState();
2738                         if (!PyErr_Occurred())
2739                                 PLy_exception_set(PLy_exc_error,
2740                                                                   "unrecognized error in PLy_spi_execute_fetch_result");
2741                         Py_DECREF(result);
2742                         PLy_typeinfo_dealloc(&args);
2743                         return NULL;
2744                 }
2745                 PG_END_TRY();
2746         }
2747
2748         return (PyObject *) result;
2749 }
2750
2751
2752 /*
2753  * language handler and interpreter initialization
2754  */
2755
2756 /*
2757  * _PG_init()                   - library load-time initialization
2758  *
2759  * DO NOT make this static nor change its name!
2760  */
2761 void
2762 _PG_init(void)
2763 {
2764         /* Be sure we do initialization only once (should be redundant now) */
2765         static bool inited = false;
2766
2767         if (inited)
2768                 return;
2769
2770         pg_bindtextdomain(TEXTDOMAIN);
2771
2772         Py_Initialize();
2773         PLy_init_interp();
2774         PLy_init_plpy();
2775         if (PyErr_Occurred())
2776                 PLy_elog(FATAL, "untrapped error in initialization");
2777         PLy_procedure_cache = PyDict_New();
2778         if (PLy_procedure_cache == NULL)
2779                 PLy_elog(ERROR, "could not create procedure cache");
2780
2781         inited = true;
2782 }
2783
2784 static void
2785 PLy_init_interp(void)
2786 {
2787         PyObject   *mainmod;
2788
2789         mainmod = PyImport_AddModule("__main__");
2790         if (mainmod == NULL || PyErr_Occurred())
2791                 PLy_elog(ERROR, "could not import \"__main__\" module");
2792         Py_INCREF(mainmod);
2793         PLy_interp_globals = PyModule_GetDict(mainmod);
2794         PLy_interp_safe_globals = PyDict_New();
2795         PyDict_SetItemString(PLy_interp_globals, "GD", PLy_interp_safe_globals);
2796         Py_DECREF(mainmod);
2797         if (PLy_interp_globals == NULL || PyErr_Occurred())
2798                 PLy_elog(ERROR, "could not initialize globals");
2799 }
2800
2801 static void
2802 PLy_init_plpy(void)
2803 {
2804         PyObject   *main_mod,
2805                            *main_dict,
2806                            *plpy_mod;
2807         PyObject   *plpy,
2808                            *plpy_dict;
2809
2810         /*
2811          * initialize plpy module
2812          */
2813         if (PyType_Ready(&PLy_PlanType) < 0)
2814                 elog(ERROR, "could not initialize PLy_PlanType");
2815         if (PyType_Ready(&PLy_ResultType) < 0)
2816                 elog(ERROR, "could not initialize PLy_ResultType");
2817
2818         plpy = Py_InitModule("plpy", PLy_methods);
2819         plpy_dict = PyModule_GetDict(plpy);
2820
2821         /* PyDict_SetItemString(plpy, "PlanType", (PyObject *) &PLy_PlanType); */
2822
2823         PLy_exc_error = PyErr_NewException("plpy.Error", NULL, NULL);
2824         PLy_exc_fatal = PyErr_NewException("plpy.Fatal", NULL, NULL);
2825         PLy_exc_spi_error = PyErr_NewException("plpy.SPIError", NULL, NULL);
2826         PyDict_SetItemString(plpy_dict, "Error", PLy_exc_error);
2827         PyDict_SetItemString(plpy_dict, "Fatal", PLy_exc_fatal);
2828         PyDict_SetItemString(plpy_dict, "SPIError", PLy_exc_spi_error);
2829
2830         /*
2831          * initialize main module, and add plpy
2832          */
2833         main_mod = PyImport_AddModule("__main__");
2834         main_dict = PyModule_GetDict(main_mod);
2835         plpy_mod = PyImport_AddModule("plpy");
2836         PyDict_SetItemString(main_dict, "plpy", plpy_mod);
2837         if (PyErr_Occurred())
2838                 elog(ERROR, "could not initialize plpy");
2839 }
2840
2841 /* the python interface to the elog function
2842  * don't confuse these with PLy_elog
2843  */
2844 static PyObject *PLy_output(volatile int, PyObject *, PyObject *);
2845
2846 static PyObject *
2847 PLy_debug(PyObject * self, PyObject * args)
2848 {
2849         return PLy_output(DEBUG2, self, args);
2850 }
2851
2852 static PyObject *
2853 PLy_log(PyObject * self, PyObject * args)
2854 {
2855         return PLy_output(LOG, self, args);
2856 }
2857
2858 static PyObject *
2859 PLy_info(PyObject * self, PyObject * args)
2860 {
2861         return PLy_output(INFO, self, args);
2862 }
2863
2864 static PyObject *
2865 PLy_notice(PyObject * self, PyObject * args)
2866 {
2867         return PLy_output(NOTICE, self, args);
2868 }
2869
2870 static PyObject *
2871 PLy_warning(PyObject * self, PyObject * args)
2872 {
2873         return PLy_output(WARNING, self, args);
2874 }
2875
2876 static PyObject *
2877 PLy_error(PyObject * self, PyObject * args)
2878 {
2879         return PLy_output(ERROR, self, args);
2880 }
2881
2882 static PyObject *
2883 PLy_fatal(PyObject * self, PyObject * args)
2884 {
2885         return PLy_output(FATAL, self, args);
2886 }
2887
2888
2889 static PyObject *
2890 PLy_output(volatile int level, PyObject * self, PyObject * args)
2891 {
2892         PyObject   *so;
2893         char       *volatile sv;
2894         MemoryContext oldcontext;
2895
2896         so = PyObject_Str(args);
2897         if (so == NULL || ((sv = PyString_AsString(so)) == NULL))
2898         {
2899                 level = ERROR;
2900                 sv = dgettext(TEXTDOMAIN, "could not parse error message in plpy.elog");
2901         }
2902
2903         oldcontext = CurrentMemoryContext;
2904         PG_TRY();
2905         {
2906                 elog(level, "%s", sv);
2907         }
2908         PG_CATCH();
2909         {
2910                 MemoryContextSwitchTo(oldcontext);
2911                 PLy_error_in_progress = CopyErrorData();
2912                 FlushErrorState();
2913                 Py_XDECREF(so);
2914
2915                 /*
2916                  * returning NULL here causes the python interpreter to bail. when
2917                  * control passes back to PLy_procedure_call, we check for PG
2918                  * exceptions and re-throw the error.
2919                  */
2920                 PyErr_SetString(PLy_exc_error, sv);
2921                 return NULL;
2922         }
2923         PG_END_TRY();
2924
2925         Py_XDECREF(so);
2926
2927         /*
2928          * return a legal object so the interpreter will continue on its merry way
2929          */
2930         Py_INCREF(Py_None);
2931         return Py_None;
2932 }
2933
2934
2935 /*
2936  * Get the name of the last procedure called by the backend (the
2937  * innermost, if a plpython procedure call calls the backend and the
2938  * backend calls another plpython procedure).
2939  *
2940  * NB: this returns the SQL name, not the internal Python procedure name
2941  */
2942 static char *
2943 PLy_procedure_name(PLyProcedure * proc)
2944 {
2945         if (proc == NULL)
2946                 return "<unknown procedure>";
2947         return proc->proname;
2948 }
2949
2950 /*
2951  * Call PyErr_SetString with a vprint interface and translation support
2952  */
2953 static void
2954 PLy_exception_set(PyObject * exc, const char *fmt,...)
2955 {
2956         char            buf[1024];
2957         va_list         ap;
2958
2959         va_start(ap, fmt);
2960         vsnprintf(buf, sizeof(buf), dgettext(TEXTDOMAIN, fmt), ap);
2961         va_end(ap);
2962
2963         PyErr_SetString(exc, buf);
2964 }
2965
2966 /*
2967  * The same, pluralized.
2968  */
2969 static void
2970 PLy_exception_set_plural(PyObject *exc,
2971                                                  const char *fmt_singular, const char *fmt_plural,
2972                                                  unsigned long n,...)
2973 {
2974         char            buf[1024];
2975         va_list         ap;
2976
2977         va_start(ap, n);
2978         vsnprintf(buf, sizeof(buf),
2979                           dngettext(TEXTDOMAIN, fmt_singular, fmt_plural, n),
2980                           ap);
2981         va_end(ap);
2982
2983         PyErr_SetString(exc, buf);
2984 }
2985
2986 /* Emit a PG error or notice, together with any available info about the
2987  * current Python error.  This should be used to propagate Python errors
2988  * into PG.
2989  */
2990 static void
2991 PLy_elog(int elevel, const char *fmt,...)
2992 {
2993         char       *xmsg;
2994         int                     xlevel;
2995         StringInfoData emsg;
2996
2997         xmsg = PLy_traceback(&xlevel);
2998
2999         initStringInfo(&emsg);
3000         for (;;)
3001         {
3002                 va_list         ap;
3003                 bool            success;
3004
3005                 va_start(ap, fmt);
3006                 success = appendStringInfoVA(&emsg, dgettext(TEXTDOMAIN, fmt), ap);
3007                 va_end(ap);
3008                 if (success)
3009                         break;
3010                 enlargeStringInfo(&emsg, emsg.maxlen);
3011         }
3012
3013         PG_TRY();
3014         {
3015                 ereport(elevel,
3016                                 (errmsg("PL/Python: %s", emsg.data),
3017                                  (xmsg) ? errdetail("%s", xmsg) : 0));
3018         }
3019         PG_CATCH();
3020         {
3021                 pfree(emsg.data);
3022                 if (xmsg)
3023                         pfree(xmsg);
3024                 PG_RE_THROW();
3025         }
3026         PG_END_TRY();
3027
3028         pfree(emsg.data);
3029         if (xmsg)
3030                 pfree(xmsg);
3031 }
3032
3033 static char *
3034 PLy_traceback(int *xlevel)
3035 {
3036         PyObject   *e,
3037                            *v,
3038                            *tb;
3039         PyObject   *eob,
3040                            *vob = NULL;
3041         char       *vstr,
3042                            *estr;
3043         StringInfoData xstr;
3044
3045         /*
3046          * get the current exception
3047          */
3048         PyErr_Fetch(&e, &v, &tb);
3049
3050         /*
3051          * oops, no exception, return
3052          */
3053         if (e == NULL)
3054         {
3055                 *xlevel = WARNING;
3056                 return NULL;
3057         }
3058
3059         PyErr_NormalizeException(&e, &v, &tb);
3060         Py_XDECREF(tb);
3061
3062         eob = PyObject_Str(e);
3063         if (v && ((vob = PyObject_Str(v)) != NULL))
3064                 vstr = PyString_AsString(vob);
3065         else
3066                 vstr = "unknown";
3067
3068         /*
3069          * I'm not sure what to do if eob is NULL here -- we can't call PLy_elog
3070          * because that function calls us, so we could end up with infinite
3071          * recursion.  I'm not even sure if eob could be NULL here -- would an
3072          * Assert() be more appropriate?
3073          */
3074         estr = eob ? PyString_AsString(eob) : "unrecognized exception";
3075         initStringInfo(&xstr);
3076         appendStringInfo(&xstr, "%s: %s", estr, vstr);
3077
3078         Py_DECREF(eob);
3079         Py_XDECREF(vob);
3080         Py_XDECREF(v);
3081
3082         /*
3083          * intuit an appropriate error level based on the exception type
3084          */
3085         if (PLy_exc_error && PyErr_GivenExceptionMatches(e, PLy_exc_error))
3086                 *xlevel = ERROR;
3087         else if (PLy_exc_fatal && PyErr_GivenExceptionMatches(e, PLy_exc_fatal))
3088                 *xlevel = FATAL;
3089         else
3090                 *xlevel = ERROR;
3091
3092         Py_DECREF(e);
3093         return xstr.data;
3094 }
3095
3096 /* python module code */
3097
3098 /* some dumb utility functions */
3099 static void *
3100 PLy_malloc(size_t bytes)
3101 {
3102         void       *ptr = malloc(bytes);
3103
3104         if (ptr == NULL)
3105                 ereport(FATAL,
3106                                 (errcode(ERRCODE_OUT_OF_MEMORY),
3107                                  errmsg("out of memory")));
3108         return ptr;
3109 }
3110
3111 static void *
3112 PLy_malloc0(size_t bytes)
3113 {
3114         void       *ptr = PLy_malloc(bytes);
3115
3116         MemSet(ptr, 0, bytes);
3117         return ptr;
3118 }
3119
3120 static char *
3121 PLy_strdup(const char *str)
3122 {
3123         char       *result;
3124         size_t          len;
3125
3126         len = strlen(str) + 1;
3127         result = PLy_malloc(len);
3128         memcpy(result, str, len);
3129
3130         return result;
3131 }
3132
3133 /* define this away */
3134 static void
3135 PLy_free(void *ptr)
3136 {
3137         free(ptr);
3138 }