Changeset: 990c7202b0e8 for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB/rev/990c7202b0e8
Modified Files:
sql/backends/monet5/sql_scenario.c
sql/backends/monet5/sql_scenario.h
sql/common/sql_backend.c
sql/common/sql_backend.h
sql/include/sql_catalog.h
sql/server/sql_mvc.h
sql/server/sql_qc.c
sql/storage/store.c
sql/test/miscellaneous/Tests/simple_selects.test
Branch: sqlfuncfix
Log Message:
When a SQL function gets destroyed, delete corresponding backend code so it
won't leak. Extended backend call to pass a module name to retrieve the
function from
diffs (196 lines):
diff --git a/sql/backends/monet5/sql_scenario.c
b/sql/backends/monet5/sql_scenario.c
--- a/sql/backends/monet5/sql_scenario.c
+++ b/sql/backends/monet5/sql_scenario.c
@@ -77,13 +77,22 @@ int SQLdebug = 0;
static const char *sqlinit = NULL;
static MT_Lock sql_contextLock = MT_LOCK_INITIALIZER(sql_contextLock);
+/* if 'mod' not NULL, use it otherwise get the module from the client id */
static void
-monet5_freecode(int clientid, const char *name)
+monet5_freecode(const char *mod, int clientid, const char *name)
{
- str msg;
+ Module m = NULL;
+ str msg = MAL_SUCCEED;
- msg = SQLCacheRemove(MCgetClient(clientid), name);
- if (msg)
+ if (mod) {
+ m = getModule(putName(mod));
+ } else {
+ Client c = MCgetClient(clientid);
+ if (c)
+ m = c->usermodule;
+ }
+
+ if (m && (msg = SQLCacheRemove(m, name)))
freeException(msg); /* do something with error? */
}
@@ -1322,14 +1331,12 @@ SQLengine(Client c)
}
str
-SQLCacheRemove(Client c, const char *nme)
+SQLCacheRemove(Module m, const char *nme)
{
- Symbol s;
-
- s = findSymbolInModule(c->usermodule, nme);
+ Symbol s = findSymbolInModule(m, nme);
if (s == NULL)
throw(MAL, "cache.remove", SQLSTATE(42000) "internal error,
symbol missing\n");
- deleteSymbol(c->usermodule, s);
+ deleteSymbol(m, s);
return MAL_SUCCEED;
}
diff --git a/sql/backends/monet5/sql_scenario.h
b/sql/backends/monet5/sql_scenario.h
--- a/sql/backends/monet5/sql_scenario.h
+++ b/sql/backends/monet5/sql_scenario.h
@@ -31,7 +31,7 @@ extern str handle_error(mvc *m, int psta
extern str SQLstatement(Client cntxt, MalBlkPtr mb, MalStkPtr stk, InstrPtr
pci);
extern str SQLcompile(Client cntxt, MalBlkPtr mb, MalStkPtr stk, InstrPtr pci);
extern str SQLinclude(Client cntxt, MalBlkPtr mb, MalStkPtr stk, InstrPtr pci);
-extern str SQLCacheRemove(Client c, const char *nme);
+extern str SQLCacheRemove(Module m, const char *nme);
sql5_export str SQLescapeString(str s);
extern str SYSupdate_tables(Client cntxt, MalBlkPtr mb, MalStkPtr stk,
InstrPtr pci);
diff --git a/sql/common/sql_backend.c b/sql/common/sql_backend.c
--- a/sql/common/sql_backend.c
+++ b/sql/common/sql_backend.c
@@ -28,10 +28,10 @@
backend_functions be_funcs;
void
-backend_freecode(int clientid, const char *name)
+backend_freecode(const char *mod, int clientid, const char *name)
{
if (be_funcs.fcode != NULL)
- be_funcs.fcode(clientid, name);
+ be_funcs.fcode(mod, clientid, name);
}
char *
diff --git a/sql/common/sql_backend.h b/sql/common/sql_backend.h
--- a/sql/common/sql_backend.h
+++ b/sql/common/sql_backend.h
@@ -13,7 +13,7 @@
#include "sql_catalog.h"
#include "sql_relation.h"
-typedef void (*freecode_fptr) (int clientid, const char *name);
+typedef void (*freecode_fptr) (const char *mod, int clientid, const char
*name);
typedef char *(*create_user_fptr) (ptr mvc, char *user, char *passwd, char
enc, char *fullname, sqlid schema_id, char *schema_path, sqlid grantor_id);
typedef int (*drop_user_fptr) (ptr mvc, char *user);
@@ -44,7 +44,7 @@ typedef struct _backend_functions {
create_sub_backend sub_backend;
} backend_functions;
-extern void backend_freecode(int clientid, const char *name);
+extern void backend_freecode(const char *mod, int clientid, const char *name);
extern char *backend_create_user(ptr mvc, char *user, char *passwd, char enc,
char *fullname, sqlid defschemid, char *schema_path, sqlid grantor);
extern int backend_drop_user(ptr mvc, char *user);
diff --git a/sql/include/sql_catalog.h b/sql/include/sql_catalog.h
--- a/sql/include/sql_catalog.h
+++ b/sql/include/sql_catalog.h
@@ -16,6 +16,9 @@
#include "stream.h"
#include "matomic.h"
+#define sql_shared_module_name "sql"
+#define sql_private_module_name "user"
+
#define tr_none 0
#define tr_readonly 1
#define tr_writable 2
diff --git a/sql/server/sql_mvc.h b/sql/server/sql_mvc.h
--- a/sql/server/sql_mvc.h
+++ b/sql/server/sql_mvc.h
@@ -67,9 +67,6 @@
#define mod_explain 4
#define mod_exec 8
-#define sql_shared_module_name "sql"
-#define sql_private_module_name "user"
-
typedef struct sql_groupby_expression {
symbol *sdef;
tokens token;
diff --git a/sql/server/sql_qc.c b/sql/server/sql_qc.c
--- a/sql/server/sql_qc.c
+++ b/sql/server/sql_qc.c
@@ -31,7 +31,7 @@ static void
cq_delete(int clientid, cq *q)
{
if (q->name)
- backend_freecode(clientid, q->name);
+ backend_freecode(NULL, clientid, q->name);
/* q, params and name are allocated using sa, ie need to be delete last
*/
if (q->sa)
sa_destroy(q->sa);
diff --git a/sql/storage/store.c b/sql/storage/store.c
--- a/sql/storage/store.c
+++ b/sql/storage/store.c
@@ -124,6 +124,10 @@ func_destroy(sqlstore *store, sql_func *
assert(f->base.refcnt > 0);
if (--(f->base.refcnt) > 0)
return;
+ if (f->lang == FUNC_LANG_SQL && f->instantiated) {
+ /* clean backend code */
+ backend_freecode(sql_shared_module_name, 0, f->imp);
+ }
if (f->res)
list_destroy2(f->res, store);
list_destroy2(f->ops, store);
@@ -3274,8 +3278,12 @@ store_reset_sql_functions(sql_trans *tr,
sql_func *f = sql_trans_find_func(tr, fid); /* could have
changed by depending changes */
/* if it is on the same transaction, then don't dup it again */
if (isNew(f) || os_obj_intransaction(f->s->funcs, tr,
&f->base)) {
- f->instantiated = 0;
- _DELETE(f->imp);
+ if (f->instantiated) {
+ /* clean backend code */
+ backend_freecode(sql_shared_module_name, 0,
f->imp);
+ f->instantiated = FALSE;
+ _DELETE(f->imp);
+ }
} else if ((res = func_dup(tr, f, f->s))) {
store->table_api.rids_destroy(joined);
return res;
diff --git a/sql/test/miscellaneous/Tests/simple_selects.test
b/sql/test/miscellaneous/Tests/simple_selects.test
--- a/sql/test/miscellaneous/Tests/simple_selects.test
+++ b/sql/test/miscellaneous/Tests/simple_selects.test
@@ -869,3 +869,28 @@ select json 'iamwrongjson'
statement error
select inet '192.168.1.0/26 thisstringshouldnotbehere'
+statement ok
+create function dosomething() returns int begin return 1; end
+
+query I rowsort
+select dosomething()
+----
+1
+
+statement ok
+start transaction
+
+statement ok
+drop function dosomething
+
+statement ok
+rollback
+
+# make sure the function has backend set if the transaction has to rollback
+query I rowsort
+select dosomething()
+----
+1
+
+statement ok
+drop function dosomething
_______________________________________________
checkin-list mailing list
[email protected]
https://www.monetdb.org/mailman/listinfo/checkin-list