1 // [The "BSD licence"] 2 // Copyright (c) 2010 Alan Condit 3 // All rights reserved. 4 // 5 // Redistribution and use in source and binary forms, with or without 6 // modification, are permitted provided that the following conditions 7 // are met: 8 // 1. Redistributions of source code must retain the above copyright 9 // notice, this list of conditions and the following disclaimer. 10 // 2. Redistributions in binary form must reproduce the above copyright 11 // notice, this list of conditions and the following disclaimer in the 12 // documentation and/or other materials provided with the distribution. 13 // 3. The name of the author may not be used to endorse or promote products 14 // derived from this software without specific prior written permission. 15 // 16 // THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 17 // IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 18 // OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 19 // IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 20 // INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 21 // NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 25 // THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 27 #import <Cocoa/Cocoa.h> 28 #import "ANTLRTreeAdaptor.h" 29 #import "ANTLRCommonErrorNode.h" 30 #import "ANTLRUniqueIDMap.h" 31 32 @interface ANTLRBaseTreeAdaptor : NSObject <ANTLRTreeAdaptor, NSCopying> { 33 ANTLRUniqueIDMap *treeToUniqueIDMap; 34 NSInteger uniqueNodeID; 35 } 36 37 @property (retain, getter=getTreeToUniqueIDMap, setter=setTreeToUniqueIDMap:) ANTLRUniqueIDMap *treeToUniqueIDMap; 38 @property (getter=getUniqueNodeID, setter=setUniqueNodeID:) NSInteger uniqueNodeID; 39 40 + (id<ANTLRTreeAdaptor>) newEmptyTree; 41 42 - (id) init; 43 44 - (id) copyWithZone:(NSZone *)aZone; 45 46 - (id) emptyNode; 47 48 - (ANTLRUniqueIDMap *)getTreeToUniqueIDMap; 49 - (void) setTreeToUniqueIDMap:(ANTLRUniqueIDMap *)aMapNode; 50 51 - (NSInteger)getUniqueID; 52 - (void) setUniqueNodeID:(NSInteger)aUniqueNodeID; 53 54 /** create tree node that holds the start and stop tokens associated 55 * with an error. 56 * 57 * If you specify your own kind of tree nodes, you will likely have to 58 * override this method. CommonTree returns Token.INVALID_TOKEN_TYPE 59 * if no token payload but you might have to set token type for diff 60 * node type. 61 * 62 * You don't have to subclass CommonErrorNode; you will likely need to 63 * subclass your own tree node class to avoid class cast exception. 64 */ 65 - (id) errorNode:(id<ANTLRTokenStream>)anInput 66 From:(id<ANTLRToken>)startToken 67 To:(id<ANTLRToken>)stopToken 68 Exception:(NSException *) e; 69 70 - (BOOL) isNil:(id<ANTLRTree>) aTree; 71 72 - (id<ANTLRTree>)dupTree:(id<ANTLRTree>)aTree; 73 /** This is generic in the sense that it will work with any kind of 74 * tree (not just Tree interface). It invokes the adaptor routines 75 * not the tree node routines to do the construction. 76 */ 77 - (id<ANTLRTree>)dupTree:(id<ANTLRTree>)aTree Parent:(id<ANTLRTree>)parent; 78 - (id<ANTLRTree>)dupNode:(id<ANTLRTree>)aNode; 79 /** Add a child to the tree t. If child is a flat tree (a list), make all 80 * in list children of t. Warning: if t has no children, but child does 81 * and child isNil then you can decide it is ok to move children to t via 82 * t.children = child.children; i.e., without copying the array. Just 83 * make sure that this is consistent with have the user will build 84 * ASTs. 85 */ 86 - (void) addChild:(id<ANTLRTree>)aChild toTree:(id<ANTLRTree>)aTree; 87 88 /** If oldRoot is a nil root, just copy or move the children to newRoot. 89 * If not a nil root, make oldRoot a child of newRoot. 90 * 91 * old=^(nil a b c), new=r yields ^(r a b c) 92 * old=^(a b c), new=r yields ^(r ^(a b c)) 93 * 94 * If newRoot is a nil-rooted single child tree, use the single 95 * child as the new root node. 96 * 97 * old=^(nil a b c), new=^(nil r) yields ^(r a b c) 98 * old=^(a b c), new=^(nil r) yields ^(r ^(a b c)) 99 * 100 * If oldRoot was null, it's ok, just return newRoot (even if isNil). 101 * 102 * old=null, new=r yields r 103 * old=null, new=^(nil r) yields ^(nil r) 104 * 105 * Return newRoot. Throw an exception if newRoot is not a 106 * simple node or nil root with a single child node--it must be a root 107 * node. If newRoot is ^(nil x) return x as newRoot. 108 * 109 * Be advised that it's ok for newRoot to point at oldRoot's 110 * children; i.e., you don't have to copy the list. We are 111 * constructing these nodes so we should have this control for 112 * efficiency. 113 */ 114 - (id<ANTLRTree>)becomeRoot:(id<ANTLRTree>)aNewRoot old:(id<ANTLRTree>)oldRoot; 115 116 /** Transform ^(nil x) to x and nil to null */ 117 - (id<ANTLRTree>)rulePostProcessing:(id<ANTLRTree>)aRoot; 118 119 - (id<ANTLRTree>)becomeRootfromToken:(id<ANTLRToken>)aNewRoot old:(id<ANTLRTree>)oldRoot; 120 121 - (id<ANTLRTree>)createTree:(NSInteger)aTType With:(id<ANTLRToken>)aFromToken; 122 123 - (id<ANTLRTree>)createTree:(NSInteger)aTType FromToken:(id<ANTLRToken>)aFromToken Text:(NSString *)theText; 124 125 - (id<ANTLRTree>)createTree:(NSInteger)aTType Text:(NSString *)theText; 126 127 - (NSInteger) getType:(id<ANTLRTree>)aTree; 128 129 - (void) setType:(id<ANTLRTree>)aTree Type:(NSInteger)type; 130 131 - (NSString *)getText:(id<ANTLRTree>)aTree; 132 133 - (void) setText:(id<ANTLRTree>)aTree Text:(NSString *)theText; 134 135 - (id<ANTLRTree>) getChild:(id<ANTLRTree>)aTree At:(NSInteger)i; 136 137 - (void) setChild:(id<ANTLRTree>)aTree At:(NSInteger)index Child:(id<ANTLRTree>)aChild; 138 139 - (id<ANTLRTree>) deleteChild:(id<ANTLRTree>)aTree Index:(NSInteger)index; 140 141 - (NSInteger) getChildCount:(id<ANTLRTree>)aTree; 142 143 - (NSInteger) getUniqueID:(id<ANTLRTree>)node; 144 145 /** Tell me how to create a token for use with imaginary token nodes. 146 * For example, there is probably no input symbol associated with imaginary 147 * token DECL, but you need to create it as a payload or whatever for 148 * the DECL node as in ^(DECL type ID). 149 * 150 * This is a variant of createToken where the new token is derived from 151 * an actual real input token. Typically this is for converting '{' 152 * tokens to BLOCK etc... You'll see 153 * 154 * r : lc='{' ID+ '}' -> ^(BLOCK[$lc] ID+) ; 155 * 156 * If you care what the token payload objects' type is, you should 157 * override this method and any other createToken variant. 158 */ 159 - (id<ANTLRToken>)createToken:(NSInteger)aTType Text:(NSString *)theText; 160 161 - (id<ANTLRToken>)createToken:(id<ANTLRToken>)aFromToken; 162 163 @end 164