1//
2//  ANTLRHashRule.m
3//  ANTLR
4//
5// Copyright (c) 2010 Alan Condit
6// All rights reserved.
7//
8// Redistribution and use in source and binary forms, with or without
9// modification, are permitted provided that the following conditions
10// are met:
11// 1. Redistributions of source code must retain the above copyright
12//    notice, this list of conditions and the following disclaimer.
13// 2. Redistributions in binary form must reproduce the above copyright
14//    notice, this list of conditions and the following disclaimer in the
15//    documentation and/or other materials provided with the distribution.
16// 3. The name of the author may not be used to endorse or promote products
17//    derived from this software without specific prior written permission.
18//
19// THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
20// IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
21// OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
22// IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
23// INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24// NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28// THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29
30#define SUCCESS (0)
31#define FAILURE (-1)
32#define ANTLR_MEMO_RULE_UNKNOWN -1
33
34#import "ANTLRHashRule.h"
35
36/*
37 * Start of ANTLRHashRule
38 */
39@implementation ANTLRHashRule
40
41@synthesize LastHash;
42
43+(id)newANTLRHashRule
44{
45    return [[ANTLRHashRule alloc] init];
46}
47
48+(id)newANTLRHashRuleWithLen:(NSInteger)aBuffSize
49{
50    return [[ANTLRHashRule alloc] initWithLen:aBuffSize];
51}
52
53-(id)init
54{
55    self = [super initWithLen:HASHSIZE];
56    if ( self != nil ) {
57    }
58    return( self );
59}
60
61-(id)initWithLen:(NSInteger)aBuffSize
62{
63    self = [super initWithLen:aBuffSize];
64    if ( self != nil ) {
65        mode = 0;
66    }
67    return( self );
68}
69
70-(void)dealloc
71{
72#ifdef DEBUG_DEALLOC
73    NSLog( @"called dealloc in ANTLRHashRule" );
74#endif
75    ANTLRRuleMemo *tmp, *rtmp;
76    int Index;
77    
78    if ( self.fNext != nil ) {
79        for( Index = 0; Index < BuffSize; Index++ ) {
80            tmp = ptrBuffer[Index];
81            while ( tmp && tmp != ptrBuffer[Index] ) {
82                rtmp = tmp;
83                if ([tmp isKindOfClass:[ANTLRLinkBase class]])
84                    tmp = (ANTLRRuleMemo *)tmp.fNext;
85                else
86                    tmp = nil;
87                [rtmp dealloc];
88            }
89        }
90    }
91    [super dealloc];
92}
93
94- (NSInteger)count
95{
96    NSInteger aCnt = 0;
97    
98    for (int i = 0; i < BuffSize; i++) {
99        if ( ptrBuffer[i] != nil ) {
100            aCnt++;
101        }
102    }
103    return aCnt;
104}
105                          
106- (NSInteger) length
107{
108    return BuffSize;
109}
110
111- (NSInteger) size
112{
113    NSInteger aSize = 0;
114    
115    for (int i = 0; i < BuffSize; i++) {
116        if ( ptrBuffer[i] != nil ) {
117            aSize += sizeof(id);
118        }
119    }
120    return aSize;
121}
122                                  
123                                  
124-(void)deleteANTLRHashRule:(ANTLRRuleMemo *)np
125{
126    ANTLRRuleMemo *tmp, *rtmp;
127    int Index;
128    
129    if ( self.fNext != nil ) {
130        for( Index = 0; Index < BuffSize; Index++ ) {
131            tmp = ptrBuffer[Index];
132            while ( tmp && tmp != ptrBuffer[Index ] ) {
133                rtmp = tmp;
134                if ([tmp isKindOfClass:[ANTLRLinkBase class]])
135                    tmp = (ANTLRRuleMemo *)tmp.fNext;
136                else
137                    tmp = nil;
138                [rtmp release];
139            }
140        }
141    }
142}
143
144-(void)delete_chain:(ANTLRRuleMemo *)np
145{
146    if ( np.fNext != nil )
147        [self delete_chain:np.fNext];
148    [np dealloc];
149}
150
151-(ANTLRRuleMemo **)getPtrBuffer
152{
153    return( ptrBuffer );
154}
155
156-(void)setPtrBuffer:(ANTLRRuleMemo **)np
157{
158    ptrBuffer = np;
159}
160
161- (NSNumber *)getRuleMemoStopIndex:(NSInteger)aStartIndex
162{
163    ANTLRRuleMemo *aRule;
164    NSNumber *stopIndex;
165    NSInteger anIndex;
166    
167    anIndex = ( aStartIndex >= BuffSize ) ? aStartIndex % BuffSize : aStartIndex;
168    if ((aRule = ptrBuffer[anIndex]) == nil) {
169        return nil;
170    }
171    stopIndex = [aRule getStopIndex:aStartIndex];
172    return stopIndex;
173}
174
175- (void)putRuleMemo:(ANTLRRuleMemo *)aRule AtStartIndex:(NSInteger)aStartIndex
176{
177    NSInteger anIndex;
178    
179    anIndex = (aStartIndex >= BuffSize) ? aStartIndex %= BuffSize : aStartIndex;
180    if ( ptrBuffer[anIndex] == nil ) {
181        ptrBuffer[anIndex] = aRule;
182        [aRule retain];
183    }
184    else {
185        do {
186            if ( [aRule.startIndex integerValue] == aStartIndex ) {
187                [aRule setStartIndex:aRule.stopIndex];
188                return;
189            }
190            aRule = aRule.fNext;
191        } while ( aRule != nil );
192    }
193}
194
195- (void)putRuleMemoAtStartIndex:(NSInteger)aStartIndex StopIndex:(NSInteger)aStopIndex
196{
197    ANTLRRuleMemo *aRule, *newRule;
198    NSInteger anIndex;
199    NSInteger aMatchIndex;
200
201    anIndex = (aStartIndex >= BuffSize) ? aStartIndex % BuffSize : aStartIndex;
202    aRule = ptrBuffer[anIndex];
203    if ( aRule == nil ) {
204        aRule = [ANTLRRuleMemo newANTLRRuleMemoWithStartIndex:[NSNumber numberWithInteger:aStartIndex]
205                                                    StopIndex:[NSNumber numberWithInteger:aStopIndex]];
206        [aRule retain];
207        ptrBuffer[anIndex] = aRule;
208    }
209    else {
210        aMatchIndex = [aRule.startIndex integerValue];
211        if ( aStartIndex > aMatchIndex ) {
212            if ( aRule != ptrBuffer[anIndex] ) {
213                [aRule retain];
214            }
215            aRule.fNext = ptrBuffer[anIndex];
216            ptrBuffer[anIndex] = aRule;
217            return;
218        }
219        while (aRule.fNext != nil) {
220            aMatchIndex = [((ANTLRRuleMemo *)aRule.fNext).startIndex integerValue];
221            if ( aStartIndex > aMatchIndex ) {
222                newRule = [ANTLRRuleMemo newANTLRRuleMemoWithStartIndex:[NSNumber numberWithInteger:aStartIndex]
223                                                              StopIndex:[NSNumber numberWithInteger:aStopIndex]];
224                [newRule retain];
225                newRule.fNext = aRule.fNext;
226                aRule.fNext = newRule;
227                return;
228            }
229            if ( aMatchIndex == aStartIndex ) {
230                [aRule setStartIndex:aRule.stopIndex];
231                return;
232            }
233            aRule = aRule.fNext;
234        }
235    }
236}
237
238- (NSInteger)getLastHash
239{
240    return LastHash;
241}
242
243- (void)setLastHash:(NSInteger)aHash
244{
245    LastHash = aHash;
246}
247
248- (NSInteger)getMode
249{
250    return mode;
251}
252
253- (void)setMode:(NSInteger)aMode
254{
255    mode = aMode;
256}
257
258- (void) insertObject:(ANTLRRuleMemo *)aRule atIndex:(NSInteger)anIndex
259{
260    NSInteger Index;
261    
262    Index = ( anIndex >= BuffSize ) ? anIndex % BuffSize : anIndex;
263    if (aRule != ptrBuffer[Index]) {
264        if ( ptrBuffer[Index] ) [ptrBuffer[Index] release];
265        [aRule retain];
266    }
267    ptrBuffer[Index] = aRule;
268}
269
270- (ANTLRRuleMemo *)objectAtIndex:(NSInteger)anIndex
271{
272    NSInteger anIdx;
273
274    anIdx = ( anIndex >= BuffSize ) ? anIndex % BuffSize : anIndex;
275    return ptrBuffer[anIdx];
276}
277
278
279@end
280