001: /* Copyright (C) 2004 - 2007 db4objects Inc. http://www.db4o.com
002:
003: This file is part of the db4o open source object database.
004:
005: db4o is free software; you can redistribute it and/or modify it under
006: the terms of version 2 of the GNU General Public License as published
007: by the Free Software Foundation and as clarified by db4objects' GPL
008: interpretation policy, available at
009: http://www.db4o.com/about/company/legalpolicies/gplinterpretation/
010: Alternatively you can write to db4objects, Inc., 1900 S Norfolk Street,
011: Suite 350, San Mateo, CA 94403, USA.
012:
013: db4o is distributed in the hope that it will be useful, but WITHOUT ANY
014: WARRANTY; without even the implied warranty of MERCHANTABILITY or
015: FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
016: for more details.
017:
018: You should have received a copy of the GNU General Public License along
019: with this program; if not, write to the Free Software Foundation, Inc.,
020: 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
021: package EDU.purdue.cs.bloat.tree;
022:
023: import java.util.*;
024:
025: /**
026: * AscendVisitor is the superclass of Type0Visitor and Type1Visitor,
027: * conveniently containing the common code. It makes an upward traversal of the
028: * tree as if it were a binary tree (nodes with more than two children, such as
029: * a method call, are considered in a form similar to curried form).
030: *
031: * @author Thomas VanDrunen
032: */
033:
034: public abstract class AscendVisitor extends TreeVisitor {
035:
036: Hashtable defInfoMap; /* the same as the fields of Stack Optimizer */
037:
038: Hashtable useInfoMap; /* of the same name */
039:
040: LocalExpr start; /* where we start the search from */
041:
042: Node previous;
043:
044: Vector visited;
045:
046: public AscendVisitor(final Hashtable defInfoMap,
047: final Hashtable useInfoMap) {
048: this .defInfoMap = defInfoMap;
049: this .useInfoMap = useInfoMap;
050:
051: visited = new Vector();
052: }
053:
054: abstract public void check(Node node);
055:
056: public void visitTree(final Tree tree) {
057:
058: final ListIterator iter = tree.stmts().listIterator(
059: tree.stmts().lastIndexOf(previous));
060:
061: if (iter.hasPrevious()) {
062: final Stmt p = (Stmt) iter.previous();
063: check(p);
064: }
065: /*
066: * Object prev = iter.previous(); if (prev instanceof LocalExpr)
067: * check(prev);
068: */
069: }
070:
071: public void visitExprStmt(final ExprStmt stmt) {
072:
073: previous = stmt;
074: stmt.parent().visit(this );
075: }
076:
077: public void visitIfCmpStmt(final IfCmpStmt stmt) {
078:
079: if (stmt.right() == previous) {
080: check(stmt.left());
081: } else if (stmt.left() == previous) {
082: previous = stmt;
083: stmt.parent().visit(this );
084: }
085: }
086:
087: public void visitIfZeroStmt(final IfZeroStmt stmt) {
088:
089: previous = stmt;
090: stmt.parent.visit(this );
091: }
092:
093: public void visitInitStmt(final InitStmt stmt) {
094:
095: final LocalExpr[] targets = stmt.targets();
096: for (int i = 0; i < targets.length; i++) {
097: if (targets[i] == previous) {
098: if (i > 0) {
099: check(targets[i - 1]);
100: } else {
101: break;
102: }
103: }
104: }
105: }
106:
107: public void visitGotoStmt(final GotoStmt stmt) {
108:
109: }
110:
111: public void visitLabelStmt(final LabelStmt stmt) {
112:
113: }
114:
115: public void visitMonitorStmt(final MonitorStmt stmt) {
116:
117: previous = stmt;
118: stmt.parent().visit(this );
119: }
120:
121: public void visitPhiStmt(final PhiStmt stmt) {
122:
123: if (stmt instanceof PhiCatchStmt) {
124: visitPhiCatchStmt((PhiCatchStmt) stmt);
125: } else if (stmt instanceof PhiJoinStmt) {
126: visitPhiJoinStmt((PhiJoinStmt) stmt);
127: /*
128: * else if (stmt instanceof PhiReturnStmt)
129: * visitPhiReturnStmt((PhiReturnStmt) stmt);
130: */
131: }
132: }
133:
134: public void visitCatchExpr(final CatchExpr expr) {
135:
136: }
137:
138: public void visitDefExpr(final DefExpr expr) {
139: if (expr instanceof MemExpr) {
140: visitMemExpr((MemExpr) expr);
141: }
142: }
143:
144: public void visitStackManipStmt(final StackManipStmt stmt) {
145:
146: }
147:
148: public void visitPhiCatchStmt(final PhiCatchStmt stmt) {
149:
150: }
151:
152: public void visitPhiJoinStmt(final PhiJoinStmt stmt) {
153:
154: }
155:
156: public void visitRetStmt(final RetStmt stmt) {
157:
158: }
159:
160: public void visitReturnExprStmt(final ReturnExprStmt stmt) {
161:
162: previous = stmt;
163: stmt.parent.visit(this );
164: }
165:
166: public void visitReturnStmt(final ReturnStmt stmt) {
167:
168: }
169:
170: public void visitAddressStoreStmt(final AddressStoreStmt stmt) {
171:
172: }
173:
174: public void visitStoreExpr(final StoreExpr expr) {
175:
176: if ((expr.target() instanceof LocalExpr)
177: || (expr.target() instanceof StaticFieldExpr)) {
178: if (previous == expr.expr()) { // can't be target, because then
179: // it would be a definition, for which
180: // Type0Visitor is not called
181: previous = expr;
182: expr.parent.visit(this );
183: }
184: }
185:
186: else if (expr.target() instanceof ArrayRefExpr) {
187: if (previous == expr.expr()) {
188: check(((ArrayRefExpr) expr.target()).index());
189: } else if (previous == expr.target()) {
190: previous = expr;
191: expr.parent.visit(this );
192: }
193: }
194:
195: else if (expr.target() instanceof FieldExpr) {
196: if (previous == expr.expr()) {
197: check(expr.target());
198: } else if (previous == expr.target()) {
199: previous = expr;
200: expr.parent.visit(this );
201: }
202: }
203: }
204:
205: public void visitJsrStmt(final JsrStmt stmt) {
206:
207: }
208:
209: public void visitSwitchStmt(final SwitchStmt stmt) {
210:
211: if (previous == stmt.index()) {
212: previous = stmt;
213: stmt.parent.visit(this );
214: }
215: }
216:
217: public void visitThrowStmt(final ThrowStmt stmt) {
218:
219: }
220:
221: public void visitStmt(final Stmt stmt) {
222:
223: }
224:
225: public void visitSCStmt(final SCStmt stmt) {
226:
227: }
228:
229: public void visitSRStmt(final SRStmt stmt) {
230:
231: }
232:
233: public void visitArithExpr(final ArithExpr expr) {
234:
235: if (previous == expr.left()) {
236: previous = expr;
237: expr.parent.visit(this );
238: } else if (previous == expr.right()) {
239: check(expr.left());
240: }
241:
242: }
243:
244: public void visitArrayLengthExpr(final ArrayLengthExpr expr) {
245:
246: }
247:
248: public void visitMemExpr(final MemExpr expr) {
249:
250: if (expr instanceof MemRefExpr) {
251: visitMemRefExpr((MemRefExpr) expr);
252: } else if (expr instanceof VarExpr) {
253: visitVarExpr((VarExpr) expr);
254: }
255:
256: }
257:
258: public void visitMemRefExpr(final MemRefExpr expr) {
259: if (expr instanceof FieldExpr) {
260: visitFieldExpr((FieldExpr) expr);
261: } else if (expr instanceof StaticFieldExpr) {
262: visitStaticFieldExpr((StaticFieldExpr) expr);
263: } else if (expr instanceof ArrayRefExpr) {
264: visitArrayRefExpr((ArrayRefExpr) expr);
265: }
266:
267: }
268:
269: public void visitArrayRefExpr(final ArrayRefExpr expr) {
270:
271: if (previous == expr.array()) { // the array reference is like the
272: previous = expr; // left child
273: expr.parent().visit(this );
274: } else if (previous == expr.index()) {
275: check(expr.array()); // right child
276: }
277: }
278:
279: public void visitCallExpr(final CallExpr expr) {
280: if (expr instanceof CallMethodExpr) {
281: visitCallMethodExpr((CallMethodExpr) expr);
282: }
283: if (expr instanceof CallStaticExpr) {
284: visitCallStaticExpr((CallStaticExpr) expr);
285: }
286:
287: }
288:
289: public void visitCallMethodExpr(final CallMethodExpr expr) {
290:
291: if (previous == expr.receiver()) {
292: previous = expr;
293: expr.parent.visit(this );
294: }
295:
296: else {
297: final Expr[] params = expr.params();
298: for (int i = 0; i < params.length; i++) {
299: if (params[i] == previous) {
300: if (i > 0) {
301: check(params[i - 1]);
302: } else {
303: check(expr.receiver());
304: }
305: }
306: }
307: }
308:
309: }
310:
311: public void visitCallStaticExpr(final CallStaticExpr expr) {
312:
313: final Expr[] params = expr.params();
314: for (int i = 0; i < params.length; i++) {
315: if (params[i] == previous) {
316: if (i > 0) {
317: check(params[i - 1]);
318: } else {
319: previous = expr;
320: expr.parent().visit(this );
321: }
322: break;
323: }
324: }
325:
326: }
327:
328: public void visitCastExpr(final CastExpr expr) {
329:
330: previous = expr;
331: expr.parent.visit(this );
332: }
333:
334: public void visitConstantExpr(final ConstantExpr expr) {
335:
336: }
337:
338: public void visitFieldExpr(final FieldExpr expr) {
339:
340: if (previous == expr.object()) {
341: previous = expr;
342: expr.parent.visit(this );
343: }
344: }
345:
346: public void visitInstanceOfExpr(final InstanceOfExpr expr) {
347:
348: if (previous == expr.expr()) {
349: previous = expr;
350: expr.parent.visit(this );
351: }
352: }
353:
354: public void visitLocalExpr(final LocalExpr expr) {
355:
356: }
357:
358: public void visitNegExpr(final NegExpr expr) {
359:
360: if (previous == expr.expr()) {
361: previous = expr;
362: expr.parent.visit(this );
363: }
364: }
365:
366: public void visitNewArrayExpr(final NewArrayExpr expr) {
367:
368: if (previous == expr.size()) {
369: previous = expr;
370: expr.parent.visit(this );
371: }
372: }
373:
374: public void visitNewExpr(final NewExpr expr) {
375:
376: }
377:
378: public void visitNewMultiArrayExpr(final NewMultiArrayExpr expr) {
379:
380: final Expr[] dims = expr.dimensions;
381: for (int i = 0; i < dims.length; i++) {
382: if (dims[i] == previous) {
383: if (i > 0) {
384: check(dims[i - 1]);
385: } else {
386: previous = expr;
387: expr.parent().visit(this );
388: }
389: }
390: }
391:
392: }
393:
394: public void visitCheckExpr(final CheckExpr expr) {
395: if (expr instanceof ZeroCheckExpr) {
396: visitZeroCheckExpr((ZeroCheckExpr) expr);
397: } else if (expr instanceof RCExpr) {
398: visitRCExpr((RCExpr) expr);
399: } else if (expr instanceof UCExpr) {
400: visitUCExpr((UCExpr) expr);
401: }
402: }
403:
404: public void visitZeroCheckExpr(final ZeroCheckExpr expr) {
405: /*
406: * if (previous == expr.expr()) { previous = expr;
407: * expr.parent.visit(this); }
408: */
409: }
410:
411: public void visitRCExpr(final RCExpr expr) {
412:
413: }
414:
415: public void visitUCExpr(final UCExpr expr) {
416:
417: }
418:
419: public void visitReturnAddressExpr(final ReturnAddressExpr expr) {
420:
421: }
422:
423: public void visitShiftExpr(final ShiftExpr expr) {
424:
425: if (previous == expr.expr()) { // the expression to be shifted is like
426: previous = expr; // the left child
427: expr.parent().visit(this );
428: } else if (previous == expr.bits()) {
429: check(expr.expr()); // the right child
430: }
431: }
432:
433: public void visitStackExpr(final StackExpr expr) {
434:
435: }
436:
437: public void visitVarExpr(final VarExpr expr) {
438: if (expr instanceof LocalExpr) {
439: visitLocalExpr((LocalExpr) expr);
440: }
441: if (expr instanceof StackExpr) {
442: visitStackExpr((StackExpr) expr);
443: }
444: }
445:
446: public void visitStaticFieldExpr(final StaticFieldExpr expr) {
447:
448: }
449:
450: public void visitExpr(final Expr expr) {
451:
452: }
453:
454: public void visitNode(final Node node) {
455:
456: }
457: }
|