[pypy-commit] lang-smalltalk default: added STRING_REPLACE primitive(105) and test

lwassermann noreply at buildbot.pypy.org
Wed Feb 27 14:08:33 CET 2013


Author: Lars Wassermann <lars.wassermann at gmail.com>
Branch: 
Changeset: r103:c395af8c249f
Date: 2013-02-27 14:06 +0100
http://bitbucket.org/pypy/lang-smalltalk/changeset/c395af8c249f/

Log:	added STRING_REPLACE primitive(105) and test

diff --git a/spyvm/primitives.py b/spyvm/primitives.py
--- a/spyvm/primitives.py
+++ b/spyvm/primitives.py
@@ -496,6 +496,31 @@
     interp.space.objtable['w_display'] = w_rcvr
     return w_rcvr
 
+ at expose_primitive(STRING_REPLACE, unwrap_spec=[object, index1_0, index1_0, object, index1_0])
+def func(interp, s_frame, w_rcvr, start, stop, w_replacement, repStart):
+    """replaceFrom: start to: stop with: replacement startingAt: repStart 
+    Primitive. This destructively replaces elements from start to stop in the 
+    receiver starting at index, repStart, in the collection, replacement. Answer 
+    the receiver. Range checks are performed in the primitive only. Essential 
+    for Pharo Candle Symbols.
+    | index repOff |
+    repOff := repStart - start.
+    index := start - 1.
+    [(index := index + 1) <= stop]
+        whileTrue: [self at: index put: (replacement at: repOff + index)]"""
+    if (start < 0 or start - 1 > stop or repStart < 0):
+        raise PrimitiveFailedError()
+    if w_rcvr.__class__ is not w_replacement.__class__:
+        raise PrimitiveFailedError()
+    if (w_rcvr.size() <= stop
+            or w_replacement.size() < repStart + (stop - start)):
+        raise PrimitiveFailedError()
+    repOff = repStart - start
+    for i0 in range(start, stop + 1):
+        w_rcvr.atput0(interp.space, i0, w_replacement.at0(interp.space, repOff + i0))
+    return w_rcvr
+
+
 @expose_primitive(SCREEN_SIZE, unwrap_spec=[object])
 def func(interp, s_frame, w_rcvr):
     # XXX get the real screen size
diff --git a/spyvm/test/test_primitives.py b/spyvm/test/test_primitives.py
--- a/spyvm/test/test_primitives.py
+++ b/spyvm/test/test_primitives.py
@@ -446,8 +446,8 @@
     from test_interpreter import new_frame
     w_frame, s_frame = new_frame("<never called, but used for method generation>",
             space=space)
-    w_block = prim(200, map(wrap, ["anActiveContext", 2, [wrap(1), wrap(2)]]), 
-            w_frame)
+    w_block = prim(primitives.CLOSURE_COPY_WITH_COPIED_VALUES, map(wrap, 
+                    ["anActiveContext", 2, [wrap(1), wrap(2)]]), w_frame)
     assert w_block is not space.w_nil
     w_w_block = wrapper.BlockClosureWrapper(space, w_block)
     assert w_w_block.startpc() is 0
@@ -455,6 +455,20 @@
     assert w_w_block.at0(1) == wrap(2)
     assert w_w_block.numArgs() is 2
 
+def test_primitive_string_copy():
+    w_r = prim(primitives.STRING_REPLACE, ["aaaaa", 1, 5, "ababab", 1])
+    assert w_r.as_string() == "ababa"
+    w_r = prim(primitives.STRING_REPLACE, ["aaaaa", 1, 5, "ababab", 2])
+    assert w_r.as_string() == "babab"
+    w_r = prim(primitives.STRING_REPLACE, ["aaaaa", 2, 5, "ccccc", 1])
+    assert w_r.as_string() == "acccc"
+    w_r = prim(primitives.STRING_REPLACE, ["aaaaa", 2, 4, "ccccc", 1])
+    assert w_r.as_string() == "accca"
+    prim_fails(primitives.STRING_REPLACE, ["aaaaa", 0, 4, "ccccc", 1])
+    prim_fails(primitives.STRING_REPLACE, ["aaaaa", 1, 6, "ccccc", 2])
+    prim_fails(primitives.STRING_REPLACE, ["aaaaa", 2, 6, "ccccc", 1])
+    prim_fails(primitives.STRING_REPLACE, [['a', 'b'], 1, 4, "ccccc", 1])
+
 def build_up_closure_environment(args, copiedValues=[]):
     from test_interpreter import new_frame
     w_frame, s_initial_context = new_frame("<never called, but used for method generation>",
@@ -465,7 +479,7 @@
                                 size_arguments, copiedValues)
     s_initial_context.push_all([closure] + args)
     interp = interpreter.Interpreter(space)
-    w_active_context = prim_table[201 + size_arguments](interp, s_initial_context, size_arguments)
+    w_active_context = prim_table[primitives.CLOSURE_VALUE + size_arguments](interp, s_initial_context, size_arguments)
     return s_initial_context, closure, w_active_context.as_context_get_shadow(space)
 
 def test_primitive_closure_value():


More information about the pypy-commit mailing list