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 : /*
14 : * (authors) M. Kersten
15 : *
16 : * MAL builder
17 : * The MAL builder library containst the primitives to simplify construction
18 : * of programs by compilers. It has grown out of the MonetDB/SQL code generator.
19 : * The strings being passed as arguments are copied in the process.
20 : *
21 : */
22 : #include "monetdb_config.h"
23 : #include "mal_builder.h"
24 : #include "mal_function.h"
25 : #include "mal_namespace.h"
26 :
27 : InstrPtr
28 16676306 : newAssignmentArgs(MalBlkPtr mb, int args)
29 : {
30 16676306 : InstrPtr q = newInstructionArgs(mb, NULL, NULL, args);
31 16676163 : int k;
32 :
33 16676163 : if (q == NULL)
34 : return NULL;
35 16676162 : k = newTmpVariable(mb, TYPE_any);
36 16675350 : if (k < 0) {
37 : // construct an exception message to be passed to upper layers using ->errors
38 0 : str msg = createException(MAL, "newAssignment",
39 : "Can not allocate variable");
40 0 : addMalException(mb, msg);
41 0 : freeException(msg);
42 0 : freeInstruction(q);
43 0 : return NULL;
44 : }
45 16675350 : getArg(q, 0) = k;
46 16675350 : return q;
47 : }
48 :
49 : InstrPtr
50 3316931 : newAssignment(MalBlkPtr mb)
51 : {
52 3316931 : return newAssignmentArgs(mb, MAXARG);
53 : }
54 :
55 : InstrPtr
56 6920140 : newStmt(MalBlkPtr mb, const char *module, const char *name)
57 : {
58 6920140 : return newStmtArgs(mb, module, name, MAXARG);
59 : }
60 :
61 : InstrPtr
62 9335928 : newStmtArgs(MalBlkPtr mb, const char *module, const char *name, int args)
63 : {
64 9335928 : InstrPtr q;
65 9335928 : const char *mName = putName(module), *nName = putName(name);
66 :
67 9336554 : if (mName == NULL || nName == NULL)
68 : return NULL;
69 :
70 9336554 : q = newInstructionArgs(mb, mName, nName, args);
71 9336083 : if (q == NULL)
72 : return NULL;
73 :
74 9336083 : setDestVar(q, newTmpVariable(mb, TYPE_any));
75 9335470 : if (getDestVar(q) < 0) {
76 0 : str msg = createException(MAL, "newStmtArgs",
77 : "Can not allocate variable");
78 0 : addMalException(mb, msg);
79 0 : freeException(msg);
80 0 : freeInstruction(q);
81 0 : return NULL;
82 : }
83 : return q;
84 : }
85 :
86 : InstrPtr
87 0 : newReturnStmt(MalBlkPtr mb)
88 : {
89 0 : InstrPtr q = newAssignment(mb);
90 :
91 0 : if (q != NULL)
92 0 : q->barrier = RETURNsymbol;
93 0 : return q;
94 : }
95 :
96 : InstrPtr
97 13359427 : newFcnCallArgs(MalBlkPtr mb, const char *mod, const char *fcn, int args)
98 : {
99 13359427 : const char *fcnName, *modName;
100 13359427 : modName = putName(mod);
101 13359412 : fcnName = putName(fcn);
102 13359450 : if (modName == NULL || fcnName == NULL)
103 : return NULL;
104 :
105 13359450 : InstrPtr q = newAssignmentArgs(mb, args);
106 :
107 13358771 : if (q != NULL) {
108 13358771 : setModuleId(q, modName);
109 13359474 : setFunctionId(q, fcnName);
110 : }
111 : return q;
112 : }
113 :
114 : InstrPtr
115 13358306 : newFcnCall(MalBlkPtr mb, const char *mod, const char *fcn)
116 : {
117 13358306 : return newFcnCallArgs(mb, mod, fcn, MAXARG);
118 : }
119 :
120 : InstrPtr
121 0 : newComment(MalBlkPtr mb, const char *val)
122 : {
123 0 : InstrPtr q = newInstruction(mb, NULL, NULL);
124 0 : ValRecord cst;
125 0 : int k;
126 :
127 0 : if (q == NULL)
128 : return NULL;
129 0 : q->token = REMsymbol;
130 0 : q->barrier = 0;
131 0 : if (VALinit(&cst, TYPE_str, val) == NULL) {
132 0 : str msg = createException(MAL, "newComment", "Can not allocate comment");
133 0 : addMalException(mb, msg);
134 0 : freeException(msg);
135 0 : freeInstruction(q);
136 0 : return NULL;
137 : }
138 0 : k = defConstant(mb, TYPE_str, &cst);
139 0 : if (k < 0) {
140 0 : freeInstruction(q);
141 0 : return NULL;
142 : }
143 0 : getArg(q, 0) = k;
144 0 : clrVarConstant(mb, getArg(q, 0));
145 0 : setVarDisabled(mb, getArg(q, 0));
146 0 : return q;
147 : }
148 :
149 : InstrPtr
150 370 : newCatchStmt(MalBlkPtr mb, const char *nme)
151 : {
152 370 : InstrPtr q = newAssignment(mb);
153 370 : int i = findVariable(mb, nme);
154 :
155 370 : if (q == NULL)
156 : return NULL;
157 370 : q->barrier = CATCHsymbol;
158 370 : if (i < 0) {
159 185 : i = newVariable(mb, nme, strlen(nme), TYPE_str);
160 185 : if (i < 0) {
161 0 : str msg = createException(MAL, "newCatchStmt",
162 : "Can not allocate variable");
163 0 : addMalException(mb, msg);
164 0 : freeException(msg);
165 0 : freeInstruction(q);
166 0 : return NULL;
167 : }
168 : }
169 370 : getArg(q, 0) = i;
170 370 : return q;
171 : }
172 :
173 : InstrPtr
174 185 : newRaiseStmt(MalBlkPtr mb, const char *nme)
175 : {
176 185 : InstrPtr q = newAssignment(mb);
177 185 : int i = findVariable(mb, nme);
178 :
179 185 : if (q == NULL)
180 : return NULL;
181 185 : q->barrier = RAISEsymbol;
182 185 : if (i < 0) {
183 185 : i = newVariable(mb, nme, strlen(nme), TYPE_str);
184 185 : if (i < 0) {
185 0 : str msg = createException(MAL, "newRaiseStmt",
186 : "Can not allocate variable");
187 0 : addMalException(mb, msg);
188 0 : freeException(msg);
189 0 : freeInstruction(q);
190 0 : return NULL;
191 : }
192 : }
193 185 : getArg(q, 0) = i;
194 185 : return q;
195 : }
196 :
197 : InstrPtr
198 370 : newExitStmt(MalBlkPtr mb, const char *nme)
199 : {
200 370 : InstrPtr q = newAssignment(mb);
201 370 : int i = findVariable(mb, nme);
202 :
203 370 : if (q == NULL)
204 : return NULL;
205 370 : q->barrier = EXITsymbol;
206 370 : if (i < 0) {
207 0 : i = newVariable(mb, nme, strlen(nme), TYPE_str);
208 0 : if (i < 0) {
209 0 : str msg = createException(MAL, "newExitStmt",
210 : "Can not allocate variable");
211 0 : addMalException(mb, msg);
212 0 : freeException(msg);
213 0 : freeInstruction(q);
214 0 : return NULL;
215 : }
216 : }
217 370 : getArg(q, 0) = i;
218 370 : return q;
219 : }
220 :
221 : InstrPtr
222 554921 : pushEndInstruction(MalBlkPtr mb)
223 : {
224 554921 : if (mb->errors)
225 : return NULL;
226 554887 : InstrPtr q = newInstruction(mb, NULL, NULL);
227 :
228 554884 : if (q == NULL)
229 : return NULL;
230 554884 : q->token = ENDsymbol;
231 554884 : q->barrier = 0;
232 554884 : q->argc = 0;
233 554884 : q->retc = 0;
234 554884 : q->argv[0] = 0;
235 554884 : pushInstruction(mb, q);
236 554883 : if (mb->errors)
237 : return NULL;
238 : return q;
239 : }
240 :
241 : int
242 924179 : getIntConstant(MalBlkPtr mb, int val)
243 : {
244 924179 : int _t;
245 924179 : ValRecord cst;
246 :
247 924179 : cst.vtype = TYPE_int;
248 924179 : cst.val.ival = val;
249 924179 : cst.len = 0;
250 924179 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
251 924180 : if (_t < 0)
252 397879 : _t = defConstant(mb, TYPE_int, &cst);
253 924179 : return _t;
254 : }
255 :
256 : InstrPtr
257 18186580 : pushInt(MalBlkPtr mb, InstrPtr q, int val)
258 : {
259 18186580 : int _t;
260 18186580 : ValRecord cst;
261 :
262 18186580 : if (q == NULL || mb->errors)
263 : return q;
264 18186611 : cst.vtype = TYPE_int;
265 18186611 : cst.val.ival = val;
266 18186611 : cst.len = 0;
267 18186611 : _t = defConstant(mb, TYPE_int, &cst);
268 18181762 : if (_t >= 0)
269 18181620 : return pushArgument(mb, q, _t);
270 : return q;
271 : }
272 :
273 : int
274 0 : getBteConstant(MalBlkPtr mb, bte val)
275 : {
276 0 : int _t;
277 0 : ValRecord cst;
278 :
279 0 : cst.vtype = TYPE_bte;
280 0 : cst.val.btval = val;
281 0 : cst.len = 0;
282 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
283 0 : if (_t < 0)
284 0 : _t = defConstant(mb, TYPE_bte, &cst);
285 0 : return _t;
286 : }
287 :
288 : InstrPtr
289 0 : pushBte(MalBlkPtr mb, InstrPtr q, bte val)
290 : {
291 0 : int _t;
292 0 : ValRecord cst;
293 :
294 0 : if (q == NULL || mb->errors)
295 : return q;
296 0 : cst.vtype = TYPE_bte;
297 0 : cst.val.btval = val;
298 0 : cst.len = 0;
299 0 : _t = defConstant(mb, TYPE_bte, &cst);
300 0 : if (_t >= 0)
301 0 : return pushArgument(mb, q, _t);
302 : return q;
303 : }
304 :
305 : int
306 0 : getOidConstant(MalBlkPtr mb, oid val)
307 : {
308 0 : int _t;
309 0 : ValRecord cst;
310 :
311 0 : cst.vtype = TYPE_oid;
312 0 : cst.val.oval = val;
313 0 : cst.len = 0;
314 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
315 0 : if (_t < 0)
316 0 : _t = defConstant(mb, TYPE_oid, &cst);
317 0 : return _t;
318 : }
319 :
320 : InstrPtr
321 106 : pushOid(MalBlkPtr mb, InstrPtr q, oid val)
322 : {
323 106 : int _t;
324 106 : ValRecord cst;
325 :
326 106 : if (q == NULL || mb->errors)
327 : return q;
328 106 : cst.vtype = TYPE_oid;
329 106 : cst.val.oval = val;
330 106 : cst.len = 0;
331 106 : _t = defConstant(mb, TYPE_oid, &cst);
332 106 : if (_t >= 0)
333 106 : return pushArgument(mb, q, _t);
334 : return q;
335 : }
336 :
337 : InstrPtr
338 0 : pushVoid(MalBlkPtr mb, InstrPtr q)
339 : {
340 0 : int _t;
341 0 : ValRecord cst;
342 :
343 0 : if (q == NULL || mb->errors)
344 : return q;
345 0 : cst.vtype = TYPE_void;
346 0 : cst.val.oval = oid_nil;
347 0 : cst.len = 0;
348 0 : _t = defConstant(mb, TYPE_void, &cst);
349 0 : if (_t >= 0)
350 0 : return pushArgument(mb, q, _t);
351 : return q;
352 : }
353 :
354 : int
355 0 : getLngConstant(MalBlkPtr mb, lng val)
356 : {
357 0 : int _t;
358 0 : ValRecord cst;
359 :
360 0 : cst.vtype = TYPE_lng;
361 0 : cst.val.lval = val;
362 0 : cst.len = 0;
363 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
364 0 : if (_t < 0)
365 0 : _t = defConstant(mb, TYPE_lng, &cst);
366 0 : return _t;
367 : }
368 :
369 : InstrPtr
370 13620313 : pushLng(MalBlkPtr mb, InstrPtr q, lng val)
371 : {
372 13620313 : int _t;
373 13620313 : ValRecord cst;
374 :
375 13620313 : if (q == NULL || mb->errors)
376 : return q;
377 13620315 : cst.vtype = TYPE_lng;
378 13620315 : cst.val.lval = val;
379 13620315 : cst.len = 0;
380 13620315 : _t = defConstant(mb, TYPE_lng, &cst);
381 13619353 : if (_t >= 0)
382 13619351 : return pushArgument(mb, q, _t);
383 : return q;
384 : }
385 :
386 : int
387 0 : getShtConstant(MalBlkPtr mb, sht val)
388 : {
389 0 : int _t;
390 0 : ValRecord cst;
391 :
392 0 : cst.vtype = TYPE_sht;
393 0 : cst.val.shval = val;
394 0 : cst.len = 0;
395 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
396 0 : if (_t < 0)
397 0 : _t = defConstant(mb, TYPE_sht, &cst);
398 0 : return _t;
399 : }
400 :
401 : InstrPtr
402 0 : pushSht(MalBlkPtr mb, InstrPtr q, sht val)
403 : {
404 0 : int _t;
405 0 : ValRecord cst;
406 :
407 0 : if (q == NULL || mb->errors)
408 : return q;
409 0 : cst.vtype = TYPE_sht;
410 0 : cst.val.shval = val;
411 0 : cst.len = 0;
412 0 : _t = defConstant(mb, TYPE_sht, &cst);
413 0 : if (_t >= 0)
414 0 : return pushArgument(mb, q, _t);
415 : return q;
416 : }
417 :
418 : #ifdef HAVE_HGE
419 : int
420 0 : getHgeConstant(MalBlkPtr mb, hge val)
421 : {
422 0 : int _t;
423 0 : ValRecord cst;
424 :
425 0 : cst.vtype = TYPE_oid;
426 0 : cst.val.hval = val;
427 0 : cst.len = 0;
428 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
429 0 : if (_t < 0)
430 0 : _t = defConstant(mb, TYPE_hge, &cst);
431 0 : return _t;
432 : }
433 :
434 : InstrPtr
435 0 : pushHge(MalBlkPtr mb, InstrPtr q, hge val)
436 : {
437 0 : int _t;
438 0 : ValRecord cst;
439 :
440 0 : if (q == NULL || mb->errors)
441 : return q;
442 0 : cst.vtype = TYPE_hge;
443 0 : cst.val.hval = val;
444 0 : cst.len = 0;
445 0 : _t = defConstant(mb, TYPE_hge, &cst);
446 0 : if (_t >= 0)
447 0 : return pushArgument(mb, q, _t);
448 : return q;
449 : }
450 : #endif
451 :
452 : int
453 0 : getDblConstant(MalBlkPtr mb, dbl val)
454 : {
455 0 : int _t;
456 0 : ValRecord cst;
457 :
458 0 : cst.vtype = TYPE_dbl;
459 0 : cst.val.dval = val;
460 0 : cst.len = 0;
461 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
462 0 : if (_t < 0)
463 0 : _t = defConstant(mb, TYPE_dbl, &cst);
464 0 : return _t;
465 : }
466 :
467 : InstrPtr
468 0 : pushDbl(MalBlkPtr mb, InstrPtr q, dbl val)
469 : {
470 0 : int _t;
471 0 : ValRecord cst;
472 :
473 0 : if (q == NULL || mb->errors)
474 : return q;
475 0 : cst.vtype = TYPE_dbl;
476 0 : cst.val.dval = val;
477 0 : cst.len = 0;
478 0 : _t = defConstant(mb, TYPE_dbl, &cst);
479 0 : if (_t >= 0)
480 0 : return pushArgument(mb, q, _t);
481 : return q;
482 : }
483 :
484 : int
485 0 : getFltConstant(MalBlkPtr mb, flt val)
486 : {
487 0 : int _t;
488 0 : ValRecord cst;
489 :
490 0 : cst.vtype = TYPE_flt;
491 0 : cst.val.fval = val;
492 0 : cst.len = 0;
493 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
494 0 : if (_t < 0)
495 0 : _t = defConstant(mb, TYPE_flt, &cst);
496 0 : return _t;
497 : }
498 :
499 : InstrPtr
500 0 : pushFlt(MalBlkPtr mb, InstrPtr q, flt val)
501 : {
502 0 : int _t;
503 0 : ValRecord cst;
504 :
505 0 : if (q == NULL || mb->errors)
506 : return q;
507 0 : cst.vtype = TYPE_flt;
508 0 : cst.val.fval = val;
509 0 : cst.len = 0;
510 0 : _t = defConstant(mb, TYPE_flt, &cst);
511 0 : if (_t >= 0)
512 0 : return pushArgument(mb, q, _t);
513 : return q;
514 : }
515 :
516 : int
517 3886464 : getStrConstant(MalBlkPtr mb, str val)
518 : {
519 3886464 : int _t;
520 3886464 : ValRecord cst;
521 :
522 3886464 : VALset(&cst, TYPE_str, val);
523 3886388 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
524 3886427 : if (_t < 0) {
525 1044652 : if ((cst.val.sval = GDKmalloc(cst.len)) == NULL)
526 : return -1;
527 1044659 : memcpy(cst.val.sval, val, cst.len); /* includes terminating \0 */
528 1044659 : _t = defConstant(mb, TYPE_str, &cst);
529 : }
530 : return _t;
531 : }
532 :
533 : InstrPtr
534 3698746 : pushStr(MalBlkPtr mb, InstrPtr q, const char *Val)
535 : {
536 3698746 : int _t;
537 3698746 : ValRecord cst;
538 :
539 3698746 : if (q == NULL || mb->errors)
540 : return q;
541 3698754 : if (VALinit(&cst, TYPE_str, Val) == NULL) {
542 0 : str msg = createException(MAL, "pushStr",
543 : "Can not allocate string variable");
544 0 : addMalException(mb, msg);
545 0 : freeException(msg);
546 : } else {
547 3699046 : _t = defConstant(mb, TYPE_str, &cst);
548 3698423 : if (_t >= 0)
549 3698423 : return pushArgument(mb, q, _t);
550 : }
551 : return q;
552 : }
553 :
554 : int
555 0 : getBitConstant(MalBlkPtr mb, bit val)
556 : {
557 0 : int _t;
558 0 : ValRecord cst;
559 :
560 0 : cst.vtype = TYPE_bit;
561 0 : cst.val.btval = val;
562 0 : cst.len = 0;
563 0 : _t = fndConstant(mb, &cst, MAL_VAR_WINDOW);
564 0 : if (_t < 0)
565 0 : _t = defConstant(mb, TYPE_bit, &cst);
566 0 : return _t;
567 : }
568 :
569 : InstrPtr
570 845143 : pushBit(MalBlkPtr mb, InstrPtr q, bit val)
571 : {
572 845143 : int _t;
573 845143 : ValRecord cst;
574 :
575 845143 : if (q == NULL || mb->errors)
576 : return q;
577 845143 : cst.vtype = TYPE_bit;
578 845143 : cst.val.btval = val;
579 845143 : cst.len = 0;
580 845143 : _t = defConstant(mb, TYPE_bit, &cst);
581 845136 : if (_t >= 0)
582 845135 : return pushArgument(mb, q, _t);
583 : return q;
584 : }
585 :
586 : InstrPtr
587 741461 : pushNil(MalBlkPtr mb, InstrPtr q, int tpe)
588 : {
589 741461 : int _t;
590 741461 : ValRecord cst;
591 :
592 741461 : if (q == NULL || mb->errors)
593 : return q;
594 741460 : cst.len = 0;
595 741460 : if (!isaBatType(tpe) && tpe != TYPE_bat) {
596 265551 : assert(tpe < MAXATOMS); /* in particular, tpe!=TYPE_any */
597 265551 : if (tpe == TYPE_void) {
598 80 : cst.vtype = TYPE_void;
599 80 : cst.val.oval = oid_nil;
600 : } else {
601 265471 : if (VALinit(&cst, tpe, ATOMnilptr(tpe)) == NULL) {
602 0 : str msg = createException(MAL, "pushNil",
603 : "Can not allocate nil variable");
604 0 : addMalException(mb, msg);
605 0 : freeException(msg);
606 : }
607 : }
608 265551 : _t = defConstant(mb, tpe, &cst);
609 : } else {
610 475909 : cst.vtype = TYPE_bat;
611 475909 : cst.val.bval = bat_nil;
612 475909 : _t = defConstant(mb, TYPE_bat, &cst);
613 475909 : getVarType(mb, _t) = tpe;
614 : }
615 741460 : if (_t >= 0) {
616 741460 : q = pushArgument(mb, q, _t);
617 : }
618 : return q;
619 : }
620 :
621 : InstrPtr
622 0 : pushNilType(MalBlkPtr mb, InstrPtr q, char *tpe)
623 : {
624 0 : int _t, idx;
625 0 : ValRecord cst;
626 0 : str msg;
627 :
628 0 : if (q == NULL || mb->errors)
629 : return q;
630 0 : idx = getAtomIndex(tpe, strlen(tpe), TYPE_any);
631 0 : if (idx < 0 || idx >= GDKatomcnt || idx >= MAXATOMS) {
632 0 : msg = createException(MAL, "pushNilType",
633 : "Can not allocate type variable");
634 : } else {
635 0 : cst.vtype = TYPE_void;
636 0 : cst.val.oval = oid_nil;
637 0 : cst.len = 0;
638 0 : msg = convertConstant(idx, &cst);
639 0 : if (msg == MAL_SUCCEED) {
640 0 : _t = defConstant(mb, idx, &cst);
641 0 : if (_t >= 0) {
642 0 : return pushArgument(mb, q, _t);
643 : }
644 : }
645 : }
646 0 : if (msg) {
647 0 : addMalException(mb, msg);
648 0 : freeException(msg);
649 : }
650 : return q;
651 : }
652 :
653 : InstrPtr
654 292424 : pushType(MalBlkPtr mb, InstrPtr q, int tpe)
655 : {
656 292424 : int _t;
657 292424 : ValRecord cst;
658 292424 : str msg;
659 :
660 292424 : if (q == NULL || mb->errors)
661 : return q;
662 292424 : cst.vtype = TYPE_void;
663 292424 : cst.val.oval = oid_nil;
664 292424 : cst.len = 0;
665 292424 : msg = convertConstant(tpe, &cst);
666 292423 : if (msg != MAL_SUCCEED) {
667 0 : addMalException(mb, msg);
668 0 : freeException(msg);
669 : } else {
670 292423 : _t = defConstant(mb, tpe, &cst);
671 292412 : if (_t >= 0) {
672 292410 : return pushArgument(mb, q, _t);
673 : }
674 : }
675 : return q;
676 : }
677 :
678 : InstrPtr
679 0 : pushZero(MalBlkPtr mb, InstrPtr q, int tpe)
680 : {
681 0 : int _t;
682 0 : ValRecord cst;
683 0 : str msg;
684 :
685 0 : if (q == NULL || mb->errors)
686 : return q;
687 0 : cst.vtype = TYPE_int;
688 0 : cst.val.ival = 0;
689 0 : cst.len = 0;
690 0 : msg = convertConstant(tpe, &cst);
691 0 : if (msg != MAL_SUCCEED) {
692 0 : addMalException(mb, msg);
693 0 : freeException(msg);
694 : } else {
695 0 : _t = defConstant(mb, tpe, &cst);
696 0 : if (_t >= 0)
697 0 : return pushArgument(mb, q, _t);
698 : }
699 : return q;
700 : }
701 :
702 : InstrPtr
703 1 : pushValue(MalBlkPtr mb, InstrPtr q, ValPtr vr)
704 : {
705 1 : int _t;
706 1 : ValRecord cst;
707 :
708 1 : if (q == NULL || mb->errors)
709 : return q;
710 1 : if (VALcopy(&cst, vr) == NULL) {
711 0 : str msg = createException(MAL, "pushValue", "Can not allocate variable");
712 0 : addMalException(mb, msg);
713 0 : freeException(msg);
714 : } else {
715 1 : _t = defConstant(mb, cst.vtype, &cst);
716 1 : if (_t >= 0)
717 1 : return pushArgument(mb, q, _t);
718 : }
719 : return q;
720 : }
|