]> andersk Git - splint.git/blame - src/constraintTerm.c
Made cosmetic improves to messages.
[splint.git] / src / constraintTerm.c
CommitLineData
616915dd 1/*
2** constraintExpr.c
3*/
4
5//#define DEBUGPRINT 1
6
7# include <ctype.h> /* for isdigit */
8# include "lclintMacros.nf"
9# include "basic.h"
10# include "cgrammar.h"
11# include "cgrammar_tokens.h"
12
13# include "exprChecks.h"
616915dd 14# include "exprNodeSList.h"
15
616915dd 16/*@-czechfcns@*/
17
18//#include "constraintExpr.h"
19
28bf4b0b 20/*@access exprNode @*/
a8e557d3 21
f0171cff 22bool constraintTerm_isDefined (constraintTerm t)
990ec868 23{
24 return t != NULL;
25}
26
28bf4b0b 27/*@unused@*/ static bool constraintTerm_same (constraintTerm p_term1, constraintTerm p_term2) ;
2934b455 28
d46ce6a4 29void constraintTerm_free (/*@only@*/ constraintTerm term)
30{
990ec868 31 llassert (constraintTerm_isDefined (term));
32
d46ce6a4 33 fileloc_free (term->loc);
34
35 switch (term->kind)
36 {
37 case EXPRNODE:
38 /* we don't free an exprNode*/
39 break;
40 case SREF:
41 /* sref */
795e7f34 42 sRef_free (term->value.sref);
d46ce6a4 43 break;
44 case INTLITERAL:
45 /* don't free an int */
46 break;
47 case ERRORBADCONSTRAINTTERMTYPE:
48 default:
49 /* type was set incorrectly */
50 llcontbug (message("constraintTerm_free type was set incorrectly"));
51 }
795e7f34 52 // term->value.intlit = 0;
53 term->kind = ERRORBADCONSTRAINTTERMTYPE;
d46ce6a4 54 free (term);
55}
616915dd 56
4ab867d6 57/*@only@*/ static/*@out@*/ constraintTerm new_constraintTermExpr (void)
616915dd 58{
59 constraintTerm ret;
60 ret = dmalloc (sizeof (* ret ) );
bb25bea6 61 ret->value.intlit = 0;
616915dd 62 return ret;
63}
64
65
66bool constraintTerm_isIntLiteral (constraintTerm term)
67{
dc92450f 68 llassert(term != NULL);
616915dd 69
70 if (term->kind == INTLITERAL)
71 return TRUE;
72
73 return FALSE;
74}
75
d30bc0c7 76
77bool constraintTerm_isInitBlock (/*@observer@*/ /*@temp@*/ constraintTerm c) /*@*/
78{
79 llassert (c != NULL);
80 if (c->kind == EXPRNODE)
81 {
82
83 if (exprNode_isInitBlock(c->value.expr) )
84 {
85 return TRUE;
86 }
87 }
88 return FALSE;
89}
90
91
a779b61e 92bool constraintTerm_isExprNode (/*@observer@*/ /*@temp@*/ constraintTerm c) /*@*/
93{
94 llassert (c != NULL);
95 if (c->kind == EXPRNODE)
96 {
97 return TRUE;
98 }
99 return FALSE;
100}
101
102
d30bc0c7 103int constraintTerm_getInitBlockLength (/*@observer@*/ /*@temp@*/ constraintTerm c) /*@*/
104{
105
106 exprNodeList list;
107 int ret;
108 llassert (c != NULL);
109 llassert (constraintTerm_isInitBlock (c) );
110 llassert (c->kind == EXPRNODE);
111
112 llassert(exprNode_isDefined(c->value.expr) );
113
114 if (exprNode_isUndefined(c->value.expr) )
115 {
116 return 1;
117 }
118
119 if (c->value.expr->edata == exprData_undefined)
120 {
121 return 1;
122 }
123 list = exprData_getArgs(c->value.expr->edata);
124
125 ret = exprNodeList_size(list);
126
127 return ret;
128}
129
130
131
dc92450f 132bool constraintTerm_isStringLiteral (constraintTerm c) /*@*/
616915dd 133{
dc92450f 134 llassert (c != NULL);
616915dd 135 if (c->kind == EXPRNODE)
136 {
137 if (exprNode_knownStringValue(c->value.expr) )
138 {
139 return TRUE;
140 }
141 }
142 return FALSE;
143}
144
d30bc0c7 145
146
616915dd 147cstring constraintTerm_getStringLiteral (constraintTerm c)
148{
dc92450f 149 llassert (c != NULL);
616915dd 150 llassert (constraintTerm_isStringLiteral (c) );
151 llassert (c->kind == EXPRNODE);
152
dc92450f 153 return (cstring_copy ( multiVal_forceString (exprNode_getValue (c->value.expr) ) ) );
616915dd 154}
155
4ab867d6 156constraintTerm constraintTerm_simplify (/*@returned@*/ constraintTerm term) /*@modifies term@*/
616915dd 157{
158 if (term->kind == EXPRNODE)
159 {
160 if ( exprNode_knownIntValue (term->value.expr ) )
161 {
162 long int temp;
28bf4b0b 163
616915dd 164 temp = exprNode_getLongValue (term->value.expr);
dc92450f 165 term->value.intlit = (int)temp;
616915dd 166 term->kind = INTLITERAL;
167 }
168 }
169 return term;
170}
171
172fileloc constraintTerm_getFileloc (constraintTerm t)
173{
990ec868 174 llassert (constraintTerm_isDefined (t));
616915dd 175 return (fileloc_copy (t->loc) );
176}
177
a8e557d3 178constraintTermType constraintTerm_getKind (constraintTerm t)
179{
180 llassert (constraintTerm_isDefined(t) );
181
182 return (t->kind);
183}
184
185/*@exposed@*/ sRef constraintTerm_getSRef (constraintTerm t)
186{
187 llassert (constraintTerm_isDefined(t) );
188 llassert (t->kind == SREF);
189
190 return (t->value.sref);
191}
192
03d670b6 193/*@only@*/ constraintTerm constraintTerm_makeExprNode (/*@dependent@*/ exprNode e)
616915dd 194{
195 constraintTerm ret = new_constraintTermExpr();
d46ce6a4 196 ret->loc = fileloc_copy(exprNode_getfileloc(e));
616915dd 197 ret->value.expr = e;
198 ret->kind = EXPRNODE;
199 ret = constraintTerm_simplify(ret);
200 return ret;
201}
202
28bf4b0b 203/*@only@*/ constraintTerm constraintTerm_makesRef (/*@temp@*/ /*@observer@*/ sRef s)
616915dd 204{
205 constraintTerm ret = new_constraintTermExpr();
206 ret->loc = fileloc_undefined;
4ab867d6 207 ret->value.sref = sRef_saveCopy(s);
616915dd 208 ret->kind = SREF;
209 ret = constraintTerm_simplify(ret);
210 return ret;
211}
212
795e7f34 213
214
616915dd 215constraintTerm constraintTerm_copy (constraintTerm term)
216{
217 constraintTerm ret;
218 ret = new_constraintTermExpr();
219 ret->loc = fileloc_copy (term->loc);
795e7f34 220
221 switch (term->kind)
222 {
223 case EXPRNODE:
224 ret->value.expr = term->value.expr;
225 break;
226 case INTLITERAL:
227 ret->value.intlit = term->value.intlit;
228 break;
229
230 case SREF:
231 ret->value.sref = sRef_saveCopy(term->value.sref);
232 break;
233 default:
234 BADEXIT;
235 }
616915dd 236 ret->kind = term->kind;
237 return ret;
238}
239
d46ce6a4 240constraintTerm constraintTerm_setFileloc (/*@returned@*/ constraintTerm term, fileloc loc)
616915dd 241{
dc92450f 242 llassert(term != NULL);
d46ce6a4 243
28bf4b0b 244 if ( fileloc_isDefined( term->loc ) )
d46ce6a4 245 fileloc_free(term->loc);
246
616915dd 247 term->loc = fileloc_copy(loc);
248 return term;
249}
250
251
d46ce6a4 252static cstring constraintTerm_getName (constraintTerm term)
616915dd 253{
254 cstring s;
255 s = cstring_undefined;
256
257 llassert (term != NULL);
258
259 switch (term->kind)
260 {
261 case EXPRNODE:
262 /*@i334*/ //wtf
263 s = message ("%s", exprNode_unparse (term->value.expr) );
264 break;
265 case INTLITERAL:
a1fa5e0c 266 s = message (" %d ", (int) term->value.intlit);
616915dd 267 break;
268
269 case SREF:
d46ce6a4 270 s = message ("%q", sRef_unparse (term->value.sref) );
616915dd 271
272 break;
c3e695ff 273 default:
274 BADEXIT;
275 /*@notreached@*/
616915dd 276 break;
277 }
616915dd 278
c3e695ff 279 return s;
616915dd 280}
281
282constraintTerm
d46ce6a4 283constraintTerm_doSRefFixBaseParam (/*@returned@*/constraintTerm term, exprNodeList arglist) /*@modifies term@*/
616915dd 284{
285 llassert (term != NULL);
286
287 switch (term->kind)
288 {
289 case EXPRNODE:
290 /*@i334*/ //wtf
291 // s = message ("%s @ %s ", exprNode_unparse (term->value.expr),
292 // fileloc_unparse (term->loc) );
293 break;
294 case INTLITERAL:
295 // s = message (" %d ", term->value.intlit);
296 break;
297
298 case SREF:
299 term->value.sref = sRef_fixBaseParam (term->value.sref, arglist);
300 // s = message ("%s ", sRef_unparse (term->value.sref) );
301
302 break;
c3e695ff 303 default:
304 BADEXIT;
616915dd 305 }
306 return term;
307
308}
309
616915dd 310cstring constraintTerm_print (constraintTerm term) /*@*/
311{
312 cstring s;
313 s = cstring_undefined;
314
315 llassert (term != NULL);
316
317 switch (term->kind)
318 {
319 case EXPRNODE:
320 /*@i334*/ //wtf
a779b61e 321 s = message ("%s @ %q", exprNode_unparse (term->value.expr),
616915dd 322 fileloc_unparse (term->loc) );
323 break;
324 case INTLITERAL:
a779b61e 325 s = message ("%d", (int)term->value.intlit);
616915dd 326 break;
327
328 case SREF:
a779b61e 329 s = message ("%q", sRef_unparseDebug (term->value.sref) );
616915dd 330
331 break;
c3e695ff 332 default:
333 BADEXIT;
616915dd 334 }
335
336 return s;
337}
338
339
b9904f57 340constraintTerm constraintTerm_makeIntLiteral (long i)
616915dd 341{
342 constraintTerm ret = new_constraintTermExpr();
343 ret->value.intlit = i;
344 ret->kind = INTLITERAL;
345 ret->loc = fileloc_undefined;
346 return ret;
347}
348
349bool constraintTerm_canGetValue (constraintTerm term)
350{
351 if (term->kind == INTLITERAL)
b9904f57 352 {
353 return TRUE;
354 }
355 else if (term->kind == SREF)
356 {
357 if (sRef_hasValue (term->value.sref))
358 {
359 multiVal mval = sRef_getValue (term->value.sref);
360
361 return multiVal_isInt (mval); /* for now, only try to deal with int values */
362 }
363 else
364 {
365 return FALSE;
366 }
367 }
368 else if (term->kind == EXPRNODE)
369 {
370 return FALSE;
371 }
616915dd 372 else
b9904f57 373 {
374 return FALSE;
375 }
616915dd 376}
377
b9904f57 378long constraintTerm_getValue (constraintTerm term)
616915dd 379{
b9904f57 380 llassert (constraintTerm_canGetValue (term));
381
382 if (term->kind == INTLITERAL)
383 {
384 return term->value.intlit;
385 }
386 else if (term->kind == SREF)
387 {
388 if (sRef_hasValue (term->value.sref))
389 {
390 multiVal mval = sRef_getValue (term->value.sref);
391
392 return multiVal_forceInt (mval); /* for now, only try to deal with int values */
393 }
394 else
395 {
396 BADBRANCH;
397 }
398 }
399 else if (term->kind == EXPRNODE)
400 {
401 BADBRANCH;
402 }
403 else
404 {
405 BADBRANCH;
406 }
407
d30bc0c7 408 BADEXIT;
616915dd 409}
410
616915dd 411/* same and similar are similar but not the same*/
bb25bea6 412static bool constraintTerm_same (constraintTerm term1, constraintTerm term2)
616915dd 413{
414 llassert (term1 !=NULL && term2 !=NULL);
415
416 if ( (term1->kind != term2->kind) || (term1->kind != EXPRNODE) )
417 {
418 return FALSE;
419 }
420
421 DPRINTF ( (message
422 ("Comparing srefs for %s and %s ", constraintTerm_print(term1), constraintTerm_print(term2)
423 )
424 )
425 );
426
427 if (sRef_same (term1->value.expr->sref, term2->value.expr->sref) )
428 {
429 DPRINTF ((message (" %s and %s are same", constraintTerm_print(term1), constraintTerm_print(term2) ) ));
430 return TRUE;
431 }
432 else
433 {
434 DPRINTF ((message (" %s and %s are not same", constraintTerm_print(term1), constraintTerm_print(term2) ) ));
435 return FALSE;
436 }
437
438}
439
bb25bea6 440static /*@exposed@*/ sRef constraintTerm_getsRef (constraintTerm t)
616915dd 441{
dc92450f 442 llassert (t != NULL);
616915dd 443 if (t->kind == EXPRNODE)
444 {
c3e695ff 445 return exprNode_getSref(t->value.expr);
616915dd 446 }
447
448 if (t->kind == SREF)
449 {
c3e695ff 450 return t->value.sref;
616915dd 451 }
452
453 return sRef_undefined;
454}
455
456bool constraintTerm_probSame (constraintTerm term1, constraintTerm term2)
457{
458 cstring s1, s2;
459
460 llassert (term1 !=NULL && term2 !=NULL);
461
462 DPRINTF ( (message
463 ("Comparing srefs for %s and %s ", constraintTerm_print(term1), constraintTerm_print(term2)
464 )
465 )
466 );
467
468 s1 = constraintTerm_getName (term1);
469 s2 = constraintTerm_getName (term2);
470
471 if (cstring_equal (s1, s2) )
472 {
d46ce6a4 473 DPRINTF ((message (" %q and %q are same", s1, s2 ) ) );
616915dd 474 return TRUE;
475 }
476 else
477 {
d46ce6a4 478 DPRINTF ((message (" %q and %q are not same", s1, s2 ) ) );
616915dd 479 return FALSE;
480 }
481}
482
483bool constraintTerm_similar (constraintTerm term1, constraintTerm term2)
484{
485 sRef s1, s2;
486
487 llassert (term1 !=NULL && term2 !=NULL);
90bc41f7 488
b9904f57 489 if (constraintTerm_canGetValue (term1) && constraintTerm_canGetValue (term2))
490 /* evans 2001-07-24: was (term1->kind == INTLITERAL) && (term2->kind == INTLITERAL) ) */
90bc41f7 491 {
b9904f57 492 long t1, t2;
90bc41f7 493
b9904f57 494 t1 = constraintTerm_getValue (term1);
90bc41f7 495 t2 = constraintTerm_getValue (term2);
b9904f57 496
497 return (t1 == t2);
90bc41f7 498 }
b9904f57 499
500 if (constraintTerm_canGetValue (term1) || constraintTerm_canGetValue (term2))
501 {
502 /* evans 2001-07-24: is this right? */ /*@i534@*/
503 return FALSE;
504 }
505
616915dd 506 s1 = constraintTerm_getsRef (term1);
507 s2 = constraintTerm_getsRef (term2);
508
b9904f57 509 if (!(sRef_isValid(s1) && sRef_isValid(s2)))
616915dd 510 {
511 return FALSE;
512 }
513
b9904f57 514 DPRINTF( (message
616915dd 515 ("Comparing srefs for %s and %s ", constraintTerm_print(term1), constraintTerm_print(term2)
516 )
517 )
518 );
b9904f57 519
520 if (sRef_similarRelaxed(s1, s2) || sRef_sameName (s1, s2) )
521 {
522 DPRINTF ((message (" %s and %s are same", constraintTerm_print(term1), constraintTerm_print(term2) ) ));
523 return TRUE;
524 }
525 else
526 {
527 DPRINTF ((message (" %s and %s are not same", constraintTerm_print(term1), constraintTerm_print(term2) ) ));
528 return FALSE;
529 }
616915dd 530}
920a3797 531
532void constraintTerm_dump ( /*@observer@*/ constraintTerm t, FILE *f)
533{
534 fileloc loc;
535 constraintTermValue value;
536 constraintTermType kind;
537 uentry u;
538
539 loc = t->loc;
540
541 value = t->value;
542
543 kind = t->kind;
544
545 fprintf(f, "%d\n", (int) kind);
546
547 switch (kind)
548 {
549
550 case EXPRNODE:
551 u = exprNode_getUentry(t->value.expr);
28bf4b0b 552 fprintf(f, "%s\n", cstring_toCharsSafe( uentry_rawName (u) )
553 );
920a3797 554 break;
555
556 case SREF:
557 {
558 sRef s;
559
560 s = t->value.sref;
561
562 if (sRef_isResult (s ) )
563 {
564 fprintf(f, "Result\n");
565 }
566 else if (sRef_isParam (s ) )
567 {
568 int param;
569 ctype ct;
570 cstring ctString;
571
572
573 ct = sRef_getType (s);
574 param = sRef_getParam(s);
575
576 ctString = ctype_dump(ct);
577
28bf4b0b 578 fprintf(f, "Param %s %d\n", cstring_toCharsSafe(ctString), (int) param );
920a3797 579 cstring_free(ctString);
580 }
581 else
582 {
583 u = sRef_getUentry(s);
28bf4b0b 584 fprintf(f, "%s\n", cstring_toCharsSafe(uentry_rawName (u) ) );
920a3797 585 }
586
587 }
588 break;
589
590 case INTLITERAL:
b9904f57 591 fprintf (f, "%ld\n", t->value.intlit);
920a3797 592 break;
593
594 default:
595 BADEXIT;
596 }
597
598}
599
600
601/*@only@*/ constraintTerm constraintTerm_undump ( FILE *f)
602{
920a3797 603 constraintTermType kind;
604 constraintTerm ret;
605
606 uentry ue;
607
6970c11b 608 char *str;
609 char *os;
920a3797 610
611 str = mstring_create (MAX_DUMP_LINE_LENGTH);
612 os = str;
6970c11b 613 str = fgets (os, MAX_DUMP_LINE_LENGTH, f);
920a3797 614
28bf4b0b 615 kind = (constraintTermType) reader_getInt(&str);
920a3797 616 str = fgets(os, MAX_DUMP_LINE_LENGTH, f);
617
618 switch (kind)
619 {
620
621 case SREF:
622 {
623 sRef s;
624 char * term;
28bf4b0b 625 term = reader_getWord(&str);
920a3797 626
627 if (strcmp (term, "Result") == 0 )
628 {
b072092f 629 s = sRef_makeResult (ctype_unknown);
920a3797 630 }
631 else if (strcmp (term, "Param" ) == 0 )
632 {
633 int param;
634 char *str2, *ostr2;
635
636 ctype t;
637
28bf4b0b 638 reader_checkChar(&str, ' ');
639 str2 = reader_getWord(&str);
640 param = reader_getInt(&str);
920a3797 641
642 ostr2 = str2;
643 t = ctype_undump(&str2) ;
6970c11b 644 s = sRef_makeParam (param, t, stateInfo_makeLoc (g_currentloc));
920a3797 645 free (ostr2);
646 }
647 else //This must be an identified that we can search for
648 // in usymTab
649 {
28bf4b0b 650 cstring termStr = cstring_makeLiteralTemp(term);
651
652 ue = usymtab_lookup (termStr);
920a3797 653 s = uentry_getSref(ue);
654 }
655
656 ret = constraintTerm_makesRef(s);
657
658 free(term);
659 }
660 break;
661
662 case EXPRNODE:
663 {
664 sRef s;
665 char * term;
28bf4b0b 666 cstring termStr;
920a3797 667
28bf4b0b 668 term = reader_getWord(&str);
920a3797 669 //This must be an identifier that we can search for
670 // in usymTab
28bf4b0b 671 termStr = cstring_makeLiteralTemp(term);
920a3797 672
28bf4b0b 673 ue = usymtab_lookup (termStr);
920a3797 674 s = uentry_getSref(ue);
675 ret = constraintTerm_makesRef(s);
676
677 free (term);
678 }
679 break;
680
681
682 case INTLITERAL:
683 {
684 int i;
685
28bf4b0b 686 i = reader_getInt(&str);
920a3797 687 ret = constraintTerm_makeIntLiteral (i);
688 }
689 break;
690
691 default:
692 BADEXIT;
693 }
694 free (os);
695
696 return ret;
697}
698
699
700
701
This page took 0.153787 seconds and 5 git commands to generate.