tools/binary_size/libsupersize/bcanalyzer.py
def _ParseBcAnalyzer(lines):
  """A generator to extract bytes() from bcanalyzer dump of a BC file."""

  # ...
  # <TYPE_BLOCK_ID NumWords=103 BlockCodeSize=4>
  #    ... (See above; parsed by _BcTypeInfo)
  # <TYPE_BLOCK_ID>
  # ...
  # <CONSTANTS_BLOCK NumWords=93 BlockCodeSize=4>
  #   <SETTYPE abbrevid=4 op0=1/>  # Current type id := 1 ==> int8*.
  #   <CE_INBOUNDS_GEP op0=3 op1=4 op2=1 op3=12 op4=57 op5=12 op6=57/>
  #   <SETTYPE abbrevid=4 op0=2/>  # Current type id := 2 ==> int8[4].
  #   <CSTRING abbrevid=11 op0=70 op1=111 op2=111/> record string = 'Foo'
  #   <STRING abbrevid=11 op0=70 op1=111 op2=111 op3=1/>  # {'F','o','o',1}.
  #   <SETTYPE abbrevid=6 op0=7/>    # Current type id := 7 ==> int32.
  #   <INTEGER abbrevid=5 op0=2000/> # Stores 1000.
  #   <INTEGER abbrevid=5 op0=2001/> # Stores -1000.
  #   <SETTYPE abbrevid=4 op0=8/>    # Current type id := 8 ==> int16[4].
  #   <NULL/>
  #   <DATA abbrevid=11 op0=8400 op1=10100 op2=11500 op3=0/>
  # </CONSTANTS_BLOCK>
  # ...

  # Notes:
  # - Only parse first <TYPE_BLOCK_ID> and first <CONSTANTS_BLOCK>.
  # - <CONSTANTS_BLOCK> is stateful: A "current type id" exists, and that's set
  #   by <SETTYPE>, with op0= referring to type id.
  #   - For array lengths one needs to refer to the corresponding <ARRAY>.
  # - Strings / arrays are in <CSTRING>, <STRING>, and <DATA>.
  #   - abbrevid=# is redundant (repeats tag type) and unused
  #   - Character data are stored in op0=# op1=# ..., one per character. These
  #     values should fit in the proper range, and can be fairly large.
  #   - <CSTRING> has implicit 0 at end.
  #   - Data lengths agree with the length in the matching <ARRAY> entry.
  #   - "record string" text is not very useful: It only appears if all
  #     characters are printable.
  # - Signed vs. unsigned types are undistinguished.
  #   - In <INTEGER>, the op0= value is stored as 2 * abs(x) + (signed ? 0 : 1).
  #   - In <ARRAY> of int, values are coerced to unsigned type.
  # - Strings and int arrays are undistinguished.
  #   - <CSTRING>: If an uint8 array happens to end with 0, then this gets used!
  # - Arrays (or integers) of all-0 appear as <NULL/>. Presumably this gets
  #   placed into .bss section.

  STATE_VOID = 0
  STATE_TYPE_BLOCK = 1
  STATE_CONST_BLOCK = 2
  state = STATE_VOID

  type_info = None
  consts_cur_type = None

  # State machine to parse the *first* <TYPE_BLOCK_ID> to initialize
  # |type_info|, then the *first* <CONSTANTS_BLOCK> to yield strings.
  for line in lines:
    line = line.lstrip()
    (tag_type, tag, attrib_pos) = ParseTag(line)
    if tag_type is None:
      continue
    if state == STATE_VOID:
      if _IsOpeningTag(tag_type):
        if tag == 'TYPE_BLOCK_ID':
          if type_info is None:
            state = STATE_TYPE_BLOCK
            type_info = _BcTypeInfo()
        elif tag == 'CONSTANTS_BLOCK':
          if type_info is not None:
            state = STATE_CONST_BLOCK

    elif state == STATE_TYPE_BLOCK:
      if _IsClosingTag(tag_type) and tag == 'TYPE_BLOCK_ID':
        state = STATE_VOID
      else:
        type_info.Feed(line, tag, attrib_pos)

    elif state == STATE_CONST_BLOCK:
      if _IsClosingTag(tag_type) and tag == 'CONSTANTS_BLOCK':
        # Skip remaining data, including subsequent <CONSTANTS_BLOCK>s.
        break
      if tag == 'SETTYPE':
        try:
          consts_cur_type_id = next(_ParseOpItems(line, attrib_pos))  # op0.
        except StopIteration:
          return
        consts_cur_type = type_info.GetArrayType(consts_cur_type_id)
      elif consts_cur_type and consts_cur_type.width <= _CHAR_WIDTH_LIMIT:
        if tag in ['CSTRING', 'STRING', 'DATA']:
          # Exclude 32-bit / 4-byte strings since they're rarely used, and are
          # likely confused with 32-bit int arrays.
          s = consts_cur_type.ParseOpItemsAsBytes(line, attrib_pos,
                                                  tag == 'CSTRING')
          yield (consts_cur_type, s)
A generator to extract bytes() from bcanalyzer dump of a BC file.
A generator to extract bytes() from bcanalyzer dump of a BC file.
A generator to extract bytes () from bcanalyzer dump of a BC file .
def _ParseBcAnalyzer(lines):
  #   - Character data are stored in op0=# op1=, one per character. These
  STATE_VOID = 0
  STATE_TYPE_BLOCK = 1
  STATE_CONST_BLOCK = 2
  state = STATE_VOID
  type_info = None
  consts_cur_type = None
  for line in lines:
    line = line.lstrip()
    (tag_type, tag, attrib_pos) = ParseTag(line)
    if tag_type is None:
      continue
    if state == STATE_VOID:
      if _IsOpeningTag(tag_type):
        if tag == 'TYPE_BLOCK_ID':
          if type_info is None:
            state = STATE_TYPE_BLOCK
            type_info = _BcTypeInfo()
        elif tag == 'CONSTANTS_BLOCK':
          if type_info is not None:
            state = STATE_CONST_BLOCK
    elif state == STATE_TYPE_BLOCK:
      if _IsClosingTag(tag_type) and tag == 'TYPE_BLOCK_ID':
        state = STATE_VOID
      else:
        type_info.Feed(line, tag, attrib_pos)
    elif state == STATE_CONST_BLOCK:
      if _IsClosingTag(tag_type) and tag == 'CONSTANTS_BLOCK':
        break
      if tag == 'SETTYPE':
        try:
          consts_cur_type_id = next(_ParseOpItems(line, attrib_pos))  
        except StopIteration:
          return
        consts_cur_type = type_info.GetArrayType(consts_cur_type_id)
      elif consts_cur_type and consts_cur_type.width <= _CHAR_WIDTH_LIMIT:
        if tag in ['CSTRING', 'STRING', 'DATA']:
          s = consts_cur_type.ParseOpItemsAsBytes(line, attrib_pos,
                                                  tag == 'CSTRING')
          yield (consts_cur_type, s)
def _ParseBcAnalyzer ( lines ) : STATE_VOID = 0 STATE_TYPE_BLOCK = 1 STATE_CONST_BLOCK = 2 state = STATE_VOID type_info = None consts_cur_type = None for line in lines : line = line . lstrip ( ) ( tag_type , tag , attrib_pos ) = ParseTag ( line ) if tag_type is None : continue if state == STATE_VOID : if _IsOpeningTag ( tag_type ) : if tag == 'TYPE_BLOCK_ID' : if type_info is None : state = STATE_TYPE_BLOCK type_info = _BcTypeInfo ( ) elif tag == 'CONSTANTS_BLOCK' : if type_info is not None : state = STATE_CONST_BLOCK elif state == STATE_TYPE_BLOCK : if _IsClosingTag ( tag_type ) and tag == 'TYPE_BLOCK_ID' : state = STATE_VOID else : type_info . Feed ( line , tag , attrib_pos ) elif state == STATE_CONST_BLOCK : if _IsClosingTag ( tag_type ) and tag == 'CONSTANTS_BLOCK' : break if tag == 'SETTYPE' : try : consts_cur_type_id = next ( _ParseOpItems ( line , attrib_pos ) ) except StopIteration : return consts_cur_type = type_info . GetArrayType ( consts_cur_type_id ) elif consts_cur_type and consts_cur_type . width <= _CHAR_WIDTH_LIMIT : if tag in [ 'CSTRING' , 'STRING' , 'DATA' ] : s = consts_cur_type . ParseOpItemsAsBytes ( line , attrib_pos , tag == 'CSTRING' ) yield ( consts_cur_type , s )
A generator to extract bytes() from bcanalyzer dump of a BC file.
A generator to extract bytes () from bcanalyzer dump of a BC file .
"""A generator to extract bytes() from bcanalyzer dump of a BC file.""" # ... # <TYPE_BLOCK_ID NumWords=103 BlockCodeSize=4> #    ... (See above; parsed by _BcTypeInfo) # <TYPE_BLOCK_ID> # ... # <CONSTANTS_BLOCK NumWords=93 BlockCodeSize=4> #   <SETTYPE abbrevid=4 op0=1/>  # Current type id := 1 ==> int8*. #   <CE_INBOUNDS_GEP op0=3 op1=4 op2=1 op3=12 op4=57 op5=12 op6=57/> #   <SETTYPE abbrevid=4 op0=2/>  # Current type id := 2 ==> int8[4]. #   <CSTRING abbrevid=11 op0=70 op1=111 op2=111/> record string = 'Foo' #   <STRING abbrevid=11 op0=70 op1=111 op2=111 op3=1/>  # {'F','o','o',1}. #   <SETTYPE abbrevid=6 op0=7/>    # Current type id := 7 ==> int32. #   <INTEGER abbrevid=5 op0=2000/> # Stores 1000. #   <INTEGER abbrevid=5 op0=2001/> # Stores -1000. #   <SETTYPE abbrevid=4 op0=8/>    # Current type id := 8 ==> int16[4]. #   <NULL/> #   <DATA abbrevid=11 op0=8400 op1=10100 op2=11500 op3=0/> # </CONSTANTS_BLOCK> # ... # Notes: # - Only parse first <TYPE_BLOCK_ID> and first <CONSTANTS_BLOCK>. # - <CONSTANTS_BLOCK> is stateful: A "current type id" exists, and that's set #   by <SETTYPE>, with op0= referring to type id. #   - For array lengths one needs to refer to the corresponding <ARRAY>. # - Strings / arrays are in <CSTRING>, <STRING>, and <DATA>. #   - abbrevid=# is redundant (repeats tag type) and unused #   - Character data are stored in op0=# op1=# ..., one per character. These #     values should fit in the proper range, and can be fairly large. #   - <CSTRING> has implicit 0 at end. #   - Data lengths agree with the length in the matching <ARRAY> entry. #   - "record string" text is not very useful: It only appears if all #     characters are printable. # - Signed vs. unsigned types are undistinguished. #   - In <INTEGER>, the op0= value is stored as 2 * abs(x) + (signed ? 0 : 1). #   - In <ARRAY> of int, values are coerced to unsigned type. # - Strings and int arrays are undistinguished. #   - <CSTRING>: If an uint8 array happens to end with 0, then this gets used! # - Arrays (or integers) of all-0 appear as <NULL/>. Presumably this gets #   placed into .bss section. # State machine to parse the *first* <TYPE_BLOCK_ID> to initialize # |type_info|, then the *first* <CONSTANTS_BLOCK> to yield strings. # Skip remaining data, including subsequent <CONSTANTS_BLOCK>s. # op0. # Exclude 32-bit / 4-byte strings since they're rarely used, and are # likely confused with 32-bit int arrays.
lines