/[ascend]/trunk/ascend/compiler/exprs.c
ViewVC logotype

Contents of /trunk/ascend/compiler/exprs.c

Parent Directory Parent Directory | Revision Log Revision Log


Revision 2781 - (show annotations) (download) (as text)
Fri Jun 20 05:12:07 2014 UTC (4 years, 2 months ago) by jpye
File MIME type: text/x-csrc
File size: 17221 byte(s)
remove RCS comments per warnings from clang 3.4
1 /* ASCEND modelling environment
2 Copyright (C) 2006 Carnegie Mellon University
3 Copyright (C) 1990, 1993, 1994 Thomas Guthrie Epperly
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2, or (at your option)
8 any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program. If not, see <http://www.gnu.org/licenses/>.
17 *//**
18 @file
19 Expression Module
20
21 Requires:
22 #include "utilities/ascConfig.h"
23 #include "fractions.h"
24
25 #include "dimen.h"
26 #include "expr_types.h"
27 *//*
28 by Tom Epperly
29 Last in CVS: $Revision: 1.13 $ $Date: 1998/02/05 16:35:58 $ $Author: ballan $
30 */
31
32 #include <stdio.h>
33 #include <assert.h>
34
35 #include <ascend/general/platform.h>
36 #include <ascend/general/panic.h>
37
38 #include <ascend/general/ascMalloc.h>
39 #include <ascend/general/list.h>
40 #include <ascend/general/pool.h>
41 #include "symtab.h"
42
43
44 #include "functype.h"
45 #include "expr_types.h"
46 #include "func.h"
47 #include "name.h"
48 #include "sets.h"
49 #include "instance_enum.h"
50 #include "cmpfunc.h"
51 #include "exprs.h"
52
53 /*------------------------------------------------------------------------------
54 MEMORY USAGE
55
56 Using 'pool' or else regular malloc...
57 */
58
59 #ifdef ASC_NO_POOL
60 #define EXPRSUSESPOOL FALSE
61 #else
62 #define EXPRSUSESPOOL TRUE
63 #endif
64
65 #if EXPRSUSESPOOL /* using 'g_exprs_pool' for memory management */
66 /** global for our memory manager */
67 static pool_store_t g_exprs_pool = NULL;
68 /* aim for 4096 chunks including malloc overhead */
69 # define EMP_LEN 10
70 # if (SIZEOF_VOID_P == 8)
71 # define EMP_WID 63
72 # else
73 # define EMP_WID 127
74 # endif
75 /* retune rpwid if the size of struct name changes */
76 # define EMP_ELT_SIZE (sizeof(struct Expr))
77 # define EMP_MORE_ELTS 10
78 /**< Number of slots filled if more elements needed.
79 So if the pool grows, it grows by EMP_MORE_ELTS*EMP_WID elements at a time. */
80 # define EMP_MORE_BARS 500
81 /**< This is the number of pool bar slots to add during expansion.
82 not all the slots will be filled immediately. */
83
84 /**
85 This function is called at compiler startup time and destroy at shutdown.
86 */
87 void exprs_init_pool(void) {
88 if (g_exprs_pool != NULL ) {
89 ASC_PANIC("ERROR: exprs_init_pool called twice.\n");
90 }
91 g_exprs_pool = pool_create_store(EMP_LEN, EMP_WID, EMP_ELT_SIZE,
92 EMP_MORE_ELTS, EMP_MORE_BARS);
93 if (g_exprs_pool == NULL) {
94 ASC_PANIC("ERROR: exprs_init_pool unable to allocate pool.\n");
95 }
96 }
97
98 void exprs_destroy_pool(void) {
99 if (g_exprs_pool==NULL) return;
100 pool_clear_store(g_exprs_pool);
101 pool_destroy_store(g_exprs_pool);
102 g_exprs_pool = NULL;
103 }
104
105 void exprs_report_pool()
106 {
107 if (g_exprs_pool==NULL) {
108 FPRINTF(ASCERR,"ExprsPool is empty\n");
109 }
110 FPRINTF(ASCERR,"ExprsPool ");
111 pool_print_store(ASCERR,g_exprs_pool,0);
112 }
113
114 # define EPMALLOC \
115 ((struct Expr *)(pool_get_element(g_exprs_pool)))
116 /**< get a token. Token is the size of the struct struct Expr */
117
118 # define EPFREE(p) \
119 (pool_free_element(g_exprs_pool,((void *)p)))
120 /**< return a struct Expr */
121
122 # define EXPR_CHECK_MEMORY(VAR) \
123 AssertMemory(VAR)
124
125 #else /* not using 'g_exprs_pool'... */
126
127 void exprs_init_pool(void) {}
128 void exprs_destroy_pool(void) {}
129 void exprs_report_pool(void){
130 FPRINTF(ASCERR,"ExprsPool not used at all\n");
131 }
132
133 # define EPFREE(p) \
134 ASC_FREE(p)
135
136 # define EPMALLOC \
137 ASC_NEW(struct Expr)
138
139 # define EXPR_CHECK_MEMORY(VAR) \
140 AssertAllocatedMemory(result,sizeof(struct Expr))
141
142 #endif
143
144
145 # define EXPR_NEW(VAR,TYPE) \
146 VAR = EPMALLOC; \
147 VAR->t = TYPE; \
148 VAR->next = NULL
149
150 /*------------------------------------------------------------------------------
151 CREATION ROUTINES
152 */
153
154 struct Expr *CreateVarExpr(struct Name *n)
155 {
156 register struct Expr *result;
157 assert(n!=NULL);
158 AssertMemory(n);
159 EXPR_NEW(result,e_var);
160 result->v.nptr = n;
161 EXPR_CHECK_MEMORY(result);
162
163 return result;
164 }
165
166 void InitVarExpr(struct Expr *result,CONST struct Name *n)
167 {
168 assert(n!=NULL);
169 AssertMemory(n);
170 result->t = e_var;
171 result->v.nptr = (struct Name *)n;
172 result->next = NULL;
173 }
174
175 struct Expr *CreateOpExpr(enum Expr_enum t)
176 {
177 register struct Expr *result;
178 assert((t!=e_var)&&(t!=e_func)&&(t!=e_int)&&(t!=e_real)&&(t!=e_zero));
179 EXPR_NEW(result,t);
180 #if EXPRSUSESPOOL
181 AssertMemory(result);
182 #else
183 AssertAllocatedMemory(result,sizeof(enum Expr_enum)+sizeof(struct Expr *));
184 #endif
185 return result;
186 }
187
188 struct Expr *CreateSatisfiedExpr(struct Name *n, double tol,
189 CONST dim_type *dims)
190 {
191 register struct Expr *result;
192 EXPR_NEW(result,e_satisfied);
193 result->v.se.sen = n;
194 result->v.se.ser.rvalue = tol;
195 result->v.se.ser.dimensions = dims;
196 EXPR_CHECK_MEMORY(result);
197 return result;
198 }
199
200 struct Expr *CreateFuncExpr(CONST struct Func *f)
201 {
202 register struct Expr *result;
203 EXPR_NEW(result,e_func);
204 result->v.fptr = f;
205 EXPR_CHECK_MEMORY(result);
206 return result;
207 }
208
209 struct Expr *CreateIntExpr(long int i)
210 {
211 register struct Expr *result;
212 EXPR_NEW(result,e_int);
213 result->v.ivalue = i;
214 EXPR_CHECK_MEMORY(result);
215 return result;
216 }
217
218 struct Expr *CreateRealExpr(double r, CONST dim_type *dims)
219 {
220 register struct Expr *result;
221 EXPR_NEW(result,e_real);
222 result->v.r.rvalue = r;
223 result->v.r.dimensions = dims;
224 EXPR_CHECK_MEMORY(result);
225 return result;
226 }
227
228 struct Expr *CreateTrueExpr(void)
229 {
230 register struct Expr *result;
231 EXPR_NEW(result,e_boolean);
232 result->v.bvalue = 1;
233 EXPR_CHECK_MEMORY(result);
234 return result;
235 }
236
237 struct Expr *CreateFalseExpr(void)
238 {
239 register struct Expr *result;
240 EXPR_NEW(result,e_boolean);
241 result->v.bvalue = 0;
242 EXPR_CHECK_MEMORY(result);
243 return result;
244 }
245
246 struct Expr *CreateAnyExpr(void)
247 {
248 register struct Expr *result;
249 EXPR_NEW(result,e_boolean);
250 result->v.bvalue = 2;
251 EXPR_CHECK_MEMORY(result);
252 return result;
253 }
254
255 struct Expr *CreateSetExpr(struct Set *set)
256 {
257 register struct Expr *result;
258 EXPR_NEW(result,e_set);
259 result->v.s = set;
260 EXPR_CHECK_MEMORY(result);
261 return result;
262 }
263
264
265 struct Expr *CreateSymbolExpr(symchar *sym)
266 {
267 register struct Expr *result;
268 assert(AscFindSymbol(sym)!=NULL);
269 EXPR_NEW(result,e_symbol);
270 result->v.sym_ptr = sym;
271 EXPR_CHECK_MEMORY(result);
272 return result;
273 }
274
275 struct Expr *CreateQStringExpr(CONST char *qstr)
276 {
277 register struct Expr *result;
278 EXPR_NEW(result,e_qstring);
279 result->v.sym_ptr = (symchar *)qstr; /* qstr really not symbol */
280 EXPR_CHECK_MEMORY(result);
281 return result;
282 }
283
284 struct Expr *CreateBuiltin(enum Expr_enum t, struct Set *set)
285 {
286 register struct Expr *result;
287 EXPR_NEW(result,t);
288 result->v.s = set;
289 EXPR_CHECK_MEMORY(result);
290 return result;
291 }
292
293 /*------------------------------------------------------------------------------
294 MANIPULATION ROUTINES
295 */
296
297 void LinkExprs(struct Expr *cur, struct Expr *next)
298 {
299 assert(cur!=NULL);
300 AssertMemory(cur);
301 cur->next = next;
302 }
303
304 struct Expr *NextExprF(CONST struct Expr *e)
305 {
306 assert(e!=NULL);
307 AssertMemory(e);
308 return e->next;
309 }
310
311 enum Expr_enum ExprTypeF(CONST struct Expr *e)
312 {
313 assert(e!=NULL);
314 AssertMemory(e);
315 return e->t;
316 }
317
318 CONST struct Name *ExprNameF(CONST struct Expr *e)
319 {
320 assert(e!=NULL);
321 AssertMemory(e);
322 return e->v.nptr;
323 }
324
325 CONST struct Func *ExprFuncF(CONST struct Expr *e)
326 {
327 assert(e!=NULL);
328 AssertMemory(e);
329 return e->v.fptr;
330 }
331
332 long ExprIValueF(CONST struct Expr *e)
333 {
334 assert(e!=NULL);
335 AssertMemory(e);
336 return e->v.ivalue;
337 }
338
339 double ExprRValueF(CONST struct Expr *e)
340 {
341 assert(e!=NULL);
342 AssertMemory(e);
343 return e->v.r.rvalue;
344 }
345
346 CONST dim_type *ExprRDimensionsF(CONST struct Expr *e)
347 {
348 assert(e!=NULL);
349 AssertMemory(e);
350 return e->v.r.dimensions;
351 }
352
353 CONST struct Name *SatisfiedExprNameF(CONST struct Expr *e)
354 {
355 assert(e!=NULL);
356 AssertMemory(e);
357 return e->v.se.sen ;
358 }
359
360 double SatisfiedExprRValueF(CONST struct Expr *e)
361 {
362 assert(e!=NULL);
363 AssertMemory(e);
364 return e->v.se.ser.rvalue;
365 }
366
367 CONST dim_type *SatisfiedExprRDimensionsF(CONST struct Expr *e)
368 {
369 assert(e!=NULL);
370 AssertMemory(e);
371 return e->v.se.ser.dimensions;
372 }
373
374 /* This function can be made HALF as long by being a little
375 * smarter about how we return the head of the list.
376 */
377 struct Expr *CopyExprList(CONST struct Expr *e)
378 {
379 register struct Expr *result, *p;
380 register CONST struct Expr *ep;
381 if (e==NULL) return NULL;
382 AssertMemory(e);
383 ep = e;
384 switch(ep->t){
385 case e_func:
386 result = EPMALLOC;
387 result->v.fptr = ep->v.fptr;
388 break;
389 case e_var:
390 result = EPMALLOC;
391 result->v.nptr = CopyName(ep->v.nptr);
392 break;
393 case e_int:
394 result = EPMALLOC;
395 result->v.ivalue = ep->v.ivalue;
396 break;
397 case e_zero:
398 case e_real:
399 result = EPMALLOC;
400 result->v.r.rvalue = ep->v.r.rvalue;
401 result->v.r.dimensions = ep->v.r.dimensions;
402 break;
403 case e_boolean:
404 result = EPMALLOC;
405 result->v.bvalue = ep->v.bvalue;
406 break;
407 case e_set:
408 result = EPMALLOC;
409 result->v.s = CopySetList(ep->v.s);
410 break;
411 case e_symbol:
412 result = EPMALLOC;
413 result->v.sym_ptr = ep->v.sym_ptr;
414 break;
415 case e_card:
416 case e_choice:
417 case e_sum:
418 case e_prod:
419 case e_union:
420 case e_inter:
421 result = EPMALLOC;
422 result->v.s = CopySetList(ep->v.s);
423 break;
424 default:
425 result = EPMALLOC;
426 break;
427 }
428 result->t = ep->t;
429 AssertMemory(result);
430 p = result;
431 while (ep->next != NULL) {
432 ep = ep->next;
433 AssertMemory(ep);
434 switch(ep->t) {
435 case e_func:
436 p->next = EPMALLOC;
437 p = p->next;
438 p->v.fptr = ep->v.fptr;
439 break;
440 case e_var:
441 p->next = EPMALLOC;
442 p = p->next;
443 p->v.nptr = CopyName(ep->v.nptr);
444 break;
445 case e_int:
446 p->next = EPMALLOC;
447 p = p->next;
448 p->v.ivalue = ep->v.ivalue;
449 break;
450 case e_real:
451 case e_zero:
452 p->next = EPMALLOC;
453 p = p->next;
454 p->v.r.rvalue = ep->v.r.rvalue;
455 p->v.r.dimensions = ep->v.r.dimensions;
456 break;
457 case e_boolean:
458 p->next = EPMALLOC;
459 p = p->next;
460 p->v.bvalue = ep->v.bvalue;
461 break;
462 case e_set:
463 p->next = EPMALLOC;
464 p = p->next;
465 p->v.s = CopySetList(ep->v.s);
466 break;
467 case e_symbol:
468 p->next = EPMALLOC;
469 p = p->next;
470 p->v.sym_ptr = ep->v.sym_ptr;
471 break;
472 case e_card:
473 case e_choice:
474 case e_sum:
475 case e_prod:
476 case e_union:
477 case e_inter:
478 p->next = EPMALLOC;
479 p = p->next;
480 p->v.s = CopySetList(ep->v.s);
481 break;
482 default:
483 p->next = EPMALLOC;
484 p = p->next;
485 break;
486 }
487 p->t = ep->t;
488 AssertMemory(p);
489 }
490 p->next = NULL;
491 AssertMemory(result);
492 return result;
493 }
494
495 void DestroyExprList(struct Expr *e)
496 {
497 register struct Expr *next,*ep;
498 ep = e;
499 while(ep!=NULL) {
500 AssertMemory(ep);
501 next = ep->next;
502 switch(ep->t) {
503 case e_var:
504 DestroyName(ep->v.nptr);
505 break;
506 case e_set:
507 case e_card:
508 case e_choice:
509 case e_sum:
510 case e_prod:
511 case e_union:
512 case e_inter:
513 DestroySetList(ep->v.s);
514 break;
515 default:
516 break;
517 }
518 EPFREE((char *)ep);
519 ep = next;
520 }
521 }
522
523 struct Expr *JoinExprLists(struct Expr *e1, struct Expr *e2)
524 {
525 register struct Expr *e;
526 if (e1 == NULL) return e2;
527 AssertMemory(e1);
528 e = e1;
529 /* find end of expr list */
530 while(e->next) e = e->next;
531 /* link to e2 */
532 e->next = e2;
533 AssertMemory(e1);
534 return e1;
535 }
536
537 unsigned long ExprListLength(CONST struct Expr *e)
538 {
539 register CONST struct Expr *ptr;
540 unsigned long len = 0L;
541
542 AssertMemory(e);
543 ptr = e;
544 while (ptr) {
545 ptr = ptr->next;
546 len++;
547 }
548 return len;
549 }
550
551
552 int ExprBValueF(CONST struct Expr *e)
553 {
554 assert(e&&(e->t==e_boolean));
555 AssertMemory(e);
556 return e->v.bvalue;
557 }
558
559 struct Set *ExprSValueF(CONST struct Expr *e)
560 {
561 assert(e&&(e->t==e_set));
562 AssertMemory(e);
563 return e->v.s;
564 }
565
566 symchar *ExprSymValueF(CONST struct Expr *e)
567 {
568 assert(e&&(e->t==e_symbol));
569 AssertMemory(e);
570 return e->v.sym_ptr;
571 }
572
573 CONST char *ExprQStrValueF(CONST struct Expr *e)
574 {
575 assert(e&&(e->t==e_qstring));
576 AssertMemory(e);
577 return (CONST char *)(e->v.sym_ptr); /* remember not a symbol */
578 }
579
580 CONST struct Set *ExprBuiltinSetF(CONST struct Expr *e)
581 {
582 assert(e!=NULL);
583 AssertMemory(e);
584 return e->v.s;
585 }
586
587 int ExprsEqual(CONST struct Expr *e1, CONST struct Expr *e2)
588 {
589 if (e1==e2) return 1;
590 while ((e1!=NULL)&&(e2!=NULL)){
591 AssertMemory(e1);
592 AssertMemory(e2);
593 if (ExprType(e1)!=ExprType(e2)) return 0;
594 switch(ExprType(e1)){
595 case e_var:
596 if (!NamesEqual(ExprName(e1),ExprName(e2))) return 0;
597 break;
598 case e_func:
599 if (ExprFunc(e1)!=ExprFunc(e2)) return 0;
600 break;
601 case e_int:
602 if (ExprIValue(e1)!=ExprIValue(e2)) return 0;
603 break;
604 case e_real:
605 if ((ExprRValue(e1)!=ExprRValue(e2))||
606 (!SameDimen(ExprRDimensions(e1),ExprRDimensions(e2)))) return 0;
607 break;
608 case e_boolean:
609 if (ExprBValue(e1)!=ExprBValue(e2)) return 0;
610 break;
611 case e_set:
612 if (!SetStructuresEqual(ExprSValue(e1),ExprSValue(e2))) return 0;
613 break;
614 case e_symbol:
615 if (CmpSymchar(ExprSymValue(e1),ExprSymValue(e2))!=0) return 0;
616 break;
617 default: break;
618 }
619 e1 = NextExpr(e1);
620 e2 = NextExpr(e2);
621 }
622 return ((e1==NULL)&&(e2==NULL));
623 }
624
625 int CompareExprs(CONST struct Expr *e1, CONST struct Expr *e2)
626 {
627 int ctmp;
628 long int ltmp;
629 double rtmp;
630 if (e1==e2) return 0;
631 if (e1==NULL) return 1;
632 if (e2==NULL) return -1;
633 while ((e1!=NULL)&&(e2!=NULL)){
634 AssertMemory(e1);
635 AssertMemory(e2);
636 ctmp = ExprType(e1) - ExprType(e2);
637 if (ctmp != 0) {
638 if (ctmp >0) {
639 return 1;
640 } else {
641 return -1;
642 }
643 }
644 switch(ExprType(e1)){
645 case e_var:
646 ctmp = CompareNames(ExprName(e1),ExprName(e2));
647 if (ctmp != 0) return ctmp;
648 break;
649 case e_func:
650 ctmp = strcmp(FuncName(ExprFunc(e1)),FuncName(ExprFunc(e2)));
651 if (ctmp != 0) return ctmp;
652 break;
653 case e_int:
654 ltmp = ExprIValue(e1) - ExprIValue(e2);
655 if (ltmp != 0L) {
656 if (ltmp > 0L) {
657 return 1;
658 } else {
659 return -1;
660 }
661 }
662 break;
663 case e_real:
664 rtmp = ExprRValue(e1) - ExprRValue(e2);
665 if (rtmp != 0.0) {
666 if (rtmp > 0.0) {
667 return 1;
668 } else {
669 return -1;
670 }
671 }
672 ctmp = CmpDimen(ExprRDimensions(e1),ExprRDimensions(e2));
673 if (ctmp != 0) return ctmp;
674 break;
675 case e_boolean:
676 if (ExprBValue(e1)!=ExprBValue(e2)) {
677 if (ExprBValue(e1) >0) {
678 return 1;
679 } else {
680 return -1;
681 }
682 }
683 break;
684 case e_set:
685 ctmp = CompareSetStructures(ExprSValue(e1),ExprSValue(e2));
686 if (ctmp != 0) return ctmp;
687 break;
688 case e_symbol:
689 ctmp = CmpSymchar(ExprSymValue(e1),ExprSymValue(e2));
690 if (ctmp != 0) return ctmp;
691 break;
692
693 case e_nop: /* fallthru */
694 case e_undefined: /* fallthru */
695 case e_glassbox: /* fallthru */
696 case e_blackbox: /* fallthru */
697 case e_opcode: /* fallthru */
698 case e_token: /* fallthru */
699 case e_zero: /* fallthru */
700 case e_uminus: /* fallthru */
701 case e_plus: /* fallthru */
702 case e_minus: /* fallthru */
703 case e_times: /* fallthru */
704 case e_divide: /* fallthru */
705 case e_power: /* fallthru */
706 case e_ipower: /* fallthru */
707 case e_bol_token: /* fallthru */
708 case e_notequal: /* fallthru */
709 case e_equal: /* fallthru */
710 case e_less: /* fallthru */
711 case e_greater: /* fallthru */
712 case e_lesseq: /* fallthru */
713 case e_greatereq: /* fallthru */
714 case e_maximize: /* fallthru */
715 case e_minimize: /* fallthru */
716 case e_boolean_eq: /* fallthru */
717 case e_boolean_neq: /* fallthru */
718 case e_or: /* fallthru */
719 case e_and: /* fallthru */
720 case e_not:
721 break;
722 case e_satisfied:
723 ctmp = CompareNames(SatisfiedExprName(e1),SatisfiedExprName(e2));
724 if (ctmp != 0) return ctmp;
725 rtmp = SatisfiedExprRValue(e1) - SatisfiedExprRValue(e2);
726 if (rtmp != 0.0) {
727 if (rtmp > 0.0) {
728 return 1;
729 } else {
730 return -1;
731 }
732 }
733 ctmp = CmpDimen(SatisfiedExprRDimensions(e1),
734 SatisfiedExprRDimensions(e2));
735 if (ctmp != 0) return ctmp;
736 break;
737 case e_subexpr:
738 case e_const:
739 case e_par:
740 case e_in:
741 case e_st:
742 break;
743 case e_qstring:
744 ctmp = strcmp(ExprQStrValue(e1),ExprQStrValue(e2));
745 if (ctmp != 0) return ctmp;
746 break;
747 case e_sum: /* fall thru */
748 case e_prod: /* fall thru */
749 case e_card: /* fall thru */
750 case e_choice: /* fall thru */
751 case e_union: /* fall thru */
752 case e_inter:
753 ctmp = CompareSetStructures(ExprBuiltinSet(e1),ExprBuiltinSet(e2));
754 if (ctmp != 0) return ctmp;
755 break;
756 }
757 e1 = NextExpr(e1);
758 e2 = NextExpr(e2);
759 }
760 /* shorter is < longer */
761 if (e2!=NULL) return 1;
762 if (e1!=NULL) return -1;
763 return 0;
764 }

john.pye@anu.edu.au
ViewVC Help
Powered by ViewVC 1.1.22