This file is indexed.

/usr/lib/python2.7/dist-packages/simpleparse/generator.py is in python-simpleparse 2.2.0-1.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
"""Abstract representation of an in-memory grammar that generates parsers"""
from simpleparse.stt.TextTools import TextTools
import traceback

class Generator:
    '''Abstract representation of an in-memory grammar that generates parsers
    
    The generator class manages a collection of
    ElementToken objects.  These element token objects
    allow the generator to be separated from the
    particular parser associated with any particular EBNF
    grammar.  In fact, it is possible to create entire grammars
    using only the generator objects as a python API.
    '''
    def __init__( self ):
        """Initialise the Generator"""
        self.names = []
        self.rootObjects = []
        self.methodSource = None
        self.definitionSources = []
    def getNameIndex( self, name ):
        '''Return the index into the main list for the given name'''
        try:
            return self.names.index( name )
        except ValueError:
            
            for source in self.definitionSources:
                if name in source:
                    return self.addDefinition( name, source[name])
##			import pdb
##			pdb.set_trace()
            raise NameError( '''The name %s is not defined within this generator'''%(repr(name)), self )
    def getRootObjects( self, ):
        '''Return the list of root generator objects'''
        return self.rootObjects
    def getNames( self, ):
        '''Return the list of root generator objects'''
        return self.names
    def getRootObject( self, name ):
        """Get a particular root object by name"""
        return self.getRootObjects()[ self.getNameIndex(name)]
    
    def addDefinition( self, name, rootElement ):
        '''Add a new definition (object) to the generator'''
        try:
            self.names.index( name )
            raise NameError( '''Attempt to redefine an existing name %s'''%(name), self )
        except ValueError:
            self.names.append( name )
            self.rootObjects.append( rootElement )
            return self.getNameIndex( name )
    def buildParser( self, name, methodSource=None ):
        '''Build the given parser definition, returning a TextTools parsing tuple'''
        self.parserList = []
        self.terminalParserCache = {}
        self.methodSource = methodSource
        i = 0
        while i < len(self.rootObjects):
            # XXX Note: rootObjects will grow in certain cases where
            # a grammar is loading secondary grammars into itself
            rootObject = self.rootObjects[i]
            try:
                if len(self.parserList) <= i or self.parserList[i] is None:
                    parser = tuple(rootObject.toParser( self ))
                    self.setTerminalParser( i, parser )
            except NameError as err:
                currentRuleName = self.names[i]
                err.args = err.args + ('current declaration is %s'%(currentRuleName), )
                raise
            i = i + 1
        assert None not in self.parserList, str( self.parserList)
        return self.parserList [self.getNameIndex (name)]
    def setTerminalParser( self, index, parser ):
        """Explicitly set the parser value for given name"""
        while index >= len(self.parserList):
            self.parserList.append(None)
        self.parserList[index] = parser
    def getTerminalParser( self, index ):
        """Try to retrieve a parser from the parser-list"""
        try:
            return self.parserList[ index ]
        except IndexError:
            return None
    def cacheCustomTerminalParser( self, index, flags, parser ):
        """Optimization to reuse customized terminal parsers"""
        self.terminalParserCache[ (index,flags) ] = parser
    def getCustomTerminalParser( self, index, flags ):
        """Retrieved a cached customized terminal parser or None"""
        return self.terminalParserCache.get( (index, flags))
        
    def getParserList (self):
        return self.parserList


    def getObjectForName( self, name):
        """Determine whether our methodSource has a parsing method for the given name

        returns ( flags or 0 , tagobject)
        """
        testName = "_m_"+name
        if hasattr( self.methodSource, testName):
            method = getattr( self.methodSource, testName )
            if callable(method):
                return  TextTools.CallTag, method
            elif method == TextTools.AppendMatch:
                return method, name
            elif method in (TextTools.AppendToTagobj, TextTools.AppendTagobj):
                object = self.getTagObjectForName( name )
                if method == TextTools.AppendToTagobj:
                    if not ( hasattr( object, 'append') and callable(object.append)):
                        raise ValueError( """Method source %s declares production %s to use AppendToTagobj method, but doesn't given an object with an append method in _o_%s (gave %s)"""%(repr(self.methodSource), name,name, repr(object)))
                return method, object
            else:
                raise ValueError( """Unrecognised command value %s (not callable, not one of the Append* constants) found in methodSource %s, name=%s"""%( repr(method),repr(methodSource),name))
        return 0, name
    def getTagObjectForName( self, name ):
        """Get any explicitly defined tag object for the given name"""
        testName = "_o_"+name
        if hasattr( self.methodSource, testName):
            object = getattr( self.methodSource, testName )
            return object
        return name
    def addDefinitionSource( self, item ):
        """Add a source for definitions when the current grammar doesn't supply
        a particular rule (effectively common/shared items for the grammar)."""
        self.definitionSources.append( item )


### Compatability API
##  This API exists to allow much of the code written with SimpleParse 1.0
##  to work with SimpleParse 2.0
class GeneratorAPI1:
    """Stand-in class supporting operation of SimpleParse 1.0 applications

    There was really only the one method of interest, parserbyname,
    everything else was internal (and is now part of
    simpleparsegrammar.py).
    """
    def __init__( self, production, prebuilt=() ):
        from simpleparse.parser import Parser
        self.parser = Parser( production, prebuilts=prebuilt )
    def parserbyname( self, name ):
        """Retrieve a tag-table by production name"""
        return self.parser.buildTagger( name )

def buildParser( declaration, prebuiltnodes=() ):
    """API 1.0 primary entry point, returns a GeneratorAPI1 instance

    That object will respond to the parserbyname API expected by
    SimpleParse 1.0 applications.
    """
    return GeneratorAPI1( declaration, prebuiltnodes )