001: /* Generated By:JJTree: Do not edit this line. JJTAnnotationParserState.java */
002: package org.codehaus.aspectwerkz.annotation.expression.ast;
003:
004: class JJTAnnotationParserState {
005: private java.util.Stack nodes;
006:
007: private java.util.Stack marks;
008:
009: private int sp; // number of nodes on stack
010:
011: private int mk; // current mark
012:
013: private boolean node_created;
014:
015: JJTAnnotationParserState() {
016: nodes = new java.util.Stack();
017: marks = new java.util.Stack();
018: sp = 0;
019: mk = 0;
020: }
021:
022: /*
023: * Determines whether the current node was actually closed and pushed. This should only be called in the final user
024: * action of a node scope.
025: */
026: boolean nodeCreated() {
027: return node_created;
028: }
029:
030: /*
031: * Call this to reinitialize the node stack. It is called automatically by the parser's ReInit() method.
032: */
033: void reset() {
034: nodes.removeAllElements();
035: marks.removeAllElements();
036: sp = 0;
037: mk = 0;
038: }
039:
040: /*
041: * Returns the root node of the AST. It only makes sense to call this after a successful parse.
042: */
043: Node rootNode() {
044: return (Node) nodes.elementAt(0);
045: }
046:
047: /* Pushes a node on to the stack. */
048: void pushNode(Node n) {
049: nodes.push(n);
050: ++sp;
051: }
052:
053: /*
054: * Returns the node on the top of the stack, and remove it from the stack.
055: */
056: Node popNode() {
057: if (--sp < mk) {
058: mk = ((Integer) marks.pop()).intValue();
059: }
060: return (Node) nodes.pop();
061: }
062:
063: /* Returns the node currently on the top of the stack. */
064: Node peekNode() {
065: return (Node) nodes.peek();
066: }
067:
068: /*
069: * Returns the number of children on the stack in the current node scope.
070: */
071: int nodeArity() {
072: return sp - mk;
073: }
074:
075: void clearNodeScope(Node n) {
076: while (sp > mk) {
077: popNode();
078: }
079: mk = ((Integer) marks.pop()).intValue();
080: }
081:
082: void openNodeScope(Node n) {
083: marks.push(new Integer(mk));
084: mk = sp;
085: n.jjtOpen();
086: }
087:
088: /*
089: * A definite node is constructed from a specified number of children. That number of nodes are popped from the
090: * stack and made the children of the definite node. Then the definite node is pushed on to the stack.
091: */
092: void closeNodeScope(Node n, int num) {
093: mk = ((Integer) marks.pop()).intValue();
094: while (num-- > 0) {
095: Node c = popNode();
096: c.jjtSetParent(n);
097: n.jjtAddChild(c, num);
098: }
099: n.jjtClose();
100: pushNode(n);
101: node_created = true;
102: }
103:
104: /*
105: * A conditional node is constructed if its condition is true. All the nodes that have been pushed since the node
106: * was opened are made children of the the conditional node, which is then pushed on to the stack. If the condition
107: * is false the node is not constructed and they are left on the stack.
108: */
109: void closeNodeScope(Node n, boolean condition) {
110: if (condition) {
111: int a = nodeArity();
112: mk = ((Integer) marks.pop()).intValue();
113: while (a-- > 0) {
114: Node c = popNode();
115: c.jjtSetParent(n);
116: n.jjtAddChild(c, a);
117: }
118: n.jjtClose();
119: pushNode(n);
120: node_created = true;
121: } else {
122: mk = ((Integer) marks.pop()).intValue();
123: node_created = false;
124: }
125: }
126: }
|