def codetest(self, func, **kwds): import inspect try: func = func.im_func except AttributeError: pass #name = func.func_name graph = build_flow(func, **kwds) graph.source = inspect.getsource(func) self.show(graph) return graph
def test_tweak_generator_graph(self): def f(n, x, y, z): z *= 10 yield n + 1 z -= 10 # graph = make_generator_entry_graph(f) func1 = graph._tweaked_func if option.view: graph.show() GeneratorIterator = graph._tweaked_func._generator_next_method_of_ assert hasattr(GeneratorIterator, 'next') # graph_next = build_flow(GeneratorIterator.next.im_func) join_blocks(graph_next) if option.view: graph_next.show() # graph1 = build_flow(func1) if option.view: graph1.show()
def test_automatic(self): def f(n, x, y, z): z *= 10 yield n + 1 z -= 10 # graph = build_flow(f) if option.view: graph.show() block = graph.startblock assert len(block.exits) == 1 assert block.exits[0].target is graph.returnblock
def test_translate_cast(): cdef = "typedef ssize_t Py_ssize_t;" cts = parse_source(cdef) def f(): return cts.cast('Py_ssize_t*', 0) graph = build_flow(f) simplify_graph(graph) assert len(graph.startblock.operations) == 1 op = graph.startblock.operations[0] assert op.args[0] == const(rffi.cast) assert op.args[1].value is cts.gettype('Py_ssize_t*')
def test_translate_gettype(): cdef = "typedef ssize_t Py_ssize_t;" cts = parse_source(cdef) def f(): return cts.gettype('Py_ssize_t*') graph = build_flow(f) simplify_graph(graph) # Check that the result is constant-folded assert graph.startblock.operations == [] [link] = graph.startblock.exits assert link.target is graph.returnblock assert link.args[0] == const(rffi.CArrayPtr(rffi.SSIZE_T))
def test_tweak_generator_graph(self): def f(n, x, y, z): z *= 10 yield n + 1 z -= 10 # graph = build_flow(f) GeneratorIterator = make_generatoriterator_class(graph) replace_graph_with_bootstrap(GeneratorIterator, graph) func1 = attach_next_method(GeneratorIterator, graph) if option.view: graph.show() # assert func1._generator_next_method_of_ is GeneratorIterator assert hasattr(GeneratorIterator, 'next') # graph_next = build_flow(GeneratorIterator.next.im_func) join_blocks(graph_next) if option.view: graph_next.show() # graph1 = build_flow(func1) if option.view: graph1.show()
def buildflowgraph(self, func, mute_dot=False): """Get the flow graph for a function.""" if not isinstance(func, types.FunctionType): raise TypeError("buildflowgraph() expects a function, " "got %r" % (func,)) if func in self._prebuilt_graphs: graph = self._prebuilt_graphs.pop(func) else: if self.config.translation.verbose: log(nice_repr_for_func(func)) graph = build_flow(func) simplify.simplify_graph(graph) if self.config.translation.list_comprehension_operations: simplify.detect_list_comprehension(graph) if not self.config.translation.verbose and not mute_dot: log.dot() self.graphs.append(graph) # store the graph in our list return graph
def buildflowgraph(self, func, mute_dot=False): """Get the flow graph for a function.""" if not isinstance(func, types.FunctionType): raise TypeError("buildflowgraph() expects a function, " "got %r" % (func, )) if func in self._prebuilt_graphs: graph = self._prebuilt_graphs.pop(func) else: if self.config.translation.verbose: log(nice_repr_for_func(func)) graph = build_flow(func) simplify.simplify_graph(graph) if self.config.translation.list_comprehension_operations: simplify.detect_list_comprehension(graph) if not self.config.translation.verbose and not mute_dot: log.dot() self.graphs.append(graph) # store the graph in our list return graph
def test_translate_enum(): cdef = """ typedef enum { mp_ass_subscript = 3, mp_length = 4, mp_subscript = 5, } Slot; """ cts = parse_source(cdef) def f(): return cts.gettype('Slot').mp_length graph = build_flow(f) simplify_graph(graph) # Check that the result is constant-folded assert graph.startblock.operations == [] [link] = graph.startblock.exits assert link.target is graph.returnblock assert link.args[0] == const(4)
def test_replace_graph_with_bootstrap(self): def func(n, x, y, z): yield n yield n # graph = build_flow(func) if option.view: graph.show() block = graph.startblock ops = block.operations assert ops[0].opname == 'simple_call' # e = Entry1() assert ops[1].opname == 'setattr' # e.g_n = n assert ops[1].args[1].value == 'g_n' assert ops[2].opname == 'setattr' # e.g_x = x assert ops[2].args[1].value == 'g_x' assert ops[3].opname == 'setattr' # e.g_y = y assert ops[3].args[1].value == 'g_y' assert ops[4].opname == 'setattr' # e.g_z = z assert ops[4].args[1].value == 'g_z' assert ops[5].opname == 'simple_call' # g = GeneratorIterator(e) assert ops[5].args[1] == ops[0].result assert len(ops) == 6 assert len(block.exits) == 1 assert block.exits[0].target is graph.returnblock
return dotgen.generate(storedir, target) def _makecharmap(): result = {} for i in range(256): result[chr(i)] = '_%02X' % i for c in 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789': result[c] = c result['_'] = '__' return result CHAR_MAP = _makecharmap() del _makecharmap def safename(name): # turn a random string into something that is a valid dot identifier, # avoiding invalid characters and prepending '_' to make sure it is # not a keyword name = ''.join([CHAR_MAP[c] for c in name]) return '_' + name if __name__ == '__main__': def f(x): i = 0 while i < x: i += 1 return i graph = build_flow(f) make_dot('f', graph)