00001
00025 package org.objectweb.jonas_ejb.lib;
00026
00027 import java.util.ArrayList;
00028 import java.util.Map;
00029 import java.util.Stack;
00030
00031 import javax.ejb.EJBObject;
00032
00033 import org.objectweb.jonas_ejb.deployment.ejbql.ASTArithmeticExpression;
00034 import org.objectweb.jonas_ejb.deployment.ejbql.ASTArithmeticFactor;
00035 import org.objectweb.jonas_ejb.deployment.ejbql.ASTArithmeticLiteral;
00036 import org.objectweb.jonas_ejb.deployment.ejbql.ASTArithmeticTerm;
00037 import org.objectweb.jonas_ejb.deployment.ejbql.ASTBetweenExpression;
00038 import org.objectweb.jonas_ejb.deployment.ejbql.ASTBooleanExpression;
00039 import org.objectweb.jonas_ejb.deployment.ejbql.ASTBooleanLiteral;
00040 import org.objectweb.jonas_ejb.deployment.ejbql.ASTCmpPathExpression;
00041 import org.objectweb.jonas_ejb.deployment.ejbql.ASTCollectionMemberExpression;
00042 import org.objectweb.jonas_ejb.deployment.ejbql.ASTCollectionValuedPathExpression;
00043 import org.objectweb.jonas_ejb.deployment.ejbql.ASTComparisonExpression;
00044 import org.objectweb.jonas_ejb.deployment.ejbql.ASTConditionalExpression;
00045 import org.objectweb.jonas_ejb.deployment.ejbql.ASTConditionalFactor;
00046 import org.objectweb.jonas_ejb.deployment.ejbql.ASTConditionalTerm;
00047 import org.objectweb.jonas_ejb.deployment.ejbql.ASTDatetimeExpression;
00048 import org.objectweb.jonas_ejb.deployment.ejbql.ASTEJBQL;
00049 import org.objectweb.jonas_ejb.deployment.ejbql.ASTEmptyCollectionComparisonExpression;
00050 import org.objectweb.jonas_ejb.deployment.ejbql.ASTEntityBeanExpression;
00051 import org.objectweb.jonas_ejb.deployment.ejbql.ASTFloatingPointLiteral;
00052 import org.objectweb.jonas_ejb.deployment.ejbql.ASTFunctionsReturningNumerics;
00053 import org.objectweb.jonas_ejb.deployment.ejbql.ASTFunctionsReturningStrings;
00054 import org.objectweb.jonas_ejb.deployment.ejbql.ASTIdentificationVariable;
00055 import org.objectweb.jonas_ejb.deployment.ejbql.ASTInExpression;
00056 import org.objectweb.jonas_ejb.deployment.ejbql.ASTInputParameter;
00057 import org.objectweb.jonas_ejb.deployment.ejbql.ASTIntegerLiteral;
00058 import org.objectweb.jonas_ejb.deployment.ejbql.ASTLikeExpression;
00059 import org.objectweb.jonas_ejb.deployment.ejbql.ASTLiteral;
00060 import org.objectweb.jonas_ejb.deployment.ejbql.ASTNullComparisonExpression;
00061 import org.objectweb.jonas_ejb.deployment.ejbql.ASTPath;
00062 import org.objectweb.jonas_ejb.deployment.ejbql.ASTSingleValuedCmrPathExpression;
00063 import org.objectweb.jonas_ejb.deployment.ejbql.ASTSingleValuedPathExpression;
00064 import org.objectweb.jonas_ejb.deployment.ejbql.ASTStringExpression;
00065 import org.objectweb.jonas_ejb.deployment.ejbql.ASTStringLiteral;
00066 import org.objectweb.jonas_ejb.deployment.ejbql.ASTWhereClause;
00067 import org.objectweb.jonas_ejb.deployment.ejbql.EJBQLConstants;
00068 import org.objectweb.jonas_ejb.deployment.ejbql.ParseException;
00069 import org.objectweb.jonas_ejb.deployment.ejbql.SimpleNode;
00070 import org.objectweb.jorm.api.PMapper;
00071 import org.objectweb.jorm.lib.JormPathHelper;
00072 import org.objectweb.jorm.naming.api.PName;
00073 import org.objectweb.jorm.type.api.PType;
00074 import org.objectweb.medor.api.Field;
00075 import org.objectweb.medor.expression.api.MalformedExpressionException;
00076 import org.objectweb.medor.expression.api.Expression;
00077 import org.objectweb.medor.filter.api.FieldOperand;
00078 import org.objectweb.medor.expression.api.Operand;
00079 import org.objectweb.medor.filter.jorm.lib.IsNullPName;
00080 import org.objectweb.medor.expression.lib.Abs;
00081 import org.objectweb.medor.expression.lib.And;
00082 import org.objectweb.medor.filter.lib.BasicFieldOperand;
00083 import org.objectweb.medor.expression.lib.BasicOperand;
00084 import org.objectweb.medor.expression.lib.BasicParameterOperand;
00085 import org.objectweb.medor.filter.lib.CollectionOperand;
00086 import org.objectweb.medor.expression.lib.Concat;
00087 import org.objectweb.medor.expression.lib.DivideBy;
00088 import org.objectweb.medor.expression.lib.Equal;
00089 import org.objectweb.medor.expression.lib.FirstLocate;
00090 import org.objectweb.medor.expression.lib.Greater;
00091 import org.objectweb.medor.expression.lib.GreaterEqual;
00092 import org.objectweb.medor.filter.lib.InCollection;
00093 import org.objectweb.medor.expression.lib.IndexedLocate;
00094 import org.objectweb.medor.filter.lib.IsEmpty;
00095 import org.objectweb.medor.filter.lib.IsNull;
00096 import org.objectweb.medor.expression.lib.Length;
00097 import org.objectweb.medor.expression.lib.Like;
00098 import org.objectweb.medor.expression.lib.Lower;
00099 import org.objectweb.medor.expression.lib.LowerEqual;
00100 import org.objectweb.medor.filter.lib.MemberOf;
00101 import org.objectweb.medor.expression.lib.Minus;
00102 import org.objectweb.medor.expression.lib.Mod;
00103 import org.objectweb.medor.expression.lib.Mult;
00104 import org.objectweb.medor.expression.lib.Not;
00105 import org.objectweb.medor.expression.lib.NotEqual;
00106 import org.objectweb.medor.expression.lib.Or;
00107 import org.objectweb.medor.expression.lib.Plus;
00108 import org.objectweb.medor.expression.lib.Sqrt;
00109 import org.objectweb.medor.expression.lib.Substring;
00110 import org.objectweb.medor.expression.lib.UMinus;
00111 import org.objectweb.medor.query.api.PropagatedField;
00112 import org.objectweb.medor.query.jorm.lib.PNameField;
00113 import org.objectweb.medor.query.jorm.lib.QueryBuilder;
00114 import org.objectweb.medor.type.lib.PTypeSpaceMedor;
00115 import org.objectweb.medor.type.lib.QType;
00116
00139 public class EjbqlQueryFilterVisitor extends EjbqlAbstractVisitor {
00140
00141 Expression qf = null;
00142 PMapper mapper = null;
00143 Map fields = null;
00144 Class[] parameterTypes;
00145 QueryBuilder qb;
00146
00147 static final String OP_IGNORE = "ignore";
00148
00158 public EjbqlQueryFilterVisitor(PMapper _mapper,
00159 Map _fields,
00160 Class[] parameterTypes,
00161 ASTEJBQL ejbql,
00162 QueryBuilder qb) throws Exception {
00163 mapper = _mapper;
00164 fields = _fields;
00165 this.parameterTypes = parameterTypes;
00166 this.qb = qb;
00167 visit(ejbql);
00168 }
00169
00173 public Expression getQueryFilter() {
00174 return qf;
00175 }
00176
00181 public Object visit(ASTWhereClause node, Object data) {
00182 visit((SimpleNode) node, data);
00183 if (OP_IGNORE.equals(((Stack) data).peek())) {
00184 qf = null;
00185 } else {
00186 qf = (Expression) ((Stack) data).pop();
00187 }
00188 return null;
00189 }
00190
00197 public Object visit(ASTSingleValuedPathExpression node, Object data) {
00198 visit((SimpleNode) node, data);
00199 try {
00200 String path = (String) ((ASTPath) ((Stack) data).pop()).value;
00201 Field f = (Field) fields.get(path);
00202
00203
00204 ((Stack) data).push(new BasicFieldOperand(f));
00205 } catch (Exception e) {
00206 throw new VisitorException(e);
00207 }
00208 return null;
00209 }
00210
00217 public Object visit(ASTCmpPathExpression node, Object data) {
00218 visit((SimpleNode) node, data);
00219 try {
00220 String path = (String) ((ASTPath) ((Stack) data).pop()).value;
00221 Field f = (Field) fields.get(path);
00222
00223 ((Stack) data).push(new BasicFieldOperand(f));
00224 } catch (Exception e) {
00225 throw new VisitorException(e);
00226 }
00227 return null;
00228 }
00229
00236 public Object visit(ASTSingleValuedCmrPathExpression node, Object data) {
00237 visit((SimpleNode) node, data);
00238 try {
00239 String path = (String) ((ASTPath) ((Stack) data).pop()).value;
00240 Field f = (Field) fields.get(path);
00241
00242 ((Stack) data).push(new BasicFieldOperand(f));
00243 } catch (Exception e) {
00244 throw new VisitorException(e);
00245 }
00246 return null;
00247 }
00248
00255 public Object visit(ASTCollectionValuedPathExpression node, Object data) {
00256 visit((SimpleNode) node, data);
00257 try {
00258
00259 String path = (String) ((ASTPath) ((Stack) data).pop()).value;
00260 String[] parts = splitPath(path);
00261 String first = parts[0];
00262 String rest = mergePath(parts, 1, parts.length - 1);
00263 QueryBuilder subquery = new QueryBuilder(qb);
00264 subquery.define("", qb.navigate(first));
00265 Field f = subquery.project(subquery.navigate(rest));
00266 ((Stack) data).push(new BasicFieldOperand(f));
00267 } catch (Exception e) {
00268 throw new VisitorException(e);
00269 }
00270 return null;
00271 }
00272
00277 public Object visit(ASTConditionalExpression node, Object data) {
00278 visit((SimpleNode) node, data);
00279 Object ret = ((Stack) data).pop();
00280 for (int i = 1; i < node.jjtGetNumChildren(); i++) {
00281 if (OP_IGNORE.equals(ret)) {
00282 ret = ((Stack) data).pop();
00283 } else if (OP_IGNORE.equals(((Stack) data).peek())) {
00284 ((Stack) data).pop();
00285 } else {
00286 ret = new Or((Expression) ((Stack) data).pop(), (Expression) ret);
00287 }
00288 }
00289
00290 ((Stack) data).push(ret);
00291 return null;
00292 }
00293
00298 public Object visit(ASTConditionalTerm node, Object data) {
00299 visit((SimpleNode) node, data);
00300 Object ret = ((Stack) data).pop();
00301 for (int i = 1; i < node.jjtGetNumChildren(); i++) {
00302 if (OP_IGNORE.equals(ret)) {
00303 ret = ((Stack) data).pop();
00304 } else if (OP_IGNORE.equals(((Stack) data).peek())) {
00305 ((Stack) data).pop();
00306 } else {
00307 ret = new And((Expression) ((Stack) data).pop(), (Expression) ret);
00308 }
00309 }
00310
00311 ((Stack) data).push(ret);
00312 return null;
00313 }
00314
00319 public Object visit(ASTConditionalFactor node, Object data) {
00320 visit((SimpleNode) node, data);
00321 if (node.not) {
00322 if (!OP_IGNORE.equals(((Stack) data).peek())) {
00323 Expression ret = (Expression) ((Stack) data).pop();
00324
00325 ((Stack) data).push(new Not(ret));
00326 }
00327 }
00328 return null;
00329 }
00330
00335 public Object visit(ASTBetweenExpression node, Object data) {
00336 visit((SimpleNode) node, data);
00337 Expression[] terms = new Expression[3];
00338 terms[2] = (Expression) ((Stack) data).pop();
00339 terms[1] = (Expression) ((Stack) data).pop();
00340 terms[0] = (Expression) ((Stack) data).pop();
00341 if (node.not) {
00342 ((Stack) data).push(new Or(new Lower(terms[0], terms[1]), new Greater(terms[0], terms[2])));
00343 } else {
00344 ((Stack) data).push(new And(new GreaterEqual(terms[0], terms[1]), new LowerEqual(terms[0], terms[2])));
00345 }
00346 return null;
00347 }
00348
00354 public Object visit(ASTInExpression node, Object data) {
00355 visit((SimpleNode) node, data);
00356 Stack s = (Stack) data;
00357 ArrayList c = new ArrayList();
00358 for (int i = 1; i <= node.eltnum; i++) {
00359 c.add(s.pop());
00360 }
00361 CollectionOperand co = new CollectionOperand(c);
00362 FieldOperand f = (FieldOperand) s.pop();
00363 if (node.not) {
00364 s.push(new Not(new InCollection(f, co, f.getField().getType())));
00365 } else {
00366 s.push(new InCollection(f, co, f.getField().getType()));
00367 }
00368 return null;
00369 }
00370
00376 public Object visit(ASTLikeExpression node, Object data) {
00377 visit((SimpleNode) node, data);
00378 Stack s = (Stack) data;
00379 Expression e1 = (Expression) s.pop();
00380 Expression e2 = (Expression) s.pop();
00381 Expression e3 = null;
00382 if (node.third) {
00383
00384 e3 = (Expression) s.pop();
00385 }
00386 if (e3 == null) {
00387 s.push(new Like(e2, e1, node.not));
00388 } else {
00389 s.push(new Like(e3, e2, e1, node.not));
00390 }
00391 return null;
00392 }
00393
00398 public Object visit(ASTNullComparisonExpression node, Object data) {
00399 visit((SimpleNode) node, data);
00400 Stack s = (Stack) data;
00401 Expression e1 = (Expression) s.pop();
00402 if ((e1 instanceof BasicParameterOperand)
00403 && (e1.getType().getTypeCode() == QType.TYPECODE_PNAME)) {
00404
00405 if (node.not) {
00406 s.push(new Not(new IsNullPName(((BasicParameterOperand)e1).getName())));
00407 } else {
00408 s.push(new IsNullPName(((BasicParameterOperand)e1).getName()));
00409 }
00410 } else if (e1.getType().getTypeCode() == PType.TYPECODE_REFERENCE) {
00411
00412
00413
00414 Field f = ((FieldOperand) e1).getField();
00415 PNameField pnf = null;
00416 if (f instanceof PNameField) {
00417 pnf = (PNameField) f;
00418 } else if (f instanceof PropagatedField) {
00419 pnf = (PNameField)((PropagatedField) f).getOriginFields()[0];
00420 } else {
00421
00422 throw new Error("Operand of IS NULL not valid !?");
00423 }
00424 Operand op2;
00425 if (mapper == null) {
00426
00427 op2 = new BasicOperand("pnamenull");
00428 } else {
00429
00430 PName pnamenull = JormPathHelper.getPNameCoder(pnf.getPNamingContextParameter(),
00431 mapper).getNull();
00432 op2 = new BasicOperand(pnamenull, PTypeSpaceMedor.PNAME);
00433 }
00434 if (node.not) {
00435 s.push(new Not(new Equal(e1, op2)));
00436 } else {
00437 s.push(new Equal(e1, op2));
00438 }
00439 } else {
00440
00441 if (node.not) {
00442 s.push(new Not(new IsNull(e1)));
00443 } else {
00444 s.push(new IsNull(e1));
00445 }
00446 }
00447 return null;
00448
00449 }
00450
00457 public Object visit(ASTEmptyCollectionComparisonExpression node, Object data) {
00458 visit((SimpleNode) node, data);
00459 Stack s = (Stack) data;
00460 Expression e = (Expression) s.pop();
00461 Expression res = new IsEmpty(e);
00462 if (node.not) {
00463 res = new Not(res);
00464 }
00465 s.push(res);
00466 return null;
00467 }
00468
00474 public Object visit(ASTCollectionMemberExpression node, Object data) {
00475 visit((SimpleNode) node, data);
00476 Stack s = (Stack) data;
00477 Expression e2 = (Expression) s.pop();
00478 Expression e1 = (Expression) s.pop();
00479 ArrayList le2 = new ArrayList(); le2.add(e2);
00480 ArrayList le1 = new ArrayList(); le1.add(e1);
00481 Expression res = null;
00482 try {
00483 res = new MemberOf(le1, le2);
00484 } catch (MalformedExpressionException e) {
00485 throw new Error("Operand expression of MEMBER OF malformed: "
00486 + e + e.getNestedException());
00487 }
00488 if (node.not) {
00489 s.push(new Not(res));
00490 } else {
00491 s.push(res);
00492 }
00493 return null;
00494 }
00495
00496
00505 public Object visit(ASTComparisonExpression node, Object data) {
00506 visit((SimpleNode) node, data);
00507 Expression[] terms = new Expression[2];
00508 terms[1] = (Expression) ((Stack) data).pop();
00509 terms[0] = (Expression) ((Stack) data).pop();
00510 int op = ((Integer) node.ops.get(0)).intValue();
00511 switch (op) {
00512 case EJBQLConstants.EQ:
00513 ((Stack) data).push(new Equal(terms[0], terms[1]));
00514 break;
00515 case EJBQLConstants.NE:
00516 ((Stack) data).push(new NotEqual(terms[0], terms[1]));
00517 break;
00518 case EJBQLConstants.GT:
00519 ((Stack) data).push(new Greater(terms[0], terms[1]));
00520 break;
00521 case EJBQLConstants.GE:
00522 ((Stack) data).push(new GreaterEqual(terms[0], terms[1]));
00523 break;
00524 case EJBQLConstants.LT:
00525 ((Stack) data).push(new Lower(terms[0], terms[1]));
00526 break;
00527 case EJBQLConstants.LE:
00528 ((Stack) data).push(new LowerEqual(terms[0], terms[1]));
00529 break;
00530 }
00531 return null;
00532 }
00533
00538 public Object visit(ASTArithmeticExpression node, Object data) {
00539 visit((SimpleNode) node, data);
00540 Expression ret = (Expression) ((Stack) data).pop();
00541 for (int i = 0; i < node.jjtGetNumChildren() - 1; i++) {
00542 switch (((Integer) node.ops.get(node.jjtGetNumChildren() - 2 - i)).intValue()) {
00543 case EJBQLConstants.PLUS:
00544 ret = new Plus((Expression) ((Stack) data).pop(), ret);
00545 break;
00546 case EJBQLConstants.MINUS:
00547 ret = new Minus((Expression) ((Stack) data).pop(), ret);
00548 break;
00549 }
00550 }
00551
00552 ((Stack) data).push(ret);
00553 return null;
00554 }
00555
00560 public Object visit(ASTArithmeticTerm node, Object data) {
00561 visit((SimpleNode) node, data);
00562 Expression ret = (Expression) ((Stack) data).pop();
00563 for (int i = 0; i < node.jjtGetNumChildren() - 1; i++) {
00564 switch (((Integer) node.ops.get(node.jjtGetNumChildren() - 2 - i)).intValue()) {
00565 case EJBQLConstants.MULT:
00566 ret = new Mult((Expression) ((Stack) data).pop(), ret);
00567 break;
00568 case EJBQLConstants.DIV:
00569 ret = new DivideBy((Expression) ((Stack) data).pop(), ret);
00570 break;
00571 }
00572 }
00573
00574 ((Stack) data).push(ret);
00575 return null;
00576 }
00577
00582 public Object visit(ASTArithmeticFactor node, Object data) {
00583 visit((SimpleNode) node, data);
00584 Expression ret = (Expression) ((Stack) data).pop();
00585 if (node.ops.size() > 0) {
00586 if (((Integer) node.ops.get(0)).intValue() == EJBQLConstants.MINUS) {
00587 ret = new UMinus((Expression) ret);
00588 }
00589 }
00590
00591 ((Stack) data).push(ret);
00592 return null;
00593 }
00594
00595
00600 public Object visit(ASTStringExpression node, Object data) {
00601 visit((SimpleNode) node, data);
00602
00603 return null;
00604 }
00605
00610 public Object visit(ASTDatetimeExpression node, Object data) {
00611 visit((SimpleNode) node, data);
00612
00613 return null;
00614 }
00615
00620 public Object visit(ASTBooleanExpression node, Object data) {
00621 visit((SimpleNode) node, data);
00622
00623 return null;
00624 }
00625
00630 public Object visit(ASTEntityBeanExpression node, Object data) {
00631 visit((SimpleNode) node, data);
00632
00633 return null;
00634 }
00635
00642 public Object visit(ASTFunctionsReturningStrings node, Object data) {
00643 visit((SimpleNode) node, data);
00644 Stack s = (Stack) data;
00645 int op = ((Integer) node.ops.get(0)).intValue();
00646 Expression ret = null;
00647 Expression e1, e2;
00648 switch (op) {
00649 case EJBQLConstants.CONCAT:
00650
00651 e2 = (Expression) s.pop();
00652 e1 = (Expression) s.pop();
00653 ret = new Concat(e1, e2);
00654 break;
00655 case EJBQLConstants.SUBSTRING:
00656
00657 Expression e3 = (Expression) s.pop();
00658 e2 = (Expression) s.pop();
00659 e1 = (Expression) s.pop();
00660 ret = new Substring(e1, e2, e3);
00661 break;
00662 }
00663
00664 s.push(ret);
00665 return null;
00666 }
00667
00668
00679 public Object visit(ASTFunctionsReturningNumerics node, Object data) {
00680 visit((SimpleNode) node, data);
00681 Stack s = (Stack) data;
00682 int op = ((Integer) node.ops.get(0)).intValue();
00683 Expression e1, e2;
00684 Expression ret = null;
00685 switch (op) {
00686 case EJBQLConstants.LENGTH:
00687 e1 = (Expression) s.pop();
00688 ret = new Length(e1);
00689 break;
00690 case EJBQLConstants.LOCATE:
00691
00692 Expression e3 = null;
00693 if (node.third) {
00694
00695 e3 = (Expression) s.pop();
00696 }
00697 e2 = (Expression) s.pop();
00698 e1 = (Expression) s.pop();
00699
00700 if (node.third) {
00701 ret = new IndexedLocate(e2, e1, e3);
00702 } else {
00703 ret = new FirstLocate(e1, e2);
00704 }
00705 break;
00706 case EJBQLConstants.ABS:
00707 e1 = (Expression) s.pop();
00708 ret = new Abs(e1);
00709 break;
00710 case EJBQLConstants.SQRT:
00711 e1 = (Expression) s.pop();
00712 ret = new Sqrt(e1);
00713 break;
00714 case EJBQLConstants.MOD:
00715 e2 = (Expression) s.pop();
00716 e1 = (Expression) s.pop();
00717 ret = new Mod(e1, e2);
00718 break;
00719 }
00720
00721 s.push(ret);
00722 return null;
00723 }
00724
00729 public Object visit(ASTIdentificationVariable node, Object data) {
00730 String fieldname = (String) node.value + "." + Field.PNAMENAME;
00731 Field f = (Field) fields.get(fieldname);
00732 ((Stack) data).push(new BasicFieldOperand(f));
00733 return null;
00734 }
00735
00740 public Object visit(ASTLiteral node, Object data) {
00741 visit((SimpleNode) node, data);
00742 return null;
00743 }
00744
00749 public Object visit(ASTStringLiteral node, Object data) {
00750 ((Stack) data).push(new BasicOperand((String) node.value));
00751 return null;
00752 }
00753
00758 public Object visit(ASTArithmeticLiteral node, Object data) {
00759 visit((SimpleNode) node, data);
00760 return null;
00761 }
00762
00767 public Object visit(ASTIntegerLiteral node, Object data) {
00768 ((Stack) data).push(new BasicOperand(((Long) node.value).longValue()));
00769 return null;
00770 }
00771
00776 public Object visit(ASTFloatingPointLiteral node, Object data) {
00777 ((Stack) data).push(new BasicOperand(((Double) node.value).doubleValue()));
00778 return null;
00779 }
00780
00785 public Object visit(ASTBooleanLiteral node, Object data) {
00786 ((Stack) data).push(new BasicOperand(((Boolean) node.value).booleanValue()));
00787 return null;
00788 }
00789
00794 public Object visit(ASTInputParameter node, Object data) {
00795 try {
00796 int pIndex = ((Integer) node.value).intValue() - 1;
00797 if (pIndex >= parameterTypes.length) {
00798 throw new ParseException("Parameter ?" + (pIndex + 1)
00799 + " is out of range (max = "
00800 + parameterTypes.length + ")");
00801 }
00802 if (EJBObject.class.isAssignableFrom(parameterTypes[pIndex])) {
00803
00804
00805 throw new Error("EJBObject params not implemented");
00806 }
00807 Operand op = new BasicParameterOperand(JormType.getPType(parameterTypes[pIndex], false),
00808 "?" + node.value);
00809 ((Stack) data).push(op);
00810 return null;
00811 } catch (ParseException e) {
00812 throw new VisitorException(e);
00813 }
00814 }
00815
00819 public Object visit(ASTPath node, Object data) {
00820 ((Stack) data).push(node);
00821 return null;
00822 }
00823 }