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    ANTLRHashRule *aNewANTLRHashRule;
46    
47    aNewANTLRHashRule = [[ANTLRHashRule alloc] init];
48	return( aNewANTLRHashRule );
49}
50
51+(id)newANTLRHashRuleWithLen:(NSInteger)aBuffSize
52{
53    ANTLRHashRule *aNewANTLRHashRule;
54    
55    aNewANTLRHashRule = [[ANTLRHashRule alloc] initWithLen:aBuffSize];
56	return( aNewANTLRHashRule );
57}
58
59-(id)init
60{
61	if ((self = [super initWithLen:HASHSIZE]) != nil) {
62		fNext = nil;
63	}
64    return( self );
65}
66
67-(id)initWithLen:(NSInteger)aBuffSize
68{
69	if ((self = [super initWithLen:aBuffSize]) != nil) {
70		fNext = nil;
71        mode = 0;
72	}
73    return( self );
74}
75
76-(void)dealloc
77{
78    ANTLRRuleMemo *tmp, *rtmp;
79    int Index;
80	
81    if ( self.fNext != nil ) {
82        for( Index = 0; Index < BuffSize; Index++ ) {
83            tmp = ptrBuffer[Index];
84            while ( tmp && tmp != ptrBuffer[Index] ) {
85                rtmp = tmp;
86                // tmp = [tmp getfNext];
87                tmp = (ANTLRRuleMemo *)tmp.fNext;
88                [rtmp dealloc];
89            }
90        }
91    }
92	[super dealloc];
93}
94
95- (NSInteger)count
96{
97    id anElement;
98    NSInteger aCnt = 0;
99    
100    for (int i = 0; i < BuffSize; i++) {
101        anElement = ptrBuffer[i];
102        if ( anElement != nil ) {
103            aCnt++;
104        }
105    }
106    return aCnt;
107}
108                          
109- (NSInteger) length
110{
111    return BuffSize;
112}
113
114- (NSInteger) size
115{
116    id anElement;
117    NSInteger aSize = 0;
118    
119    for (int i = 0; i < BuffSize; i++) {
120        if ((anElement = ptrBuffer[i]) != nil) {
121            aSize += sizeof(id);
122        }
123    }
124    return aSize;
125}
126                                  
127                                  
128-(void)deleteANTLRHashRule:(ANTLRRuleMemo *)np
129{
130    ANTLRRuleMemo *tmp, *rtmp;
131    int Index;
132    
133    if ( self.fNext != nil ) {
134        for( Index = 0; Index < BuffSize; Index++ ) {
135            tmp = ptrBuffer[Index];
136            while ( tmp && tmp != ptrBuffer[Index ] ) {
137                rtmp = tmp;
138                tmp = tmp.fNext;
139                [rtmp dealloc];
140            }
141        }
142    }
143}
144
145-(void)delete_chain:(ANTLRRuleMemo *)np
146{
147    if ( np.fNext != nil )
148		[self delete_chain:np.fNext];
149	[np dealloc];
150}
151
152-(ANTLRRuleMemo **)getPtrBuffer
153{
154	return( ptrBuffer );
155}
156
157-(void)setPtrBuffer:(ANTLRRuleMemo **)np
158{
159	ptrBuffer = np;
160}
161
162- (NSNumber *)getRuleMemoStopIndex:(NSInteger)aStartIndex
163{
164    ANTLRRuleMemo *aRule;
165    NSNumber *stopIndex;
166    NSInteger anIndex;
167    
168    anIndex = ( aStartIndex >= BuffSize ) ? aStartIndex %= BuffSize : aStartIndex;
169    if ((aRule = ptrBuffer[anIndex]) == nil) {
170        return nil;
171    }
172    stopIndex = [aRule getStopIndex:aStartIndex];
173    return stopIndex;
174}
175
176- (void)putRuleMemo:(ANTLRRuleMemo *)aRule AtStartIndex:(NSInteger)aStartIndex
177{
178    NSInteger anIndex;
179    
180    anIndex = (aStartIndex >= BuffSize) ? aStartIndex %= BuffSize : aStartIndex;
181    if ( ptrBuffer[anIndex] == nil ) {
182        ptrBuffer[anIndex] = aRule;
183        [aRule retain];
184    }
185    else {
186        do {
187            if ( [aRule.startIndex integerValue] == aStartIndex ) {
188                [aRule setStartIndex:aRule.stopIndex];
189                return;
190            }
191            aRule = aRule.fNext;
192        } while ( aRule != nil );
193    }
194}
195
196- (void)putRuleMemoAtStartIndex:(NSInteger)aStartIndex StopIndex:(NSInteger)aStopIndex
197{
198    ANTLRRuleMemo *aRule, *newRule;
199    NSInteger anIndex;
200    NSInteger aMatchIndex;
201
202    anIndex = (aStartIndex >= BuffSize) ? aStartIndex %= BuffSize : aStartIndex;
203    if ((aRule = ptrBuffer[anIndex]) == 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] != nil) {
265            [ptrBuffer[Index] release];
266        }
267        [aRule retain];
268    }
269    ptrBuffer[Index] = aRule;
270}
271
272- (ANTLRRuleMemo *)objectAtIndex:(NSInteger)anIndex
273{
274    NSInteger anIdx;
275
276    anIdx = ( anIndex >= BuffSize ) ? anIndex %= BuffSize : anIndex;
277    return ptrBuffer[anIdx];
278}
279
280
281@end
282