7 # include <ctype.h> /* for isdigit */
8 # include "lclintMacros.nf"
10 # include "cgrammar.h"
11 # include "cgrammar_tokens.h"
13 # include "exprChecks.h"
14 # include "aliasChecks.h"
15 # include "exprNodeSList.h"
16 //# include "exprData.i"
22 /*@notnull@*/ constraint constraint_makeNew (void);
25 constraint makeConstraintParse (sRef x, lltok relOp, exprNode cconstant)
31 ret = constraint_makeNew();
32 llassert (sRef_isValid(x) );
37 ret->lexpr = constraintExpr_makeTermsRef (x);
38 #warning fix abstraction
40 if (relOp.tok == GE_OP)
42 else if (relOp.tok == LE_OP)
44 else if (relOp.tok == EQ_OP)
47 llfatalbug(message ("Unsupported relational operator") );
50 t = cstring_toCharsSafe (exprNode_unparse(cconstant));
52 ret->expr = constraintExpr_makeIntLiteral (c);
56 DPRINTF(("GENERATED CONSTRAINT:"));
57 DPRINTF( (message ("%s", constraint_print(ret) ) ) );
61 constraint makeConstraintParse2 (constraintExpr l, lltok relOp, exprNode cconstant)
67 ret = constraint_makeNew();
73 ret->lexpr = constraintExpr_copy (l);
74 #warning fix abstraction
76 if (relOp.tok == GE_OP)
78 else if (relOp.tok == LE_OP)
80 else if (relOp.tok == EQ_OP)
83 llfatalbug(message("Unsupported relational operator") );
86 t = cstring_toCharsSafe (exprNode_unparse(cconstant));
88 ret->expr = constraintExpr_makeIntLiteral (c);
92 DPRINTF(("GENERATED CONSTRAINT:"));
93 DPRINTF( (message ("%s", constraint_print(ret) ) ) );
98 constraint makeConstraintParse3 (constraintExpr l, lltok relOp, constraintExpr r)
101 ret = constraint_makeNew();
107 ret->lexpr = constraintExpr_copy (l);
108 #warning fix abstraction
110 if (relOp.tok == GE_OP)
112 else if (relOp.tok == LE_OP)
114 else if (relOp.tok == EQ_OP)
117 llfatalbug( message("Unsupported relational operator") );
119 ret->expr = constraintExpr_copy (r);
123 DPRINTF(("GENERATED CONSTRAINT:"));
124 DPRINTF( (message ("%s", constraint_print(ret) ) ) );
128 constraint constraint_copy (constraint c)
131 ret = constraint_makeNew();
132 ret->lexpr = constraintExpr_copy (c->lexpr);
134 ret->expr = constraintExpr_copy (c->expr);
136 ret->generatingExpr = exprNode_fakeCopy(c->generatingExpr);
140 ret->orig = constraint_copy (c->orig);
146 /*like copy expect it doesn't allocate memory for the constraint*/
148 void constraint_overWrite (constraint c1, constraint c2)
150 c1->lexpr = constraintExpr_copy (c2->lexpr);
152 c1->expr = constraintExpr_copy (c2->expr);
155 if (c2->orig != NULL)
156 c1->orig = constraint_copy (c2->orig);
159 c1->generatingExpr = exprNode_fakeCopy (c2->generatingExpr );
162 bool constraint_resolve (/*@unused@*/ constraint c)
169 /*@notnull@*/ constraint constraint_makeNew (void)
172 ret = dmalloc(sizeof (*ret) );
178 ret->generatingExpr = NULL;
182 constraint constraint_addGeneratingExpr (/*@returned@*/ constraint c, exprNode e)
185 if (c->generatingExpr == NULL)
187 c->generatingExpr = exprNode_fakeCopy(e);
188 DPRINTF ((message ("setting generatingExpr for %s to %s", constraint_print(c), exprNode_unparse(e) ) ));
192 DPRINTF ((message ("Not setting generatingExpr for %s to %s", constraint_print(c), exprNode_unparse(e) ) ));
197 fileloc constraint_getFileloc (constraint c)
199 if (c->generatingExpr)
200 return (exprNode_getfileloc (c->generatingExpr) );
202 return (constraintExpr_getFileloc (c->lexpr) );
207 static bool checkForMaxSet (constraint c)
209 if (constraintExpr_hasMaxSet(c->lexpr) || constraintExpr_hasMaxSet(c->expr) )
215 bool constraint_hasMaxSet(constraint c)
219 if (checkForMaxSet(c->orig) )
223 return (checkForMaxSet(c) );
226 constraint constraint_makeReadSafeExprNode ( exprNode po, exprNode ind)
228 constraint ret = constraint_makeNew();
229 // constraintTerm term;
230 po = exprNode_fakeCopy(po);
231 ind = exprNode_fakeCopy(ind);
232 ret->lexpr = constraintExpr_makeMaxReadExpr(po);
234 ret->expr = constraintExpr_makeValueExpr (ind);
238 constraint constraint_makeWriteSafeInt (exprNode po, int ind)
240 constraint ret = constraint_makeNew();
243 ret->lexpr =constraintExpr_makeMaxSetExpr(po);
245 ret->expr = constraintExpr_makeValueInt (ind);
249 constraint constraint_makeSRefSetBufferSize (sRef s, int size)
251 constraint ret = constraint_makeNew();
252 ret->lexpr = constraintExpr_makeSRefMaxset (s);
254 ret->expr = constraintExpr_makeValueInt (size);
259 constraint constraint_makeSRefWriteSafeInt (sRef s, int ind)
261 constraint ret = constraint_makeNew();
264 ret->lexpr = constraintExpr_makeSRefMaxset (s);
266 ret->expr = constraintExpr_makeValueInt (ind);
271 /* drl added 01/12/2000
273 makes the constraint: Ensures index <= MaxRead(buffer) */
275 constraint constraint_makeEnsureLteMaxRead(exprNode index, exprNode buffer)
277 constraint ret = constraint_makeNew();
279 ret->lexpr = constraintExpr_makeValueExpr (index);
281 ret->expr = constraintExpr_makeMaxReadExpr(buffer);
286 constraint constraint_makeWriteSafeExprNode (exprNode po, exprNode ind)
288 constraint ret = constraint_makeNew();
291 ret->lexpr =constraintExpr_makeMaxSetExpr(po);
293 ret->expr = constraintExpr_makeValueExpr (ind);
298 constraint constraint_makeReadSafeInt ( exprNode po, int ind)
300 constraint ret = constraint_makeNew();
302 po = exprNode_fakeCopy(po);
304 ret->lexpr = constraintExpr_makeMaxReadExpr(po);
306 ret->expr = constraintExpr_makeValueInt (ind);
310 constraint constraint_makeSRefReadSafeInt (sRef s, int ind)
312 constraint ret = constraint_makeNew();
315 ret->lexpr = constraintExpr_makeSRefMaxRead (s);
317 ret->expr = constraintExpr_makeValueInt (ind);
322 constraint constraint_makeEnsureMaxReadAtLeast (exprNode e1, exprNode t2, fileloc sequencePoint)
324 constraint ret = constraint_makeNew();
327 e1 = exprNode_fakeCopy (e1);
328 t2 = exprNode_fakeCopy (t2);
330 ret = constraint_makeReadSafeExprNode(e1, t2);
332 ret->lexpr = constraintExpr_setFileloc (ret->lexpr, sequencePoint);
336 // fileloc_incColumn (ret->lexpr->term->loc);
340 static constraint constraint_makeEnsuresOpConstraintExpr (constraintExpr c1, constraintExpr c2, fileloc sequencePoint, arithType ar)
346 // llassert(sequencePoint);
348 ret = constraint_makeNew();
354 ret->lexpr = constraintExpr_setFileloc (ret->lexpr, sequencePoint);
358 static constraint constraint_makeEnsuresOp (exprNode e1, exprNode e2, fileloc sequencePoint, arithType ar)
360 constraintExpr c1, c2;
366 llcontbug((message("null exprNode, Exprnodes are %s and %s",
367 exprNode_unparse(e1), exprNode_unparse(e2) )
371 // llassert (sequencePoint);
373 e = exprNode_fakeCopy(e1);
374 c1 = constraintExpr_makeValueExpr (e);
376 e = exprNode_fakeCopy(e2);
377 c2 = constraintExpr_makeValueExpr (e);
379 ret = constraint_makeEnsuresOpConstraintExpr (c1, c2, sequencePoint, ar);
385 /* make constraint ensures e1 == e2 */
387 constraint constraint_makeEnsureEqual (exprNode e1, exprNode e2, fileloc sequencePoint)
389 return ( constraint_makeEnsuresOp (e1, e2, sequencePoint, EQ) );
392 /*make constraint ensures e1 < e2 */
393 constraint constraint_makeEnsureLessThan (exprNode e1, exprNode e2, fileloc sequencePoint)
395 constraintExpr t1, t2;
397 t1 = constraintExpr_makeValueExpr (e1);
398 t2 = constraintExpr_makeValueExpr (e2);
400 /*change this to e1 <= (e2 -1) */
402 t2 = constraintExpr_makeDecConstraintExpr (t2);
404 return ( constraint_makeEnsuresOpConstraintExpr (t1, t2, sequencePoint, LTE) );
407 constraint constraint_makeEnsureLessThanEqual (exprNode e1, exprNode e2, fileloc sequencePoint)
409 return ( constraint_makeEnsuresOp (e1, e2, sequencePoint, LTE) );
412 constraint constraint_makeEnsureGreaterThan (exprNode e1, exprNode e2, fileloc sequencePoint)
414 constraintExpr t1, t2;
416 t1 = constraintExpr_makeValueExpr (e1);
417 t2 = constraintExpr_makeValueExpr (e2);
420 /* change this to e1 >= (e2 + 1) */
421 t2 = constraintExpr_makeIncConstraintExpr (t2);
424 return ( constraint_makeEnsuresOpConstraintExpr (t1, t2, sequencePoint, GTE) );
427 constraint constraint_makeEnsureGreaterThanEqual (exprNode e1, exprNode e2, fileloc sequencePoint)
429 return ( constraint_makeEnsuresOp (e1, e2, sequencePoint, GTE) );
433 exprNode exprNode_copyConstraints (/*@returned@*/ exprNode dst, exprNode src)
435 dst->ensuresConstraints = constraintList_copy (src->ensuresConstraints );
436 dst->requiresConstraints = constraintList_copy (src->requiresConstraints );
437 dst->trueEnsuresConstraints = constraintList_copy (src->trueEnsuresConstraints );
438 dst->falseEnsuresConstraints = constraintList_copy (src->falseEnsuresConstraints );
442 constraint constraint_makeMaxSetSideEffectPostDecrement (exprNode e, fileloc sequencePoint)
444 constraint ret = constraint_makeNew();
445 //constraintTerm term;
447 e = exprNode_fakeCopy(e);
448 ret->lexpr = constraintExpr_makeValueExpr (e);
451 ret->expr = constraintExpr_makeValueExpr (e);
452 ret->expr = constraintExpr_makeDecConstraintExpr (ret->expr);
454 ret->lexpr = constraintExpr_setFileloc (ret->lexpr, sequencePoint);
455 // fileloc_incColumn ( ret->lexpr->term->loc);
456 // fileloc_incColumn ( ret->lexpr->term->loc);
459 constraint constraint_makeMaxSetSideEffectPostIncrement (exprNode e, fileloc sequencePoint)
461 constraint ret = constraint_makeNew();
462 //constraintTerm term;
464 e = exprNode_fakeCopy(e);
465 ret->lexpr = constraintExpr_makeValueExpr (e);
468 ret->expr = constraintExpr_makeValueExpr (e);
469 ret->expr = constraintExpr_makeIncConstraintExpr (ret->expr);
471 ret->lexpr = constraintExpr_setFileloc (ret->lexpr, sequencePoint);
472 // fileloc_incColumn ( ret->lexpr->term->loc);
473 // fileloc_incColumn ( ret->lexpr->term->loc);
479 // constraint constraint_makeMaxReadSideEffectPostIncrement (exprNode e, fileloc sequencePoint)
481 // constraint ret = constraint_makeNew();
482 // //constraintTerm term;
484 // e = exprNode_fakeCopy(e);
485 // ret->lexpr = constraintExpr_makeMaxReadExpr(e);
488 // ret->expr = constraintExpr_makeIncConstraintExpr (e);
489 // ret->lexpr = constraintExpr_setFileLoc (ret->lexpr, sequencePoint);
494 cstring arithType_print (arithType ar) /*@*/
496 cstring st = cstring_undefined;
500 st = cstring_makeLiteral (" < ");
503 st = cstring_makeLiteral (" <= ");
506 st = cstring_makeLiteral (" > ");
509 st = cstring_makeLiteral (" >= ");
512 st = cstring_makeLiteral (" == ");
515 st = cstring_makeLiteral (" NONNEGATIVE ");
518 st = cstring_makeLiteral (" POSITIVE ");
527 void constraint_printError (constraint c, fileloc loc)
532 string = constraint_printDetailed (c);
536 if (constraint_getFileloc(c) )
538 errorLoc = constraint_getFileloc(c);
543 voptgenerror (FLG_FUNCTIONPOST, string, errorLoc);
547 voptgenerror (FLG_FUNCTIONCONSTRAINT, string, errorLoc);
552 cstring constraint_printDetailed (constraint c)
554 cstring st = cstring_undefined;
560 st = message ("Unresolved constraint:\nLclint is unable to resolve %s needed to satisfy %s", constraint_print (c), constraint_print(c->orig) );
562 st = message ("Unresolved constraint:\nLclint is unable to resolve %s", constraint_print (c));
568 st = message ("Block Post condition:\nThis function block has the post condition %s\n based on %s", constraint_print (c), constraint_print(c->orig) );
570 st = message ("Block Post condition:\nThis function block has the post condition %s", constraint_print (c));
573 if (context_getFlag (FLG_CONSTRAINTLOCATION) )
576 // llassert (c->generatingExpr);
577 temp = message ("\nOriginal Generating expression %s: %s\n", fileloc_unparse( exprNode_getfileloc (c->generatingExpr) ),
578 exprNode_unparse(c->generatingExpr) );
579 st = cstring_concat (st, temp);
581 if (constraint_hasMaxSet(c) )
584 temp2 = message ("\nHas MaxSet\n");
585 st = cstring_concat (st, temp2);
591 cstring constraint_print (constraint c) /*@*/
593 cstring st = cstring_undefined;
594 cstring type = cstring_undefined;
598 type = cstring_makeLiteral ("Ensures: ");
602 type = cstring_makeLiteral ("Requires: ");
604 st = message ("%s: %s %s %s",
606 constraintExpr_print (c->lexpr),
607 arithType_print(c->ar),
608 constraintExpr_print(c->expr)
613 /*@only@*/ constraint constraint_doSRefFixBaseParam (/*@returned@*/ /*@only@*/ constraint precondition,
614 exprNodeList arglist)
616 precondition->lexpr = constraintExpr_doSRefFixBaseParam (precondition->lexpr,
618 precondition->expr = constraintExpr_doSRefFixBaseParam (precondition->expr,
625 constraint constraint_doFixResult (constraint postcondition, exprNode fcnCall)
627 postcondition = constraint_copy (postcondition);
628 postcondition->lexpr = constraintExpr_doFixResult (postcondition->lexpr, fcnCall);
629 postcondition->expr = constraintExpr_doFixResult (postcondition->expr, fcnCall);
631 return postcondition;
634 constraint constraint_doSRefFixConstraintParam (constraint precondition,
635 exprNodeList arglist)
638 precondition = constraint_copy (precondition);
639 precondition->lexpr = constraintExpr_doSRefFixConstraintParam (precondition->lexpr, arglist);
640 precondition->expr = constraintExpr_doSRefFixConstraintParam (precondition->expr, arglist);
645 // bool constraint_hasTerm (constraint c, constraintTerm term)
647 // DPRINTF((message ("Constraint %s", constraint_print (c) ) ) );
649 // if (constraintExpr_includesTerm (c->lexpr, term) )
652 // if (constraintExpr_includesTerm (c->expr, term) )
658 /*@only@*/ constraint constraint_preserveOrig (/*@returned@*/ /*@only@*/ constraint c) /*@modifies c @*/
660 c->orig = constraint_copy (c);