def findcycles(wrappers): """Yields all cycles in the wrappers.""" # Should probably be done as a topological sort, as that would get extra # interesting information. cycles = wrapper.ignorelist() for w in wrappers: wrappers[w]._reached = False for c in findcyclesfrom(wrappers.head, cycles, []): # Skip cycles with types or classes in (there are cycles everywhere # there), and ones with functions (e.g. f->f.func_globals->f) # Is there any use for finding cycles, really? for w in c: if w.type is type or w.type is types.FunctionType or \ w.type is types.BuiltinFunctionType: break else: yield c for w in wrappers: del wrappers[w]._reached
def scan(obj, verbosity = default): # The number of objects counted so far count = 0 sys.stdout.write("Scanning..") sys.stdout.flush() # Give out a warning about an unknown object if verbosity >= level. def unknown(level, obj): if verbosity >= level: warnings.warn("Size of %s not known" % type(obj), UnknownType) # Annotations leave lots of cyclic references, so clean them up if we can _gc_collect() wrappers = wrapper.ignoredict() queue = wrapper.ignorelist([None, obj]) while len(queue) > 0: obj = queue.pop() # Check for an already-counted object if id(obj) in wrappers: continue count += 1 if count % 1000 == 0: sys.stdout.write(".") sys.stdout.flush() t = type(obj) # Check for an object with a specific rule if id(obj) in sizes.object: constructor = sizes.object[id(obj)] # Check for a type with a specific rule elif id(t) in sizes.wholetype: constructor = sizes.wholetype[id(t)] # Go through the slow code to find or make a wrapper class else: constructor = _findwrapper(obj, t, unknown, True) sizes.wholetype[id(t)] = constructor sizes.samples[id(t)] = obj # Now generate a wrapper. w = constructor(obj) queue += w.children wrappers[id(obj)] = w # Change object IDs to wrapper references print sys.stdout.write("Lifting..") count = 0 for w in wrappers: count += 1 if count % 1000 == 0: sys.stdout.write(".") sys.stdout.flush() wrappers[w].scanfinished(wrappers) wrappers[w].liftrefs(wrappers) print return wrappers