1// [The "BSD licence"] 2// Copyright (c) 2006-2007 Kay Roepke 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 "Token.h" 28#import "CommonTokenStream.h" 29 30 31@implementation CommonTokenStream 32 33@synthesize channelOverride; 34@synthesize channel; 35 36#pragma mark Initialization 37 38+ (CommonTokenStream *)newCommonTokenStream 39{ 40 return [[CommonTokenStream alloc] init]; 41} 42 43+ (CommonTokenStream *)newCommonTokenStreamWithTokenSource:(id<TokenSource>)theTokenSource 44{ 45 return [[CommonTokenStream alloc] initWithTokenSource:(id<TokenSource>)theTokenSource]; 46} 47 48+ (CommonTokenStream *)newCommonTokenStreamWithTokenSource:(id<TokenSource>)theTokenSource Channel:(NSUInteger)aChannel 49{ 50 return [[CommonTokenStream alloc] initWithTokenSource:(id<TokenSource>)theTokenSource Channel:aChannel]; 51} 52 53- (id) init 54{ 55 if ((self = [super init]) != nil) { 56 channelOverride = [[AMutableDictionary dictionaryWithCapacity:100] retain]; 57 channel = TokenChannelDefault; 58 } 59 return self; 60} 61 62- (id) initWithTokenSource:(id<TokenSource>)theTokenSource 63{ 64 if ((self = [super initWithTokenSource:theTokenSource]) != nil) { 65 channelOverride = [[AMutableDictionary dictionaryWithCapacity:100] retain]; 66 channel = TokenChannelDefault; 67 } 68 return self; 69} 70 71- (id) initWithTokenSource:(id<TokenSource>)theTokenSource Channel:(NSUInteger)aChannel 72{ 73 if ((self = [super initWithTokenSource:theTokenSource]) != nil) { 74 channelOverride = [[AMutableDictionary dictionaryWithCapacity:100] retain]; 75 channel = aChannel; 76 } 77 return self; 78} 79 80- (void) dealloc 81{ 82#ifdef DEBUG_DEALLOC 83 NSLog( @"called dealloc in CommonTokenStream" ); 84#endif 85 if ( channelOverride ) [channelOverride release]; 86 if ( tokens ) [tokens release]; 87 [self setTokenSource:nil]; 88 [super dealloc]; 89} 90 91/** Always leave index on an on-channel token. */ 92- (void) consume 93{ 94 if (index == -1) [self setup]; 95 index++; 96 [self sync:index]; 97 while ( ((CommonToken *)[tokens objectAtIndex:index]).channel != channel ) { 98 index++; 99 [self sync:index]; 100 } 101} 102 103#pragma mark Lookahead 104 105- (id<Token>) LB:(NSInteger)k 106{ 107 if ( k == 0 || (index-k) < 0 ) { 108 return nil; 109 } 110 int i = index; 111 int n = 1; 112 // find k good tokens looking backwards 113 while ( n <= k ) { 114 i = [self skipOffTokenChannelsReverse:i-1]; 115 n++; 116 } 117 if ( i < 0 ) { 118 return nil; 119 } 120 return [tokens objectAtIndex:i]; 121} 122 123- (id<Token>) LT:(NSInteger)k 124{ 125 if ( index == -1 ) [self setup]; 126 if ( k == 0 ) return nil; 127 if ( k < 0 ) return [self LB:-k]; 128 int i = index; 129 int n = 1; 130 while ( n < k ) { 131 i = [self skipOffTokenChannels:i+1]; 132 n++; 133 } 134// if ( i >= (NSInteger)[tokens count] ) { 135// return [CommonToken eofToken]; 136// } 137 if ( i > range ) range = i; 138 return [tokens objectAtIndex:i]; 139} 140 141#pragma mark Channels & Skipping 142 143- (NSInteger) skipOffTokenChannels:(NSInteger) idx 144{ 145 [self sync:idx]; 146 while ( ((CommonToken *)[tokens objectAtIndex:idx]).channel != channel ) { 147 idx++; 148 [self sync:idx]; 149 } 150 return idx; 151} 152 153- (NSInteger) skipOffTokenChannelsReverse:(NSInteger) i 154{ 155 while ( i >= 0 && ((CommonToken *)[tokens objectAtIndex:i]).channel != channel ) { 156 i--; 157 } 158 return i; 159} 160 161- (void) reset 162{ 163 [super reset]; 164 index = [self skipOffTokenChannels:0]; 165} 166 167- (void) setup 168{ 169 index = 0; 170 [self sync:0]; 171 int i = 0; 172 while ( ((CommonToken *)[tokens objectAtIndex:i]).channel != channel ) { 173 i++; 174 [self sync:i]; 175 } 176 // leave index pointing at first token on channel 177 index = i; 178} 179 180- (NSInteger) getNumberOfOnChannelTokens 181{ 182 NSInteger n = 0; 183 [self fill]; 184 for( int i = 0; i < [tokens count]; i++ ) { 185 CommonToken *t = [tokens objectAtIndex:i]; 186 if ( t.channel == channel ) 187 n++; 188 if ( t.type == TokenTypeEOF ) 189 break; 190 } 191 return n; 192} 193 194/** Reset this token stream by setting its token source. */ 195- (void) setTokenSource:(id<TokenSource>)aTokenSource 196{ 197 [super setTokenSource:aTokenSource]; 198 channel = TokenChannelDefault; 199} 200 201- (id) copyWithZone:(NSZone *)aZone 202{ 203 CommonTokenStream *copy; 204 205 // copy = [[[self class] allocWithZone:aZone] init]; 206 copy = [super copyWithZone:aZone]; // allocation occurs in BaseTree 207 if ( self.channelOverride ) 208 copy.channelOverride = [channelOverride copyWithZone:aZone]; 209 copy.channel = channel; 210 return copy; 211} 212 213- (NSUInteger)channel 214{ 215 return channel; 216} 217 218- (void)setChannel:(NSUInteger)aChannel 219{ 220 channel = aChannel; 221} 222 223- (AMutableDictionary *)channelOverride 224{ 225 return channelOverride; 226} 227 228- (void)setChannelOverride:(AMutableDictionary *)anOverride 229{ 230 channelOverride = anOverride; 231} 232 233#ifdef DONTUSENOMO 234#pragma mark Token access 235 236- (NSArray *) tokensInRange:(NSRange)aRange 237{ 238 return [tokens subarrayWithRange:aRange]; 239} 240 241#pragma mark Accessors 242 243- (id<TokenSource>) getTokenSource 244{ 245 return tokenSource; 246} 247 248- (NSArray *) tokensInRange:(NSRange)aRange inBitSet:(ANTLRBitSet *)aBitSet 249{ 250 unsigned int startIndex = aRange.location; 251 unsigned int stopIndex = aRange.location+aRange.length; 252 if ( index == -1 ) { 253 [self setup]; 254 } 255 if (stopIndex >= [tokens count]) { 256 stopIndex = [tokens count] - 1; 257 } 258 AMutableArray *filteredTokens = [AMutableArray arrayWithCapacity:100]; 259 unsigned int i=0; 260 for (i = startIndex; i<=stopIndex; i++) { 261 id<Token> token = [tokens objectAtIndex:i]; 262 if (aBitSet == nil || [aBitSet member:token.type]) { 263 [filteredTokens addObject:token]; 264 } 265 } 266 if ([filteredTokens count]) { 267 return filteredTokens; 268 } else { 269 [filteredTokens release]; 270 return nil; 271 } 272} 273 274- (NSArray *) tokensInRange:(NSRange)aRange withTypes:(NSArray *)tokenTypes 275{ 276 ANTLRBitSet *bits = [[ANTLRBitSet alloc] initWithArrayOfBits:tokenTypes]; 277 NSArray *returnTokens = [[self tokensInRange:aRange inBitSet:bits] retain]; 278 [bits release]; 279 return returnTokens; 280} 281 282- (NSArray *) tokensInRange:(NSRange)aRange withType:(NSInteger)tokenType 283{ 284 ANTLRBitSet *bits = [[ANTLRBitSet alloc] init]; 285 [bits add:tokenType]; 286 NSArray *returnTokens = [[self tokensInRange:aRange inBitSet:bits] retain]; 287 [bits release]; 288 return returnTokens; 289} 290 291- (id<Token>) getToken:(NSInteger)i 292{ 293 return [tokens objectAtIndex:i]; 294} 295 296- (NSInteger) size 297{ 298 return [tokens count]; 299} 300 301- (void) rewind 302{ 303 [self seek:lastMarker]; 304} 305 306- (void) rewind:(NSInteger)marker 307{ 308 [self seek:marker]; 309} 310 311- (void) seek:(NSInteger)anIndex 312{ 313 index = anIndex; 314} 315#pragma mark toString routines 316 317- (NSString *) toString 318{ 319 if ( index == -1 ) { 320 [self setup]; 321 } 322 return [self toStringFromStart:0 ToEnd:[tokens count]]; 323} 324 325- (NSString *) toStringFromStart:(NSInteger)startIdx ToEnd:(NSInteger) stopIdx 326{ 327 NSMutableString *stringBuffer; 328 id<Token> t; 329 330 if ( startIdx < 0 || stopIdx < 0 ) { 331 return nil; 332 } 333 if ( index == -1 ) { 334 [self setup]; 335 } 336 if ( stopIdx >= [tokens count] ) { 337 stopIdx = [tokens count]-1; 338 } 339 stringBuffer = [NSMutableString stringWithCapacity:30]; 340 for (int i = startIdx; i <= stopIdx; i++) { 341 t = (id<Token>)[tokens objectAtIndex:i]; 342 [stringBuffer appendString:[t text]]; 343 } 344 return stringBuffer; 345} 346 347- (NSString *) toStringFromToken:(id<Token>)startToken ToToken:(id<Token>)stopToken 348{ 349 if (startToken && stopToken) { 350 int startIdx = [startToken getTokenIndex]; 351 int stopIdx = [stopToken getTokenIndex]; 352 return [self toStringFromStart:startIdx ToEnd:stopIdx]; 353 } 354 return nil; 355} 356#endif 357 358@end 359