def test_float_conversion_implicit(self): def f(ii): return 1.0 + ii res = self.interpret(f, [r_int64(100000000)]) assert type(res) is float assert res == 100000001. res = self.interpret(f, [r_int64(1234567890123456789)]) assert type(res) is float assert self.float_eq(res, 1.2345678901234568e+18)
def test_str_of_longlong(self): def f(i): return str(i) res = self.interpret(f, [r_int64(0)]) assert self.ll_to_string(res) == '0' res = self.interpret(f, [r_int64(413974738222117)]) assert self.ll_to_string(res) == '413974738222117'
def __init__(self): self.check_frequency = -1 # NB. use of r_int64 to be extremely far on the safe side: # this is increasing by one after each loop or bridge is # compiled, and it must not overflow. If the backend implements # complete freeing in cpu.free_loop_and_bridges(), then it may # be possible to get arbitrary many of them just by waiting long # enough. But in this day and age, you'd still never have the # patience of waiting for a slowly-increasing 64-bit number to # overflow :-) # According to my estimates it's about 5e9 years given 1000 loops # per second self.current_generation = r_int64(1) self.next_check = r_int64(-1) self.alive_loops = {}
def set_max_age(self, max_age, check_frequency=0): if max_age <= 0: self.next_check = r_int64(-1) else: self.max_age = max_age if check_frequency <= 0: check_frequency = int(math.sqrt(max_age)) self.check_frequency = check_frequency self.next_check = self.current_generation + 1
def test_hash(self): def f(x): return objectmodel.compute_hash(x) res = self.interpret(f, [123456789]) assert res == 123456789 res = self.interpret(f, [r_int64(123456789012345678)]) if sys.maxint == 2147483647: # check the way we compute such a hash so far assert res == -1506741426 + 9 * 28744523 else: assert res == 123456789012345678
def test_isinstance_vs_int_types(self): class FakeSpace(object): def wrap(self, x): if x is None: return [None] if isinstance(x, str): return x if isinstance(x, r_int64): return int(x) return "XXX" wrap._annspecialcase_ = 'specialize:argtype(0)' space = FakeSpace() def wrap(x): return space.wrap(x) res = self.interpret(wrap, [r_int64(0)]) assert res == 0
class JitCellToken(AbstractDescr): """Used for rop.JUMP, giving the target of the jump. This is different from TreeLoop: the TreeLoop class contains the whole loop, including 'operations', and goes away after the loop was compiled; but the LoopDescr remains alive and points to the generated assembler. """ target_tokens = None failed_states = None retraced_count = 0 terminating = False # see TerminatingLoopToken in compile.py invalidated = False outermost_jitdriver_sd = None # and more data specified by the backend when the loop is compiled number = -1 generation = r_int64(0) # one purpose of LoopToken is to keep alive the CompiledLoopToken # returned by the backend. When the LoopToken goes away, the # CompiledLoopToken has its __del__ called, which frees the assembler # memory and the ResumeGuards. compiled_loop_token = None def __init__(self): # For memory management of assembled loops self._keepalive_jitcell_tokens = {} # set of other JitCellToken def record_jump_to(self, jitcell_token): assert isinstance(jitcell_token, JitCellToken) self._keepalive_jitcell_tokens[jitcell_token] = None def __repr__(self): return '<Loop %d, gen=%d>' % (self.number, self.generation) def repr_of_descr(self): return '<Loop%d>' % self.number def dump(self): self.compiled_loop_token.cpu.dump_loop_token(self)
def test_downcast_int(self): def f(i): return int(i) res = self.interpret(f, [r_int64(0)]) assert res == 0
def g(n): if n > 0: return f(r_int64(0)) else: return f(0)