[pypy-commit] pypy faster-rstruct-2: implement rgc.ll_for_resizable_list, which is the equivalent of llstr(), but for lists
antocuni
pypy.commits at gmail.com
Mon May 8 06:01:33 EDT 2017
Author: Antonio Cuni <anto.cuni at gmail.com>
Branch: faster-rstruct-2
Changeset: r91199:ed23f8739819
Date: 2017-05-08 12:00 +0200
http://bitbucket.org/pypy/pypy/changeset/ed23f8739819/
Log: implement rgc.ll_for_resizable_list, which is the equivalent of
llstr(), but for lists
diff --git a/rpython/rlib/rgc.py b/rpython/rlib/rgc.py
--- a/rpython/rlib/rgc.py
+++ b/rpython/rlib/rgc.py
@@ -1226,7 +1226,7 @@
list.sort(lst, *args, **kwds)
self.__from_list(lst)
- def _nonmoving_raw_ptr_for_resizable_list(self):
+ def _get_ll_list(self):
if self._ll_list is None:
existing_items = list(self)
from rpython.rtyper.lltypesystem import lltype, rffi
@@ -1237,8 +1237,11 @@
self._ll_list.items = lltype.malloc(LIST.items.TO, n)
self.__from_list(existing_items)
assert self._ll_list is not None
- return ll_nonmovable_raw_ptr_for_resizable_list(self._ll_list)
- #return self._raw_items
+ return self._ll_list
+
+ def _nonmoving_raw_ptr_for_resizable_list(self):
+ ll_list = self._get_ll_list()
+ return ll_nonmovable_raw_ptr_for_resizable_list(ll_list)
def resizable_list_supporting_raw_ptr(lst):
return _ResizableListSupportingRawPtr(lst)
@@ -1247,6 +1250,18 @@
assert isinstance(lst, _ResizableListSupportingRawPtr)
return lst._nonmoving_raw_ptr_for_resizable_list()
+def ll_for_resizable_list(lst):
+ """
+ This is the equivalent of llstr(), but for lists. It can be called only if
+ the list has been created by calling resizable_list_supporting_raw_ptr().
+
+ In theory, all the operations on lst are immediately visible also on
+ ll_list. However, support for that is incomplete in
+ _ResizableListSupportingRawPtr and as such, the pointer becomes invalid as
+ soon as you call a resizing operation on lst.
+ """
+ assert isinstance(lst, _ResizableListSupportingRawPtr)
+ return lst._get_ll_list()
def _check_resizable_list_of_chars(s_list):
from rpython.annotator import model as annmodel
@@ -1289,6 +1304,23 @@
return hop.gendirectcall(ll_nonmovable_raw_ptr_for_resizable_list,
v_list)
+class Entry(ExtRegistryEntry):
+ _about_ = ll_for_resizable_list
+
+ def compute_result_annotation(self, s_list):
+ from rpython.rtyper.llannotation import lltype_to_annotation
+ _check_resizable_list_of_chars(s_list)
+ LIST = _ResizableListSupportingRawPtr._get_lltype()
+ return lltype_to_annotation(lltype.Ptr(LIST))
+
+ def specialize_call(self, hop):
+ hop.exception_cannot_occur()
+ assert hop.args_r[0].lowleveltype == hop.r_result.lowleveltype
+ v_ll_list, = hop.inputargs(*hop.args_r)
+ return hop.genop('same_as', [v_ll_list],
+ resulttype = hop.r_result.lowleveltype)
+
+
@jit.dont_look_inside
def ll_nonmovable_raw_ptr_for_resizable_list(ll_list):
"""
diff --git a/rpython/rlib/test/test_rgc.py b/rpython/rlib/test/test_rgc.py
--- a/rpython/rlib/test/test_rgc.py
+++ b/rpython/rlib/test/test_rgc.py
@@ -304,6 +304,50 @@
data = subprocess.check_output([str(exename), '.', '.', '.'])
assert data.strip().endswith('OK!')
+def test_ll_for_resizable_list():
+ def f(n):
+ lst = ['a', 'b', 'c']
+ lst = rgc.resizable_list_supporting_raw_ptr(lst)
+ lst.append(chr(n))
+ assert lst[3] == chr(n)
+ assert lst[-1] == chr(n)
+ #
+ ll_list = rgc.ll_for_resizable_list(lst)
+ assert lst[:] == ['a', 'b', 'c', chr(n)]
+ assert ll_list.length == 4
+ assert [ll_list.items[i] for i in range(4)] == ['a', 'b', 'c', chr(n)]
+ #
+ lst[-3] = 'X'
+ assert ll_list.items[1] == 'X'
+ ll_list.items[2] = 'Y'
+ assert lst[-2] == 'Y'
+ #
+ return lst
+ #
+ # direct untranslated run
+ lst = f(35)
+ assert isinstance(lst, rgc._ResizableListSupportingRawPtr)
+ #
+ # llinterp run
+ interpret(f, [35])
+ #
+ # compilation with the GC transformer
+ import subprocess
+ from rpython.translator.interactive import Translation
+ #
+ def main(argv):
+ f(len(argv))
+ print "OK!"
+ return 0
+ #
+ t = Translation(main, gc="incminimark")
+ t.disable(['backendopt'])
+ t.set_backend_extra_options(c_debug_defines=True)
+ exename = t.compile()
+ data = subprocess.check_output([str(exename), '.', '.', '.'])
+ assert data.strip().endswith('OK!')
+
+
def test_ListSupportingRawPtr_direct():
lst = ['a', 'b', 'c']
lst = rgc.resizable_list_supporting_raw_ptr(lst)
@@ -353,7 +397,8 @@
check_nonresizing()
assert lst._ll_list is None
p = lst._nonmoving_raw_ptr_for_resizable_list()
- ll_list = lst._ll_list
+ ll_list = rgc.ll_for_resizable_list(lst)
+ assert ll_list is lst._ll_list
check_nonresizing()
assert lst._ll_list == ll_list
assert p[0] == ll_list.items[0] == 'a'
More information about the pypy-commit
mailing list