[pypy-commit] pypy reflex-support: TString pythonization (CINT-only)
wlav
noreply at buildbot.pypy.org
Sat Aug 31 01:21:54 CEST 2013
Author: Wim Lavrijsen <WLavrijsen at lbl.gov>
Branch: reflex-support
Changeset: r66702:b04d6eba8a11
Date: 2013-08-30 14:39 -0700
http://bitbucket.org/pypy/pypy/changeset/b04d6eba8a11/
Log: TString pythonization (CINT-only)
diff --git a/pypy/module/cppyy/capi/cint_capi.py b/pypy/module/cppyy/capi/cint_capi.py
--- a/pypy/module/cppyy/capi/cint_capi.py
+++ b/pypy/module/cppyy/capi/cint_capi.py
@@ -9,6 +9,8 @@
from rpython.rtyper.lltypesystem import rffi, lltype
from rpython.rlib import libffi, rdynload
+from pypy.module.cppyy.capi.capi_types import C_OBJECT
+
__all__ = ['identify', 'std_string_name', 'eci', 'c_load_dictionary']
@@ -71,6 +73,23 @@
# CINT-specific pythonizations ===============================================
+_c_charp2TString = rffi.llexternal(
+ "cppyy_charp2TString",
+ [rffi.CCHARP], C_OBJECT,
+ threadsafe=ts_helper,
+ compilation_info=eci)
+def c_charp2TString(space, svalue):
+ charp = rffi.str2charp(svalue)
+ result = _c_charp2TString(charp)
+ rffi.free_charp(charp)
+ return result
+_c_TString2TString = rffi.llexternal(
+ "cppyy_TString2TString",
+ [C_OBJECT], C_OBJECT,
+ threadsafe=ts_helper,
+ compilation_info=eci)
+def c_TString2TString(space, cppobject):
+ return _c_TString2TString(cppobject)
def _get_string_data(space, w_obj, m1, m2 = None):
from pypy.module.cppyy import interp_cppyy
@@ -305,6 +324,33 @@
_method_alias(space, w_pycppclass, "__cmp__", "CompareTo")
_method_alias(space, w_pycppclass, "_cppyy_as_builtin", "Data")
+ # ROOT-specific converters (TODO: this is a general problem and would serve
+ # with its own API; problem is that constructing temporaries leads to recursive
+ # calls, as the copy-constructor takes a type of the same class, so uses the
+ # same converter)
+ from pypy.module.cppyy import converter
+ class TStringConverter(converter.InstanceConverter):
+ def __init__(self, space, extra):
+ from pypy.module.cppyy import interp_cppyy
+ cppclass = interp_cppyy.scope_byname(space, "TString")
+ converter.InstanceConverter.__init__(self, space, cppclass)
+
+ def _unwrap_object(self, space, w_obj):
+ from pypy.module.cppyy import interp_cppyy
+ if isinstance(w_obj, interp_cppyy.W_CPPInstance):
+ arg = converter.InstanceConverter._unwrap_object(self, space, w_obj)
+ return c_TString2TString(space, arg)
+ else:
+ return c_charp2TString(space, space.str_w(w_obj))
+
+ def free_argument(self, space, arg, call_local):
+ from pypy.module.cppyy import interp_cppyy, capi
+ capi.c_destruct(space, self.cppclass, rffi.cast(capi.C_OBJECT, rffi.cast(rffi.VOIDPP, arg)[0]))
+
+ # TODO: make an API for this
+ converter._converters["TString"] = TStringConverter
+ converter._converters["const TString&"] = TStringConverter
+
elif name == "TTree":
_method_alias(space, w_pycppclass, "_unpythonized_Branch", "Branch")
@@ -315,7 +361,7 @@
elif name[0:8] == "TVectorT": # TVectorT<> template
_method_alias(space, w_pycppclass, "__len__", "GetNoElements")
-
+
# destruction callback (needs better solution, but this is for CINT
# only and should not appear outside of ROOT-specific uses)
from pypy.module.cpyext.api import cpython_api, CANNOT_FAIL
diff --git a/pypy/module/cppyy/include/cintcwrapper.h b/pypy/module/cppyy/include/cintcwrapper.h
--- a/pypy/module/cppyy/include/cintcwrapper.h
+++ b/pypy/module/cppyy/include/cintcwrapper.h
@@ -17,6 +17,9 @@
long long cppyy_ttree_GetEntry(void* vtree, long long entry);
+ cppyy_object_t cppyy_charp2TString(const char* str);
+ cppyy_object_t cppyy_TString2TString(cppyy_object_t ptr);
+
#ifdef __cplusplus
}
#endif // ifdef __cplusplus
diff --git a/pypy/module/cppyy/src/cintcwrapper.cxx b/pypy/module/cppyy/src/cintcwrapper.cxx
--- a/pypy/module/cppyy/src/cintcwrapper.cxx
+++ b/pypy/module/cppyy/src/cintcwrapper.cxx
@@ -24,6 +24,7 @@
// for pythonization
#include "TTree.h"
#include "TBranch.h"
+#include "TString.h"
#include "Api.h"
@@ -994,3 +995,11 @@
long long cppyy_ttree_GetEntry(void* vtree, long long entry) {
return (long long)((TTree*)vtree)->GetEntry((Long64_t)entry);
}
+
+cppyy_object_t cppyy_charp2TString(const char* str) {
+ return (cppyy_object_t)new TString(str);
+}
+
+cppyy_object_t cppyy_TString2TString(cppyy_object_t ptr) {
+ return (cppyy_object_t)new TString(*(TString*)ptr);
+}
diff --git a/pypy/module/cppyy/test/test_cint.py b/pypy/module/cppyy/test/test_cint.py
--- a/pypy/module/cppyy/test/test_cint.py
+++ b/pypy/module/cppyy/test/test_cint.py
@@ -141,6 +141,29 @@
for j in v:
assert round(v[int(math.sqrt(j)+0.5)]-j, 5) == 0.
+ def test04_TStringTObjString(self):
+ """Test string/TString interchangebility"""
+
+ import cppyy
+
+ test = "aap noot mies"
+
+ s1 = cppyy.gbl.TString(test )
+ s2 = str(s1)
+
+ assert s1 == test
+ assert test == s2
+ assert s1 == s2
+
+ s3 = cppyy.gbl.TObjString(s2)
+ assert s3 == test
+ assert s2 == s3
+
+ # force use of: TNamed(const TString &name, const TString &title)
+ n = cppyy.gbl.TNamed(test, cppyy.gbl.TString("title"))
+ assert n.GetTitle() == "title"
+ assert n.GetName() == test
+
class AppTestCINTTTREE:
spaceconfig = dict(usemodules=['cppyy', '_rawffi', '_ffi', 'itertools'])
More information about the pypy-commit
mailing list