self.acclist = numpy.zeros((0x100,), numpy.int16)
n_acclist = 0
self.accept = numpy.zeros((0x100,), numpy.int16)
- n_accept = 1
+ n_states = 1
# transitions[i, j] is transition on character j in state i
# in our way of thinking, 0 is don't care and -1 is failure
transitions = numpy.zeros((0x100, 0x101), numpy.int16)
# generate acclist, accept and transition tables
- while n_accept < len(flex_state_to_action):
- action = flex_state_to_action[n_accept]
+ while n_states < len(flex_state_to_action):
+ action = flex_state_to_action[n_states]
state, transition = _dfa.actions[action]
- #print('state', n_accept, 'transition', transition)
+ #print('state', n_states, 'transition', transition)
del threads0[prefix_slop:]
transit(transition)
#print(threads0[prefix_slop:])
- if n_accept >= self.accept.shape[0]:
+ if n_states >= self.accept.shape[0]:
# extend accept
new_accept = numpy.zeros(
(self.accept.shape[0] * 2,),
)
new_accept[:self.accept.shape[0]] = self.accept
self.accept = new_accept
- self.accept[n_accept] = n_acclist
+ self.accept[n_states] = n_acclist
for k in [j for i in threads0[prefix_slop:] for j in i]:
acc = k >> 1
if k & 1:
if (
- n_acclist == self.accept[n_accept] or
+ n_acclist == self.accept[n_states] or
self.acclist[n_acclist - 1] != acc | FlexDFA.YY_TRAILING_HEAD_MASK
):
# look back to start of trailing context, then accept
n_acclist += 1
# calculate transition row from _dfa.state character-to-action table
- if n_accept >= transitions.shape[0]:
+ if n_states >= transitions.shape[0]:
# extend transitions
new_transitions = numpy.zeros(
(transitions.shape[0] * 2, 0x101),
next_flex_state = len(flex_state_to_action)
action_to_flex_state[next_action] = next_flex_state
flex_state_to_action.append(next_action)
- transitions[n_accept, character0:character1] = next_flex_state
+ transitions[n_states, character0:character1] = next_flex_state
character0 = character1
assert character0 == 0x100
- n_accept += 1
-
- # remap NUL transitions to 0x100 and replace with EOB transitions
- transitions[:, 0x100] = transitions[:, 0]
- transitions[:, 0] = eob_state
+ n_states += 1
# finalize the acclist and accept tables
self.acclist = self.acclist[:n_acclist]
- if n_accept >= self.accept.shape[0]:
+ if n_states >= self.accept.shape[0]:
new_accept = numpy.zeros(
(self.accept.shape[0] * 2,),
numpy.int16
)
new_accept[:self.accept.shape[0]] = self.accept
self.accept = new_accept
- self.accept[n_accept] = n_acclist
- self.accept = self.accept[:n_accept + 1]
+ self.accept[n_states] = n_acclist
+ self.accept = self.accept[:n_states + 1]
+
+ # finalize the transitions table
+ transitions = transitions[:n_states, :]
+ transitions[:, 0x100] = transitions[:, 0]
+ transitions[:, 0] = eob_state
# state 0 is the jam state, the EOB state will be added later on
- self.states = numpy.zeros((0x100, 2), numpy.int16) # base, def
- n_states = 1
+ self.states = numpy.zeros((n_states, 2), numpy.int16) # base, def
self.entries = numpy.full((0x200, 2), -1, numpy.int16) # nxt, chk
self.entries[:0x101, :] = 0 # jam state just returns to jam state
self.entries[0, 0] = eob_state # except for the EOB transition
transitions[:, numpy.newaxis, :] != transitions[numpy.newaxis, :, :],
2
)
- while n_states < n_accept:
+ for i in range(1, n_states):
# find most similar/earliest existing state to use as default
- default_state = numpy.argmin(dist[:n_states, n_states], 0)
+ state_done = numpy.argmin(dist[:i, i], 0)
indices = numpy.nonzero(
- transitions[n_states] != transitions[default_state]
+ transitions[i, :] != transitions[state_done, :]
)[0]
if indices.shape[0] == 0:
# when copying another state, need to have the same base, though
# the base will not matter since there will be no entries, it is
# is because of the awkward way the compressed lookup is written
- start_index = self.states[default_state, 0]
+ start_index = self.states[state_done, 0]
else:
# make sure entries array is at least large enough to find a spot
while self.entries.shape[0] < n_entries + 0x101:
if not numpy.any(entries_used[indices + start_index]):
break
start_index += 1
- self.entries[indices + start_index, 0] = transitions[n_states, indices]
- self.entries[indices + start_index, 1] = n_states
+ self.entries[indices + start_index, 0] = transitions[i, indices]
+ self.entries[indices + start_index, 1] = i
entries_used[indices + start_index] = True
if n_entries < start_index + 0x101:
n_entries = start_index + 0x101
- if n_states >= self.states.shape[0]:
- new_states = numpy.zeros(
- (self.states.shape[0] * 2, 2),
- numpy.int16
- )
- new_states[:self.states.shape[0], :] = self.states
- self.states = new_states
- self.states[n_states, 0] = start_index
- self.states[n_states, 1] = default_state
- n_states += 1
+ self.states[i, 0] = start_index
+ self.states[i, 1] = state_done
- # finalize states and entries tables
+ # finalize entries table
self.entries = self.entries[:n_entries, :]
- self.states = self.states[:n_states, :]
def generate(plex, skel_file, out_file):
nfa = plex.to_nfa()