KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > aspectj > compiler > base > ast > BlockStmt


1 /* -*- Mode: Java; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*-
2  *
3  * This file is part of the compiler and core tools for the AspectJ(tm)
4  * programming language; see http://aspectj.org
5  *
6  * The contents of this file are subject to the Mozilla Public License
7  * Version 1.1 (the "License"); you may not use this file except in
8  * compliance with the License. You may obtain a copy of the License at
9  * either http://www.mozilla.org/MPL/ or http://aspectj.org/MPL/.
10  *
11  * Software distributed under the License is distributed on an "AS IS" basis,
12  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
13  * for the specific language governing rights and limitations under the
14  * License.
15  *
16  * The Original Code is AspectJ.
17  *
18  * The Initial Developer of the Original Code is Xerox Corporation. Portions
19  * created by Xerox Corporation are Copyright (C) 1999-2002 Xerox Corporation.
20  * All Rights Reserved.
21  *
22  * Contributor(s):
23  */

24
25 package org.aspectj.compiler.base.ast;
26
27 import org.aspectj.compiler.base.*;
28 import org.aspectj.compiler.base.cst.BlockScope;
29
30 import org.aspectj.compiler.base.bcg.CodeBuilder;
31
32 /**
33   * @grammar { stmts* }
34   * @child Stmts tmpStmts
35   * @child Stmts stmts
36   */

37 public class BlockStmt extends Stmt {
38
39     public boolean isEmpty() {
40         final int len = getStmts().size();
41         for (int i = 0; i < len; i++) {
42             if (! getStmts().get(i).isEmpty())
43                 return false;
44         }
45         return true;
46     }
47     
48     public void requireBlockStmt() { ; }
49
50     private static Stmt makeStmt(ASTObject node) {
51         if (node instanceof Stmt) return (Stmt)node;
52         if (node instanceof Expr) return new ExprStmt(node.getSourceLocation(),(Expr)node);
53         throw new RuntimeException JavaDoc("node can not be made into a statement: "+node);
54     }
55
56     public BlockStmt(SourceLocation location, ASTObject node1) {
57         this(location,node1 instanceof BlockStmt ? ((BlockStmt)node1).getStmts() :
58              new Stmts(location,new Stmt[] {makeStmt(node1)}));
59     }
60     public BlockStmt(SourceLocation location, ASTObject node1, ASTObject node2) {
61         this(location,new Stmts(location,new Stmt[] {makeStmt(node1), makeStmt(node2)}));
62     }
63     public BlockStmt(SourceLocation location, ASTObject node1, ASTObject node2, ASTObject node3) {
64         this(location,new Stmts(location,new Stmt[] {makeStmt(node1), makeStmt(node2), makeStmt(node3)}));
65     }
66     public BlockStmt(SourceLocation location, ASTObject node1, ASTObject node2, ASTObject node3, ASTObject node4) {
67         this(location,new Stmts(location,new Stmt[] {makeStmt(node1), makeStmt(node2), makeStmt(node3), makeStmt(node4)}));
68     }
69
70     // ------------------------------
71
// INTRO from FlowCheckerPass
72

73     /**
74       * when the -lenient option is used,
75       * we declare that empty block don't have to be live.
76       * This makes code like: return 2; {} legal.
77       */

78     public boolean mustBeLive() { return !getOptions().lenient; }
79
80     public void walkFlow(FlowCheckerPass w) {
81         Stmts s = getStmts();
82         for (int i = 0, len = s.size(); i < len; i++) {
83             Stmt st = s.get(i);
84             if (! w.isLive() && st.mustBeLive()) {
85                 st.showError("unreachable statement");
86                 break;
87             } else {
88                 w.process(s.get(i));
89             }
90         }
91     }
92
93     // ------------------------------
94
// Intro: ByteCodeCleanupPass
95

96     public void walkCleanup(ByteCodeCleanupPass w) {
97         makeTempsExplicit();
98         getStmts().walkCleanup(w);
99     }
100
101     public ASTObject postCleanup(ByteCodeCleanupPass w) {
102         if (getStmts().size() == 0) {
103             return getAST().makeEmptyStmt().setSource(this);
104         } else {
105             return this;
106         }
107     }
108
109     protected void makeTempsExplicit() {
110         if (tmpStmts != null) {
111             for (int i = 0, len = tmpStmts.size(); i < len; i++) {
112                 getStmts().add(0, tmpStmts.get(i));
113             }
114             tmpStmts = null;
115         }
116     }
117
118     // ------------------------------
119
// Intro: FrameLocPass
120

121     public void walkFrameLoc(FrameLocPass walker) {
122         int start = walker.getfs();
123         super.walkFrameLoc(walker);
124         walker.setfs(start);
125     }
126
127     //INTRO from ScopePass
128
public void preScope(ScopeWalker walker) { walker.pushBlock(); }
129     public ASTObject postScope(ScopeWalker walker) { walker.popBlock(); return this; }
130
131     //XXX this counter could be trouble
132
//int temporaries = 0;
133
//Stmts tmpStmts; // = new Stmts();
134
public VarDec makeTemporary(Type type) {
135 // String id = "ajc$tmp$" + ++temporaries;
136
//
137
// if (getDeclaringType() != null && getDeclaringType().isAnonymous()) {
138
// id += "x";
139
// }
140

141         VarDec tmp = getAST().makeVarDec(type, "ajc$tmp", null);
142         addTemporary(tmp);
143         tmpStmts.add(0, tmp);
144         return tmp;
145     }
146
147     public void addTemporary(VarDec tmp) {
148         if (getTmpStmts() == null) setTmpStmts(getAST().makeStmts()); //new Stmts(getCompiler());
149
tmp.setId(tmp.getId() + tmpStmts.size());
150         tmpStmts.add(0, tmp);
151     }
152
153     public void checkReturnType(Type expectedReturnType) {
154         ReturnTypeChecker rtc = new ReturnTypeChecker(getCompiler(),expectedReturnType);
155         rtc.process(stmts);
156     }
157
158     //!!! way too simple
159
static class ReturnTypeChecker extends Walker {
160         Type expectedReturnType;
161
162         ReturnTypeChecker(JavaCompiler compiler, Type expectedReturnType) {
163             super(compiler);
164             this.expectedReturnType = expectedReturnType;
165         }
166
167         public boolean preProcess(ASTObject node) {
168             if (node instanceof ReturnStmt) {
169                 Expr returnExpr = ((ReturnStmt)node).getExpr();
170                 if (returnExpr == null) {
171                     if (!expectedReturnType.isEquivalent(getTypeManager().voidType)) {
172                         node.showError(expectedReturnType.toShortString()+" return expected");
173                     }
174                 } else {
175                     if (!expectedReturnType.isAssignableFrom(returnExpr.getType())) {
176                         node.showError(expectedReturnType.toShortString()+" return expected");
177                     }
178                 }
179                 return true;
180             }
181             return !(node instanceof TypeDec);
182         }
183     }
184
185     public void unparse(CodeWriter writer) {
186         writer.openBlock();
187         if (tmpStmts != null) writer.write(tmpStmts);
188         writer.write(stmts);
189         writer.closeBlock();
190     }
191
192     public void cleanup() {
193         stmts = null;
194         tmpStmts = null;
195         super.cleanup();
196     }
197
198     // ------------------------------
199
// bcg
200
protected void cgStmt(CodeBuilder cb) {
201         cb.enterBlock();
202         stmts.cgStmts(cb);
203         cb.exitBlock();
204     }
205
206     // ------------------------------
207
// convenience constructors
208

209     public BlockStmt(SourceLocation location, Stmts _stmts) {
210         this(location, null, _stmts);
211     }
212
213     //BEGIN: Generated from @child and @property
214
protected Stmts tmpStmts;
215     public Stmts getTmpStmts() { return tmpStmts; }
216     public void setTmpStmts(Stmts _tmpStmts) {
217         if (_tmpStmts != null) _tmpStmts.setParent(this);
218         tmpStmts = _tmpStmts;
219     }
220
221     protected Stmts stmts;
222     public Stmts getStmts() { return stmts; }
223     public void setStmts(Stmts _stmts) {
224         if (_stmts != null) _stmts.setParent(this);
225         stmts = _stmts;
226     }
227
228     public BlockStmt(SourceLocation location, Stmts _tmpStmts, Stmts _stmts) {
229         super(location);
230         setTmpStmts(_tmpStmts);
231         setStmts(_stmts);
232     }
233     protected BlockStmt(SourceLocation source) {
234         super(source);
235     }
236
237     public ASTObject copyWalk(CopyWalker walker) {
238         BlockStmt ret = new BlockStmt(getSourceLocation());
239         ret.preCopy(walker, this);
240         if (tmpStmts != null) ret.setTmpStmts( (Stmts)walker.process(tmpStmts) );
241         if (stmts != null) ret.setStmts( (Stmts)walker.process(stmts) );
242         return ret;
243     }
244
245     public ASTObject getChildAt(int childIndex) {
246         switch(childIndex) {
247         case 0: return tmpStmts;
248         case 1: return stmts;
249         default: return super.getChildAt(childIndex);
250         }
251     }
252      public String JavaDoc getChildNameAt(int childIndex) {
253         switch(childIndex) {
254         case 0: return "tmpStmts";
255         case 1: return "stmts";
256         default: return super.getChildNameAt(childIndex);
257         }
258     }
259      public void setChildAt(int childIndex, ASTObject child) {
260         switch(childIndex) {
261         case 0: setTmpStmts((Stmts)child); return;
262         case 1: setStmts((Stmts)child); return;
263         default: super.setChildAt(childIndex, child); return;
264         }
265     }
266      public int getChildCount() {
267         return 2;
268     }
269
270     public String JavaDoc getDefaultDisplayName() {
271         return "BlockStmt()";
272     }
273
274     //END: Generated from @child and @property
275
}
276
277
278
Popular Tags