88
99import argparse
1010import contextlib
11+ import functools
1112import gc
1213import json
1314import mmap
1415import os
15- import re
1616import sys
1717import subprocess
1818
4545# Size of the chunks that are fed to the XML parser
4646_PARSE_CHUNK_SIZE = 1 << 16
4747
48- # Start tag of a <dump> element (but not of the <dumps> element)
49- _DUMP_START_TAG_RE = re .compile (rb'<dump[\s>]' )
48+ _DUMP_START_TAG = b'<dump '
5049_DUMP_END_TAG = b'</dump>'
5150
5251
@@ -76,23 +75,15 @@ def _feed_without_configurations(parser, filename):
7675 if os .fstat (f .fileno ()).st_size == 0 :
7776 return
7877 with mmap .mmap (f .fileno (), 0 , access = mmap .ACCESS_READ ) as data :
79- first = _DUMP_START_TAG_RE . search ( data )
78+ first = data . find ( _DUMP_START_TAG )
8079 last = data .rfind (_DUMP_END_TAG )
81- if first is None or last < first . start () :
80+ if first < 0 or last < first :
8281 parser .feed (data [:])
8382 else :
84- parser .feed (data [:first . start () ])
83+ parser .feed (data [:first ])
8584 parser .feed (data [last + len (_DUMP_END_TAG ):])
8685
8786
88- def _read_chunks (f ):
89- while True :
90- chunk = f .read (_PARSE_CHUNK_SIZE )
91- if not chunk :
92- return
93- yield chunk
94-
95-
9687def _load_location (location , element ):
9788 """Load location from element/dict"""
9889 location .file = element .get ('file' )
@@ -1271,8 +1262,6 @@ def __init__(self):
12711262 self .configurations = [] # completed configurations
12721263 self .cfg = None
12731264 self .cfg_arguments = [] # function arguments for Configuration node initialization
1274- self .cfg_function = None
1275- self .cfg_valueflow = None
12761265
12771266 # Iterating <varlist> in a <scope>.
12781267 self .iter_scope_varlist = False
@@ -1299,10 +1288,9 @@ def start(self, tag, attrib):
12991288
13001289 # Parse valueflows (list of values)
13011290 elif tag == 'value' :
1302- self . cfg_valueflow .values .append (Value (attrib ))
1291+ cfg . valueflow [ - 1 ] .values .append (Value (attrib ))
13031292 elif tag == 'values' :
1304- self .cfg_valueflow = ValueFlow (attrib )
1305- cfg .valueflow .append (self .cfg_valueflow )
1293+ cfg .valueflow .append (ValueFlow (attrib ))
13061294
13071295 # Parse scopes
13081296 elif tag == 'scope' :
@@ -1323,14 +1311,13 @@ def start(self, tag, attrib):
13231311
13241312 # Parse functions
13251313 elif tag == 'function' :
1326- self .cfg_function = Function (attrib , cfg .scopes [- 1 ])
1327- cfg .functions .append (self .cfg_function )
1314+ cfg .functions .append (Function (attrib , cfg .scopes [- 1 ]))
13281315
13291316 # Parse function arguments
13301317 elif tag == 'arg' :
13311318 arg_nr = int (attrib .get ('nr' ))
13321319 arg_variable_id = attrib .get ('variable' )
1333- self . cfg_function .argumentId [arg_nr ] = arg_variable_id
1320+ cfg . functions [ - 1 ] .argumentId [arg_nr ] = arg_variable_id
13341321
13351322 # Parse directives list
13361323 elif tag == 'directive' :
@@ -1356,10 +1343,6 @@ def start(self, tag, attrib):
13561343 if self .iter_typedef_info :
13571344 cfg .typedefInfo .append (TypedefInfo (attrib ))
13581345
1359- # Parse template-token
1360- #elif tag == 'TokenAndName': #todo add processing of containers
1361- # cfg.containers.append(Container(attrib))
1362-
13631346 # Serialize new configuration node
13641347 elif tag == 'dump' :
13651348 self .cfg = Configuration (attrib .get ('cfg' ))
@@ -1476,7 +1459,7 @@ def iterconfigurations(self):
14761459 builder = _ConfigurationBuilder ()
14771460 parser = ElementTree .XMLParser (target = builder )
14781461 with open (self .filename , 'rb' ) as f :
1479- for chunk in _read_chunks ( f ):
1462+ for chunk in iter ( functools . partial ( f . read , _PARSE_CHUNK_SIZE ), b'' ):
14801463 with _gc_disabled ():
14811464 parser .feed (chunk )
14821465 yield from builder .take_configurations ()
0 commit comments