10 declarator = {
'byte': 8,
23 EMPTY_RE = re.compile(
r'\s*$')
24 COMMENT_RE = re.compile(
r'\s*;\S*')
25 LOCAL_LABEL_RE = re.compile(
r'\s*(\.L\S+)\s*:')
26 DIRECTIVE_START_RE = re.compile(
r'\s*\.')
27 DIRECTIVE_RE = re.compile(
r'\s*\.(\S+)')
28 LABEL_RE = re.compile(
r'\s*(\S+)\s*:')
29 FORGET_LABEL_RE = re.compile(
r'\s*\.LF[BE]\d\s*:')
34 """Stand for Directive"""
40 """Stand for alignment representation"""
51 """Stand for alignment representation"""
56 class DirectiveDontSplit(Directive):
58 """Stand for alignment representation"""
64 """Generate a new label
65 @symbol_pool: the asm_symbol_pool instance"""
70 label = symbol_pool.getby_name(name)
72 return symbol_pool.add_label(name)
77 """Create asm_label of the expression @expr in the @symbol_pool
80 if not (isinstance(expr, m2_expr.ExprId)
and
85 new_lbl = symbol_pool.getby_name_create(old_lbl.name)
86 replace_id[expr] = m2_expr.ExprId(new_lbl, expr.size)
87 return replace_id[expr]
91 """Link orphan labels used by @instr to the @symbol_pool"""
93 for i, arg
in enumerate(instr.args):
98 instr.args[i] = instr.args[i].replace_expr(replace_id)
106 """Parse an assembly listing. Returns a couple (blocks, symbol_pool), where
107 blocks is a list of asm_bloc and symbol_pool the associated asm_symbol_pool
109 @mnemo: architecture used
110 @attrib: architecture attribute
111 @txt: assembly listing
112 @symbol_pool: (optional) the asm_symbol_pool instance used to handle labels
117 if symbol_pool
is None:
120 C_NEXT = asmbloc.asm_constraint.c_next
121 C_TO = asmbloc.asm_constraint.c_to
125 for line
in txt.split(
'\n'):
127 if EMPTY_RE.match(line):
130 if COMMENT_RE.match(line):
133 if FORGET_LABEL_RE.match(line):
136 match_re = LABEL_RE.match(line)
138 label_name = match_re.group(1)
139 label = symbol_pool.getby_name_create(label_name)
143 if DIRECTIVE_START_RE.match(line):
144 match_re = DIRECTIVE_RE.match(line)
145 directive = match_re.group(1)
146 if directive
in [
'text',
'data',
'bss']:
148 if directive
in [
'string',
'ascii']:
150 line = line.replace(
r'\n',
'\n').replace(
r'\r',
'\r')
151 raw = line[line.find(
r'"') + 1:line.rfind(
r'"')]
152 raw = raw.decode(
'string_escape')
153 if directive ==
'string':
157 if directive ==
'ustring':
159 line = line.replace(
r'\n',
'\n').replace(
r'\r',
'\r')
160 raw = line[line.find(
r'"') + 1:line.rfind(
r'"')] +
"\x00"
161 raw = raw.decode(
'string_escape')
162 raw =
"".join([string +
'\x00' for string
in raw])
165 if directive
in declarator:
166 data_raw = line[match_re.end():].split(
' ', 1)[1]
167 data_raw = data_raw.split(
',')
168 size = declarator[directive]
173 my_var_parser =
parse_ast(
lambda x: m2_expr.ExprId(x, size),
175 m2_expr.ExprInt(x, size))
176 base_expr.setParseAction(my_var_parser)
178 for element
in data_raw:
179 element = element.strip()
180 element_expr = base_expr.parseString(element)[0]
181 expr_list.append(element_expr.canonize())
184 raw_data.element_size = size
185 lines.append(raw_data)
187 if directive ==
'comm':
190 if directive ==
'split':
193 if directive ==
'dontsplit':
196 if directive ==
"align":
197 align_value = int(line[match_re.end():], 0)
200 if directive
in [
'file',
'intel_syntax',
'globl',
'local',
201 'type',
'size',
'align',
'ident',
'section']:
203 if directive[0:4] ==
'cfi_':
206 raise ValueError(
"unknown directive %s" % str(directive))
209 match_re = LABEL_RE.match(line)
211 label_name = match_re.group(1)
212 label = symbol_pool.getby_name_create(label_name)
218 line = line[:line.find(
';')]
219 line = line.strip(
' ').strip(
'\t')
220 instr = mnemo.fromstring(line, attrib)
226 instr.dstflow2label(symbol_pool)
229 asmbloc.log_asmbloc.info(
"___pre asm oki___")
233 state = STATE_NO_BLOC
236 block_to_nlink =
None
237 block_may_link =
False
239 while i < len(lines):
242 state = STATE_NO_BLOC
247 if state == STATE_NO_BLOC:
248 if isinstance(line, DirectiveDontSplit):
249 block_to_nlink = cur_block
252 elif isinstance(line, DirectiveSplit):
253 block_to_nlink =
None
265 blocks.append(cur_block)
266 state = STATE_IN_BLOC
268 block_to_nlink.addto(
271 block_to_nlink =
None
275 elif state == STATE_IN_BLOC:
276 if isinstance(line, DirectiveSplit):
277 state = STATE_NO_BLOC
278 block_to_nlink =
None
279 elif isinstance(line, DirectiveDontSplit):
280 state = STATE_NO_BLOC
281 block_to_nlink = cur_block
282 elif isinstance(line, DirectiveAlign):
283 cur_block.alignment = line.alignment
285 cur_block.addline(line)
286 block_to_nlink = cur_block
291 block_to_nlink =
None
292 state = STATE_NO_BLOC
295 elif isinstance(line, instruction):
296 cur_block.addline(line)
297 block_to_nlink = cur_block
298 if not line.breakflow():
302 raise RuntimeError(
"Cannot have breakflow in delayslot")
304 for dst
in line.getdstflow(symbol_pool):
305 if not isinstance(dst, m2_expr.ExprId):
307 if dst
in mnemo.regs.all_regs_ids:
311 if not line.splitflow():
312 block_to_nlink =
None
314 delayslot = line.delayslot
316 state = STATE_NO_BLOC
318 raise RuntimeError(
"unknown class %s" % line.__class__)
322 asmbloc.log_asmbloc.info(block)
323 return blocks, symbol_pool
def replace_orphan_labels