Author: Stephan <[email protected]>
Branch:
Changeset: r87:2b700db2bfa5
Date: 2011-05-19 17:53 +0200
http://bitbucket.org/pypy/lang-js/changeset/2b700db2bfa5/
Log: added jit and annotations
diff --git a/js/interpreter.py b/js/interpreter.py
--- a/js/interpreter.py
+++ b/js/interpreter.py
@@ -18,6 +18,7 @@
from pypy.rlib.rfloat import NAN, INFINITY, isnan, isinf
from pypy.rlib.objectmodel import specialize
from pypy.rlib.listsort import TimSort
+from pypy.rlib import jit
ASTBUILDER = ASTBuilder()
@@ -32,6 +33,7 @@
return w_Undefined
return f
[email protected]_look_inside
def load_source(script_source, sourcename):
temp_tree = parse(script_source)
ASTBUILDER.sourcename = sourcename
diff --git a/js/jscode.py b/js/jscode.py
--- a/js/jscode.py
+++ b/js/jscode.py
@@ -12,11 +12,20 @@
from pypy.rlib.rarithmetic import intmask
from pypy.rlib.objectmodel import we_are_translated
+from pypy.rlib.jit import JitDriver, purefunction
+
+def get_printable_location(pc, jsfunction):
+ return str(jsfunction.opcodes[pc])
+
+jitdriver = JitDriver(greens=['pc', 'self'], reds=['to_pop', 'stack', 'ctx'],
get_printable_location = get_printable_location, virtualizables=['stack'])
+
class AlreadyRun(Exception):
pass
class Stack(object):
+ _virtualizable2_ = ['content[*]', 'pointer']
def __init__(self, size):
+ self = hint(self, access_directly = True, fresh_virtualizable = True)
self.content = [None] * size
self.pointer = 0
@@ -172,6 +181,8 @@
return "\n".join([repr(i) for i in self.opcodes])
class JsFunction(object):
+ _immutable_fields_ = ["opcodes[*]"]
+
def __init__(self, name, params, code):
from pypy.rlib.debug import make_sure_not_resized
self.name = name
@@ -185,12 +196,20 @@
except ReturnException, e:
return e.value
+ def _get_opcode(self, pc):
+ assert pc >= 0
+ return self.opcodes[pc]
+
def run_bytecode(self, ctx, stack, check_stack=True):
- i = 0
+ pc = 0
to_pop = 0
try:
- while i < len(self.opcodes):
- opcode = self.opcodes[i]
+ while True:
+ jitdriver.jit_merge_point(pc=pc, stack=stack, self=self,
ctx=ctx, to_pop=to_pop)
+ if pc >= len(self.opcodes):
+ break
+
+ opcode = self._get_opcode(pc)
#if we_are_translated():
# #this is an optimization strategy for translated code
# #on top of cpython it destroys the performance
@@ -206,9 +225,14 @@
assert result is None
if isinstance(opcode, BaseJump):
- i = opcode.do_jump(stack, i)
+ new_pc = opcode.do_jump(stack, pc)
+ condition = new_pc < pc
+ pc = new_pc
+ if condition:
+ jitdriver.can_enter_jit(pc=pc, stack=stack, self=self,
ctx=ctx, to_pop=to_pop)
+ continue
else:
- i += 1
+ pc += 1
if isinstance(opcode, WITH_START):
to_pop += 1
elif isinstance(opcode, WITH_END):
@@ -265,6 +289,7 @@
stack.append(w_Undefined)
class LOAD_INTCONSTANT(Opcode):
+ _immutable_fields_ = ['w_intvalue']
def __init__(self, value):
self.w_intvalue = W_IntNumber(int(value))
@@ -313,6 +338,7 @@
stack.append(w_Null)
class LOAD_VARIABLE(Opcode):
+ _immutable_fields_ = ['identifier']
def __init__(self, identifier):
self.identifier = identifier
@@ -656,6 +682,7 @@
return sub(ctx, prev, value)
class BaseStore(Opcode):
+ _immutable_fields_ = ['name']
def __init__(self, name):
self.name = name
@@ -766,6 +793,7 @@
return 'LABEL %d' % (self.num,)
class BaseJump(Opcode):
+ _immutable_fields_ = ['where']
def __init__(self, where):
self.where = where
self.decision = False
diff --git a/js/jsobj.py b/js/jsobj.py
--- a/js/jsobj.py
+++ b/js/jsobj.py
@@ -10,6 +10,8 @@
RO = 4
IT = 8
+from pypy.rlib import jit
+
class SeePage(NotImplementedError):
pass
@@ -372,6 +374,7 @@
self.set_length(arrayindex+1)
class W_Boolean(W_Primitive):
+ _immutable_fields_ = ['boolval']
def __init__(self, boolval):
self.boolval = bool(boolval)
@@ -454,6 +457,7 @@
return 'number'
class W_IntNumber(W_BaseNumber):
+ _immutable_fields_ = ['intval']
""" Number known to be an integer
"""
def __init__(self, intval):
@@ -490,6 +494,7 @@
return intmask(rffi.cast(rffi.UINT, n))
class W_FloatNumber(W_BaseNumber):
+ _immutable_fields_ = ['floatval']
""" Number known to be a float
"""
def __init__(self, floatval):
@@ -631,6 +636,7 @@
"""remove the last pushed object"""
return self.scope.pop()
+ @jit.unroll_safe
def resolve_identifier(self, ctx, identifier):
for i in range(len(self.scope)-1, -1, -1):
obj = self.scope[i]
diff --git a/js/targetjsstandalone.py b/js/targetjsstandalone.py
--- a/js/targetjsstandalone.py
+++ b/js/targetjsstandalone.py
@@ -27,5 +27,9 @@
driver.exe_name = 'js-%(backend)s'
return entry_point, None
+def jitpolicy(driver):
+ from pypy.jit.codewriter.policy import JitPolicy
+ return JitPolicy()
+
if __name__ == '__main__':
entry_point(sys.argv)
diff --git a/js/test/jit.py b/js/test/jit.py
new file mode 100644
--- /dev/null
+++ b/js/test/jit.py
@@ -0,0 +1,34 @@
+import sys
+from pypy import conftest
+class o:
+ view = False
+ viewloops = True
+conftest.option = o
+
+from pypy.jit.metainterp.test.test_basic import LLJitMixin
+
+from js import interpreter
+from js.jscode import JsCode, jitdriver
+from js.jsobj import ExecutionContext
+
+class TestLLtype(LLJitMixin):
+ def test_append(self):
+ code = """
+ function f() {
+ for(i = 0; i < 100; i++){
+ }
+ }
+ f();
+ """
+ jsint = interpreter.Interpreter()
+ ctx = jsint.w_Global
+ bytecode = JsCode()
+ interpreter.load_source(code, '').emit(bytecode)
+ func = bytecode.make_js_function()
+
+ def interp_w(c):
+ jitdriver.set_param("inlining", True)
+ code_val = func.run(ExecutionContext([ctx]))
+ interp_w(1)
+ self.meta_interp(interp_w, [6], listcomp=True, backendopt=True,
listops=True)
+
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit