Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
P
Postgres FD Implementation
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Abuhujair Javed
Postgres FD Implementation
Commits
970a2d1c
Commit
970a2d1c
authored
Oct 22, 2001
by
Tom Lane
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Rebuild cached function definition after CREATE OR REPLACE FUNCTION.
Fix typlen-vs-typmod errors inherited from pltcl.
parent
b2e859a4
Changes
1
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
121 additions
and
113 deletions
+121
-113
src/pl/plpython/plpython.c
src/pl/plpython/plpython.c
+121
-113
No files found.
src/pl/plpython/plpython.c
View file @
970a2d1c
...
@@ -29,7 +29,7 @@
...
@@ -29,7 +29,7 @@
* MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
* MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.
*
*
* IDENTIFICATION
* IDENTIFICATION
* $Header: /cvsroot/pgsql/src/pl/plpython/plpython.c,v 1.
8 2001/10/06 23:21:45
tgl Exp $
* $Header: /cvsroot/pgsql/src/pl/plpython/plpython.c,v 1.
9 2001/10/22 19:32:27
tgl Exp $
*
*
*********************************************************************
*********************************************************************
*/
*/
...
@@ -73,9 +73,8 @@ typedef PyObject *(*PLyDatumToObFunc) (const char *);
...
@@ -73,9 +73,8 @@ typedef PyObject *(*PLyDatumToObFunc) (const char *);
typedef
struct
PLyDatumToOb
{
typedef
struct
PLyDatumToOb
{
PLyDatumToObFunc
func
;
PLyDatumToObFunc
func
;
FmgrInfo
typfunc
;
FmgrInfo
typfunc
;
Oid
typoutput
;
Oid
typelem
;
Oid
typelem
;
int2
typlen
;
bool
typbyval
;
}
PLyDatumToOb
;
}
PLyDatumToOb
;
typedef
struct
PLyTupleToOb
{
typedef
struct
PLyTupleToOb
{
...
@@ -94,7 +93,7 @@ typedef union PLyTypeInput {
...
@@ -94,7 +93,7 @@ typedef union PLyTypeInput {
typedef
struct
PLyObToDatum
{
typedef
struct
PLyObToDatum
{
FmgrInfo
typfunc
;
FmgrInfo
typfunc
;
Oid
typelem
;
Oid
typelem
;
int2
typlen
;
bool
typbyval
;
}
PLyObToDatum
;
}
PLyObToDatum
;
typedef
struct
PLyObToTuple
{
typedef
struct
PLyObToTuple
{
...
@@ -121,6 +120,8 @@ typedef struct PLyTypeInfo {
...
@@ -121,6 +120,8 @@ typedef struct PLyTypeInfo {
*/
*/
typedef
struct
PLyProcedure
{
typedef
struct
PLyProcedure
{
char
*
proname
;
char
*
proname
;
TransactionId
fn_xmin
;
CommandId
fn_cmin
;
PLyTypeInfo
result
;
/* also used to store info for trigger tuple type */
PLyTypeInfo
result
;
/* also used to store info for trigger tuple type */
PLyTypeInfo
args
[
FUNC_MAX_ARGS
];
PLyTypeInfo
args
[
FUNC_MAX_ARGS
];
int
nargs
;
int
nargs
;
...
@@ -192,11 +193,11 @@ static void PLy_free(void *);
...
@@ -192,11 +193,11 @@ static void PLy_free(void *);
/* sub handlers for functions and triggers
/* sub handlers for functions and triggers
*/
*/
static
Datum
PLy_function_handler
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
);
static
Datum
PLy_function_handler
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
);
static
HeapTuple
PLy_trigger_handler
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
);
static
HeapTuple
PLy_trigger_handler
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
);
static
PyObject
*
PLy_function_build_args
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
);
static
PyObject
*
PLy_function_build_args
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
);
static
PyObject
*
PLy_trigger_build_args
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
,
static
PyObject
*
PLy_trigger_build_args
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
,
HeapTuple
*
);
HeapTuple
*
);
static
HeapTuple
PLy_modify_tuple
(
PLyProcedure
*
,
PyObject
*
,
static
HeapTuple
PLy_modify_tuple
(
PLyProcedure
*
,
PyObject
*
,
TriggerData
*
,
HeapTuple
);
TriggerData
*
,
HeapTuple
);
...
@@ -206,12 +207,14 @@ static PyObject *PLy_procedure_call(PLyProcedure *, char *, PyObject *);
...
@@ -206,12 +207,14 @@ static PyObject *PLy_procedure_call(PLyProcedure *, char *, PyObject *);
/* returns a cached PLyProcedure, or creates, stores and returns
/* returns a cached PLyProcedure, or creates, stores and returns
* a new PLyProcedure.
* a new PLyProcedure.
*/
*/
static
PLyProcedure
*
PLy_procedure_get
(
PG_FUNCTION_ARGS
,
bool
);
static
PLyProcedure
*
PLy_procedure_get
(
FunctionCallInfo
fcinfo
,
bool
);
static
PLyProcedure
*
PLy_procedure_create
(
FunctionCallInfo
fcinfo
,
bool
is_trigger
,
HeapTuple
procTup
,
char
*
key
);
static
PLyProcedure
*
PLy_procedure_create
(
PG_FUNCTION_ARGS
,
bool
,
char
*
);
static
void
PLy_procedure_compile
(
PLyProcedure
*
,
const
char
*
);
static
void
PLy_procedure_compile
(
PLyProcedure
*
,
const
char
*
);
static
char
*
PLy_procedure_munge_source
(
const
char
*
,
const
char
*
);
static
char
*
PLy_procedure_munge_source
(
const
char
*
,
const
char
*
);
static
PLyProcedure
*
PLy_procedure_new
(
const
char
*
name
);
static
void
PLy_procedure_delete
(
PLyProcedure
*
);
static
void
PLy_procedure_delete
(
PLyProcedure
*
);
static
void
PLy_typeinfo_init
(
PLyTypeInfo
*
);
static
void
PLy_typeinfo_init
(
PLyTypeInfo
*
);
...
@@ -249,7 +252,6 @@ static PyObject *PLy_interp_safe = NULL;
...
@@ -249,7 +252,6 @@ static PyObject *PLy_interp_safe = NULL;
static
PyObject
*
PLy_interp_safe_globals
=
NULL
;
static
PyObject
*
PLy_interp_safe_globals
=
NULL
;
static
PyObject
*
PLy_importable_modules
=
NULL
;
static
PyObject
*
PLy_importable_modules
=
NULL
;
static
PyObject
*
PLy_procedure_cache
=
NULL
;
static
PyObject
*
PLy_procedure_cache
=
NULL
;
static
char
*
PLy_procedure_fmt
=
"__plpython_procedure_%s_%u"
;
char
*
PLy_importable_modules_list
[]
=
{
char
*
PLy_importable_modules_list
[]
=
{
"array"
,
"array"
,
...
@@ -387,12 +389,12 @@ plpython_call_handler(PG_FUNCTION_ARGS)
...
@@ -387,12 +389,12 @@ plpython_call_handler(PG_FUNCTION_ARGS)
* to take no arguments and return an argument of type opaque.
* to take no arguments and return an argument of type opaque.
*/
*/
HeapTuple
HeapTuple
PLy_trigger_handler
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
proc
)
PLy_trigger_handler
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
proc
)
{
{
DECLARE_EXC
();
DECLARE_EXC
();
HeapTuple
rv
=
NULL
;
HeapTuple
rv
=
NULL
;
PyObject
*
plargs
=
NULL
;
PyObject
*
volatile
plargs
=
NULL
;
PyObject
*
plrv
=
NULL
;
PyObject
*
volatile
plrv
=
NULL
;
enter
();
enter
();
...
@@ -468,12 +470,16 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
...
@@ -468,12 +470,16 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
HeapTuple
otup
)
HeapTuple
otup
)
{
{
DECLARE_EXC
();
DECLARE_EXC
();
PyObject
*
plntup
,
*
plkeys
,
*
platt
,
*
plval
,
*
plstr
;
PyObject
*
volatile
plntup
;
PyObject
*
volatile
plkeys
;
PyObject
*
volatile
platt
;
PyObject
*
volatile
plval
;
PyObject
*
volatile
plstr
;
HeapTuple
rtup
;
HeapTuple
rtup
;
int
natts
,
i
,
j
,
attn
,
atti
;
int
natts
,
i
,
j
,
attn
,
atti
;
int
*
modattrs
;
int
*
volatile
modattrs
;
Datum
*
modvalues
;
Datum
*
volatile
modvalues
;
char
*
modnulls
;
char
*
volatile
modnulls
;
TupleDesc
tupdesc
;
TupleDesc
tupdesc
;
plntup
=
plkeys
=
platt
=
plval
=
plstr
=
NULL
;
plntup
=
plkeys
=
platt
=
plval
=
plstr
=
NULL
;
...
@@ -556,8 +562,8 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
...
@@ -556,8 +562,8 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
modvalues
[
j
]
=
FunctionCall3
(
&
proc
->
result
.
out
.
r
.
atts
[
atti
].
typfunc
,
modvalues
[
j
]
=
FunctionCall3
(
&
proc
->
result
.
out
.
r
.
atts
[
atti
].
typfunc
,
CStringGetDatum
(
src
),
CStringGetDatum
(
src
),
proc
->
result
.
out
.
r
.
atts
[
atti
].
typelem
,
ObjectIdGetDatum
(
proc
->
result
.
out
.
r
.
atts
[
atti
].
typelem
)
,
proc
->
result
.
out
.
r
.
atts
[
atti
].
typlen
);
Int32GetDatum
(
tupdesc
->
attrs
[
j
]
->
atttypmod
)
);
modnulls
[
j
]
=
' '
;
modnulls
[
j
]
=
' '
;
Py_DECREF
(
plstr
);
Py_DECREF
(
plstr
);
...
@@ -588,13 +594,13 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
...
@@ -588,13 +594,13 @@ PLy_modify_tuple(PLyProcedure *proc, PyObject *pltd, TriggerData *tdata,
}
}
PyObject
*
PyObject
*
PLy_trigger_build_args
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
proc
,
HeapTuple
*
rv
)
PLy_trigger_build_args
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
proc
,
HeapTuple
*
rv
)
{
{
DECLARE_EXC
();
DECLARE_EXC
();
TriggerData
*
tdata
;
TriggerData
*
tdata
;
PyObject
*
pltname
,
*
pltevent
,
*
pltwhen
,
*
pltlevel
,
*
pltrelid
;
PyObject
*
pltname
,
*
pltevent
,
*
pltwhen
,
*
pltlevel
,
*
pltrelid
;
PyObject
*
pltargs
,
*
pytnew
,
*
pytold
;
PyObject
*
pltargs
,
*
pytnew
,
*
pytold
;
PyObject
*
pltdata
=
NULL
;
PyObject
*
volatile
pltdata
=
NULL
;
char
*
stroid
;
char
*
stroid
;
enter
();
enter
();
...
@@ -723,13 +729,13 @@ PLy_trigger_build_args(PG_FUNCTION_ARGS, PLyProcedure *proc, HeapTuple *rv)
...
@@ -723,13 +729,13 @@ PLy_trigger_build_args(PG_FUNCTION_ARGS, PLyProcedure *proc, HeapTuple *rv)
/* function handler and friends
/* function handler and friends
*/
*/
Datum
Datum
PLy_function_handler
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
proc
)
PLy_function_handler
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
proc
)
{
{
DECLARE_EXC
();
DECLARE_EXC
();
Datum
rv
;
Datum
rv
;
PyObject
*
plargs
=
NULL
;
PyObject
*
volatile
plargs
=
NULL
;
PyObject
*
plrv
=
NULL
;
PyObject
*
volatile
plrv
=
NULL
;
PyObject
*
plrv_so
=
NULL
;
PyObject
*
volatile
plrv_so
=
NULL
;
char
*
plrv_sc
;
char
*
plrv_sc
;
enter
();
enter
();
...
@@ -792,9 +798,9 @@ PLy_function_handler(PG_FUNCTION_ARGS, PLyProcedure *proc)
...
@@ -792,9 +798,9 @@ PLy_function_handler(PG_FUNCTION_ARGS, PLyProcedure *proc)
plrv_so
=
PyObject_Str
(
plrv
);
plrv_so
=
PyObject_Str
(
plrv
);
plrv_sc
=
PyString_AsString
(
plrv_so
);
plrv_sc
=
PyString_AsString
(
plrv_so
);
rv
=
FunctionCall3
(
&
proc
->
result
.
out
.
d
.
typfunc
,
rv
=
FunctionCall3
(
&
proc
->
result
.
out
.
d
.
typfunc
,
PointerGetDatum
(
plrv_sc
),
PointerGetDatum
(
plrv_sc
),
proc
->
result
.
out
.
d
.
typelem
,
ObjectIdGetDatum
(
proc
->
result
.
out
.
d
.
typelem
)
,
proc
->
result
.
out
.
d
.
typlen
);
Int32GetDatum
(
-
1
)
);
}
}
RESTORE_EXC
();
RESTORE_EXC
();
...
@@ -828,11 +834,11 @@ PLy_procedure_call(PLyProcedure *proc, char *kargs, PyObject *vargs)
...
@@ -828,11 +834,11 @@ PLy_procedure_call(PLyProcedure *proc, char *kargs, PyObject *vargs)
}
}
PyObject
*
PyObject
*
PLy_function_build_args
(
PG_FUNCTION_ARGS
,
PLyProcedure
*
proc
)
PLy_function_build_args
(
FunctionCallInfo
fcinfo
,
PLyProcedure
*
proc
)
{
{
DECLARE_EXC
();
DECLARE_EXC
();
PyObject
*
arg
=
NULL
;
PyObject
*
volatile
arg
=
NULL
;
PyObject
*
args
=
NULL
;
PyObject
*
volatile
args
=
NULL
;
int
i
;
int
i
;
enter
();
enter
();
...
@@ -868,9 +874,9 @@ PLy_function_build_args(PG_FUNCTION_ARGS, PLyProcedure *proc)
...
@@ -868,9 +874,9 @@ PLy_function_build_args(PG_FUNCTION_ARGS, PLyProcedure *proc)
Datum
dt
;
Datum
dt
;
dt
=
FunctionCall3
(
&
(
proc
->
args
[
i
].
in
.
d
.
typfunc
),
dt
=
FunctionCall3
(
&
(
proc
->
args
[
i
].
in
.
d
.
typfunc
),
fcinfo
->
arg
[
i
],
fcinfo
->
arg
[
i
],
proc
->
args
[
i
].
in
.
d
.
typelem
,
ObjectIdGetDatum
(
proc
->
args
[
i
].
in
.
d
.
typelem
)
,
proc
->
args
[
i
].
in
.
d
.
typlen
);
Int32GetDatum
(
-
1
)
);
ct
=
DatumGetCString
(
dt
);
ct
=
DatumGetCString
(
dt
);
arg
=
(
proc
->
args
[
i
].
in
.
d
.
func
)(
ct
);
arg
=
(
proc
->
args
[
i
].
in
.
d
.
func
)(
ct
);
pfree
(
ct
);
pfree
(
ct
);
...
@@ -898,45 +904,68 @@ PLy_function_build_args(PG_FUNCTION_ARGS, PLyProcedure *proc)
...
@@ -898,45 +904,68 @@ PLy_function_build_args(PG_FUNCTION_ARGS, PLyProcedure *proc)
/* PLyProcedure functions
/* PLyProcedure functions
*/
*/
PLyProcedure
*
static
PLyProcedure
*
PLy_procedure_get
(
PG_FUNCTION_ARGS
,
bool
is_trigger
)
PLy_procedure_get
(
FunctionCallInfo
fcinfo
,
bool
is_trigger
)
{
{
Oid
fn_oid
;
HeapTuple
procTup
;
char
key
[
128
];
char
key
[
128
];
PyObject
*
plproc
;
PyObject
*
plproc
;
PLyProcedure
*
proc
;
PLyProcedure
*
proc
=
NULL
;
int
rv
;
int
rv
;
enter
();
enter
();
rv
=
snprintf
(
key
,
sizeof
(
key
),
"%u"
,
fcinfo
->
flinfo
->
fn_oid
);
fn_oid
=
fcinfo
->
flinfo
->
fn_oid
;
procTup
=
SearchSysCache
(
PROCOID
,
ObjectIdGetDatum
(
fn_oid
),
0
,
0
,
0
);
if
(
!
HeapTupleIsValid
(
procTup
))
elog
(
ERROR
,
"plpython: cache lookup for procedure %u failed"
,
fn_oid
);
rv
=
snprintf
(
key
,
sizeof
(
key
),
"%u%s"
,
fn_oid
,
is_trigger
?
"_trigger"
:
""
);
if
((
rv
>=
sizeof
(
key
))
||
(
rv
<
0
))
if
((
rv
>=
sizeof
(
key
))
||
(
rv
<
0
))
elog
(
FATAL
,
"plpython: Buffer overrun in %s:%d"
,
__FILE__
,
__LINE__
);
elog
(
FATAL
,
"plpython: Buffer overrun in %s:%d"
,
__FILE__
,
__LINE__
);
plproc
=
PyDict_GetItemString
(
PLy_procedure_cache
,
key
);
plproc
=
PyDict_GetItemString
(
PLy_procedure_cache
,
key
);
if
(
plproc
==
NULL
)
return
PLy_procedure_create
(
fcinfo
,
is_trigger
,
key
);
Py_INCREF
(
plproc
);
if
(
plproc
!=
NULL
)
if
(
!
PyCObject_Check
(
plproc
))
{
elog
(
FATAL
,
"plpython: Expected a PyCObject, didn't get one"
);
Py_INCREF
(
plproc
);
if
(
!
PyCObject_Check
(
plproc
))
elog
(
FATAL
,
"plpython: Expected a PyCObject, didn't get one"
);
mark
();
mark
();
proc
=
PyCObject_AsVoidPtr
(
plproc
);
proc
=
PyCObject_AsVoidPtr
(
plproc
);
if
(
proc
->
me
!=
plproc
)
if
(
proc
->
me
!=
plproc
)
elog
(
FATAL
,
"plpython: Aiieee, proc->me != plproc"
);
elog
(
FATAL
,
"plpython: Aiieee, proc->me != plproc"
);
/* did we find an up-to-date cache entry? */
if
(
proc
->
fn_xmin
!=
procTup
->
t_data
->
t_xmin
||
proc
->
fn_cmin
!=
procTup
->
t_data
->
t_cmin
)
{
Py_DECREF
(
plproc
);
proc
=
NULL
;
}
}
if
(
proc
==
NULL
)
proc
=
PLy_procedure_create
(
fcinfo
,
is_trigger
,
procTup
,
key
);
ReleaseSysCache
(
procTup
);
return
proc
;
return
proc
;
}
}
PLyProcedure
*
static
PLyProcedure
*
PLy_procedure_create
(
PG_FUNCTION_ARGS
,
bool
is_trigger
,
char
*
key
)
PLy_procedure_create
(
FunctionCallInfo
fcinfo
,
bool
is_trigger
,
HeapTuple
procTup
,
char
*
key
)
{
{
char
procName
[
256
];
char
procName
[
256
];
DECLARE_EXC
();
DECLARE_EXC
();
HeapTuple
procTup
;
Form_pg_proc
procStruct
;
Form_pg_proc
procStruct
;
Oid
fn_oid
;
PLyProcedure
*
volatile
proc
;
PLyProcedure
*
volatile
proc
;
char
*
volatile
procSource
=
NULL
;
char
*
volatile
procSource
=
NULL
;
Datum
procDatum
;
Datum
procDatum
;
...
@@ -944,19 +973,28 @@ PLy_procedure_create(PG_FUNCTION_ARGS, bool is_trigger, char *key)
...
@@ -944,19 +973,28 @@ PLy_procedure_create(PG_FUNCTION_ARGS, bool is_trigger, char *key)
enter
();
enter
();
fn_oid
=
fcinfo
->
flinfo
->
fn_oid
;
procTup
=
SearchSysCache
(
PROCOID
,
ObjectIdGetDatum
(
fn_oid
),
0
,
0
,
0
);
if
(
!
HeapTupleIsValid
(
procTup
))
elog
(
ERROR
,
"plpython: cache lookup for procedure
\"
%u
\"
failed"
,
fn_oid
);
procStruct
=
(
Form_pg_proc
)
GETSTRUCT
(
procTup
);
procStruct
=
(
Form_pg_proc
)
GETSTRUCT
(
procTup
);
rv
=
snprintf
(
procName
,
sizeof
(
procName
),
PLy_procedure_fmt
,
rv
=
snprintf
(
procName
,
sizeof
(
procName
),
NameStr
(
procStruct
->
proname
),
fn_oid
);
"__plpython_procedure_%s_%u%s"
,
NameStr
(
procStruct
->
proname
),
fcinfo
->
flinfo
->
fn_oid
,
is_trigger
?
"_trigger"
:
""
);
if
((
rv
>=
sizeof
(
procName
))
||
(
rv
<
0
))
if
((
rv
>=
sizeof
(
procName
))
||
(
rv
<
0
))
elog
(
FATAL
,
"plpython: Procedure name would overrun buffer"
);
elog
(
FATAL
,
"plpython: Procedure name would overrun buffer"
);
proc
=
PLy_procedure_new
(
procName
);
proc
=
PLy_malloc
(
sizeof
(
PLyProcedure
));
proc
->
proname
=
PLy_malloc
(
strlen
(
procName
)
+
1
);
strcpy
(
proc
->
proname
,
procName
);
proc
->
fn_xmin
=
procTup
->
t_data
->
t_xmin
;
proc
->
fn_cmin
=
procTup
->
t_data
->
t_cmin
;
PLy_typeinfo_init
(
&
proc
->
result
);
for
(
i
=
0
;
i
<
FUNC_MAX_ARGS
;
i
++
)
PLy_typeinfo_init
(
&
proc
->
args
[
i
]);
proc
->
nargs
=
0
;
proc
->
code
=
proc
->
interp
=
proc
->
reval
=
proc
->
statics
=
NULL
;
proc
->
globals
=
proc
->
me
=
NULL
;
SAVE_EXC
();
SAVE_EXC
();
if
(
TRAP_EXC
())
if
(
TRAP_EXC
())
{
{
...
@@ -1037,8 +1075,6 @@ PLy_procedure_create(PG_FUNCTION_ARGS, bool is_trigger, char *key)
...
@@ -1037,8 +1075,6 @@ PLy_procedure_create(PG_FUNCTION_ARGS, bool is_trigger, char *key)
PointerGetDatum
(
&
procStruct
->
prosrc
));
PointerGetDatum
(
&
procStruct
->
prosrc
));
procSource
=
DatumGetCString
(
procDatum
);
procSource
=
DatumGetCString
(
procDatum
);
ReleaseSysCache
(
procTup
);
PLy_procedure_compile
(
proc
,
procSource
);
PLy_procedure_compile
(
proc
,
procSource
);
pfree
(
procSource
);
pfree
(
procSource
);
...
@@ -1170,29 +1206,6 @@ PLy_procedure_munge_source(const char *name, const char *src)
...
@@ -1170,29 +1206,6 @@ PLy_procedure_munge_source(const char *name, const char *src)
return
mrc
;
return
mrc
;
}
}
PLyProcedure
*
PLy_procedure_new
(
const
char
*
name
)
{
int
i
;
PLyProcedure
*
proc
;
enter
();
proc
=
PLy_malloc
(
sizeof
(
PLyProcedure
));
proc
->
proname
=
PLy_malloc
(
strlen
(
name
)
+
1
);
strcpy
(
proc
->
proname
,
name
);
PLy_typeinfo_init
(
&
proc
->
result
);
for
(
i
=
0
;
i
<
FUNC_MAX_ARGS
;
i
++
)
PLy_typeinfo_init
(
&
proc
->
args
[
i
]);
proc
->
nargs
=
0
;
proc
->
code
=
proc
->
interp
=
proc
->
reval
=
proc
->
statics
=
NULL
;
proc
->
globals
=
proc
->
me
=
NULL
;
leave
();
return
proc
;
}
void
void
PLy_procedure_delete
(
PLyProcedure
*
proc
)
PLy_procedure_delete
(
PLyProcedure
*
proc
)
{
{
...
@@ -1314,8 +1327,8 @@ PLy_output_datum_func2(PLyObToDatum *arg, Form_pg_type typeStruct)
...
@@ -1314,8 +1327,8 @@ PLy_output_datum_func2(PLyObToDatum *arg, Form_pg_type typeStruct)
enter
();
enter
();
perm_fmgr_info
(
typeStruct
->
typinput
,
&
arg
->
typfunc
);
perm_fmgr_info
(
typeStruct
->
typinput
,
&
arg
->
typfunc
);
arg
->
typelem
=
(
Oid
)
typeStruct
->
typelem
;
arg
->
typelem
=
typeStruct
->
typelem
;
arg
->
typ
len
=
typeStruct
->
typlen
;
arg
->
typ
byval
=
typeStruct
->
typbyval
;
}
}
void
void
...
@@ -1334,10 +1347,9 @@ PLy_input_datum_func2(PLyDatumToOb *arg, Form_pg_type typeStruct)
...
@@ -1334,10 +1347,9 @@ PLy_input_datum_func2(PLyDatumToOb *arg, Form_pg_type typeStruct)
{
{
char
*
type
;
char
*
type
;
arg
->
typoutput
=
typeStruct
->
typoutput
;
perm_fmgr_info
(
typeStruct
->
typoutput
,
&
arg
->
typfunc
);
perm_fmgr_info
(
typeStruct
->
typoutput
,
&
arg
->
typfunc
);
arg
->
typlen
=
typeStruct
->
typlen
;
arg
->
typelem
=
typeStruct
->
typelem
;
arg
->
typelem
=
typeStruct
->
typelem
;
arg
->
typbyval
=
typeStruct
->
typbyval
;
/* hmmm, wierd. means this arg will always be converted
/* hmmm, wierd. means this arg will always be converted
* to a python None
* to a python None
...
@@ -1516,9 +1528,10 @@ PLyDict_FromTuple(PLyTypeInfo *info, HeapTuple tuple, TupleDesc desc)
...
@@ -1516,9 +1528,10 @@ PLyDict_FromTuple(PLyTypeInfo *info, HeapTuple tuple, TupleDesc desc)
PyDict_SetItemString
(
dict
,
key
,
Py_None
);
PyDict_SetItemString
(
dict
,
key
,
Py_None
);
else
else
{
{
vdat
=
OidFunctionCall3
(
info
->
in
.
r
.
atts
[
i
].
typoutput
,
vattr
,
vdat
=
FunctionCall3
(
&
info
->
in
.
r
.
atts
[
i
].
typfunc
,
ObjectIdGetDatum
(
info
->
in
.
r
.
atts
[
i
].
typelem
),
vattr
,
Int32GetDatum
(
info
->
in
.
r
.
atts
[
i
].
typlen
));
ObjectIdGetDatum
(
info
->
in
.
r
.
atts
[
i
].
typelem
),
Int32GetDatum
(
desc
->
attrs
[
i
]
->
atttypmod
));
vsrc
=
DatumGetCString
(
vdat
);
vsrc
=
DatumGetCString
(
vdat
);
/* no exceptions allowed
/* no exceptions allowed
...
@@ -1873,7 +1886,7 @@ PLy_spi_prepare(PyObject *self, PyObject *args)
...
@@ -1873,7 +1886,7 @@ PLy_spi_prepare(PyObject *self, PyObject *args)
DECLARE_EXC
();
DECLARE_EXC
();
PLyPlanObject
*
plan
;
PLyPlanObject
*
plan
;
PyObject
*
list
=
NULL
;
PyObject
*
list
=
NULL
;
PyObject
*
optr
=
NULL
;
PyObject
*
volatile
optr
=
NULL
;
char
*
query
;
char
*
query
;
enter
();
enter
();
...
@@ -2037,7 +2050,8 @@ PyObject *
...
@@ -2037,7 +2050,8 @@ PyObject *
PLy_spi_execute_plan
(
PyObject
*
ob
,
PyObject
*
list
,
int
limit
)
PLy_spi_execute_plan
(
PyObject
*
ob
,
PyObject
*
list
,
int
limit
)
{
{
DECLARE_EXC
();
DECLARE_EXC
();
int
nargs
,
i
,
rv
;
volatile
int
nargs
;
int
i
,
rv
;
PLyPlanObject
*
plan
;
PLyPlanObject
*
plan
;
enter
();
enter
();
...
@@ -2080,12 +2094,10 @@ PLy_spi_execute_plan(PyObject *ob, PyObject *list, int limit)
...
@@ -2080,12 +2094,10 @@ PLy_spi_execute_plan(PyObject *ob, PyObject *list, int limit)
*/
*/
for
(
i
=
0
;
i
<
nargs
;
i
++
)
for
(
i
=
0
;
i
<
nargs
;
i
++
)
{
{
/* FIXME -- typbyval the proper check?
if
(
!
plan
->
args
[
i
].
out
.
d
.
typbyval
&&
*/
(
plan
->
values
[
i
]
!=
(
Datum
)
NULL
))
if
((
plan
->
values
[
i
]
!=
(
Datum
)
NULL
)
&&
{
(
plan
->
args
[
i
].
out
.
d
.
typlen
<
0
))
pfree
(
DatumGetPointer
(
plan
->
values
[
i
]));
{
pfree
((
void
*
)
plan
->
values
[
i
]);
plan
->
values
[
i
]
=
(
Datum
)
NULL
;
plan
->
values
[
i
]
=
(
Datum
)
NULL
;
}
}
}
}
...
@@ -2100,21 +2112,19 @@ PLy_spi_execute_plan(PyObject *ob, PyObject *list, int limit)
...
@@ -2100,21 +2112,19 @@ PLy_spi_execute_plan(PyObject *ob, PyObject *list, int limit)
{
{
for
(
i
=
0
;
i
<
nargs
;
i
++
)
for
(
i
=
0
;
i
<
nargs
;
i
++
)
{
{
Datum
typelem
,
typlen
,
dv
;
PyObject
*
elem
,
*
so
;
PyObject
*
elem
,
*
so
;
char
*
sv
;
char
*
sv
;
typelem
=
ObjectIdGetDatum
(
plan
->
args
[
i
].
out
.
d
.
typelem
);
typlen
=
Int32GetDatum
(
plan
->
args
[
i
].
out
.
d
.
typlen
);
elem
=
PySequence_GetItem
(
list
,
i
);
elem
=
PySequence_GetItem
(
list
,
i
);
so
=
PyObject_Str
(
elem
);
so
=
PyObject_Str
(
elem
);
sv
=
PyString_AsString
(
so
);
sv
=
PyString_AsString
(
so
);
dv
=
CStringGetDatum
(
sv
);
/* FIXME -- if this can elog, we have leak
/* FIXME -- if this can elog, we have leak
*/
*/
plan
->
values
[
i
]
=
FunctionCall3
(
&
(
plan
->
args
[
i
].
out
.
d
.
typfunc
),
plan
->
values
[
i
]
=
FunctionCall3
(
&
(
plan
->
args
[
i
].
out
.
d
.
typfunc
),
dv
,
typelem
,
typlen
);
CStringGetDatum
(
sv
),
ObjectIdGetDatum
(
plan
->
args
[
i
].
out
.
d
.
typelem
),
Int32GetDatum
(
-
1
));
Py_DECREF
(
so
);
Py_DECREF
(
so
);
Py_DECREF
(
elem
);
Py_DECREF
(
elem
);
...
@@ -2126,12 +2136,10 @@ PLy_spi_execute_plan(PyObject *ob, PyObject *list, int limit)
...
@@ -2126,12 +2136,10 @@ PLy_spi_execute_plan(PyObject *ob, PyObject *list, int limit)
for
(
i
=
0
;
i
<
nargs
;
i
++
)
for
(
i
=
0
;
i
<
nargs
;
i
++
)
{
{
/* FIXME -- typbyval the proper check?
if
(
!
plan
->
args
[
i
].
out
.
d
.
typbyval
&&
*/
(
plan
->
values
[
i
]
!=
(
Datum
)
NULL
))
if
((
plan
->
values
[
i
]
!=
(
Datum
)
NULL
)
&&
(
plan
->
args
[
i
].
out
.
d
.
typlen
<
0
))
{
{
pfree
(
(
void
*
)
plan
->
values
[
i
]
);
pfree
(
DatumGetPointer
(
plan
->
values
[
i
])
);
plan
->
values
[
i
]
=
(
Datum
)
NULL
;
plan
->
values
[
i
]
=
(
Datum
)
NULL
;
}
}
}
}
...
@@ -2413,11 +2421,11 @@ PLy_notice(PyObject *self, PyObject *args)
...
@@ -2413,11 +2421,11 @@ PLy_notice(PyObject *self, PyObject *args)
PyObject
*
PyObject
*
PLy_log
(
int
level
,
PyObject
*
self
,
PyObject
*
args
)
PLy_log
(
volatile
int
level
,
PyObject
*
self
,
PyObject
*
args
)
{
{
DECLARE_EXC
();
DECLARE_EXC
();
PyObject
*
so
;
PyObject
*
so
;
char
*
sv
;
char
*
volatile
sv
;
enter
();
enter
();
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment