Line data Source code
1 : /*
2 : * SPDX-License-Identifier: MPL-2.0
3 : *
4 : * This Source Code Form is subject to the terms of the Mozilla Public
5 : * License, v. 2.0. If a copy of the MPL was not distributed with this
6 : * file, You can obtain one at http://mozilla.org/MPL/2.0/.
7 : *
8 : * Copyright 2024 MonetDB Foundation;
9 : * Copyright August 2008 - 2023 MonetDB B.V.;
10 : * Copyright 1997 - July 2008 CWI.
11 : */
12 :
13 : #include "monetdb_config.h"
14 :
15 : #include "sql_qc.h"
16 : #include "sql_mvc.h"
17 : #include "sql_atom.h"
18 : #include "rel_exp.h"
19 : #include "gdk_time.h"
20 :
21 : qc *
22 38588 : qc_create(sql_allocator *sa, int clientid, int seqnr)
23 : {
24 38588 : qc *r = SA_NEW(sa, qc);
25 38588 : if (!r)
26 : return NULL;
27 38588 : *r = (qc) {
28 : .clientid = clientid,
29 : .id = seqnr,
30 : };
31 38588 : return r;
32 : }
33 :
34 : static void
35 334 : cq_delete(int clientid, cq *q)
36 : {
37 334 : if (q->name)
38 332 : backend_freecode(NULL, clientid, q->name);
39 : /* q, params and name are allocated using sa, ie need to be delete last */
40 334 : if (q->sa)
41 334 : sa_destroy(q->sa);
42 334 : }
43 :
44 : static void
45 179 : cq_restart(int clientid, cq *q)
46 : {
47 179 : if (q->f->imp)
48 179 : backend_freecode(NULL, clientid, q->f->imp);
49 179 : q->f->instantiated = false;
50 179 : }
51 :
52 : void
53 208 : qc_delete(qc *cache, cq *q)
54 : {
55 208 : cq *n, *p = NULL;
56 :
57 208 : if (cache) {
58 209 : for (n = cache->q; n; p = n, n = n->next) {
59 209 : if (n == q) {
60 208 : if (p) {
61 1 : p->next = q->next;
62 : } else {
63 207 : cache->q = q->next;
64 : }
65 208 : cq_delete(cache->clientid, q);
66 208 : cache->nr--;
67 208 : break;
68 : }
69 : }
70 : }
71 208 : }
72 :
73 : void
74 15989 : qc_clean(qc *cache)
75 : {
76 15989 : cq *n, *p = NULL;
77 :
78 15989 : if (cache) {
79 16084 : for (n = cache->q; n; ) {
80 95 : p = n->next;
81 95 : cq_delete(cache->clientid, n);
82 95 : cache->nr--;
83 95 : n = p;
84 : }
85 15989 : cache->q = NULL;
86 : }
87 15989 : }
88 :
89 : void
90 20491 : qc_restart(qc *cache)
91 : {
92 20491 : if (cache) {
93 20670 : for (cq *q = cache->q; q; q = q->next)
94 179 : cq_restart(cache->clientid, q);
95 : }
96 20491 : }
97 :
98 :
99 : void
100 38588 : qc_destroy(qc *cache)
101 : {
102 38588 : cq *q, *n;
103 :
104 38588 : if (cache) {
105 38619 : for (q = cache->q; q; q = n) {
106 31 : n = q->next;
107 :
108 31 : cq_delete(cache->clientid, q);
109 31 : cache->nr--;
110 : }
111 : }
112 38588 : }
113 :
114 : cq *
115 6118 : qc_find(qc *cache, int id)
116 : {
117 6118 : cq *q;
118 :
119 6118 : if (cache) {
120 6119 : for (q = cache->q; q; q = q->next) {
121 6107 : if (q->id == id) {
122 6106 : q->count++;
123 6106 : return q;
124 : }
125 : }
126 : }
127 : return NULL;
128 : }
129 :
130 : cq *
131 334 : qc_insert(qc *cache, sql_allocator *sa, sql_rel *r, symbol *s, list *params, mapi_query_t type, char *cmd, int no_mitosis)
132 : {
133 334 : int namelen;
134 334 : sql_func *f = SA_NEW(sa, sql_func);
135 334 : cq *n = SA_ZNEW(sa, cq);
136 334 : list *res = NULL;
137 :
138 334 : if (!n || !f || !cache)
139 : return NULL;
140 334 : n->id = cache->id++;
141 334 : cache->nr++;
142 :
143 334 : n->sa = sa;
144 334 : n->rel = r;
145 334 : n->s = s;
146 :
147 334 : n->next = cache->q;
148 334 : n->type = type;
149 334 : n->count = 1;
150 334 : namelen = 5 + ((n->id+7)>>3) + ((cache->clientid+7)>>3);
151 334 : char *name = sa_alloc(sa, namelen);
152 334 : n->no_mitosis = no_mitosis;
153 334 : n->created = timestamp_current();
154 334 : if (!name)
155 : return NULL;
156 334 : (void) snprintf(name, namelen, "p%d_%d", n->id, cache->clientid);
157 334 : n->name = name;
158 334 : cache->q = n;
159 :
160 334 : if (r && is_project(r->op) && !list_empty(r->exps)) {
161 285 : sql_arg *a;
162 285 : node *m;
163 :
164 285 : res = sa_list(sa);
165 1798 : for(m = r->exps->h; m; m = m->next) {
166 1513 : sql_exp *e = m->data;
167 1513 : sql_subtype *t = exp_subtype(e);
168 :
169 1513 : a = NULL;
170 1513 : if (t)
171 1508 : a = sql_create_arg(sa, NULL, t, ARG_OUT);
172 1513 : append(res, a);
173 : }
174 : }
175 :
176 334 : *f = (sql_func) {
177 : .mod = sql_private_module_name,
178 : .type = F_PROC,
179 : .lang = FUNC_LANG_SQL,
180 : .query = cmd,
181 : .ops = params,
182 : .res = res,
183 : };
184 334 : base_init(sa, &f->base, 0, true, NULL);
185 334 : f->base.new = 1;
186 334 : f->base.id = n->id;
187 334 : f->base.name = f->imp = name;
188 334 : f->instantiated = true;
189 334 : n->f = f;
190 334 : return n;
191 : }
192 :
193 : int
194 0 : qc_size(qc *cache)
195 : {
196 0 : return cache ? cache->nr : 0;
197 : }
|