1 | /* |
2 | * This Source Code Form is subject to the terms of the Mozilla Public |
3 | * License, v. 2.0. If a copy of the MPL was not distributed with this |
4 | * file, You can obtain one at http://mozilla.org/MPL/2.0/. |
5 | * |
6 | * Copyright 1997 - July 2008 CWI, August 2008 - 2019 MonetDB B.V. |
7 | */ |
8 | |
9 | #include "monetdb_config.h" |
10 | #include "sql_mem.h" |
11 | #include "sql_symbol.h" |
12 | #include "sql_parser.h" |
13 | |
14 | int symbol_debug = 0; |
15 | |
16 | static symbol * |
17 | symbol_init(symbol *s, tokens token, symtype type ) |
18 | { |
19 | s->token = token; |
20 | s->type = type; |
21 | return s; |
22 | } |
23 | |
24 | symbol * |
25 | symbol_create(sql_allocator *sa, tokens token, char *data) |
26 | { |
27 | symbol *s = SA_NEW(sa, symbol); |
28 | |
29 | if (s) { |
30 | symbol_init(s, token, type_string); |
31 | s->data.sval = data; |
32 | if (symbol_debug) |
33 | fprintf(stderr, "%p = symbol_create_string(%s,%s)\n" , s, token2string(s->token), s->data.sval); |
34 | } |
35 | return s; |
36 | } |
37 | |
38 | symbol * |
39 | symbol_create_list(sql_allocator *sa, tokens token, dlist *data) |
40 | { |
41 | symbol *s = SA_NEW(sa, symbol); |
42 | |
43 | if (s) { |
44 | symbol_init(s, token, type_list); |
45 | s->data.lval = data; |
46 | if (symbol_debug) |
47 | fprintf(stderr, "%p = symbol_create_list(%s,%p)\n" , s, token2string(s->token), s->data.lval); |
48 | } |
49 | return s; |
50 | } |
51 | |
52 | symbol * |
53 | symbol_create_int(sql_allocator *sa, tokens token, int data) |
54 | { |
55 | symbol *s = SA_NEW(sa, symbol); |
56 | |
57 | if (s) { |
58 | symbol_init(s, token, type_int); |
59 | s->data.i_val = data; |
60 | if (symbol_debug) |
61 | fprintf(stderr, "%p = symbol_create_int(%s,%d)\n" , s, token2string(s->token), data); |
62 | } |
63 | return s; |
64 | } |
65 | |
66 | symbol * |
67 | symbol_create_lng(sql_allocator *sa, tokens token, lng data) |
68 | { |
69 | symbol *s = SA_NEW(sa, symbol); |
70 | |
71 | if (s) { |
72 | symbol_init(s, token, type_lng); |
73 | s->data.l_val = data; |
74 | if (symbol_debug) |
75 | fprintf(stderr, "%p = symbol_create_lng(%s," LLFMT")\n" , s, token2string(s->token), data); |
76 | } |
77 | return s; |
78 | } |
79 | |
80 | symbol * |
81 | symbol_create_symbol(sql_allocator *sa, tokens token, symbol *data) |
82 | { |
83 | symbol *s = SA_NEW(sa, symbol); |
84 | |
85 | if (s) { |
86 | symbol_init(s, token, type_symbol); |
87 | s->data.sym = data; |
88 | if (symbol_debug) |
89 | fprintf(stderr, "%p = symbol_create_symbol(%s,%s)\n" , s, token2string(s->token), token2string(data->token)); |
90 | } |
91 | return s; |
92 | } |
93 | |
94 | static dnode * |
95 | dnode_create(sql_allocator *sa ) |
96 | { |
97 | dnode *n = SA_NEW(sa, dnode); |
98 | |
99 | if (n) |
100 | n->next = NULL; |
101 | return n; |
102 | } |
103 | |
104 | static dnode * |
105 | dnode_create_string(sql_allocator *sa, const char *data) |
106 | { |
107 | dnode *n = dnode_create(sa); |
108 | |
109 | if (n) { |
110 | n->data.sval = (char*)data; |
111 | n->type = type_string; |
112 | } |
113 | return n; |
114 | } |
115 | static dnode * |
116 | dnode_create_list(sql_allocator *sa, dlist *data) |
117 | { |
118 | dnode *n = dnode_create(sa); |
119 | |
120 | if (n) { |
121 | n->data.lval = data; |
122 | n->type = type_list; |
123 | } |
124 | return n; |
125 | } |
126 | static dnode * |
127 | dnode_create_int(sql_allocator *sa, int data) |
128 | { |
129 | dnode *n = dnode_create(sa); |
130 | |
131 | if (n) { |
132 | n->data.i_val = data; |
133 | n->type = type_int; |
134 | } |
135 | return n; |
136 | } |
137 | static dnode * |
138 | dnode_create_lng(sql_allocator *sa, lng data) |
139 | { |
140 | dnode *n = dnode_create(sa); |
141 | |
142 | if (n) { |
143 | n->data.l_val = data; |
144 | n->type = type_lng; |
145 | } |
146 | return n; |
147 | } |
148 | static dnode * |
149 | dnode_create_symbol(sql_allocator *sa, symbol *data) |
150 | { |
151 | dnode *n = dnode_create(sa); |
152 | |
153 | if (n) { |
154 | n->data.sym = data; |
155 | n->type = type_symbol; |
156 | } |
157 | return n; |
158 | } |
159 | |
160 | static dnode * |
161 | dnode_create_type(sql_allocator *sa, sql_subtype *data) |
162 | { |
163 | dnode *n = dnode_create(sa); |
164 | |
165 | if (n) { |
166 | if (data) |
167 | n->data.typeval = *data; |
168 | else |
169 | n->data.typeval.type = NULL; |
170 | n->type = type_type; |
171 | } |
172 | return n; |
173 | } |
174 | |
175 | dlist * |
176 | dlist_create(sql_allocator *sa) |
177 | { |
178 | dlist *l = SA_NEW(sa, dlist); |
179 | |
180 | if (l) { |
181 | l->h = l->t = NULL; |
182 | l->cnt = 0; |
183 | } |
184 | return l; |
185 | } |
186 | |
187 | int |
188 | dlist_length(dlist *l) |
189 | { |
190 | return l->cnt; |
191 | } |
192 | |
193 | static dlist * |
194 | dlist_append_default(dlist *l, dnode *n) |
195 | { |
196 | if (l->cnt) { |
197 | l->t->next = n; |
198 | } else { |
199 | l->h = n; |
200 | } |
201 | l->t = n; |
202 | l->cnt++; |
203 | return l; |
204 | } |
205 | |
206 | dlist * |
207 | dlist_append_string(sql_allocator *sa, dlist *l, const char *data) |
208 | { |
209 | dnode *n = dnode_create_string(sa, data); |
210 | |
211 | if (!n) |
212 | return NULL; |
213 | return dlist_append_default(l, n); |
214 | } |
215 | |
216 | dlist * |
217 | dlist_append_list(sql_allocator *sa, dlist *l, dlist *data) |
218 | { |
219 | dnode *n = dnode_create_list(sa, data); |
220 | |
221 | if (!n) |
222 | return NULL; |
223 | return dlist_append_default(l, n); |
224 | } |
225 | |
226 | dlist * |
227 | dlist_append_int(sql_allocator *sa, dlist *l, int data) |
228 | { |
229 | dnode *n = dnode_create_int(sa, data); |
230 | |
231 | if (!n) |
232 | return NULL; |
233 | return dlist_append_default(l, n); |
234 | } |
235 | |
236 | dlist * |
237 | dlist_append_lng(sql_allocator *sa, dlist *l, lng data) |
238 | { |
239 | dnode *n = dnode_create_lng(sa, data); |
240 | |
241 | if (!n) |
242 | return NULL; |
243 | return dlist_append_default(l, n); |
244 | } |
245 | |
246 | dlist * |
247 | dlist_append_symbol(sql_allocator *sa, dlist *l, symbol *data) |
248 | { |
249 | dnode *n = dnode_create_symbol(sa, data); |
250 | |
251 | if (!n) |
252 | return NULL; |
253 | return dlist_append_default(l, n); |
254 | } |
255 | |
256 | dlist * |
257 | dlist_append_type(sql_allocator *sa, dlist *l, sql_subtype *data) |
258 | { |
259 | dnode *n = dnode_create_type(sa, data); |
260 | |
261 | if (!n) |
262 | return NULL; |
263 | return dlist_append_default(l, n); |
264 | } |
265 | |
266 | symbol * |
267 | newSelectNode(sql_allocator *sa, int distinct, struct dlist *selection, struct dlist *into, symbol *from, symbol *where, symbol *groupby, symbol *having, symbol *orderby, symbol *name, symbol *limit, symbol *offset, symbol *sample, symbol *window) |
268 | { |
269 | SelectNode *sn = SA_NEW(sa, SelectNode); |
270 | symbol *s = (symbol *) sn; |
271 | |
272 | if (s) { |
273 | symbol_init(s, SQL_SELECT, type_symbol); |
274 | sn->distinct = distinct; |
275 | sn->lateral = 0; |
276 | sn->limit = limit; |
277 | sn->offset = offset; |
278 | sn->sample = sample; |
279 | sn->selection = selection; |
280 | sn->into = into; |
281 | sn->from = from; |
282 | sn->where = where; |
283 | sn->groupby = groupby; |
284 | sn->having = having; |
285 | sn->orderby = orderby; |
286 | sn->name = name; |
287 | sn->window = window; |
288 | } |
289 | return s; |
290 | } |
291 | |
292 | symbol * |
293 | newAtomNode(sql_allocator *sa, atom *data) |
294 | { |
295 | AtomNode *an = SA_NEW(sa, AtomNode); |
296 | symbol *s = (symbol *) an; |
297 | |
298 | if (s) { |
299 | symbol_init(s, SQL_ATOM, type_symbol); |
300 | an->a = data; |
301 | } |
302 | return s; |
303 | } |
304 | |