[pypy-commit] pypy faster-rstruct: merge heads
antocuni
noreply at buildbot.pypy.org
Mon Nov 23 18:58:30 EST 2015
Author: Antonio Cuni <anto.cuni at gmail.com>
Branch: faster-rstruct
Changeset: r80875:c9ab4be2f15b
Date: 2015-11-24 00:59 +0100
http://bitbucket.org/pypy/pypy/changeset/c9ab4be2f15b/
Log: merge heads
diff --git a/rpython/rlib/rstruct/standardfmttable.py b/rpython/rlib/rstruct/standardfmttable.py
--- a/rpython/rlib/rstruct/standardfmttable.py
+++ b/rpython/rlib/rstruct/standardfmttable.py
@@ -12,7 +12,7 @@
from rpython.rlib.rstruct import ieee
from rpython.rlib.rstruct.error import StructError, StructOverflowError
from rpython.rlib.unroll import unrolling_iterable
-from rpython.rlib.strstorage import str_storage_getitem
+from rpython.rlib.strstorage import str_storage_getitem, str_storage_supported
from rpython.rlib import rarithmetic
from rpython.rtyper.lltypesystem import rffi
@@ -185,6 +185,13 @@
data = fmtiter.read(size)
fmtiter.appendobj(ieee.unpack_float(data, fmtiter.bigendian))
return
+ if not str_storage_supported(TYPE):
+ # this happens e.g. on win32 and ARM32: we cannot read the string
+ # content as an array of doubles because it's not properly
+ # aligned. But we can read a longlong and convert to float
+ assert TYPE == rffi.DOUBLE
+ assert rffi.sizeof(TYPE) == 8
+ return unpack_longlong2float(fmtiter)
try:
# fast path
val = unpack_fastpath(TYPE)(fmtiter)
@@ -195,6 +202,16 @@
fmtiter.appendobj(float(val))
return unpack_ieee
+ at specialize.argtype(0)
+def unpack_longlong2float(fmtiter):
+ from rpython.rlib.rstruct.runpack import runpack
+ from rpython.rlib.longlong2float import longlong2float
+ s = fmtiter.read(8)
+ llval = runpack('q', s) # this is a bit recursive, I know
+ doubleval = longlong2float(llval)
+ fmtiter.appendobj(doubleval)
+
+
unpack_double = make_ieee_unpacker(rffi.DOUBLE)
unpack_float = make_ieee_unpacker(rffi.FLOAT)
@@ -229,7 +246,7 @@
@specialize.argtype(0)
def unpack_int_fastpath_maybe(fmtiter):
- if fmtiter.bigendian != native_is_bigendian:
+ if fmtiter.bigendian != native_is_bigendian or not str_storage_supported(TYPE):
return False
try:
intvalue = unpack_fastpath(TYPE)(fmtiter)
diff --git a/rpython/rlib/strstorage.py b/rpython/rlib/strstorage.py
--- a/rpython/rlib/strstorage.py
+++ b/rpython/rlib/strstorage.py
@@ -32,6 +32,18 @@
from rpython.rtyper.annlowlevel import llstr
from rpython.rlib.objectmodel import specialize
+def compute_offsetof(TP, field):
+ """
+ NOT_RPYTHON
+ """
+ obj = lltype.malloc(TP, 0)
+ baseadr = llmemory.cast_ptr_to_adr(obj)
+ offset = llmemory.offsetof(TP, field)
+ interioradr = baseadr + offset
+ return (llmemory.cast_adr_to_int(interioradr, 'forced') -
+ llmemory.cast_adr_to_int(baseadr, 'forced'))
+
+
@specialize.memo()
def rpy_string_as_type(TP):
# sanity check that STR is actually what we think it is
@@ -42,8 +54,19 @@
STR_AS_TP = lltype.GcStruct('rpy_string_as_%s' % TP,
('hash', lltype.Signed),
('chars', lltype.Array(TP, hints={'immutable': True})))
+ # sanity check
+ assert compute_offsetof(STR, 'chars') == compute_offsetof(STR_AS_TP, 'chars')
return STR_AS_TP
+ at specialize.memo()
+def str_storage_supported(TP):
+ try:
+ rpy_string_as_type(TP)
+ except AssertionError:
+ return False
+ else:
+ return True
+
@specialize.ll()
def str_storage_getitem(TP, s, index):
STR_AS_TP = rpy_string_as_type(TP)
diff --git a/rpython/rlib/test/test_strstorage.py b/rpython/rlib/test/test_strstorage.py
--- a/rpython/rlib/test/test_strstorage.py
+++ b/rpython/rlib/test/test_strstorage.py
@@ -1,7 +1,7 @@
import py
import struct
from rpython.rtyper.lltypesystem import lltype, rffi
-from rpython.rlib.strstorage import str_storage_getitem
+from rpython.rlib.strstorage import str_storage_getitem, str_storage_supported
from rpython.rlib.rarithmetic import r_singlefloat
from rpython.rtyper.test.tool import BaseRtypingTest
@@ -22,6 +22,8 @@
assert int(x) == 43
def test_float(self):
+ if not str_storage_supported(lltype.Float):
+ py.test.skip('str_storage_getitem(lltype.Float) not supported on this machine')
buf = struct.pack('@dd', 12.3, 45.6)
size = struct.calcsize('@d')
assert self.str_storage_getitem(lltype.Float, buf, 0) == 12.3
More information about the pypy-commit
mailing list