MCPcopy
hub / github.com/rocky/python-uncompyle6 / ingest

Method ingest

uncompyle6/scanners/scanner2.py:184–502  ·  view source on GitHub ↗

Create "tokens" the bytecode of an Python code object. Largely these are the opcode name, but in some cases that has been modified to make parsing easier. returning a list of uncompyle6 Token's. Some transformations are made to assist the deparsing grammar:

(self, co, classname=None, code_objects={}, show_asm=None)

Source from the content-addressed store, hash-verified

182 return free, names, varnames
183
184 def ingest(self, co, classname=None, code_objects={}, show_asm=None):
185 """
186 Create "tokens" the bytecode of an Python code object. Largely these
187 are the opcode name, but in some cases that has been modified to make parsing
188 easier.
189 returning a list of uncompyle6 Token's.
190
191 Some transformations are made to assist the deparsing grammar:
192 - various types of LOAD_CONST's are categorized in terms of what they load
193 - COME_FROM instructions are added to assist parsing control structures
194 - operands with stack argument counts or flag masks are appended to the opcode name, e.g.:
195 * BUILD_LIST, BUILD_SET
196 * MAKE_FUNCTION and FUNCTION_CALLS append the number of positional arguments
197 - EXTENDED_ARGS instructions are removed
198
199 Also, when we encounter certain tokens, we add them to a set which will cause custom
200 grammar rules. Specifically, variable arg tokens like MAKE_FUNCTION or BUILD_LIST
201 cause specific rules for the specific number of arguments they take.
202 """
203 if not show_asm:
204 show_asm = self.show_asm
205
206 bytecode = self.build_instructions(co)
207
208 if show_asm in ("both", "before"):
209 print("\n# ---- disassembly:")
210 bytecode.disassemble_bytes(
211 co.co_code,
212 varnames=co.co_varnames,
213 names=co.co_names,
214 constants=co.co_consts,
215 cells=bytecode._cell_names,
216 line_starts=bytecode._linestarts,
217 asm_format="extended",
218 )
219
220 # list of tokens/instructions
221 new_tokens = []
222
223 # "customize" is in the process of going away here
224 customize = {}
225 if self.is_pypy:
226 customize["PyPy"] = 0
227
228 codelen = len(self.code)
229
230 free, names, varnames = self.unmangle_code_names(co, classname)
231 self.names = names
232
233 # Scan for assertions. Later we will
234 # turn 'LOAD_GLOBAL' to 'LOAD_ASSERT'.
235 # 'LOAD_ASSERT' is used in assert statements.
236 self.load_asserts = set()
237 for i in self.op_range(0, codelen):
238 # We need to detect the difference between:
239 # raise AssertionError
240 # and
241 # assert ...

Callers

nothing calls this directly

Calls 15

unmangle_code_namesMethod · 0.95
find_jump_targetsMethod · 0.95
extended_arg_valMethod · 0.95
patch_continueMethod · 0.95
formatMethod · 0.95
TokenClass · 0.90
build_instructionsMethod · 0.80
op_rangeMethod · 0.80
get_argumentMethod · 0.80
addMethod · 0.80
opname_for_offsetMethod · 0.80
op_nameMethod · 0.80

Tested by

no test coverage detected