[pypy-svn] r52544 - in pypy/branch/jit-refactoring/pypy/lang/js: . test
fijal at codespeak.net
fijal at codespeak.net
Sat Mar 15 02:28:52 CET 2008
Author: fijal
Date: Sat Mar 15 02:28:50 2008
New Revision: 52544
Modified:
pypy/branch/jit-refactoring/pypy/lang/js/baseop.py
pypy/branch/jit-refactoring/pypy/lang/js/interpreter.py
pypy/branch/jit-refactoring/pypy/lang/js/jscode.py
pypy/branch/jit-refactoring/pypy/lang/js/jsobj.py
pypy/branch/jit-refactoring/pypy/lang/js/operations.py
pypy/branch/jit-refactoring/pypy/lang/js/test/test_interp.py
pypy/branch/jit-refactoring/pypy/lang/js/test/test_parser.py
Log:
More tests passing.
Modified: pypy/branch/jit-refactoring/pypy/lang/js/baseop.py
==============================================================================
--- pypy/branch/jit-refactoring/pypy/lang/js/baseop.py (original)
+++ pypy/branch/jit-refactoring/pypy/lang/js/baseop.py Sat Mar 15 02:28:50 2008
@@ -3,6 +3,8 @@
"""
from pypy.lang.js.jsobj import W_String, W_IntNumber, W_FloatNumber
+from pypy.rlib.rarithmetic import r_uint, intmask, INFINITY, NAN, ovfcheck,\
+ isnan, isinf
def plus(ctx, nleft, nright):
if isinstance(nleft, W_String) or isinstance(nright, W_String):
@@ -21,3 +23,15 @@
fleft = nleft.ToNumber()
fright = nright.ToNumber()
return W_FloatNumber(fleft + fright)
+
+def sub(ctx, nleft, nright):
+ if isinstance(nleft, W_IntNumber) and isinstance(nright, W_IntNumber):
+ ileft = nleft.ToInt32()
+ iright = nright.ToInt32()
+ try:
+ return W_IntNumber(ovfcheck(ileft - iright))
+ except OverflowError:
+ return W_FloatNumber(float(ileft) - float(iright))
+ fleft = nleft.ToNumber()
+ fright = nright.ToNumber()
+ return W_FloatNumber(fleft - fright)
Modified: pypy/branch/jit-refactoring/pypy/lang/js/interpreter.py
==============================================================================
--- pypy/branch/jit-refactoring/pypy/lang/js/interpreter.py (original)
+++ pypy/branch/jit-refactoring/pypy/lang/js/interpreter.py Sat Mar 15 02:28:50 2008
@@ -9,6 +9,7 @@
from pypy.lang.js.execution import ThrowException, JsTypeError
from pypy.rlib.objectmodel import we_are_translated
from pypy.rlib.streamio import open_file_as_stream
+from pypy.lang.js.jscode import JsCode
ASTBUILDER = ASTBuilder()
@@ -551,7 +552,10 @@
def run(self, script):
"""run the interpreter"""
- return script.execute(self.global_context)
+ bytecode = JsCode()
+ script.emit(bytecode)
+ bytecode.run(self.global_context)
+ # XXX not sure what this should return
def wrap_arguments(pyargs):
"receives a list of arguments and wrap then in their js equivalents"
Modified: pypy/branch/jit-refactoring/pypy/lang/js/jscode.py
==============================================================================
--- pypy/branch/jit-refactoring/pypy/lang/js/jscode.py (original)
+++ pypy/branch/jit-refactoring/pypy/lang/js/jscode.py Sat Mar 15 02:28:50 2008
@@ -1,7 +1,9 @@
-from pypy.lang.js.jsobj import W_IntNumber, W_FloatNumber, W_String
+from pypy.lang.js.jsobj import W_IntNumber, W_FloatNumber, W_String,\
+ W_Array, W_PrimitiveObject, W_Reference, ActivationObject
+from pypy.lang.js.execution import JsTypeError
from pypy.rlib.unroll import unrolling_iterable
-from pypy.lang.js.baseop import plus
+from pypy.lang.js.baseop import plus, sub
class AlreadyRun(Exception):
pass
@@ -128,8 +130,8 @@
def __init__(self, value):
self.w_intvalue = W_IntNumber(int(value))
- def eval(self, ctx):
- return self.w_intvalue
+ def eval(self, ctx, stack):
+ stack.append(self.w_intvalue)
def __repr__(self):
return 'LOAD_INTCONSTANT %s' % (self.w_intvalue.intval,)
@@ -148,8 +150,8 @@
def __init__(self, value):
self.w_stringvalue = W_String(value)
- def eval(self, ctx):
- return self.w_stringvalue
+ def eval(self, ctx, stack):
+ stack.append(self.w_stringvalue)
def get_literal(self):
return W_String(self.strval).ToString()
@@ -161,8 +163,8 @@
def __init__(self, identifier):
self.identifier = identifier
- def eval(self, ctx):
- return ctx.resolve_identifier(self.identifier)
+ def eval(self, ctx, stack):
+ stack.append(ctx.resolve_identifier(self.identifier).GetValue())
def __repr__(self):
return 'LOAD_VARIABLE "%s"' % (self.identifier,)
@@ -171,12 +173,12 @@
def __init__(self, counter):
self.counter = counter
- def eval(self, ctx):
+ def eval(self, ctx, stack):
proto = ctx.get_global().Get('Array').Get('prototype')
array = W_Array(ctx, Prototype=proto, Class = proto.Class)
- for i in range(len(self.nodes)):
- array.Put(str(i), self.nodes[i].eval(ctx).GetValue())
- return array
+ for i in range(self.counter):
+ array.Put(str(self.counter - i - 1), stack.pop().GetValue())
+ stack.append(array)
def __repr__(self):
return 'LOAD_ARRAY %d' % (self.counter,)
@@ -196,8 +198,10 @@
def __init__(self, name):
self.name = name
- def eval(self, ctx):
- XXX
+ def eval(self, ctx, stack):
+ value = stack.pop().GetValue()
+ ctx.assign(self.name, value)
+ stack.append(value)
def __repr__(self):
return 'STORE "%s"' % self.name
@@ -206,11 +210,15 @@
def __init__(self, listofnames):
self.listofnames = listofnames
+ def eval(self, ctx, stack):
+ XXX
+
def __repr__(self):
return 'LOAD_OBJECT %r' % (self.listofnames,)
class SUB(BaseBinaryOperation):
- pass
+ def operation(self, ctx, left, right):
+ return sub(ctx, left, right)
class ADD(BaseBinaryOperation):
def operation(self, ctx, left, right):
@@ -302,7 +310,30 @@
pass
class POP(Opcode):
- pass
+ def eval(self, ctx, stack):
+ stack.pop()
+
+class CALL(Opcode):
+ def eval(self, ctx, stack):
+ r1 = stack.pop()
+ args = stack.pop()
+ r3 = r1.GetValue()
+ if not isinstance(r3, W_PrimitiveObject):
+ raise ThrowException(W_String("it is not a callable"))
+
+ if isinstance(r1, W_Reference):
+ r6 = r1.GetBase()
+ else:
+ r6 = None
+ if isinstance(args, ActivationObject):
+ r7 = None
+ else:
+ r7 = r6
+ try:
+ res = r3.Call(ctx=ctx, args=args.tolist(), this=r7)
+ except JsTypeError:
+ raise ThrowException(W_String('it is not a function'))
+ stack.append(res)
OpcodeMap = {}
Modified: pypy/branch/jit-refactoring/pypy/lang/js/jsobj.py
==============================================================================
--- pypy/branch/jit-refactoring/pypy/lang/js/jsobj.py (original)
+++ pypy/branch/jit-refactoring/pypy/lang/js/jsobj.py Sat Mar 15 02:28:50 2008
@@ -496,7 +496,6 @@
self.this = scope[-1]
else:
self.this = this
- # create a fast lookup
if variable is None:
self.variable = self.scope[0]
else:
@@ -512,7 +511,13 @@
return "<ExCtx %s, var: %s>"%(self.scope, self.variable)
def assign(self, name, value):
- pass
+ for obj in self.scope:
+ assert isinstance(obj, W_PrimitiveObject)
+ if obj.HasProperty(name):
+ obj.Put(name, value)
+ return
+ # if not, we need to put this thing in current scope
+ self.scope[0].Put(name, value)
def get_global(self):
return self.scope[-1]
@@ -573,11 +578,13 @@
self.base = base
self.property_name = property_name
- def GetValue(self):
+ def check_empty(self):
if self.base is None:
exception = "ReferenceError: %s is not defined"%(self.property_name,)
- raise ThrowException(W_String(exception))
-
+ raise ThrowException(W_String(exception))
+
+ def GetValue(self):
+ self.check_empty()
return self.base.Get(self.property_name)
def PutValue(self, w, ctx):
Modified: pypy/branch/jit-refactoring/pypy/lang/js/operations.py
==============================================================================
--- pypy/branch/jit-refactoring/pypy/lang/js/operations.py (original)
+++ pypy/branch/jit-refactoring/pypy/lang/js/operations.py Sat Mar 15 02:28:50 2008
@@ -9,8 +9,6 @@
W_PrimitiveObject, W_Reference, ActivationObject, W_Array, W_Boolean,\
w_Null, W_BaseNumber, isnull_or_undefined
from pypy.rlib.parsing.ebnfparse import Symbol, Nonterminal
-from pypy.rlib.rarithmetic import r_uint, intmask, INFINITY, NAN, ovfcheck,\
- isnan, isinf
from pypy.lang.js.execution import ExecutionReturned, JsTypeError,\
ThrowException
from pypy.lang.js.jscode import JsCode, JsFunction
@@ -262,27 +260,16 @@
-class Call(BinaryOp):
- def eval(self, ctx):
- r1 = self.left.eval(ctx)
- r2 = self.right.eval(ctx)
- r3 = r1.GetValue()
- if not isinstance(r3, W_PrimitiveObject):
- raise ThrowException(W_String("it is not a callable"))
-
- if isinstance(r1, W_Reference):
- r6 = r1.GetBase()
- else:
- r6 = None
- if isinstance(r2, ActivationObject):
- r7 = None
- else:
- r7 = r6
- try:
- res = r3.Call(ctx=ctx, args=r2.get_args(), this=r7)
- except JsTypeError:
- raise ThrowException(W_String('it is not a function'))
- return res
+class Call(Expression):
+ def __init__(self, pos, left, args):
+ self.pos = pos
+ self.left = left
+ self.args = args
+
+ def emit(self, bytecode):
+ self.args.emit(bytecode)
+ self.left.emit(bytecode)
+ bytecode.emit('CALL')
class Comma(BinaryOp):
def eval(self, ctx):
@@ -707,6 +694,10 @@
def eval(self, ctx):
return W_List([node.eval(ctx).GetValue() for node in self.nodes])
+ def emit(self, bytecode):
+ for node in self.nodes:
+ node.emit(bytecode)
+ bytecode.emit('LOAD_ARRAY', len(self.nodes))
##############################################################################
#
@@ -755,18 +746,6 @@
val = fleft / fright
return W_FloatNumber(val)
-def sub(ctx, nleft, nright):
- if isinstance(nleft, W_IntNumber) and isinstance(nright, W_IntNumber):
- ileft = nleft.ToInt32()
- iright = nright.ToInt32()
- try:
- return W_IntNumber(ovfcheck(ileft - iright))
- except OverflowError:
- return W_FloatNumber(float(ileft) - float(iright))
- fleft = nleft.ToNumber()
- fright = nright.ToNumber()
- return W_FloatNumber(fleft - fright)
-
class Plus(BinaryNumberOp):
operation_name = 'ADD'
@@ -914,6 +893,10 @@
for node in self.nodes:
node.emit(bytecode)
+ # we don't need to pop after certain instructions, let's
+ # list them
+ if not isinstance(node, Return):
+ bytecode.emit('POP')
def execute(self, ctx):
for varname in self.var_decl:
@@ -941,9 +924,8 @@
self.pos = pos
self.body = body
- def execute(self, ctx):
- return self.body.execute(ctx)
-
+ def emit(self, bytecode):
+ self.body.emit(bytecode)
class Return(Statement):
def __init__(self, pos, expr):
Modified: pypy/branch/jit-refactoring/pypy/lang/js/test/test_interp.py
==============================================================================
--- pypy/branch/jit-refactoring/pypy/lang/js/test/test_interp.py (original)
+++ pypy/branch/jit-refactoring/pypy/lang/js/test/test_interp.py Sat Mar 15 02:28:50 2008
@@ -4,7 +4,7 @@
from pypy.lang.js.operations import AEC, IntNumber, FloatNumber, Position, Plus
from pypy.lang.js.jsobj import W_Object, ExecutionContext, W_Root, w_Null
from pypy.lang.js.execution import ThrowException
-from pypy.lang.js.jscode import JsCode
+from pypy.lang.js.jscode import JsCode, POP
def test_simple():
bytecode = JsCode()
@@ -33,7 +33,13 @@
jsint = interpreter.Interpreter()
ctx = jsint.w_Global
try:
- code_val = jsint.run(interpreter.load_source(code, '')).GetValue()
+ bytecode = JsCode()
+ interpreter.load_source(code, '').emit(bytecode)
+ # XXX terrible hack
+ assert isinstance(bytecode.opcodes[-1], POP)
+ bytecode.opcodes.pop()
+ bytecode.run(ExecutionContext([ctx]), check_stack=False)
+ code_val = bytecode.stack[0].GetValue()
except ThrowException, excpt:
code_val = excpt.exception
print code_val, value
@@ -52,7 +58,6 @@
jsint = interpreter.Interpreter()
py.test.raises(value, 'jsint.run(interpreter.load_source(code, ""))')
-
def test_interp_parse():
yield assertv, "1+1;", 2
yield assertp, "print(1+2+3); print(1);", ["6", "1"]
Modified: pypy/branch/jit-refactoring/pypy/lang/js/test/test_parser.py
==============================================================================
--- pypy/branch/jit-refactoring/pypy/lang/js/test/test_parser.py (original)
+++ pypy/branch/jit-refactoring/pypy/lang/js/test/test_parser.py Sat Mar 15 02:28:50 2008
@@ -442,14 +442,23 @@
def test_function_decl(self):
self.check('function f(x, y, z) {x;}',
- ['DECLARE_FUNCTION f [\'x\', \'y\', \'z\'] [\n LOAD_VARIABLE "x"\n]'])
+ ['DECLARE_FUNCTION f [\'x\', \'y\', \'z\'] [\n LOAD_VARIABLE "x"\n POP\n]'])
def test_function_expression(self):
self.check('var x = function() {return x}',[
'DECLARE_VAR "x"',
'DECLARE_FUNCTION [] [\n LOAD_VARIABLE "x"\n RETURN\n]',
'LOAD_FUNCTION',
- 'STORE "x"'])
+ 'STORE "x"',
+ 'POP'])
+
+ def test_call(self):
+ self.check('print("stuff")',[
+ 'LOAD_STRINGCONSTANT "stuff"',
+ 'LOAD_ARRAY 1',
+ 'LOAD_VARIABLE "print"',
+ 'CALL',
+ 'POP'])
from pypy.lang.js.jsparser import parse
More information about the Pypy-commit
mailing list