]> andersk Git - splint.git/blob - src/exprChecks.c
Renaming - LCLint => Splint
[splint.git] / src / exprChecks.c
1 /*
2 ** Splint - annotation-assisted static program checker
3 ** Copyright (C) 1994-2001 University of Virginia,
4 **         Massachusetts Institute of Technology
5 **
6 ** This program is free software; you can redistribute it and/or modify it
7 ** under the terms of the GNU General Public License as published by the
8 ** Free Software Foundation; either version 2 of the License, or (at your
9 ** option) any later version.
10 ** 
11 ** This program is distributed in the hope that it will be useful, but
12 ** WITHOUT ANY WARRANTY; without even the implied warranty of
13 ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 ** General Public License for more details.
15 ** 
16 ** The GNU General Public License is available from http://www.gnu.org/ or
17 ** the Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
18 ** MA 02111-1307, USA.
19 **
20 ** For information on lclint: lclint-request@cs.virginia.edu
21 ** To report a bug: lclint-bug@cs.virginia.edu
22 ** For more information: http://www.splint.org
23 */
24 /*
25 ** exprChecks.c
26 */
27
28 # include "lclintMacros.nf"
29 # include "basic.h"
30 # include "cgrammar.h"
31 # include "cgrammar_tokens.h"
32 # include "transferChecks.h"
33 # include "exprChecks.h"
34
35 /*
36 ** for now, allow exprChecks to access exprNode.
37 ** may remove this in future
38 */
39
40 /*@access exprNode@*/
41
42 static bool checkCallModifyAux (/*@exposed@*/ sRef p_s, exprNode p_f, sRef p_alias, exprNode p_err);
43 static bool checkModifyValAux (/*@exposed@*/ sRef p_s, exprNode p_f, sRef p_alias, exprNode p_err);
44 static bool checkModifyAux (/*@exposed@*/ sRef p_s, exprNode p_f, sRef p_alias, exprNode p_err);
45 static void checkSafeReturnExpr (/*@notnull@*/ exprNode p_e);
46
47 /*
48 ** called at end of expression statement
49 **
50 **  of e->kind is not an assign, empty, body or modop
51 **         verify the the value is void
52 **
53 */
54
55 void
56 exprNode_checkStatement (exprNode e)
57 {
58   bool hasError = FALSE;
59
60   if (!exprNode_isError (e))
61     {
62       exprKind ek = e->kind;
63
64       if (ek == XPR_CALL && !(ctype_isRealVoid (e->typ)))
65         { 
66           if (ctype_isKnown (e->typ))
67             {
68               if (ctype_isManifestBool (ctype_realishType (e->typ)))
69                 {
70                   hasError = optgenerror 
71                     (FLG_RETVALBOOL,
72                      message ("Return value (type %t) ignored: %s",
73                               e->typ,
74                               exprNode_unparseFirst (e)),
75                      e->loc);
76                 }
77               else if (ctype_isDirectInt (e->typ))
78                 {
79                   hasError = optgenerror 
80                     (FLG_RETVALINT,
81                      message ("Return value (type %t) ignored: %s",
82                               e->typ,
83                               exprNode_unparseFirst (e)),
84                      e->loc);
85                 }
86               else
87                 {
88                   hasError = optgenerror 
89                     (FLG_RETVALOTHER,
90                      message ("Return value (type %t) ignored: %s",
91                               e->typ,
92                               exprNode_unparseFirst (e)),
93                      e->loc);
94                 }
95             }
96         }
97
98       if (!hasError && !(exprNode_mayEscape (e))
99           && !(e->canBreak)) /* control changes are effects too! */
100         {
101           if (sRefSet_hasRealElement (e->sets)
102               || sRefSet_hasRealElement (e->msets))
103             {
104               ; /* okay */
105             }
106           else
107             {
108               if (sRefSet_isEmpty (e->sets) && sRefSet_isEmpty (e->msets))
109                 {
110                   voptgenerror
111                     (FLG_NOEFFECT,
112                      message ("Statement has no effect: %s",
113                               exprNode_unparseFirst (e)),
114                      e->loc);
115                 }
116               else
117                 {
118                   if (context_maybeSet (FLG_NOEFFECTUNCON))
119                     {
120                       if (sRefSet_hasUnconstrained (e->sets))
121                         {
122                           voptgenerror
123                             (FLG_NOEFFECTUNCON,
124                              message ("Statement has no effect (possible "
125                                       "undected modification through "
126                                       "call to %q): %s",
127                                       sRefSet_unparseUnconstrained (e->sets),
128                                       exprNode_unparseFirst (e)),
129                              e->loc);
130                         }
131                       else if (sRefSet_hasUnconstrained (e->msets))
132                         {
133                           voptgenerror
134                             (FLG_NOEFFECTUNCON,
135                              message ("Statement has no effect (possible "
136                                       "undected modification through "
137                                       "call to %q): %s",
138                                       sRefSet_unparseUnconstrained (e->msets),
139                                       exprNode_unparseFirst (e)),
140                              e->loc);
141                         }
142                       else
143                         {
144                           ; /* statement has unknown modification */
145                         }
146                     }
147                 }
148             }
149         }
150     }
151 }
152
153 static bool
154 checkRepExposed (sRef base, /*@notnull@*/ exprNode e, sRef alias, 
155                  /*@unused@*/ exprNode unused)
156 {
157   ctype btype;
158
159   if (sRef_isInvalid (alias) || sRef_sameName (base, alias))
160     {
161       btype = sRef_getType (base);
162
163       if (ctype_isAbstract (btype) && ctype_isVisiblySharable (e->typ))
164         {
165           voptgenerror (FLG_RETEXPOSE,
166                         message ("Return value exposes rep of %s: %s",
167                                  ctype_unparse (btype),
168                                  exprNode_unparse (e)),
169                         e->loc);
170           return TRUE;
171         }
172     }
173   else
174     {
175       sRef rbase = sRef_getRootBase (base);
176       btype = sRef_getType (rbase);
177                       
178       if (ctype_isAbstract (btype) && ctype_isVisiblySharable (e->typ))
179         {
180           voptgenerror 
181             (FLG_RETEXPOSE,
182              message ("Return value may expose rep of %s through alias %q: %s",
183                       ctype_unparse (btype),
184                       sRef_unparse (rbase),
185                       exprNode_unparse (e)),
186              e->loc);
187           return TRUE;
188         }
189     }
190
191   return FALSE;
192 }
193
194 static bool
195 checkRefGlobParam (sRef base, /*@notnull@*/ exprNode e,
196                    sRef alias, /*@unused@*/ exprNode unused)
197 {
198   if (sRef_isInvalid (alias) || sRef_sameName (base, alias))
199     {
200       ctype ct = e->typ;
201
202       if (ctype_isUnknown (ct))
203         {
204           ct = sRef_getType (base);
205         }
206  
207       if (ctype_isVisiblySharable (ct))
208         {
209           if (sRef_isFileOrGlobalScope (base))
210             {
211               uentry fcn = context_getHeader ();
212               bool noerror = FALSE;
213
214               if (uentry_isValid (fcn) && uentry_isFunction (fcn))
215                 {
216                   sRef res = uentry_getSref (fcn);
217
218                   /* If result is dependent and global is owned, this is okay... */
219                   if (sRef_isDependent (res)
220                       && sRef_isOwned (base))
221                     {
222                       noerror = TRUE;
223
224                     }
225                 }
226
227               if (!noerror)
228                 {
229                   voptgenerror
230                     (FLG_RETALIAS,
231                      message ("Function returns reference to global %q: %s",
232                               sRef_unparse (base),
233                               exprNode_unparse (e)),
234                      e->loc);
235                 }
236
237               return TRUE;
238             }
239           else if (sRef_isAnyParam (base))
240             {
241               uentryList params = context_getParams ();
242               int paramno = sRef_getParam (base);
243
244               if (paramno < uentryList_size (params))
245                 {
246                   uentry arg = uentryList_getN (params, paramno);
247                   sRef ref = uentry_getSref (arg);
248
249                   if (uentry_isReturned (arg) 
250                       || sRef_isOnly (ref) 
251                       || sRef_isExposed (ref)
252                       || sRef_isRefCounted (ref))
253                     {
254                       ; /* okay */
255                     }
256                   else
257                     {
258                       voptgenerror 
259                         (FLG_RETALIAS,
260                          message ("Function returns reference to parameter %q: %s",
261                                   sRef_unparse (base),
262                                   exprNode_unparse (e)),
263                          e->loc);
264                     }
265                 }
266               else
267                 {
268                   llbuglit ("ret alias: bad paramno");
269                 }
270               
271               return TRUE;
272             }
273           else
274             {
275               return FALSE;
276             }
277         }
278     }
279   else
280     {
281       if (ctype_isVisiblySharable (e->typ))
282         {
283           if (sRef_isFileOrGlobalScope (base))
284             {
285               voptgenerror 
286                 (FLG_RETALIAS,
287                  message ("Function may return reference to global %q through alias %q: %s",
288                           sRef_unparse (alias),
289                           sRef_unparse (base),
290                           exprNode_unparse (e)),
291                  e->loc);
292               return TRUE;
293             }
294           else if (sRef_isAnyParam (base) && !(sRef_isOnly (base)))
295             {
296               uentryList params = context_getParams ();
297               int paramno = sRef_getParam (base);
298               
299               if (paramno < uentryList_size (params))
300                 {
301                   uentry arg = uentryList_getN (params, paramno);
302                   
303                   if (!uentry_isReturned (arg))
304                     {
305                       voptgenerror 
306                         (FLG_RETALIAS,
307                          message 
308                          ("Function may return reference to parameter %q through alias %q: %s",
309                           sRef_unparse (base),
310                           sRef_unparse (alias),
311                           exprNode_unparse (e)),
312                          e->loc);
313                       
314                       return TRUE;
315                     }
316                 }
317               else
318                 {
319                   voptgenerror 
320                     (FLG_RETALIAS,
321                      message 
322                      ("Function may return reference to parameter %q through alias %q: %s",
323                       sRef_unparse (base),
324                       sRef_unparse (alias),
325                       exprNode_unparse (e)),
326                      e->loc);
327                   
328                   return TRUE;
329                 }
330             }
331           else
332             {
333               return FALSE;
334             }
335         }
336     }
337   return FALSE;
338 }
339
340
341 void
342 exprNode_checkModify (exprNode e, exprNode err)
343 {
344   llassert (exprNode_isDefined (e));
345
346   DPRINTF (("Check modify: %s", exprNode_unparse (e)));
347   
348   if (sRef_isValid (e->sref))
349     {
350       sRef_aliasCheckPred (checkModifyAux, sRef_isReference, e->sref, e, err);
351     }
352 }
353
354 void
355 exprNode_checkModifyVal (exprNode e, exprNode err)
356 {
357   llassert (exprNode_isDefined (e));
358   
359   DPRINTF (("Check modify val: %s", exprNode_unparse (e)));
360
361   if (sRef_isValid (e->sref))
362     {
363       sRef_aliasCheckPred (checkModifyValAux, sRef_isReference, e->sref, e, err);
364     }
365 }
366
367 void
368 exprChecks_checkNullReturn (fileloc loc)
369 {
370   if (!context_inRealFunction ())
371     {
372       /*
373       llmsg ("exprChecks_checkNullReturnExpr: not in function context");
374       */
375       return;
376     }
377   else
378     {
379       if (ctype_isFunction (context_currentFunctionType ()))
380         {
381           ctype tr = ctype_getReturnType (context_currentFunctionType ());
382
383           if (!ctype_isFirstVoid (tr))
384             {
385               if (ctype_isUnknown (tr))
386                 {
387                   voptgenerror
388                     (FLG_CONTROL,
389                      cstring_makeLiteral ("Empty return in function declared to implicitly return int"),
390                      loc);
391                 }
392               else
393                 {
394                   voptgenerror (FLG_CONTROL,
395                                 message ("Empty return in function declared to return %t", tr),
396                                 loc);
397                 }
398             }
399         }
400     }
401 }
402
403 void
404 exprNode_checkReturn (exprNode e)
405 {
406   if (!exprNode_isError (e))
407     {
408       if (!context_inRealFunction ())
409         {
410           if (context_inMacro ())
411             {
412               llerror (FLG_CONTROL,
413                        message ("Macro %s uses return (not functional)",
414                                 context_inFunctionName ()));
415             }
416           else
417             {
418               /*
419                 llbuglit ("exprNode_checkReturn: not in function context");
420                 */
421             }
422         }
423       else
424         {
425           if (ctype_isFunction (context_currentFunctionType ()))
426             {
427               checkSafeReturnExpr (e);
428             }
429           else
430             {
431               ;
432             }
433         }
434     }
435 }
436
437 void
438 exprNode_checkPred (cstring c, exprNode e)
439 {
440   ctype ct;
441
442   if (exprNode_isError (e))
443     return;
444
445   ct = exprNode_getType (e);
446
447   if (exprNode_isAssign (e))
448     {
449       voptgenerror 
450         (FLG_PREDASSIGN,
451          message ("Test expression for %s is assignment expression: %s", 
452                   c, exprNode_unparse (e)),
453          e->loc);
454     }
455
456   if (ctype_isRealBool (ct) || ctype_isUnknown (ct)) 
457          /* evs 2000-12-20 added || ctype_isUnknown to avoid spurious messages */
458     {
459      ;
460     }
461   else if (ctype_isRealPointer (ct))
462     {
463       voptgenerror
464         (FLG_PREDBOOLPTR,
465          message ("Test expression for %s not %s, type %t: %s", c, 
466                   context_printBoolName (), 
467                   ct, exprNode_unparse (e)),
468          e->loc);
469     }
470   else if (ctype_isRealInt (ct))
471     {
472       voptgenerror 
473         (FLG_PREDBOOLINT,
474          message ("Test expression for %s not %s, type %t: %s", c, 
475                   context_printBoolName (), ct, exprNode_unparse (e)),
476          e->loc);
477     }
478   else
479     {
480       voptgenerror 
481         (FLG_PREDBOOLOTHERS,
482          message ("Test expression for %s not %s, type %t: %s", c, 
483                   context_printBoolName (), ct, exprNode_unparse (e)),
484          e->loc);
485     }
486 }
487
488 void
489 exprChecks_checkUsedGlobs (globSet decl, globSet used)
490 {
491   fileloc fl = uentry_whereSpecified (context_getHeader ());
492
493   if (fileloc_isUndefined (fl))
494     {
495       fl = uentry_whereDeclared (context_getHeader ());
496     }
497
498   globSet_allElements (decl, el)
499     {
500       if (!globSet_member (used, el))
501         {
502           if (sRef_isSpecInternalState (el)
503               || sRef_isNothing (el))
504             {
505               ;
506             }
507           else
508             {
509               cstring sname = sRef_unparse (el);
510               
511               if (fileloc_isLib (fl))
512                 {
513                   voptgenerror (FLG_USEALLGLOBS,
514                                 message ("Global %s listed (%q) but not used", 
515                                          sname, fileloc_unparse (fl)),
516                                 g_currentloc);
517                 }               
518               else
519                 {
520                   voptgenerror (FLG_USEALLGLOBS,
521                                 message ("Global %s listed but not used", sname),
522                                 fl);
523                 }
524
525               cstring_free (sname);
526             }
527         }
528     } end_globSet_allElements;
529 }
530
531 void
532 exprNode_checkAllMods (sRefSet mods, uentry ue)
533 {
534   bool realParams = FALSE;
535   uentry le = context_getHeader ();
536   fileloc fl = uentry_whereSpecified (le);
537   uentryList specParamNames = uentryList_undefined;
538   uentryList paramNames = context_getParams ();
539
540   if (uentry_isFunction (le))
541     {
542       specParamNames = uentry_getParams (le);  
543
544       if (uentryList_isUndefined (specParamNames))
545         {
546           ; /* unknown params */
547         }
548       else if (uentryList_size (paramNames) != uentryList_size (specParamNames))
549         {
550           llbug
551             (message ("exprNode_checkAllMods: parameter lists have different sizes: "
552                       "%q (%d) / %q (%d)",
553                       uentryList_unparse (paramNames),
554                       uentryList_size (paramNames),
555                       uentryList_unparse (specParamNames),
556                       uentryList_size (specParamNames)));
557         }
558       else if (uentryList_size (paramNames) > 0 
559                && !uentry_hasRealName (uentryList_getN (specParamNames, 0)))
560         {
561           /* loaded from a library */
562         }
563       else
564         {
565           realParams = TRUE;
566         }
567     }
568
569   sRefSet_allElements (mods, sr)
570     {
571       if (sRef_isNothing (sr) || sRef_isSpecState (sr))
572         {
573           ; /* should report on anything? */
574         }
575       else if (sRef_isInternalState (sr))
576         {
577           if (!sRef_isModified (sr))
578             {
579               if (sRefSet_hasStatic (mods))
580                 {
581                   ; /* okay */
582                 }
583               else
584                 {
585                   if (optgenerror 
586                       (FLG_MUSTMOD,
587                        message
588                        ("Function %s specified to modify internal state "
589                         "but no internal state is modified", 
590                         uentry_rawName (ue)),
591                        uentry_whereLast (ue)))
592                     {
593                       uentry_showWhereSpecified (le);
594                     }
595                 }
596             }
597         }
598       else 
599         {
600           if (!sRef_isModified (sr))
601             {
602               cstring sname = realParams ? sRef_unparse (sr) : sRef_unparse (sr);
603               
604               if (fileloc_isLib (fl) && !realParams)
605                 {
606                   voptgenerror 
607                     (FLG_MUSTMOD,
608                      message ("Suspect object listed (%q) in modifies "
609                               "clause of %s not modified: %s", 
610                               fileloc_unparse (fl),
611                               uentry_rawName (ue),
612                               sname),
613                      uentry_whereLast (ue));
614                 }               
615               else
616                 {
617                   if (optgenerror 
618                       (FLG_MUSTMOD,
619                        message ("Suspect object listed in modifies of %s "
620                                 "not modified: %s", 
621                                 uentry_rawName (ue),
622                                 sname),
623                        uentry_whereLast (ue)))
624                     {
625                       uentry_showWhereSpecified (le);
626                     }
627                 }
628               cstring_free (sname);
629             }
630         }
631     } end_sRefSet_allElements;
632 }
633
634 void exprNode_checkMacroBody (/*@only@*/ exprNode e)
635 {
636   if (!exprNode_isError (e))
637     {
638       uentry hdr;
639
640       if (!(context_inFunctionLike () || context_inMacroConstant ()
641             || context_inUnknownMacro ()))
642         {
643           llcontbug 
644             (message 
645              ("exprNode_checkMacroBody: not in macro function or constant: %q", 
646               context_unparse ()));
647           exprNode_free (e);
648           return;
649         }
650
651       hdr = context_getHeader ();
652       
653       if (e->kind == XPR_STMTLIST || e->kind == XPR_BODY)
654         {
655           voptgenerror 
656             (FLG_MACROSTMT,
657              message 
658              ("Macro %q definition is statement list (recommend "
659               "do { ... } while (0) constuction to ensure multiple "
660               "statement macro is syntactic function)",
661               uentry_getName (hdr)),
662              fileloc_isDefined (e->loc) ? e->loc : g_currentloc);
663         }
664       
665       if (context_inMacroConstant ())
666         {
667           ctype t = uentry_getType (hdr);
668
669           uentry_setDefined (hdr, e->loc);
670           
671           if (!(exprNode_matchType (t, e)))
672             {
673               cstring uname = uentry_getName (hdr);
674
675               if (cstring_equal (uname, context_getTrueName ())
676                   || cstring_equal (uname, context_getFalseName ()))
677                 {
678                   /* 
679                   ** We need to do something special to allow FALSE and TRUE
680                   ** to be defined without reporting errors.  This is a tad
681                   ** bogus, but otherwise lots of things would break.
682                   */
683
684
685                   llassert (ctype_isManifestBool (t));
686                   /* Should also check type of e is a reasonable (?) bool type. */
687                 }
688               else 
689                 {
690                   if (optgenerror 
691                       (FLG_INCONDEFS,
692                        message
693                        ("Constant %q specified as %s, but defined as %s: %s",
694                         uentry_getName (hdr),
695                         ctype_unparse (t),
696                         ctype_unparse (e->typ),
697                         exprNode_unparse (e)),
698                        e->loc))
699                     {
700                       uentry_showWhereSpecified (hdr);
701                     }
702                 }
703
704               cstring_free (uname);
705             }
706           else
707             {
708               if (context_maybeSet (FLG_NULLSTATE)
709                   && ctype_isUA(t) 
710                   && ctype_isRealPointer (t)
711                   && exprNode_isNullValue (e))
712                 {
713                   uentry ue = usymtab_getTypeEntry (ctype_typeId (t));
714                   sRef   sr = uentry_getSref (ue);
715                   
716                   if (!sRef_possiblyNull (sr))
717                     {
718                       vgenhinterror 
719                         (FLG_NULLSTATE,
720                          message ("Constant %q of non-null type %s defined "
721                                   "as null: %s",
722                                   uentry_getName (hdr), ctype_unparse (t),
723                                   exprNode_unparse (e)),
724                          message ("If %s can be null, add a /*@null@*/ "
725                                   "qualifer to its typedef.",
726                                   ctype_unparse (t)),
727                          e->loc);
728                     }
729                   
730                   uentry_mergeConstantValue (hdr, e->val);
731                   e->val = multiVal_undefined;
732                 }
733             }
734         }
735       else if (context_inMacroFunction () || context_inUnknownMacro ())
736         {
737           ctype rettype = context_getRetType ();
738
739           if (context_isMacroMissingParams ())
740             {
741               llassert (context_inMacroFunction ());
742
743               /*
744               ** # define newname oldname
745               **
746               ** newname is a function
747               ** specification of oldname should match
748               ** specification of newname.
749               */
750
751               if (!ctype_isFunction (e->typ))
752                 {
753                   voptgenerror 
754                     (FLG_INCONDEFS,
755                      message ("Function %s defined by unparameterized "
756                               "macro not corresponding to function",
757                               context_inFunctionName ()),
758                      e->loc);
759                 }
760               else
761                 {
762                   uentry ue = exprNode_getUentry (e);
763
764                   if (uentry_isValid (ue))
765                     {
766                       /*
767                       ** Okay, for now --- should check for consistency
768                       */
769                       /*
770                       ** uentry oldue = usymtab_lookup (cfname);
771                       */
772
773                       /* check var conformance here! */
774                     }
775                   else
776                     {
777                       voptgenerror
778                         (FLG_INCONDEFS,
779                          message ("Function %s defined by unparameterized "
780                                   "macro not corresponding to function",
781                                   context_inFunctionName ()),
782                          e->loc);
783                     }
784                   
785                   e->typ = ctype_getReturnType (e->typ);
786                   rettype = e->typ; /* avoid aditional errors */
787                 }
788             }
789
790           if (ctype_isVoid (rettype) || ctype_isUnknown (rettype))
791             {
792              ; /* don't complain when void macros have values */
793             }       
794           else if (!exprNode_matchType (rettype, e))
795             {
796               if (optgenerror 
797                   (FLG_INCONDEFS,
798                    message ("Function %q specified to return %s, "
799                             "implemented as macro having type %s: %s",
800                             uentry_getName (hdr),
801                             ctype_unparse (rettype), ctype_unparse (e->typ),
802                             exprNode_unparse (e)),
803                    e->loc))
804                 {
805                   uentry_showWhereSpecified (hdr);
806                 }
807             }
808           else
809             {
810               switch (e->kind)
811                 {
812                   /* these expressions have values: */
813                 case XPR_PARENS: case XPR_ASSIGN: 
814                 case XPR_EMPTY: case XPR_VAR:
815                 case XPR_OP: case XPR_POSTOP: 
816                 case XPR_PREOP: case XPR_CALL: 
817                 case XPR_SIZEOFT: case XPR_SIZEOF: 
818                 case XPR_ALIGNOFT: case XPR_ALIGNOF: 
819                 case XPR_CAST: case XPR_FETCH: 
820                 case XPR_COMMA: case XPR_COND: 
821                 case XPR_ARROW: case XPR_CONST: 
822                 case XPR_STRINGLITERAL: case XPR_NUMLIT:
823                 case XPR_FACCESS: case XPR_OFFSETOF:
824
825                   checkReturnTransfer (e, hdr);
826                   break;
827
828                   /* these expressions don't */
829                 case XPR_LABEL:
830                 case XPR_VAARG: case XPR_ITER: 
831                 case XPR_FOR: case XPR_FORPRED:
832                 case XPR_GOTO: case XPR_CONTINUE: 
833                 case XPR_BREAK: case XPR_RETURN:
834                 case XPR_NULLRETURN: case XPR_IF: 
835                 case XPR_IFELSE: case XPR_DOWHILE:
836                 case XPR_WHILE: case XPR_STMT: 
837                 case XPR_STMTLIST: case XPR_SWITCH:
838                 case XPR_INIT: case XPR_BODY: 
839                 case XPR_NODE: case XPR_ITERCALL:
840                 case XPR_TOK: case XPR_CASE: 
841                 case XPR_FTCASE: case XPR_FTDEFAULT:
842                 case XPR_DEFAULT: case XPR_WHILEPRED:
843                 case XPR_BLOCK: case XPR_INITBLOCK:
844                   if (optgenerror 
845                       (FLG_INCONDEFS,
846                        message ("Function %q specified to return %s, "
847                                 "implemented as macro with no result: %s",
848                                 uentry_getName (hdr),
849                                 ctype_unparse (rettype), 
850                                 exprNode_unparse (e)),
851                        e->loc))
852                     {
853                       uentry_showWhereSpecified (hdr);
854                     }
855                 }
856             }
857
858           usymtab_checkFinalScope (FALSE);
859         }
860       else
861         {
862           llbug (message ("exprNode_checkMacroBody: not in macro function: %q", context_unparse ()));
863         }
864
865       exprNode_free (e);
866     }
867
868   context_exitFunction ();
869   return;
870 }
871
872 void exprNode_checkFunctionBody (exprNode body)
873 {
874   if (!exprNode_isError (body))
875     {
876       bool noret = context_getFlag (FLG_NORETURN);
877       bool checkret = exprNode_mustEscape (body);
878
879       if (!checkret 
880           && noret 
881           && !exprNode_errorEscape (body)
882           && context_inRealFunction ()
883           && ctype_isFunction (context_currentFunctionType ()))
884         {
885           ctype tr = ctype_getReturnType (context_currentFunctionType ());
886           
887           if (!ctype_isFirstVoid (tr)) 
888             {
889               if (ctype_isUnknown (tr))
890                 {
891                   voptgenerror 
892                     (FLG_NORETURN,
893                      cstring_makeLiteral ("Path with no return in function declared to implicity return int"), 
894                      g_currentloc);
895                 }
896               else
897                 {
898                   voptgenerror 
899                     (FLG_NORETURN,
900                      message ("Path with no return in function declared to return %t", 
901                               tr),
902                      g_currentloc);
903                 }
904             }
905         }
906       
907       if (!checkret)
908         {
909           context_returnFunction ();
910         }
911     }
912 }
913 /*drl modified */
914
915
916 void exprNode_checkFunction (/*@unused@*/ uentry ue, /*@only@*/ exprNode fcnBody)
917 {
918   constraintList c, t, post;
919   constraintList c2, fix;
920   constraintList implicitFcnConstraints;
921
922   /*@owned@*/ exprNode body;
923
924   context_enterInnerContext ();
925
926   body = fcnBody;
927
928   /*
929     if we're not going to be printing any errors for buffer overflows
930     we can skip the checking to improve performance
931     
932     FLG_DEBUGFUNCTIONCONSTRAINT controls wheather we perform the check anyway
933     in order to find potential problems like assert failures and seg faults...
934   */
935
936   if  (!context_getFlag(FLG_DEBUGFUNCTIONCONSTRAINT)  )
937     /* check if errors will printed */
938     if (! (context_getFlag(FLG_DEBUGFUNCTIONCONSTRAINT) ||
939            context_getFlag(FLG_FUNCTIONCONSTRAINT) ||
940            context_getFlag(FLG_ARRAYBOUNDS) ||
941            context_getFlag(FLG_ARRAYBOUNDSREAD) ||
942            context_getFlag(FLG_CHECKPOST) 
943            )
944         )
945       {
946         exprNode_free (body);
947         context_exitInnerPlain();
948
949         return;
950       }
951   
952   exprNode_generateConstraints (body);
953
954   
955   c =   uentry_getFcnPreconditions (ue);
956   DPRINTF(("function constraints\n"));
957   DPRINTF (("\n\n\n\n\n\n\n"));
958
959   
960    if (constraintList_isDefined(c) )
961      {
962
963        DPRINTF ( (message ("Function preconditions are %s \n\n\n\n\n", constraintList_printDetailed (c) ) ) );
964        
965        body->requiresConstraints = constraintList_reflectChangesFreePre (body->requiresConstraints, c);
966        
967        c2  =  constraintList_copy (c);
968        fix =  constraintList_makeFixedArrayConstraints (body->uses);
969        c2  =  constraintList_reflectChangesFreePre (c2, fix);
970        constraintList_free(fix);
971        if ( context_getFlag (FLG_ORCONSTRAINT) )
972          {
973            t = constraintList_reflectChangesOr (body->requiresConstraints, c2 );
974          }
975        else
976          {
977            t = constraintList_reflectChanges(body->requiresConstraints, c2);
978          }
979    
980        constraintList_free(body->requiresConstraints);
981        DPRINTF ( (message ("The body has the required constraints: %s", constraintList_printDetailed (t) ) ) );
982
983        body->requiresConstraints = t;
984        
985        t = constraintList_mergeEnsures (c, body->ensuresConstraints);
986        constraintList_free(body->ensuresConstraints);
987        
988        body->ensuresConstraints = t;
989        
990        DPRINTF ( (message ("The body has the ensures constraints: %s", constraintList_printDetailed (t) ) ) );
991        constraintList_free(c2);
992      }
993    
994    if (constraintList_isDefined(c) )
995      {
996        DPRINTF((message ("The Function %s has the preconditions %s", uentry_unparse(ue), constraintList_printDetailed(c) ) ) );
997      }
998    else
999      {
1000        DPRINTF((message ("The Function %s has no preconditions", uentry_unparse(ue) ) ) );
1001      }
1002
1003    implicitFcnConstraints = getImplicitFcnConstraints();
1004    
1005    if (constraintList_isDefined(implicitFcnConstraints) )
1006      {
1007           if (context_getFlag (FLG_IMPLICTCONSTRAINT) )
1008               {
1009                 body->requiresConstraints = constraintList_reflectChangesFreePre (body->requiresConstraints, implicitFcnConstraints );
1010               }
1011      }
1012
1013    body->requiresConstraints = constraintList_sort (body->requiresConstraints);
1014    
1015    constraintList_printError(body->requiresConstraints, g_currentloc);
1016    
1017    post =   uentry_getFcnPostconditions (ue);
1018
1019    if ( context_getFlag (FLG_CHECKPOST) )
1020      {
1021        if (constraintList_isDefined(post) )
1022          {
1023            
1024            constraintList post2;
1025            
1026            DPRINTF ( (message ("The declared function postconditions are %s \n\n\n\n\n", constraintList_printDetailed (post) ) ) );
1027            
1028            post = constraintList_reflectChangesFreePre (post, body->ensuresConstraints);
1029            
1030            post2  =  constraintList_copy (post);
1031            fix =  constraintList_makeFixedArrayConstraints (body->uses);
1032            post2  =  constraintList_reflectChangesFreePre (post2, fix);
1033            constraintList_free(fix);
1034            if ( context_getFlag (FLG_ORCONSTRAINT) )
1035              {
1036                t = constraintList_reflectChangesOr (post2, body->ensuresConstraints);
1037              }
1038            else
1039              {
1040                t = constraintList_reflectChanges(post2, body->ensuresConstraints);
1041              }
1042            
1043            constraintList_free(post2);
1044            
1045            constraintList_free(post);
1046            post = t;
1047            
1048          
1049
1050        printf("Unresolved post conditions\n");
1051        constraintList_printErrorPostConditions(post, g_currentloc);
1052          }
1053      }
1054    
1055    if (constraintList_isDefined(post) )
1056      {
1057        constraintList_free(post);
1058      }
1059    
1060    body->ensuresConstraints = constraintList_sort(body->ensuresConstraints);
1061
1062    if ( context_getFlag (FLG_FUNCTIONPOST) )
1063      {
1064        constraintList_printError(body->ensuresConstraints, g_currentloc);
1065      }
1066    
1067    /*   ConPrint (message ("Unable to resolve function constraints:\n%s", constraintList_printDetailed(body->requiresConstraints) ), g_currentloc);
1068
1069         ConPrint (message ("Splint has found function post conditions:\n%s", constraintList_printDetailed(body->ensuresConstraints) ), g_currentloc);
1070   
1071         printf ("The required constraints are:\n%s", constraintList_printDetailed(body->requiresConstraints) );
1072         printf ("The ensures constraints are:\n%s", constraintList_printDetailed(body->ensuresConstraints) );
1073    */
1074    
1075    if (constraintList_isDefined(c) )
1076      constraintList_free(c);
1077
1078    context_exitInnerPlain();
1079
1080    /*is it okay not to free this?*/
1081   exprNode_free (body);
1082   }
1083
1084 void exprChecks_checkEmptyMacroBody (void)
1085 {
1086   uentry hdr;
1087   
1088   if (!(context_inFunctionLike () || context_inMacroConstant ()
1089         || context_inUnknownMacro ()))
1090     {
1091       llcontbug 
1092         (message ("exprNode_checkEmptyMacroBody: not in macro function or constant: %q", 
1093                   context_unparse ()));
1094       return;
1095     }
1096   
1097   hdr = context_getHeader ();
1098   
1099   beginLine ();
1100   
1101   if (uentry_isFunction (hdr))
1102     {
1103       voptgenerror 
1104         (FLG_MACROEMPTY,
1105          message 
1106          ("Macro definition for %q is empty", uentry_getName (hdr)),
1107          g_currentloc);
1108
1109       usymtab_checkFinalScope (FALSE);
1110     }
1111
1112   context_exitFunction ();
1113   return;
1114 }
1115
1116 void exprNode_checkIterBody (/*@only@*/ exprNode body)
1117 {
1118   context_exitAllClauses ();
1119
1120   context_exitFunction ();
1121   exprNode_free (body);
1122 }
1123
1124 void exprNode_checkIterEnd (/*@only@*/ exprNode body)
1125 {
1126   context_exitAllClauses ();
1127   context_exitFunction ();
1128   exprNode_free (body);
1129 }
1130
1131 static
1132 bool checkModifyAuxAux (/*@exposed@*/ sRef s, exprNode f, sRef alias, exprNode err)
1133 {
1134   bool hasMods = context_hasMods ();
1135   flagcode errCode = hasMods ? FLG_MODIFIES : FLG_MODNOMODS;
1136
1137   if (exprNode_isDefined (f))
1138     {
1139       f->sets = sRefSet_insert (f->sets, s); 
1140     }
1141
1142   if (context_getFlag (FLG_MODIFIES) 
1143       && (hasMods || context_getFlag (FLG_MODNOMODS)))
1144     {
1145       sRefSet mods = context_modList ();
1146
1147       if (!sRef_canModify (s, mods))
1148         {
1149           sRef rb = sRef_getRootBase (s);
1150           
1151           
1152           if (sRef_isFileOrGlobalScope (rb))
1153             {
1154               if (!context_checkGlobMod (rb))
1155                 {
1156                   return FALSE;
1157                 }
1158             }
1159           
1160           if (sRef_isInvalid (alias) || sRef_sameName (s, alias))
1161             {
1162               if (sRef_isLocalVar (sRef_getRootBase (s)))
1163                 {
1164                   voptgenerror 
1165                     (errCode,
1166                      message 
1167                      ("Undocumented modification of internal state (%q): %s", 
1168                       sRef_unparse (s), exprNode_unparse (err)), 
1169                      exprNode_isDefined (f) ? f->loc : g_currentloc);
1170                 }
1171               else
1172                 {
1173                   if (sRef_isSystemState (s))
1174                     {
1175                       if (errCode == FLG_MODNOMODS) 
1176                         {
1177                           if (context_getFlag (FLG_MODNOMODS))
1178                             {
1179                               errCode = FLG_MODFILESYSTEM;
1180                             }
1181                         }
1182                       else
1183                         {
1184                           errCode = FLG_MODFILESYSTEM;
1185                         }
1186                     }
1187
1188                   voptgenerror 
1189                     (errCode,
1190                      message ("Undocumented modification of %q: %s", 
1191                               sRef_unparse (s), exprNode_unparse (err)), 
1192                      exprNode_isDefined (f) ? f->loc : g_currentloc);
1193                 }
1194               
1195               return TRUE;
1196             }
1197           else
1198             {
1199               if (sRef_isReference (s) && !sRef_isAddress (alias))
1200                 {
1201                   voptgenerror 
1202                     (errCode,
1203                      message
1204                      ("Possible undocumented modification of %q through alias %q: %s", 
1205                       sRef_unparse (s),
1206                       sRef_unparse (alias),
1207                       exprNode_unparse (err)),
1208                      exprNode_isDefined (f) ? f->loc : g_currentloc);
1209                   return TRUE;
1210                 }
1211             }
1212         }
1213     }
1214   else
1215     {
1216       if (context_maybeSet (FLG_MUSTMOD))
1217         {
1218           (void) sRef_canModify (s, context_modList ());
1219         }
1220       
1221       if (sRef_isRefsField (s))
1222         {
1223           sRef_setModified (s);
1224         }
1225     }
1226   
1227   return FALSE;
1228 }
1229
1230 static
1231 bool checkModifyAux (/*@exposed@*/ sRef s, exprNode f, sRef alias, exprNode err)
1232 {
1233   DPRINTF (("Check modify aux: %s", sRef_unparseFull (s)));
1234
1235   if (sRef_isReference (s) && sRef_isObserver (s) 
1236       && context_maybeSet (FLG_MODOBSERVER))
1237     {    
1238       cstring sname;
1239       
1240       if (sRef_isPointer (s)) 
1241         {
1242           sRef base = sRef_getBase (s);
1243           sname = sRef_unparse (base);
1244         }
1245       else 
1246         {
1247           if (sRef_isAddress (s))
1248             {
1249               sRef p = sRef_constructPointer (s);
1250               sname = sRef_unparse (p);
1251             }
1252           else
1253             {
1254               sname = sRef_unparse (s);
1255             }
1256         }
1257       
1258       if (!sRef_isValid (alias) || sRef_sameName (s, alias))
1259         {
1260           if (sRef_isMeaningful (s))
1261             {
1262               if (optgenerror 
1263                   (FLG_MODOBSERVER,
1264                    message ("Suspect modification of observer %s: %s", 
1265                             sname, exprNode_unparse (err)), 
1266                    exprNode_isDefined (f) ? f->loc : g_currentloc))
1267                 {
1268                   sRef_showExpInfo (s);
1269                 }
1270             }
1271           else
1272             {
1273               voptgenerror 
1274                 (FLG_MODOBSERVER,
1275                  message ("Suspect modification of observer returned by "
1276                           "function call: %s", 
1277                           exprNode_unparse (err)), 
1278                  exprNode_isDefined (f) ? f->loc : g_currentloc);
1279             }
1280         }
1281       else
1282         {
1283           if (optgenerror
1284               (FLG_MODOBSERVER,
1285                message ("Suspect modification of observer %s through alias %q: %s", 
1286                         sname, sRef_unparse (alias), exprNode_unparse (err)), 
1287                exprNode_isDefined (f) ? f->loc : g_currentloc))
1288             {
1289               sRef_showExpInfo (s);
1290             }
1291         }
1292       
1293       cstring_free (sname);
1294     }
1295   
1296   (void) checkModifyAuxAux (s, f, alias, err);
1297   return FALSE;
1298 }
1299
1300 static
1301 bool checkModifyValAux (/*@exposed@*/ sRef s, exprNode f, sRef alias, exprNode err)
1302 {
1303   (void) checkModifyAuxAux (s, f, alias, err);
1304   return FALSE;
1305 }
1306
1307 static
1308 bool checkCallModifyAux (/*@exposed@*/ sRef s, exprNode f, sRef alias, exprNode err)
1309 {
1310   bool result = FALSE;
1311
1312   DPRINTF (("Check modify aux: %s / %s",
1313             sRef_unparse (s), sRef_unparse (alias)));
1314
1315   if (sRef_isObserver (s) && context_maybeSet (FLG_MODOBSERVER))
1316     {    
1317       sRef p = sRef_isAddress (s) ? sRef_constructPointer (s) : s;
1318       cstring sname = sRef_unparse (p);
1319
1320       if (!sRef_isValid (alias) || sRef_sameName (s, alias))
1321         {
1322           if (sRef_isMeaningful (s))
1323             {
1324               result = optgenerror 
1325                 (FLG_MODOBSERVER,
1326                  message ("Suspect modification of observer %s: %s", 
1327                           sname, exprNode_unparse (err)), 
1328                  exprNode_isDefined (f) ? f->loc : g_currentloc);
1329             }
1330           else
1331             {
1332               result = optgenerror 
1333                 (FLG_MODOBSERVER,
1334                  message ("Suspect modification of observer returned by "
1335                           "function call: %s", 
1336                           exprNode_unparse (err)), 
1337                  exprNode_isDefined (f) ? f->loc : g_currentloc);
1338             }
1339         }
1340       else
1341         {
1342           result = optgenerror 
1343             (FLG_MODOBSERVER,
1344              message
1345              ("Suspect modification of observer %s through alias %q: %s", 
1346               sname, sRef_unparse (alias), exprNode_unparse (err)), 
1347              exprNode_isDefined (f) ? f->loc : g_currentloc);
1348         }
1349       
1350       cstring_free (sname);
1351     }
1352   else if (context_maybeSet (FLG_MODIFIES))
1353     {
1354       DPRINTF (("can modify: %s / %s",
1355                 sRef_unparse (s),
1356                 sRefSet_unparse (context_modList ())));
1357
1358       if (!(sRef_canModifyVal (s, context_modList ())))
1359         {
1360           sRef p = sRef_isAddress (s) ? sRef_constructPointer (s) : s;
1361           cstring sname = sRef_unparse (p);
1362           bool hasMods = context_hasMods ();
1363           sRef rb = sRef_getRootBase (s);
1364           flagcode errCode = hasMods ? FLG_MODIFIES : FLG_MODNOMODS;
1365           bool check = TRUE;
1366
1367           DPRINTF (("Can't modify! %s", sRef_unparse (s)));
1368
1369           if (sRef_isFileOrGlobalScope (rb))
1370             {
1371               uentry ue = sRef_getUentry (rb);
1372               
1373               /* be more specific here! */
1374               if (!uentry_isCheckedModify (ue))
1375                 {
1376                   check = FALSE;
1377                 }
1378             }
1379           
1380           if (check)
1381             {
1382               if (!sRef_isValid (alias) || sRef_sameName (s, alias))
1383                 {
1384                   if (sRef_isLocalVar (sRef_getRootBase (s)))
1385                     {
1386                       voptgenerror 
1387                         (errCode,
1388                          message 
1389                          ("Undocumented modification of internal "
1390                           "state (%q) through call to %s: %s", 
1391                           sRef_unparse (s), exprNode_unparse (f),
1392                           exprNode_unparse (err)), 
1393                          exprNode_isDefined (f) ? f->loc : g_currentloc);
1394                     }
1395                   else
1396                     {
1397                       if (sRef_isSystemState (s))
1398                         {
1399                           if (errCode == FLG_MODNOMODS) 
1400                             {
1401                               if (context_getFlag (FLG_MODNOMODS))
1402                                 {
1403                                   errCode = FLG_MODFILESYSTEM;
1404                                 }
1405                             }
1406                           else
1407                             {
1408                               errCode = FLG_MODFILESYSTEM;
1409                             }
1410                         }
1411                       
1412                       result = optgenerror 
1413                         (errCode,
1414                          message ("Undocumented modification of %s "
1415                                   "possible from call to %s: %s", 
1416                                   sname,
1417                                   exprNode_unparse (f),
1418                                   exprNode_unparse (err)),
1419                          exprNode_isDefined (f) ? f->loc : g_currentloc);
1420                     }
1421                 }
1422               else
1423                 {
1424                   result = optgenerror
1425                     (errCode,
1426                      message ("Undocumented modification of %s possible "
1427                               "from call to %s (through alias %q): %s", 
1428                               sname,
1429                               exprNode_unparse (f), 
1430                               sRef_unparse (alias), 
1431                               exprNode_unparse (err)),
1432                      exprNode_isDefined (f) ? f->loc : g_currentloc);
1433                 }
1434             }
1435           cstring_free (sname);
1436         }
1437     }
1438   else
1439     {
1440       if (context_maybeSet (FLG_MUSTMOD))
1441         {
1442           (void) sRef_canModifyVal (s, context_modList ());
1443         }
1444     }
1445
1446   return result;
1447 }
1448
1449 void exprNode_checkCallModifyVal (sRef s, exprNodeList args, exprNode f, exprNode err)
1450 {
1451   s = sRef_fixBaseParam (s, args);
1452   DPRINTF (("Check call modify: %s", sRef_unparse (s)));
1453   sRef_aliasCheckPred (checkCallModifyAux, NULL, s, f, err);
1454 }
1455
1456 void
1457 exprChecks_checkExport (uentry e)
1458 {
1459   if (context_checkExport (e))
1460     {
1461       fileloc fl = uentry_whereDeclared (e);
1462       
1463       if (fileloc_isHeader (fl) && !fileloc_isLib (fl) 
1464           && !fileloc_isImport (fl) && !uentry_isStatic (e))
1465         {
1466           if (uentry_isFunction (e) || 
1467               (uentry_isVariable (e) && ctype_isFunction (uentry_getType (e))))
1468             {
1469               voptgenerror 
1470                 (FLG_EXPORTFCN,
1471                  message ("Function exported, but not specified: %q", 
1472                           uentry_getName (e)),
1473                  fl);
1474             }
1475           else if (uentry_isExpandedMacro (e))
1476             {
1477               voptgenerror
1478                 (FLG_EXPORTMACRO,
1479                  message ("Expanded macro exported, but not specified: %q", 
1480                           uentry_getName (e)),
1481                  fl);
1482             }
1483           else if (uentry_isVariable (e) && !uentry_isParam (e)) 
1484             {
1485               voptgenerror 
1486                 (FLG_EXPORTVAR,
1487                  message ("Variable exported, but not specified: %q", 
1488                           uentry_getName (e)),
1489                  fl);
1490             }
1491           else if (uentry_isEitherConstant (e))
1492             {
1493               voptgenerror 
1494                 (FLG_EXPORTCONST,
1495                  message ("Constant exported, but not specified: %q", 
1496                           uentry_getName (e)),
1497                  fl);
1498             }
1499           else if (uentry_isIter (e) || uentry_isEndIter (e))
1500             {
1501               voptgenerror 
1502                 (FLG_EXPORTITER,
1503                  message ("Iterator exported, but not specified: %q", 
1504                           uentry_getName (e)),
1505                  fl);
1506             }
1507
1508           else if (uentry_isDatatype (e))
1509             {
1510               ; /* error already reported */
1511             }
1512           else
1513             {
1514               BADEXIT;
1515             }
1516         }
1517     }
1518 }
1519
1520 static void checkSafeReturnExpr (/*@notnull@*/ exprNode e)
1521 {
1522   ctype tr = ctype_getReturnType (context_currentFunctionType ());
1523   ctype te = exprNode_getType (e);
1524
1525   /* evans 2001-08-21: added test to warn about void returns from void functions */
1526   if (ctype_isVoid (tr))
1527     {
1528       (void) gentypeerror
1529         (te, e, tr, exprNode_undefined,
1530          message ("Return expression from function declared void: %s", exprNode_unparse (e)),
1531          e->loc);
1532       return;
1533     }
1534
1535   if (!ctype_forceMatch (tr, te) && !exprNode_matchLiteral (tr, e))
1536     {
1537       (void) gentypeerror
1538         (te, e, tr, exprNode_undefined,
1539          message ("Return value type %t does not match declared type %t: %s",
1540                   te, tr, exprNode_unparse (e)),
1541          e->loc);
1542     }
1543   else
1544     {
1545       sRef ret = e->sref;
1546       uentry rval = context_getHeader ();
1547       sRef resultref = uentry_getSref (rval);
1548
1549       DPRINTF (("Check return: %s / %s / %s",
1550                 exprNode_unparse (e),
1551                 sRef_unparseFull (e->sref),
1552                 uentry_unparse (rval)));
1553
1554       checkReturnTransfer (e, rval);
1555
1556       DPRINTF (("After return: %s / %s / %s",
1557                 exprNode_unparse (e),
1558                 sRef_unparseFull (e->sref),
1559                 uentry_unparse (rval)));
1560
1561       if (!(sRef_isExposed (uentry_getSref (context_getHeader ()))
1562             || sRef_isObserver (uentry_getSref (context_getHeader ())))
1563           && (context_getFlag (FLG_RETALIAS) 
1564               || context_getFlag (FLG_RETEXPOSE)))
1565         {
1566           sRef base = sRef_getRootBase (ret);
1567           ctype rtype = e->typ;
1568
1569           if (ctype_isUnknown (rtype))
1570             {
1571               rtype = tr;
1572             }
1573
1574           if (ctype_isVisiblySharable (rtype))
1575             {
1576               if (context_getFlag (FLG_RETALIAS))
1577                 {
1578                   sRef_aliasCheckPred (checkRefGlobParam, NULL, base, 
1579                                        e, exprNode_undefined);
1580                 }
1581               
1582               if (context_getFlag (FLG_RETEXPOSE) && sRef_isIReference (ret) 
1583                   && !sRef_isExposed (resultref) && !sRef_isObserver (resultref))
1584                 {
1585                   sRef_aliasCheckPred (checkRepExposed, NULL, base, e, 
1586                                        exprNode_undefined);
1587                 }
1588             }
1589         }
1590     }
1591 }
1592
1593
1594
1595
1596
This page took 0.176408 seconds and 5 git commands to generate.