From nickm at sitius.com Tue Jul 1 00:23:24 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Mon, 30 Jun 2003 18:23:24 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> Message-ID: <3F00B85C.FD8AD186@sitius.com> I've attached test files. > OK, I don't understand this. Isn't the 2nd constructor redundant? Yes it is but, having it makes certain calls more efficient (it's cheating, in a way ), see the commented section in the py-file, may be def with args can be made so it is really redundant. > Why are you using no_init? For the same reason, not that it makes sence for my first example, but in general, I want my most offsen called overload to be first in the list - so defined last. > Doesn't this stuff work for regular > functions and member functions, too? Yes it works, see the test. > ...and shouldn't we get rid of the need to write the outer > "args(...)"? It is not necessary to have it, you can write (arg("a") = (int)0, arg("b") = (double)0, arg("n") = std::string())) instead of args(arg("a") = (int)0, arg("b") = (double)0, arg("n") = std::string())) but you'll probably want args("a","b","c", arg("n") = std::string())) instead of (arg("a"), arg("b"), arg("c"), arg("n") = std::string())) > > I suggest you write the documentation which would explain all this, Sure, but I think I'll wait a bit to see all of your comments:) > but posting informally is fine if you try to ensure that I don't have > to ask you lots more questions in order to understand it ;-) I hope this all makes sense to you. Regards > > >> Nit: the coding style should be made consistent with the rest of the > >> library. These don't really fit: > >> > >> > std::size_t j = nargs, k = nargs, size=PyTuple_GET_SIZE(f->m_arg_names.ptr()); > >> > >> > }else ++k; > >> > > > > I will look into this. If you mean that some new line are missing, > > consider it fixed. > > Also that you used commas between variable declarations, K&R braces > within functions, no spaces around '?', '<', '>', ... > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com -------------- next part -------------- ''' >>> from keywords import * >>> f = Foo() >>> b = Bar() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> b.a(), b.b(), b.n() (0, 0.0, '') >>> f = Foo(1) >>> b = Bar(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> b.a(), b.b(), b.n() (1, 0.0, '') >>> f = Foo(1,1.0) >>> b = Bar(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> b.a(), b.b(), b.n() (1, 1.0, '') >>> f = Foo(1,1.0,"1") >>> b = Bar(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') >>> b.a(), b.b(), b.n() (1, 1.0, '1') >>> f = Foo(a=1) >>> b = Bar(a=1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> b.a(), b.b(), b.n() (1, 0.0, '') >>> f = Foo(b=1) >>> b = Bar(b=1) >>> f.a(), f.b(), f.n() (0, 1.0, '') >>> b.a(), b.b(), b.n() (0, 1.0, '') >>> f = Foo(n="1") >>> b = Bar(n="1") >>> f.a(), f.b(), f.n() (0, 0.0, '1') >>> b.a(), b.b(), b.n() (0, 0.0, '1') >>> f = Foo(1,n="1") >>> b = Bar(1,n="1") >>> f.a(), f.b(), f.n() (1, 0.0, '1') >>> b.a(), b.b(), b.n() (1, 0.0, '1') >>> f.set() >>> b.set() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> b.a(), b.b(), b.n() (0, 0.0, '') >>> f.set(1) >>> b.set(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> b.a(), b.b(), b.n() (1, 0.0, '') >>> f.set(1,1.0) >>> b.set(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> b.a(), b.b(), b.n() (1, 1.0, '') >>> f.set(1,1.0,"1") >>> b.set(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') >>> b.a(), b.b(), b.n() (1, 1.0, '1') >>> f.set(a=1) >>> b.set(a=1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> b.a(), b.b(), b.n() (1, 0.0, '') >>> f.set(b=1) >>> b.set(b=1) >>> f.a(), f.b(), f.n() (0, 1.0, '') >>> b.a(), b.b(), b.n() (0, 1.0, '') >>> f.set(n="1") >>> b.set(n="1") >>> f.a(), f.b(), f.n() (0, 0.0, '1') >>> b.a(), b.b(), b.n() (0, 0.0, '1') >>> f.set(1,n="1") >>> b.set(1,n="1") >>> f.a(), f.b(), f.n() (1, 0.0, '1') >>> b.a(), b.b(), b.n() (1, 0.0, '1') ''' ############################# # Sample from my computer ############################# #>>> from time import time #>>> def callNtimes(f, n=100000): #... t = time() #... for i in range(0,n): #... f() #... return time()-t #... #>>> callNtimes(f.set) #1.1100000143051147 #>>> callNtimes(b.set) #2.4220000505447388 #>>> callNtimes(lambda: f.set(1)) #1.968000054359436 #>>> callNtimes(lambda: b.set(1)) #2.8289999961853027 #>>> callNtimes(lambda: f.set(1,.1)) #2.3279999494552612 #>>> callNtimes(lambda: b.set(1,.1)) #2.843999981880188 #>>> callNtimes(lambda: f.set(1,.1,'1')) #2.656000018119812 #>>> callNtimes(lambda: b.set(1,.1,'1')) #2.656999945640564 def run(args = None): import sys import doctest if args is not None: sys.argv = args return doctest.testmod(sys.modules.get(__name__)) if __name__ == '__main__': print "running..." import sys sys.exit(run()[0]) -------------- next part -------------- A non-text attachment was scrubbed... Name: keywords.cpp Type: application/x-unknown-content-type-cppfile Size: 2999 bytes Desc: not available URL: From nickm at sitius.com Tue Jul 1 00:36:39 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Mon, 30 Jun 2003 18:36:39 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> Message-ID: <3F00BB77.43379507@sitius.com> Oh, and I meant to explain a bit of how it works. case 1. init > and def(*,*, overloads()) define overloaded functions with fixed arity, meaning that m_min_arity == m_max_arity for each of them. When a call is made that has nargs == overload.m_min_arity == overload.m_max_arity, the overload proceeds case 2. When args are used only one overload is created and in general it will have m_min_arity != m_max_arity, based on how many arguments have default values. When a call is made that matches this (m_min_arity,m_max_arity) range then the default args are used to fill in the blanks to m_max_arity, and only if this is possible the overload proceeds. From christophe.grimault at novagrid.com Tue Jul 1 11:50:36 2003 From: christophe.grimault at novagrid.com (christophe grimault) Date: Tue, 01 Jul 2003 09:50:36 +0000 Subject: [C++-sig] Simply calling a routine ... References: <3EF9CAF4.80208@cenix-bioscience.com> <3EFAE527.3040301@cenix-bioscience.com> <3EFC15EF.2070304@novagrid.com> <3EAC249A.30605@globalite.com.br> Message-ID: <3F01596C.1080905@novagrid.com> Nicodemus wrote: > christophe grimault wrote: > >> Hi all, >> >> I have a written several routines in C++ using blitz++. These >> routines are called sucessively by the 'main' routine. I want to >> rewrite the main in python in order to gain development speed and >> flexibility. The routines use blitz++ matrix template library >> but the interfaces to the routine are very common C++ calls with >> basic C++ types (int, float*, short*, etc...) : >> >> int foo( short* a, float b, float* c, int N ){ >> Array A(N); >> A.data() = a; >> >> // Do some work >> >> >> return ( ERROR_CODE ); >> } >> >> Is it straightforward to declare these routines with pyste >> (or the classic boost method). Does the use of blitz in these >> routines (which belong to another file than the main, beginning >> with include of blitz.hh) complicates the process. I'm a bit lost >> because of the use of "templates in blitz++" versus "integration with >> boost". > > > > What problems are you having exactly? And I don't know how you would > pass the parameters to this function, except if you create the arrays > in C++ too. If you don't care about reading the array values in > Python, you can treat them as opaque pointers... check > return_opaque_pointer: > > http://www.boost.org/libs/python/doc/v2/return_opaque_pointer.html The arrays can be created in Python, but could be simple python C-arrays (not numeric), and all the "numerical" work is done in C++ routines. > >> Also, as you can see in the example routine above, I started with >> a creation of a blitz array 'A' from the array 'a'. Because I'm >> afraid of the work to get back and forth from Numeric array in Python >> to Blitz++ templated Array in C++ is a complicated and big amount >> of work. > > > > Perhaps, but I don't believe it would be such a pain... you can create > simple wrappers that would do the job nicely; If there is a lot of > functions, then perhaps you could even implement to-python and > from-python conversions for Numeric arrays, as demonstrated here (for > C++ standard containers): > > http://www.boost.org/libs/python/doc/v2/faq.html#question2 I believe this is a better way... I have play a lot more with boost to get more familiar with the possibilities. I'm just lacking time. Thanks for the hints. I will probably have new questions in a near future ! > >> Thanks for any response on these to points, and for any suggestion or >> criticism on my way of handling the problem. Christophe Grimault > > > > Hope that helps! > > Regards, > Nicodemus. > > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > -- ------------------------------------------------------ | Christophe Grimault Tel: 02 23 23 52 59 | | NovaGrid SA http://www.novagrid.com | | fax: 02 23 23 62 32 | | mail: christophe.grimault at novagrid.com | | 2, Bd Sebastopol | | 35000 RENNES | | France | |______________________________________________________| From wilson at afn.org Tue Jul 1 14:54:38 2003 From: wilson at afn.org (Jim Wilson) Date: Tue, 01 Jul 2003 08:54:38 -0400 Subject: [C++-sig] Pyste overload problem Message-ID: Pystitos, Earlier, I posted a Pyste problem on g.c.l.b.user, to a deafening silence: http://article.gmane.org/gmane.comp.lib.boost.user/3793 so I presume I posted to the wrong list. I notice most Pyste discussion is here, and that similar complaints suggest "Get the CVS" as a panacea. Sure enough, after an hour of CVS and another hour of building, the problem is gone! Alas, another similar one takes its place. foo.h: void bar(char**); void bar(); foo.pyste: Function("bar", "foo.h") Pyste issues no "needs-a-policy" complaint. Instead, it apparently generates code which calls bar(char*), a function which does not exist. Any advice? Jim Wilson Gainesville, FL From dalwan01 at student.umu.se Tue Jul 1 20:51:33 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Tue, 01 Jul 2003 20:51:33 +0200 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: References: <3efdfd94.975.16838@student.umu.se> Message-ID: <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> At 00:34 2003-06-29, you wrote: >"Daniel Wallin" writes: > > >> Yeah, but I doubt it's saving much, and it leads to much > >> complication (c.f. instance_new and instance_dealloc in > >> libs/python/src/object/class.cpp). If objects are > >> getting created and destroyed a *lot* it could reduce > >> fragmentation and increase locality... but as I said I > >> have big doubts. > > > > Yeah, fragmentation issues can always be solved with pool > > allocation. > >But locality can't, for what that's worth. Frankly I think >it's not worth much. Me neither. > > Is the complexity only due to value-holders, or just > > different kind of holders? Seems to me (without having > > looked at instance_new/instance_dealloc yet..) like you > > would need the same allocation routines for > > pointer-holders as well. > >I'm trying to tell you it has nothing to do with the how the >holders contain their data [though see below]; it's about >how/where the holders themselves are constructed. > >The object model is something like this: every wrapped class >instance contains an endogenous linked list of holders (to >handle multiple inheritance from wrapped classes) and some >raw storage to use for holder allocation. A class wrapper >knows the size and alignment of its default holder, so >usually the holder will be allocated right in the raw >storage. If the holder turns out to be too big for that >storage, e.g. the default holder contains an auto_ptr but >for some reason a value_holder is used, or a >value_holder is used where U is derived from T, then the >holder will be dynamically allocated instead. Additional >holders in MI situations can also end up being dynamically >allocated. Arranging for the extra storage in the Python >object means we have to fool Python into thinking the >objects are variable-length (like a tuple), and incurs a few >other complications. Ok, I have very little knowledge in how Python memory management works. In luabind we always allocate dynamically. We also don't support multiple inheritance from wrapped classes. >Well, OK, actually I suppose the argument forwarding problem >(http://tinyurl.com/fist) causes a lot of additional >complexity because references need to be passed through >reference_wrapper arguments, and that would go away if >there were no value_holders. I barely even notice that >anymore, since it was part of BPLv1... but now that you >mention it, value_holder is probably causing more >complication in the code than in-place holder allocation. >Eliminating both might be a huge simplification. >Additionally, it might become possible to convert nearly any >object to nearly any kind of smart pointer. value_holders >impose some real limitations on usability. The actual allocation of the holders could be in a language dependent layer though, in which case it would be an implementation detail if it's in-place or heap allocated. We don't have any issues with allocating the holder memory together with the instance object in lua. > >> >> That rule makes me nervous, because the terms are > >> >> backwards when calling lua/python from C++. Do people > >> >> get confused? > >> > > >> > I don't think they do, I don't think anyone has reported any > >> > problems with it yet. It's backwards for a reason though, > >> > and it's pretty clear when to use which placeholder. (except > >> > in some special cases, where documentation helps). > >> > >> OK. Maybe we could allow a default argument which would > >> "just work" for these cases. Another option is "_", which > >> is used in MPL for something similar. > > > > Sure, that would be nice. You can also introduce additional > > placeholder aliases for the cases where '_N' and 'result' > > doesn't fit very well. > >My point is that I'm trying to get away from a scenario >where users have to think about which choice is right, when >the context dictates that there can only be one right >choice. Adding different names for the choices doesn't >help with that problem. This is a minor nit. Yeah, for those cases (object_cast, object::assign for instance) we could use default argument or a 'magic' placeholder. >It sounds like we're converging quite rapidly. What other >issues do we need to deal with? I don't know. I'm sure more issues will pop up later on though. :) How do we proceed from here? Daniel Wallin, dalwan01 at student.umu.se From grafik666 at redshift-software.com Tue Jul 1 22:04:37 2003 From: grafik666 at redshift-software.com (Rene Rivera) Date: Tue, 1 Jul 2003 15:04:37 -0500 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> Message-ID: <20030701150438-r01010800-634c4eb8-0860-0108@12.100.89.43> [2003-07-01] Daniel Wallin wrote: >At 00:34 2003-06-29, you wrote: >>It sounds like we're converging quite rapidly. What other >>issues do we need to deal with? > >I don't know. I'm sure more issues will pop up later on though. :) >How do we proceed from here? Even though I followed most of this conversation... I'd personally like to see a summary of decisions. After that finding out what I and others can help with; deciding where to put the work; what to name / where to put the common code; do we want to move the dev discussion to a dedicated list; etc. Some possible answers to those: I imagine doing some of this in the boost-sandbox project is best. Question is do we do all the dev work there or do we keep the LuaBind part where it is? I can contact Jeremy about adding Daniel and Arvid to it, so that Dave can continue enjoying his vacation ;-) As for the name of the common code, I think there was one previous suggestion which I can't remember. But my suggestion is Boost.Tie. It's on par with Boost.Bind, but tie is one of the terms used for binding at runtime/dynamically. I would assume Boost.Lua would be the conterpart to Boost.Python. -- grafik - Don't Assume Anything -- rrivera (at) acm.org - grafik (at) redshift-software.com -- 102708583 (at) icq From shi at imaging.robarts.ca Wed Jul 2 02:29:19 2003 From: shi at imaging.robarts.ca (Shi Sherebrin) Date: Tue, 01 Jul 2003 20:29:19 -0400 Subject: [C++-sig] question about using a python object from C++ Message-ID: <3F02275F.7090704@imaging.robarts.ca> hello, I've spent a lot of time reading the Boost web pages, and I'm still mystified. I have a class that I built in Python. I want to use this class in C++. From reading about Boost it seems to allow bidirectional operation, but I can't find a simple (or any) example of using C++ to access a Python object. Could someone please point me in the right direction? Further digging has led me to the "embedding Python" pages of the main python docs, but that seems quite complicated for C++, and I'd imagine simplifying that is one of the things Boost.Python does. So is there a simple example somewhere of how to do this: In Python I have defined the class "myclass", and it has methods "Init", "Run" & "Shutdown" Ideally, in C++ I want to be able to do something like: ... myclass obj; obj.Init(initdata); obj.Run(params); obj.Shutdown(); thanks in advance for any help on this, Shi. From seefeld at sympatico.ca Wed Jul 2 03:57:23 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Tue, 01 Jul 2003 21:57:23 -0400 Subject: [C++-sig] deriving in python from a C++ base class Message-ID: <3F023C03.6090000@sympatico.ca> hi there, I have trouble extending a demo from the tutorial (taken from http://www.boost.org/libs/python/doc/tutorial/doc/exposing_classes.html). Instead of just instantiating objects of type 'World' in python, I subclass 'World' first, making calls to base class methods from the constructor: class MyWorld(World): def __init__(self): self.set('hi there') print self.greet() that ought to be possible (or so I thought), but instantiating a 'MyWorld' object (still inside python) yields: Traceback (most recent call last): File "test.py", line 18, in ? world = MyWorld() File "test.py", line 10, in __init__ self.set('hi there') TypeError: bad argument type for built-in operation Reading on in the tutorial I find some information about polymorphism on http://www.boost.org/libs/python/doc/tutorial/doc/class_virtual_functions.html, but that page explicitely states that the use of auxiliary wrapper classes is only needed in case I want to access the virtual (python overridden) methods from within C++, which is not (yet) my case, i.e. as far as I'm aware of in my little test there isn't any form of polymorphism involved. What am I missing ? Thanks, Stefan From rwgk at yahoo.com Wed Jul 2 04:36:43 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Tue, 1 Jul 2003 19:36:43 -0700 (PDT) Subject: [C++-sig] question about using a python object from C++ In-Reply-To: <3F02275F.7090704@imaging.robarts.ca> Message-ID: <20030702023644.30673.qmail@web20201.mail.yahoo.com> --- Shi Sherebrin wrote: > I've spent a lot of time reading the Boost web pages, and I'm still > mystified. I have a class that I built in Python. I want to use this > class in C++. From reading about Boost it seems to allow bidirectional > operation, but I can't find a simple (or any) example of using C++ to > access a Python object. Could someone please point me in the right > direction? I am confused by your "ideal" example, but maybe this is useful: Given sandbx/matrix.py: class matrix: def __init__(self, (n_rows, n_columns)): self.n = (n_rows, n_columns) Attached is the code that shows how you can create a sandbx.matrix.matrix instance in C++. This is the test: from sandbx_boost import to_matrix m = to_matrix.to_matrix() assert m.n == (2,3) Ralf P.S.: Sorry for all the namespace stuff. It is not essential. This is just what I have. #include #include #include namespace sandbx { namespace { boost::python::handle<> import_module(const char* module_name) { using namespace boost::python; return handle<>(PyImport_ImportModule(const_cast(module_name))); } boost::python::object to_matrix() { using namespace boost::python; object matrix_module(import_module("sandbx.matrix")); object matrix = matrix_module.attr("matrix"); return matrix(make_tuple(2,3)); } void init_module() { using namespace boost::python; def("to_matrix", to_matrix); } }} // namespace sandbx:: BOOST_PYTHON_MODULE(to_matrix) { sandbx::init_module(); } __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From rwgk at yahoo.com Wed Jul 2 04:47:30 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Tue, 1 Jul 2003 19:47:30 -0700 (PDT) Subject: [C++-sig] deriving in python from a C++ base class In-Reply-To: <3F023C03.6090000@sympatico.ca> Message-ID: <20030702024730.17335.qmail@web20207.mail.yahoo.com> --- Stefan Seefeld wrote: > class MyWorld(World): > def __init__(self): > self.set('hi there') > print self.greet() I think you have to call World.__init__() before you can use the instance. Here is more information: http://www.boost.org/libs/python/doc/PyConDC_2003/bpl.html#inheritance Ralf __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From seefeld at sympatico.ca Wed Jul 2 05:14:57 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Tue, 01 Jul 2003 23:14:57 -0400 Subject: [C++-sig] deriving in python from a C++ base class In-Reply-To: <20030702024730.17335.qmail@web20207.mail.yahoo.com> References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> Message-ID: <3F024E31.5020404@sympatico.ca> Ralf W. Grosse-Kunstleve wrote: > --- Stefan Seefeld wrote: > >>class MyWorld(World): >> def __init__(self): >> self.set('hi there') >> print self.greet() > > > I think you have to call World.__init__() before you can use the instance. > Here is more information: > > http://www.boost.org/libs/python/doc/PyConDC_2003/bpl.html#inheritance thanks, that works ! I still have a question, though: The reason I missed that was that in my real code I initialized the class_<> with a no_init argument, as that was declared to be the way to make the (C++) class non-instantiable. However, even though I only want subclasses to be instantiated, I of course do need to initialize the base class (i.e. run its constructor). How should I do that, then ? Thanks again, Stefan From seefeld at sympatico.ca Wed Jul 2 05:35:09 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Tue, 01 Jul 2003 23:35:09 -0400 Subject: [C++-sig] deriving in python from a C++ base class In-Reply-To: <20030702024730.17335.qmail@web20207.mail.yahoo.com> References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> Message-ID: <3F0252ED.2020307@sympatico.ca> Ralf W. Grosse-Kunstleve wrote: > --- Stefan Seefeld wrote: > >>class MyWorld(World): >> def __init__(self): >> self.set('hi there') >> print self.greet() > > > I think you have to call World.__init__() before you can use the instance. playing more with the code, I'm observing the following: * instantiating 'MyWorld' in python will not call the World's constructor * instantiating a 'MyWorld' object from within C++ will call the constructor * adding a call to 'World.__init__(self)' into the definition of MyWorld.__init__ will call World's constructor twice, or, more generally, n + 1 times, if n is the number of times I call World.__init__. That seems to me quite error-prone and I'm wondering why it is done the way it is. More than error-prone, I'm wondering how I could make it such that I can instantiate 'MyWorld' from python *and* C++, and still get the base constructor called once per instance in both cases. Thanks, Stefan PS: by the way, I found the article you cite very useful, and I think that it illustrates things that are not or less clearly documented in the tutorial / reference. May be some of the text could be copied over... From nicodemus at globalite.com.br Wed Jul 2 17:00:46 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Wed, 02 Jul 2003 12:00:46 -0300 Subject: [C++-sig] Pyste overload problem In-Reply-To: References: Message-ID: <3F02F39E.5090604@globalite.com.br> Hi Jim, Jim Wilson wrote: > foo.h: > > void bar(char**); > void bar(); > > foo.pyste: > > Function("bar", "foo.h") > > Pyste issues no "needs-a-policy" complaint. Instead, it apparently > generates > code which calls bar(char*), a function which does not exist. It sure does look like a bug, I will take a look into it. Thanks for the report! Alas, it might take a while for me to solve this, because I am a little swamped right now (college finals), but I will look at it ASAP. Regards, Nicodemus. From phil at freehackers.org Wed Jul 2 17:05:26 2003 From: phil at freehackers.org (Philippe Fremy) Date: Wed, 2 Jul 2003 17:05:26 +0200 Subject: [C++-sig] Linking problem Message-ID: <200307021705.26875.phil@freehackers.org> Hi, I get a beyound-my-level-of-comprehension linking problem with boost and msvc. The problematic code is : typedef const char * (*data2str)( const unsigned char * data, int len ); template char const * data2strWrapperWithList( boost::python::list dataList ) { Apdu apdu = list2apdu( dataList ); return (const char *) ((*f)( apdu.bytes(), apdu.len() )); } [...] // hex2str functions def( "hex2str", data2strWrapperWithList ); def( "block2str", &(data2strWrapperWithList) ); [...] Visual reports me a "Unresolved external symbol: char const * __cdecl data2strWrapperWithList( class boost::python::list)" (?...) It links fine if I comment the .def related to these data2str converters. It links fine under linux. Does anybody have any hint ? regards, Philippe ps: please include my in any replay as I am not subscribed. -- Talk less, code more! From rwgk at yahoo.com Wed Jul 2 17:55:29 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Wed, 2 Jul 2003 08:55:29 -0700 (PDT) Subject: [C++-sig] Linking problem In-Reply-To: <200307021705.26875.phil@freehackers.org> Message-ID: <20030702155529.6076.qmail@web20206.mail.yahoo.com> --- Philippe Fremy wrote: > template > char const * data2strWrapperWithList( boost::python::list dataList ) > { > Apdu apdu = list2apdu( dataList ); > return (const char *) ((*f)( apdu.bytes(), apdu.len() )); > } Maybe VC gets confused because "f" does not appear in the signature of your function? I'd try to work around this like so: template struct data2strWrapper { static char const* WithList(boost::python::list dataList) { Apdu apdu = list2apdu( dataList ); return (const char *) ((*f)( apdu.bytes(), apdu.len() )); } }; Then def data2strWrapper::WithList. Ralf __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From mike at nospam.com Wed Jul 2 21:43:00 2003 From: mike at nospam.com (Mike Rovner) Date: Wed, 2 Jul 2003 12:43:00 -0700 Subject: [C++-sig] VC++ 7.1 (VStudio.NET 2003) linking problem Message-ID: I'm trying to move my project from VC++ 7.0 to 7.1 There was no problem under 7.0 I have several classes to wrap separated to several source files, i.e. file1.cpp #include ... f(){ class_("C1")...; } file2: #include ... class_("C0")...; f(); When linking I got the following: error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in file1.obj repeating for every holder from _1 to _9. Googling and boost archive searching were unsuccessful. boost was taken from latest CVS. Any clues and/or links are very appreciated. Regards, Mike From jjanecek at telusplanet.net Wed Jul 2 22:07:07 2003 From: jjanecek at telusplanet.net (John Janecek) Date: Wed, 02 Jul 2003 14:07:07 -0600 Subject: [C++-sig] Linking Problem, Boost and MSVC In-Reply-To: <20030702160008.4882.80110.Mailman@mail.python.org> Message-ID: <5.1.0.14.2.20030702135857.00b428a8@mail.telusplanet.net> This is not very scientific, but when it comes to linking with MSVC I have discovered that you get unresolved linking errors unless all the libraries are not linked with the same "code generation". Project, Settings, C++, Code Generation. and then use run-time library. I set it to use Multithreaded-DLL. sometimes warnings still occur but it seems to work. I have been unable to get boost to compile using JAM files so therefore i use the VC IDE like show in the tutorial. Also if anyone is intrested i wrapped jrtp library using boost. http://pyjrtplib.sourceforge.net/ John From rwgk at yahoo.com Wed Jul 2 22:53:50 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Wed, 2 Jul 2003 13:53:50 -0700 (PDT) Subject: [C++-sig] VC++ 7.1 (VStudio.NET 2003) linking problem In-Reply-To: Message-ID: <20030702205350.86160.qmail@web20209.mail.yahoo.com> I am using VC++ 7.1 without having link problems. But IIRC someone mentioned problems with pre-compiled header files. Could this be related to your difficulties? Ralf --- Mike Rovner wrote: > I'm trying to move my project from VC++ 7.0 to 7.1 > There was no problem under 7.0 > When linking I got the following: > > error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" > (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in file1.obj __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From sagarwal at cs.ucsd.edu Wed Jul 2 22:56:56 2003 From: sagarwal at cs.ucsd.edu (Sameer Agarwal) Date: Wed, 2 Jul 2003 13:56:56 -0700 (PDT) Subject: [C++-sig] VC++ 7.1 (VStudio.NET 2003) linking problem In-Reply-To: <20030702205350.86160.qmail@web20209.mail.yahoo.com> Message-ID: well for one thing, the notation in your 98 paper is much more consistent and correct as compared to the notation in the book chapter. Infact you keep going back and forth between using p and f for the phase function. Besides that the subscripts for L are also mixed up at a number of places. I went through the 98 paper yesterday and that does not have any mistakes in it. sameer On Wed, 2 Jul 2003, Ralf W. Grosse-Kunstleve wrote: > I am using VC++ 7.1 without having link problems. > But IIRC someone mentioned problems with pre-compiled header files. > Could this be related to your difficulties? > Ralf > > --- Mike Rovner wrote: > > I'm trying to move my project from VC++ 7.0 to 7.1 > > There was no problem under 7.0 > > When linking I got the following: > > > > error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" > > (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in file1.obj > > > __________________________________ > Do you Yahoo!? > SBC Yahoo! DSL - Now only $29.95 per month! > http://sbc.yahoo.com > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > From sagarwal at cs.ucsd.edu Wed Jul 2 23:02:16 2003 From: sagarwal at cs.ucsd.edu (Sameer Agarwal) Date: Wed, 2 Jul 2003 14:02:16 -0700 (PDT) Subject: [C++-sig] VC++ 7.1 (VStudio.NET 2003) linking problem In-Reply-To: Message-ID: oops, many apologies, this was not meant for this mailinglist. sameer On Wed, 2 Jul 2003, Sameer Agarwal wrote: > well for one thing, the notation in your 98 paper is much more consistent > and correct as compared to the notation in the book chapter. Infact you > keep going back and forth between using p and f for the phase function. > Besides that the subscripts for L are also mixed up at a number of places. > > I went through the 98 paper yesterday and that does not have any mistakes > in it. > > sameer > > > > On Wed, 2 Jul 2003, Ralf W. Grosse-Kunstleve wrote: > > > I am using VC++ 7.1 without having link problems. > > But IIRC someone mentioned problems with pre-compiled header files. > > Could this be related to your difficulties? > > Ralf > > > > --- Mike Rovner wrote: > > > I'm trying to move my project from VC++ 7.0 to 7.1 > > > There was no problem under 7.0 > > > When linking I got the following: > > > > > > error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" > > > (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in file1.obj > > > > > > __________________________________ > > Do you Yahoo!? > > SBC Yahoo! DSL - Now only $29.95 per month! > > http://sbc.yahoo.com > > > > _______________________________________________ > > C++-sig mailing list > > C++-sig at python.org > > http://mail.python.org/mailman/listinfo/c++-sig > > > > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > From mike at nospam.com Thu Jul 3 00:28:01 2003 From: mike at nospam.com (Mike Rovner) Date: Wed, 2 Jul 2003 15:28:01 -0700 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: <20030702205350.86160.qmail@web20209.mail.yahoo.com> Message-ID: Ralf W. Grosse-Kunstleve wrote: > I am using VC++ 7.1 without having link problems. > But IIRC someone mentioned problems with pre-compiled header files. > Could this be related to your difficulties? Yes. PCH are ON. I'll check on turnining them off. BTW, patching boost from anonymous namespace (back) to static solves the problem. The patch is: boost/tuple/detail/tuple_basic.hpp: 603,605c603 < namespace { < detail::swallow_assign ignore; < } --- > static detail::swallow_assign ignore; boost/bind/placeholders.hpp: 39c39 < #elif (defined(BOOST_MSVC) && BOOST_MSVC <= 1300) || (defined(__DECCXX_VER) && __DECCXX_VER <= 60590031) || defined(__MWERKS__) --- > #elif (defined(BOOST_MSVC) && BOOST_MSVC <= 1400) || (defined(__DECCXX_VER) && __DECCXX_VER <= 60590031) || defined(__MWERKS__) Regards, Mike From mike at nospam.com Thu Jul 3 01:28:44 2003 From: mike at nospam.com (Mike Rovner) Date: Wed, 2 Jul 2003 16:28:44 -0700 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: <20030702205350.86160.qmail@web20209.mail.yahoo.com> Message-ID: Mike Rovner wrote: > Ralf W. Grosse-Kunstleve wrote: >> I am using VC++ 7.1 without having link problems. >> But IIRC someone mentioned problems with pre-compiled header files. >> Could this be related to your difficulties? > > Yes. PCH are ON. I'll check on turnining them off. You are right. Disabling pre-compiled headers eliminate the problem as well. Thank you, Ralf. Regards, Mike From nicodemus at globalite.com.br Thu Jul 3 02:01:55 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Wed, 02 Jul 2003 21:01:55 -0300 Subject: [C++-sig] Pyste overload problem In-Reply-To: <3F02F39E.5090604@globalite.com.br> References: <3F02F39E.5090604@globalite.com.br> Message-ID: <3F037273.3020608@globalite.com.br> Nicodemus wrote: > Hi Jim, > > Jim Wilson wrote: > >> foo.h: >> >> void bar(char**); >> void bar(); >> >> foo.pyste: >> >> Function("bar", "foo.h") >> >> Pyste issues no "needs-a-policy" complaint. Instead, it apparently >> generates >> code which calls bar(char*), a function which does not exist. > > > > It sure does look like a bug, I will take a look into it. Thanks for > the report! Fixed in CVS. Thanks again Jim. Regards, Nicodemus. From rwgk at yahoo.com Thu Jul 3 02:43:42 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Wed, 2 Jul 2003 17:43:42 -0700 (PDT) Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem In-Reply-To: Message-ID: <20030703004342.91959.qmail@web20206.mail.yahoo.com> --- Mike Rovner wrote: > You are right. Disabling pre-compiled headers eliminate the problem as well. I am curious, what is the effect of enabling or disabling pre-compiled headers on the compile times? Huge, modest, small? Ralf __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From mike at nospam.com Thu Jul 3 03:17:28 2003 From: mike at nospam.com (Mike Rovner) Date: Wed, 2 Jul 2003 18:17:28 -0700 Subject: [C++-sig] Re: Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: <20030703004342.91959.qmail@web20206.mail.yahoo.com> Message-ID: Ralf W. Grosse-Kunstleve wrote: > I am curious, what is the effect of enabling or disabling > pre-compiled headers on the compile times? Huge, modest, small? Unfortunately I can't tell in this case, because I was off my computer. But from _very_ recent experience with the same project on vc70 - _if_ PCH is build correctly (which is not always the case and vc seems to rebuild them - I have settings to auto) then effect is rather big - two- three- fold (about 40sec instead of 1.5-2min per file). That's the best answer I have in hand. As by nature I have to recompile very often I'll try to do some measuments and post results (in a while ;)). Regards, Mike From prabhu at aero.iitm.ernet.in Thu Jul 3 12:11:45 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Thu, 3 Jul 2003 15:41:45 +0530 Subject: [C++-sig] Installing Pyste. Message-ID: <16132.353.879474.386569@monster.linux.in> Hi, Before starting to use Pyste I wanted to install it in a common location instead of running it off Boost's CVS tree. I find it easier to manage packages when I can install them somewhere. To this end I wrote a trivial setup_pyste.py using distutils that works. Its not great but works. Here is what I did: Use the following setup_pyste.py # -------------------- import os from distutils.core import setup boost_base_dir = "/path/to/your/boost/dir" pyste_src_dir = os.path.join(boost_base_dir, "libs/python/pyste/src") setup (name = "Pyste", version = "1.0", description = "Pyste - Python Semi-Automatic Exporter", maintainer = "Bruno da Silva de Oliveira", maintainer_email = "nicodemus at globalite.com.br", licence = "Boost License", long_description = "Pyste is a Boost.Python code generator", url = "http://www.boost.org/libs/python/pyste/index.html", platforms = ['Any'], packages = ['Pyste'], scripts = ['pyste.py'], package_dir = {'Pyste': pyste_src_dir} ) # -------------------- This installs Pyste inside /site-packages/Pyste. I wrote a simple wrapper pyste.py script to use this like so: # -------------------- #!/usr/bin/env python import time import sys from Pyste import pyste if __name__ == '__main__': start = time.clock() pyste.UsePsyco() status = pyste.Main() print '%0.2f seconds' % (time.clock()-start) sys.exit(status) # -------------------- Make this executable and finally do: python setup_pyste.py install to install Pyste. Finally add a __init__.py into /site-packages/Pyste. It would be nice if something like this were included the repository. Thanks for Boost.Python and Pyste! cheers, prabhu From prabhu at aero.iitm.ernet.in Thu Jul 3 12:11:59 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Thu, 3 Jul 2003 15:41:59 +0530 Subject: [C++-sig] Problems with Pyste from CVS. Message-ID: <16132.367.739589.337322@monster.linux.in> Hi, I just updated my local CVS checkout of Boost. I tried running Pyste and got the following traceback. The same exact pyste file worked fine a little while earlier with an older checkout (June 25th) of CVS. If you need any more information let me know. I can also try and generate a smaller test case that I can include here (right now I don't have one). Thanks. prabhu -------------------------------------------------- Traceback (most recent call last): File "/usr/local/bin/pyste.py", line 11, in ? status = pyste.Main() File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/pyste.py", line 195, in Main declarations, parsed_header = parser.parse(header, all_tails) File "/usr/local/stow/pyste//lib/python2.2/site-packages/Pyste/CppParser.py", line 82, in parse declarations = ParseDeclarations(xmlfile) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 437, in ParseDeclarations parser.Parse(filename) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 36, in Parse self.ParseElement(id, element) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 60, in ParseElement func(id, element) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 371, in ParseOperatorMethod self.ParseMethod(id, element, ClassOperator) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 356, in ParseMethod classname = self.GetDecl(element.get('context'))._FullName() File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 98, in GetDecl self.ParseElement(id, elem) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 60, in ParseElement func(id, element) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 291, in ParseClass class_._AddMember(member) File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/declarations.py", line 123, in _AddMember m._is_unique = False AttributeError: 'str' object has no attribute '_is_unique' From nicodemus at globalite.com.br Thu Jul 3 12:48:49 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 03 Jul 2003 07:48:49 -0300 Subject: [C++-sig] Problems with Pyste from CVS. In-Reply-To: <16132.367.739589.337322@monster.linux.in> References: <16132.367.739589.337322@monster.linux.in> Message-ID: <3F040A11.1010508@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >Hi, > >I just updated my local CVS checkout of Boost. I tried running Pyste >and got the following traceback. The same exact pyste file worked >fine a little while earlier with an older checkout (June 25th) of CVS. > >If you need any more information let me know. I can also try and >generate a smaller test case that I can include here (right now I >don't have one). > > I test case would be great! If you can isolate to a single file of yours, you could also send me the parsed xml file (run with --debug), so I can reproduce the problem here. I have changed some of Pyste internals to accomodate meta-programming in the Pyste files, so some bugs might come up. Thanks a lot, Nicodemus. From nicodemus at globalite.com.br Thu Jul 3 12:51:23 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 03 Jul 2003 07:51:23 -0300 Subject: [C++-sig] Installing Pyste. In-Reply-To: <16132.353.879474.386569@monster.linux.in> References: <16132.353.879474.386569@monster.linux.in> Message-ID: <3F040AAB.1060008@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >Before starting to use Pyste I wanted to install it in a common >location instead of running it off Boost's CVS tree. I find it easier >to manage packages when I can install them somewhere. To this end I >wrote a trivial setup_pyste.py using distutils that works. Its not >great but works. Here is what I did: > > > That looks great, Prabhu! If you could write some documentation on how to use it, I will gladly add it to the distribution. Just a small text file explaining how to install it would be great. Thanks a lot! Nicodemus. From prabhu at aero.iitm.ernet.in Thu Jul 3 14:24:03 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Thu, 3 Jul 2003 17:54:03 +0530 Subject: [C++-sig] Problems with Pyste from CVS. In-Reply-To: <3F040A11.1010508@globalite.com.br> References: <16132.367.739589.337322@monster.linux.in> <3F040A11.1010508@globalite.com.br> Message-ID: <16132.8291.587836.869633@monster.linux.in> Hi, >>>>> "N" == nicodemus writes: >> If you need any more information let me know. I can also try >> and generate a smaller test case that I can include here (right >> now I don't have one). N> I test case would be great! If you can isolate to a single file N> of yours, you could also send me the parsed xml file (run with N> --debug), so I can reproduce the problem here. Thanks for the quick response! I found a _minimal_ test case that has triggers the problem for me. // -------------------- namespace test { class A { public: A() {} int _name; }; }// namespace test // -------------------- Further testing shows that its the '_name' thats causing problems. I change that to '_nam' and it works! Wierd. Besides, it has to be a data or member function of the class. A normal function with name _name works fine. Hope this helps. prabhu From prabhu at aero.iitm.ernet.in Thu Jul 3 14:42:29 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Thu, 3 Jul 2003 18:12:29 +0530 Subject: [C++-sig] Installing Pyste. In-Reply-To: <3F040AAB.1060008@globalite.com.br> References: <16132.353.879474.386569@monster.linux.in> <3F040AAB.1060008@globalite.com.br> Message-ID: <16132.9397.35714.194993@monster.linux.in> >>>>> "N" == nicodemus writes: [Pyste setup script] N> That looks great, Prabhu! If you could write some documentation N> on how to use it, I will gladly add it to the N> distribution. Just a small text file explaining how to install N> it would be great. To set this up in the distribution here are the things one needs to do: 1. Add an empty __init__.py file to libs/python/pyste/src/. 2. Add the attached setup.py to libs/python/pyste/. 3. Add the attached pyste.py to libs/python/pyste/scripts/ or to an appropriate location of your choice. However in that case you'd need to modify the setup.py script to change the location of this script. 4. Now folks who want to install Pyste via distutils do the usual python setup.py install, dance. The nice thing about the above is that it will not interfere with the current setup where folks use Pyste it out of the source tree. It will be possible to elminiate the two pyste.py scripts but that will require moving the files around and might disturb the existing setup. Hope this helps. cheers, prabhu -------------- next part -------------- A non-text attachment was scrubbed... Name: setup.py Type: application/octet-stream Size: 655 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: pyste.py Type: application/octet-stream Size: 239 bytes Desc: not available URL: From prabhu at aero.iitm.ernet.in Thu Jul 3 17:45:30 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Thu, 3 Jul 2003 21:15:30 +0530 Subject: [C++-sig] Pyste and virtual operators. Message-ID: <16132.20378.670119.410404@monster.linux.in> Hi, My experience with Boost.Python and Pyste have so far been superb. Thanks for the wonderful library and tool! I think I've just found a bug with Pyste regarding handling virtual operators. Virtual functions seem to be OK but operators cause trouble. Consider the following minimal test code: // ------- file.hpp ------------- namespace test { class Op { public: virtual ~Op() {} virtual Op& operator ++ () = 0; }; } // -------------------- I now wrap this using something like so in a Pyste file. op = AllFromHeader('file.hpp') When generating file.cpp everything is fine but when compiling the file errors are generated since the wrapper code does not generate wrappers for the operator and this cannot be instantiated. In the above case there is no wrapper code generated at all. The problem also persists with concrete virtual member operators -- since the wrappers are not generated. The code compiles but there would be problems since one would not be able to overload it in a derived class in Python. I guess this is a bug? Thanks! cheers, prabhu From prabhu at aero.iitm.ernet.in Thu Jul 3 22:26:06 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Fri, 4 Jul 2003 01:56:06 +0530 Subject: [C++-sig] Pyste and overloaded virtual functions. Message-ID: <16132.37214.90457.136653@monster.linux.in> Hi, Sorry to bother you like this every few hours but I've found another bug with Pyste (previous version) when generating code for overloaded virtual functions. Here is a test program. // ---------- overload.hpp ---------- namespace test { class Base { public: virtual void f(const int i) = 0; }; class A : public Base{ public: void f(const int i) {} void f(const double d, const int i) {} }; } // -------------------- When compiling the file that Pyste generates for this, it produces this error message: overload.cpp: In function `void init_module_overload()': overload.cpp:59: no matching function for call to `boost::python::class_::def (const char[2], {unknown type}, void ({anonymous}::test_A_Wrapper::*)(int))' The generated code segment for the function looks like this: .def("f", &test::A::f, &test_A_Wrapper::default_f) .def("f", (void (test::A::*)(const double, const int) )&test::A::f) The fix is to replace it like so: .def("f", (void (test::A::*)(const int) ) &test::A::f, &test_A_Wrapper::default_f) .def("f", (void (test::A::*)(const double, const int) )&test::A::f) Only the first line is changed. I've also attached a patch to ClassExporter.py that fixes this for me. Oh! I just spent an hour and a half debugging this but it looks like this was fixed in the latest version that has the _name bug. FWIW, I've attached the patch anyway but this patch is for the ClassExporter.py version 1.29. cheers, prabhu -------------- next part -------------- A non-text attachment was scrubbed... Name: ClassExporter.patch Type: application/octet-stream Size: 525 bytes Desc: not available URL: From dave at boost-consulting.com Thu Jul 3 19:33:57 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 13:33:57 -0400 Subject: [C++-sig] Re: Interest in luabind References: <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> <20030701150438-r01010800-634c4eb8-0860-0108@12.100.89.43> Message-ID: Rene Rivera writes: > [2003-07-01] Daniel Wallin wrote: > >>At 00:34 2003-06-29, you wrote: >>>It sounds like we're converging quite rapidly. What other >>>issues do we need to deal with? >> >>I don't know. I'm sure more issues will pop up later on though. :) >>How do we proceed from here? > > Even though I followed most of this conversation... I'd personally > like to see a summary of decisions. I think that would be great. Volunteers? > After that finding out what I and others can help with; deciding > where to put the work; what to name / where to put the common code; > do we want to move the dev discussion to a dedicated list; etc. > > Some possible answers to those: > > I imagine doing some of this in the boost-sandbox project is > best. I'm not sure; I want to refactor parts of Boost.Python anyway. Given that we have a pile of tests, etc., I think it would be better to do this evolution in the main CVS. On a branch, if nothing else. > Question is do we do all the dev work there or do we keep the > LuaBind part where it is? I can contact Jeremy about adding Daniel > and Arvid to it, so that Dave can continue enjoying his vacation ;-) I think it's best to have everything in one repository so we can be aggressive about sharing architecture and technology. > As for the name of the common code, I think there was one previous > suggestion which I can't remember. But my suggestion is > Boost.Tie. It's on par with Boost.Bind, but tie is one of the terms > used for binding at runtime/dynamically. I would assume Boost.Lua > would be the conterpart to Boost.Python. Tie already has a meaning in the tuples library. I think we ought to consider something that has more connotations of _dynamic_ _language_ binding. It's a bit unfortunate because we probably don't like some of the connotations, but "Boost.Script" might be the most apporpriate name. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 3 22:48:36 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 16:48:36 -0400 Subject: [C++-sig] Re: Linking Problem, Boost and MSVC References: <20030702160008.4882.80110.Mailman@mail.python.org> <5.1.0.14.2.20030702135857.00b428a8@mail.telusplanet.net> Message-ID: John Janecek writes: > This is not very scientific, but when it comes to linking with MSVC > I have discovered that you get unresolved linking errors unless all > the libraries are not linked with the same "code generation". Part of the reason for the Boost.Build system is to help ensure that sort of thing is set up properly. > Project, Settings, C++, Code Generation. and then use run-time > library. > > I set it to use Multithreaded-DLL. > > sometimes warnings still occur but it seems to work. > > I have been unable to get boost to compile using JAM files What's the problem? > so therefore i use the VC IDE like show in the tutorial. > > Also if anyone is intrested i wrapped jrtp library using boost. > > http://pyjrtplib.sourceforge.net/ What is it? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 3 19:48:27 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 13:48:27 -0400 Subject: [C++-sig] Re: question about using a python object from C++ References: <3F02275F.7090704@imaging.robarts.ca> Message-ID: Shi Sherebrin writes: > hello, > > I've spent a lot of time reading the Boost web pages, and I'm still > mystified. I have a class that I built in Python. I want to use this > class in C++. From reading about Boost it seems to allow > bidirectional operation, but I can't find a simple (or any) example of > using C++ to access a Python object. Could someone please point me in > the right direction? Getting ahold of the Python class object in C++ is your first problem. The easiest way is to pass it as an argument to a wrapped C++ function: void f(boost::python::object python_class) { ... } Now you can construct an instance of the class just as you would in Python: void f(object python_class) { object instance = python_class(3, "hello", 22.5); instance.Run(42) instance.Shutdown(); ... } >>> class Foo: ... def __init__(count, message, rating): ... self.count = count ... self.message = message ... self.rating = rating ... >>> import my_extension >>> my_extension.f(Foo) If you can't pass the class into your C++ function, you'll have to use the Python 'C' API to access the module in which you've created it and pull out the class attribute: // Retrieve the main module // Have to use the Python 'C' API for this part unfortunately. object main_module( python::handle<>( python::borrowed(PyImport_AddModule("__main__")) )); // get __main__.Foo object Foo = main_module.attr("Foo"); // instantiate one object inst = Foo(3, "hello", 22.5); // use it. inst.Run(42) inst.Shutdown(); -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 3 23:12:56 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 17:12:56 -0400 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: Message-ID: "Mike Rovner" writes: > I'm trying to move my project from VC++ 7.0 to 7.1 > There was no problem under 7.0 > > I have several classes to wrap separated to several source files, i.e. > > file1.cpp > #include > ... > f(){ > class_("C1")...; > } > > file2: > #include > ... > class_("C0")...; > f(); > > When linking I got the following: > > error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" > (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in file1.obj > > repeating for every holder from _1 to _9. > > Googling and boost archive searching were unsuccessful. > boost was taken from latest CVS. > Any clues and/or links are very appreciated. Mike, Jason Shirk, a compiler engineer at Microsoft (jasonsh-at-microsoft.com), says: Hmm, I might need more info. I made a little test that shows the same problem mentioned in those messages, but my little test fails with VC6, VC7, VC7.1, and VC8. It's possible that if I fix that problem I just found, the one you've reported will go away. Still, it seems best to get a repro. So, please send him a reproducible test case. Thanks, -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 3 23:14:11 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 17:14:11 -0400 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem In-Reply-To: (Mike Rovner's message of "Wed, 2 Jul 2003 12:43:00 -0700") References: Message-ID: "Mike Rovner" writes: > I'm trying to move my project from VC++ 7.0 to 7.1 > There was no problem under 7.0 > > I have several classes to wrap separated to several source files, i.e. > > file1.cpp > #include > ... > f(){ > class_("C1")...; > } > > file2: > #include > ... > class_("C0")...; > f(); > > When linking I got the following: > > error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" > (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in file1.obj > > repeating for every holder from _1 to _9. > > Googling and boost archive searching were unsuccessful. > boost was taken from latest CVS. > Any clues and/or links are very appreciated. Mike, Jason Shirk, a compiler engineer at Microsoft (jasonsh-at-microsoft.com), says: Hmm, I might need more info. I made a little test that shows the same problem mentioned in those messages, but my little test fails with VC6, VC7, VC7.1, and VC8. It's possible that if I fix that problem I just found, the one you've reported will go away. Still, it seems best to get a repro. So, please send him a reproducible test case. Thanks, -- Dave Abrahams Boost Consulting www.boost-consulting.com From dalwan01 at student.umu.se Thu Jul 3 23:41:00 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Thu, 03 Jul 2003 23:41:00 +0200 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: <20030701150438-r01010800-634c4eb8-0860-0108@12.100.89.43> References: <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> Message-ID: <5.1.0.14.0.20030703233314.03ab4e48@student.umu.se> At 22:04 2003-07-01, you wrote: >[2003-07-01] Daniel Wallin wrote: > > >At 00:34 2003-06-29, you wrote: > >>It sounds like we're converging quite rapidly. What other > >>issues do we need to deal with? > > > >I don't know. I'm sure more issues will pop up later on though. :) > >How do we proceed from here? > > >As for the name of the common code, I think there was one previous >suggestion which I can't remember. But my suggestion is Boost.Tie. It's on >par with Boost.Bind, but tie is one of the terms used for binding at >runtime/dynamically. I would assume Boost.Lua would be the conterpart to >Boost.Python. I think 'tie' is a bit vague. I don't have any suggestions at the moment though. Also, we would very much like to keep the name 'luabind'. Daniel Wallin, dalwan01 at student.umu.se From dalwan01 at student.umu.se Thu Jul 3 23:50:59 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Thu, 03 Jul 2003 23:50:59 +0200 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: References: <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> <20030701150438-r01010800-634c4eb8-0860-0108@12.100.89.43> Message-ID: <5.1.0.14.0.20030703234114.03ab38c8@student.umu.se> At 19:33 2003-07-03, you wrote: >Rene Rivera writes: > > > [2003-07-01] Daniel Wallin wrote: > > > >> > >>I don't know. I'm sure more issues will pop up later on though. :) > >>How do we proceed from here? > > > After that finding out what I and others can help with; deciding > > where to put the work; what to name / where to put the common code; > > do we want to move the dev discussion to a dedicated list; etc. > > > > Some possible answers to those: > > > > Question is do we do all the dev work there or do we keep the > > LuaBind part where it is? I can contact Jeremy about adding Daniel > > and Arvid to it, so that Dave can continue enjoying his vacation ;-) > >I think it's best to have everything in one repository so we can be >aggressive about sharing architecture and technology. I agree. > > As for the name of the common code, I think there was one previous > > suggestion which I can't remember. But my suggestion is > > Boost.Tie. It's on par with Boost.Bind, but tie is one of the terms > > used for binding at runtime/dynamically. I would assume Boost.Lua > > would be the conterpart to Boost.Python. > >Tie already has a meaning in the tuples library. I think we ought to >consider something that has more connotations of _dynamic_ _language_ >binding. It's a bit unfortunate because we probably don't like some >of the connotations, but "Boost.Script" might be the most apporpriate >name. Script it better.. It doesn't feel good though, but it might just take some time to get used to. :) Daniel Wallin, dalwan01 at student.umu.se From dave at boost-consulting.com Fri Jul 4 00:11:45 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 18:11:45 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> Message-ID: [Nikolay, please leave a blank line between quotations for readability. Thanks!] Nikolay Mladenov writes: > I've attached test files. > >> OK, I don't understand this. Isn't the 2nd constructor redundant? > > Yes it is but, having it makes certain calls more efficient (it's > cheating, in a way ), see the commented section in the py-file, may > be def with args can be made so it is really redundant. OK, I would like to see "irrelevancies" removed from the code for any test case, though... unless you think the efficiency issue is closely related to the keyword support, in which case you'll have to convince me (please). >> Why are you using no_init? > > For the same reason, not that it makes sence for my first example, > but in general, I want my most offsen called overload to be first in > the list - so defined last. That still doesn't explain why you'd want to use no_init. Why not just define the more-important constructor 2nd? >> Doesn't this stuff work for regular functions and member functions, >> too? > > Yes it works, see the test. Fantastic. >> ...and shouldn't we get rid of the need to write the outer >> "args(...)"? > It is not necessary to have it, you can write > (arg("a") = (int)0, arg("b") = (double)0, arg("n") = std::string())) > instead of > args(arg("a") = (int)0, arg("b") = (double)0, arg("n") = > std::string())) > but you'll probably want > args("a","b","c", arg("n") = std::string())) > instead of > (arg("a"), arg("b"), arg("c"), arg("n") = std::string())) Understood... but is it really wise to give people more than One (And Preferably Only One) Obvious Way To Do It? I might be inclined to support only: args("a","b","c") and: (arg("a"), arg("b"), arg("c"), arg("n") = std::string())) Or even drop the 1st and go with (arg("a"), arg("b"), arg("c")) Thoughts? >> I suggest you write the documentation which would explain all this, > > Sure, but I think I'll wait a bit to see all of your comments:) OK. >> but posting informally is fine if you try to ensure that I don't have >> to ask you lots more questions in order to understand it ;-) > > I hope this all makes sense to you. It does. In the examples, I'd prefer to see arg("a") = int() , arg("b") = double() , arg("n") = std::string() or arg("a") = 0 , arg("b") = 0.0 , arg("n") = std::string() or arg("a") = 0 , arg("b") = 0.0 , arg("n") = "" instead of arg("a") = (int)0 , arg("b") = (double)0 , arg("n") = std::string() Aside from that and my previous comments, it looks scrumptious! -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 00:14:05 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 18:14:05 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00BB77.43379507@sitius.com> Message-ID: Nikolay Mladenov writes: > Oh, and I meant to explain a bit of how it works. > > case 1. init > and def(*,*, overloads()) define overloaded > functions with fixed arity, > meaning that m_min_arity == m_max_arity for each of them. When a call is > made that has > nargs == overload.m_min_arity == overload.m_max_arity, the overload > proceeds > > case 2. When args are used only one overload is created and in general > it will have m_min_arity != m_max_arity, > based on how many arguments have default values. When a call is made > that matches this (m_min_arity,m_max_arity) > range then the default args are used to fill in the blanks to > m_max_arity, and only if this is possible the overload proceeds. Thanks, sounds perfect. As you could probably tell from working on it, that approach fell right into all the "slots" I'd left in the code for you (well me, really, but I never got around to it -- so thanks!) -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 01:39:37 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 19:39:37 -0400 Subject: [C++-sig] Re: Interest in luabind References: <3efdfd94.975.16838@student.umu.se> <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> Message-ID: Daniel Wallin writes: > At 00:34 2003-06-29, you wrote: >>"Daniel Wallin" writes: >> > Ok, I have very little knowledge in how Python memory management > works. In luabind we always allocate dynamically. We also don't > support multiple inheritance from wrapped classes. Oh, but that's cheap. At least in Boost.Python it is. I assume it would be the same in luabind if you were using holders. >>Well, OK, actually I suppose the argument forwarding problem >>(http://tinyurl.com/fist) causes a lot of additional >>complexity because references need to be passed through >>reference_wrapper arguments, and that would go away if >>there were no value_holders. I barely even notice that >>anymore, since it was part of BPLv1... but now that you >>mention it, value_holder is probably causing more >>complication in the code than in-place holder allocation. >>Eliminating both might be a huge simplification. >>Additionally, it might become possible to convert nearly any >>object to nearly any kind of smart pointer. value_holders >>impose some real limitations on usability. > > The actual allocation of the holders could be in a language > dependent layer though, in which case it would be an implementation > detail if it's in-place or heap allocated. We don't have any issues > with allocating the holder memory together with the instance object > in lua. But without value_holders it seems silly, and value_holders themselves seem to lead to a great deal of complication, soo... Looking at the big picture I'm rather inclined to go with something much simpler. I guess that using placement new in value holders might be a way to gain a whole lot of simplicity, though. OK, here's my conclusion (hope you agree): there's no need for value_holders or in-dynamic-object allocation of C++ data in any initial merged version of the library. We can always optimize later if it doesn't incur too much code complexity. >>It sounds like we're converging quite rapidly. What other >>issues do we need to deal with? > > I don't know. I'm sure more issues will pop up later on though. :) > How do we proceed from here? I think Rene raised that already; let's continue in that branch of the thread. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 01:45:24 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 19:45:24 -0400 Subject: [C++-sig] Re: Linking Problem, Boost and MSVC References: <20030702160008.4882.80110.Mailman@mail.python.org> <5.1.0.14.2.20030702135857.00b428a8@mail.telusplanet.net> Message-ID: John Janecek writes: > Also if anyone is intrested i wrapped jrtp library using boost. > > http://pyjrtplib.sourceforge.net/ Care to write up a patch for the projects page at http://www.boost.org/libs/python/doc/projects.html? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 01:46:44 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 19:46:44 -0400 Subject: [C++-sig] Re: Refactoring, Compilation Speed, Pyste, Lua/Ruby/JavaScript... References: Message-ID: "Brett Calcott" writes: >> >> There is (http://www.python.org/cgi-bin/moinmoin/boost_2epython), but >> note that it doesn't do ReST and I much prefer CVS for this sort of >> thing. I hate editing in a webpage, and I like to be able to apply >> all the usual revision control tools. I'd happily give you Boost CVS >> access if you wanted to do it that way. If you have a strong >> preference for Wiki it's no problem, since you'll be doing most of the >> interaction anyway. > > You're right. Editing in a webpage has all the power of windows > notepad. Only better: you can't resize the editor pane! > I'll cut and paste into a document, and we can sort out CVS access. > >> >> > Where shall we start :) >> >> What are you interested in? > > Let me have a think, and I'll start a new thread. I'm in the middle of > packing, so it might be a few days away. > > I look forward to you filling my brain up :) I think you can get a lot of good material from the luabind discussion. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Fri Jul 4 01:55:30 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 03 Jul 2003 20:55:30 -0300 Subject: [C++-sig] Problems with Pyste from CVS. In-Reply-To: <16132.8291.587836.869633@monster.linux.in> References: <16132.367.739589.337322@monster.linux.in> <3F040A11.1010508@globalite.com.br> <16132.8291.587836.869633@monster.linux.in> Message-ID: <3F04C272.6030002@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >I found a _minimal_ test case that has triggers the problem for me. > >// -------------------- >namespace test { > >class A { >public: > A() {} > int _name; >}; > >}// namespace test >// -------------------- > >Further testing shows that its the '_name' thats causing problems. I >change that to '_nam' and it works! Wierd. Besides, it has to be a >data or member function of the class. A normal function with name >_name works fine. > > Yep, as I feared. 8( I have been doing some internal changes to Pyste to support meta-programming, and my plan was to allow the user to access information about the declarations using "_" to acess the attributes: namespace test { struct C { void Foo(const int, double); }; } ---- C = Class('test::C', ...) print C._name # prints "C" print C._FullName() # prints "test::C" print C.Foo._parameters[0]._FullName() # prints "const int" And so on. But of course, it didn't occur to me that the attributes of the objects would get in conflict with the declarations. Well, duh! Anyway, I will reverse this changes, since they clearly don't work. I have to find a way to allow the user to access the attributes, and what I've thought so far is providing access to them using operator []: print C['name'] print C['fullname'] print C['parameters'][0]['fullname'] But I think it makes the syntax confusing... 8( Any one has any ideas? They are most welcome. Regards, Nicodemus. From grafik666 at redshift-software.com Fri Jul 4 01:59:14 2003 From: grafik666 at redshift-software.com (Rene Rivera) Date: Thu, 3 Jul 2003 18:59:14 -0500 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: Message-ID: <20030703185917-r01010800-6f8c6a34-0860-0108@12.100.89.43> [2003-07-03] David Abrahams wrote: >Rene Rivera writes: > >> [2003-07-01] Daniel Wallin wrote: >> >>>At 00:34 2003-06-29, you wrote: >>>>It sounds like we're converging quite rapidly. What other >>>>issues do we need to deal with? >>> >>>I don't know. I'm sure more issues will pop up later on though. :) >>>How do we proceed from here? >> >> Even though I followed most of this conversation... I'd personally >> like to see a summary of decisions. > >I think that would be great. Volunteers? I can try and go through the thread, reading more carefully than the first time around, and collect some of the info. (will take a few days) And post the results :-) >> After that finding out what I and others can help with; deciding >> where to put the work; what to name / where to put the common code; >> do we want to move the dev discussion to a dedicated list; etc. >> >> Some possible answers to those: >> >> I imagine doing some of this in the boost-sandbox project is >> best. > >I'm not sure; I want to refactor parts of Boost.Python anyway. Given >that we have a pile of tests, etc., I think it would be better to do >this evolution in the main CVS. On a branch, if nothing else. I thought that for such a restructuring you would not want to mess with the current BP, even if on a branch? But I can see that it would be easier than copying over a bunch of BP code. Any ideas/preferences on: Where do we discuss the refactoring of the common code and the laubind dev? It seems like noise polution to keep it on this list. Daniel do you have a non-user list set up for LuaBind? Or we can add a list to the SF boost project. -- grafik - Don't Assume Anything -- rrivera (at) acm.org - grafik (at) redshift-software.com -- 102708583 (at) icq From wilson at afn.org Fri Jul 4 02:10:40 2003 From: wilson at afn.org (Jim Wilson) Date: Thu, 03 Jul 2003 20:10:40 -0400 Subject: [C++-sig] Pyste-generated extentsion Aborts Python Message-ID: Nicodemus, I got the CVS, and it seemed to fix the "overloaded bar(char**)" problem I mentioned before. My goal was to wrap (at least a portion of) the Fast Light ToolKit (FLTK: http://www.fltk.org ). Others are attempting this with SWIG ( http://pyfltk.sourceforge.net/ ), but I was hoping Pyste would simplify the job. Alas, I'm not sure I can simplify the files I'm wrapping, but my wrapper is quite lightweight. Since I didn't want to figure out all those "needs- a-policy" complaints, I wrote a small header which exposed only the routines I needed from FLTK Version 1.1.4. I'm not sure you want this, but here it is: fltk.h: class Fl { // A class masquerading as a namespace, public: // Fl is essentially a buch of static methods static int run(); }; #include <.../Fl_Window.H> // This will be instanciated fltk.pyste: Class("Fl", "fltk.h") w = Class("Fl_Window", "fltk.h") exclude(w.icon) # Easier to exclude than use the exclude(w.child) # trick I did with class Fl, since exclude(w.current) # I may want to *do* something with exclude(w.array) # my Fl_Window! exclude(w.resizable) exclude(w._ddfdesign_kludge) (In fltk.h, <...> was the path prefix my the directory holding Fl_Window.h.) I pysted, beat bjam into submission, and got a clean compile and link. Now came python: >>>from fltk import Fl, Fl_Window >>>w = Fl_Window(0,0, 600,400) >>>w.show() >>>Fl.run() Abort The "w = ..." line, creates a window in the upper left corner (0,0) of size 600x400 pixels. The next draws it on the screen, the last one fires up the event loop. The window is momentarily displayed before it immediately vanishes and "Abort" appears (followed by the bash prompt). The running python is half as big as the SWIG version though ;D. I'd appreciate any advice. Jim Wilson From grafik666 at redshift-software.com Fri Jul 4 02:12:40 2003 From: grafik666 at redshift-software.com (Rene Rivera) Date: Thu, 3 Jul 2003 19:12:40 -0500 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: <5.1.0.14.0.20030703234114.03ab38c8@student.umu.se> Message-ID: <20030703191241-r01010800-bcf7a38d-0860-0108@12.100.89.43> >>I think it's best to have everything in one repository so we can be >>aggressive about sharing architecture and technology. > >I agree. OK :-) >> > As for the name of the common code, I think there was one previous >> > suggestion which I can't remember. But my suggestion is >> > Boost.Tie. It's on par with Boost.Bind, but tie is one of the terms >> > used for binding at runtime/dynamically. I would assume Boost.Lua >> > would be the conterpart to Boost.Python. >> >>Tie already has a meaning in the tuples library. I think we ought to >>consider something that has more connotations of _dynamic_ _language_ >>binding. It's a bit unfortunate because we probably don't like some >>of the connotations, but "Boost.Script" might be the most apporpriate >>name. > >Script it better.. It doesn't feel good though, but it might just take >some time to get used to. :) Script has "limiting" connotations in my mind. After all what happens when we add bindings for other non-scripting languages like: Lisp/CLOS, Smalltalk, Haskell, etc. And for non-language related bindings like CORBA, COM, SOAP, XMLRPC, etc. Boost.Language is a thought, but too broad. Boost.Bind is taken. ;-) Boost.Interface might work. Boost.Objects perhaps? Or Boost.ObjectBind? -- grafik - Don't Assume Anything -- rrivera (at) acm.org - grafik (at) redshift-software.com -- 102708583 (at) icq From dave at boost-consulting.com Fri Jul 4 00:19:15 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 18:19:15 -0400 Subject: [C++-sig] Re: Pyste and virtual operators. References: <16132.20378.670119.410404@monster.linux.in> Message-ID: Prabhu Ramachandran writes: > My experience with Boost.Python and Pyste have so far been superb. > Thanks for the wonderful library and tool! You're welcome! We really appreciate that you're pushing on it hard enough to find problems. Thanks! -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Fri Jul 4 02:25:34 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 03 Jul 2003 21:25:34 -0300 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: <20030703191241-r01010800-bcf7a38d-0860-0108@12.100.89.43> References: <20030703191241-r01010800-bcf7a38d-0860-0108@12.100.89.43> Message-ID: <3F04C97E.7050600@globalite.com.br> Rene Rivera wrote: >Script has "limiting" connotations in my mind. After all what happens when >we add bindings for other non-scripting languages like: Lisp/CLOS, >Smalltalk, Haskell, etc. And for non-language related bindings like CORBA, >COM, SOAP, XMLRPC, etc. > >Boost.Language is a thought, but too broad. Boost.Bind is taken. ;-) >Boost.Interface might work. Boost.Objects perhaps? Or Boost.ObjectBind? > > Perhaps Boost.Export? After all, it is all about exporting C++ code to other languages... just a thought. 8) From mike at nospam.com Fri Jul 4 02:25:56 2003 From: mike at nospam.com (Mike Rovner) Date: Thu, 3 Jul 2003 17:25:56 -0700 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: Message-ID: David Abrahams wrote: > "Mike Rovner" writes: >> error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" >> (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in file1.obj > So, please send him a reproducible test case. Sure, this will be the first thing to do after holidays, i.e. on Monday. As I understand, better extract relevant parts from BPL. It seems easy to do. Thanks, Mike From nicodemus at globalite.com.br Fri Jul 4 02:26:17 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 03 Jul 2003 21:26:17 -0300 Subject: [C++-sig] Pyste-generated extentsion Aborts Python In-Reply-To: References: Message-ID: <3F04C9A9.1070907@globalite.com.br> Hi Jim! Jim Wilson wrote: > Nicodemus, > > I got the CVS, and it seemed to fix the "overloaded bar(char**)" > problem I mentioned before. My goal was to wrap (at least a portion > of) the Fast Light ToolKit (FLTK: http://www.fltk.org ). Others are > attempting this with SWIG ( http://pyfltk.sourceforge.net/ ), but I > was hoping Pyste would simplify the job. > > Alas, I'm not sure I can simplify the files I'm wrapping, but my wrapper > is quite lightweight. Since I didn't want to figure out all those > "needs- > a-policy" complaints, I wrote a small header which exposed only the > routines > I needed from FLTK Version 1.1.4. This does not seems like a good idea... the policies are *really* needed. If you want to expose only a few functions, then you can always exclude() the ones that you don't want. > I'm not sure you want this, but here it is: > > fltk.h: > > class Fl { // A class masquerading as a namespace, > public: // Fl is essentially a buch of static methods > static int run(); > }; > #include <.../Fl_Window.H> // This will be instanciated > > fltk.pyste: > > Class("Fl", "fltk.h") > w = Class("Fl_Window", "fltk.h") > exclude(w.icon) # Easier to exclude than use the > exclude(w.child) # trick I did with class Fl, since > exclude(w.current) # I may want to *do* something with > exclude(w.array) # my Fl_Window! > exclude(w.resizable) > exclude(w._ddfdesign_kludge) > > (In fltk.h, <...> was the path prefix my the directory holding > Fl_Window.h.) > > I pysted, beat bjam into submission, and got a clean compile and > link. Now > came python: > > >>>from fltk import Fl, Fl_Window > >>>w = Fl_Window(0,0, 600,400) > >>>w.show() > >>>Fl.run() > Abort > > The "w = ..." line, creates a window in the upper left corner (0,0) of > size > 600x400 pixels. The next draws it on the screen, the last one fires > up the > event loop. The window is momentarily displayed before it immediately > vanishes and "Abort" appears (followed by the bash prompt). Hmm... could you post the code generated? > The running python is half as big as the SWIG version though ;D. Indeed? I always thought that SWIG would need less memory (not necessarily faster), since it is autogenerated C... congratulations to Boost.Python then. 8) Regards, Nicodemus. From djowel at gmx.co.uk Fri Jul 4 02:28:17 2003 From: djowel at gmx.co.uk (Joel de Guzman) Date: Fri, 4 Jul 2003 08:28:17 +0800 Subject: [C++-sig] Re: Interest in luabind References: <20030703191241-r01010800-bcf7a38d-0860-0108@12.100.89.43> <3F04C97E.7050600@globalite.com.br> Message-ID: <00d401c341c3$503b0820$0100a8c0@godzilla> Nicodemus wrote: > Rene Rivera wrote: > >> Script has "limiting" connotations in my mind. After all >> what happens when we add bindings for other >> non-scripting languages like: Lisp/CLOS, Smalltalk, >> Haskell, etc. And for non-language related bindings like >> CORBA, COM, SOAP, XMLRPC, etc. >> >> Boost.Language is a thought, but too broad. Boost.Bind >> is taken. ;-) Boost.Interface might work. Boost.Objects >> perhaps? Or Boost.ObjectBind? >> >> > Perhaps Boost.Export? After all, it is all about > exporting C++ code to other languages... just a thought. > 8) Boost.Export is a good name. -- Joel de Guzman joel at boost-consulting.com http://www.boost-consulting.com http://spirit.sf.net From dave at boost-consulting.com Fri Jul 4 00:35:01 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 18:35:01 -0400 Subject: [C++-sig] Re: deriving in python from a C++ base class References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F0252ED.2020307@sympatico.ca> Message-ID: Stefan Seefeld writes: > Ralf W. Grosse-Kunstleve wrote: >> --- Stefan Seefeld wrote: >> >>>class MyWorld(World): >>> def __init__(self): >>> self.set('hi there') >>> print self.greet() >> I think you have to call World.__init__() before you can use the >> instance. > > playing more with the code, I'm observing the following: > > * instantiating 'MyWorld' in python will not call the World's constructor Right. Not calling the base __init__ is always an option in Python. > * instantiating a 'MyWorld' object from within C++ will call the constructor Huh? MyWorld is a Python object. How do you instantiate MyWorld from within C++? The only way I know how to do that is: void instantiate_myworld(myworld_class) { object myworld_object = myworld_class(); ... } And that will do exactly the same thing as: >>> MyWorld() in Python. No World::World() gets called. > * adding a call to 'World.__init__(self)' into the definition of MyWorld.__init__ > will call World's constructor twice, or, more generally, n + 1 times, if > n is the number of times I call World.__init__. How? Test case please? > That seems to me quite error-prone and I'm wondering why it is done > the way it is. What you're describing doesn't match any understanding I have of the system, so I can't say yet. > More than error-prone, I'm wondering how I could make it such that I > can instantiate 'MyWorld' from python *and* C++, and still get the > base constructor called once per instance in both cases. Need clarification. > Thanks, > Stefan > > PS: by the way, I found the article you cite very useful, and I think that > it illustrates things that are not or less clearly documented in the > tutorial / reference. May be some of the text could be copied over... Specific suggestions will certainly be considered. -- Dave Abrahams Boost Consulting www.boost-consulting.com From wilson at afn.org Fri Jul 4 02:43:50 2003 From: wilson at afn.org (Jim Wilson) Date: Thu, 03 Jul 2003 20:43:50 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: <3F04C9A9.1070907@globalite.com.br> References: <3F04C9A9.1070907@globalite.com.br> Message-ID: Nicodemus, > Hmm... could you post the code generated? Gladly. http://www.afn.org/~wilson/fltk.cpp > I always thought that SWIG would need less memory I think my comparison may be unfair. The pyFLTK guys have wrapped way more of the toolkit than I have so far attempted. And, their hybrid approach seems to have very coarse granularity. Still, I was impressed with Pyste, etal. Jim From dave at boost-consulting.com Fri Jul 4 00:25:41 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 18:25:41 -0400 Subject: [C++-sig] Re: deriving in python from a C++ base class References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F024E31.5020404@sympatico.ca> Message-ID: Stefan Seefeld writes: > Ralf W. Grosse-Kunstleve wrote: >> --- Stefan Seefeld wrote: >> >>>class MyWorld(World): >>> def __init__(self): >>> self.set('hi there') >>> print self.greet() >> I think you have to call World.__init__() before you can use the >> instance. >> Here is more information: >> http://www.boost.org/libs/python/doc/PyConDC_2003/bpl.html#inheritance > > thanks, that works ! > > I still have a question, though: > > The reason I missed that was that in my real code I initialized the > class_<> with a no_init argument, as that was declared to be the way > to make the (C++) class non-instantiable. Passing no_init to the class_<...> doesn't affect the C++ class' instantiability; it only affects the instantiability of the corresponding Python class. > However, even though I only want subclasses to be instantiated, I of > course do need to initialize the base class (i.e. run its > constructor). > > How should I do that, then ? I'm afraid there's no good way to impose that restriction yet. As a matter of fact, no_init should be more sophisticated and raise an exception only when the Python class of the "self" argument is an exact match for the wrapped class (not a subclass). Maybe you'd like to contribute the code for that? Note, however, that it still wouldn't be a very useful check, since there's nothing to prevent: >>> class Foo(WrappedClass): ... pass ... >>> x = Foo() Foo is essentially identical to WrappedClass, so what have you enforced by preventing: >>> x = WrappedClass ?? -- Dave Abrahams Boost Consulting www.boost-consulting.com From grafik666 at redshift-software.com Fri Jul 4 03:06:42 2003 From: grafik666 at redshift-software.com (Rene Rivera) Date: Thu, 3 Jul 2003 20:06:42 -0500 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: <00d401c341c3$503b0820$0100a8c0@godzilla> Message-ID: <20030703200643-r01010800-1116bdc4-0860-0108@12.100.89.43> [2003-07-04] Joel de Guzman wrote: >Nicodemus wrote: >> Rene Rivera wrote: >> >>> Script has "limiting" connotations in my mind. After all >>> what happens when we add bindings for other >>> non-scripting languages like: Lisp/CLOS, Smalltalk, >>> Haskell, etc. And for non-language related bindings like >>> CORBA, COM, SOAP, XMLRPC, etc. >>> >>> Boost.Language is a thought, but too broad. Boost.Bind >>> is taken. ;-) Boost.Interface might work. Boost.Objects >>> perhaps? Or Boost.ObjectBind? >>> >>> >> Perhaps Boost.Export? After all, it is all about >> exporting C++ code to other languages... just a thought. >> 8) > >Boost.Export is a good name. Yes, good suggestion indeed :-) -- grafik - Don't Assume Anything -- rrivera (at) acm.org - grafik (at) redshift-software.com -- 102708583 (at) icq From wilson at afn.org Fri Jul 4 03:25:27 2003 From: wilson at afn.org (Jim Wilson) Date: Thu, 03 Jul 2003 21:25:27 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: <3F04C9A9.1070907@globalite.com.br> References: <3F04C9A9.1070907@globalite.com.br> Message-ID: Nicodemus, You wrote (regarding my abbreviated class Fl): > This does not seems like a good idea... the policies are *really* > needed. If you want to expose only a few functions, then you can > always exclude() the ones that you don't want. I revised my fltk.h: #include // Where my FLTK #include // headers reside and fltk.pyste (to exclude the troublesom functions): f = Class("Fl", "fltk.h") exclude(f.readqueue) exclude(f.first_window) exclude(f.next_window) exclude(f.modal) exclude(f.grab) exclude(f.belowmouse) exclude(f.pushed) exclude(f.focus) exclude(f.selection_owner) exclude(f.get_boxtype) w = Class("Fl_Window", "fltk.h") exclude(w.icon) exclude(w.child) exclude(w.current) exclude(w.array) exclude(w.resizable) exclude(w._ddfdesign_kludge) And *now* I remember why I did it the way I did. Pyste silently generates (a somewhat longer) fltk.cpp (available renamed) at: http://www.afn.org/~wilson/fltk.cxx But when compiling it, gcc goes berserk and generates all sorts of cryptic template diagnostics. Since I don't understand templates, I'm hopelessly lost! Hence my pragmatism ;). If it'll do any good, I'm happy to tgz or zip the FLTK headers for your entertainment. Jim From nicodemus at globalite.com.br Fri Jul 4 03:39:05 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 03 Jul 2003 22:39:05 -0300 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: References: <3F04C9A9.1070907@globalite.com.br> Message-ID: <3F04DAB9.6000906@globalite.com.br> Jim Wilson wrote: > Nicodemus, > > You wrote (regarding my abbreviated class Fl): > >> This does not seems like a good idea... the policies are *really* >> needed. If you want to expose only a few functions, then you can >> always exclude() the ones that you don't want. > > > I revised my fltk.h: > > #include // Where my FLTK > #include // headers reside > > and fltk.pyste (to exclude the troublesom functions): > > f = Class("Fl", "fltk.h") > exclude(f.readqueue) > exclude(f.first_window) > exclude(f.next_window) > exclude(f.modal) > exclude(f.grab) > exclude(f.belowmouse) > exclude(f.pushed) > exclude(f.focus) > exclude(f.selection_owner) > exclude(f.get_boxtype) > w = Class("Fl_Window", "fltk.h") > exclude(w.icon) > exclude(w.child) > exclude(w.current) > exclude(w.array) > exclude(w.resizable) > exclude(w._ddfdesign_kludge) > > And *now* I remember why I did it the way I did. Pyste silently > generates (a somewhat longer) fltk.cpp (available renamed) at: > > http://www.afn.org/~wilson/fltk.cxx > > But when compiling it, gcc goes berserk and generates all sorts of > cryptic template diagnostics. Since I don't understand templates, > I'm hopelessly lost! Hence my pragmatism ;). Oh yeah... if you export a class down in the hiearchy and don't export the classes that are above it, Pyste will export the methods of the base classes as methods of the derived class. This allow you to export only the class that you are interested, instead to have to export all its base classes too. If it is generating problems tought, then it is probably a bug. The first lines of the error messages normally tell what is wrong... if you could post this, it would be great. 8) From dave at boost-consulting.com Fri Jul 4 04:47:26 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 22:47:26 -0400 Subject: [C++-sig] Re: Problems with Pyste from CVS. References: <16132.367.739589.337322@monster.linux.in> <3F040A11.1010508@globalite.com.br> <16132.8291.587836.869633@monster.linux.in> <3F04C272.6030002@globalite.com.br> Message-ID: Nicodemus writes: > Any one has any ideas? They are most welcome. Names containing double underscores or starting with an underscore followed by a capital letter are reserved to the C++ implementation, so they can't conflict with anything the user might legally define as a class member. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 04:50:14 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 22:50:14 -0400 Subject: [C++-sig] Re: Interest in luabind References: <20030703185917-r01010800-6f8c6a34-0860-0108@12.100.89.43> Message-ID: Rene Rivera writes: > I thought that for such a restructuring you would not want to mess with the > current BP, even if on a branch? That's what branches are for! > But I can see that it would be easier than copying over a bunch of > BP code. Yep. > Any ideas/preferences on: Where do we discuss the refactoring of the > common code and the laubind dev? It seems like noise polution to > keep it on this list. Daniel do you have a non-user list set up for > LuaBind? Or we can add a list to the SF boost project. I prefer here, but only a little. Those interested in Boost.Python internals (I'm thinking of people like Brett Calcott and Dirk Gerrits here) would have to subscribe to whatever other forum we pick. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 04:55:43 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 22:55:43 -0400 Subject: [C++-sig] Re: Interest in luabind References: <00d401c341c3$503b0820$0100a8c0@godzilla> <20030703200643-r01010800-1116bdc4-0860-0108@12.100.89.43> Message-ID: Rene Rivera writes: > [2003-07-04] Joel de Guzman wrote: > >>Nicodemus wrote: >>> Rene Rivera wrote: >>> >>>> Script has "limiting" connotations in my mind. After all >>>> what happens when we add bindings for other >>>> non-scripting languages like: Lisp/CLOS, Smalltalk, >>>> Haskell, etc. And for non-language related bindings like >>>> CORBA, COM, SOAP, XMLRPC, etc. >>>> >>>> Boost.Language is a thought, but too broad. Boost.Bind >>>> is taken. ;-) Boost.Interface might work. Boost.Objects >>>> perhaps? Or Boost.ObjectBind? >>>> >>>> >>> Perhaps Boost.Export? After all, it is all about >>> exporting C++ code to other languages... just a thought. >>> 8) >> >>Boost.Export is a good name. > > Yes, good suggestion indeed :-) Too general, IMO, as are Boost.Interface, Boost.Objects, and Boost.ObjectBind. Also almost all of the code will be specific to dynamic languages, so I don't see how Haskell can figure into this. Your other points are well taken. Another too-general name which I like better than others so far: Boost.Binding. OTOH, I think this is a bicycle shed question. Notice how many responses we got all of a sudden in this thread? . Anyway, this is just a library for library writers and I'm content to call it "the common core" until we really need a name. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 05:11:15 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 03 Jul 2003 23:11:15 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python References: Message-ID: Jim Wilson writes: > The "w = ..." line, creates a window in the upper left corner (0,0) of size > 600x400 pixels. The next draws it on the screen, the last one fires up the > event loop. The window is momentarily displayed before it immediately > vanishes and "Abort" appears (followed by the bash prompt). FWIW, FLTK has some design problems which make it nearly impossible to wrap safely with any wrapping system. So if you're seeing crashes, I'm not surprised. You can read about it in this thread: http://mail.python.org/pipermail/c++-sig/2002-December/003117.html HTH, -- Dave Abrahams Boost Consulting www.boost-consulting.com From rwgk at yahoo.com Fri Jul 4 06:12:41 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Thu, 3 Jul 2003 21:12:41 -0700 (PDT) Subject: [C++-sig] Re: Interest in luabind In-Reply-To: <20030703200643-r01010800-1116bdc4-0860-0108@12.100.89.43> Message-ID: <20030704041241.56569.qmail@web20201.mail.yahoo.com> --- Rene Rivera wrote: > [2003-07-04] Joel de Guzman wrote: > > >Nicodemus wrote: > >> Rene Rivera wrote: > >> > >>> Script has "limiting" connotations in my mind. After all > >>> what happens when we add bindings for other > >>> non-scripting languages like: Lisp/CLOS, Smalltalk, > >>> Haskell, etc. And for non-language related bindings like > >>> CORBA, COM, SOAP, XMLRPC, etc. Hm, so many guests... it must be a Boost.Party! Ralf __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From dalwan01 at student.umu.se Fri Jul 4 08:39:52 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Fri, 04 Jul 2003 08:39:52 +0200 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: References: <3efdfd94.975.16838@student.umu.se> <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> Message-ID: <5.1.0.14.0.20030704082338.02d44e58@student.umu.se> At 01:39 2003-07-04, you wrote: >Daniel Wallin writes: > > > At 00:34 2003-06-29, you wrote: > >>"Daniel Wallin" writes: > >> > > Ok, I have very little knowledge in how Python memory management > > works. In luabind we always allocate dynamically. We also don't > > support multiple inheritance from wrapped classes. > >Oh, but that's cheap. At least in Boost.Python it is. I assume it >would be the same in luabind if you were using holders. Yeah it would. The thing is that lua doesn't have classes, all it has is the ability to 'hook' on certain events on objects, so the class system is something luabind introduces. Multiple inheritance would mean we would need to make some decisions on how to handle method-dispatching, and how to handle diamond shapes. This is isolated behavior of the luabind class-system though, so it has nothing to do with the shared code. Although, we might introduce MI if there is sufficient need for it. > >>Well, OK, actually I suppose the argument forwarding problem > >>(http://tinyurl.com/fist) causes a lot of additional > >>complexity because references need to be passed through > >>reference_wrapper arguments, and that would go away if > >>there were no value_holders. I barely even notice that > >>anymore, since it was part of BPLv1... but now that you > >>mention it, value_holder is probably causing more > >>complication in the code than in-place holder allocation. > >>Eliminating both might be a huge simplification. > >>Additionally, it might become possible to convert nearly any > >>object to nearly any kind of smart pointer. value_holders > >>impose some real limitations on usability. > > > > The actual allocation of the holders could be in a language > > dependent layer though, in which case it would be an implementation > > detail if it's in-place or heap allocated. We don't have any issues > > with allocating the holder memory together with the instance object > > in lua. > >But without value_holders it seems silly, and value_holders >themselves seem to lead to a great deal of complication, soo... > >Looking at the big picture I'm rather inclined to go with something >much simpler. I guess that using placement new in value holders >might be a way to gain a whole lot of simplicity, though. > >OK, here's my conclusion (hope you agree): there's no need for >value_holders or in-dynamic-object allocation of C++ data in any >initial merged version of the library. We can always optimize later >if it doesn't incur too much code complexity. I agree that value_holders isn't needed in the initial version, but having functions that allocate the storage for holders in language dependent code doesn't really add any complexity. Daniel Wallin, dalwan01 at student.umu.se From dalwan01 at student.umu.se Fri Jul 4 08:45:06 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Fri, 04 Jul 2003 08:45:06 +0200 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: <20030703185917-r01010800-6f8c6a34-0860-0108@12.100.89.43> References: Message-ID: <5.1.0.14.0.20030704084129.03abbac0@student.umu.se> At 01:59 2003-07-04, you wrote: >[2003-07-03] David Abrahams wrote: > > >> After that finding out what I and others can help with; deciding > >> where to put the work; what to name / where to put the common code; > >> do we want to move the dev discussion to a dedicated list; etc. > >> > >> Some possible answers to those: > >> > >> I imagine doing some of this in the boost-sandbox project is > >> best. > > > >I'm not sure; I want to refactor parts of Boost.Python anyway. Given > >that we have a pile of tests, etc., I think it would be better to do > >this evolution in the main CVS. On a branch, if nothing else. > > > >Any ideas/preferences on: Where do we discuss the refactoring of the common >code and the laubind dev? It seems like noise polution to keep it on this >list. Daniel do you have a non-user list set up for LuaBind? Or we can add a >list to the SF boost project. We don't have any non-user list, but I could add one if needed. I think I would prefer a separate list, for easy archiving purposes. :) Daniel Wallin, dalwan01 at student.umu.se From wilson at afn.org Fri Jul 4 15:11:51 2003 From: wilson at afn.org (Jim Wilson) Date: Fri, 04 Jul 2003 09:11:51 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: References: Message-ID: David, You wrote: > > FWIW, FLTK has some design problems which make it nearly impossible to > wrap safely with any wrapping system. So if you're seeing crashes, > I'm not surprised. You can read about it in this thread: > > http://mail.python.org/pipermail/c++-sig/2002-December/003117.html I *think* I vaguely grasp the concepts in your reference. Certainly, I'm aware of the volitile nature of Python objects (including functions), and I sense that calling an evaporated function rarely produces anything useful. I can imagine that something deep in the bowels of some Boost template library has become upset with "void (*func)(...)", and has justifiably decided to issue a long, incomprehensible (to me) complaint about it. I'm not sure why Spitzak chose his simple-minded callback mechanism. I can attest that it makes it easy for simple minds (like mine) to understand ;) Certainly, the alternative virtual method/override that you suggest is also available (although the pertinent method is declared "protected"; I'm not sure what impact this might have on a Boost-based Python wrapper). However, in my ignorance of what I now see may be *future* problems, I chose to allow FLTK to sling raw pointers to its heart's content and exposed only a more disciplined subset of its interface. Pyste generated a .cpp file without a whimper and either: 1. relied on g++ to issue incomprehensible diagnostics- once-removed about Pyste-generated code not intended for human consumption, or 2. relied on Python to issue the even-less-useful diagnostic "Abort". I think this is a Pyste problem, and I believe Nicodemus would want to know about it. For what it's worth, I can cause pyFLTK's SWIG-generated wrapper issue a somewhat related diagnostic: "Segmentation fault" :(. Jim From seefeld at sympatico.ca Fri Jul 4 15:43:38 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Fri, 04 Jul 2003 09:43:38 -0400 Subject: [C++-sig] Re: deriving in python from a C++ base class References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F0252ED.2020307@sympatico.ca> Message-ID: <751832ec5fb30ea081b54bfad350eef93f05821b@Orthosoft.ca> Hi David, David Abrahams wrote: >>PS: by the way, I found the article you cite very useful, and I think that >> it illustrates things that are not or less clearly documented in the >> tutorial / reference. May be some of the text could be copied over... > > > Specific suggestions will certainly be considered. something that I'd like to understand is the relationship between the C++ classes / objects and the corresponding python classes / objects. I noted that I can call the parent's __init__ function multiple times, which invokes the C++ base class constructor. It seems that way I can instantiate more than one base class objects. Is that a specific boost.python problem/feature or is that part of the python object model ? (It's hard to debug python, i.e. I can't log the 'this pointer' in python, so I only know from boost.python that there are multiple C++ base instances).... Stefan From prabhu at aero.iitm.ernet.in Fri Jul 4 16:40:49 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Fri, 4 Jul 2003 20:10:49 +0530 Subject: [C++-sig] Pyste: feature requests Message-ID: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> Hi, I've been trying to wrap a fairly large library of mine using Boost.Python. I've been using Pyste to generate the wrapper code. Since the library is large, I've been using Pyste's --multiple option. Something like this: pyste.py --module=test --out build --multiple file1.pyste file2.pyste I find a few inconveniences and difficulties with this approach and it would be nice to have the following features: 1. Something like the C compiler's '-c' option. In this case Pyste should simply generate the wrapper code and none of the module code i.e. for an invocation like so: pyste.py --out build --multiple -c file1.pyste nothing should be added to test.cpp and just a _file.cpp (or whatever) should be generated which can be then compiled. Then invoking pyste.py --module=test --out build/ --multiple file1.pyste \ file2.pyste should generate test.cpp with the appropriate code. This makes it much easier to handle dependencies. Perhaps the option should be called '-w' for 'just-wrap'? 2. Instead of generating files for each header, it would be useful if one file were generated per pyste file when --multiple were used. The trouble with the current approach of --multiple is that several files can be generated per pyste file. This causes problems with dependencies since one does not (easily) know apriori what files will be generated. For example changing -D options could change the number of files generated. Perhaps instead of changing the behaviour of the --multiple option one one could add another option called --one-file (with a better name). Alternatively if the argument to --out is a filename (file.cpp) that may or may not exist then that file is written, if the argument is a directory (which exists) then multiple files can be generated in that directory. I think these options or something along these lines would make life easier when wrapping larger libraries. What do you folks think? Thanks! cheers, prabhu From dave at boost-consulting.com Fri Jul 4 17:06:03 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 11:06:03 -0400 Subject: [C++-sig] Re: deriving in python from a C++ base class References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F0252ED.2020307@sympatico.ca> <751832ec5fb30ea081b54bfad350eef93f05821b@Orthosoft.ca> Message-ID: Stefan Seefeld writes: > Hi David, > > David Abrahams wrote: > >>>PS: by the way, I found the article you cite very useful, and I think that >>> it illustrates things that are not or less clearly documented in the >>> tutorial / reference. May be some of the text could be copied over... >> Specific suggestions will certainly be considered. > > something that I'd like to understand is the relationship between the > C++ classes / objects and the corresponding python classes / objects. Is that covered in the paper? If so, *specifically* which sections of text would you like to see "copied over?" > I noted that I can call the parent's __init__ function multiple times, > which invokes the C++ base class constructor. It seems that way I can > instantiate more than one base class objects. Is that a specific > boost.python problem/feature or is that part of the python object model > ? (It's hard to debug python, i.e. I can't log the 'this pointer' in > python, so I only know from boost.python that there are multiple C++ > base instances).... The fact that you can call __init__ as many times as you want is part of the Python model. The fact that, for a wrapped class, it creates a C++ object each time is part of the way Boost.Python works. It might be possible to issue an exception when that happens but it hardly seems worthwhile to me. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 4 17:17:22 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 11:17:22 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python References: Message-ID: Jim Wilson writes: > David, > > You wrote: >> FWIW, FLTK has some design problems which make it nearly impossible >> to >> wrap safely with any wrapping system. So if you're seeing crashes, >> I'm not surprised. You can read about it in this thread: >> http://mail.python.org/pipermail/c++-sig/2002-December/003117.html > > I *think* I vaguely grasp the concepts in your reference. Certainly, I'm > aware of the volitile nature of Python objects (including functions), and > I sense that calling an evaporated function rarely produces > anything useful. The problems in my reference have much more to do with the volatile nature of whatever's at the end of your C++ void* than with the volatile nature of Python objects. At least the latter have destructors which can be hooked. > I can imagine that something deep in the bowels of some Boost > template library has become upset with "void (*func)(...)", and has > justifiably decided to issue a long, incomprehensible (to me) > complaint about it. Not if, as you described, it's a runtime Abort. That was a crash, plain and simple, and as I've tried to suggest I think it's a FLTK-ish sort of thing having to do with the inability to manage object lifetimes in a disciplined way. > I'm not sure why Spitzak chose his simple-minded callback mechanism. > I can attest that it makes it easy for simple minds (like mine) to > understand ;) Certainly, the alternative virtual method/override > that you suggest is also available It's provided by FLTK? That's news to me! > (although the pertinent method is declared "protected"; I'm not > sure what impact this might have on a Boost-based Python wrapper). Only a little; when you wrap the class you just need a using declaration in your virtual-function-dispatching subclass. > However, in my ignorance of what I now see may be *future* problems, > I chose to allow FLTK to sling raw pointers to its heart's content > and exposed only a more disciplined subset of its interface. Pyste > generated a .cpp file without a whimper and either: 1. relied on g++ > to issue incomprehensible diagnostics- once-removed about > Pyste-generated code not intended for human consumption, or > 2. relied on Python to issue the even-less-useful diagnostic > "Abort". I don't believe that either is the case. There may in fact be a Pyste problem, though. > I think this is a Pyste problem, and I believe Nicodemus would want > to know about it. > > For what it's worth, I can cause pyFLTK's SWIG-generated wrapper issue a > somewhat related diagnostic: "Segmentation fault" :(. Probably the same FLTK-ish sort of thing I referred to just now. -- Dave Abrahams Boost Consulting www.boost-consulting.com From seefeld at sympatico.ca Fri Jul 4 17:31:54 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Fri, 04 Jul 2003 11:31:54 -0400 Subject: [C++-sig] Re: deriving in python from a C++ base class References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F0252ED.2020307@sympatico.ca> <751832ec5fb30ea081b54bfad350eef93f05821b@Orthosoft.ca> Message-ID: David Abrahams wrote: >>something that I'd like to understand is the relationship between the >>C++ classes / objects and the corresponding python classes / objects. > > > Is that covered in the paper? If so, *specifically* which sections > of text would you like to see "copied over?" Well, partly. The section entitled 'Inheritance' discusses the initialization of the base class through a call to it's __init__ method, and you specifically talk about the lookup of the base class: "Because C++ object construction is a one-step operation, C++ instance data cannot be constructed until the arguments are available in the __init__ function..." This and the following paragraphs make some very important points. As a C++ programmer I'm used to a specific object model / type system, so I believe it would be very useful to discuss how that maps to python, and how boost.python does the dispatching. You may consider this a detail especially for first-time users, but it really helps to understand these things to be efficient in the use of boost.python. >>I noted that I can call the parent's __init__ function multiple times, >>which invokes the C++ base class constructor. It seems that way I can >>instantiate more than one base class objects. Is that a specific >>boost.python problem/feature or is that part of the python object model >>? (It's hard to debug python, i.e. I can't log the 'this pointer' in >>python, so I only know from boost.python that there are multiple C++ >>base instances).... > > > The fact that you can call __init__ as many times as you want is part > of the Python model. The fact that, for a wrapped class, it creates a > C++ object each time is part of the way Boost.Python works. It might > be possible to issue an exception when that happens but it hardly > seems worthwhile to me. Ok. But I do believe that it should be explained. Forgetting to call __init__ on the base class may be a common error, especially for C++ programmers who are used to things like default constructors. Thanks, Stefan From nickm at sitius.com Fri Jul 4 18:09:30 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Fri, 04 Jul 2003 12:09:30 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00BB77.43379507@sitius.com> Message-ID: <3F05A6BA.AF698054@sitius.com> David Abrahams wrote: > Thanks, sounds perfect. As you could probably tell from working on > it, that approach fell right into all the "slots" I'd left in the code > for you (well me, really, but I never got around to it -- so thanks!) I would even say that you didn't leave me any choice:). I was actually following an artical that you had posted long before that. So the interface should match to what you had in mind. From nickm at sitius.com Fri Jul 4 19:04:41 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Fri, 04 Jul 2003 13:04:41 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> Message-ID: <3F05B3A9.7B2F29E8@sitius.com> David Abrahams wrote: > OK, I would like to see "irrelevancies" removed from the code for any > test case, though... unless you think the efficiency issue is closely > related to the keyword support, in which case you'll have to convince > me (please). I am not sure what needs convincing? There is an efficiency issue. Don't you agree? I put those just so to answer you question on why I have redundant constructor. I don't mean to keep them > > >> Why are you using no_init? > > > > For the same reason, not that it makes sence for my first example, > > but in general, I want my most offsen called overload to be first in > > the list - so defined last. > > That still doesn't explain why you'd want to use no_init. Why not > just define the more-important constructor 2nd? Are you saying that I should put the first constructor as parameter of the class_ constructor? Cause I really prefer the def way for exporting constructors. I was not realizing the fact that class_() implicitly defines default constructor for a long time, and I think that this is somewhat confusing. > > >> Doesn't this stuff work for regular functions and member functions, > >> too? > > > > Yes it works, see the test. > > Fantastic. > > >> ...and shouldn't we get rid of the need to write the outer > >> "args(...)"? > > It is not necessary to have it, you can write > > (arg("a") = (int)0, arg("b") = (double)0, arg("n") = std::string())) > > instead of > > args(arg("a") = (int)0, arg("b") = (double)0, arg("n") = > > std::string())) > > but you'll probably want > > args("a","b","c", arg("n") = std::string())) > > instead of > > (arg("a"), arg("b"), arg("c"), arg("n") = std::string())) > > Understood... but is it really wise to give people more than One (And > Preferably Only One) Obvious Way To Do It? Why not? They are not *too* different, are they? > > I might be inclined to support only: > > args("a","b","c") > > and: > > (arg("a"), arg("b"), arg("c"), arg("n") = std::string())) > > Or even drop the 1st and go with > > (arg("a"), arg("b"), arg("c")) > > Thoughts? Well, originally I thought that args() is already in the library so it should not be removed. So if you insist on being minimal, than probably we should support args("a","b","c") // which is already there arg("d")=1 and at the end: ( args("a","b","c"), arg("d")=1, arg("e")=std::string() ) ( arg("a"), arg("d")=1, arg("e")=std::string() ) > From prabhu at aero.iitm.ernet.in Fri Jul 4 21:31:15 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 01:01:15 +0530 Subject: [C++-sig] Pyste: bug: overriding overloaded virtual functions. Message-ID: <16133.54787.174958.488899@monster.linux.in> Hi, One more bug. Consider an overloaded virtual function that is implemented in the base class and not overridden in the derived class. // --------- overload.hpp -------- namespace test { class Base { public: virtual void f() {} virtual void f(const int i){} }; class A : public Base { public: void f(){} }; } // --------- overload.hpp -------- Running Pyste on this produces this wrapper code: // ---------- wrapper code ---------- struct test_A_Wrapper: test::A { [...] void f(const int p0) { call_method< void >(self, "f", p0); } void default_f(const int p0) { test::A::f(p0); // <<=========== ERROR. test::Base::f(p0); // <<=========== Should be this. } [...] // ---------- wrapper code ---------- Attached is a patch (two lines) for the _current_ CVS code that fixes this. cheers, prabhu -------------- next part -------------- A non-text attachment was scrubbed... Name: ClassExporter.patch Type: application/octet-stream Size: 659 bytes Desc: not available URL: From nicodemus at globalite.com.br Sat Jul 5 00:50:38 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 19:50:38 -0300 Subject: [C++-sig] Pyste and overloaded virtual functions. In-Reply-To: <16132.37214.90457.136653@monster.linux.in> References: <16132.37214.90457.136653@monster.linux.in> Message-ID: <3F0604BE.7010605@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >Sorry to bother you like this every few hours but I've found another >bug with Pyste (previous version) when generating code for overloaded >virtual functions. Here is a test program. > >// ---------- overload.hpp ---------- >namespace test { >class Base { >public: > virtual void f(const int i) = 0; >}; > >class A : public Base{ >public: > void f(const int i) {} > void f(const double d, const int i) {} >}; >} >// -------------------- > > >The generated code segment for the function looks like this: > > .def("f", &test::A::f, &test_A_Wrapper::default_f) > .def("f", (void (test::A::*)(const double, const int) )&test::A::f) > >The fix is to replace it like so: > > .def("f", (void (test::A::*)(const int) ) &test::A::f, &test_A_Wrapper::default_f) > .def("f", (void (test::A::*)(const double, const int) )&test::A::f) > >Only the first line is changed. I've also attached a patch to >ClassExporter.py that fixes this for me. Oh! I just spent an hour >and a half debugging this but it looks like this was fixed in the >latest version that has the _name bug. FWIW, I've attached the patch >anyway but this patch is for the ClassExporter.py version 1.29. > > Yeah, it is fixed in the new version, but thanks for the patch anyway! 8) Regards, Nicodemus. From nicodemus at globalite.com.br Sat Jul 5 00:52:23 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 19:52:23 -0300 Subject: [C++-sig] Installing Pyste. In-Reply-To: <16132.9397.35714.194993@monster.linux.in> References: <16132.353.879474.386569@monster.linux.in> <3F040AAB.1060008@globalite.com.br> <16132.9397.35714.194993@monster.linux.in> Message-ID: <3F060527.8020707@globalite.com.br> Prabhu Ramachandran wrote: >[Pyste setup script] > > >To set this up in the distribution here are the things one needs to >do: > > 1. Add an empty __init__.py file to libs/python/pyste/src/. > > 2. Add the attached setup.py to libs/python/pyste/. > > 3. Add the attached pyste.py to libs/python/pyste/scripts/ or to an > appropriate location of your choice. However in that case you'd > need to modify the setup.py script to change the location of this > script. > > 4. Now folks who want to install Pyste via distutils do the usual > python setup.py install, dance. > >The nice thing about the above is that it will not interfere with the >current setup where folks use Pyste it out of the source tree. It >will be possible to elminiate the two pyste.py scripts but that will >require moving the files around and might disturb the existing setup. > > I added it to the distribution, it is in "libs/python/pyste/install". I moved the pyste/src dir to pyste/src/Pyste, and made a few changes to your setup.py. Thanks a lot Prabhu! Regards, Nicodemus. From nicodemus at globalite.com.br Sat Jul 5 00:54:12 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 19:54:12 -0300 Subject: [C++-sig] Pyste: bug: overriding overloaded virtual functions. In-Reply-To: <16133.54787.174958.488899@monster.linux.in> References: <16133.54787.174958.488899@monster.linux.in> Message-ID: <3F060594.6020809@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >Hi, > >One more bug. Consider an overloaded virtual function that is >implemented in the base class and not overridden in the derived class. > >// --------- overload.hpp -------- >namespace test { >class Base { >public: > virtual void f() {} > virtual void f(const int i){} >}; > >class A : public Base { >public: > void f(){} >}; >} >// --------- overload.hpp -------- > >Running Pyste on this produces this wrapper code: > >// ---------- wrapper code ---------- >struct test_A_Wrapper: test::A >{ > [...] > void f(const int p0) { > call_method< void >(self, "f", p0); > } > > void default_f(const int p0) { > test::A::f(p0); // <<=========== ERROR. > test::Base::f(p0); // <<=========== Should be this. > } > [...] >// ---------- wrapper code ---------- > > >Attached is a patch (two lines) for the _current_ CVS code that fixes >this. > > I just applied your patch. I really appreciate your effort in finding this problems, thanks a lot! Regards, Nicodemus. From nicodemus at globalite.com.br Sat Jul 5 01:00:57 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 20:00:57 -0300 Subject: [C++-sig] Pyste: feature requests In-Reply-To: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> References: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> Message-ID: <3F060729.4040409@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >Hi, > > 1. Something like the C compiler's '-c' option. In this case Pyste > should simply generate the wrapper code and none of the module > code i.e. for an invocation like so: > > pyste.py --out build --multiple -c file1.pyste > > nothing should be added to test.cpp and just a _file.cpp (or > whatever) should be generated which can be then compiled. Then > invoking > > pyste.py --module=test --out build/ --multiple file1.pyste \ > file2.pyste > > should generate test.cpp with the appropriate code. This makes it > much easier to handle dependencies. Perhaps the option should be > called '-w' for 'just-wrap'? > I don't understand exactly what you are saying. Are you suggesting that instead of generating: #include <...> BOOST_PYTHON_MODULE(module) { class_(...); } You want to be able to generate just this: class_(...); ? How does that help you handle dependencies? > 2. Instead of generating files for each header, it would be useful if > one file were generated per pyste file when --multiple were used. > The trouble with the current approach of --multiple is that > several files can be generated per pyste file. This causes > problems with dependencies since one does not (easily) know > apriori what files will be generated. For example changing -D > options could change the number of files generated. Perhaps > instead of changing the behaviour of the --multiple option one one > could add another option called --one-file (with a better name). > Alternatively if the argument to --out is a filename (file.cpp) > that may or may not exist then that file is written, if the > argument is a directory (which exists) then multiple files can be > generated in that directory. > > Good idea! When I implemented the --multiple option, I didn't consider dependencies. I will put in my TODO list, shouldn't be too hard to implement this. >I think these options or something along these lines would make life >easier when wrapping larger libraries. > >What do you folks think? > Thanks a lot for your suggestions! Regards, Nicodemus. From nicodemus at globalite.com.br Sat Jul 5 01:10:35 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 20:10:35 -0300 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: <3F04DAB9.6000906@globalite.com.br> References: <3F04C9A9.1070907@globalite.com.br> <3F04DAB9.6000906@globalite.com.br> Message-ID: <3F06096B.9080005@globalite.com.br> Nicodemus wrote: > If it is generating problems tought, then it is probably a bug. The > first lines of the error messages normally tell what is wrong... if > you could post this, it would be great. 8) Jim sent me the error messages, and they are avaiable here: http://www.afn.org/~wilson/g++.errs Looking at the error message, there is 3 problematic lines, 159, 163 and 166, which are respectively: .def_readonly("scheme_", &Fl::scheme_) ... .def_readwrite("error", &Fl::error) ... .def("damage", (void (*)(int))&Fl::damage) Try to exclude those members. If that compiles, then we can investigate why those are not compiling. Regards, Nicodemus. From dave at boost-consulting.com Sat Jul 5 01:48:55 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 19:48:55 -0400 Subject: [C++-sig] Re: Interest in luabind References: <3efdfd94.975.16838@student.umu.se> <5.1.0.14.0.20030701203157.03a83ff0@student.umu.se> <5.1.0.14.0.20030704082338.02d44e58@student.umu.se> Message-ID: Daniel Wallin writes: > At 01:39 2003-07-04, you wrote: >>Daniel Wallin writes: >> >> > At 00:34 2003-06-29, you wrote: >> >>"Daniel Wallin" writes: >> >> >> > Ok, I have very little knowledge in how Python memory management >> > works. In luabind we always allocate dynamically. We also don't >> > support multiple inheritance from wrapped classes. >> >>Oh, but that's cheap. At least in Boost.Python it is. I assume it >>would be the same in luabind if you were using holders. > > Yeah it would. The thing is that lua doesn't have classes, all it > has is the ability to 'hook' on certain events on objects, so the > class system is something luabind introduces. Multiple inheritance > would mean we would need to make some decisions on how to handle > method-dispatching, and how to handle diamond shapes. I understand. Sounds like you made a good trade-off. > This is isolated behavior of the luabind class-system though, so it > has nothing to do with the shared code. Although, we might introduce > MI if there is sufficient need for it. Doesn't sound like it would be worthwhile. >> > The actual allocation of the holders could be in a language >> > dependent layer though, in which case it would be an implementation >> > detail if it's in-place or heap allocated. We don't have any issues >> > with allocating the holder memory together with the instance object >> > in lua. >> >>But without value_holders it seems silly, and value_holders >>themselves seem to lead to a great deal of complication, soo... >> >>Looking at the big picture I'm rather inclined to go with something >>much simpler. I guess that using placement new in value holders >>might be a way to gain a whole lot of simplicity, though. >> >>OK, here's my conclusion (hope you agree): there's no need for >>value_holders or in-dynamic-object allocation of C++ data in any >>initial merged version of the library. We can always optimize later >>if it doesn't incur too much code complexity. > > I agree that value_holders isn't needed in the initial version, but having > functions that allocate the storage for holders in language dependent > code doesn't really add any complexity. Agreed. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sat Jul 5 01:55:04 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 19:55:04 -0400 Subject: [C++-sig] Re: Interest in luabind References: <5.1.0.14.0.20030704084129.03abbac0@student.umu.se> Message-ID: Daniel Wallin writes: >>Any ideas/preferences on: Where do we discuss the refactoring of the common >>code and the laubind dev? It seems like noise polution to keep it on this >>list. Daniel do you have a non-user list set up for LuaBind? Or we can add a >>list to the SF boost project. > > We don't have any non-user list, but I could add one if needed. > I think I would prefer a separate list, for easy archiving purposes. :) OK, I just requested boost-langbinding at lists.sf.net. When it is activeated sometime in the next 24 hours you can subscribe at http://lists.sourceforge.net/mailman/listinfo/boost-langbinding -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Sat Jul 5 02:02:05 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 21:02:05 -0300 Subject: [C++-sig] Problems with Pyste from CVS. In-Reply-To: <16132.367.739589.337322@monster.linux.in> References: <16132.367.739589.337322@monster.linux.in> Message-ID: <3F06157D.2000607@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >I just updated my local CVS checkout of Boost. I tried running Pyste >and got the following traceback. The same exact pyste file worked >fine a little while earlier with an older checkout (June 25th) of CVS. > >If you need any more information let me know. I can also try and >generate a smaller test case that I can include here (right now I >don't have one). > >Thanks. >prabhu > >-------------------------------------------------- >Traceback (most recent call last): > File "/usr/local/bin/pyste.py", line 11, in ? > status = pyste.Main() > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/pyste.py", line 195, in Main > declarations, parsed_header = parser.parse(header, all_tails) > File "/usr/local/stow/pyste//lib/python2.2/site-packages/Pyste/CppParser.py", line 82, in parse > declarations = ParseDeclarations(xmlfile) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 437, in ParseDeclarations > parser.Parse(filename) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 36, in Parse > self.ParseElement(id, element) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 60, in ParseElement > func(id, element) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 371, in ParseOperatorMethod > self.ParseMethod(id, element, ClassOperator) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 356, in ParseMethod > classname = self.GetDecl(element.get('context'))._FullName() > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 98, in GetDecl > self.ParseElement(id, elem) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 60, in ParseElement > func(id, element) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/GCCXMLParser.py", line 291, in ParseClass > class_._AddMember(member) > File "/usr/local/stow/pyste/lib/python2.2/site-packages/Pyste/declarations.py", line 123, in _AddMember > m._is_unique = False >AttributeError: 'str' object has no attribute '_is_unique' > I reverted the changes that I have made before, and this bug should be gone now. Thanks for all your work on reporting this Prabhu! Regards, Nicodemus. From dave at boost-consulting.com Sat Jul 5 02:05:59 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 20:05:59 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> <3F05B3A9.7B2F29E8@sitius.com> Message-ID: Nikolay Mladenov writes: > David Abrahams wrote: >> OK, I would like to see "irrelevancies" removed from the code for any >> test case, though... unless you think the efficiency issue is closely >> related to the keyword support, in which case you'll have to convince >> me (please). > > I am not sure what needs convincing? There is an efficiency issue. Don't > you agree? I suppose so. I meant that if you want to keep those extra constructors in the examples or tests for this feature I want to be convinced that they're relevant. It sounds like you don't want to keep them, though. > I put those just so to answer you question on why I have redundant > constructor. Thanks. > I don't mean to keep them > > >> >> >> Why are you using no_init? >> > >> > For the same reason, not that it makes sence for my first example, >> > but in general, I want my most offsen called overload to be first in >> > the list - so defined last. >> >> That still doesn't explain why you'd want to use no_init. Why not >> just define the more-important constructor 2nd? > > > Are you saying that I should put the first constructor as parameter of > the class_ constructor? Well, at least you *could*. > Cause I really prefer the def way for exporting constructors. I can understand that. > I was not realizing the fact that class_() implicitly defines > default constructor for a long time, and I think that this is > somewhat confusing. Understandable. People were even more confused when BPL allowed them to write classes that couldn't be constructed by default. Maybe we should deprecate the def() way and provide a mechanism for chaining init<...>() instances in the class_<...> constructor (e.g. with commas). At least that would focus all attention in the same place. >> >> ...and shouldn't we get rid of the need to write the outer >> >> "args(...)"? >> > It is not necessary to have it, you can write >> > (arg("a") = (int)0, arg("b") = (double)0, arg("n") = std::string())) >> > instead of >> > args(arg("a") = (int)0, arg("b") = (double)0, arg("n") = >> > std::string())) >> > but you'll probably want >> > args("a","b","c", arg("n") = std::string())) >> > instead of >> > (arg("a"), arg("b"), arg("c"), arg("n") = std::string())) >> >> Understood... but is it really wise to give people more than One (And >> Preferably Only One) Obvious Way To Do It? > > > Why not? It's "unpythonic". Have you tried >>> import this ? > They are not *too* different, are they? Sometimes things which are almost the same but subtly different are worse than things which are very different. It bothers me to have two things like that whose name differs only in plurality. >> I might be inclined to support only: >> >> args("a","b","c") >> >> and: >> >> (arg("a"), arg("b"), arg("c"), arg("n") = std::string())) >> >> Or even drop the 1st and go with >> >> (arg("a"), arg("b"), arg("c")) >> >> Thoughts? > > > Well, originally I thought that args() is already in the library so > it should not be removed. We could keep it for backward compatibility but deprecate it by removing it from the docs. > So if you insist on being minimal I don't insist on it, but I think it might be a good idea. > than probably we should support > > args("a","b","c") // which is already there Grr... > arg("d")=1 I like this one. > and at the end: > > ( args("a","b","c"), arg("d")=1, arg("e")=std::string() ) Grr... What about ( arg("a"),"b", "c", arg("d")=1, arg("e")=std::string() ) Instead? > ( arg("a"), arg("d")=1, arg("e")=std::string() ) Fine. -Dave P.S. I'm not terribly convinced of my own position here. Any bit of additional resistance from you and I'll probably cave ;-) -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Sat Jul 5 02:06:48 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 21:06:48 -0300 Subject: [C++-sig] Re: Problems with Pyste from CVS. In-Reply-To: References: <16132.367.739589.337322@monster.linux.in> <3F040A11.1010508@globalite.com.br> <16132.8291.587836.869633@monster.linux.in> <3F04C272.6030002@globalite.com.br> Message-ID: <3F061698.5080101@globalite.com.br> David Abrahams wrote: >Nicodemus writes: > > > >>Any one has any ideas? They are most welcome. >> >> > >Names containing double underscores or starting with an underscore >followed by a capital letter are reserved to the C++ implementation, >so they can't conflict with anything the user might legally define as >a class member. > Thanks for the suggestion Dave! But "void _Foo(int) {}" compiles fine with intel 7.1.0. I am not saying that you are wrong, but apparently some code with an underscore followed by a capital letter compiles fine depending on the compiler. So I assume that there is code that uses invalid names, even thought the specification says otherwise... From dave at boost-consulting.com Sat Jul 5 02:46:12 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 20:46:12 -0400 Subject: [C++-sig] Re: Interest in luabind References: <5.1.0.14.0.20030704084129.03abbac0@student.umu.se> Message-ID: David Abrahams writes: > Daniel Wallin writes: > >>>Any ideas/preferences on: Where do we discuss the refactoring of the common >>>code and the laubind dev? It seems like noise polution to keep it on this >>>list. Daniel do you have a non-user list set up for LuaBind? Or we can add a >>>list to the SF boost project. >> >> We don't have any non-user list, but I could add one if needed. >> I think I would prefer a separate list, for easy archiving purposes. :) > > OK, I just requested boost-langbinding at lists.sf.net. When it is > activeated sometime in the next 24 hours you can subscribe at > http://lists.sourceforge.net/mailman/listinfo/boost-langbinding It's up now. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sat Jul 5 02:48:10 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 20:48:10 -0400 Subject: [C++-sig] Re: Problems with Pyste from CVS. References: <16132.367.739589.337322@monster.linux.in> <3F040A11.1010508@globalite.com.br> <16132.8291.587836.869633@monster.linux.in> <3F04C272.6030002@globalite.com.br> <3F061698.5080101@globalite.com.br> Message-ID: Nicodemus writes: > David Abrahams wrote: > >>Nicodemus writes: >> >> >>>Any one has any ideas? They are most welcome. >>> >> >>Names containing double underscores or starting with an underscore >>followed by a capital letter are reserved to the C++ implementation, >>so they can't conflict with anything the user might legally define as >>a class member. >> > > Thanks for the suggestion Dave! > > But "void _Foo(int) {}" compiles fine with intel 7.1.0. > > I am not saying that you are wrong, but apparently some code with an > underscore followed by a capital letter compiles fine depending on the > compiler. Almost any compiler will compile that without complaint. The standard library has to compiles *somehow* ;-) > So I assume that there is code that uses invalid names, even thought > the specification says otherwise... Sure, but we can only be expected to work reliably on correct code. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Sat Jul 5 02:59:04 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 21:59:04 -0300 Subject: [C++-sig] Re: Problems with Pyste from CVS. In-Reply-To: References: <16132.367.739589.337322@monster.linux.in> <3F040A11.1010508@globalite.com.br> <16132.8291.587836.869633@monster.linux.in> <3F04C272.6030002@globalite.com.br> <3F061698.5080101@globalite.com.br> Message-ID: <3F0622D8.1010709@globalite.com.br> David Abrahams wrote: >Nicodemus writes: > > > >>David Abrahams wrote: >> >> >>>Names containing double underscores or starting with an underscore >>>followed by a capital letter are reserved to the C++ implementation, >>>so they can't conflict with anything the user might legally define as >>>a class member. >>> >>> >>> >>Thanks for the suggestion Dave! >> >>But "void _Foo(int) {}" compiles fine with intel 7.1.0. >> >>I am not saying that you are wrong, but apparently some code with an >>underscore followed by a capital letter compiles fine depending on the >>compiler. >> >> > >Almost any compiler will compile that without complaint. The >standard library has to compiles *somehow* ;-) > > > >>So I assume that there is code that uses invalid names, even thought >>the specification says otherwise... >> >> > >Sure, but we can only be expected to work reliably on correct code. > Yeah, seems good enough. 8) Thanks again for the suggestion. Regards, Nicodemus. From wilson at afn.org Sat Jul 5 03:24:47 2003 From: wilson at afn.org (Jim Wilson) Date: Fri, 04 Jul 2003 21:24:47 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: <3F06096B.9080005@globalite.com.br> References: <3F04C9A9.1070907@globalite.com.br> <3F04DAB9.6000906@globalite.com.br> <3F06096B.9080005@globalite.com.br> Message-ID: Nicodemus, Remember, I only sent you the first forty lines. I excluded the three functions you suggested, and it got better. Following your example, I grepped g++'s compiler output (a nasty process involving copying and pasting from my terminal since I still can't coerce g++ to write to stderr or stdout) and found ten more offending functions embedded inside 200 lines of error messages. I excluded those, and on the next pass only five. The next pass only three, ... Finally, after I eliminated seemingly all overloaded functions: exclude(f.scheme_) # Your three exclude(f.error) exclude(f.damage) exclude(f.idle) # Plus a few more exclude(f.warning) exclude(f.atclose) exclude(f.scheme_bg_) exclude(f.add_handler) exclude(f.set_labeltype) exclude(f.set_boxtype) exclude(f.args) exclude(f.add_timeout) exclude(f.add_fd) exclude(f.set_idle) exclude(f.set_atclose) exclude(f.remove_handler) exclude(f.fatal) exclude(f.repeat_timeout) exclude(f.has_timeout) exclude(f.set_abort) exclude(f.remove_timeout) exclude(f.add_check) exclude(f.remove_check) exclude(f.add_idle) exclude(f.has_idle) exclude(f.remove_idle) it compiled! Of course, it sucked in a few new libraries, but I scurried around and found them all. Alas, still no joy. But no "Abort" either! >>>from fltk import Fl,Fl_Window Traceback (most recent call last): File "", line 1, in ? RuntimeError: Boost.Python - All overloads must be exported before \ calling 'class_<...>("Fl").staticmethod("scheme")' I hope this gives you a clue, because I'm clueless. Jim From wilson at afn.org Sat Jul 5 03:27:51 2003 From: wilson at afn.org (Jim Wilson) Date: Fri, 04 Jul 2003 21:27:51 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: References: Message-ID: David, > The problems in my reference have much more to do with the volatile > nature of whatever's at the end of your C++ void* than with the > volatile nature of Python objects. At least the latter have > destructors which can be hooked. Then, I misunderstood completely. I can certainly see a problem if some FLTK Widget wasn't informed of the demise of its "callback" or its associated "data". I can further understand there would be hell to pay if FLTK arbitrarily delete'd something without communicating the fact to the Python wrapper. As I admitted elsewhere, I am not a Pythonista; I am only a sympathizer. My experience with FLTK has only been with C++, and only pidjin C++ at that, but I have been quite pleased with the way FLTK upholds its contracts. Now, it may be FLTK programs/data data tend to be small enough to elude thrashing pointers, while Python data (with the interpreter) tend to obesity thus becoming easy targets for those same pointers. >> I can imagine that something deep in the bowels of some Boost >> template library has become upset with "void (*func)(...)", and has >> justifiably decided to issue a long, incomprehensible (to me) >> complaint about it. > > Not if, as you described, it's a runtime Abort. That was a crash, > plain and simple, and as I've tried to suggest I think it's a > FLTK-ish sort of thing having to do with the inability to manage > object lifetimes in a disciplined way. I assume you hadn't yet read my followup to my own post: http://article.gmane.org/gmane.comp.python.c%2B%2B/3666 > [Overridable virtual methods] provided by FLTK? That's news to me! You and I are likely on different planes of understanding . Too many ()'s in a row make my eyes water, so this may not be what you were talking about. FLTK's "Fl_Widget" is the base class for almost everything in FLTK; it provides a unary virtual method "void handle(int)" to receive events intended for the Widget. ("Nullary" sounds LISPish to me. I didn't graduate MIT; I flunked out of Purdue. I had to Google "nullary function" to discover it was a function with no parameters. I would be quite content with such a function. I could then use (subclassed) Widget methods to extract any information the parameter might have conveyed.) >> For what it's worth, I can cause pyFLTK's SWIG-generated wrapper issue a >> somewhat related diagnostic: "Segmentation fault" . > > > Probably the same FLTK-ish sort of thing I referred to just now. Could be, but I didn't give FLTK too much chance to lob any pointers with the pin pulled out. FYE, here is the interactive Python: >>> from fltk import Fl,Fl_Window,Fl_Button # SWIGed, not Boosted >>> w = Fl_Window(300,200) # Create a little window >>> Fl_Button(100,75,100,50,"Click Here") # Pay no attention to the man ... >>> w.show # Oops! I meant w.show() > >>> w.show() Segmentation fault PyFLTK is just as new as Pyste. To my eye, SWIG specs are quite complicated. I suspect something is amiss a little higher than FLTK. I undertook my little experiment in hopes that I could convince the pyFLTK guys of my assertion that a Boost.python extension would be smaller than a SWIG based one. If Pyste delivers on its promise, it *certainly* would be easier to maintain. Jim From nickm at sitius.com Sat Jul 5 03:42:24 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Fri, 04 Jul 2003 21:42:24 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> <3F05B3A9.7B2F29E8@sitius.com> Message-ID: <3F062D00.65E0B4D6@sitius.com> David Abrahams wrote: > > Nikolay Mladenov writes: > > > David Abrahams wrote: > >> OK, I would like to see "irrelevancies" removed from the code for any > >> test case, though... unless you think the efficiency issue is closely > >> related to the keyword support, in which case you'll have to convince > >> me (please). > > > > I am not sure what needs convincing? There is an efficiency issue. Don't > > you agree? > > I suppose so. I meant that if you want to keep those extra > constructors in the examples or tests for this feature I want to be > convinced that they're relevant. It sounds like you don't want to > keep them, though. It is probably good to make clear the advantages and disadvantage of the different ways of defining optional arguments, but I don't insist doing it in the keywords docs and samples. I'll keep those extra constructors in my code though:) > > I was not realizing the fact that class_() implicitly defines > > default constructor for a long time, and I think that this is > > somewhat confusing. > > Understandable. People were even more confused when BPL allowed them > to write classes that couldn't be constructed by default. > > Maybe we should deprecate the def() way and provide a mechanism for > chaining init<...>() instances in the class_<...> constructor > (e.g. with commas). At least that would focus all attention in the > same place. I would better like it if def is the only way of defining constructors. Initially I thought that staticmethod should be implemented as policy, but you convinced me into the "python"-ian way: staticmethod is a statement in python. Well so is __init__, and in python it is def'ed as any other method. Why should we explicitly specify that the class is not constructable (with no_init) (the c++ way), instead of explicitly exporting constructor with def (the python way). "There should be one-- and preferably only one --obvious way to do it" ;-) and def should be it for exporting methods:) I have exported a lot non-constructable classes as bases and as collections of staticmethods. And we don't really need the default constructability shortcut, especially now, having pyste. > It's "unpythonic". Have you tried > > >>> import this > I see:). Zen is speaking:) It was good reminding it. > What about > > ( arg("a"),"b", "c", arg("d")=1, arg("e")=std::string() ) > I had not thought about that one and I like it. And I'll do it. > Instead? > > > ( arg("a"), arg("d")=1, arg("e")=std::string() ) > > Fine. > > -Dave > > P.S. I'm not terribly convinced of my own position here. Any bit of > additional resistance from you and I'll probably cave ;-) I wasn't really resisting. Until you mentioned deprecating def(init<...>()). And if you promise to forget about it, than we can probably say we agree:) Regards, Nikolay From nicodemus at globalite.com.br Sat Jul 5 03:40:48 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 04 Jul 2003 22:40:48 -0300 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: References: <3F04C9A9.1070907@globalite.com.br> <3F04DAB9.6000906@globalite.com.br> <3F06096B.9080005@globalite.com.br> Message-ID: <3F062CA0.6000706@globalite.com.br> Hi Jim, Jim Wilson wrote: > >>>from fltk import Fl,Fl_Window > Traceback (most recent call last): > File "", line 1, in ? > RuntimeError: Boost.Python - All overloads must be exported > before \ > calling 'class_<...>("Fl").staticmethod("scheme")' > > I hope this gives you a clue, because I'm clueless. Hah! You just found a bug, congratulations! ;) I didn't know myself, but you have to use "staticmethod" only after all the overloads of a static method were exported. Consider: struct C { static int foo(int x) { return x; } static int foo(int x, int y) { return y; } }; Pyste naively generates: class_< C >("C", init< >()) .def(init< const C& >()) .def("foo", (int (*)(int))&C::foo) .staticmethod("foo") .def("foo", (int (*)(int, int))&C::foo) .staticmethod("foo") ; And running that from Python gives the same error. 8) It should generate: class_< C >("C", init< >()) .def(init< const C& >()) .def("foo", (int (*)(int))&C::foo) .def("foo", (int (*)(int, int))&C::foo) .staticmethod("foo") ; I will fix ASAP (tomorrow I don't think it is possible, because I am about to leave home), but tomorrow it should be fixed. 8) Why the other functions didn't compile is still a mistery. Could you post the signature of one of them, along with the generated code for that function? Also, thanks a lot for all your efforts in finding this problems! Regards, Nicodemus. From dave at boost-consulting.com Sat Jul 5 04:12:35 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 22:12:35 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python References: Message-ID: Jim Wilson writes: > David, > > > The problems in my reference have much more to do with the volatile > > nature of whatever's at the end of your C++ void* than with the > > volatile nature of Python objects. At least the latter have > > destructors which can be hooked. > > > Then, I misunderstood completely. I can certainly see a problem if > some FLTK Widget wasn't informed of the demise of its "callback" or > its associated "data". I can further understand there would be hell > to pay if FLTK arbitrarily delete'd something without communicating > the fact to the Python wrapper. > > As I admitted elsewhere, I am not a Pythonista; I am only a sympathizer. > My experience with FLTK has only been with C++, and only pidjin C++ at > that, but I have been quite pleased with the way FLTK upholds its > contracts. If you don't guarantee very much, it's easy to meet expectations . > Now, it may be FLTK programs/data data tend to be small enough to > elude thrashing pointers, while Python data (with the interpreter) > tend to obesity thus becoming easy targets for those same pointers. Maybe. I won't speculate. > > [Overridable virtual methods] provided by FLTK? That's news to me! > > You and I are likely on different planes of understanding . Too many > ()'s in a row make my eyes water, so this may not be what you were talking > about. > > FLTK's "Fl_Widget" is the base class for almost everything in FLTK; > it provides a unary virtual method "void handle(int)" to receive events > intended for the Widget. Well, OK, but I meant that instead of passing around unbundled function pointers + void*s for additional data it would be better to pass a pointer to an object with a virtual destructor and invocation function, so that destruction could do something intelligent. > ("Nullary" sounds LISPish to me. I didn't graduate MIT; Me neither. > I flunked out of Purdue. I had to Google "nullary function" to > discover it was a function with no parameters. So sorry. > I would be quite content with such a function. I could then use > (subclassed) Widget methods to extract any information the parameter > might have conveyed.) > > >> For what it's worth, I can cause pyFLTK's SWIG-generated wrapper issue a > >> somewhat related diagnostic: "Segmentation fault" . > > > > > > Probably the same FLTK-ish sort of thing I referred to just now. > > > Could be, but I didn't give FLTK too much chance to lob any pointers with > the pin pulled out. FYE, here is the interactive Python: > > >>> from fltk import Fl,Fl_Window,Fl_Button # SWIGed, not Boosted > >>> w = Fl_Window(300,200) # Create a little window > >>> Fl_Button(100,75,100,50,"Click Here") # Pay no attention to the man ... > > >>> w.show # Oops! I meant w.show() > > > >>> w.show() > Segmentation fault Hard to tell much from that. > PyFLTK is just as new as Pyste. To my eye, SWIG specs are quite > complicated. I suspect something is amiss a little higher than > FLTK. I undertook my little experiment in hopes that I could > convince the pyFLTK guys of my assertion that a Boost.python > extension would be smaller than a SWIG based one. That would be interesting, if so. I've already had reports that they're faster (to my great surprise). > If Pyste delivers on its promise, it *certainly* would be easier to > maintain. That would be delicious. Do let us know how things turn out. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sat Jul 5 04:25:06 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 04 Jul 2003 22:25:06 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> <3F05B3A9.7B2F29E8@sitius.com> <3F062D00.65E0B4D6@sitius.com> Message-ID: Nikolay Mladenov writes: > David Abrahams wrote: >> >> Nikolay Mladenov writes: >> >> > David Abrahams wrote: >> >> >> OK, I would like to see "irrelevancies" removed from the code for any >> >> test case, though... unless you think the efficiency issue is closely >> >> related to the keyword support, in which case you'll have to convince >> >> me (please). >> > >> > I am not sure what needs convincing? There is an efficiency issue. Don't >> > you agree? >> >> I suppose so. I meant that if you want to keep those extra >> constructors in the examples or tests for this feature I want to be >> convinced that they're relevant. It sounds like you don't want to >> keep them, though. > > > It is probably good to make clear the advantages and disadvantage of > the different ways of defining optional arguments Agreed. > but I don't insist doing it in the keywords docs and samples. Good. Probably the tutorial should have some info about this. > I'll keep those extra constructors in my code though:) It's your code! >> > I was not realizing the fact that class_() implicitly defines >> > default constructor for a long time, and I think that this is >> > somewhat confusing. >> >> Understandable. People were even more confused when BPL allowed >> them to write classes that couldn't be constructed by default. >> >> Maybe we should deprecate the def() way and provide a mechanism for >> chaining init<...>() instances in the class_<...> constructor >> (e.g. with commas). At least that would focus all attention in the >> same place. > > I would better like it if def is the only way of defining constructors. > Initially I thought that staticmethod should be implemented as policy, > but you convinced me into the "python"-ian way: staticmethod is a > statement in python. > Well so is __init__, and in python it is def'ed as any other > method. Well, that's a good point. > Why should we explicitly specify that the class is not constructable > (with no_init) (the c++ way), > instead of explicitly exporting constructor with def (the python way). > "There should be one-- and preferably only one --obvious way to do it" > ;-) > and def should be it for exporting methods:) I understand the principle, but sometimes you have to make compromises at the language boundary. Besides, not having to explicitly specify default constructors is both the C++ and the Python way. Consider: >>> class Foo: ... pass # no explicit __init__ ... >>> x = Foo() # OK struct Foo {}; // no explicit constructor Foo x; // OK Why should I have to write an explicit __init__ in order to expose Foo to Python? > I have exported a lot non-constructable classes as bases and as > collections of staticmethods. Yes, but at least if the class is abstract you'll get a compile-time error if you don't supply no_init, while if we eliminate the default constructor definition compiling and linking would succeed for default constructible classes, but fail at runtime when you try to instantiate them (unless you remember the init<...>(), which maybe doesn't appear anywhere in the C++ class declaration). I consider failing at compile time to be far superior. > And we don't really need the default constructability shortcut, > especially now, having pyste. A lot of people still don't use Pyste. >> It's "unpythonic". Have you tried >> >> >>> import this > > I see:). Zen is speaking:) > It was good reminding it. > >> What about >> >> ( arg("a"),"b", "c", arg("d")=1, arg("e")=std::string() ) >> > > I had not thought about that one and I like it. And I'll do it. > > >> Instead? >> >> > ( arg("a"), arg("d")=1, arg("e")=std::string() ) >> >> Fine. >> >> -Dave >> >> P.S. I'm not terribly convinced of my own position here. Any bit of >> additional resistance from you and I'll probably cave ;-) > > > I wasn't really resisting. Until you mentioned deprecating > def(init<...>()). And if you promise to forget about it, than we > can probably say we agree:) I guess I'm not feeling quite *that* relaxed yet ;-) -- Dave Abrahams Boost Consulting www.boost-consulting.com From prabhu at aero.iitm.ernet.in Sat Jul 5 04:37:47 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 08:07:47 +0530 Subject: [C++-sig] Installing Pyste. In-Reply-To: <3F060527.8020707@globalite.com.br> References: <16132.353.879474.386569@monster.linux.in> <3F040AAB.1060008@globalite.com.br> <16132.9397.35714.194993@monster.linux.in> <3F060527.8020707@globalite.com.br> Message-ID: <16134.14843.810333.125316@monster.linux.in> >>>>> "N" == nicodemus writes: >> [Pyste setup script] N> I added it to the distribution, it is in N> "libs/python/pyste/install". I moved the pyste/src dir to N> pyste/src/Pyste, and made a few changes to your setup.py. N> Thanks a lot Prabhu! Great! In that case you could also move the pyste/src/Pyste/pyste.py script into pyste/src and modify it to import modules from the Pyste package. If this is done you will no longer need the separate pyste.py script. Unfortunately I can't see/get your latest changes to the code in CVS or submit a patch since pserver access to CVS for me is via the backup server and is delayed by about 24hrs. :( cheers, prabhu From prabhu at aero.iitm.ernet.in Sat Jul 5 04:44:51 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 08:14:51 +0530 Subject: [C++-sig] Pyste: bug: overriding overloaded virtual functions. In-Reply-To: <3F060594.6020809@globalite.com.br> References: <16133.54787.174958.488899@monster.linux.in> <3F060594.6020809@globalite.com.br> Message-ID: <16134.15267.100344.853472@monster.linux.in> >>>>> "N" == nicodemus writes: N> I just applied your patch. I really appreciate your effort in N> finding this problems, thanks a lot! No problem. I also tried solving the problem where Pyste was not generating wrapper code for virtual operators. Unfortunately the code was a little too complex and I was not able to generate a patch. I thought I had to re-order some of the function definitions (move ExportOperators above ExportVirtualFunctions etc.) and did not want to go that far. Is this also fixed in CVS? Thanks! cheers, prabhu From prabhu at aero.iitm.ernet.in Sat Jul 5 04:58:17 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 08:28:17 +0530 Subject: [C++-sig] Pyste: feature requests In-Reply-To: <3F060729.4040409@globalite.com.br> References: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> <3F060729.4040409@globalite.com.br> Message-ID: <16134.16073.870902.351091@monster.linux.in> >>>>> "N" == nicodemus writes: >> 1. Something like the C compiler's '-c' option. In this case >> Pyste >> should simply generate the wrapper code and none of the module >> code i.e. for an invocation like so: >> >> pyste.py --out build --multiple -c file1.pyste N> I don't understand exactly what you are saying. Are you N> suggesting that instead of generating: N> #include <...> N> BOOST_PYTHON_MODULE(module) { N> class_(...); N> } N> You want to be able to generate just this: N> class_(...); N> ? N> How does that help you handle dependencies? No, what I mean is 'pyste.py --multiple -c file.pyste' should generate this (edited for brevity): // ------------ _file.cpp ---------- // Includes ===== #include // Using ======= using namespace boost::python; // Declarations ==== namespace { struct test_A_Wrapper: test::A { [...] }; [ other wrappers etc. ] // Module =========== void _Export_file_pyste() { class_<...> } // ------------ _file.cpp ---------- And without -c this command: pyste.py --module=test --multiple file1.pyste file2.pyste should *only* generate: // ---------- test.cpp ---------- // Include ============== #include // Exports =============== void _Export_file_pyste(); // Module ================ BOOST_PYTHON_MODULE(test) { _Export_file_pyste(); } // ---------- test.cpp ---------- I hope this is clear. I think you will see what I am getting at here. This way if file.pyste changes then only _file.cpp changes. None of the other wrapper code sources will change and pyste will run faster since all you need to process is one of the pyste files. Its much easier for users to use and incrementally wrap their libraries and very convenient for development. >> 2. Instead of generating files for each header, it would be >> useful if >> one file were generated per pyste file when --multiple were N> Good idea! When I implemented the --multiple option, I didn't N> consider dependencies. I will put in my TODO list, shouldn't be N> too hard to implement this. That would be great! Thanks! N> Thanks a lot for your suggestions! My pleasure! cheers, prabhu From nickm at sitius.com Sat Jul 5 05:20:13 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Fri, 04 Jul 2003 23:20:13 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> <3F05B3A9.7B2F29E8@sitius.com> <3F062D00.65E0B4D6@sitius.com> Message-ID: <3F0643ED.2FC59290@sitius.com> David Abrahams wrote: > >> Maybe we should deprecate the def() way and provide a mechanism for > >> chaining init<...>() instances in the class_<...> constructor > >> (e.g. with commas). At least that would focus all attention in the > >> same place. > > > > I would better like it if def is the only way of defining constructors. > > Initially I thought that staticmethod should be implemented as policy, > > but you convinced me into the "python"-ian way: staticmethod is a > > statement in python. > > Well so is __init__, and in python it is def'ed as any other > > method. > > Well, that's a good point. So you agree here. > > > Why should we explicitly specify that the class is not constructable > > (with no_init) (the c++ way), > > instead of explicitly exporting constructor with def (the python way). > > "There should be one-- and preferably only one --obvious way to do it" > > ;-) > > and def should be it for exporting methods:) > > I understand the principle, but sometimes you have to make compromises > at the language boundary. Besides, not having to explicitly specify > default constructors is both the C++ and the Python way. Consider: > > >>> class Foo: > ... pass # no explicit __init__ > ... > >>> x = Foo() # OK > > struct Foo {}; // no explicit constructor > Foo x; // OK > > Why should I have to write an explicit __init__ in order to expose > Foo to Python? And I do here. > > > I have exported a lot non-constructable classes as bases and as > > collections of staticmethods. > > Yes, but at least if the class is abstract you'll get a compile-time > error if you don't supply no_init, while if we eliminate the default > constructor definition compiling and linking would succeed for default > constructible classes, but fail at runtime when you try to instantiate > them (unless you remember the init<...>(), which maybe doesn't appear > anywhere in the C++ class declaration). I consider failing at compile > time to be far superior. And completely agree here Ok. I see the dilemma. And I'm starting see your point about the comma separated inits, though I wouldn't really enjoy writing them. But this is getting a little bit far from the keywords, and the init problem really got me cycling. > > I guess I'm not feeling quite *that* relaxed yet ;-) > So, do you feel we have differences left about the keywords? From prabhu at aero.iitm.ernet.in Sat Jul 5 05:52:35 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 09:22:35 +0530 Subject: [C++-sig] Allocating objects on the heap by default. Message-ID: <16134.19331.719492.865019@monster.linux.in> Hi, I have a question that I'm not sure has much to do with Boost.Python itself but I'm wrapping some code via Boost.Python and need to know what the best approach is to solve the problem. The code is designed to be used by allocating objects on the heap (via new) and handing them off to very simple containers that manage these objects. The lifetime of the objects is also managed by the container. So here is a quick example. // -------------------- class Obj { public: Obj(); ~Obj(); }; class Mgr { public: Mgr(); ~Mgr(); // deletes memory for objects in container. void add(Obj* a); void popBack(); private: std::vector arr; }; void usage() { Obj *o = new Obj(); Mgr *m = new Mgr(); m->add(o); delete m; } // -------------------- Perhaps the design is totally stupid, but its used consistently everywhere and quite simple once you know you can't delete an object you created and passed to a manager. Juas as the user has to manage and remember to invoke delete for every new he has to remember that the manager manages memory as well. I don't see that as a bad decision but I guess purists would not agree with me. Anyway, I want to wrap the code above (except the usage function) and want to arrange for Boost.Python to allocate all of the objects, Obj and Mgr in the heap by default. After wrapping the above via Boost.Python and using it from Python this is what happens: >>> import test >>> a = test.Obj() >>> b = test.Mgr() >>> b.add(a) >>> del b Segmentation fault. Trouble here is that Obj is not allocated on the heap but on the stack, just as one would expect in C++. Yes, I read the penultimate FAQ entry and my question is: can I arrange the wrappers to automatically allocate Obj and Mgr objects on the heap and additionally be handled by a shared_ptr/auto_ptr without having to write a factory function like NewObj for every single class? I'd like to avoid writing factory functions just to do this since I have lots of classes like this. If the object is allocated on the heap by default and I manage the object via boost::shared_ptr then the above segfault will not happen. Is there a way that this can be handled easily? Alternatively can this be generated via Pyste/Python magic? FWIW and FYI, not that it matters but SWIG does this by default -- allocates everything via new and deals with the resulting opaque pointers. Also, is the above approach of creating objects and handing them off to a manager a bad thing to do in general? Whats a better approach? This is a generic c++ question but the issue arises in the context of wrapping so I thought it sufficient relevant to post here and not a c++ list. I'm sorry if this is inappropriate. Any suggestions will be much appreciated. Thanks! cheers, prabhu From vladimir at pobox.com Sat Jul 5 09:59:00 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: Sat, 05 Jul 2003 00:59:00 -0700 Subject: [C++-sig] boost::python and threads Message-ID: <3F068544.10204@pobox.com> Howdy, I'm working on wrapping a C++ library that heavily uses threads internally, and makes callbacks to user-defined functions on various non-user-created threads. (This is basically the situation that provided the impetus for PEP 311, after discussion on python-dev -- note that I'm working with Python 2.3 because of this, but I beileve that the PEP 311 patch could be back-ported to 2.2 should anyone need it.) However, I'm running into problems getting the correct wrappers for my classes, to get the various Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS and PyGILState_Ensure/PyGILState_Release combos in the various places. A little background about my problem: from an IDL for a Foo interface, I generate two C++ classes, "Foo" and "FooProxy". Both of these are wrapped in smart pointers and are always passed as such in the C++ library, so we have FooHandle and FooProxyHandle. If Foo defines a "bar();" operation, then class Foo will have a "virtual void bar() = 0;", and I have to subclass and implement it, from python or C++. I have a wrapper class that does the call_method<>() dance; in this wrapper class, I also place PyGILState_Ensure/PyGILState_Release around the call_method<>() call. FooProxy is a remote object that I get as a result of calling various functions to get a proxy -- it has a "void bar();" (non-virtual) that I can call. However, because the call can be made synchronously, I need to wrap the call to bar() with Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS. It's this problem that I'm directly dealing with -- I can't figure out a way to wrap class FooProxy such that I can manage the current ThreadState and the GIL around them. I can create another wrapper class that does the right thing and calls FooProxy::bar(), but functions are returning a FooProxy (not mywrapper_for_FooProxy), and I already have a Handle as a wrapper specified in the boost::python class_... so I end up with incorrect types half the time. However, an alternative solution that I was thinknig of is to bake the thread smarts directly into boost::python. It seems to me that call_method and similar should always be wrapped with a PyGILState_Ensure/PyGILState_Release. Also, an additional call policy could be added, something like "allow_threads", which would cause b::p to call Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the function invocation on C++. This seems like a much more generally useful solution than me trying to do the dance in wrapper classes. Is this the right way to go? If so, I'd appreciate any pointers on implementing a new call policy, especially if it's possible to both specify allow_threads and a return_value_policy. Thanks, - Vladimir From prabhu at aero.iitm.ernet.in Sat Jul 5 15:41:05 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 19:11:05 +0530 Subject: [C++-sig] Random access iterators, and sequence protocol. Message-ID: <16134.54641.351847.619835@monster.linux.in> Hi, I have a container class that defines an operator [] (std::size_t) and also has a size function that returns the number of elements in the container. It does not provide access to an internal iterator. To get the '[]' wrapped with Pyste I need to rename the function as __getitem__ of course. I also renamed size to __len__. However, I would like to do this: for i in container: i.something() To do this __getitem__ needs to generate an IndexError when the index is greater than or equal to size. Do I _have_ to register an exception translator from something like std::range_error? Is there an easier way to do this? The docs don't reveal any easier solutions. It would be nice if this were also as easy as doing it via range, or iterator. :) Thanks. cheers, prabhu From dalwan01 at student.umu.se Sat Jul 5 15:59:04 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Sat, 05 Jul 2003 15:59:04 +0200 Subject: [C++-sig] Re: Interest in luabind In-Reply-To: References: <5.1.0.14.0.20030704084129.03abbac0@student.umu.se> Message-ID: <5.1.0.14.0.20030705155844.03b1ee78@student.umu.se> At 02:46 2003-07-05, you wrote: >David Abrahams writes: > > > Daniel Wallin writes: > >> We don't have any non-user list, but I could add one if needed. > >> I think I would prefer a separate list, for easy archiving purposes. :) > > > > OK, I just requested boost-langbinding at lists.sf.net. When it is > > activeated sometime in the next 24 hours you can subscribe at > > http://lists.sourceforge.net/mailman/listinfo/boost-langbinding > >It's up now. Ok great. --- Daniel Wallin From nicodemus at globalite.com.br Sat Jul 5 18:13:39 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sat, 05 Jul 2003 13:13:39 -0300 Subject: [C++-sig] Installing Pyste. In-Reply-To: <16134.14843.810333.125316@monster.linux.in> References: <16132.353.879474.386569@monster.linux.in> <3F040AAB.1060008@globalite.com.br> <16132.9397.35714.194993@monster.linux.in> <3F060527.8020707@globalite.com.br> <16134.14843.810333.125316@monster.linux.in> Message-ID: <3F06F933.8000804@globalite.com.br> Prabhu Ramachandran wrote: >>>>>>"N" == nicodemus writes: >>>>>> >>>>>> > > >> [Pyste setup script] > > N> I added it to the distribution, it is in > N> "libs/python/pyste/install". I moved the pyste/src dir to > N> pyste/src/Pyste, and made a few changes to your setup.py. > N> Thanks a lot Prabhu! > >Great! In that case you could also move the pyste/src/Pyste/pyste.py >script into pyste/src and modify it to import modules from the Pyste >package. If this is done you will no longer need the separate >pyste.py script. Unfortunately I can't see/get your latest changes to >the code in CVS or submit a patch since pserver access to CVS for me >is via the backup server and is delayed by about 24hrs. :( > > Don't worry, I made the necessary changes. I reduced pyste.py to: from Pyste import pyste pyste.Main() To avoid code duplication, and changed the setup.py to work from pyste/install. 8) Thanks again for the contribution! Regards, Nicodemus. From nicodemus at globalite.com.br Sat Jul 5 18:20:30 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sat, 05 Jul 2003 13:20:30 -0300 Subject: [C++-sig] Pyste: feature requests In-Reply-To: <16134.16073.870902.351091@monster.linux.in> References: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> <3F060729.4040409@globalite.com.br> <16134.16073.870902.351091@monster.linux.in> Message-ID: <3F06FACE.1030005@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >>>>>>"N" == nicodemus writes: >>>>>> >>>>>> > > >> 1. Something like the C compiler's '-c' option. In this case > >> Pyste > >> should simply generate the wrapper code and none of the module > >> code i.e. for an invocation like so: > >> > >> pyste.py --out build --multiple -c file1.pyste > > N> I don't understand exactly what you are saying. Are you > N> suggesting that instead of generating: > > N> #include <...> > N> BOOST_PYTHON_MODULE(module) { > N> class_(...); > N> } > > N> You want to be able to generate just this: > N> class_(...); > N> ? > > N> How does that help you handle dependencies? > >No, what I mean is 'pyste.py --multiple -c file.pyste' should generate >this (edited for brevity): > >// ------------ _file.cpp ---------- >// Includes ===== >#include >// Using ======= >using namespace boost::python; >// Declarations ==== >namespace { >struct test_A_Wrapper: test::A >{ >[...] >}; >[ other wrappers etc. ] >// Module =========== >void _Export_file_pyste() >{ > class_<...> >} >// ------------ _file.cpp ---------- > >And without -c this command: > pyste.py --module=test --multiple file1.pyste file2.pyste >should *only* generate: > >// ---------- test.cpp ---------- >// Include ============== >#include >// Exports =============== >void _Export_file_pyste(); > >// Module ================ >BOOST_PYTHON_MODULE(test) >{ > _Export_file_pyste(); >} >// ---------- test.cpp ---------- > >I hope this is clear. I think you will see what I am getting at here. >This way if file.pyste changes then only _file.cpp changes. None of >the other wrapper code sources will change and pyste will run faster >since all you need to process is one of the pyste files. Its much >easier for users to use and incrementally wrap their libraries and >very convenient for development. > I see. Unfortunately this breaks backward compability. 8/ But notice that Pyste only overwrites files if they changed, otherwise it leaves them intact, so as to not disturb build systems out there that depend on time-stamps. I think a good option would be something like --xml-cache=, where Pyste would get the generated gccxml files, or write them there in case they are not found. The bottleneck with Pyste is always GCCXML, since it has to basically compile the source files. What do you think? Regards, Nicodemus. From nicodemus at globalite.com.br Sat Jul 5 18:25:41 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sat, 05 Jul 2003 13:25:41 -0300 Subject: [C++-sig] Pyste: bug: overriding overloaded virtual functions. In-Reply-To: <16134.15267.100344.853472@monster.linux.in> References: <16133.54787.174958.488899@monster.linux.in> <3F060594.6020809@globalite.com.br> <16134.15267.100344.853472@monster.linux.in> Message-ID: <3F06FC05.506@globalite.com.br> Prabhu Ramachandran wrote: >>>>>>"N" == nicodemus writes: >>>>>> >>>>>> > > N> I just applied your patch. I really appreciate your effort in > N> finding this problems, thanks a lot! > >No problem. I also tried solving the problem where Pyste was not >generating wrapper code for virtual operators. Unfortunately the code >was a little too complex and I was not able to generate a patch. I >thought I had to re-order some of the function definitions (move >ExportOperators above ExportVirtualFunctions etc.) and did not want to >go that far. Is this also fixed in CVS? > > No, not yet. I think I will change the way operators are currently exported. Currently, it tries to use Boost.Python's facilities for operators, ie: struct A { A operator+(const B); } It will generate: class_(...) .def(self + other()) ; But I will change it to export the explicit Python special names, to ease dealing with virtual operators: class(...) .def("__add__", &A::operator+) ; You people think that this is a great loss in readability? Because this would let my code in the operators section much more clear. Regards, Nicodemus. From prabhu at aero.iitm.ernet.in Sat Jul 5 18:28:01 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 21:58:01 +0530 Subject: [C++-sig] Installing Pyste. In-Reply-To: <3F06F933.8000804@globalite.com.br> References: <16132.353.879474.386569@monster.linux.in> <3F040AAB.1060008@globalite.com.br> <16132.9397.35714.194993@monster.linux.in> <3F060527.8020707@globalite.com.br> <16134.14843.810333.125316@monster.linux.in> <3F06F933.8000804@globalite.com.br> Message-ID: <16134.64657.790446.709348@monster.linux.in> >>>>> "N" == nicodemus writes: >> Great! In that case you could also move the >> pyste/src/Pyste/pyste.py script into pyste/src and modify it to >> import modules from the Pyste package. If this is done you >> will no longer need the separate pyste.py script. >> Unfortunately I can't see/get your latest changes to the code >> in CVS or submit a patch since pserver access to CVS for me is >> via the backup server and is delayed by about 24hrs. :( N> Don't worry, I made the necessary changes. I reduced pyste.py N> to: Great! Thanks! I also was able to update my CVS checkout a few hours after I sent that message. N> from Pyste import pyste N> pyste.main() Ah, did not notice that. Thats fine. N> To avoid code duplication, and changed the setup.py to work N> from pyste/install. 8) Thanks again for the contribution! My pleasure. cheers, prabhu From nicodemus at globalite.com.br Sat Jul 5 18:41:41 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sat, 05 Jul 2003 13:41:41 -0300 Subject: [C++-sig] Random access iterators, and sequence protocol. In-Reply-To: <16134.54641.351847.619835@monster.linux.in> References: <16134.54641.351847.619835@monster.linux.in> Message-ID: <3F06FFC5.9010909@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >Hi, > >I have a container class that defines an operator [] (std::size_t) and >also has a size function that returns the number of elements in the >container. It does not provide access to an internal iterator. To >get the '[]' wrapped with Pyste I need to rename the function as >__getitem__ of course. I also renamed size to __len__. However, I >would like to do this: > >for i in container: > i.something() > >To do this __getitem__ needs to generate an IndexError when the index >is greater than or equal to size. Do I _have_ to register an >exception translator from something like std::range_error? Is there >an easier way to do this? The docs don't reveal any easier solutions. >It would be nice if this were also as easy as doing it via range, or >iterator. :) > > Make a wrapper for your __getitem__, that throws IndexError when an invalid index is passed (untested): Object my__getitem__(Container& c, int index) { if (index < 0) { // allow negative indexes index = c.size() + index; } if (index >= c.size()) { PyErr_SetString(PyExc_IndexError, "index out of range"); boost::python::throw_error_already_set(); } return c[index]; } If you want to be able to set items in your container in Python with the [] operator, you will have to define also a __setitem__. 8) Then in your pyste file: Include('mywrappers.hpp') Container = Class(...) add_method(Container, 'my__getitem__') add_method(Container, 'my__setitem__') HTH, Nicodemus. From prabhu at aero.iitm.ernet.in Sat Jul 5 19:01:30 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 22:31:30 +0530 Subject: [C++-sig] Pyste: feature requests In-Reply-To: <3F06FACE.1030005@globalite.com.br> References: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> <3F060729.4040409@globalite.com.br> <16134.16073.870902.351091@monster.linux.in> <3F06FACE.1030005@globalite.com.br> Message-ID: <16135.1130.25021.736201@monster.linux.in> Hi Nicodemus, >>>>> "N" == nicodemus writes: >> >> 1. Something like the C compiler's '-c' option. In this case >> >> Pyste >> >> should simply generate the wrapper code and none of the >> >> module code i.e. for an invocation like so: N> I see. Unfortunately this breaks backward compability. 8/ But N> notice that Pyste only overwrites files if they changed, N> otherwise it leaves them intact, so as to not disturb build N> systems out there that depend on time-stamps. Yes, I noticed the SmartFile while poking around. Neat. If backwards compatibility is the problem you could always define a new option that does not interfere with the current working. Something like this: --only-wrapper for individual files with only the export functions and without generating the module code. --only-main for the main module.cpp file that calls the exports and initializes the module. N> I think a good option would be something like N> --xml-cache=, where Pyste would get the generated gccxml N> files, or write them there in case they are not found. The N> bottleneck with Pyste is always GCCXML, since it has to N> basically compile the source files. What do you think? Yes, that also sounds OK to me. If the wrapper-generation time will drop and not every single file will be re-parsed/compiled and wrapped then I'm OK with a --xml-cache option. Basically, the trouble is that with many .pyste files its a pain changing just one Pyste file and waiting for a long while for pyste (gccxml actually) to finish. The other desireable feature would be to dump only one file per .pyste file. This makes dependencies with something like SCons a non-issue. If not its hard to figure out which files depend on what. Again if backwards compatibility is a problem perhaps another option --one-file needs to be added. Thanks! cheers, prabhu From prabhu at aero.iitm.ernet.in Sat Jul 5 19:04:37 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 22:34:37 +0530 Subject: [C++-sig] Pyste: bug: overriding overloaded virtual functions. In-Reply-To: <3F06FC05.506@globalite.com.br> References: <16133.54787.174958.488899@monster.linux.in> <3F060594.6020809@globalite.com.br> <16134.15267.100344.853472@monster.linux.in> <3F06FC05.506@globalite.com.br> Message-ID: <16135.1317.243948.101718@monster.linux.in> >>>>> "N" == nicodemus writes: [virtual operators bug] N> But I will change it to export the explicit Python special N> names, to ease dealing with virtual operators: N> class(...) N> .def("__add__", &A::operator+) N> ; N> You people think that this is a great loss in readability? I'm OK with the above since it reads quite naturally to *me*. I'm not sure what others will feel though. cheers, prabhu From nicodemus at globalite.com.br Sat Jul 5 19:10:48 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sat, 05 Jul 2003 14:10:48 -0300 Subject: [C++-sig] Pyste: feature requests In-Reply-To: <16135.1130.25021.736201@monster.linux.in> References: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> <3F060729.4040409@globalite.com.br> <16134.16073.870902.351091@monster.linux.in> <3F06FACE.1030005@globalite.com.br> <16135.1130.25021.736201@monster.linux.in> Message-ID: <3F070698.1070906@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >Hi Nicodemus, > > > N> I see. Unfortunately this breaks backward compability. 8/ But > N> notice that Pyste only overwrites files if they changed, > N> otherwise it leaves them intact, so as to not disturb build > N> systems out there that depend on time-stamps. > >Yes, I noticed the SmartFile while poking around. Neat. > >If backwards compatibility is the problem you could always define a >new option that does not interfere with the current working. >Something like this: > > --only-wrapper > for individual files with only the export functions > and without generating the module code. > > --only-main > for the main module.cpp file that calls the exports and > initializes the module. > Yeah, it is an option too. > N> I think a good option would be something like > N> --xml-cache=, where Pyste would get the generated gccxml > N> files, or write them there in case they are not found. The > N> bottleneck with Pyste is always GCCXML, since it has to > N> basically compile the source files. What do you think? > >Yes, that also sounds OK to me. If the wrapper-generation time will >drop and not every single file will be re-parsed/compiled and wrapped >then I'm OK with a --xml-cache option. > > Great, I will implement that then. >Basically, the trouble is that with many .pyste files its a pain >changing just one Pyste file and waiting for a long while for pyste >(gccxml actually) to finish. > > I understand. >The other desireable feature would be to dump only one file per .pyste >file. This makes dependencies with something like SCons a non-issue. >If not its hard to figure out which files depend on what. Again if >backwards compatibility is a problem perhaps another option --one-file >needs to be added. > I am working on this right now. 8) Regards, Nicodemus. From nickm at sitius.com Sat Jul 5 19:53:03 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Sat, 05 Jul 2003 13:53:03 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> Message-ID: <3F07107F.4A9C3763@sitius.com> > However, an alternative solution that I was thinknig of is to bake the > thread smarts directly into boost::python. It seems to me that > call_method and similar should always be wrapped with a > PyGILState_Ensure/PyGILState_Release. I guess you can do that without a problem? >Also, an additional call policy > could be added, something like "allow_threads", which would cause b::p > to call Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the > function invocation on C++. This seems like a much more generally > useful solution than me trying to do the dance in wrapper classes. > > Is this the right way to go? If so, I'd appreciate any pointers on > implementing a new call policy, especially if it's possible to both > specify allow_threads and a return_value_policy. Look here: http://boost.org/libs/python/doc/v2/CallPolicies.html It should be very easy for you to write a call policy. And than you can just use it like that return_value_policy() > > Thanks, > - Vladimir From nickm at sitius.com Sat Jul 5 19:58:34 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Sat, 05 Jul 2003 13:58:34 -0400 Subject: [C++-sig] Re: Random access iterators, and sequence protocol. References: <16134.54641.351847.619835@monster.linux.in> Message-ID: <3F0711CA.537E6CF7@sitius.com> > To do this __getitem__ needs to generate an IndexError when the index > is greater than or equal to size. Do I _have_ to register an > exception translator from something like std::range_error? Is there > an easier way to do this? I don't think you can do it any easier than that. And besides, if you export std::range_error this will automatically apply to your future container exports. From prabhu at aero.iitm.ernet.in Sat Jul 5 20:06:36 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 23:36:36 +0530 Subject: [C++-sig] Random access iterators, and sequence protocol. In-Reply-To: <3F06FFC5.9010909@globalite.com.br> References: <16134.54641.351847.619835@monster.linux.in> <3F06FFC5.9010909@globalite.com.br> Message-ID: <16135.5036.246333.78630@monster.linux.in> >>>>> "N" == nicodemus writes: >> To do this __getitem__ needs to generate an IndexError when the >> index is greater than or equal to size. Do I _have_ to >> register an exception translator from something like >> std::range_error? Is there an easier way to do this? The docs >> don't reveal any easier solutions. It would be nice if this >> were also as easy as doing it via range, or iterator. :) N> Make a wrapper for your __getitem__, that throws IndexError N> when an invalid index is passed (untested): [snip example] Thanks. I was aware of that. I wanted to know if there were an easier way. :) I guess this should be a fairly common requirement anyway so having some boilerplate code would be useful. It struck me that since Pyste files are pure Python files it would certainly be useful if a *user* could share common functions that generate code that is common across Pyste files that they have. To this end it would be nice if 'import' could work in the directory where the .pyste file exists. So perhaps something like this would be useful in pyste.py::ParseArguments(): for file in files: d = os.path.dirname(os.path.abspath(file)) if d not in sys.path: sys.path.append(d) That way any of the .pyste files could import others in their directory without having to resort to doing it in each of their source files. Thanks! cheers, prabhu From prabhu at aero.iitm.ernet.in Sat Jul 5 20:10:33 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sat, 5 Jul 2003 23:40:33 +0530 Subject: [C++-sig] Re: Random access iterators, and sequence protocol. In-Reply-To: <3F0711CA.537E6CF7@sitius.com> References: <16134.54641.351847.619835@monster.linux.in> <3F0711CA.537E6CF7@sitius.com> Message-ID: <16135.5273.335324.194444@monster.linux.in> >>>>> "NM" == Nikolay Mladenov writes: >> To do this __getitem__ needs to generate an IndexError when the >> index is greater than or equal to size. Do I _have_ to >> register an exception translator from something like >> std::range_error? Is there an easier way to do this? NM> I don't think you can do it any easier than that. And besides, NM> if you export std::range_error this will automatically apply NM> to your future container exports. True, but if you don't want to add the size related checks in the C++ library that you are wrapping (for whatever reason) and instead want to do it in the wrapper functions then you'd need to write the wrapper for each container. Anyway, since .pyste files can import .py files it should be easy to share code that does this internally and one would merely have to write one function that does the job. Thanks. cheers, prabhu From nickm at sitius.com Sat Jul 5 20:37:18 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Sat, 05 Jul 2003 14:37:18 -0400 Subject: [C++-sig] Re: Random access iterators, and sequence protocol. References: <16134.54641.351847.619835@monster.linux.in> <3F0711CA.537E6CF7@sitius.com> <16135.5273.335324.194444@monster.linux.in> Message-ID: <3F071ADE.D4AEAECE@sitius.com> Ok. Than may be you could write an index_check call policy that does the index checking in the precall... Prabhu Ramachandran wrote: > > >>>>> "NM" == Nikolay Mladenov writes: > > >> To do this __getitem__ needs to generate an IndexError when the > >> index is greater than or equal to size. Do I _have_ to > >> register an exception translator from something like > >> std::range_error? Is there an easier way to do this? > > NM> I don't think you can do it any easier than that. And besides, > NM> if you export std::range_error this will automatically apply > NM> to your future container exports. > > True, but if you don't want to add the size related checks in the C++ > library that you are wrapping (for whatever reason) and instead want > to do it in the wrapper functions then you'd need to write the wrapper > for each container. Anyway, since .pyste files can import .py files > it should be easy to share code that does this internally and one > would merely have to write one function that does the job. > > Thanks. > > cheers, > prabhu From dave at boost-consulting.com Sun Jul 6 00:35:28 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 05 Jul 2003 18:35:28 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> Message-ID: Prabhu Ramachandran writes: > Hi, > > I have a question that I'm not sure has much to do with Boost.Python > itself but I'm wrapping some code via Boost.Python and need to know > what the best approach is to solve the problem. > > The code is designed to be used by allocating objects on the heap (via > new) and handing them off to very simple containers that manage these > objects. The lifetime of the objects is also managed by the > container. So here is a quick example. > > // -------------------- > class Obj { > public: > Obj(); > ~Obj(); > }; > > class Mgr { > public: > Mgr(); > ~Mgr(); // deletes memory for objects in container. > void add(Obj* a); > void popBack(); > private: > std::vector arr; > }; > > void usage() > { > Obj *o = new Obj(); > Mgr *m = new Mgr(); > m->add(o); > delete m; > } > // -------------------- > > Perhaps the design is totally stupid, but its used consistently > everywhere and quite simple once you know you can't delete an object > you created and passed to a manager. Juas as the user has to manage > and remember to invoke delete for every new he has to remember that > the manager manages memory as well. I don't see that as a bad > decision but I guess purists would not agree with me. Nor pragmatists. You should use std::vector > and handle only shared_ptr everywhere and then users don't need to remember to delete anything, ever. > Anyway, I want to wrap the code above (except the usage function) > and want to arrange for Boost.Python to allocate all of the objects, > Obj and Mgr in the heap by default. After wrapping the above via > Boost.Python and using it from Python this is what happens: > >>>> import test >>>> a = test.Obj() >>>> b = test.Mgr() >>>> b.add(a) >>>> del b > Segmentation fault. > > Trouble here is that Obj is not allocated on the heap but on the > stack, just as one would expect in C++. No, everything you construct from Python is allocated on the heap. The trouble here is that: 1. the "a" object thinks it still has ownership of the Obj instance. 2. The Obj instance is essentially allocated as a member of a "holder" object which is part of the Python object (on the heap) so you can't delete it. You could only delete the outer object (if it were allocated with new, which it isn't). > Yes, I read the penultimate FAQ entry and my question is: can I > arrange the wrappers to automatically allocate Obj and Mgr objects > on the heap and additionally be handled by a shared_ptr shared_ptr won't help you because you have no way to release ownership and your Mgr class expects to be able to call delete here. > /auto_ptr > without having to write a factory function like NewObj for every > single class? class_ >("Obj") ... ; does that. > I'd like to avoid writing factory functions just to > do this since I have lots of classes like this. If the object is > allocated on the heap by default and I manage the object via > boost::shared_ptr then the above segfault will not happen. In that case, if you're lucky, you'll get a segfault later when you write >>> del a > Is there a way that this can be handled easily? Alternatively can > this be generated via Pyste/Python magic? You need to write thin wrappers for functions such as Mgr::add which take auto_ptr instead of Obj* if you want to transfer ownership in this way. When we get luabind integration you won't have to do that, though. > FWIW and FYI, not that it matters but SWIG does this by default -- > allocates everything via new and deals with the resulting opaque > pointers. by dealing with opaque pointers, SWIG leaves your Python at the mercy of your C++, which is IMO a bad thing. > Also, is the above approach of creating objects and handing them off > to a manager a bad thing to do in general? By raw pointer? Usually. > Whats a better approach? Use smart pointers in your manager's interface. Note that smart pointers are just lower level "managers". > This is a generic c++ question but the issue arises in the context > of wrapping so I thought it sufficient relevant to post here and not > a c++ list. I'm sorry if this is inappropriate. > > Any suggestions will be much appreciated. > HTH, -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sun Jul 6 00:38:01 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 05 Jul 2003 18:38:01 -0400 Subject: [C++-sig] Re: Random access iterators, and sequence protocol. References: <16134.54641.351847.619835@monster.linux.in> <3F06FFC5.9010909@globalite.com.br> <16135.5036.246333.78630@monster.linux.in> Message-ID: Prabhu Ramachandran writes: > Thanks. I was aware of that. I wanted to know if there were an > easier way. :) I guess this should be a fairly common requirement > anyway so having some boilerplate code would be useful. Joel de Guzman is almost finished with a library facility which makes it easier, but it will probably be a week before it's in the library. -- Dave Abrahams Boost Consulting www.boost-consulting.com From vladimir at pobox.com Sun Jul 6 00:26:04 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: Sat, 05 Jul 2003 15:26:04 -0700 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: <3F07107F.4A9C3763@sitius.com> References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> Message-ID: <3F07507C.1090601@pobox.com> Nikolay Mladenov wrote: >>However, an alternative solution that I was thinknig of is to bake the >>thread smarts directly into boost::python. It seems to me that >>call_method and similar should always be wrapped with a >>PyGILState_Ensure/PyGILState_Release. >> >> > >I guess you can do that without a problem? > Yeah, though I'm having a slight issue with call_method invocations where the return-type is void, since I need to split up the conversion and the actual "return r;" call. >>Also, an additional call policy >>could be added, something like "allow_threads", which would cause b::p >>to call Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the >>function invocation on C++. This seems like a much more generally >>useful solution than me trying to do the dance in wrapper classes. >> >>Is this the right way to go? If so, I'd appreciate any pointers on >>implementing a new call policy, especially if it's possible to both >>specify allow_threads and a return_value_policy. >> >> > >Look here: http://boost.org/libs/python/doc/v2/CallPolicies.html >It should be very easy for you to write a call policy. >And than you can just use it like that > >return_value_policy() > Whoops, I completely missed the overview concept page.. thank you, looks straightforward enough. However, in looking at the code more, I don't think that a call policy would do it -- since no Py_* API functions can be called betwen BEGIN/END macros, they need to go around the final call into C++, thus need to be inserted directly into invoke.hpp. The changes aren't much, but I'm getting a crash-course in boost::python innards :) Thanks, - Vlad From nicodemus at globalite.com.br Sun Jul 6 03:20:46 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sat, 05 Jul 2003 22:20:46 -0300 Subject: [C++-sig] Pyste: feature requests In-Reply-To: <3F070698.1070906@globalite.com.br> References: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> <3F060729.4040409@globalite.com.br> <16134.16073.870902.351091@monster.linux.in> <3F06FACE.1030005@globalite.com.br> <16135.1130.25021.736201@monster.linux.in> <3F070698.1070906@globalite.com.br> Message-ID: <3F07796E.2060300@globalite.com.br> Nicodemus wrote: > Hi Prabhu, > > Prabhu Ramachandran wrote: > >> The other desireable feature would be to dump only one file per .pyste >> file. This makes dependencies with something like SCons a non-issue. >> If not its hard to figure out which files depend on what. Again if >> backwards compatibility is a problem perhaps another option --one-file >> needs to be added. >> > I am working on this right now. 8) Ok, it is in CVS now. If you find any bug, please report that I will try to fix it ASAP. Alas, I was planning to work more on Pyste tomorrow (specially fixing the staticmethod bug and the virtual operators), bug I just remembered that I have a final monday. Sorry everyone that was waiting for this fixes, I will only be able to work on them next week. Regards, Nicodemus. From prabhu at aero.iitm.ernet.in Sun Jul 6 05:04:59 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sun, 6 Jul 2003 08:34:59 +0530 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> Message-ID: <16135.37339.318448.715944@monster.linux.in> Hi David, Thanks for the response! Makes many things clear. >>>>> "DA" == David Abrahams writes: >> Perhaps the design is totally stupid, but its used consistently >> everywhere and quite simple once you know you can't delete an >> object you created and passed to a manager. Juas as the user >> has to manage and remember to invoke delete for every new he >> has to remember that the manager manages memory as well. I >> don't see that as a bad decision but I guess purists would not >> agree with me. DA> Nor pragmatists. You should use std::vector > DA> and handle only shared_ptr everywhere and then users DA> don't need to remember to delete anything, ever. Hmm, so you are saying none of the functions should have ever been written to deal with raw pointers at all and should all have used shared_ptr? But at some point using shared_ptr requires one to handle reference cycles and figure how to break them (using weak_ptrs). I'll admit that this is probably rare (although I can think of a few candidates in my code) and a lot easier to deal with. It also requires that the users generate shared_ptrs when they create a new object. Am I correct? There are also performance issues I'll need to worry about. The boost "smart pointer" docs should prove useful here. If this is what it takes perhaps I'll clean up my library to do this correctly in the future. For now I'll stick to the existing impure and non-pragmatic approach. :) >>>>> import test a = test.Obj() b = test.Mgr() b.add(a) del b >> Segmentation fault. >> >> Trouble here is that Obj is not allocated on the heap but on >> the stack, just as one would expect in C++. DA> No, everything you construct from Python is allocated on the DA> heap. The trouble here is that: DA> 1. the "a" object thinks it still has ownership of the Obj DA> instance. DA> 2. The Obj instance is essentially allocated as a member of a DA> "holder" object which is part of the Python object (on DA> the heap) so you can't delete it. You could only delete DA> the outer object (if it were allocated with new, which it DA> isn't). Ahh, yes. My analysis was poor. Thanks for this. Its now so much clearer. >> Yes, I read the penultimate FAQ entry and my question is: can I >> arrange the wrappers to automatically allocate Obj and Mgr >> objects on the heap and additionally be handled by a shared_ptr DA> shared_ptr won't help you because you have no way to release DA> ownership and your Mgr class expects to be able to call delete DA> here. Yes, so auto_ptr is my friend over here. >> /auto_ptr without having to write a factory function like >> NewObj for every single class? DA> class_ >("Obj") DA> ... DA> ; DA> does that. Neat. I missed out looking at class_'s HeldType. This solves most of my problems here. Wonderful! Now I need to get Pyste to do this also. Currently Pyste registers a ::register_ptr_to_python< std::auto_ptr< Obj > >(); which from what I gather won't allow auto_ptr to handle a newly constructed Obj instance. Is this correct? So should Pyste's use_auto_ptr also pass a HeldType as std::auto_ptr? Or should this be another option? >> I'd like to avoid writing factory functions just to do this >> since I have lots of classes like this. If the object is >> allocated on the heap by default and I manage the object via >> boost::shared_ptr then the above segfault will not happen. DA> In that case, if you're lucky, you'll get a segfault later DA> when you write >>>> del a Yes, my mistake. >> Is there a way that this can be handled easily? Alternatively >> can this be generated via Pyste/Python magic? DA> You need to write thin wrappers for functions such as Mgr::add DA> which take auto_ptr instead of Obj* if you want to DA> transfer ownership in this way. When we get luabind DA> integration you won't have to do that, though. Well, I was considering adding auto_ptr support to the library itself by overloading the add type of methods to accept an auto_ptr also. This will fix the issue. >> FWIW and FYI, not that it matters but SWIG does this by default >> -- allocates everything via new and deals with the resulting >> opaque pointers. DA> by dealing with opaque pointers, SWIG leaves your Python at DA> the mercy of your C++, which is IMO a bad thing. Yes, and this necessitates using the 'thisown' ownership flag in SWIG. That does indeed allow the user to shoot himself in the foot and take the interpreter along with him. >> Whats a better approach? DA> Use smart pointers in your manager's interface. Note that DA> smart pointers are just lower level "managers". Many thanks! For now I'll add overloads to handle an auto_ptr and later consider moving to shared_ptr. I still need to get a handle on the performance of shared_ptr though. The only issue that I need clarification is on how Pyste should do handle this. When use_auto_ptr(Obj) is specified should it register both the to_python converter and also pass the HeldType as auto_ptr or should the HeldType parameter be handled by something like handle_with_auto_ptr(Obj)? I think the latter is better but am not quite sure. I can submit a patch to handle this if this its OK. Thanks again David, I think this clears up most matters for me. regards, prabhu From prabhu at aero.iitm.ernet.in Sun Jul 6 05:05:37 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sun, 6 Jul 2003 08:35:37 +0530 Subject: [C++-sig] Re: Random access iterators, and sequence protocol. In-Reply-To: References: <16134.54641.351847.619835@monster.linux.in> <3F06FFC5.9010909@globalite.com.br> <16135.5036.246333.78630@monster.linux.in> Message-ID: <16135.37377.645664.957646@monster.linux.in> >>>>> "DA" == David Abrahams writes: DA> Prabhu Ramachandran writes: >> Thanks. I was aware of that. I wanted to know if there were >> an easier way. :) I guess this should be a fairly common >> requirement anyway so having some boilerplate code would be >> useful. DA> Joel de Guzman is almost finished with a library facility DA> which makes it easier, but it will probably be a week before DA> it's in the library. Great! Thanks. prabhu From dave at boost-consulting.com Sun Jul 6 02:18:39 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 05 Jul 2003 20:18:39 -0400 Subject: [C++-sig] Re: deriving in python from a C++ base class References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F0252ED.2020307@sympatico.ca> <751832ec5fb30ea081b54bfad350eef93f05821b@Orthosoft.ca> Message-ID: Stefan Seefeld writes: > David Abrahams wrote: > >>>something that I'd like to understand is the relationship between the >>>C++ classes / objects and the corresponding python classes / objects. >> Is that covered in the paper? If so, *specifically* which sections >> of text would you like to see "copied over?" > > Well, partly. The section entitled 'Inheritance' discusses the > initialization of the base class through a call to it's __init__ method, > and you specifically talk about the lookup of the base class: > > "Because C++ object construction is a one-step operation, C++ > instance data cannot be constructed until the arguments are available > in the __init__ function..." > > This and the following paragraphs make some very important points. Could you be specific about the ending point of the text you'd like to see incorporated as well as the beginning point? > As a C++ programmer I'm used to a specific object model / type system, > so I believe it would be very useful to discuss how that maps to python, > and how boost.python does the dispatching. That's not really in the paper, is it? > You may consider this a detail especially for first-time users, but > it really helps to understand these things to be efficient in the > use of boost.python. Sure, I agree. >>>I noted that I can call the parent's __init__ function multiple times, >>>which invokes the C++ base class constructor. It seems that way I can >>>instantiate more than one base class objects. Is that a specific >>>boost.python problem/feature or is that part of the python object model >>>? (It's hard to debug python, i.e. I can't log the 'this pointer' in >>>python, so I only know from boost.python that there are multiple C++ >>>base instances).... >> >> The fact that you can call __init__ as many times as you want is part >> of the Python model. The fact that, for a wrapped class, it creates a >> C++ object each time is part of the way Boost.Python works. It might >> be possible to issue an exception when that happens but it hardly >> seems worthwhile to me. > > Ok. But I do believe that it should be explained. Forgetting to call > __init__ on the base class may be a common error, especially for C++ > programmers who are used to things like default constructors. That's a good idea. Joel, what do you think about mentioning in the tutorial that wrapped C++ objects are created by calling their __init__ functions? -- Dave Abrahams Boost Consulting www.boost-consulting.com From prabhu at aero.iitm.ernet.in Sun Jul 6 05:16:29 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sun, 6 Jul 2003 08:46:29 +0530 Subject: [C++-sig] Pyste: feature requests In-Reply-To: <3F07796E.2060300@globalite.com.br> References: <16133.37361.459195.608938@grapevine.cfl.aero.iitm.ernet.in> <3F060729.4040409@globalite.com.br> <16134.16073.870902.351091@monster.linux.in> <3F06FACE.1030005@globalite.com.br> <16135.1130.25021.736201@monster.linux.in> <3F070698.1070906@globalite.com.br> <3F07796E.2060300@globalite.com.br> Message-ID: <16135.38029.69450.466415@monster.linux.in> >>>>> "N" == nicodemus writes: >>> The other desireable feature would be to dump only one file >>> per .pyste file. This makes dependencies with something like >>> SCons a non-issue. If not its hard to figure out which files >>> depend on what. Again if backwards compatibility is a problem >>> perhaps another option --one-file needs to be added. >>> >> I am working on this right now. 8) N> Ok, it is in CVS now. If you find any bug, please report that I N> will try to fix it ASAP. Alas, I was planning to work more on Wow! That was fast. Your changes haven't propagated to the backup servers yet but I'll be able to check it out tommorow. N> Pyste tomorrow (specially fixing the staticmethod bug and the N> virtual operators), bug I just remembered that I have a final N> monday. Sorry everyone that was waiting for this fixes, I will N> only be able to work on them next week. No problem, good luck on the exam! Thanks again for taking the time to do all this in record time. Much appreciated. cheers, prabhu From dave at boost-consulting.com Sun Jul 6 02:31:03 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 05 Jul 2003 20:31:03 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> Message-ID: Nikolay Mladenov writes: >> However, an alternative solution that I was thinknig of is to bake the >> thread smarts directly into boost::python. It seems to me that >> call_method and similar should always be wrapped with a >> PyGILState_Ensure/PyGILState_Release. > > I guess you can do that without a problem? > >>Also, an additional call policy >> could be added, something like "allow_threads", which would cause b::p >> to call Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the >> function invocation on C++. This seems like a much more generally >> useful solution than me trying to do the dance in wrapper classes. >> >> Is this the right way to go? If so, I'd appreciate any pointers on >> implementing a new call policy, especially if it's possible to both >> specify allow_threads and a return_value_policy. > > Look here: http://boost.org/libs/python/doc/v2/CallPolicies.html > It should be very easy for you to write a call policy. > And than you can just use it like that > > return_value_policy() I don't believe that call policies can do what he wants yet, since there's no provision for state to be carried across the precall() and postcall() functions as required by Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS. Some kind of redesign would probably be in order. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sun Jul 6 02:53:42 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 05 Jul 2003 20:53:42 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> Message-ID: Vladimir Vukicevic writes: > Howdy, > > I'm working on wrapping a C++ library that heavily uses threads > internally, and makes callbacks to user-defined functions on various > non-user-created threads. (This is basically the situation that > provided the impetus for PEP 311, after discussion on python-dev -- Yes, I was a prime instigator of that discussion because users were having difficulty wrapping functions which call into QT, which in turn may invoke PyQT callbacks, which, because they may be called on a thread, would unconditionally acquire the GIL. If users' functions didn't release the GIL before calling into QT, it was very bad juju. > note that I'm working with Python 2.3 because of this, but I beileve > that the PEP 311 patch could be back-ported to 2.2 should anyone need > it.) However, I'm running into problems getting the correct wrappers > for my classes, to get the various > Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS and > PyGILState_Ensure/PyGILState_Release combos in the various places. > > A little background about my problem: from an IDL for a Foo interface, > I generate two C++ classes, "Foo" and "FooProxy". Both of these are > wrapped in smart pointers and are always passed as such in the C++ > library, so we have FooHandle and FooProxyHandle. If Foo defines a > "bar();" operation, then class Foo will have a "virtual void bar() = > 0;", and I have to subclass and implement it, from python or C++. I > have a wrapper class that does the call_method<>() dance; in this > wrapper class, I also place PyGILState_Ensure/PyGILState_Release > around the call_method<>() call. Sounds right. > FooProxy is a remote object that I get as a result of calling various > functions to get a proxy -- it has a "void bar();" (non-virtual) that > I can call. Hmm. This is totally off-topic, but it seems odd to me (and inconvenient, in C++) that FooProxy is not derived from Foo. > However, because the call can be made synchronously, I > need to wrap the call to bar() with Py_BEGIN_ALLOW_THREADS and > Py_END_ALLOW_THREADS. Well, not exactly, IIUC. The reasons to wrap it in Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS are: 1. Because it might take a long time and you want other threads to be able to use the Python interpreter. 2. Because the call actually *depends* on other threads using the Python interpreter during its execution in order to be able to reach completion. > It's this problem that I'm directly dealing with -- I can't figure > out a way to wrap class FooProxy such that I can manage the current > ThreadState and the GIL around them. I can create another wrapper > class Do you mean like a virtual-function-dispatching class, the kind with the initial "PyObject* self" argument to its constructors? > that does the right thing and calls FooProxy::bar(), but > functions are returning a FooProxy (not mywrapper_for_FooProxy) I thought you said that all the C++ interfaces passed FooProxyHandle (?) > and I already have a Handle as a wrapper specified in the > boost::python class_... so I end up with incorrect types half the > time. Specifically, what problem are you having? Could you show a function you are unable to wrap properly and describe the specific problems you're having? > However, an alternative solution that I was thinknig of is to bake the > thread smarts directly into boost::python. I have always thought that should happen in some form or other anyway. > It seems to me that call_method and similar should always be wrapped > with a PyGILState_Ensure/PyGILState_Release. Some people know their extensions are only being called on the main thread and not everyone will be ready to pay the cost for acquiring the GIL on every callback. IMO supplying a GILState class which acquires on construction and releases on destruction *should* be enough. > Also, an additional call policy could be added, something like > "allow_threads", which would cause b::p to call > Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the function > invocation on C++. This seems like a much more generally useful > solution than me trying to do the dance in wrapper classes. I think some change to the requirements and usage of CallPolicies would be neccessary in order to support that (see my reply to Nikolay), but I agree with the general idea. > Is this the right way to go? Probably. I also think that some people want automatic Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS for *all* of their wrapped functions, and that should probably be configurable, too. You have to be careful with that, though: once you do Py_BEGIN_ALLOW_THREADS you can't use any Boost.Python facilities which use the Python 'C' API (e.g. object, handle<>, ...) until you reach Py_END_ALLOW_THREADS. > If so, I'd appreciate any pointers on implementing a new call > policy, especially if it's possible to both specify allow_threads > and a return_value_policy. I think you'd better start by looking at the macro definition of Py_BEGIN_ALLOW_THREADS et al and then at how policies are used to see how state can be stored for the duration of the call they affect, as the macros are wont to do. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nickm at sitius.com Sun Jul 6 05:45:40 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Sat, 05 Jul 2003 23:45:40 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> Message-ID: <3F079B64.871FE4C7@sitius.com> David Abrahams wrote: > > I don't believe that call policies can do what he wants yet, since > there's no provision for state to be carried across the precall() and > postcall() functions as required by Py_BEGIN_ALLOW_THREADS and > Py_END_ALLOW_THREADS. Yeah, ok. But this seems to be a bug, since the docs say x is obbject of type P - model of CallPolicy: than x.precall() .... x.postcall() and x should be able to carry the thread state. The fact that most call policies are static and cannot chain this type of calls should probably be fixed? From dave at boost-consulting.com Sun Jul 6 02:23:13 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 05 Jul 2003 20:23:13 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> <3F05B3A9.7B2F29E8@sitius.com> <3F062D00.65E0B4D6@sitius.com> <3F0643ED.2FC59290@sitius.com> Message-ID: Nikolay Mladenov writes: > Ok. I see the dilemma. And I'm starting see your point about the > comma separated inits, though I wouldn't really enjoy writing them. > > But this is getting a little bit far from the keywords, and the init > problem really got me cycling. I went cycling today, too. 40 miles on the tandem with my wife in the Alaska sunshine with views of all three mountain ranges and Mt. McKinley (Denali)! >> I guess I'm not feeling quite *that* relaxed yet ;-) >> > > So, do you feel we have differences left about the keywords? Nope. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nickm at sitius.com Sun Jul 6 05:47:38 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Sat, 05 Jul 2003 23:47:38 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> <3F07507C.1090601@pobox.com> Message-ID: <3F079BDA.1DA3991B@sitius.com> Vladimir Vukicevic wrote: > > Nikolay Mladenov wrote: > > >>However, an alternative solution that I was thinknig of is to bake the > >>thread smarts directly into boost::python. It seems to me that > >>call_method and similar should always be wrapped with a > >>PyGILState_Ensure/PyGILState_Release. > >> > >> > > > >I guess you can do that without a problem? > > > Yeah, though I'm having a slight issue with call_method invocations > where the return-type is void, since I need to split up the conversion > and the actual "return r;" call. > > >>Also, an additional call policy > >>could be added, something like "allow_threads", which would cause b::p > >>to call Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the > >>function invocation on C++. This seems like a much more generally > >>useful solution than me trying to do the dance in wrapper classes. > >> > >>Is this the right way to go? If so, I'd appreciate any pointers on > >>implementing a new call policy, especially if it's possible to both > >>specify allow_threads and a return_value_policy. > >> > >> > > > >Look here: http://boost.org/libs/python/doc/v2/CallPolicies.html > >It should be very easy for you to write a call policy. > >And than you can just use it like that > > > >return_value_policy() > > > Whoops, I completely missed the overview concept page.. thank you, looks > straightforward enough. However, in looking at the code more, I don't > think that a call policy would do it -- since no Py_* API functions can > be called betwen BEGIN/END macros, I didn't see this in the python docs? >they need to go around the final call > into C++, thus need to be inserted directly into invoke.hpp. And how can you be sure that the c++ call won't call back to python? >The > changes aren't much, but I'm getting a crash-course in boost::python > innards :) > > Thanks, > - Vlad From dave at boost-consulting.com Sun Jul 6 08:59:30 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sun, 06 Jul 2003 02:59:30 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> <3F079B64.871FE4C7@sitius.com> Message-ID: Nikolay Mladenov writes: > David Abrahams wrote: >> >> I don't believe that call policies can do what he wants yet, since >> there's no provision for state to be carried across the precall() and >> postcall() functions as required by Py_BEGIN_ALLOW_THREADS and >> Py_END_ALLOW_THREADS. > > Yeah, ok. But this seems to be a bug, since the docs say > x is obbject of type P - model of CallPolicy: > than > x.precall() > .... > x.postcall() Yes; that is not a bug. > and x should be able to carry the thread state. Not if the wrapped function is re-entered. The docs don't say anything about when the policies object is created. In fact each wrapped function has a single instance of the policies object. > The fact that most call policies are static and cannot chain this > type of calls should probably be fixed? Maybe so, but that's not enough to fix the problem. -- Dave Abrahams Boost Consulting www.boost-consulting.com From ganssauge at gmx.de Sat Jul 5 18:20:41 2003 From: ganssauge at gmx.de (Gottfried Ganßauge) Date: Sat, 5 Jul 2003 18:20:41 +0200 Subject: [C++-sig] pyste and functions returning opaque pointers Message-ID: Hi, i am wrapping a C library containing several functions returning opaque pointers. When i wrap several functions returning the same opaque pointer, the BOOST_PYTHON_OPAQUE_SPECIALIZED_TYPE_ID-Makro for the pointer type is issued as many times as I'm having functions returning the same pointer type. Consider the following source: ggbug.h ===== typedef struct anonymous *type1; type1 f1(); type1 f2() ggbug.pyste ======== h = AllFromHeader("ggbug.h") set_policy ( h.f1, return_value_policy(return_opaque_pointer)) set_policy ( h.f2, return_value_policy(return_opaque_pointer)) "pyste ggbug.pyste" produces the following ggbug.cpp ======= // Includes ==================================================================== #include #include // Using ======================================================================= using namespace boost::python; // Declarations ================================================================ BOOST_PYTHON_OPAQUE_SPECIALIZED_TYPE_ID(anonymous)BOOST_PYTHON_OPAQUE_SPECIA LIZE D_TYPE_ID(anonymous) // Module ====================================================================== BOOST_PYTHON_MODULE(ggbug) { def("f1", &f1, return_value_policy< return_opaque_pointer >()); def("f2", &f2, return_value_policy< return_opaque_pointer >()); } I think that one of the BOOST_PYTHON_OPAQUE_SPECIALIZED_TYPE_ID(anonymous)'s shouldn't be there Cheers, Gottfried Gan?auge From prabhu at aero.iitm.ernet.in Sun Jul 6 10:42:20 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sun, 6 Jul 2003 14:12:20 +0530 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: <16135.37339.318448.715944@monster.linux.in> References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> Message-ID: <16135.57580.378421.78488@monster.linux.in> Hi, Clarifying my own misunderstanding after a little more experimentation. :) >>>>> "PR" == Prabhu Ramachandran writes: >>> /auto_ptr without having to write a factory function like >>> NewObj for every single class? DA> class_ >("Obj") ... DA> ; DA> does that. PR> Neat. I missed out looking at class_'s HeldType. This solves PR> most of my problems here. Wonderful! [snip] PR> Many thanks! For now I'll add overloads to handle an PR> auto_ptr and later consider moving to shared_ptr. I still PR> need to get a handle on the performance of shared_ptr though. This approach of overloading the functions will not work with the HeldType being set to std::auto_ptr since Boost.Python will still call the raw pointer version. So the way around this is to do as you originally said, wrap the add function to handle std::auto_ptr and hide the raw pointer interface when exposing it to Python. PR> The only issue that I need clarification is on how Pyste PR> should do handle this. When use_auto_ptr(Obj) is specified PR> should it register both the to_python converter and also pass PR> the HeldType as auto_ptr or should the HeldType parameter be PR> handled by something like handle_with_auto_ptr(Obj)? I think PR> the latter is better but am not quite sure. I can submit a PR> patch to handle this if this its OK. I clearly need to add a separate option because when I specify the HeldType a converter from std::auto_ptr seems already registeded for Obj. Specifically I got the following error when I used use_auto_ptr and also passed a HeldType parameter: RuntimeError: trying to register to_python_converter for a type which already has a registered to_python_converter I'll submit a patch to support using auto_ptr or shared_ptr as a HeldType sometime tommorow. Thanks again. cheers, prabhu From prabhu at aero.iitm.ernet.in Sun Jul 6 20:36:15 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Mon, 7 Jul 2003 00:06:15 +0530 Subject: [C++-sig] Pyste: patch for HeldType and sys.path. Message-ID: <16136.27679.575203.893865@monster.linux.in> Hi, Attached is a patch to Pyste that allows one to specify the HeldType template argument for class_. I've only added auto_ptr and shared_ptr support. They can be used by doing something like so: A = Class('test::A', header.hpp') hold_with_auto_ptr(A) # alternatively hold_with_shared_ptr(A) I've also changed pyste.py to modify sys.path such that the directories containing the Pyste interface files are in the path. This makes it easy to import a Python module that could define functions for commonly used functionality (like generating simple wrappers). cheers, prabhu -------------- next part -------------- A non-text attachment was scrubbed... Name: Pyste.patch Type: application/octet-stream Size: 2199 bytes Desc: not available URL: From vladimir at pobox.com Sun Jul 6 20:09:29 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: Sun, 06 Jul 2003 11:09:29 -0700 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: References: <3F068544.10204@pobox.com> Message-ID: <3F0865D9.6040401@pobox.com> David Abrahams wrote: >>FooProxy is a remote object that I get as a result of calling various >>functions to get a proxy -- it has a "void bar();" (non-virtual) that >>I can call. > > >Hmm. This is totally off-topic, but it seems odd to me (and >inconvenient, in C++) that FooProxy is not derived from Foo. > Live servants and proxies live in different class hierarchies; the Proxy objects just know how to add their tag to a packet and serialize arguments to operations, whereas Foo might have additional data members and the like. (The library in question is the Ice communications library, at http://www.zeroc.com/ .) >>However, because the call can be made synchronously, I >>need to wrap the call to bar() with Py_BEGIN_ALLOW_THREADS and >>Py_END_ALLOW_THREADS. > >Well, not exactly, IIUC. The reasons to wrap it in >Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS are: > > 1. Because it might take a long time and you want other threads to > be able to use the Python interpreter. > > 2. Because the call actually *depends* on other threads using the > Python interpreter during its execution in order to be able to > reach completion. Right; I have both cases happening -- i.e. there's a "waitForShutdown();" that you can call on the main message dispatcher -- if you call that without releasing the GIL, you shoot yourself in the foot :). The case #2 is what I'm trying to deal with now, as I have a RPC invoked by process B on process A, and then in A's handler it attempts to execute an rpc on process B -- and it blocks, since B is still waiting for the completion of the original call (while holding the GIL). >>It's this problem that I'm directly dealing with -- I can't figure >>out a way to wrap class FooProxy such that I can manage the current >>ThreadState and the GIL around them. I can create another wrapper >>class > >Do you mean like a virtual-function-dispatching class, the kind with >the initial "PyObject* self" argument to its constructors? Yes. >>that does the right thing and calls FooProxy::bar(), but >>functions are returning a FooProxy (not mywrapper_for_FooProxy) > > >I thought you said that all the C++ interfaces passed FooProxyHandle >(?) Sorry, my mistake.. it is a FooProxyHandle. Internally FooProxy is typedef'd to ::Ice::ProxyHandle< ::IceProxy::Foo> :) >>and I already have a Handle as a wrapper specified in the >>boost::python class_... so I end up with incorrect types half the >>time. > > >Specifically, what problem are you having? Could you show a function >you are unable to wrap properly and describe the specific problems >you're having? Sure; see end of message, as it's somewhat lengthy and I didn't want to clutter up the replies. (*) >>However, an alternative solution that I was thinking of is to bake the >>thread smarts directly into boost::python. > > >I have always thought that should happen in some form or other anyway. > >>It seems to me that call_method and similar should always be wrapped >>with a PyGILState_Ensure/PyGILState_Release. > > >Some people know their extensions are only being called on the main >thread and not everyone will be ready to pay the cost for acquiring >the GIL on every callback. IMO supplying a GILState class which >acquires on construction and releases on destruction *should* be >enough. Hmm, I'm not sure what you mean; where would you apply the GILState class? I agree though, acquiring the GIL on every callback is heavyhanded, but necessary for some applications (like mine, where I don't know exactly which thread a callback will get invoked on for a particular object instance). >>Also, an additional call policy could be added, something like >>"allow_threads", which would cause b::p to call >>Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the function >>invocation on C++. This seems like a much more generally useful >>solution than me trying to do the dance in wrapper classes. > >I think some change to the requirements and usage of CallPolicies >would be neccessary in order to support that (see my reply to >Nikolay), but I agree with the general idea. > >>Is this the right way to go? > >Probably. I also think that some people want automatic >Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS for *all* of their wrapped >functions, and that should probably be configurable, too. You have to >be careful with that, though: once you do Py_BEGIN_ALLOW_THREADS you >can't use any Boost.Python facilities which use the Python 'C' API >(e.g. object, handle<>, ...) until you reach Py_END_ALLOW_THREADS. Yep; I assume invoke.hpp is the lowest-level at which the C++ function is actually invoked. I'd like to do the wrapping in caller.hpp, at which point I could extend call policies, but invoke() uses a result converter which will need to make Python API calls. So I wrap the actual call to f() in invoke.hpp. The only wrinkle I'm having now is in call<> and call_method<>, where the return type is void (because the compiler doesn't like R _r = baz(); return _r; where R is void :) -- I've tried, unsuccessfully, to specialize these functions for return types of void, but I'm afraid my C++-fu isn't making the grade. >>If so, I'd appreciate any pointers on implementing a new call >>policy, especially if it's possible to both specify allow_threads >>and a return_value_policy. > >I think you'd better start by looking at the macro definition of >Py_BEGIN_ALLOW_THREADS et al and then at how policies are used to see >how state can be stored for the duration of the call they affect, as >the macros are wont to do. * Specific function problem: Each ProxyHandle exports (via the ProxyHandle class) a checkedCast() static member, that can be used to convert ProxyHandle (which is the root of all proxies) to a specific proxy type. checkedCast() checkedcast actually creates a new ProxyHandle object, and then copies the target server information into it from the ProxyHandle, so there's no "cast" in the C++ sense going on (though it does check if it can dynamic_cast<> the Proxy::Object* to a Proxy::Foo*, and if so, just does that). To have support for checkedCast in python, I create wrapper functions such as: namespace pyce_Hello_casts { ::IceInternal::ProxyHandle< ::IceProxy::Hello> _Hello_checkedCast (const ::Ice::ObjectPrx& o) { return ::IceInternal::ProxyHandle< ::IceProxy::Hello>::checkedCast (o); } }; and my class_<> def looks like: class_< ::IceProxy::Hello , ::IceInternal::ProxyHandle< ::IceProxy::Hello >, bases< ::IceProxy::Ice::Object >, boost::noncopyable > ("HelloPrx") .def("sayHello", &::IceProxy::Hello::sayHello) .def("checkedCast", pyce_Hello_casts::_Hello_checkedCast) .staticmethod("checkedCast") ; This all works fine, until I want to intercept the call to sayHello() (to save/restore the ThreadState goop). I can create a wrapper that derives from ::IceProxy::Hello, but then I have to deal with that PyObject* constructor, for which I have no need for here -- I'm never going to utilize call_method, and HelloPrx will never be derived from in python-land. The sayHello() and other member functions are also not virtual. I could do a dance with a custom-written overload dispatch for each function. If I went the wrapper route, I would need to implement my own version of checkedCast that can convert to my wrapper, and add some implicitly_convertible statements, and make sure that no references to ::IceProxy::Hello (or the equivalent handle) get exposed anywhere.. certainly feasable, but a pain, especially for cases where I get a handle to a ::IceProxy::Hello in C++ and I'd have to convert. But both approaches seem like they're far too verbose. I'll probably create a call_method_with_threads<> such that the non-GIL-acquiring call_method<> is still available; extending call policies would allow a nice implementation for GIL-releasing and non-GIL-releasing C++ calls in caller.hpp, but the problem with the ResultConverter being called from invoke.hpp still remains. If there was a base class for all result converters, it could perhaps acquire the GIL in its constructor and release in the destructor, though no such class exists (that I can see?), and it would be yet another mutex acquisition/release. I'm currently running into a snag in invoke.hpp, though; I've modified the non-void-return calls to invoke as such: template inline PyObject* invoke(fn_tag, RC*, F& f BOOST_PP_ENUM_TRAILING_BINARY_PARAMS_Z(1, N, AC, & ac) ) { PyThreadState *_save; Py_UNBLOCK_THREADS typename boost::function_traits::result_type _r = f( BOOST_PP_ENUM_BINARY_PARAMS_Z(1, N, ac, () BOOST_PP_INTERCEPT) ); Py_BLOCK_THREADS return RC()(_r); } .. but the function_traits invocation doesn't seem to be doing what I want, as I'm getting errors of the form: /usr/local/boost/boost/python/detail/invoke.hpp:105: base class ` boost::detail::function_traits_helper' has incomplete type I apologize for the long message; I hope I've come across clearer instead of muddying up the waters more. Thanks for the help and ideas! - Vlad From seefeld at sympatico.ca Sun Jul 6 21:35:46 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Sun, 06 Jul 2003 15:35:46 -0400 Subject: [C++-sig] Re: deriving in python from a C++ base class In-Reply-To: References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F0252ED.2020307@sympatico.ca> <751832ec5fb30ea081b54bfad350eef93f05821b@Orthosoft.ca> Message-ID: <3F087A12.30201@sympatico.ca> David Abrahams wrote: >>"Because C++ object construction is a one-step operation, C++ >> instance data cannot be constructed until the arguments are available >>in the __init__ function..." >> >>This and the following paragraphs make some very important points. > > > Could you be specific about the ending point of the text you'd like > to see incorporated as well as the beginning point? > > >>As a C++ programmer I'm used to a specific object model / type system, >>so I believe it would be very useful to discuss how that maps to python, >>and how boost.python does the dispatching. > > > That's not really in the paper, is it? no. When I ran into the problem with the non-initialized base class, it was Ralf who pointed me to this paper (see the beginning of this thread). Reading the cited paragraph, I started to understand the problem. That made me curious so I tried calling __init__ multiple times, so I discovered that multiple base objects were bound to my derived class. I'v been working with python for quite some time, but in this particular context with a C++ base class this cought my attention, as this is obviously something were the C++ and the python way of life differ dramatically. That's why I'd like to see some discussion of these issues. >>Ok. But I do believe that it should be explained. Forgetting to call >>__init__ on the base class may be a common error, especially for C++ >>programmers who are used to things like default constructors. > > > That's a good idea. Joel, what do you think about mentioning in the > tutorial that wrapped C++ objects are created by calling their > __init__ functions? May be if the tutorial stays as it is, but at appropriate places you point to some special chapters with a 'for details see...' icon, covering particular topics such as this in depth. Thanks a lot ! Stefan From djowel at gmx.co.uk Mon Jul 7 00:48:34 2003 From: djowel at gmx.co.uk (Joel de Guzman) Date: Mon, 7 Jul 2003 06:48:34 +0800 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> <3F05B3A9.7B2F29E8@sitius.com> <3F062D00.65E0B4D6@sitius.com> <3F0643ED.2FC59290@sitius.com> Message-ID: <003901c34410$bea97d10$0100a8c0@godzilla> David Abrahams wrote: >> But this is getting a little bit far from the keywords, >> and the init problem really got me cycling. > > I went cycling today, too. 40 miles on the tandem with my > wife in the Alaska sunshine with views of all three > mountain ranges and > Mt. McKinley (Denali)! Wow! I can only imagine! -- Joel de Guzman joel at boost-consulting.com http://www.boost-consulting.com http://spirit.sf.net From djowel at gmx.co.uk Mon Jul 7 00:54:38 2003 From: djowel at gmx.co.uk (Joel de Guzman) Date: Mon, 7 Jul 2003 06:54:38 +0800 Subject: [C++-sig] Re: deriving in python from a C++ base class References: <20030702024730.17335.qmail@web20207.mail.yahoo.com> <3F0252ED.2020307@sympatico.ca> <751832ec5fb30ea081b54bfad350eef93f05821b@Orthosoft.ca> <3F087A12.30201@sympatico.ca> Message-ID: <004301c34411$97105a70$0100a8c0@godzilla> Stefan Seefeld wrote: >>> Ok. But I do believe that it should be explained. >>> Forgetting to call __init__ on the base class may be a >>> common error, especially for C++ programmers who are >>> used to things like default constructors. >> >> >> That's a good idea. Joel, what do you think about >> mentioning in the tutorial that wrapped C++ objects are >> created by calling their __init__ functions? > > May be if the tutorial stays as it is, but at appropriate > places you > point to some special chapters with a 'for details > see...' icon, covering particular topics such as this in > depth. I think it's better that this issue be added in the tutorial. It's too easy to miss. A short paragraph will go a long way. -- Joel de Guzman joel at boost-consulting.com http://www.boost-consulting.com http://spirit.sf.net From vladimir at pobox.com Mon Jul 7 00:54:15 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: Sun, 06 Jul 2003 15:54:15 -0700 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: <3F0865D9.6040401@pobox.com> References: <3F068544.10204@pobox.com> <3F0865D9.6040401@pobox.com> Message-ID: <3F08A897.2000208@pobox.com> Attached is a patch which seems to work for me, under some light testing. I'm writing some heavy stress-test code right now. I'm very open to suggestions on how to do away with call_void_method_with_gil/call_void_with_gil so that call_method_with_gil and call_with_gil can be used with void-returning functions as well. Note that I'm not necessarily submitting this for review for possible inclusion in b::p, but am more curious if this approach is valid -- though if there's interest I'd be willing to do any work necessary to make it ready. I think with some #ifdefs it could play nice with cases where the user doesn't care about the GIL and other issues; however, it does depend on Python 2.3. - Vlad -------------- next part -------------- An embedded and charset-unspecified text was scrubbed... Name: boost-python.patch URL: From dave at boost-consulting.com Mon Jul 7 07:56:12 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 01:56:12 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> Message-ID: Vladimir, In addition to my earlier responses I'd like to point you at this posting from Patrick Hartling. http://article.gmane.org/gmane.comp.python.c++/2833 I'd really like to get all these threading issues squared away in Boost.Python, and I especially hope that since threading is so important in lua that threading integration will benefit from the luabind discussions. In any case, proposals for patches to the Boost.Python core are very much appreciated. -Dave -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 7 07:57:00 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 01:57:00 -0400 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: (David Abrahams's message of "Sat, 05 Jul 2003 20:31:03 -0400") References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> Message-ID: Vladimir, In addition to my earlier responses I'd like to point you at this posting from Patrick Hartling. http://article.gmane.org/gmane.comp.python.c++/2833 I'd really like to get all these threading issues squared away in Boost.Python, and I especially hope that since threading is so important in lua that threading integration will benefit from the luabind discussions. In any case, proposals for patches to the Boost.Python core are very much appreciated. -Dave -- Dave Abrahams Boost Consulting www.boost-consulting.com From pierre.barbier at cirad.fr Mon Jul 7 11:07:58 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 07 Jul 2003 11:07:58 +0200 Subject: [C++-sig] Problem with embedding python with boost.python Message-ID: <3F09386E.4000003@cirad.fr> I try to embed python in a C++ program. I wrote a module that works if I compile it for extending python ... and I wrote a simple interpreter that works as an embedded one ! But now I want to extend the embedded interpreter to allow access to the C++ classes ! The extension module is called "editor". My problem is that whenever I try to import the module in python, the program just abort ... the import is done by evaluating 'import edtitor' inside the python interpreter ... I show you the interpreter code ! Of course, the module is defined using boost.python ! An extra-question is : if I use Py_file_input, I can't retrieve the output of the python command, if I use Py_single_input, I can retrieve the output, but I can't do any assignment or printing ... how can I have both ??? I really begin to think python was not designed to embedded :( Tthe interpreter class is : class PythonWnd : public QMainWindow { Q_OBJECT public: PythonWnd(QWidget * parent = 0, const char * name = 0, WFlags f = WType_TopLevel); ~PythonWnd(); public slots: void evalCommand(); protected: void LaunchPython(); void ClosePython(); void ExecutePython(const QString command); QTextEdit *output; QLineEdit *edit; QVBox *layout; boost::python::object main_module; boost::python::dict main_namespace; }; The initialization function that is : void PythonWnd::LaunchPython() { // register the module editor with the interpreter if (PyImport_AppendInittab("editor", init_module_editor) == -1) { cerr << "Error, cannot load editor module !" << endl; throw std::runtime_error("Failed to add embedded_hello to the interpreter's " "builtin modules"); } // Initialize the interpreter Py_Initialize(); // Get the main module ... main_module = object(boost::python::handle<>(borrowed(PyImport_AddModule("__main__")))); main_namespace = dict(boost::python::handle<>(borrowed(PyModule_GetDict(main_module.ptr())))); } Then the interpretor function (launched each time a line is to be evaluated ... it's an iteractive interpretor) is: void PythonWnd::ExecutePython(const QString command) { char *cmd; cmd = new char[command.length()+1]; strcpy(cmd, command.latin1()); stringstream ss; try { PyObject *obj = PyRun_String(cmd, Py_file_input, main_namespace.ptr(), main_namespace.ptr()); boost::python::handle<> hres(obj); boost::python::object res(hres); //std::string res_cmd = extract(res.attr("__repr__")()); std::string res_cmd = call_method(res.ptr(),"__repr__"); ss << res_cmd; } catch(error_already_set) { PyErr_Print(); ss << "Error, exception thrown ... look at console for details" << endl; PyObject *exception, *v, *tb, *hook; } output->append(ss.str().c_str()); delete cmd; } -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From dirk at gerrits.homeip.net Mon Jul 7 11:39:58 2003 From: dirk at gerrits.homeip.net (Dirk Gerrits) Date: Mon, 07 Jul 2003 11:39:58 +0200 Subject: [C++-sig] Re: Problem with embedding python with boost.python In-Reply-To: <3F09386E.4000003@cirad.fr> References: <3F09386E.4000003@cirad.fr> Message-ID: Pierre Barbier de Reuille wrote: > I try to embed python in a C++ program. I wrote a module that works if I > compile it for extending python ... and I wrote a simple interpreter > that works as an embedded one ! > > But now I want to extend the embedded interpreter to allow access to the > C++ classes ! > > The extension module is called "editor". My problem is that whenever I > try to import the module in python, the program just abort ... the > import is done by evaluating 'import edtitor' inside the python > interpreter ... I show you the interpreter code ! Of course, the module > is defined using boost.python ! > > An extra-question is : if I use Py_file_input, I can't retrieve the > output of the python command, if I use Py_single_input, I can retrieve > the output, but I can't do any assignment or printing ... how can I have > both ??? I really begin to think python was not designed to embedded :( Well this is not really a question of embedding or not. Python's eval, exec, and execfile statements work in the same way. Anyway, what you could do is use Py_file_input for all but the last line of code, then use Py_eval_input for the last line. Or you could let the code store the result in a variable and read that variable from the main_namespace: PyObject *obj = PyRun_String("result = 5**2", Py_file_input, main_namespace.ptr(), main_namespace.ptr()); boost::python::handle<> hres(obj); boost::python::object res = main_namespace["result"]; > Tthe interpreter class is : > > class PythonWnd : public QMainWindow > { > Q_OBJECT > > public: > PythonWnd(QWidget * parent = 0, const char * name = 0, WFlags f = > WType_TopLevel); > ~PythonWnd(); > > public slots: > void evalCommand(); > > protected: > void LaunchPython(); > void ClosePython(); > void ExecutePython(const QString command); > QTextEdit *output; > QLineEdit *edit; > QVBox *layout; > boost::python::object main_module; > boost::python::dict main_namespace; > > }; > > The initialization function that is : > > void PythonWnd::LaunchPython() > { > // register the module editor with the interpreter > if (PyImport_AppendInittab("editor", init_module_editor) == -1) > { > cerr << "Error, cannot load editor module !" << endl; > throw std::runtime_error("Failed to add embedded_hello to the > interpreter's " > "builtin modules"); > } > // Initialize the interpreter > Py_Initialize(); > // Get the main module ... > main_module = > object(boost::python::handle<>(borrowed(PyImport_AddModule("__main__")))); > main_namespace = > dict(boost::python::handle<>(borrowed(PyModule_GetDict(main_module.ptr())))); > > } > > Then the interpretor function (launched each time a line is to be > evaluated ... it's an iteractive interpretor) is: > > void PythonWnd::ExecutePython(const QString command) > { > char *cmd; > cmd = new char[command.length()+1]; > strcpy(cmd, command.latin1()); > stringstream ss; > try > { > PyObject *obj = PyRun_String(cmd, Py_file_input, > main_namespace.ptr(), main_namespace.ptr()); > boost::python::handle<> hres(obj); > boost::python::object res(hres); > //std::string res_cmd = extract(res.attr("__repr__")()); > std::string res_cmd = call_method(res.ptr(),"__repr__"); > ss << res_cmd; > } > catch(error_already_set) > { > PyErr_Print(); > ss << "Error, exception thrown ... look at console for details" << > endl; > PyObject *exception, *v, *tb, *hook; > } > output->append(ss.str().c_str()); > delete cmd; > } > > command.latin1() is not null-terminated I think, which would make the strcpy fail. (Not sure, I don't use Qt.) Wouldn't it be easier and safer to do: QString cmd = command + '\0'; ... PyObject *obj = PyRun_String(cmd.latin1(), Py_file_input, main_namespace.ptr(), main_namespace.ptr()); ? Are you sure the interpreter aborts only when you import your module? If latin1() does what I think it does then your program could crash on any piece of Python code. Regards, Dirk Gerrits From dirk at gerrits.homeip.net Mon Jul 7 11:44:40 2003 From: dirk at gerrits.homeip.net (Dirk Gerrits) Date: Mon, 07 Jul 2003 11:44:40 +0200 Subject: [C++-sig] Re: Problem with embedding python with boost.python In-Reply-To: References: <3F09386E.4000003@cirad.fr> Message-ID: Dirk Gerrits wrote: > command.latin1() is not null-terminated I think, which would make the > strcpy fail. (Not sure, I don't use Qt.) Wouldn't it be easier and safer > to do: > > QString cmd = command + '\0'; > ... > PyObject *obj = PyRun_String(cmd.latin1(), Py_file_input, > main_namespace.ptr(), main_namespace.ptr()); > > ? Ah I just read that latin1() DOES provide a null-terminated string. Sorry. But then I don't understand why you were copying it in the first place. Care to elaborate? Regards, Dirk Gerrits From pierre.barbier at cirad.fr Mon Jul 7 11:56:43 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 07 Jul 2003 11:56:43 +0200 Subject: [C++-sig] Re: Problem with embedding python with boost.python In-Reply-To: References: <3F09386E.4000003@cirad.fr> Message-ID: <3F0943DB.2080409@cirad.fr> I copied it just because the PyRun_String command take a "char *" and that latin1 returns a "const char*" ... si you have to copy it ! For my other problem, I just solved it ... the solution is to replace the AppendInittab by : PyImport_AppendInittab("editor", initeditor) and ti define initeditor with : extern "C" void initeditor(); ... when testing I forgot the 'extern "C"' ! Now it works and I'm working on your recommandations to retrieve the output ! Tanks ! Dirk Gerrits wrote: > Dirk Gerrits wrote: > >> command.latin1() is not null-terminated I think, which would make the >> strcpy fail. (Not sure, I don't use Qt.) Wouldn't it be easier and >> safer to do: >> >> QString cmd = command + '\0'; >> ... >> PyObject *obj = PyRun_String(cmd.latin1(), Py_file_input, >> main_namespace.ptr(), main_namespace.ptr()); >> >> ? > > > Ah I just read that latin1() DOES provide a null-terminated string. > Sorry. > > But then I don't understand why you were copying it in the first > place. Care to elaborate? > > Regards, > Dirk Gerrits > > > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From dirk at gerrits.homeip.net Mon Jul 7 12:10:26 2003 From: dirk at gerrits.homeip.net (Dirk Gerrits) Date: Mon, 07 Jul 2003 12:10:26 +0200 Subject: [C++-sig] Re: Problem with embedding python with boost.python In-Reply-To: <3F0943DB.2080409@cirad.fr> References: <3F09386E.4000003@cirad.fr> <3F0943DB.2080409@cirad.fr> Message-ID: Pierre Barbier de Reuille wrote: > I copied it just because the PyRun_String command take a "char *" and > that latin1 returns a "const char*" ... si you have to copy it ! Well PyRun_String doesn't actually modify your string. In fact, in the Python CVS it takes a const char* as an argument. For now, you can just use const_cast(command.latin1()) as an argument, no copying necessary. > For my other problem, I just solved it ... the solution is to replace > the AppendInittab by : > PyImport_AppendInittab("editor", initeditor) > > and ti define initeditor with : > > extern "C" void initeditor(); > > ... when testing I forgot the 'extern "C"' ! > > Now it works and I'm working on your recommandations to retrieve the > output ! > > Tanks ! You're welcome. By the way, there are plans to make embedding with Boost.Python significantly easier. I'm not sure when they will be fully implemented, but hopefully before the end of this summer. Any new developments will be posted here on the C++ SIG. > Dirk Gerrits wrote: > >> Dirk Gerrits wrote: >> >>> command.latin1() is not null-terminated I think, which would make the >>> strcpy fail. (Not sure, I don't use Qt.) Wouldn't it be easier and >>> safer to do: >>> >>> QString cmd = command + '\0'; >>> ... >>> PyObject *obj = PyRun_String(cmd.latin1(), Py_file_input, >>> main_namespace.ptr(), main_namespace.ptr()); >>> >>> ? >> >> >> >> Ah I just read that latin1() DOES provide a null-terminated string. >> Sorry. >> >> But then I don't understand why you were copying it in the first >> place. Care to elaborate? >> >> Regards, >> Dirk Gerrits From prabhu at aero.iitm.ernet.in Mon Jul 7 15:03:55 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Mon, 7 Jul 2003 18:33:55 +0530 Subject: [C++-sig] Pyste: serious bug with --multiple. Message-ID: <16137.28603.185263.111639@monster.linux.in> Hi, Found a serious bug with Pyste's --multiple option. It would not mix up the declarations and put them in wrong files. I've attached a patch that fixes this problem. Generating only one file per --multiple is nice but still has the old problem where if I change one interface file I need to wait several minutes for pyste (gccxml actually) to regenerate the files. Nicodemus suggested that a --xml-cache option would be useful. However even with that option you'd generate many xml files and will need to keep track of those files etc. Instead I have a much simpler approach that will solve much of our problems. 1. Add a --only-wrap option that will process any number of interface files and will generate the necessary wrapper code and *will not* generate a _main.cpp file. Further, it will add an extra function to each _interface_name.cpp file that reads something like this: void _interface_name_module_init() { Export_SomeClass(); Export_SomeHeader_H(); // ... } 2. The --multiple option with the --only-main option will simply create a _main.cpp with something like this: void _interface_name_module_init(); BOOST_PYTHON_MODULE(module_name) { _interface_name_module(); // ... } Note that the above does not need to use gccxml at all since it only needs the interface file names. This should make it possible to selectively compile individual interfaces via --multiple --only-wrap and then generate a _main.cpp separately using all the interfaces very quickly. There are other issues not related to the above also but I won't go into them here. I'm going to go ahead and implement --only-main and --only-wrap on my copy of the code here and will submit it to the list if it works nicely. I'll let you folks decide if it goes into CVS or not. cheers, prabhu -------------- next part -------------- An embedded and charset-unspecified text was scrubbed... Name: Pyste1.patch URL: From prabhu at aero.iitm.ernet.in Mon Jul 7 17:07:18 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Mon, 7 Jul 2003 20:37:18 +0530 Subject: [C++-sig] Pyste: added new build options. Message-ID: <16137.36006.159444.648080@monster.linux.in> Hi, I've finished implementing a --only-wrap and --only-main option for Pyste. It works nicely in that I can now generate and build my wrappers incrementally, interface file by interface file. Something like this: pyste.py --only-wrap --module=test --out . --multiple file1.pyste pyste.py --only-wrap --module=test --out . --multiple file2.pyste [...] pyste.py --only-main --module=test --out . \ --multiple file1.pyste [...] fileN.pyste the last command completes in no time since it does not use GCCXML and writes a simple _main.cpp file. Nicodemus, I can mail the list another patch for this but I've already sent two other patches maybe so you'd prefer one big patch that incorporates my earlier two as well, i.e. (a) support for hold_with_*, add path to sys.path, (b) fix for the --multiple bug and (c) support for the --only-wrap and --only-main? Please let me know what you'd prefer and I'll send you the appropriate patch. cheers, prabhu From vladimir at pobox.com Mon Jul 7 17:31:56 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: Mon, 07 Jul 2003 08:31:56 -0700 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> Message-ID: <3F09926C.5090302@pobox.com> David Abrahams wrote: >Vladimir, > >In addition to my earlier responses I'd like to point you at this >posting from Patrick Hartling. > >http://article.gmane.org/gmane.comp.python.c++/2833 > >I'd really >like to get all these threading issues squared away in Boost.Python, >and I especially hope that since threading is so important in lua that >threading integration will benefit from the luabind discussions. In >any case, proposals for patches to the Boost.Python core are very >much appreciated. > > Thanks for the article pointer.. I see what you meant by the guard class earlier. Patrick seems to have basically implemented (in a fairly elegant way!) what the Python 2.3 PyGILStateEnsure/Release functions do; my patches to call.hpp and call_method.hpp do virtually the same thing, by creating a call_method_with_gil that one can use in wrappers instead of call_method. The difficulty seems to be calling from python into C++, in invoke.hpp. My patch took a first stab at it, but I didn't look closely enough -- the arguments passed to f() in the invoke() calls are all arg converters. What I'd really like to have happen is for a function foo, to have an invoke() and an invoke_helper, where the invoke_helper has the exact same signature as foo but inserts Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the actual call to foo() (or, more accurately, the pointer to foo). This can't happen in the actual invoke() call, as my patch attempts to do, because the arg converters need to use Python API calls (oops!). I'm working on adding an invoke_helper which will do the two-step invocation, but I need to study the to_python interface in more detail. - Vlad From nicodemus at globalite.com.br Mon Jul 7 21:01:54 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 16:01:54 -0300 Subject: [C++-sig] pyste and functions returning opaque pointers In-Reply-To: References: Message-ID: <3F09C3A2.4040008@globalite.com.br> Gottfried Gan?auge wrote: >I think that one of the BOOST_PYTHON_OPAQUE_SPECIALIZED_TYPE_ID(anonymous)'s >shouldn't be there > > Yes, thanks for reporting this! 8) It's fixed in CVS now. Regards, Nicodemus. From nicodemus at globalite.com.br Mon Jul 7 21:09:35 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 16:09:35 -0300 Subject: [C++-sig] Pyste: patch for HeldType and sys.path. In-Reply-To: <16136.27679.575203.893865@monster.linux.in> References: <16136.27679.575203.893865@monster.linux.in> Message-ID: <3F09C56F.5050902@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >Attached is a patch to Pyste that allows one to specify the HeldType >template argument for class_. I've only added auto_ptr and shared_ptr >support. They can be used by doing something like so: > > A = Class('test::A', header.hpp') > hold_with_auto_ptr(A) > # alternatively > hold_with_shared_ptr(A) > >I've also changed pyste.py to modify sys.path such that the >directories containing the Pyste interface files are in the path. >This makes it easy to import a Python module that could define >functions for commonly used functionality (like generating simple >wrappers). > >cheers, >prabhu > Applied, thanks a lot Prabhu! Regards, Nicodemus. From nicodemus at globalite.com.br Mon Jul 7 21:09:32 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 16:09:32 -0300 Subject: [C++-sig] Pyste: serious bug with --multiple. In-Reply-To: <16137.28603.185263.111639@monster.linux.in> References: <16137.28603.185263.111639@monster.linux.in> Message-ID: <3F09C56C.4050802@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >Found a serious bug with Pyste's --multiple option. It would not mix >up the declarations and put them in wrong files. I've attached a >patch that fixes this problem. > Applied, thanks again! >Generating only one file per --multiple is nice but still has the old >problem where if I change one interface file I need to wait several >minutes for pyste (gccxml actually) to regenerate the files. >Nicodemus suggested that a --xml-cache option would be useful. >However even with that option you'd generate many xml files and will >need to keep track of those files etc. > Yes, the idea was that Pyste would generate a xml file for each header parsed. Keeping them updated would be the build's system job: when a header is modified, it should delete the corresponding xml file, so that Pyste would rebuild it. > Instead I have a much simpler >approach that will solve much of our problems. > > 1. Add a --only-wrap option that will process any number of interface > files and will generate the necessary wrapper code and *will not* > generate a _main.cpp file. Further, it will add an extra function > to each _interface_name.cpp file that reads something like this: > > void _interface_name_module_init() > { > Export_SomeClass(); > Export_SomeHeader_H(); > // ... > } > > 2. The --multiple option with the --only-main option will simply > create a _main.cpp with something like this: > > void _interface_name_module_init(); > BOOST_PYTHON_MODULE(module_name) > { > _interface_name_module(); > // ... > } > > Note that the above does not need to use gccxml at all since it > only needs the interface file names. This should make it possible > to selectively compile individual interfaces via --multiple > --only-wrap and then generate a _main.cpp separately using all the > interfaces very quickly. > > If that solves your problem, that's fine then. 8) But I don't see a need for the _interface_name_module_init() function, since BOOST_PYTHON_MODULE can call them, and the fact that Base classes must be exported first, would make things complicated. >There are other issues not related to the above also but I won't go >into them here. > >I'm going to go ahead and implement --only-main and --only-wrap on my >copy of the code here and will submit it to the list if it works >nicely. I'll let you folks decide if it goes into CVS or not. > > Sure thing, I don't see why not. 8) Let's implement this then, if that solves the problem. >cheers, >prabhu > Thanks a lot Prabhu. Your efforts in improving Pyste are greatly appreciated! Regards, Nicodemus. From nicodemus at globalite.com.br Mon Jul 7 21:12:21 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 16:12:21 -0300 Subject: [C++-sig] Pyste: added new build options. In-Reply-To: <16137.36006.159444.648080@monster.linux.in> References: <16137.36006.159444.648080@monster.linux.in> Message-ID: <3F09C615.4080606@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >I've finished implementing a --only-wrap and --only-main option for >Pyste. It works nicely in that I can now generate and build my >wrappers incrementally, interface file by interface file. Something >like this: > > pyste.py --only-wrap --module=test --out . --multiple file1.pyste > pyste.py --only-wrap --module=test --out . --multiple file2.pyste > [...] > pyste.py --only-main --module=test --out . \ > --multiple file1.pyste [...] fileN.pyste > >the last command completes in no time since it does not use GCCXML and >writes a simple _main.cpp file. > > Thank you very much Prabhu! 8) >Nicodemus, I can mail the list another patch for this but I've already >sent two other patches maybe so you'd prefer one big patch that >incorporates my earlier two as well, i.e. > > (a) support for hold_with_*, add path to sys.path, > (b) fix for the --multiple bug and > (c) support for the --only-wrap and --only-main? > >Please let me know what you'd prefer and I'll send you the appropriate >patch. > I already applied the other too, you can send only this new patch. Could you also write a doc patch, explaining this new options? The relevant file is pyste/doc/pyste.txt. >cheers, >prabhu > > Thanks again! Nicodemus. From prabhu at aero.iitm.ernet.in Mon Jul 7 21:16:36 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 00:46:36 +0530 Subject: [C++-sig] Strange behaviour for inheritance with C++ classes. Message-ID: <16137.50964.550088.466596@monster.linux.in> Hi, Here is a simple test case for some code that gives me strange behavior under (gcc version 2.95.4 20011002 (Debian prerelease)). Atleast the behavior is not what I expected. $ python -V Python 2.2.1 // -------- test.hpp ------ #include class Pure { public: virtual ~Pure(){} virtual void f() = 0; }; class Derived : public Pure { public: Derived(){} ~Derived(){} void f() {cout << "This is Derived::f\n";} }; // -------- test.hpp ------ I wrapped this via Pyste using test = AllFromHeader('test.hpp') I then ran the following test under Python: >>> import test >>> class A(test.Derived): ... def __init__(self): ... test.Derived.__init__(self) ... >>> d = test.Derived() >>> print isinstance(d, test.Derived) 1 >>> print isinstance(d, test.Pure) 0 >>> test.func(d) Traceback (most recent call last): File "", line 1, in ? TypeError: bad argument type for built-in operation >>> a = A() >>> print isinstance(a, test.Derived) 1 >>> print isinstance(a, test.Pure) 0 >>> test.func(a) Traceback (most recent call last): File "", line 1, in ? TypeError: bad argument type for built-in operation >>> class B(test.Pure): ... def __init__(self): ... test.Pure.__init__(self) ... def f(self): ... print "B.f" ... >>> b = B() >>> test.func (b) B.f What surprises me is the following: 1. d is not an instance of test.Pure but if I did everything (i.e. defined all the classes) in pure Python thats the way it would be! 2. test.func should work with anything that is derived from test.Pure but neither did 'd' nor did 'a' work but 'b' did work! So what is going on here and what must I do to see the behaviour that one would expect? My apologies in advance if this is a silly mistake that I've made but I can't see why the above does not work. Perhaps Pyste is doing something incorrectly but I cant see whats wrong there either. Thanks. prabhu From prabhu at aero.iitm.ernet.in Mon Jul 7 21:50:46 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 01:20:46 +0530 Subject: [C++-sig] Pyste: added new build options. In-Reply-To: <3F09C615.4080606@globalite.com.br> References: <16137.36006.159444.648080@monster.linux.in> <3F09C615.4080606@globalite.com.br> Message-ID: <16137.53014.729719.186773@monster.linux.in> >>>>> "N" == nicodemus writes: >> (a) support for hold_with_*, add path to sys.path, >> (b) fix for the --multiple bug and >> (c) support for the --only-wrap and --only-main? >> >> Please let me know what you'd prefer and I'll send you the >> appropriate patch. N> I already applied the other too, you can send only this new I've attached the patch for the new options. The patched pyste.py file also has updated documentation on the available options. Take a look at my changes and if you think its OK check it in. The SingleCodeUnit.py changes just one line. I explicity call close since I don't really trust/know when the object will actually be deleted. Maybe I'm paranoid but I think its better safe than sorry. N> patch. Could you also write a doc patch, explaining this new N> options? The relevant file is pyste/doc/pyste.txt. Oh, all the Pyste docs are generated from that text file? Cool! I'll add documentation to it. I was thinking of adding a few things: * installation via distutils (I think its worth documenting) * update the options page (that is if you think my patch is OK). * There is a small section in the Wrapper docs where I'd like to clarify a point. * Mention that you can import another Python file in the same directory and use that. I don't quite know where this would go but I guess the wrapper section is good enough. However its going to take me a little while to add this. Is it OK if I get to this by the weekend (or if lucky earlier)? Actually, I think it would be great if we could also look at the following features: 1. Can we specify exclude/rename function names in greater detail. Currently its impossible to selectively exclude one particular overloaded function. 2. The current --multiple option generates one file per interface file. I guess that is OK but maybe it would be useful to optionally specify the output filename in the interface. I think this should be a low priority to do item (if at all it is useful). cheers, prabhu -------------- next part -------------- An embedded and charset-unspecified text was scrubbed... Name: Pyste2.patch URL: From prabhu at aero.iitm.ernet.in Mon Jul 7 21:24:29 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 00:54:29 +0530 Subject: [C++-sig] Pyste: serious bug with --multiple. In-Reply-To: <3F09C56C.4050802@globalite.com.br> References: <16137.28603.185263.111639@monster.linux.in> <3F09C56C.4050802@globalite.com.br> Message-ID: <16137.51437.370253.761478@monster.linux.in> >>>>> "N" == nicodemus writes: N> Yes, the idea was that Pyste would generate a xml file for each N> header parsed. Keeping them updated would be the build's system N> job: when a header is modified, it should delete the N> corresponding xml file, so that Pyste would rebuild it. Oh! OK but its more complicated than my solution. N> But I don't see a need for the _interface_name_module_init() N> function, since BOOST_PYTHON_MODULE can call them, and the fact N> that Base classes must be exported first, would make things N> complicated. The reason for the _interface_name_module_init is that I'd like one function that has a known name and that is independant of what was generated. This way I can generate the _main.cpp without any need to use GCCXML. N> Thanks a lot Prabhu. Your efforts in improving Pyste are N> greatly appreciated! No problem. cheers, prabhu From dave at boost-consulting.com Mon Jul 7 21:55:49 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 15:55:49 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> Message-ID: Prabhu Ramachandran writes: > Hi David, > > Thanks for the response! Makes many things clear. > >>>>>> "DA" == David Abrahams writes: > > >> Perhaps the design is totally stupid, but its used consistently > >> everywhere and quite simple once you know you can't delete an > >> object you created and passed to a manager. Juas as the user > >> has to manage and remember to invoke delete for every new he > >> has to remember that the manager manages memory as well. I > >> don't see that as a bad decision but I guess purists would not > >> agree with me. > > DA> Nor pragmatists. You should use std::vector > > DA> and handle only shared_ptr everywhere and then users > DA> don't need to remember to delete anything, ever. > > Hmm, so you are saying none of the functions should have ever been > written to deal with raw pointers at all and should all have used > shared_ptr? Raw pointers are low-level. High-level interfaces are easier to use correctly and much easier to wrap. > But at some point using shared_ptr requires one to handle > reference cycles and figure how to break them So does manual new/delete. > (using weak_ptrs). I'll admit that this is probably rare (although > I can think of a few candidates in my code) and a lot easier to deal > with. It also requires that the users generate shared_ptrs when > they create a new object. I'm not sure what you mean by that. > Am I correct? There are also performance issues I'll need to worry > about. The boost "smart pointer" docs should prove useful here. If > this is what it takes perhaps I'll clean up my library to do this > correctly in the future. For now I'll stick to the existing impure > and non-pragmatic approach. :) OK. > DA> You need to write thin wrappers for functions such as Mgr::add > DA> which take auto_ptr instead of Obj* if you want to > DA> transfer ownership in this way. When we get luabind > DA> integration you won't have to do that, though. > > Well, I was considering adding auto_ptr support to the library itself > by overloading the add type of methods to accept an auto_ptr also. > This will fix the issue. Yep. > Many thanks! For now I'll add overloads to handle an auto_ptr and > later consider moving to shared_ptr. I still need to get a handle on > the performance of shared_ptr though. > > The only issue that I need clarification is on how Pyste should do > handle this. When use_auto_ptr(Obj) is specified should it register > both the to_python converter and also pass the HeldType as auto_ptr or > should the HeldType parameter be handled by something like > handle_with_auto_ptr(Obj)? I think the latter is better but am not > quite sure. I can submit a patch to handle this if this its OK. I'm not fond of the idea of hard-coding auto_ptr and shared_ptr into Pyste; there are other important smart pointers. It would be better to write: A.held_by('std::auto_ptr') If Pyste wants to supply auto_ptr and shared_ptr objects so that A.held_by(auto_ptr) or A.held_by(shared_ptr) could work as well, that would be good. Another possibility is to get rid of the first option altogether and ask people to write: def my_smart_ptr(pointee): return 'my_smart_ptr<' + str(pointee) + '>' so that A.held_by(my_smart_ptr) will work. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Mon Jul 7 22:00:38 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 17:00:38 -0300 Subject: [C++-sig] Strange behaviour for inheritance with C++ classes. In-Reply-To: <16137.50964.550088.466596@monster.linux.in> References: <16137.50964.550088.466596@monster.linux.in> Message-ID: <3F09D166.1060304@globalite.com.br> An HTML attachment was scrubbed... URL: From dave at boost-consulting.com Mon Jul 7 21:57:21 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 15:57:21 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16135.57580.378421.78488@monster.linux.in> Message-ID: Prabhu Ramachandran writes: > Hi, > > Clarifying my own misunderstanding after a little more > experimentation. :) > >>>>>> "PR" == Prabhu Ramachandran writes: > > >>> /auto_ptr without having to write a factory function like > >>> NewObj for every single class? > > DA> class_ >("Obj") ... > DA> ; > DA> does that. > > PR> Neat. I missed out looking at class_'s HeldType. This solves > PR> most of my problems here. Wonderful! > > [snip] > > PR> Many thanks! For now I'll add overloads to handle an > PR> auto_ptr and later consider moving to shared_ptr. I still > PR> need to get a handle on the performance of shared_ptr though. > > This approach of overloading the functions will not work with the > HeldType being set to std::auto_ptr since Boost.Python will still call > the raw pointer version. If you register the auto_ptr version last it will be preferred. > So the way around this is to do as you originally said, wrap the add > function to handle std::auto_ptr and hide the raw pointer interface > when exposing it to Python. > > PR> The only issue that I need clarification is on how Pyste > PR> should do handle this. When use_auto_ptr(Obj) is specified > PR> should it register both the to_python converter and also pass > PR> the HeldType as auto_ptr or should the HeldType parameter be > PR> handled by something like handle_with_auto_ptr(Obj)? I think > PR> the latter is better but am not quite sure. I can submit a > PR> patch to handle this if this its OK. > > I clearly need to add a separate option because when I specify the > HeldType a converter from std::auto_ptr seems already registeded for > Obj. I'm not sure why that would be. > Specifically I got the following error when I used use_auto_ptr ^^^^^^^^^^^^ what's that? > and also passed a HeldType parameter: > > RuntimeError: trying to register to_python_converter for a type > which already has a registered to_python_converter > > I'll submit a patch to support using auto_ptr or shared_ptr as a > HeldType sometime tommorow. -- Dave Abrahams Boost Consulting www.boost-consulting.com From temas at box5.net Mon Jul 7 22:05:18 2003 From: temas at box5.net (Thomas Muldowney) Date: 07 Jul 2003 15:05:18 -0500 Subject: [C++-sig] Strange behaviour for inheritance with C++ classes. In-Reply-To: <3F09D166.1060304@globalite.com.br> References: <16137.50964.550088.466596@monster.linux.in> <3F09D166.1060304@globalite.com.br> Message-ID: <1057608318.6023.9.camel@corrosion> On Mon, 2003-07-07 at 15:00, Nicodemus wrote: > Hi Prabhu, > Yeah, it is a Pyste bug. ;) > The problem is related to AllFromHeader, if you explicitly export each > class the problem goes away. The inheritance tests didn't catch this > because they don't use AllFromHeader. > It is fixed in CVS now, thanks for the report! > > Regards, > Nicodemus. > _______________________________________________ C++-sig mailing list > C++-sig at python.org http://mail.python.org/mailman/listinfo/c++-sig Is there any chance of a CVS snapshot of pyste sometime soon? The SF public CVS lag is making it a real pain to get these important updates. --temas From nicodemus at globalite.com.br Mon Jul 7 22:11:54 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 17:11:54 -0300 Subject: [C++-sig] Pyste: serious bug with --multiple. In-Reply-To: <16137.51437.370253.761478@monster.linux.in> References: <16137.28603.185263.111639@monster.linux.in> <3F09C56C.4050802@globalite.com.br> <16137.51437.370253.761478@monster.linux.in> Message-ID: <3F09D40A.4040505@globalite.com.br> Hi Prabhu, Prabhu Ramachandran wrote: >>>>>>"N" == nicodemus writes: >>>>>> >>>>>> > > N> Yes, the idea was that Pyste would generate a xml file for each > N> header parsed. Keeping them updated would be the build's system > N> job: when a header is modified, it should delete the > N> corresponding xml file, so that Pyste would rebuild it. > >Oh! OK but its more complicated than my solution. > Yes. 8) > N> But I don't see a need for the _interface_name_module_init() > N> function, since BOOST_PYTHON_MODULE can call them, and the fact > N> that Base classes must be exported first, would make things > N> complicated. > >The reason for the _interface_name_module_init is that I'd like one >function that has a known name and that is independant of what was >generated. This way I can generate the _main.cpp without any need to >use GCCXML. > Hmm, I see. But unfortunately this will cause problems, such as: test.h ---- struct A {}; struct B: A {}; x.pyste ---- Class('A', 'test.h') y.pyste ---- Class('D', 'test.h') You would have two functions, init_x and init_y, but you have to call first init_x, otherwise you will get a runtime error. That's why I think more control of which class is instanciated first is needed. Of course, we can demand that our users put all files in a hierarchy in the same Pyste file, but that breaks the purpose of the --multiple option (to reduce compile time), since it is common that type hierarchies have a base class that all other classes derive from; besides this gives the users one more thing to worry about. Regards, Nicodemus. From nicodemus at globalite.com.br Mon Jul 7 22:13:31 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 17:13:31 -0300 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16135.57580.378421.78488@monster.linux.in> Message-ID: <3F09D46B.3030608@globalite.com.br> David Abrahams wrote: >Prabhu Ramachandran writes: > > >>Specifically I got the following error when I used use_auto_ptr >> >> > ^^^^^^^^^^^^ >what's that? > > That is a Pyste function that registers a converter for an auto_ptr: C = Class(...) use_auto_ptr(C) Regards, Nicodemus. From dave at boost-consulting.com Mon Jul 7 22:13:39 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 16:13:39 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F0865D9.6040401@pobox.com> Message-ID: Vladimir Vukicevic writes: > David Abrahams wrote: > > >>FooProxy is a remote object that I get as a result of calling various > >>functions to get a proxy -- it has a "void bar();" (non-virtual) that > >>I can call. > > > > >Hmm. This is totally off-topic, but it seems odd to me (and > >inconvenient, in C++) that FooProxy is not derived from Foo. > > > Live servants and proxies live in different class hierarchies; the > Proxy objects just know how to add their tag to a packet and serialize > arguments to operations, whereas Foo might have additional data > members and the like. Which is why Foo ought to be an empty abstract base class. But anyway... > >>It's this problem that I'm directly dealing with -- I can't figure > >>out a way to wrap class FooProxy such that I can manage the current > >>ThreadState and the GIL around them. I can create another wrapper > >>class > > > >Do you mean like a virtual-function-dispatching class, the kind with > >the initial "PyObject* self" argument to its constructors? > > Yes. > > >>that does the right thing and calls FooProxy::bar(), but > >>functions are returning a FooProxy (not mywrapper_for_FooProxy) > > > > > >I thought you said that all the C++ interfaces passed FooProxyHandle > >(?) > > Sorry, my mistake.. it is a FooProxyHandle. Internally FooProxy is > typedef'd to ::Ice::ProxyHandle< ::IceProxy::Foo> :) See boost/python/converter/register_ptr_to_python.hpp in the CVS. > >>and I already have a Handle as a wrapper specified in the > >>boost::python class_... so I end up with incorrect types half the > >>time. > > > > > >Specifically, what problem are you having? Could you show a function > >you are unable to wrap properly and describe the specific problems > >you're having? > > Sure; see end of message, as it's somewhat lengthy and I didn't want > to clutter up the replies. (*) > > >>However, an alternative solution that I was thinking of is to bake the > >>thread smarts directly into boost::python. > > > > >I have always thought that should happen in some form or other anyway. > > > >>It seems to me that call_method and similar should always be wrapped > >>with a PyGILState_Ensure/PyGILState_Release. > > > > >Some people know their extensions are only being called on the main > >thread and not everyone will be ready to pay the cost for acquiring > >the GIL on every callback. IMO supplying a GILState class which > >acquires on construction and releases on destruction *should* be > >enough. > > Hmm, I'm not sure what you mean; where would you apply the GILState > class? I agree though, acquiring the GIL on every callback is > heavyhanded, but necessary for some applications (like mine, where I > don't know exactly which thread a callback will get invoked on for a > particular object instance). I guess from your other messages you figured that out. > >>Also, an additional call policy could be added, something like > >>"allow_threads", which would cause b::p to call > >>Py_BEGIN_ALLOW_THREADS and Py_END_ALLOW_THREADS around the function > >>invocation on C++. This seems like a much more generally useful > >>solution than me trying to do the dance in wrapper classes. > > > >I think some change to the requirements and usage of CallPolicies > >would be neccessary in order to support that (see my reply to > >Nikolay), but I agree with the general idea. > > > >>Is this the right way to go? > > >Probably. I also think that some people want automatic > >Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS for *all* of their wrapped > >functions, and that should probably be configurable, too. You have to > >be careful with that, though: once you do Py_BEGIN_ALLOW_THREADS you > >can't use any Boost.Python facilities which use the Python 'C' API > >(e.g. object, handle<>, ...) until you reach Py_END_ALLOW_THREADS. > > Yep; I assume invoke.hpp is the lowest-level at which the C++ > function is actually invoked. Close. > >>If so, I'd appreciate any pointers on implementing a new call > >>policy, especially if it's possible to both specify allow_threads > >>and a return_value_policy. > > > >I think you'd better start by looking at the macro definition of > >Py_BEGIN_ALLOW_THREADS et al and then at how policies are used to see > >how state can be stored for the duration of the call they affect, as > >the macros are wont to do. > > * Specific function problem: > > Each ProxyHandle exports (via the ProxyHandle class) a > checkedCast() static member, that can be used to convert > ProxyHandle (which is the root of all proxies) to a > specific proxy type. checkedCast() checkedcast actually creates a new > ProxyHandle object, and then copies the target server > information into it from the ProxyHandle, so there's no > "cast" in the C++ sense going on (though it does check if it can > dynamic_cast<> the Proxy::Object* to a Proxy::Foo*, and if so, just > does that). > > To have support for checkedCast in python, I create wrapper functions > such as: > > namespace pyce_Hello_casts { > ::IceInternal::ProxyHandle< ::IceProxy::Hello> _Hello_checkedCast ^^^^^^^^^^^^^^^^^^ This name is reserved for your C++ implementation. > (const ::Ice::ObjectPrx& o) > { > return ::IceInternal::ProxyHandle< ::IceProxy::Hello>::checkedCast (o); > } > }; > > and my class_<> def looks like: > > class_< ::IceProxy::Hello , > ::IceInternal::ProxyHandle< ::IceProxy::Hello >, > bases< ::IceProxy::Ice::Object >, > boost::noncopyable > > ("HelloPrx") > .def("sayHello", &::IceProxy::Hello::sayHello) > .def("checkedCast", pyce_Hello_casts::_Hello_checkedCast) > .staticmethod("checkedCast") > ; > > This all works fine, until I want to intercept the call to sayHello() > (to save/restore the ThreadState goop). I can create a wrapper that > derives from ::IceProxy::Hello, but then I have to deal with that > PyObject* constructor, for which I have no need for here -- I'm never > going to utilize call_method, and HelloPrx will never be derived from > in python-land. The sayHello() and other member functions are also > not virtual. I could do a dance with a custom-written overload > dispatch for each function. If I went the wrapper route, I would need > to implement my own version of checkedCast that can convert to my > wrapper, and add some implicitly_convertible statements, and make sure > that no references to ::IceProxy::Hello (or the equivalent handle) get > exposed anywhere.. certainly feasable, but a pain, especially for > cases where I get a handle to a ::IceProxy::Hello in C++ and I'd have > to convert. > > But both approaches seem like they're far too verbose. I'll probably > create a call_method_with_threads<> such that the non-GIL-acquiring > call_method<> is still available; extending call policies would allow > a nice implementation for GIL-releasing and non-GIL-releasing C++ > calls in caller.hpp, but the problem with the ResultConverter being > called from invoke.hpp still remains. If there was a base class for > all result converters, it could perhaps acquire the GIL in its > constructor and release in the destructor, though no such class exists > (that I can see?), and it would be yet another mutex > acquisition/release. This is all very complicated sounding, and I can't tell whether it's still an issue in light of the guard object idea, and I have so much to catch up on I don't think I have time to analyze. If there's still an issue here, could you boil it down a bit? -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Mon Jul 7 22:15:28 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 17:15:28 -0300 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: <3F062CA0.6000706@globalite.com.br> References: <3F04C9A9.1070907@globalite.com.br> <3F04DAB9.6000906@globalite.com.br> <3F06096B.9080005@globalite.com.br> <3F062CA0.6000706@globalite.com.br> Message-ID: <3F09D4E0.2050305@globalite.com.br> Nicodemus wrote: > Hah! You just found a bug, congratulations! ;) > I didn't know myself, but you have to use "staticmethod" only after > all the overloads of a static method were exported. Ok, fixed in CVS, sorry about the delay. Thanks again Jim. Regards, Nicodemus. From prabhu at aero.iitm.ernet.in Mon Jul 7 22:19:19 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 01:49:19 +0530 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> Message-ID: <16137.54727.970073.487393@monster.linux.in> >>>>> "DA" == David Abrahams writes: >> Hmm, so you are saying none of the functions should have ever >> been written to deal with raw pointers at all and should all >> have used shared_ptr? DA> Raw pointers are low-level. High-level interfaces are easier DA> to use correctly and much easier to wrap. Indeed. >> But at some point using shared_ptr requires one to handle >> reference cycles and figure how to break them DA> So does manual new/delete. Yes, but I've done that already and don't have the time to change all my code to use smart pointers now. Essentially, its not a trivial change for me to make (since my library is quite large and uses pointers quite a bit) so I'll postpone this and update my to-do list. >> (using weak_ptrs). I'll admit that this is probably rare >> (although I can think of a few candidates in my code) and a lot >> easier to deal with. It also requires that the users generate >> shared_ptrs when they create a new object. DA> I'm not sure what you mean by that. Its nothing important but what I meant was that a user of the library has to use 'shared_ptr p(new A());' and not new A(). No big deal at all but its a change nonetheless. >> The only issue that I need clarification is on how Pyste should >> do handle this. When use_auto_ptr(Obj) is specified should it >> register both the to_python converter and also pass the >> HeldType as auto_ptr or should the HeldType parameter be >> handled by something like handle_with_auto_ptr(Obj)? I think >> the latter is better but am not quite sure. I can submit a >> patch to handle this if this its OK. DA> I'm not fond of the idea of hard-coding auto_ptr and DA> shared_ptr into Pyste; there are other important smart DA> pointers. It would be better to write: DA> A.held_by('std::auto_ptr') Yes, I was thinking the same thing but didn't mention it in my earlier list of items! I knew I forgot something. DA> If Pyste wants to supply auto_ptr and shared_ptr objects so DA> that DA> A.held_by(auto_ptr) DA> or DA> A.held_by(shared_ptr) Hmm, I am not sure if the A.held_by approach is easy to do but I do know that this can be done easily: holder(A, 'std::auto_ptr') Would that do? Thanks. prabhu From dave at boost-consulting.com Mon Jul 7 22:15:37 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 16:15:37 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F07107F.4A9C3763@sitius.com> <3F09926C.5090302@pobox.com> Message-ID: Vladimir Vukicevic writes: > David Abrahams wrote: > >> Vladimir, In addition to my earlier responses I'd like to point you >> at this >> posting from Patrick Hartling. >> http://article.gmane.org/gmane.comp.python.c++/2833 >> >>I'd really >>like to get all these threading issues squared away in Boost.Python, >>and I especially hope that since threading is so important in lua that >>threading integration will benefit from the luabind discussions. In >>any case, proposals for patches to the Boost.Python core are very >>much appreciated. >> > Thanks for the article pointer.. I see what you meant by the guard > class earlier. Patrick seems to have basically implemented (in a > fairly elegant way!) what the Python 2.3 PyGILStateEnsure/Release > functions do; my patches to call.hpp and call_method.hpp do virtually > the same thing, by creating a call_method_with_gil that one can use in > wrappers instead of call_method. > > The difficulty seems to be calling from python into C++, in invoke.hpp. My patch took a first stab at it, but I didn't look closely enough -- > the arguments passed to f() in the invoke() calls are all arg > converters. What I'd really like to have happen is for a function > foo, to have an invoke() and an invoke_helper, where the invoke_helper > has the exact same signature as foo but inserts Py_BEGIN_ALLOW_THREADS > and Py_END_ALLOW_THREADS around the actual call to foo() (or, more > accurately, the pointer to foo). This can't happen in the actual > invoke() call, as my patch attempts to do, because the arg converters > need to use Python API calls (oops!). I'm working on adding an > invoke_helper which will do the two-step invocation, but I need to > study the to_python interface in more detail. I think the key here is to find a way to wrap the wrapped (member) function pointer f in a function *adapter* which does Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Mon Jul 7 22:31:48 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 17:31:48 -0300 Subject: [C++-sig] Pyste: added new build options. In-Reply-To: <16137.53014.729719.186773@monster.linux.in> References: <16137.36006.159444.648080@monster.linux.in> <3F09C615.4080606@globalite.com.br> <16137.53014.729719.186773@monster.linux.in> Message-ID: <3F09D8B4.6070604@globalite.com.br> Prabhu Ramachandran wrote: >>>>>>"N" == nicodemus writes: >>>>>> >>>>>> > > >> (a) support for hold_with_*, add path to sys.path, > >> (b) fix for the --multiple bug and > >> (c) support for the --only-wrap and --only-main? > >> > >> Please let me know what you'd prefer and I'll send you the > >> appropriate patch. > > N> I already applied the other too, you can send only this new > >I've attached the patch for the new options. The patched pyste.py >file also has updated documentation on the available options. Take a >look at my changes and if you think its OK check it in. The >SingleCodeUnit.py changes just one line. I explicity call close since >I don't really trust/know when the object will actually be deleted. >Maybe I'm paranoid but I think its better safe than sorry. > Certainly, it was a lapse from my part. 8) "Explicit is better than implicit", after all. I didn't check it in yet because I think there is one thing that is still pending. See my other post, about the order of instantiation of classes. > N> patch. Could you also write a doc patch, explaining this new > N> options? The relevant file is pyste/doc/pyste.txt. > >Oh, all the Pyste docs are generated from that text file? Cool! I'll >add documentation to it. > Yes, it is cool. 8) It uses Joel's quickdoc: boost\libs\spirit\example\application\quickdoc >I was thinking of adding a few things: > > * installation via distutils (I think its worth documenting) > * update the options page (that is if you think my patch is OK). > * There is a small section in the Wrapper docs where I'd like to > clarify a point. > * Mention that you can import another Python file in the same > directory and use that. I don't quite know where this would go but > I guess the wrapper section is good enough. > >However its going to take me a little while to add this. Is it OK if >I get to this by the weekend (or if lucky earlier)? > Sounds great! Thanks a lot. >Actually, I think it would be great if we could also look at the >following features: > > 1. Can we specify exclude/rename function names in greater detail. > Currently its impossible to selectively exclude one particular > overloaded function. > > I think that will be solved when meta programming is avaiable in the Pyste files. I don't know how to stretch the current syntax to support this, but suggestions are welcome. > 2. The current --multiple option generates one file per interface > file. I guess that is OK but maybe it would be useful to > optionally specify the output filename in the interface. I think > this should be a low priority to do item (if at all it is > useful). > > I think it would clutter the command line interface a little, but if it is useful we could add it. Regards, Nicodemus. From prabhu at aero.iitm.ernet.in Mon Jul 7 23:08:26 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 02:38:26 +0530 Subject: [C++-sig] Pyste: added new build options. In-Reply-To: <3F09D8B4.6070604@globalite.com.br> References: <16137.36006.159444.648080@monster.linux.in> <3F09C615.4080606@globalite.com.br> <16137.53014.729719.186773@monster.linux.in> <3F09D8B4.6070604@globalite.com.br> Message-ID: <16137.57674.91106.745828@monster.linux.in> Hi, Glad to note that the other Pure/Derived issue was a Pyste bug with AllFromHeader. I was quite upset. SF's CVS being on backup is indeed a pain! >>>>> "N" == nicodemus writes: [snip] N> I didn't check it in yet because I think there is one thing N> that is still pending. See my other post, about the order of N> instantiation of classes. [From other message] N> Hmm, I see. But unfortunately this will cause problems, such N> as: N> test.h ---- N> struct A {}; N> struct B: A {}; N> x.pyste ---- N> Class('A', 'test.h') N> y.pyste ---- N> Class('D', 'test.h') N> You would have two functions, init_x and init_y, but you have N> to call first init_x, otherwise you will get a runtime N> error. That's why I think more control of which class is N> instanciated first is needed. Of course, we can demand that our N> users put all files in a hierarchy in the same Pyste file, but N> that breaks the purpose of the --multiple option (to reduce N> compile time), since it is common that type hierarchies have a N> base class that all other classes derive from; besides this N> gives the users one more thing to worry about. Arghh! This is a pain. Another issue is if two pyste files export different functions (free functions) from the same header we will end up with a name clash but I'm assuming that users can be asked to export all functions from the same file. I really like the feature of generating individual files and then generating a _main.cpp file. It makes a huge difference to building wrappers. So I'd like to see some sort of solution for this. Perhaps the --multiple option will generate a separate special file that contains information on the bases of each class that was exported. Something like this: _file1 = {'A':('Export_A', [])} _file2 = {'B': ('Export_B', ['A'])} I'm tired and not quite thinking straight but the idea is that you generate information on what depends on what and append that information to a file. I think this should be a reasonable solution, even if its a hack -- perhaps there is a better way? Do only the order of wrappers and class declarations matter? OTOH, when GCCXML parses the file you already know the base classes of a particular class, so can one generate a special name for the Module function such that when it is sorted you will get the right order? Consider that class B is the base and A is derived from it. class B -> Export_A_B class A -> Export_B_A Then looking at the Export functions one could decide which function to call first. What do you think? Is there a way out of this? I'd really appreciate if we could find a decent solution for this. >> 1. Can we specify exclude/rename function names in greater >> detail. >> Currently its impossible to selectively exclude one particular >> overloaded function. N> I think that will be solved when meta programming is avaiable N> in the Pyste files. I don't know how to stretch the current N> syntax to support this, but suggestions are welcome. OK, there is no hurry for this. The above is far more important. >> 2. The current --multiple option generates one file per >> interface >> file. I guess that is OK but maybe it would be useful to >> optionally specify the output filename in the interface. I >> think this should be a low priority to do item (if at all it is >> useful). N> I think it would clutter the command line interface a little, N> but if it is useful we could add it. No, its not that useful. Right now I think having a working --only-wrap/only-main would be great! Thanks! regards, prabhu From nicodemus at globalite.com.br Mon Jul 7 23:27:14 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 18:27:14 -0300 Subject: [C++-sig] Pyste: added new build options. In-Reply-To: <16137.57674.91106.745828@monster.linux.in> References: <16137.36006.159444.648080@monster.linux.in> <3F09C615.4080606@globalite.com.br> <16137.53014.729719.186773@monster.linux.in> <3F09D8B4.6070604@globalite.com.br> <16137.57674.91106.745828@monster.linux.in> Message-ID: <3F09E5B2.9090308@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >Glad to note that the other Pure/Derived issue was a Pyste bug with >AllFromHeader. I was quite upset. > I can imagine. 8) >>>>>>"N" == nicodemus writes: >>>>>> >>>>>> > >[snip] > > N> I didn't check it in yet because I think there is one thing > N> that is still pending. See my other post, about the order of > N> instantiation of classes. > >[From other message] > > N> Hmm, I see. But unfortunately this will cause problems, such > N> as: > > N> test.h ---- > N> struct A {}; > N> struct B: A {}; > > N> x.pyste ---- > N> Class('A', 'test.h') > > N> y.pyste ---- > N> Class('D', 'test.h') > > N> You would have two functions, init_x and init_y, but you have > N> to call first init_x, otherwise you will get a runtime > N> error. That's why I think more control of which class is > N> instanciated first is needed. Of course, we can demand that our > N> users put all files in a hierarchy in the same Pyste file, but > N> that breaks the purpose of the --multiple option (to reduce > N> compile time), since it is common that type hierarchies have a > N> base class that all other classes derive from; besides this > N> gives the users one more thing to worry about. > >Arghh! This is a pain. Another issue is if two pyste files export >different functions (free functions) from the same header we will end >up with a name clash but I'm assuming that users can be asked to >export all functions from the same file. > > I would like to avoid that kind of thing... it is error prone, and only generates compile time errors, which are a pain to read. >I really like the feature of generating individual files and then >generating a _main.cpp file. It makes a huge difference to building >wrappers. So I'd like to see some sort of solution for this. Perhaps >the --multiple option will generate a separate special file that >contains information on the bases of each class that was exported. >Something like this: > >_file1 = {'A':('Export_A', [])} >_file2 = {'B': ('Export_B', ['A'])} > >I'm tired and not quite thinking straight but the idea is that you >generate information on what depends on what and append that >information to a file. I think this should be a reasonable solution, >even if its a hack -- perhaps there is a better way? Do only the >order of wrappers and class declarations matter? > > But then to generate the main.cpp you must have already generated all the others? I think that makes things more complicated than are worth... 8/ Perhaps the --xml-cache option would be better, if we can't solve this problem? Another option would be to make Pyste accept some xml files. >OTOH, when GCCXML parses the file you already know the base classes of >a particular class, so can one generate a special name for the Module >function such that when it is sorted you will get the right order? >Consider that class B is the base and A is derived from it. > > class B -> Export_A_B > class A -> Export_B_A > >Then looking at the Export functions one could decide which function >to call first. What do you think? Is there a way out of this? > But how would we know the name of the functions when we will generate main.cpp without calling GCCXML (which is the point of having "Export" functions in the files)? > >> 2. The current --multiple option generates one file per > >> interface > >> file. I guess that is OK but maybe it would be useful to > >> optionally specify the output filename in the interface. I > >> think this should be a low priority to do item (if at all it is > >> useful). > > N> I think it would clutter the command line interface a little, > N> but if it is useful we could add it. > >No, its not that useful. > Hmm, ok then. >Right now I think having a working --only-wrap/only-main would be >great! > > Ok, let us focus on that. I am working at the virtual operators too. Regards, Nicodemus. From dave at boost-consulting.com Mon Jul 7 23:23:24 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 17:23:24 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> Message-ID: Prabhu Ramachandran writes: >>>>>> "DA" == David Abrahams writes: > > >> Hmm, so you are saying none of the functions should have ever > >> been written to deal with raw pointers at all and should all > >> have used shared_ptr? > > DA> Raw pointers are low-level. High-level interfaces are easier > DA> to use correctly and much easier to wrap. > > Indeed. > > >> But at some point using shared_ptr requires one to handle > >> reference cycles and figure how to break them > > DA> So does manual new/delete. > > Yes, but I've done that already and don't have the time to change all > my code to use smart pointers now. Essentially, its not a trivial > change for me to make (since my library is quite large and uses > pointers quite a bit) so I'll postpone this and update my to-do list. > > >> (using weak_ptrs). I'll admit that this is probably rare > >> (although I can think of a few candidates in my code) and a lot > >> easier to deal with. It also requires that the users generate > >> shared_ptrs when they create a new object. > > DA> I'm not sure what you mean by that. > > Its nothing important but what I meant was that a user of the library > has to use 'shared_ptr p(new A());' and not new A(). Not if the library supplies a shared_ptr factory function for A. A::create(); I'd tend to hide A's constructor(s) as well. > DA> If Pyste wants to supply auto_ptr and shared_ptr objects so > DA> that > > DA> A.held_by(auto_ptr) > DA> or > DA> A.held_by(shared_ptr) > > Hmm, I am not sure if the A.held_by approach is easy to do What could be hard about it? > but I do know that this can be done easily: > > holder(A, 'std::auto_ptr') > > Would that do? It ain't pretty, but it works. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 7 23:24:55 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 17:24:55 -0400 Subject: [C++-sig] Re: Strange behaviour for inheritance with C++ classes. References: <16137.50964.550088.466596@monster.linux.in> <3F09D166.1060304@globalite.com.br> <1057608318.6023.9.camel@corrosion> Message-ID: Thomas Muldowney writes: > On Mon, 2003-07-07 at 15:00, Nicodemus wrote: >> Hi Prabhu, >> Yeah, it is a Pyste bug. ;) >> The problem is related to AllFromHeader, if you explicitly export each >> class the problem goes away. The inheritance tests didn't catch this >> because they don't use AllFromHeader. >> It is fixed in CVS now, thanks for the report! >> >> Regards, >> Nicodemus. >> _______________________________________________ C++-sig mailing list >> C++-sig at python.org http://mail.python.org/mailman/listinfo/c++-sig > > Is there any chance of a CVS snapshot of pyste sometime soon? The SF > public CVS lag is making it a real pain to get these important updates. Somebody should make a tool which continuously scours the CVSWeb interface and keeps a snapshot up-to-date as things change. Should be easy enough for someone with http and Python knowledge, and would benefit all SourceForge users immensely. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Mon Jul 7 23:37:27 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 07 Jul 2003 18:37:27 -0300 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> Message-ID: <3F09E817.3050204@globalite.com.br> David Abrahams wrote: >Prabhu Ramachandran writes: > > >> DA> If Pyste wants to supply auto_ptr and shared_ptr objects so >> DA> that >> >> DA> A.held_by(auto_ptr) >> DA> or >> DA> A.held_by(shared_ptr) >> >>Hmm, I am not sure if the A.held_by approach is easy to do >> >> > >What could be hard about it? > > Because there is an ambiguity here, since you can acess the members of a class with the same syntax: exclude(A.foo) # exclude the foo member exclude(A.held_by) # exclude the held_by member Plus, all other options use the function syntax. Cheers, Nicodemus. From prabhu at aero.iitm.ernet.in Mon Jul 7 23:37:04 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 03:07:04 +0530 Subject: [C++-sig] Pyste: added new build options. In-Reply-To: <3F09E5B2.9090308@globalite.com.br> References: <16137.36006.159444.648080@monster.linux.in> <3F09C615.4080606@globalite.com.br> <16137.53014.729719.186773@monster.linux.in> <3F09D8B4.6070604@globalite.com.br> <16137.57674.91106.745828@monster.linux.in> <3F09E5B2.9090308@globalite.com.br> Message-ID: <16137.59392.77793.770006@monster.linux.in> >>>>> "N" == nicodemus writes: >> Arghh! This is a pain. Another issue is if two pyste files >> export different functions (free functions) from the same >> header we will end up with a name clash but I'm assuming that >> users can be asked to export all functions from the same file. N> I would like to avoid that kind of thing... it is error prone, N> and only generates compile time errors, which are a pain to N> read. I agree so perhaps the Export_Header_H can be renamed to Export_Interface_File_H? That way it should be safe, right? [snip] N> But then to generate the main.cpp you must have already N> generated all the others? I think that makes things more N> complicated than are worth... 8/ Perhaps the --xml-cache option N> would be better, if we can't solve this problem? Another option N> would be to make Pyste accept some xml files. [snip] N> But how would we know the name of the functions when we will N> generate main.cpp without calling GCCXML (which is the point of N> having "Export" functions in the files)? Well, we could parse the *.cpp files that were generated and extract the 'void Export_\w*?();' functions. That should not be very hard to do but I dont know how you feel about it. cheers, prabhu From prabhu at aero.iitm.ernet.in Mon Jul 7 23:38:10 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 03:08:10 +0530 Subject: [C++-sig] Re: Strange behaviour for inheritance with C++ classes. In-Reply-To: References: <16137.50964.550088.466596@monster.linux.in> <3F09D166.1060304@globalite.com.br> <1057608318.6023.9.camel@corrosion> Message-ID: <16137.59458.853584.504565@monster.linux.in> >>>>> "DA" == David Abrahams writes: DA> Somebody should make a tool which continuously scours the DA> CVSWeb interface and keeps a snapshot up-to-date as things DA> change. Should be easy enough for someone with http and DA> Python knowledge, and would benefit all SourceForge users DA> immensely. The trouble is that the CVSWeb interface is served off the backup server. prabhu From dave at boost-consulting.com Tue Jul 8 03:48:10 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 21:48:10 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> Message-ID: Nicodemus writes: > David Abrahams wrote: > >>Prabhu Ramachandran writes: >> >>> DA> If Pyste wants to supply auto_ptr and shared_ptr objects so >>> DA> that >>> >>> DA> A.held_by(auto_ptr) >>> DA> or >>> DA> A.held_by(shared_ptr) >>> >>>Hmm, I am not sure if the A.held_by approach is easy to do >>> >> >>What could be hard about it? >> > > Because there is an ambiguity here, since you can acess the members of > a class with the same syntax: > > exclude(A.foo) # exclude the foo member > exclude(A.held_by) # exclude the held_by member > > Plus, all other options use the function syntax. OK, holder(A, auto_ptr) is still a possibility. I don't have a strong feeling about what it should be though. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Tue Jul 8 03:48:30 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 07 Jul 2003 21:48:30 -0400 Subject: [C++-sig] Re: Strange behaviour for inheritance with C++ classes. References: <16137.50964.550088.466596@monster.linux.in> <3F09D166.1060304@globalite.com.br> <1057608318.6023.9.camel@corrosion> <16137.59458.853584.504565@monster.linux.in> Message-ID: Prabhu Ramachandran writes: >>>>>> "DA" == David Abrahams writes: > > DA> Somebody should make a tool which continuously scours the > DA> CVSWeb interface and keeps a snapshot up-to-date as things > DA> change. Should be easy enough for someone with http and > DA> Python knowledge, and would benefit all SourceForge users > DA> immensely. > > The trouble is that the CVSWeb interface is served off the backup > server. :( -- Dave Abrahams Boost Consulting www.boost-consulting.com From prabhu at aero.iitm.ernet.in Tue Jul 8 05:01:34 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 08:31:34 +0530 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> Message-ID: <16138.13326.952123.635272@monster.linux.in> >>>>> "DA" == David Abrahams writes: [snip] DA> OK, DA> holder(A, auto_ptr) DA> is still a possibility. I don't have a strong feeling about DA> what it should be though. How about holder(A, 'std::auto_ptr'), holder(A, 'boost::shared_ptr'), holder(A, 'user::smart_ptr'). Internally the HeldType will add the right template parameter? But what if the smart pointer is not a templated class? In that case we'd need to use something like this: holder(A, 'std::auto_ptr< %s >'), holder(A, 'user::smart_ptr'). Is that OK or is it too ugly? cheers, prabhu From mike at nospam.com Tue Jul 8 05:03:26 2003 From: mike at nospam.com (Mike Rovner) Date: Mon, 7 Jul 2003 20:03:26 -0700 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: Message-ID: Mike Rovner wrote: > David Abrahams wrote: >> "Mike Rovner" writes: >>> error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" >>> (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in >>> file1.obj > >> So, please send him a reproducible test case. > > As I understand, better extract relevant parts from BPL. It seems > easy to do. I failed to create "stand-alone" test case (without boost.python). So (meanwhile I hope) here is (latest from CVS) boost(.python) dependent test case: PCH: boost/python.hpp Other settings in vcproj by default. Tested only debug build with VS.NET 2003 and Python2.2. Hope I didn't miss anything. Regards, Mike begin 666 test.cpp M(VEN8VQU9&4@/&)O;W-T+W!Y=&AO;BYH<' ^#0IUPT*("!S=&0Z.G-TR!R971UPT*("!S=&0Z.G-TR!R971U71H;VX[( T*#0IS=')U8W0 at 5#(- M"GL-"B @9&]U8FQE('9A;#L-"@T*("!S=&%T:6,@PT*("!4,B8@(&=E="AI;G0@ M:2D@>R!R971U"(L)E0R.CIV86PI#0H@(" @.PT* M("!C;&%S7!E/2)6:7-U86P@ M0RLK(@T*"59E71H;VXB#0H)4V-C M4')O:F5C=$YA;64](B(-"@E38V-,;V-A;%!A=&@](B(^#0H)/%!L871F;W)M M55S86=E/2)&04Q312(- M"@D)"4-H87)A8W1E'!A;G-I;VX](C$B#0H)"0D)061D:71I;VYA;$EN8VQU9&5$:7)E8W1O71H;VXN<&-H(@T*"0D)"4%S71H;VXN<&1B(@T*"0D)"4EM<&]R=$QI M8G)A71H;VXN=&QB(B\^#0H)"0D\5&]O; T*"0D)"4YA;64](E9#4&]S M=$)U:6QD179E;G14;V]L(B\^#0H)"0D\5&]O; T*"0D)"4YA;64](E9#4')E M0G5I;&1%=F5N=%1O;VPB+SX-"@D)"3Q4;V]L#0H)"0D)3F%M93TB5D-071H;VY\5VEN,S(B M#0H)"0E/=71P=71$:7)E8W1OF5S M0U)U;E1I;65,:6)R87)Y57-A9V4](D9!3%-%(@T*"0D)0VAAF%T:6]N/2(P(@T*"0D)"4%D M9&ET:6]N86Q);F-L=61E1&ER96-T;W)I97,](E,Z7&)O;W-T(@T*"0D)"5!R M97!R;V-E7!E26YF;STB5%)512(-"@D)"0E071H;VXN<&-H(@T*"0D)"4%S M71H;VXM;V)J+R(- M"@D)"0E/8FIE8W1&:6QE/2(N7&1E8G5G+7!Y=&AO;BUO8FHO(@T*"0D)"5!R M;V=R86U$871A0F%S949I;&5.86UE/2(N7&1E8G5G+7!Y=&AO;BUO8FHO(@T* M"0D)"5=A71H M;VY?9&5B=6=?9"YL:6(B+SX-"@D)"3Q4;V]L#0H)"0D)3F%M93TB5D--241, M5&]O;"(-"@D)"0E071H;VXN=&QB M(B\^#0H)"0D\5&]O; T*"0D)"4YA;64](E9#4&]S=$)U:6QD179E;G14;V]L M(B\^#0H)"0D\5&]O; T*"0D)"4YA;64](E9#4')E0G5I;&1%=F5N=%1O;VPB M+SX-"@D)"3Q4;V]L#0H)"0D)3F%M93TB5D-07!E/2(R(@T*"0D)57-E3V9-1D,](C B M#0H)"0E!5$Q-:6YI;6EZ97-#4G5N5&EM94QI8G)A71H;VXN<&-H(@T*"0D)"4%S71H;VY?9"YL:6(B+SX-"@D)"3Q4;V]L#0H)"0D)3F%M93TB5D--241, M5&]O;"(-"@D)"0E071H;VXN=&QB M(B\^#0H)"0D\5&]O; T*"0D)"4YA;64](E9#4&]S=$)U:6QD179E;G14;V]L M(@T*"0D)"41E'E'96YE&EL:6%R>4UA;F%G9617#MR8SMD968[71H M;VY?8F%S92YC<' B/@T*"0D)/"]&:6QE/@T*"0D)/$9I;&4-"@D)"0E296QA M=&EV95!A=&@](BXN7"XN7'-R8UQC;VYV97)T97)<8G5I;'1I;E]C;VYV97)T M97)S+F-P<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E M4&%T:#TB+BY<+BY<71H;VXN8W!P(CX-"@D)"3PO M1FEL93X-"@D)"3Q&:6QE#0H)"0D)4F5L871I=F50871H/2(N+EPN+EQS2YC<' B/@T*"0D)/"]& M:6QE/@T*"0D)/$9I;&4-"@D)"0E296QA=&EV95!A=&@](BXN7"XN7'-R8UQS M='(N8W!P(CX-"@D)"3PO1FEL93X-"@D)"3Q&:6QE#0H)"0D)4F5L871I=F50 M871H/2(N+EPN+EQS71H;VY<8F%S97,N M:'!P(CX-"@D)"3PO1FEL93X-"@D)"3Q&:6QE#0H)"0D)4F5L871I=F50871H M/2(N+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY<8F]R71H;VY<8V%L;"YH<' B/@T*"0D)/"]&:6QE/@T*"0D) M/$9I;&4-"@D)"0E296QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T7'!Y M=&AO;EQC86QL7VUE=&AO9"YH<' B/@T*"0D)/"]&:6QE/@T*"0D)/$9I;&4- M"@D)"0E296QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T7'!Y=&AO;EQC M87-T+FAP<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E M4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY<9&%T85]M96UB97)S+FAP<"(^#0H)"0D\ M+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY< M+BY<8F]O71H;VY<9&EC="YH<' B/@T*"0D)/"]&:6QE/@T*"0D)/$9I;&4-"@D)"0E2 M96QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T7'!Y=&AO;EQE;G5M+FAP M<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB M+BY<+BY<+BY<+BY<8F]O&-E<'1I;VY?=')A;G-L871O'1R86-T+FAP<"(^#0H)"0D\+T9I;&4^#0H) M"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY<;'9A;'5E7V9R;VU?<'ET>7!E+FAP<"(^ M#0H)"0D\+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB+BY< M+BY<+BY<+BY<8F]O71H;VY<;6%N86=E7VYE=U]O8FIE8W0N:'!P(CX-"@D) M"3PO1FEL93X-"@D)"3Q&:6QE#0H)"0D)4F5L871I=F50871H/2(N+EPN+EPN M+EPN+EQB;V]S=%QP>71H;VY<;6]D=6QE+FAP<"(^#0H)"0D\+T9I;&4^#0H) M"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY<;V)J96-T+FAP M<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB M+BY<+BY<+BY<+BY<8F]O71H;VY<;V)J96-T7VET96US+FAP<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL M90T*"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY< M;V)J96-T7W!R;W1O8V]L+FAP<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL90T* M"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY<;W!E M71H;VY<;W1H97(N:'!P(CX-"@D)"3PO M1FEL93X-"@D)"3Q&:6QE#0H)"0D)4F5L871I=F50871H/2(N+EPN+EPN+EPN M+EQB;V]S=%QP>71H;VY<;W9E71H;VY<<')O M>'DN:'!P(CX-"@D)"3PO1FEL93X-"@D)"3Q&:6QE#0H)"0D)4F5L871I=F50 M871H/2(N+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY<<'1R+FAP<"(^#0H)"0D\ M+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY< M+BY<8F]O&ES=&EN9U]O8FIE8W0N:'!P(CX-"@D)"3PO M1FEL93X-"@D)"3Q&:6QE#0H)"0D)4F5L871I=F50871H/2(N+EPN+EPN+EPN M+EQB;V]S=%QP>71H;VY<71H;VY< M71H;VY<=&%G+FAP<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL M90T*"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H M;VY<=&]?<'ET:&]N7VEN9&ER96-T+FAP<"(^#0H)"0D\+T9I;&4^#0H)"0D\ M1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O7!E7VED+FAP M<"(^#0H)"0D\+T9I;&4^#0H)"0D\1FEL90T*"0D)"5)E;&%T:79E4&%T:#TB M+BY<+BY<+BY<+BY<8F]O71H;VY<9&5T86EL7&%R9U]T=7!L95]S:7IE+FAP<"(^#0H)"0D)/"]&:6QE M/@T*"0D)"3Q&:6QE#0H)"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY< M8F]O71H;VY<9&5T86EL7&-A;&Q?;V)J96-T+FAP<"(^#0H) M"0D)/"]&:6QE/@T*"0D)"3Q&:6QE#0H)"0D)"5)E;&%T:79E4&%T:#TB+BY< M+BY<+BY<+BY<8F]O71H;VY<9&5T86EL7&-H87)?87)R87DN:'!P(CX- M"@D)"0D\+T9I;&4^#0H)"0D)/$9I;&4-"@D)"0D)4F5L871I=F50871H/2(N M+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY<9&5T86EL7&-O;F9I9RYH<' B/@T* M"0D)"3PO1FEL93X-"@D)"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN M7"XN7"XN7"XN7&)O;W-T7'!Y=&AO;EQD971A:6Q<8V]N71H;VY<9&5T86EL7&1E8V]R M871E9%]T>7!E7VED+FAP<"(^#0H)"0D)/"]&:6QE/@T*"0D)"3Q&:6QE#0H) M"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY<9&5T86EL7&1E9F%U;'1S7V=E;BYH<' B/@T*"0D)"3PO1FEL93X- M"@D)"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O M;W-T7'!Y=&AO;EQD971A:6Q<9&5P96YD96YT+FAP<"(^#0H)"0D)/"]&:6QE M/@T*"0D)"3Q&:6QE#0H)"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY< M8F]O&-E<'1I;VY?:&%N9&QE71H;VY<9&5T86EL7&EF7V5L M71H;VY<9&5T86EL7&EN9&ER M96-T7W1R86ET71H;VY<9&5T86EL7&UE;6)E71H;VY<9&5T86EL7&US M=F-?='EP96EN9F\N:'!P(CX-"@D)"0D\+T9I;&4^#0H)"0D)/$9I;&4-"@D) M"0D)4F5L871I=F50871H/2(N+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY<9&5T M86EL7&YO;F4N:'!P(CX-"@D)"0D\+T9I;&4^#0H)"0D)/$9I;&4-"@D)"0D) M4F5L871I=F50871H/2(N+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY<9&5T86EL M7&YO=%]S<&5C:69I960N:'!P(CX-"@D)"0D\+T9I;&4^#0H)"0D)/$9I;&4- M"@D)"0D)4F5L871I=F50871H/2(N+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY< M9&5T86EL7&]P97)A=&]R7VED+FAP<"(^#0H)"0D)/"]&:6QE/@T*"0D)"3Q& M:6QE#0H)"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY<9&5T86EL7'!Y=&AO;C(R7V9I>&5D+F at B/@T*"0D) M"3PO1FEL93X-"@D)"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN M7"XN7"XN7&)O;W-T7'!Y=&AO;EQD971A:6Q<71H;VY<9&5T86EL7')E='5R M;FEN9RYH<' B/@T*"0D)"3PO1FEL93X-"@D)"0D\1FEL90T*"0D)"0E296QA M=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T7'!Y=&AO;EQD971A:6Q<71H;VY<9&5T86EL7'-T71H;VY<9&5T86EL M7'1R86YS;&%T95]E>&-E<'1I;VXN:'!P(CX-"@D)"0D\+T9I;&4^#0H)"0D) M/$9I;&4-"@D)"0D)4F5L871I=F50871H/2(N+EPN+EPN+EPN+EQB;V]S=%QP M>71H;VY<9&5T86EL7'1Y<&5?;&ES="YH<' B/@T*"0D)"3PO1FEL93X-"@D) M"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T M7'!Y=&AO;EQD971A:6Q<='EP95]L:7-T7VEM<&PN:'!P(CX-"@D)"0D\+T9I M;&4^#0H)"0D)/$9I;&4-"@D)"0D)4F5L871I=F50871H/2(N+EPN+EPN+EPN M+EQB;V]S=%QP>71H;VY<9&5T86EL7'1Y<&5?;&ES=%]I;7!L7VYO7W!T71H;VY<9&5T M86EL7'9O:61?71H;VY<8V]N=F5R=&5R7&%R9U]F71H;VY<8V]N=F5R=&5R7&-O;G-T71H;VXN:'!P(CX-"@D) M"0D\+T9I;&4^#0H)"0D)/$9I;&4-"@D)"0D)4F5L871I=F50871H/2(N+EPN M+EPN+EPN+EQB;V]S=%QP>71H;VY<8V]N=F5R=&5R7&EM<&QI8VET+FAP<"(^ M#0H)"0D)/"]&:6QE/@T*"0D)"3Q&:6QE#0H)"0D)"5)E;&%T:79E4&%T:#TB M+BY<+BY<+BY<+BY<8F]O71H;VY<8V]N=F5R=&5R7'!O:6YT97)?='EP95]I9"YH<' B/@T*"0D) M"3PO1FEL93X-"@D)"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN M7"XN7"XN7&)O;W-T7'!Y=&AO;EQC;VYV97)T97)<<'EO8FIE8W1?=')A:71S M+FAP<"(^#0H)"0D)/"]&:6QE/@T*"0D)"3Q&:6QE#0H)"0D)"5)E;&%T:79E M4&%T:#TB+BY<+BY<+BY<+BY<8F]O6]B M:F5C=%]T>7!E+FAP<"(^#0H)"0D)/"]&:6QE/@T*"0D)"3Q&:6QE#0H)"0D) M"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71Y<&5?87)G7V9R;VU?<'ET:&]N+FAP<"(^#0H)"0D)/"]&:6QE M/@T*"0D)"3Q&:6QE#0H)"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY< M8F]O71Y<&5?;V)J96-T7VUG71H;VY<8V]N=F5R=&5R7')E M9VES=&5R960N:'!P(CX-"@D)"0D\+T9I;&4^#0H)"0D)/$9I;&4-"@D)"0D) M4F5L871I=F50871H/2(N+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY<8V]N=F5R M=&5R7')E9VES=&5R961?<&]I;G1E92YH<' B/@T*"0D)"3PO1FEL93X-"@D) M"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T M7'!Y=&AO;EQC;VYV97)T97)<71H;VY<8V]N=F5R=&5R7')E='5R;E]F71H;VY<8V]N=F5R=&5R7'1O7W!Y=&AO;E]F=6YC=&EO;E]T>7!E+FAP M<"(^#0H)"0D)/"]&:6QE/@T*"0D)/"]&:6QT97(^#0H)"0D\1FEL=&5R#0H) M"0D)3F%M93TB;V)J96-T(@T*"0D)"49I;'1E71H;VY<;V)J96-T7&-L87-S7V-O;G9E71H;VY<;V)J96-T7&-L87-S7V1E=&%I;"YH<' B/@T*"0D) M"3PO1FEL93X-"@D)"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN M7"XN7"XN7&)O;W-T7'!Y=&AO;EQO8FIE8W1<8VQA71H;VY<;V)J96-T7&9I;F1?:6YS M=&%N8V4N:'!P(CX-"@D)"0D\+T9I;&4^#0H)"0D)/$9I;&4-"@D)"0D)4F5L M871I=F50871H/2(N+EPN+EPN+EPN+EQB;V]S=%QP>71H;VY<;V)J96-T7&9O M71H;VY<;V)J96-T7&9U M;F-T:6]N+FAP<"(^#0H)"0D)/"]&:6QE/@T*"0D)"3Q&:6QE#0H)"0D)"5)E M;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O71H;VY< M;V)J96-T7&9U;F-T:6]N7V]B:F5C="YH<' B/@T*"0D)"3PO1FEL93X-"@D) M"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T M7'!Y=&AO;EQO8FIE8W1<:6YH97)I=&%N8V4N:'!P(CX-"@D)"0D\+T9I;&4^ M#0H)"0D)/$9I;&4-"@D)"0D)4F5L871I=F50871H/2(N+EPN+EPN+EPN+EQB M;V]S=%QP>71H;VY<;V)J96-T7&EN71H;VY<;V)J M96-T7'!O:6YT97)?:&]L9&5R+FAP<"(^#0H)"0D)/"]&:6QE/@T*"0D)"3Q& M:6QE#0H)"0D)"5)E;&%T:79E4&%T:#TB+BY<+BY<+BY<+BY<8F]O5]F=6YC=&EO;BYH<' B/@T*"0D)"3PO1FEL93X-"@D) M"0D\1FEL90T*"0D)"0E296QA=&EV95!A=&@](BXN7"XN7"XN7"XN7&)O;W-T M7'!Y=&AO;EQO8FIE8W1<7!E/2)6:7-U86P@ M0RLK(@T*"59ET$S1D%$-C S+35!03 at M-#7!E/2(R(@T*"0D)0VAA3TB,2(-"@D)"0E5 M71H;VY?9"YL:6(B#0H)"0D)3W5T<'5T1FEL93TB M)"A/=71$:7(I+W1E41I71H;VXR M,B]L:6)S.U,Z7&)O;W-T7&QI8G-<<'ET:&]N7&)U:6QD7%9I7-T96T](C(B#0H)"0D)26UP;W)T3&EB3TB)"A/=71$ M:7(I+W1E4=E M;F5R871O6UE;G14;V]L(B\^#0H)"0D\5&]O; T*"0D)"4YA;64](E9#36%N86=E M9%=R87!P97)'96YE'-D(@T* M"0D)56YI<75E261E;G1I9FEESDS.3DU,S at P+3@Y0D0M-&(P-"TX.$5" M+38R-49"134R14)&0GTB/@T*"0D\+T9I;'1E Hi, I was thinking of something along these lines: 1. While writing the module section for each class, also add a comment that contains all the bases in order (via ClassBases). Something like so: // bases = [B, C, D] void Export_A() 2. I'll then read this 'bases' information when generating _main.cpp and then for each base, ensure that the order is such that each of the bases or ancestral bases is exported earlier. I'm guessing that this should be fairly easy to do and does not seem too bad a hack to be considered inelegant. It also eliminates the need to generate a separate file. Is there a simpler way or an alternative? Thoughts? BTW, in your code you group the exporters based on the header used and then sort the list based on Order. I'm not sure that this approach is guaranteed to work all the time since if the base is in another header the sorting won't work. However, I might be wrong and if you are sure that it will work then we could do that, i.e. write the header info and then the 'Order' then do the same thing that you do. Will this approach work? What do you folks think? Thanks! cheers, prabhu From prabhu at aero.iitm.ernet.in Tue Jul 8 10:56:47 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Tue, 8 Jul 2003 14:26:47 +0530 Subject: [C++-sig] Pyste: problems with inheritance across headers. Message-ID: <16138.34639.379626.879015@monster.linux.in> Hi, I found a few more serious bugs with Pyste. I split up a simple class hierarchy over several header files and also made different pyste files to wrap these. Pyste has difficulty with executing the module functions in the right order (as I suspected in an earlier post) and also has difficulties with the base classes. The trouble being that the exported_names are grouped by headers and only the exported names grouped by header are known when generating the code for a class. So if a base class is in another header the bases will not be correctly set leading to problems. Possible resolution for this problem: 1. Compute all the exported names in one go and then use that information when generating the code. 2. Additionally, do not use grouping by headers to order the writes. A more sophisticated approach is needed to get the right sequence of module initialization. 3. Assume that all bases are exported by default instead of relying on exported_names. I guess this is not an option. :( The necessity of the exported_names destroys my plans of incremental generation of wrappers without generating an additional file with necessary information. Why? Well, because when you generate wrappers with a single pyste file it has no way of knowing the exported names from other pyste files and therefore will not set the bases correctly. So the only way of doing this would be to allow Pyste to generate the xml file into an _interface.xml in individual steps and then get Pyste to use the generated XML files touching only the wrapper files that changed. My guess is that this will reduce the time taken to generate the interface files. This is what Nicodemus was saying earlier but I learnt it from 'The University of Hard Knocks'. Essentially the --only-wrap and --only-main options are useless. Instead we need a --generate-xml and --use-xml option. --generate-xml simply generates the xml file(s) and --use-xml does not call gccxml and uses the generated xml file(s). Its up to the build system to determine when and how to generate the xml file when the interface file changes and that is quite easy to do. I've attached a tarball of the files that demonstrate the above problem with inheritance across several headers. Anyway, I'd like to know if the above approach for multiple files is possible or I'm missing something again. If it is, I can probably work on a patch sometime, unless Nicodemus has it covered. cheers, prabhu -------------- next part -------------- A non-text attachment was scrubbed... Name: pyste_bug.tar.gz Type: application/octet-stream Size: 801 bytes Desc: pyste bug demo URL: From dave at boost-consulting.com Tue Jul 8 15:23:12 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 08 Jul 2003 09:23:12 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> Message-ID: Prabhu Ramachandran writes: >>>>>> "DA" == David Abrahams writes: > > [snip] > DA> OK, > > DA> holder(A, auto_ptr) > > DA> is still a possibility. I don't have a strong feeling about > DA> what it should be though. > > How about holder(A, 'std::auto_ptr'), holder(A, 'boost::shared_ptr'), > holder(A, 'user::smart_ptr'). I dislike that because it assumes too much about the way to spell the smart pointer type: it would have to be of the form 'pointer_name', which rules out, e.g. 'pointer_name'. > Internally the HeldType will add the right template parameter? But > what if the smart pointer is not a templated class? That's why I was suggesting holder(class_ID, unary_callable) The callable object is free to form the string any way it likes. > In that case > we'd need to use something like this: > > holder(A, 'std::auto_ptr< %s >'), holder(A, 'user::smart_ptr'). ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ I don't understand what this part is illustrating. > Is that OK or is it too ugly? The %s is not too bad, and would be easier to use on-the-fly than my callable interface holder(A, lambda s: 'std::auto_ptr< %s >' % s) Though slightly less-flexible. I don't have a strong feeling for what's better here. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Tue Jul 8 15:24:29 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 08 Jul 2003 09:24:29 -0400 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: Message-ID: "Mike Rovner" writes: > Mike Rovner wrote: >> David Abrahams wrote: >>> "Mike Rovner" writes: >>>> error LNK2005: "class boost::arg<3> `anonymous namespace'::_3" >>>> (?_3@?A0x2264d27d@@3V?$arg@$02 at boost@@A) already defined in >>>> file1.obj >> >>> So, please send him a reproducible test case. >> >> As I understand, better extract relevant parts from BPL. It seems >> easy to do. > > I failed to create "stand-alone" test case (without boost.python). > So (meanwhile I hope) here is (latest from CVS) boost(.python) dependent > test case: > > PCH: boost/python.hpp > Other settings in vcproj by default. > > Tested only debug build with VS.NET 2003 and Python2.2. > > Hope I didn't miss anything. Did you cc: this to Jason Shirk? He's the only one who can do anything with it. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Tue Jul 8 18:11:38 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Tue, 08 Jul 2003 13:11:38 -0300 Subject: [C++-sig] Pyste: Resolution of order of exports. In-Reply-To: <16138.18831.392828.183865@monster.linux.in> References: <16138.18831.392828.183865@monster.linux.in> Message-ID: <3F0AED3A.6020701@globalite.com.br> Prabhu Ramachandran wrote: >Hi, > >I was thinking of something along these lines: > > 1. While writing the module section for each class, also add a > comment that contains all the bases in order (via ClassBases). > Something like so: > >// bases = [B, C, D] >void Export_A() > > > 2. I'll then read this 'bases' information when generating _main.cpp > and then for each base, ensure that the order is such that each of > the bases or ancestral bases is exported earlier. I'm guessing > that this should be fairly easy to do and does not seem too bad a > hack to be considered inelegant. It also eliminates the need to > generate a separate file. Is there a simpler way or an > alternative? Thoughts? > I don't know, it seems to much like a "hack" to me. 8/ Let's get together on IRC to discuss this better, like you proposeed. >BTW, in your code you group the exporters based on the header used and >then sort the list based on Order. I'm not sure that this approach is >guaranteed to work all the time since if the base is in another header >the sorting won't work. However, I might be wrong and if you are sure >that it will work then we could do that, i.e. write the header info >and then the 'Order' then do the same thing that you do. > >Will this approach work? What do you folks think? > > From your other email, we have a bug here. 8( Thanks Prabhu, Nicodemus. From nicodemus at globalite.com.br Tue Jul 8 18:48:22 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Tue, 08 Jul 2003 13:48:22 -0300 Subject: [C++-sig] Pyste: problems with inheritance across headers. In-Reply-To: <16138.34639.379626.879015@monster.linux.in> References: <16138.34639.379626.879015@monster.linux.in> Message-ID: <3F0AF5D6.2000207@globalite.com.br> Hi, Prabhu Ramachandran wrote: >Hi, > >I found a few more serious bugs with Pyste. I split up a simple class >hierarchy over several header files and also made different pyste >files to wrap these. Pyste has difficulty with executing the module >functions in the right order (as I suspected in an earlier post) and >also has difficulties with the base classes. The trouble being that >the exported_names are grouped by headers and only the exported names >grouped by header are known when generating the code for a class. So >if a base class is in another header the bases will not be correctly >set leading to problems. > > Yep, a serious bug indeed. 8( The original algorithm worked without problems, but I received reports (I lost the email, can't tell who was 8/) that the memory consumption was too high: while trying to export lots of classes, the memory usage reached about 600+Mb, which made pyste unusable. The memory usage grew so much because all the headers were being parsed and kept in memory, because I needed to order the exports by number of base classes, to ensure that base classes are instantiated first. Then I changed the algorithm to what it is today: group the exporters by header files, and parse one at a time, and discard the parsed declarations immediately. The rationale is that given a class C in a header file, that header contains all information needed about the base classes. Of course, I ignored that all the exporters wouldn't be avaiable at the same time to order them. We have two problems here: 1. exported_names is not working correctly, it depends on the order that the exporters generate the code, and that order is basically randomical. 2. The order that the classes are being instantiated is not correct. >Possible resolution for this problem: > > 1. Compute all the exported names in one go and then use that > information when generating the code. > Yes, that solves problem #1. Since we parse all pyste files in the beginning, we have all the name of all classes that are being exported. I just tested this and it works fine. > 2. Additionally, do not use grouping by headers to order the writes. > A more sophisticated approach is needed to get the right sequence > of module initialization. > > Yes, and here we have a hairy problem, more below. > 3. Assume that all bases are exported by default instead of relying > on exported_names. I guess this is not an option. :( > Agreed. 8/ >The necessity of the exported_names destroys my plans of incremental >generation of wrappers without generating an additional file with >necessary information. Why? Well, because when you generate wrappers >with a single pyste file it has no way of knowing the exported names >from other pyste files and therefore will not set the bases correctly. > > Indeed, we have to give Pyste all pyste files to be able to generate the correct code. >So the only way of doing this would be to allow Pyste to generate the >xml file into an _interface.xml in individual steps and then get Pyste >to use the generated XML files touching only the wrapper files that >changed. My guess is that this will reduce the time taken to generate >the interface files. This is what Nicodemus was saying earlier but I >learnt it from 'The University of Hard Knocks'. > Hehehe, I didn't know that expression. >Essentially the --only-wrap and --only-main options are useless. > 8( >Instead we need a --generate-xml and --use-xml option. --generate-xml >simply generates the xml file(s) and --use-xml does not call gccxml >and uses the generated xml file(s). Its up to the build system to >determine when and how to generate the xml file when the interface >file changes and that is quite easy to do. > Is it easy for a build system to delete a file when a file that it depends changes (I am talking here about deleting the xml file whenever the header changes)? If so, I believe that an option that tells Pyste of a directory where to write xml files would be sufficient. If a file with the same name of a header is not present, parse it with gccxml and write the file in that directory. Otherwise, use the file already there. If a header changes, the xml is deleted and Pyste will regenerate it. But first we have to solve "The Big Nasty Bug". ;) >I've attached a tarball of the files that demonstrate the above >problem with inheritance across several headers. > > Thanks! They were great help to understand better the bug. I will add them to the test suite too. >Anyway, I'd like to know if the above approach for multiple files is >possible or I'm missing something again. If it is, I can probably >work on a patch sometime, unless Nicodemus has it covered. > Let's discuss this and share some work. 8) To solve the bug, we have to somehow parse all the files first to get the ordering for them. Problem is that this consumes a lot of memory with large libraries (enough to make it unusable) if we use a naive approach. I was thinking along this line: 1. Gather all the "infos" and generate the exported_names dict. Easy enough. 2. Parse all headers, one at a time: a) For each export, we generate its "order", since we have a list of its bases and the exported_names. b) save the declarations to disk somehow, so we can generate the code later (Pickle can be our friend here). c) destroy the declarations, to save memory 3. Now we have all the exporters, in the right order. 4. For each exporter, read the parsed information from disk, generate code, dispose it. We can just keep the xml file in disk while we order the exporters, instead of actually saving it. But then we have to parse it again, and that could take a while. If that's the case, we could save a pickle representation of the declarations instead. What do you think? Thanks again Prabhu! Regards, Nicodemus. From mike at nospam.com Tue Jul 8 18:56:17 2003 From: mike at nospam.com (Mike Rovner) Date: Tue, 8 Jul 2003 09:56:17 -0700 Subject: [C++-sig] Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: Message-ID: David Abrahams wrote: >> Mike Rovner wrote: >>> David Abrahams wrote: >>>> So, please send him a reproducible test case. >>> >> Hope I didn't miss anything. > > Did you cc: this to Jason Shirk? He's the only one who can do > anything with it. Yes, of cause. Mike From mike at nospam.com Tue Jul 8 21:28:04 2003 From: mike at nospam.com (Mike Rovner) Date: Tue, 8 Jul 2003 12:28:04 -0700 Subject: [C++-sig] Re: Re: VC++ 7.1 (VStudio.NET 2003) linking problem References: <20030703004342.91959.qmail@web20206.mail.yahoo.com> Message-ID: Mike Rovner wrote: > Ralf W. Grosse-Kunstleve wrote: >> I am curious, what is the effect of enabling or disabling >> pre-compiled headers on the compile times? Huge, modest, small? With properly set PCH (I corrected a misspelling and reorganized #include order) the effect is HUGE: from 3-4 minutes per file I jumped to 10-15 sec, so overall time is less than a minute. Wow, it's fantastic. VS.NET 2003 Regards, Mike From prabhu at aero.iitm.ernet.in Tue Jul 8 21:30:53 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Wed, 9 Jul 2003 01:00:53 +0530 Subject: [C++-sig] Pyste: problems with inheritance across headers. In-Reply-To: <3F0AF5D6.2000207@globalite.com.br> References: <16138.34639.379626.879015@monster.linux.in> <3F0AF5D6.2000207@globalite.com.br> Message-ID: <16139.7149.211713.215898@monster.linux.in> Hi, >>>>> "N" == nicodemus writes: [snip bug details] As I mentioned and Nicodemus confirmed here are the current problems. N> 1. exported_names is not working correctly, it depends on the N> order that N> the exporters generate the code, and that order is basically N> randomical. N> 2. The order that the classes are being instantiated is not N> correct. N> Yes, and here we have a hairy problem, more below. [snip other details] Nicodemus and I had a very productive discussion on IRC (irc.debian.org/#pyste) and here is a brief summary of what we discussed for the benefit of the list. There are two problems as outlined above. Nicodemus also mentioned that in an earlier version of Pyste he'd parse all the headers and store the resulting XML representation in memory and this would make memory usage go up to even 600+MB. So we essentially had three problems. 1. Need parsed header information but can't keep all of the XML file related information in memory due to excessive memory usage. 2. Cannot group exporters via headers and need to generate all exported_names and only then generate the wrapper code. If this is not done the class bases information is incorrect. 3. Order of the class instantiation can potentially be incorrect. Finally, incremental generation of wrapper code also needed to be addressed. As I mentioned and Nicodemus confirmed in his reply to me, problem 2 is easily solved by first generating all the exported_names. This problem is not tied to problem 1 since the exported_names come from the Pyste interface files which are user generated and do not depend on GCCXML. The third problem was more complicated and after some discussion we came up with what believe to be a decent solution. In --multiple mode, we generate the XML for each of the headers. So for the purpose of discussion we'll assume that all the XML files exist. 1. Based on the known generated_names (that is obtained from the interface files) we parse the various XML files and generate the necessary code in the Single/MultipleCodeUnit for the respective classes, functions etc. As each file is parsed and this code is generated memory is freed thus eliminating problem 1. 2. Using the classexporters we get the class base information. This is already known and infact this information is also refined thanks to the exported names. 3. Order the execution of the Export_ClassName() function calls in the module initialization based on the class/base information and write this to the main.cpp. This code might get a little complicated but should not be too hard. The only trouble we saw with this approach was for the case without --multiple. This will require some modifications to the SingleCodeUnit class but Nicodemus said this should not be a big problem. Essentially before saving the SingleCodeUnit we'd need to order the methods correctly. As regards incremental generation generating the xml file is usually quite a slow operation and the approach we have chosen to go in for is to add two options and is best described with a simple example. pyste.py --xml-dir=xml --generate-xml file1.hpp file2.hpp ... This command merely generates the xml data from the headers and puts them inside the directory xml. pyste.py --xml-dir=xml --out=. --module=module --use-xml \ file1.pyste file2.pyste ... This command uses the generated XML files, if some of them dont exist it generates them. Once the XML files are available it uses the information in the interface files passed and then generates the wrapper code and also a _main.cpp. Nicodemus said he'd try and get the ordering of the module init functions correct since he already has the base information working correctly. I'll try to get the --use-xml and --generate-xml options working. Thats about it. If these bugs are resolved we hope that Pyste should be quite useable. cheers, prabhu From prabhu at aero.iitm.ernet.in Tue Jul 8 21:38:57 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Wed, 9 Jul 2003 01:08:57 +0530 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> Message-ID: <16139.7633.533988.44428@monster.linux.in> >>>>> "DA" == David Abrahams writes: >> How about holder(A, 'std::auto_ptr'), holder(A, >> 'boost::shared_ptr'), holder(A, 'user::smart_ptr'). DA> I dislike that because it assumes too much about the way to DA> spell the smart pointer type: it would have to be of the form DA> 'pointer_name', which rules out, DA> e.g. 'pointer_name'. [snip] >> Internally the HeldType will add the right template parameter? >> But what if the smart pointer is not a templated class? DA> That's why I was suggesting DA> holder(class_ID, unary_callable) DA> The callable object is free to form the string any way it DA> likes. >> In that case we'd need to use something like this: >> >> holder(A, 'std::auto_ptr< %s >'), holder(A, 'user::smart_ptr'). DA> ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ DA> I don't understand what this part is illustrating. It is illustrating a user namespace with a smart_ptr class that is not templated. It does not matter. I don't see the point of the callable function. It only seems to complicate the interface. When writing Pyste files the user *will* know the name of the class and will know what smart pointer he/she wants to use. In that case I see nothing wrong with the user specifying the entire HeldType i.e. holder('std::auto_ptr') or holder('pointer_name') or whatever they choose. The callable function simply adds another unnecessary layer to this and ends up doing the same thing by generating a string that specifies the smart pointer. cheers, prabhu From dave at boost-consulting.com Tue Jul 8 22:58:19 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 08 Jul 2003 16:58:19 -0400 Subject: [C++-sig] Re: Pyste: problems with inheritance across headers. References: <16138.34639.379626.879015@monster.linux.in> <3F0AF5D6.2000207@globalite.com.br> <16139.7149.211713.215898@monster.linux.in> Message-ID: Prabhu Ramachandran writes: > The only trouble we saw with this approach was for the case without > --multiple. This will require some modifications to the > SingleCodeUnit class but Nicodemus said this should not be a big > problem. Essentially before saving the SingleCodeUnit we'd need to > order the methods correctly. I admit to not having a deep understanding of the issues here, but it seems like you might solve some significant ordering problems by parsing the XML and using pickle/shelve to create representations of the classes that are quickly readable by Python, then making a separate pass over these data structures. Just-a-random-thought-ly, -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Tue Jul 8 23:01:33 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 08 Jul 2003 17:01:33 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> <16139.7633.533988.44428@monster.linux.in> Message-ID: Prabhu Ramachandran writes: >>>>>> "DA" == David Abrahams writes: > > >> How about holder(A, 'std::auto_ptr'), holder(A, > >> 'boost::shared_ptr'), holder(A, 'user::smart_ptr'). > > DA> I dislike that because it assumes too much about the way to > DA> spell the smart pointer type: it would have to be of the form > DA> 'pointer_name', which rules out, > DA> e.g. 'pointer_name'. > > [snip] > >> Internally the HeldType will add the right template parameter? > >> But what if the smart pointer is not a templated class? > > DA> That's why I was suggesting > > DA> holder(class_ID, unary_callable) > > DA> The callable object is free to form the string any way it > DA> likes. > > >> In that case we'd need to use something like this: > >> > >> holder(A, 'std::auto_ptr< %s >'), holder(A, 'user::smart_ptr'). > DA> ^^^^^^^^^^^^^^^^^^^^^^^^^^^^ > DA> I don't understand what this part is illustrating. > > It is illustrating a user namespace with a smart_ptr class that is not > templated. It does not matter. > > I don't see the point of the callable function. It only seems to > complicate the interface. Can you generate 'some_ptr' with your interface? > When writing Pyste files the user *will* > know the name of the class and will know what smart pointer he/she > wants to use. In that case I see nothing wrong with the user > specifying the entire HeldType i.e. holder('std::auto_ptr') or > holder('pointer_name') or whatever they > choose. Likewise, there's nothing wrong with skipping Pyste altogether and using the direct Boost.Python C++ interface. Pyste is about providing an even terser syntax for accomplishing the same things, and 'std::auto_ptr' is not only longer but it repeats information. Also, how will that interface work when you have a class with virtual functions that you want to be held by auto_ptr? > The callable function simply adds another unnecessary layer to this > and ends up doing the same thing by generating a string that > specifies the smart pointer. No, it makes the syntax terser, makes the interface more flexible, and works with polymorphic classes. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Tue Jul 8 23:17:02 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Tue, 08 Jul 2003 18:17:02 -0300 Subject: [C++-sig] Re: Pyste: problems with inheritance across headers. In-Reply-To: References: <16138.34639.379626.879015@monster.linux.in> <3F0AF5D6.2000207@globalite.com.br> <16139.7149.211713.215898@monster.linux.in> Message-ID: <3F0B34CE.50109@globalite.com.br> David Abrahams wrote: >Prabhu Ramachandran writes: > > > > >>The only trouble we saw with this approach was for the case without >>--multiple. This will require some modifications to the >>SingleCodeUnit class but Nicodemus said this should not be a big >>problem. Essentially before saving the SingleCodeUnit we'd need to >>order the methods correctly. >> >> > >I admit to not having a deep understanding of the issues here, but it >seems like you might solve some significant ordering problems by >parsing the XML and using pickle/shelve to create representations of >the classes that are quickly readable by Python, then making a >separate pass over these data structures. > >Just-a-random-thought-ly, > > It wouldn't necessarily solve the ordering problems, but it would certainly be much faster certainly. ;) We are considering this as an optimization (how about .pystec files? ;)). The ordering bug seems to be solved, Prabhu will test it more throughtly tonight. 8) Thanks for the hint, Nicodemus. From nicodemus at globalite.com.br Tue Jul 8 23:24:42 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Tue, 08 Jul 2003 18:24:42 -0300 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> <16139.7633.533988.44428@monster.linux.in> Message-ID: <3F0B369A.2000305@globalite.com.br> David Abrahams wrote: >Pyste is about providing >an even terser syntax for accomplishing the same things, and >'std::auto_ptr' is not only longer but it repeats information. >Also, how will that interface work when you have a class with virtual >functions that you want to be held by auto_ptr? > > I think we can provide functions for the most common smart pointers to be registered directly: hold_with_auto_ptr(A) # or perhaps: auto_ptr_holder(A)? hold_with_smart_ptr(A) And a more general purpose function for any other smart pointer: hold(A, 'my_smart_ptr') It does duplicate information, but very little in my opinion. From wilson at afn.org Wed Jul 9 00:07:20 2003 From: wilson at afn.org (Jim Wilson) Date: Tue, 08 Jul 2003 18:07:20 -0400 Subject: [C++-sig] Re: Pyste-generated extentsion Aborts Python In-Reply-To: <3F062CA0.6000706@globalite.com.br> References: <3F04C9A9.1070907@globalite.com.br> <3F04DAB9.6000906@globalite.com.br> <3F06096B.9080005@globalite.com.br> <3F062CA0.6000706@globalite.com.br> Message-ID: Nicodemus, I fetched your latest sources from CVS, and sure enough, no more boost error. I'm back to Python's "Abort". (More about that below.) Thanks for your prompt attention. You wrote: > Why the other functions didn't compile is still a mistery. Could you > post the signature of one of them, along with the generated code for > that function? Your wish is my command! (At least if I understand your wish. I think you wanted the declarations of the offending functions?) I have pared down the .h file to just the malicious functions (several of them pointers to nasty functions that take "..." as an argument!) and added necessary declarations from included files. The 50-line file at: http://www.afn.org/~wilson/fltk.h is silently digested by Pyste under the one-liner: http://www.afn.org/~wilson/fltk.pyste but Pyste's output: http://www.afn.org/~wilson/fltk.cpp hits the error jackpot in g++. Now, regarding the Python "Abort". I broke out gdb and discovered the abort happens while executing a wrapper-overridden virtual function (of an Fl_Window). I was able to get my demonstration program to run by simply excluding the virtual function! That's good news for my little demo; it's bad news for someone who might want to extend an Fl_Window subclass in Python. Now, Dave may be right. FLTK may be biting Python, and Python just bites back. Still, I think I would have seen a segfault or two out of FLTK when I "wrap" it in C++. Jim Wilson From dave at boost-consulting.com Wed Jul 9 01:29:46 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 08 Jul 2003 19:29:46 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> <16139.7633.533988.44428@monster.linux.in> <3F0B369A.2000305@globalite.com.br> Message-ID: Nicodemus writes: > David Abrahams wrote: > >>Pyste is about providing >>an even terser syntax for accomplishing the same things, and >>'std::auto_ptr' is not only longer but it repeats information. >>Also, how will that interface work when you have a class with virtual >>functions that you want to be held by auto_ptr? >> > > I think we can provide functions for the most common smart pointers to > be registered directly: > > hold_with_auto_ptr(A) # or perhaps: auto_ptr_holder(A)? > hold_with_smart_ptr(A) > > And a more general purpose function for any other smart pointer: > > hold(A, 'my_smart_ptr') > > It does duplicate information, but very little in my opinion. I think having two such syntaxes is unneccessary; new smart pointer varieties are sufficiently rare that the 2nd syntax isn't justified, and they're *used* sufficiently often that writing: def my_smart_ptr(name): return 'my_smart_ptr<%s>' % name is justified by the rest of the code that gets written... And furthermore, as I keep asking: ** What about classes with virtual functions?? ** Do you want to force the user to be knowledgeable about the name of the Pyste-generated callback class (they would have to write 'my_smart_ptr' or whatever it is)? Do you want to ask them to change their Pyste wrapping code just because they add a virtual function to their C++ code? -- Dave Abrahams Boost Consulting www.boost-consulting.com From prabhu at aero.iitm.ernet.in Wed Jul 9 05:36:27 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Wed, 9 Jul 2003 09:06:27 +0530 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> <16139.7633.533988.44428@monster.linux.in> <3F0B369A.2000305@globalite.com.br> Message-ID: <16139.36283.208984.454614@monster.linux.in> >>>>> "DA" == David Abrahams writes: DA> I think having two such syntaxes is unneccessary; new smart DA> pointer varieties are sufficiently rare that the 2nd syntax DA> isn't justified, and they're *used* sufficiently often that DA> writing: DA> def my_smart_ptr(name): DA> return 'my_smart_ptr<%s>' % name DA> is justified by the rest of the code that gets written... And DA> furthermore, as I keep asking: DA> ** What about classes with virtual functions?? ** DA> Do you want to force the user to be knowledgeable about the DA> name of the Pyste-generated callback class (they would have to DA> write 'my_smart_ptr' or whatever it is)? Do you DA> want to ask them to change their Pyste wrapping code just DA> because they add a virtual function to their C++ code? Calm down a bit please. You make a very valid point with virtual functions. Once the current major bug is fixed we'll definitely do something about it. If Nicodemus does not want to handle it I'll try and send a patch. Does the following sound OK then? holder(A, callable_or_string) If callable it calls the function at code-generation time and obtains the right HeldType, if it is a string we'll blindly use that. If you think there is no use for the case when the second argument is a string we'll drop that. The current implementation of the hold_with_auto_ptr functions is also broken and will not work for a class with virtual functions. I didn't realize that you needed to do this for virtual bases. My mistake. cheers, prabhu From dave at boost-consulting.com Wed Jul 9 07:38:49 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 09 Jul 2003 01:38:49 -0400 Subject: [C++-sig] Re: Allocating objects on the heap by default. References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> <16139.7633.533988.44428@monster.linux.in> <3F0B369A.2000305@globalite.com.br> <16139.36283.208984.454614@monster.linux.in> Message-ID: Prabhu Ramachandran writes: >>>>>> "DA" == David Abrahams writes: > > DA> I think having two such syntaxes is unneccessary; new smart > DA> pointer varieties are sufficiently rare that the 2nd syntax > DA> isn't justified, and they're *used* sufficiently often that > DA> writing: > > DA> def my_smart_ptr(name): > DA> return 'my_smart_ptr<%s>' % name > > DA> is justified by the rest of the code that gets written... And > DA> furthermore, as I keep asking: > > DA> ** What about classes with virtual functions?? ** > > DA> Do you want to force the user to be knowledgeable about the > DA> name of the Pyste-generated callback class (they would have to > DA> write 'my_smart_ptr' or whatever it is)? Do you > DA> want to ask them to change their Pyste wrapping code just > DA> because they add a virtual function to their C++ code? > > Calm down a bit please. Please don't patronize. If you ignore important points the first time I post them I don't think it's unreasonable to emphasize them the second time around. > You make a very valid point with virtual functions. Once the > current major bug is fixed we'll definitely do something about it. > If Nicodemus does not want to handle it I'll try and send a patch. > Does the following sound OK then? > > holder(A, callable_or_string) > > If callable it calls the function at code-generation time and obtains > the right HeldType, if it is a string we'll blindly use that. If you > think there is no use for the case when the second argument is a > string we'll drop that. I don't think it's useless, but I think it's silightly dangerous and needlessly TIMTOWTDI-ish. People will use it because it's slightly simpler to understand at first, but their code will be uglier and harder to maintain, and will break when they add a virtual function to the C++ class. It's better to supply one reliable mechanism than to supply options people don't need. -- Dave Abrahams Boost Consulting www.boost-consulting.com From prabhu at aero.iitm.ernet.in Wed Jul 9 08:14:23 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Wed, 9 Jul 2003 11:44:23 +0530 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> <16139.7633.533988.44428@monster.linux.in> <3F0B369A.2000305@globalite.com.br> <16139.36283.208984.454614@monster.linux.in> Message-ID: <16139.45759.532695.224817@monster.linux.in> >>>>> "DA" == David Abrahams writes: >> You make a very valid point with virtual functions. Once the >> current major bug is fixed we'll definitely do something about >> it. If Nicodemus does not want to handle it I'll try and send >> a patch. Does the following sound OK then? >> >> holder(A, callable_or_string) >> >> If callable it calls the function at code-generation time and >> obtains the right HeldType, if it is a string we'll blindly use >> that. If you think there is no use for the case when the >> second argument is a string we'll drop that. DA> I don't think it's useless, but I think it's silightly DA> dangerous and needlessly TIMTOWTDI-ish. People will use it DA> because it's slightly simpler to understand at first, but DA> their code will be uglier and harder to maintain, and will DA> break when they add a virtual function to the C++ class. It's DA> better to supply one reliable mechanism than to supply options DA> people don't need. Agreed, so we'll try and make it holder(A, callable). The callable will accept a single string representing the class or the wrapped class (if virtual). prabhu From prabhu at aero.iitm.ernet.in Wed Jul 9 09:47:17 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Wed, 9 Jul 2003 13:17:17 +0530 Subject: [C++-sig] Re: Pyste: problems with inheritance across headers. In-Reply-To: References: <16138.34639.379626.879015@monster.linux.in> <3F0AF5D6.2000207@globalite.com.br> <16139.7149.211713.215898@monster.linux.in> Message-ID: <16139.51333.372525.518236@monster.linux.in> >>>>> "DA" == David Abrahams writes: DA> Prabhu Ramachandran writes: >> The only trouble we saw with this approach was for the case >> without --multiple. This will require some modifications to >> the SingleCodeUnit class but Nicodemus said this should not be >> a big problem. Essentially before saving the SingleCodeUnit >> we'd need to order the methods correctly. DA> I admit to not having a deep understanding of the issues here, DA> but it seems like you might solve some significant ordering DA> problems by parsing the XML and using pickle/shelve to create DA> representations of the classes that are quickly readable by DA> Python, then making a separate pass over these data DA> structures. Thanks for the hint. We did think about this. We first thought that it was GCCXML that was taking much of the time to generate the XML. So we thought that if we cached the XML files we could generate the XML in separate steps and then use the generated XML files when generating the wrapper code. However subsequent timing tests by Nicodemus revealed that parsing the generated XML file takes as much time if not more than generating the XML file. So we thought of saving the parsed XML information into a picked file. However as a first attempt we went ahead with caching the XML files. It should be easy to move to using a pickled (.pystec) file once the other bugs are resolved. We did not think of using shelve. That is a good idea but we think we will have problems when trying to build the wrappers incrementally and will also have trouble with dependencies and build systems. Neither me nor Nicodemus are experts with build systems though, so clarifications from experts would help. Essentially, with the '.pystec' approach we will generate a file containing parsed information from the XML file, one for each header. With shelve we will have one shelf with all the pickles. When generating incremental compiles we thought that it would be better to have the pystec information in separate units in order to avoid dependency problems. To clarify, this is a contrived example specifically for the --multiple mode: file.pyste depends on header1.hpp, header2.hpp header{1,2}.hpp + file.pyste generates a header{1,2}.pystec file.pyste + header{1,2}.pystec generates _file.cpp + _main.cpp _file.cpp, _main.cpp generates the module. Generalize this to several pyste files and you'll see why we prefer .pystec's to one single shelf. If one of the interface files (.pyste) changes, the build system will need to update the shelf. The build system might even delete the shelf so we'll loose all the other information. From the perspective of dependencies it might be better to save one .pystec for each .pyste file. We might do that later on. Hmm, perhaps one shelf per .pyste file containing individual .pystec's. Anyway, things are still quite experimental and in flux. We hope that we end up with a decent solution though. I hope this is clear. If there is something incorrect here please let us know. Thanks. cheers, prabhu From domma at procoders.net Wed Jul 9 11:12:17 2003 From: domma at procoders.net (Achim Domma (ProCoders)) Date: Wed, 9 Jul 2003 11:12:17 +0200 Subject: [C++-sig] Compiling for 2.2 and 2.3 Message-ID: Hi, I have a project which takes some time to compile and want to provide windows binaries for python 2.2 and 2.3. Do I have to do a 'bjam -a' each time I change the python version, or is there a faster way? It's not clear to me, how much which part of boost.python depends on the python version. regards, Achim From pierre.barbier at cirad.fr Wed Jul 9 14:36:46 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Wed, 09 Jul 2003 14:36:46 +0200 Subject: [C++-sig] 'boost::STATIC_ASSERTION_FAILURE' problem ... Message-ID: <3F0C0C5E.5060506@cirad.fr> Hello, I have a type I want to export but without function nor initialisation. The line defining the type is : class_( "cell_descriptor", no_init ); This type is defined in an object defined in a library (the Boost Graph Library). Bur when I try to compile my module I have this error I don't understand : /home/barbier/apps/boost/boost/python/object/make_instance.hpp: In static member function `static PyObject* boost::python::objects::make_instance_impl::execute(Arg&) [with Arg = const boost::reference_wrapper, T = void*, Holder = boost::python::objects::value_holder, Derived = boost::python::objects::make_instance >]': /home/barbier/apps/boost/boost/python/object/class_wrapper.hpp:27: instantiated from `static PyObject* boost::python::objects::class_cref_wrapper::convert(const Src&) [with Src = void*, MakeInstance = boost::python::objects::make_instance >]' /home/barbier/apps/boost/boost/python/converter/as_to_python_function.hpp:28: instantiated from `static PyObject* boost::python::converter::as_to_python_function::convert(const void*) [with T = void*, ToPython = boost::python::objects::class_cref_wrapper > >]' /home/barbier/apps/boost/boost/python/to_python_converter.hpp:34: instantiated from `boost::python::to_python_converter::to_python_converter() [with T = void*, Conversion = boost::python::objects::class_cref_wrapper > >]' /home/barbier/apps/boost/boost/python/class.hpp:101: instantiated from `void boost::python::detail::register_class_to_python(boost::mpl::bool_, SelectHolder, T*) [with T = void*, SelectHolder = boost::python::objects::detail::select_value_holder]' /home/barbier/apps/boost/boost/python/class.hpp:577: instantiated from `void boost::python::class_::register_() const [with T = void*, X1 = boost::python::detail::not_specified, X2 = boost::python::detail::not_specified, X3 = boost::python::detail::not_specified]' /home/barbier/apps/boost/boost/python/class.hpp:605: instantiated from `boost::python::class_::class_(const char*, boost::python::no_init_t) [with T = void*, X1 = boost::python::detail::not_specified, X2 = boost::python::detail::not_specified, X3 = boost::python::detail::not_specified]' editor_python.cpp:255: instantiated from here /home/barbier/apps/boost/boost/python/object/make_instance.hpp:25: `sizeof' applied to incomplete type `boost::STATIC_ASSERTION_FAILURE' Any idea about what I need to do ? Thanks, -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From dave at boost-consulting.com Wed Jul 9 15:50:02 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 09 Jul 2003 09:50:02 -0400 Subject: [C++-sig] Re: 'boost::STATIC_ASSERTION_FAILURE' problem ... References: <3F0C0C5E.5060506@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > Hello, > > I have a type I want to export but without function nor > initialisation. The line defining the type is : > > class_( "cell_descriptor", no_init ); > > This type is defined in an object defined in a library (the Boost > Graph Library). > Bur when I try to compile my module I have this error I don't understand : > > /home/barbier/apps/boost/boost/python/object/make_instance.hpp:25: `sizeof' > applied to incomplete type `boost::STATIC_ASSERTION_FAILURE' Just look at the source line: BOOST_STATIC_ASSERT(is_class::value); The problem is that you're trying to export a non-class type with class_<...>. HTH, -- Dave Abrahams Boost Consulting www.boost-consulting.com From pierre.barbier at cirad.fr Wed Jul 9 16:01:38 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Wed, 09 Jul 2003 16:01:38 +0200 Subject: [C++-sig] Re: 'boost::STATIC_ASSERTION_FAILURE' problem ... In-Reply-To: References: <3F0C0C5E.5060506@cirad.fr> Message-ID: <3F0C2042.6000608@cirad.fr> David Abrahams wrote: >Pierre Barbier de Reuille writes: > > >>/home/barbier/apps/boost/boost/python/object/make_instance.hpp:25: `sizeof' >> applied to incomplete type `boost::STATIC_ASSERTION_FAILURE' >> >> > >Just look at the source line: > > BOOST_STATIC_ASSERT(is_class::value); > >The problem is that you're trying to export a non-class type with >class_<...>. > >HTH, > > Ok, I checked and it was indeed a non-class type. So how can I export this non-class type ? In practice, it's a void* ... Thansk, -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From dave at boost-consulting.com Wed Jul 9 17:00:03 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 09 Jul 2003 11:00:03 -0400 Subject: [C++-sig] Re: 'boost::STATIC_ASSERTION_FAILURE' problem ... References: <3F0C0C5E.5060506@cirad.fr> <3F0C2042.6000608@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > Ok, I checked and it was indeed a non-class type. So how can I export > this non-class type ? > In practice, it's a void* ... No easy way. I suggest either: a. exporting a struct which contains the void* or b. using the opaque_pointer_converter facilities to export some other pointer type and exposing thin wrappers over all functions which manipulate void* to translate between the exported type and void* -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Wed Jul 9 18:09:00 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Wed, 09 Jul 2003 13:09:00 -0300 Subject: [C++-sig] Re: Pyste: problems with inheritance across headers. In-Reply-To: <3F0B34CE.50109@globalite.com.br> References: <16138.34639.379626.879015@monster.linux.in> <3F0AF5D6.2000207@globalite.com.br> <16139.7149.211713.215898@monster.linux.in> <3F0B34CE.50109@globalite.com.br> Message-ID: <3F0C3E1C.2090906@globalite.com.br> Nicodemus wrote: > David Abrahams wrote: > >> I admit to not having a deep understanding of the issues here, but it >> seems like you might solve some significant ordering problems by >> parsing the XML and using pickle/shelve to create representations of >> the classes that are quickly readable by Python, then making a >> separate pass over these data structures. >> >> Just-a-random-thought-ly, > > It wouldn't necessarily solve the ordering problems, but it would > certainly be much faster certainly. ;) Sorry, I missed your suggestion about shelve (I read just "pickle" ). That is a great idea. All the problem with ordering is that we can't keep all the declarations in memory at the same time, issue that shelve would adress nicely! Since the solution that Prabhu and I has some problems, I think I will use shelve to handle the declarations. Thanks Dave! Nicodemus. From nicodemus at globalite.com.br Wed Jul 9 18:12:58 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Wed, 09 Jul 2003 13:12:58 -0300 Subject: [C++-sig] Re: Allocating objects on the heap by default. In-Reply-To: References: <16134.19331.719492.865019@monster.linux.in> <16135.37339.318448.715944@monster.linux.in> <16137.54727.970073.487393@monster.linux.in> <3F09E817.3050204@globalite.com.br> <16138.13326.952123.635272@monster.linux.in> <16139.7633.533988.44428@monster.linux.in> <3F0B369A.2000305@globalite.com.br> Message-ID: <3F0C3F0A.9050408@globalite.com.br> David Abrahams wrote: >Nicodemus writes: > > > >>David Abrahams wrote: >> >> >> >>>Pyste is about providing >>>an even terser syntax for accomplishing the same things, and >>>'std::auto_ptr' is not only longer but it repeats information. >>>Also, how will that interface work when you have a class with virtual >>>functions that you want to be held by auto_ptr? >>> >>> >>> >>I think we can provide functions for the most common smart pointers to >>be registered directly: >> >>hold_with_auto_ptr(A) # or perhaps: auto_ptr_holder(A)? >>hold_with_smart_ptr(A) >> >>And a more general purpose function for any other smart pointer: >> >>hold(A, 'my_smart_ptr') >> >>It does duplicate information, but very little in my opinion. >> >> > >I think having two such syntaxes is unneccessary; new smart pointer >varieties are sufficiently rare that the 2nd syntax isn't justified, >and they're *used* sufficiently often that writing: > > def my_smart_ptr(name): > return 'my_smart_ptr<%s>' % name > >is justified by the rest of the code that gets written... And >furthermore, as I keep asking: > > ** What about classes with virtual functions?? ** > >Do you want to force the user to be knowledgeable about the name of >the Pyste-generated callback class (they would have to write >'my_smart_ptr' or whatever it is)? Do you want to ask >them to change their Pyste wrapping code just because they add a >virtual function to their C++ code? > Sorry, I missed this point of yours. You are right, a more dynamic approach is needed. Even thought the callable solution is a little verbose, its use will be less frequent, and it is worth the flexibility. Regards, Nicodemus. From Gottfried.Ganssauge at HAUFE.DE Wed Jul 9 19:23:48 2003 From: Gottfried.Ganssauge at HAUFE.DE (Gottfried.Ganssauge at HAUFE.DE) Date: Wed, 9 Jul 2003 19:23:48 +0200 Subject: [C++-sig] Wrapper for exception translation Message-ID: <2040C0A1CA23D51181A30050BAAC990274AAB1@berexch.ber.haufemg.com> Hi everyone, for my current project I was in need for a simple method to make user defined exceptions within my module. The basic framework in the form of exception translation is there so I only needed to make it a bit more accessible. I made a template function exception_ (const char *name) which creates a python exception and an instance of templated translation handler. The translation handler instance is held in the python translation's class dictionary as the __handler__ attribute. Then the handler is registered as an exception translator for the Exception using register_exception_translator(). The python exception object is finally registered in the current scope's dictionary using the "name" argument to exception_(). To register an exception translator for exception e you simply call exception_ ("e") within your module init function. This implementation is quite usable for me but I would be totally glad if it could somehow be integrated with pyste. I tested it with gcc-3.2, gcc-3.3 and gcc-2.95 Cheers, Gottfried -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: except.cpp Type: application/octet-stream Size: 767 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: except.h Type: application/octet-stream Size: 4096 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: test_exc.py Type: application/octet-stream Size: 387 bytes Desc: not available URL: From dave at boost-consulting.com Wed Jul 9 19:47:31 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 09 Jul 2003 13:47:31 -0400 Subject: [C++-sig] Re: Pyste: problems with inheritance across headers. References: <16138.34639.379626.879015@monster.linux.in> <3F0AF5D6.2000207@globalite.com.br> <16139.7149.211713.215898@monster.linux.in> <3F0B34CE.50109@globalite.com.br> <3F0C3E1C.2090906@globalite.com.br> Message-ID: Nicodemus writes: > Nicodemus wrote: > >> David Abrahams wrote: >> >>> I admit to not having a deep understanding of the issues here, but it >>> seems like you might solve some significant ordering problems by >>> parsing the XML and using pickle/shelve to create representations of >>> the classes that are quickly readable by Python, then making a >>> separate pass over these data structures. >>> >>> Just-a-random-thought-ly, >> >> It wouldn't necessarily solve the ordering problems, but it would >> certainly be much faster certainly. ;) > > > Sorry, I missed your suggestion about shelve (I read just "pickle" ). > > That is a great idea. All the problem with ordering is that we can't > keep all the declarations in memory at the same time, issue that > shelve would adress nicely! Since the solution that Prabhu and I has > some problems, I think I will use shelve to handle the declarations. Again hoping for a lucky shot-in-the-dark, you might look at the general architecture used by Synopsis. It's basically like a compiler/linker: you process all the header files into some intermediate format and then they get "linked" together. An approach like that might make it easy to avoid re-"compiling". HTH, -- Dave Abrahams Boost Consulting www.boost-consulting.com From prabhu at aero.iitm.ernet.in Wed Jul 9 20:09:02 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Wed, 9 Jul 2003 23:39:02 +0530 Subject: [C++-sig] Re: Pyste: problems with inheritance across headers. In-Reply-To: References: <16138.34639.379626.879015@monster.linux.in> <3F0AF5D6.2000207@globalite.com.br> <16139.7149.211713.215898@monster.linux.in> <3F0B34CE.50109@globalite.com.br> <3F0C3E1C.2090906@globalite.com.br> Message-ID: <16140.23102.281793.652052@monster.linux.in> >>>>> "DA" == David Abrahams writes: DA> Again hoping for a lucky shot-in-the-dark, you might look at DA> the general architecture used by Synopsis. It's basically DA> like a compiler/linker: you process all the header files into DA> some intermediate format and then they get "linked" together. DA> An approach like that might make it easy to avoid DA> re-"compiling". Interesting, this is pretty much what we came up with too. Except that we decided to save the precompiled pystec files separately rather than individually. We don't yet know how well it will work out but we'll should know soon. Thanks for the hints and support! cheers, prabhu From dleary at ttlc.net Wed Jul 9 23:54:27 2003 From: dleary at ttlc.net (Dusty Leary) Date: Wed, 9 Jul 2003 17:54:27 -0400 Subject: [C++-sig] smart pointers, polymorphism Message-ID: <000501c34664$ab0dfb40$4d00a8c0@eigensoft.net> Hello, I am converting a semi-large api over to boost.python. We have been using boost::intrusive_ptr for some time now. (I can't remember exactly why). I tried switching before mailing the list. With both intrusive_ptr and shared_ptr, I am running into "conversion to base" problems. I have quite a few abstract interfaces. Each one defines an overloaded templated static "cast" function, to make it easy to cast references. (e.g. foo::bar::MyInterface::cast(someReference)), which handles using dynamic_cast or boost::shared_dynamic_cast, etc... With my previous home-grown python interfaces (stubs generated from an idl), the binding for the cast function would just extract the anonymous pointer from the PyObject (after verifying that the PyObject's type was one of our interfaces), static_cast it to IObject* (even though it might not implement IObject), then dynamic_cast it to the interface type (in this case, foo::bar::MyInterface). I am not sure if static_casting it to some possibly unrelated polymorphic type, and then dynamic_casting it to our type is valid. (Although I was sure it would always be a polymorphic type). It worked, at least for my current environment. Anyway, I can't get the casting to work properly. I am always getting "TypeError: bad argument for built-in operation."... presumably, boost.python can't find a valid overload. I have tried forcing all interfaces in the system to extend a common base interface (IObject), with no luck. (so, I define "static shared_ptr cast_iobject(IObject*)" in each interface class. Even though I have "IFoo : public IObject", a shared_ptr can't be passed into my cast function) Either, I need to special case this function, accepting PyObjects directly and doing the static_cast -> dynamic_cast thing like I did in my previous bindings, or I need to somehow make the compiler and/or boost.python infer the proper behaviour. With all of the boost::python::(converter, holder, pointee) stuff, that might be possible, but I can't make heads or tails of it. What is the proper way? From dave at boost-consulting.com Thu Jul 10 00:09:01 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 09 Jul 2003 18:09:01 -0400 Subject: [C++-sig] Re: smart pointers, polymorphism References: <000501c34664$ab0dfb40$4d00a8c0@eigensoft.net> Message-ID: Can you post a small, compilable example which illustrates your problem, along with Python test code? "Dusty Leary" writes: > Hello, > > I am converting a semi-large api over to boost.python. > > We have been using boost::intrusive_ptr for some time now. (I can't > remember exactly why). I tried switching before mailing the list. With > both intrusive_ptr and shared_ptr, I am running into "conversion to base" > problems. > > I have quite a few abstract interfaces. Each one defines an overloaded > templated static "cast" function, to make it easy to cast references. (e.g. > foo::bar::MyInterface::cast(someReference)), which handles using > dynamic_cast or boost::shared_dynamic_cast, etc... > > With my previous home-grown python interfaces (stubs generated from an idl), > the binding for the cast function would just extract the anonymous pointer > from the PyObject (after verifying that the PyObject's type was one of our > interfaces), static_cast it to IObject* (even though it might not implement > IObject), then dynamic_cast it to the interface type (in this case, > foo::bar::MyInterface). > > I am not sure if static_casting it to some possibly unrelated polymorphic > type, and then dynamic_casting it to our type is valid. (Although I was > sure it would always be a polymorphic type). It worked, at least for my > current environment. > > Anyway, I can't get the casting to work properly. > I am always getting "TypeError: bad argument for built-in operation."... > presumably, boost.python can't find a valid overload. > > I have tried forcing all interfaces in the system to extend a common base > interface (IObject), with no luck. (so, I define "static shared_ptr > cast_iobject(IObject*)" in each interface class. Even though I have "IFoo : > public IObject", a shared_ptr can't be passed into my cast function) > > Either, I need to special case this function, accepting PyObjects directly > and doing the static_cast -> dynamic_cast thing like I did in my previous > bindings, or I need to somehow make the compiler and/or boost.python infer > the proper behaviour. With all of the boost::python::(converter, holder, > pointee) stuff, that might be possible, but I can't make heads or tails of > it. > > What is the proper way? -- Dave Abrahams Boost Consulting www.boost-consulting.com From pierre.barbier at cirad.fr Thu Jul 10 11:29:53 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Thu, 10 Jul 2003 11:29:53 +0200 Subject: [C++-sig] Call policies for unreferencing iterator ... Message-ID: <3F0D3211.50002@cirad.fr> Hello, I'm writing some templates to automate export of stl stuffs (at least some of the stuffs). I hope I'll soon be able to share my work to know what you'll think of it. But before that I have a question about the iterators. I want to export the STL iterators using a STL-like interface (I've already done some work about exporting interators with python interface). My concern is : I defined the __call__ method as the operator* of the iterator. But I want to return a reference to the object (to be able to modify it if the iterator if mutable). The problem is with the call policies ! It's not an internal reference, because the reference will still be valid after the iterator is destroyed, and it's a bad idea to create it as an "existing object" for it will crash if the user try to use the pointer after the container is deleted. My problem is I don't know how to tie the lifetime of the object with the container ... and I don't even think it's possible to do that. What would you do ? I hope I'm clear enough ... Thanks, -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From Gottfried.Ganssauge at HAUFE.DE Thu Jul 10 11:44:22 2003 From: Gottfried.Ganssauge at HAUFE.DE (Gottfried.Ganssauge at HAUFE.DE) Date: Thu, 10 Jul 2003 11:44:22 +0200 Subject: [C++-sig] Patches for pyste regarding exception specifications Message-ID: <2040C0A1CA23D51181A30050BAAC990274AAB4@berexch.ber.haufemg.com> Hi everyone, I made a set of patches for pyste which allows pyste to keep exception specifications in automatically generated wrappers for classes with virtual functions. This obviously needs support from gccxml so this only works with the CVS version of gccxml. Older versions of gccxml don't generate the necessary information for this to work but in this case the code just isn't used. Furthermore this introduces a new Wrapper-Function: Exception(), which generates a call to my exception handling facility posted yesterday. Finally two minor coding errors in the wrapping of free functions are fixed which affected my project. Please see the attachment. The patches are relative to the pyste subdirectory within boost/libs/python and cover only the src subdirectory. Cheers, Gottfried -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: gg.patch Type: application/octet-stream Size: 10768 bytes Desc: not available URL: From dave at boost-consulting.com Thu Jul 10 13:19:13 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 10 Jul 2003 07:19:13 -0400 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AAB1@berexch.ber.haufemg.com> Message-ID: Gottfried.Ganssauge at HAUFE.DE writes: > for my current project I was in need for a simple method to make user > defined exceptions within my module. > The basic framework in the form of exception translation is there so I only > needed to make it a bit more accessible. > I made a template function exception_ (const char *name) which > creates a python exception and an instance of templated translation handler. > The translation handler instance is held in the python translation's class > dictionary as the __handler__ attribute. > Then the handler is registered as an exception translator for the Exception > using register_exception_translator(). > The python exception object is finally registered in the current scope's > dictionary using the "name" argument to exception_(). > > To register an exception translator for exception e you simply call > exception_ ("e") within your module init function. > > This implementation is quite usable for me but I would be totally glad if it > could somehow be integrated with pyste. This looks like a question about integration with Boost.Python itself to me. Isn't it? Could you explain how your facility improves on what's already in the library? I'm sorry to be dense, but the answer's not jumping out at me. -- Dave Abrahams Boost Consulting www.boost-consulting.com From Gottfried.Ganssauge at HAUFE.DE Thu Jul 10 13:59:07 2003 From: Gottfried.Ganssauge at HAUFE.DE (Gottfried.Ganssauge at HAUFE.DE) Date: Thu, 10 Jul 2003 13:59:07 +0200 Subject: [C++-sig] Re: Wrapper for exception translation Message-ID: <2040C0A1CA23D51181A30050BAAC990274AAB9@berexch.ber.haufemg.com> ... > > This looks like a question about integration with Boost.Python > itself to me. Isn't it? You're right, of course What I meant to say was: - I would be delighted to have this facility integrated with the library - I would be even more delighted if it was usable through some pyste enhancement > > Could you explain how your facility improves on what's already in the > library? I'm sorry to be dense, but the answer's not jumping out at > me. Currently, in order to wrap user defined exceptions you need to - allocate a python exception using PyErr_NewException This function needs to be parametrized using a specific naming convention you also need to find a place where this exception instance lives and is accessible to the exception translator - define an exception translator which signals the exception defined above - register the exception translator with the library My facility allows to do this with only one function call "exception_ (name)" within the module init function. It will allocate a python exception and store it within an instance of the translated_exception_handler<> class. The name for that exception is taken from the name parameter and the current scope according to the naming convention documented in the manual page for PyErr_NewException. A reference to the translated_exception_handler is stored within the class dictionary of the newly allocated python exception in order to keep the translator alive. The translated_exception_handler provides the exception translator to be registered with the library. It uses a generic method to obtain an exception description by calling a function get_exception_description<>() which has a default implementation in the detail namespace. Finally the python exception itself is made available in the module's namespace under the name given. get_exception_description<>() currently returns a const char * which is passed to PyErr_SetString(). It might be worthwile to make it return an object which then could be passed to PyErr_SetObject(). This modification would make it possible to pass an instance of a class which wraps the exception caught, which again would make the exception instance itself available to python programs. Another enhancement could be the generation of derived python exceptions, an area in which I have no experience yet. This could be by an additional template parameter to the exception_<>() function which defaults to the allocation with PyErr_NewException(). What do you think? > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com Cheers, Gottfried -------------- next part -------------- An HTML attachment was scrubbed... URL: From dave at boost-consulting.com Thu Jul 10 15:27:20 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 10 Jul 2003 09:27:20 -0400 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AAB9@berexch.ber.haufemg.com> Message-ID: Gottfried.Ganssauge at HAUFE.DE writes: > Currently, in order to wrap user defined exceptions you need to > > - allocate a python exception using PyErr_NewException Well, no. I don't see any call to PyErr_NewException in libs/python/test/exception_translator.cpp > This function needs to be parametrized using a specific naming > convention It's not clear to me what you're referring to. Are you sure you mean "naming convention"? > you also need to find a place where this exception instance lives > and is accessible to the exception translator I don't know what you mean here. For one thing, first "this" is a function and now "this" is an exception instance. > - define an exception translator which signals the exception defined > above What do you mean by "define an exception translator"? What do you mean by "signals the exception"? > - register the exception translator with the library This I understand to mean something like: register_exception_translator(&translate); > My facility allows to do this with only one function call > "exception_ (name)" within the module init function. > It will allocate a python exception Do you mean it will create a Python subclass of Exception? Or is it something else? I guess the docs for PyErr_NewException are a little unclear on this point, but I think it's what I said. > and store it within an instance of the > translated_exception_handler<> class. The name for that exception is > taken from the name parameter and the current scope according to the > naming convention documented in the manual page for > PyErr_NewException. Hmm, I didn't know about PyErr_NewException, but it looks useful. > A reference to the translated_exception_handler is stored within the > class dictionary of the newly allocated python exception in order to > keep the translator alive. The translated_exception_handler > provides the exception translator to be registered with the > library. OK, OK, wait. I was beginning to like where this was going, (I like what you're accomplishing) but this all sounds *way* too complex for that purpose. Especially the "creation of an anonymous class" that you do in the code here looks like a messy hack likely to break at some point. Why is such a complicated mechanism needed? > It uses a generic method to obtain an exception description > by calling a function get_exception_description<>() which has a > default implementation in the detail namespace. Finally the python > exception itself is made available in the module's namespace under > the name given. > > get_exception_description<>() currently returns a const char * which > is passed to PyErr_SetString(). It might be worthwile to make it > return an object which then could be passed to > PyErr_SetObject(). This modification would make it possible to pass > an instance of a class which wraps the exception caught, which again > would make the exception instance itself available to python > programs. > > Another enhancement could be the generation of derived python > exceptions, an area in which I have no experience yet. This could be > by an additional template parameter to the exception_<>() function > which defaults to the allocation with PyErr_NewException(). > > What do you think? I think I understand this much: your code provides the ability to easily define new Python exception types corresponding to particular C++ exception types. Bravo to that; I'd like to get this capability into the library. I do think the implementation is needlessly convoluted. Just by inspection it looks to me like you make heavy use of a dictionary // class dictionary for the new exception class dict d; which later simply goes out of scope. What's the point of that? Have I missed something? -- Dave Abrahams Boost Consulting www.boost-consulting.com From Gottfried.Ganssauge at HAUFE.DE Thu Jul 10 16:45:30 2003 From: Gottfried.Ganssauge at HAUFE.DE (Gottfried.Ganssauge at HAUFE.DE) Date: Thu, 10 Jul 2003 16:45:30 +0200 Subject: [C++-sig] Re: Wrapper for exception translation Message-ID: <2040C0A1CA23D51181A30050BAAC990274AABB@berexch.ber.haufemg.com> ... > > > Currently, in order to wrap user defined exceptions you need to > > > > - allocate a python exception using PyErr_NewException > > Well, no. I don't see any call to PyErr_NewException in > libs/python/test/exception_translator.cpp Right, you don't need to if you are content with RuntimeError exceptions. My objective was another one: I wanted to create module exceptions that are derived from the python "Exception" class. > > > This function needs to be parametrized using a specific naming > > convention > > It's not clear to me what you're referring to. Are you sure you mean > "naming convention"? Yes. From nicodemus at globalite.com.br Thu Jul 10 16:50:50 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 10 Jul 2003 11:50:50 -0300 Subject: [C++-sig] Patches for pyste regarding exception specifications In-Reply-To: <2040C0A1CA23D51181A30050BAAC990274AAB4@berexch.ber.haufemg.com> References: <2040C0A1CA23D51181A30050BAAC990274AAB4@berexch.ber.haufemg.com> Message-ID: <3F0D7D4A.4040701@globalite.com.br> Gottfried.Ganssauge at HAUFE.DE wrote: > Hi everyone, > > I made a set of patches for pyste which allows pyste to keep exception > specifications in automatically generated wrappers for classes with > virtual functions. > > This obviously needs support from gccxml so this only works with the > CVS version of gccxml. > Older versions of gccxml don't generate the necessary information for > this to work but in this case the code just isn't used. > > Furthermore this introduces a new Wrapper-Function: Exception(), which > generates a call to my exception handling facility posted yesterday. > > Finally two minor coding errors in the wrapping of free functions are > fixed which affected my project. > > Please see the attachment. > The patches are relative to the pyste subdirectory within > boost/libs/python and cover only the src subdirectory. > > Cheers, > > Gottfried > Thanks a lot Gottfried, your patch looks very clean! I will commit it as soon as Prabhu and I have fixed the "Order Bug". Just one thing I didn't understand, could you explain this change? - def SetCurrent(self, current): + def SetCurrent(self, current, missing = None): + if missing is not None: + pass + Thanks again! Nicodemus. From Gottfried.Ganssauge at HAUFE.DE Thu Jul 10 17:10:23 2003 From: Gottfried.Ganssauge at HAUFE.DE (Gottfried.Ganssauge at HAUFE.DE) Date: Thu, 10 Jul 2003 17:10:23 +0200 Subject: [C++-sig] Patches for pyste regarding exception specification s Message-ID: <2040C0A1CA23D51181A30050BAAC990274AABD@berexch.ber.haufemg.com> ... > Thanks a lot Gottfried, your patch looks very clean! I will > commit it as > soon as Prabhu and I have fixed the "Order Bug". Good luck! > > Just one thing I didn't understand, could you explain this change? > > - def SetCurrent(self, current): > + def SetCurrent(self, current, missing = None): > + if missing is not None: > + pass > + This is one of the "fixes" I mentioned in my post. Originally I planned to print a message or throw an exception when missing wouldn't be None because I didn't know what to make of that parameter. Without it I got a 'wrong number of parameters' exception but I somehow got distracted and forgot about it when I came back and didn't get any more of those exceptions. I guess that this parameter should really be called "unused" because it needs to be there only for compatibility to MultipleCodeUnit.SetCurrent(), right? > > Thanks again! my pleasure > Nicodemus. Cheers, Gottfried -------------- next part -------------- An HTML attachment was scrubbed... URL: From dave at boost-consulting.com Thu Jul 10 19:13:30 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 10 Jul 2003 13:13:30 -0400 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AABB@berexch.ber.haufemg.com> Message-ID: Gottfried.Ganssauge at HAUFE.DE writes: > ... >> >> > Currently, in order to wrap user defined exceptions you need to >> > >> > - allocate a python exception using PyErr_NewException >> >> Well, no. I don't see any call to PyErr_NewException in >> libs/python/test/exception_translator.cpp > > Right, you don't need to if you are content with RuntimeError > exceptions. or any other pre-packaged exception type provided by Python. > My objective was another one: I wanted to create module exceptions > that are derived from the python "Exception" class. >> >> > This function needs to be parametrized using a specific naming >> > convention >> >> It's not clear to me what you're referring to. Are you sure you mean >> "naming convention"? > Yes. > From the documentation to PyErr_NewException: > > ... The __module__ attribute of the new class is set to the first part > (up to the last dot) of the name argument, and the class name is set to > the last part (after the last dot). ...yeah, that's a naming convention, but I don't see how that affects the parameterization of any function. >> > you also need to find a place where this exception instance lives >> > and is accessible to the exception translator >> >> I don't know what you mean here. For one thing, first "this" is a >> function and now "this" is an exception instance. > "this function" meant PyErr_NewException which creates a new exception > instance. > > The exception instance (from now on called "e") created by > PyErr_NewException needs to live somewhere because in order to > signal a python exception you must hand e to > PyErr_SetString/PyErr_SetObject. OK, I understand that. For the record, Python exceptions are "raised", not "signalled". >> > - define an exception translator which signals the exception >> > defined above >> >> What do you mean by "define an exception translator"? > A translation function in the sense of register_exception_translator. OK. >> What do you mean by "signals the exception"? > > Calling PyErr_SetString/PyErr_SetObject. OK. >> > A reference to the translated_exception_handler is stored within >> > the class dictionary of the newly allocated python exception in >> > order to keep the translator alive. The >> > translated_exception_handler provides the exception translator to >> > be registered with the library. >> >> OK, OK, wait. I was beginning to like where this was going, (I like >> what you're accomplishing) but this all sounds *way* too complex for >> that purpose. Especially the "creation of an anonymous class" that >> you do in the code here looks like a messy hack likely to break at >> some point. Why is such a complicated mechanism needed? > > You're probably right. > > What I wanted to achieve was the following: > Create an instance of a translated_exception_handler<> t which will be > registered with the library by calling > register_exception_translator<>(). Sorry to be difficult, but I'm going to contradict you. You didn't want any of that. What you wanted was to create a new Python exception type in the module which would correspond to a particular C++ exception type and would be raised at the boundary with Python whenever a wrapped function threw the C++ exception. Right? > Normally t would be destructed by the end of exception_<>() thereby > leaving a registration to a non-existing translator - very bad > karma. I don't understand any of this. All you have to pass to register_exception_translator is a function pointer, and functions live forever. So where's the lifetime issue? > Because I didn't like to have an additional container for all > translated_exception_handler<> instances, I chose to store t within > e's class dictionary. At that moment it seemed to be the easiest > way to create a wrapper class using class_<> instead of making a > true python class by hand (and it even works!). You are right, it > is way too complex, I will change it to the mechanism I used in > opaque_pointer_converter. I don't know what that is, but before you consider doing something which is again too complex, please consider: template struct translate_exception { static char const* msg; static object python_exception_type; static void handler(E const&) { PyErr_SetString(python_exception_type.ptr(), msg.c_str()); }; translate_exception(char const* python_exception_name, char const* msg_) { // need fancier name manipulation here python_exception_type = object( handle<>(PyErr_NewException(name))); msg = msg_; register_exception_translator(handler); } }; Simple. >> > It uses a generic method to obtain an exception description >> > by calling a function get_exception_description<>() which has a >> > default implementation in the detail namespace. Finally the python >> > exception itself is made available in the module's namespace under >> > the name given. >> > >> > get_exception_description<>() currently returns a const char * which >> > is passed to PyErr_SetString(). It might be worthwile to make it >> > return an object which then could be passed to >> > PyErr_SetObject(). This modification would make it possible to pass >> > an instance of a class which wraps the exception caught, which again >> > would make the exception instance itself available to python >> > programs. >> > >> > Another enhancement could be the generation of derived python >> > exceptions, an area in which I have no experience yet. This could be >> > by an additional template parameter to the exception_<>() function >> > which defaults to the allocation with PyErr_NewException(). >> > >> > What do you think? >> >> I think I understand this much: >> >> your code provides the ability to easily define new Python >> exception types corresponding to particular C++ exception types. >> >> Bravo to that; I'd like to get this capability into the library. >> >> I do think the implementation is needlessly convoluted. Just by >> inspection it looks to me like you make heavy use of a dictionary >> >> // class dictionary for the new exception class >> dict d; >> >> which later simply goes out of scope. What's the point of that? >> Have I missed something? > It doesn't simply go out of scope. Before going out of scope it is passed to > PyErr_NewException as the new exception's class dictionary. Ah, yes, I see it now. I did miss that, sorry. > Ok then, > > I'll make a redesign ... > Thnx for your feedback. Cool! Looking forward to it. -- Dave Abrahams Boost Consulting www.boost-consulting.com From RaoulGough at yahoo.co.uk Thu Jul 10 19:42:45 2003 From: RaoulGough at yahoo.co.uk (Raoul Gough) Date: Thu, 10 Jul 2003 18:42:45 +0100 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" Message-ID: A while ago, David Abrahams wrote: >There are a few places where error reporting in Boost.Python depends >on being able to show users a reasonable representation of a C++ type >name. Currently, we use typeid(x).name() to get the name. Most >compilers produce a good result, however g++ does not. I just ran a >small experiment to see if the type encoding scheme used by G++ could >easily be deciphered, and it appears that it can. If we want to >improve error reporting with G++, it should be relatively easy. I seem to recall that the g++ typeid().name() gives you the type's mangled name, in which case the supplied c++filt will decode it for you (maybe modulo one leading underscore?). If so, I think a simple system() call would probably suffice for what David is describing. Or am I missing some more info on the difficulties involved? The source to the demangler is GPL'd, of course (in gcc/libiberty/cp-demangle.c) and is also including in gdb, AFAIK. It's currently >3000 lines of code, so I wouldn't recommend trying to reimplement it for Boost.Python! -- Raoul Gough "Let there be one measure for wine throughout our kingdom, and one measure for ale, and one measure for corn" - Magna Carta From dave at boost-consulting.com Thu Jul 10 23:18:58 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 10 Jul 2003 17:18:58 -0400 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: Message-ID: Raoul Gough writes: > A while ago, David Abrahams wrote: > >>There are a few places where error reporting in Boost.Python depends >>on being able to show users a reasonable representation of a C++ type >>name. Currently, we use typeid(x).name() to get the name. Most >>compilers produce a good result, however g++ does not. I just ran a >>small experiment to see if the type encoding scheme used by G++ could >>easily be deciphered, and it appears that it can. If we want to >>improve error reporting with G++, it should be relatively easy. > > I seem to recall that the g++ typeid().name() gives you the type's > mangled name, in which case the supplied c++filt will decode it for > you (maybe modulo one leading underscore?). If so, I think a simple > system() call would probably suffice for what David is describing. Or > am I missing some more info on the difficulties involved? > > The source to the demangler is GPL'd, of course (in > gcc/libiberty/cp-demangle.c) and is also including in gdb, AFAIK. It's > currently >3000 lines of code, so I wouldn't recommend trying to It's even easier than that; GCC supplies a library with a function you can call to demangle these names. I've forgotten the name, of course :( -- Dave Abrahams Boost Consulting www.boost-consulting.com From rwgk at yahoo.com Fri Jul 11 00:10:00 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Thu, 10 Jul 2003 15:10:00 -0700 (PDT) Subject: [C++-sig] method injector and pickling Message-ID: <20030710221000.15487.qmail@web20209.mail.yahoo.com> I ran into pickle problems when converting some of the classes in our application to make use of David's method injector (as explained in tutorial/doc/quickstart.txt). The problems disappeared when I added the if statement below to disable injection of __module__ and __file__. Proactively I added __init__ and __del__ to the list. Is this a useful modification? Should we update quickstart.txt accordingly? Ralf from scitbx.array_family import flex # see boost/libs/python/doc/tutorial/doc/quickstart.txt boost_python_metaclass = flex.double.__class__ class injector(object): class __metaclass__(boost_python_metaclass): def __init__(self, name, bases, dict): for b in bases: if type(b) not in (self, type): for k,v in dict.items(): if (k in ("__init__", "__del__", "__module__", "__file__")): continue setattr(b,k,v) return type.__init__(self, name, bases, dict) __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From brett.calcott at paradise.net.nz Fri Jul 11 07:11:51 2003 From: brett.calcott at paradise.net.nz (Brett Calcott) Date: Fri, 11 Jul 2003 15:11:51 +1000 Subject: [C++-sig] Explaining the Magic Message-ID: Hi David, I am in Aussie now, and though still homeless, I at least have an office. I thought we could make a start on our plans to document some of the boost python implementation. I brushed up on reStructuredText so, as discussed I'll try and construct a document from our conversations. As suggested I have had a look at the luabind conversation, and though I understand bits here and there I need something to tie it all too. Here's two starting questions: 1) What happens when you do the following: struct boring {}; ...etc... class_("boring") ; There seems to be a fair bit going on. - Python needs a new ClassType to be registered. - We need to construct a new type that can hold our boring struct. - Inward and outward converters need to be registered for the type. Can you gesture in the general direction where these things are done. 2) Can you give a brief overview of the data structures that are present in the registry and an overview of the process that happens as a type makes its way from c++ to python and back again. In both of these cases, I'm quite capable of reading code - but the thing I don't get from scanning the source is a sense of the architecture, both structurally, and temporally (er, I mean in what order things go on). Cheers, Brett (Kiwi in Oz) ps. Take your time to answer these -- I am trying to write a paper, and get some foundation boost_python simulation framework written, so I am happy if we progress slowly... From dleary at ttlc.net Fri Jul 11 07:49:25 2003 From: dleary at ttlc.net (Dusty Leary) Date: Fri, 11 Jul 2003 01:49:25 -0400 Subject: [C++-sig] smart pointers, polymorphism References: Message-ID: <000701c34770$2fdb5b40$c82aa8c0@dust2k> Hello, Say I have an abstract base class A, an implementation class B, and a function, void foo(A* a); If I do a normal boost::python binding, then I can call foo (from python) with instances of B... (at least, I think I can?). The problem I am having is that we are using boost::intrusive_ptr all over our project already. (We could change this perhaps, but that's the way it is now). When I expose my classes to boost, it looks like: class_ >("A").....; class_ >("B").....; In this case, when I have an python object which wraps an instance of B, I can't call my foo(A*); function. How can I make it so that the "polymorphic search" succeeds, in matching intrusive_ptr against A* parameters? From prabhu at aero.iitm.ernet.in Fri Jul 11 08:37:22 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Fri, 11 Jul 2003 12:07:22 +0530 Subject: [C++-sig] smart pointers, polymorphism In-Reply-To: <000701c34770$2fdb5b40$c82aa8c0@dust2k> References: <000701c34770$2fdb5b40$c82aa8c0@dust2k> Message-ID: <16142.23330.544176.758264@monster.linux.in> >>>>> "DL" == Dusty Leary writes: [snip] DL> class_ >("A").....; class_ boost::intrusive_ptr >("B").....; DL> How can I make it so that the "polymorphic search" succeeds, DL> in matching intrusive_ptr against A* parameters? AFAIK, class_, boost::intrusive_ptr >("B").....; should do the trick. But note that if you want to subclass these in Python and have your C++ code use the overriden virtual functions from Python you'll need to create a wrapper for the classes as described here: http://www.boost.org/libs/python/doc/tutorial/doc/class_virtual_functions.html The intrusive_ptr should be handled automatically by Boost.Python. Look here: http://www.boost.org/libs/python/doc/v2/class.html#class_-spec for more details. HTH, prabhu From hupp at cs.wisc.edu Fri Jul 11 09:27:35 2003 From: hupp at cs.wisc.edu (Adam Hupp) Date: Fri, 11 Jul 2003 02:27:35 -0500 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" In-Reply-To: References: Message-ID: <20030711072735.GB1834@upl.cs.wisc.edu> On Thu, Jul 10, 2003 at 05:18:58PM -0400, David Abrahams wrote: > It's even easier than that; GCC supplies a library with a function > you can call to demangle these names. I've forgotten the name, of > course :( See http://aspn.activestate.com/ASPN/Mail/Message/1441745 -Adam From Gottfried.Ganssauge at HAUFE.DE Fri Jul 11 12:03:30 2003 From: Gottfried.Ganssauge at HAUFE.DE (Gottfried.Ganssauge at HAUFE.DE) Date: Fri, 11 Jul 2003 12:03:30 +0200 Subject: [C++-sig] Re: Wrapper for exception translation Message-ID: <2040C0A1CA23D51181A30050BAAC990274AAC2@berexch.ber.haufemg.com> > > ... > >> > >> > Currently, in order to wrap user defined exceptions you need to > >> > > >> > - allocate a python exception using PyErr_NewException > >> > >> Well, no. I don't see any call to PyErr_NewException in > >> libs/python/test/exception_translator.cpp > > > > Right, you don't need to if you are content with RuntimeError > > exceptions. > > or any other pre-packaged exception type provided by Python. > > > My objective was another one: I wanted to create module exceptions > > that are derived from the python "Exception" class. > >> > >> > This function needs to be parametrized using a specific naming > >> > convention > >> > >> It's not clear to me what you're referring to. Are you > sure you mean > >> "naming convention"? > > Yes. > > From the documentation to PyErr_NewException: > > > > ... The __module__ attribute of the new class is set to > the first part > > (up to the last dot) of the name argument, and the > class name is set to > > the last part (after the last dot). > > ...yeah, that's a naming convention, but I don't see how that affects > the parameterization of any function. It is enforced by PyErr_NewException, so you must follow this convention. On the hand I don't think that any user of boost.python is aware of that convention, so I wanted to codify it within my facility. ... > > What I wanted to achieve was the following: > > Create an instance of a translated_exception_handler<> t > which will be > > registered with the library by calling > > register_exception_translator<>(). > > Sorry to be difficult, but I'm going to contradict you. You didn't > want any of that. What you wanted was to create a new Python > exception type in the module which would correspond to a particular > C++ exception type and would be raised at the boundary with Python > whenever a wrapped function threw the C++ exception. Right? Right. I actually described the way to do it within the current library design. > > > Normally t would be destructed by the end of exception_<>() thereby > > leaving a registration to a non-existing translator - very bad > > karma. > > I don't understand any of this. All you have to pass to > register_exception_translator is a function pointer, and functions > live forever. So where's the lifetime issue? A pointer to a function which has access to python exception instance e. As I didn't want to create separate entities I chose to supply a functor instead which has e as a member variable. > > > Because I didn't like to have an additional container for all > > translated_exception_handler<> instances, I chose to store t within > > e's class dictionary. At that moment it seemed to be the easiest > > way to create a wrapper class using class_<> instead of making a > > true python class by hand (and it even works!). You are right, it > > is way too complex, I will change it to the mechanism I used in > > opaque_pointer_converter. > > I don't know what that is, but before you consider doing something > which is again too complex, please consider: > > template > struct translate_exception > { > static char const* msg; This would need to be defined somewhere. > static object python_exception_type; ... and this would need to be defined somewhere as well. > > static void handler(E const&) > { > PyErr_SetString(python_exception_type.ptr(), msg.c_str()); > }; > > translate_exception(char const* python_exception_name, > char const* msg_) > { > // need fancier name manipulation here > python_exception_type > = object( > handle<>(PyErr_NewException(name))); > msg = msg_; > register_exception_translator(handler); > } > }; > > > Simple. Yes. ... > > I'll make a redesign ... At times you don't see the forrest, just trees ... I think this time I have a simple facility which is also easy to use (no macros). It could be even simpler with a completely different design but frankly - I have no clue how to implement that: We would need a way to somehow derive (in the python sense) a class_<> from PyExc_Exception (the type of the python Exception class) or any other python class (PyErr_NewException() has a base parameter, which could be used for that). At the same time an exception_translator should be registered for that class_<> which uses PyErr_SetObject() to raise a copy of the exception caught. This would allow us to have true Python exceptions in a pythonic sense directly wrapped around the corresponding C++ exception. > > Thnx for your feedback. > > Cool! Looking forward to it. > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com Cheers, Gottfried -------------- next part -------------- An HTML attachment was scrubbed... URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: exception.hpp Type: application/octet-stream Size: 4136 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: exception.cpp Type: application/octet-stream Size: 1854 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: exception.py Type: application/octet-stream Size: 2356 bytes Desc: not available URL: From dave at boost-consulting.com Fri Jul 11 14:39:57 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 11 Jul 2003 08:39:57 -0400 Subject: [C++-sig] Re: smart pointers, polymorphism References: <000701c34770$2fdb5b40$c82aa8c0@dust2k> Message-ID: "Dusty Leary" writes: > Say I have an abstract base class A, an implementation class B, and a > function, void foo(A* a); If I do a normal boost::python binding, then I > can call foo (from python) with instances of B... (at least, I think I > can?). > > The problem I am having is that we are using boost::intrusive_ptr all over > our project already. (We could change this perhaps, but that's the way it > is now). When I expose my classes to boost, it looks like: > > class_ >("A").....; > class_ >("B").....; > > In this case, when I have an python object which wraps an instance of B, I > can't call my foo(A*); function. > > How can I make it so that the "polymorphic search" succeeds, in matching > intrusive_ptr against A* parameters? class_ >("A").....; class_, bases >("B").....; ^^^^^^^^ ?? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 11 16:48:27 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 11 Jul 2003 10:48:27 -0400 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: <20030711072735.GB1834@upl.cs.wisc.edu> Message-ID: Adam Hupp writes: > On Thu, Jul 10, 2003 at 05:18:58PM -0400, David Abrahams wrote: >> It's even easier than that; GCC supplies a library with a function >> you can call to demangle these names. I've forgotten the name, of >> course :( > > See http://aspn.activestate.com/ASPN/Mail/Message/1441745 Of course, we still have the GPL problem if we link to that :( -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 11 16:50:05 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 11 Jul 2003 10:50:05 -0400 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: Message-ID: Raoul Gough writes: > The source to the demangler is GPL'd, of course (in > gcc/libiberty/cp-demangle.c) and is also including in gdb, AFAIK. It's > currently >3000 lines of code, so I wouldn't recommend trying to > reimplement it for Boost.Python! Well, that might just be because it's bad code or written in C with insufficient abstraction. From http://mail.python.org/pipermail/c++-sig/2002-June/001277.html it doesn't look all that hard. (famous last words). -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 11 16:51:35 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 11 Jul 2003 10:51:35 -0400 Subject: [C++-sig] Re: Call policies for unreferencing iterator ... References: <3F0D3211.50002@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > My problem is I don't know how to tie the > lifetime of the object with the container ... and I don't even think > it's possible to do that. Certainly not, if the iterator doesn't have a reference to the Python container embedded in it. > What would you do ? Redesign my interface, I guess. -- Dave Abrahams Boost Consulting www.boost-consulting.com From RaoulGough at yahoo.co.uk Fri Jul 11 19:42:15 2003 From: RaoulGough at yahoo.co.uk (Raoul Gough) Date: Fri, 11 Jul 2003 18:42:15 +0100 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: Message-ID: David Abrahams writes: > Raoul Gough writes: > >> The source to the demangler is GPL'd, of course (in >> gcc/libiberty/cp-demangle.c) and is also including in gdb, AFAIK. It's >> currently >3000 lines of code, so I wouldn't recommend trying to >> reimplement it for Boost.Python! > > Well, that might just be because it's bad code or written in C with > insufficient abstraction. From > http://mail.python.org/pipermail/c++-sig/2002-June/001277.html it > doesn't look all that hard. > > (famous last words). I once tried to look into cp-demangle.c with the naive aim of fixing a bug I'd found (ha! poor demented fool that I was) but quickly put it in my too hard basket. I hadn't heard of the __cxa_demangle routine before (thanks to Adam Hupp for the info). It seems to add about 20kB of code to an executable (on i386, mingw) which is not bad in the context of Boost.Python. What about backwards compatability, if the demangle routine is only available in >=3.1 gcc? c++filt (AFAIK) has always been available as a command-line tool. -- Raoul Gough "Let there be one measure for wine throughout our kingdom, and one measure for ale, and one measure for corn" - Magna Carta From RaoulGough at yahoo.co.uk Fri Jul 11 19:50:18 2003 From: RaoulGough at yahoo.co.uk (Raoul Gough) Date: Fri, 11 Jul 2003 18:50:18 +0100 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: <20030711072735.GB1834@upl.cs.wisc.edu> Message-ID: David Abrahams writes: > Adam Hupp writes: > >> On Thu, Jul 10, 2003 at 05:18:58PM -0400, David Abrahams wrote: >>> It's even easier than that; GCC supplies a library with a function >>> you can call to demangle these names. I've forgotten the name, of >>> course :( >> >> See http://aspn.activestate.com/ASPN/Mail/Message/1441745 > > Of course, we still have the GPL problem if we link to that :( I don't get it - would you be releasing binaries which include __cxa_demangle but no other (L)GPL'd code? I mean, if the binary came out of g++ then you've probably got LGPL'd libstdc++ code already. -- Raoul Gough "Let there be one measure for wine throughout our kingdom, and one measure for ale, and one measure for corn" - Magna Carta From dave at boost-consulting.com Fri Jul 11 20:47:49 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 11 Jul 2003 14:47:49 -0400 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: <20030711072735.GB1834@upl.cs.wisc.edu> Message-ID: Raoul Gough writes: > David Abrahams writes: > >> Adam Hupp writes: >> >>> On Thu, Jul 10, 2003 at 05:18:58PM -0400, David Abrahams wrote: >>>> It's even easier than that; GCC supplies a library with a function >>>> you can call to demangle these names. I've forgotten the name, of >>>> course :( >>> >>> See http://aspn.activestate.com/ASPN/Mail/Message/1441745 >> >> Of course, we still have the GPL problem if we link to that :( > > I don't get it - would you be releasing binaries which include > __cxa_demangle but no other (L)GPL'd code? I mean, if the binary came > out of g++ then you've probably got LGPL'd libstdc++ code already. What about MinGW? -- Dave Abrahams Boost Consulting www.boost-consulting.com From RaoulGough at yahoo.co.uk Fri Jul 11 21:29:50 2003 From: RaoulGough at yahoo.co.uk (Raoul Gough) Date: Fri, 11 Jul 2003 20:29:50 +0100 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: <20030711072735.GB1834@upl.cs.wisc.edu> Message-ID: David Abrahams writes: > Raoul Gough writes: > >> David Abrahams writes: >> >>> Of course, we still have the GPL problem if we link to that :( >> >> I don't get it - would you be releasing binaries which include >> __cxa_demangle but no other (L)GPL'd code? I mean, if the binary came >> out of g++ then you've probably got LGPL'd libstdc++ code already. > > What about MinGW? Not sure what you mean - I was already thinking about MinGW :-) Well, seriously, I mostly use the MinGW version of g++, so my comment inherently comes from within that context. As I understand it (although I'm no (L)GPL expert) I can freely redistribute binaries that include libstdc++ in compiled form. Contrast this with cygwin1.dll which is covered by the full GPL, so binaries that use it import the GPL onto all sources for the binary (obviously not desirable for Boost). This is certainly something to be aware of if you're distributing binaries at all. Actually, now that I look at some libstdc++ sources, they seem to be covered by the normal GPL but with a special exemption along the lines "...this file does not by itself cause the resulting executable to be covered by the GNU General Public License...". Oh, wait a second - here's some possibly relevant info from cp-demangle.c (which contains __cxa_demangle): In addition to the permissions in the GNU General Public License, the Free Software Foundation gives you unlimited permission to link the compiled version of this file into combinations with other programs, and to distribute those combinations without any restriction coming from the use of this file. (The General Public License restrictions do apply in other respects; for example, they cover modification of the file, and distribution when not linked into a combined executable.) I didn't think that you would be distributing any binaries, anyway. Now, cutting and pasting the demangler code, that would be a different story :-) -- Raoul Gough "Let there be one measure for wine throughout our kingdom, and one measure for ale, and one measure for corn" - Magna Carta From RaoulGough at yahoo.co.uk Fri Jul 11 21:40:09 2003 From: RaoulGough at yahoo.co.uk (Raoul Gough) Date: Fri, 11 Jul 2003 20:40:09 +0100 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" References: <20030711072735.GB1834@upl.cs.wisc.edu> Message-ID: Raoul Gough writes: [snip] > Contrast this with cygwin1.dll which is covered by the full GPL, so > binaries that use it import the GPL onto all sources for the binary > (obviously not desirable for Boost). This is certainly something to be > aware of if you're distributing binaries at all. I really shouldn't have started commenting on legal issues! I just looked at the Cygwin license info (http://www.cygwin.com/licensing.html) and it looks like any "license that complies with the Open Source definition" is acceptable for binaries that use libcygwin.a, not just the GPL. IANAL, etc... -- Raoul Gough "Let there be one measure for wine throughout our kingdom, and one measure for ale, and one measure for corn" - Magna Carta From jbrandmeyer at earthlink.net Fri Jul 11 23:19:48 2003 From: jbrandmeyer at earthlink.net (Jonathan Brandmeyer) Date: 11 Jul 2003 17:19:48 -0400 Subject: [C++-sig] Re: todo.txt "Implement type_info streaming for GCC" (David Abrahams) In-Reply-To: <20030711160009.11550.54544.Mailman@mail.python.org> References: <20030711160009.11550.54544.Mailman@mail.python.org> Message-ID: <1057958388.8589.32.camel@illuvatar> On Fri, Dave Abrahams wrote: > Of course, we still have the GPL problem if we link to that :( No more so than any other part of GNU libstdc++. The function is mandated the "multi vendor ABI standard." This facility's documentation states that it is licensed under the same terms as the rest of GNU libstdc++. It seems to me that you should have no issues with using these functions in Boost.Python. HTH, -Jonathan >From cxxabi.h (leading //es removed for plain text email): As a special exception, you may use this file as part of a free software library without restriction. Specifically, if other files instantiate templates or use macros or inline functions from this file, or you compile this file and link it with other files to produce an executable, this file does not by itself cause the resulting executable to be covered by the GNU General Public License. This exception does not however invalidate any other reasons why the executable file might be covered by the GNU General Public License. From http://gcc.gnu.org/onlinedocs/libstdc++/libstdc++-html-USERS-3.3/namespaceabi.html: (Brief description of abi::__cxa_demangle()) New ABI-mandated entry point in the C++ runtime library for demangling. ( A note at the bottom) The same demangling functionality is available via libiberty ( and libiberty.a) in GCC 3.1 and later, but that requires explicit installation (--enable-install-libiberty) and uses a different API, although the ABI is unchanged. >From the draft IA64 ABI docs: http://www.codesourcery.com/cxx-abi/abi.html#demangler From vladimir at pobox.com Sat Jul 12 02:12:57 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: 11 Jul 2003 17:12:57 -0700 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: References: <3F068544.10204@pobox.com> <3F0865D9.6040401@pobox.com> Message-ID: <1057968744.5534.139.camel@river.vlad1.com> On Mon, 2003-07-07 at 13:13, David Abrahams wrote: > Vladimir Vukicevic writes: > [...] > > This is all very complicated sounding, and I can't tell whether it's > still an issue in light of the guard object idea, and I have so much > to catch up on I don't think I have time to analyze. If there's > still an issue here, could you boil it down a bit? Sorry 'bout that, I was in a hurry when I wrote that and didn't manage to explain concisely. Essentially what I think needs to happen is the following: 1. The GIL needs to be acquired at every point that python calls into boost::python glue code. (Any such acquisition should be optional, such that extensions that don't care about threads don't have to deal with the overhead.) 2. The GIL needs to be released (threads "allowed") around every call to a native C++ function wrapped by boost::python. (This function should, if it needs to call Python or boost::python API calls, acquire the GIL itself.) I realized that I was being quite silly in my last patch, and implemented both a GIL guard class (as suggested) and also a threads allow class that do the right thing in their constructors/destructors; this simplified things tremendously. A newer patch is attached. It seems to work for me, though I'm sure that I'd need to spend some time coming up with specific test cases to be really comfortable with it. - Vlad -------------- next part -------------- A non-text attachment was scrubbed... Name: boost-python.patch Type: text/x-patch Size: 30564 bytes Desc: not available URL: From vladimir at pobox.com Sat Jul 12 02:12:58 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: 11 Jul 2003 17:12:58 -0700 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: References: <3F068544.10204@pobox.com> <3F0865D9.6040401@pobox.com> Message-ID: <1057968777.5534.141.camel@river.vlad1.com> On Mon, 2003-07-07 at 13:13, David Abrahams wrote: > Vladimir Vukicevic writes: > [...] > > This is all very complicated sounding, and I can't tell whether it's > still an issue in light of the guard object idea, and I have so much > to catch up on I don't think I have time to analyze. If there's > still an issue here, could you boil it down a bit? Sorry 'bout that, I was in a hurry when I wrote that and didn't manage to explain concisely. Essentially what I think needs to happen is the following: 1. The GIL needs to be acquired at every point that python calls into boost::python glue code. (Any such acquisition should be optional, such that extensions that don't care about threads don't have to deal with the overhead.) 2. The GIL needs to be released (threads "allowed") around every call to a native C++ function wrapped by boost::python. (This function should, if it needs to call Python or boost::python API calls, acquire the GIL itself.) I realized that I was being quite silly in my last patch, and implemented both a GIL guard class (as suggested) and also a threads allow class that do the right thing in their constructors/destructors; this simplified things tremendously. A newer patch is attached. It seems to work for me, though I'm sure that I'd need to spend some time coming up with specific test cases to be really comfortable with it. - Vlad -------------- next part -------------- A non-text attachment was scrubbed... Name: boost-python.patch Type: text/x-patch Size: 30564 bytes Desc: not available URL: From dave at boost-consulting.com Sat Jul 12 19:46:16 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 12 Jul 2003 13:46:16 -0400 Subject: [C++-sig] Re: Explaining the Magic References: Message-ID: "Brett Calcott" writes: > Hi David, > > I am in Aussie now, and though still homeless In winter!! Brrrrr... > I at least have an office. I thought we could make a start on our > plans to document some of the boost python implementation. Great! > I brushed up on reStructuredText so, as discussed I'll try and > construct a document from our conversations. > > As suggested I have had a look at the luabind conversation, and > though I understand bits here and there I need something to tie it > all too. Here's two starting questions: > > 1) What happens when you do the following: > > struct boring {}; > ...etc... > class_("boring") > ; > > There seems to be a fair bit going on. > > - Python needs a new ClassType to be registered. > - We need to construct a new type that can hold our boring struct. > - Inward and outward converters need to be registered for the type. > > Can you gesture in the general direction where these things are done. I only have time for a "off-the-top-of-my-head" answer at the moment; I suggest you step through the code with a debugger after reading this to see how it works, fill in details, and make sure I didn't forget anything. OK: A new (Python) subclass of Boost.Python.Instance (see libs/python/src/object/class.cpp) is created by invoking Boost.Python.class, the metatype: >>> boring = Boost.Python.class( ... 'boring' ... , bases_tuple # in this case, just () ... , { ... '__module__' : module_name ... , '__doc__' : doc_string # optional ... } ... ) A handle to this object is stuck in the m_class_object field of the registration associated with typeid(boring). The registry will keep that object alive forever, even if you wipe out the 'boring' attribute of the extension module (probably not a good thing). Because you didn't specify class, a to-python converter for boring is registered which copies its argument into a value_holder held by the the Python boring object. Because you didn't specify class(no_init), an __init__ function object is added to the class dictionary which default-constructs a boring in a value_holder (because you didn't specify some smart pointer or derived wrapper class as a holder) held by the Python boring object. register_class_from_python is used to register a from-python converter for shared_ptr. boost::shared_ptrs are special among smart pointers because their Deleter argument can be made to manage the whole Python object, not just the C++ object it contains, no matter how the C++ object is held. If there were any bases<>, we'd also be registering the relationship between these base classes and boring in the up/down cast graph (inheritance.[hpp/cpp]). In earlier versions of the code, we'd be registering lvalue from-python converters for the class here, but now from-python conversion for wrapped classes is handled as a special case, before consulting the registry, if the source Python object's metaclass is the Boost.Python metaclass. Hmm, that from-python converter probably ought to be handled the way class converters are, with no explicit conversions registered. > 2) Can you give a brief overview of the data structures that are > present in the registry The registry is simple: it's just a map from typeid -> registration (see boost/python/converter/registrations.hpp). lvalue_chain and rvalue_chain are simple endogenous linked lists. If you want to know more, just ask. If you want to know about the cast graph, ask me something specific in a separate message. > and an overview of the process that happens as a type makes its > way from c++ to python and back again. Big subject. I suggest some background reading: look for relevant info in the LLNL progress reports and the messages they link to. Also, http://mail.python.org/pipermail/c++-sig/2002-May/001023.html http://mail.python.org/pipermail/c++-sig/2002-December/003115.html http://aspn.activestate.com/ASPN/Mail/Message/1280898 http://mail.python.org/pipermail/c++-sig/2002-July/001755.html from c++ to python: It depends on the type and the call policies in use or, for call<>(...), call_method<>(...), or object(...), if ref or ptr is used. There are also two basic categories to to-python conversion, "return value" conversion (for Python->C++ calls) and "argument" conversion (for C++->Python calls and explicit object() conversions). The behavior of these two categories differs subtly in various ways whose details I forget at the moment. You can probably find the answers in the above references, and certainly in the code. The "default" case is by-value (copying) conversion, which uses to_python_value as a to-python converter. Since there can sensibly be only one way to convert any type to python (disregarding the idea of scoped registries for the moment), it makes sense that to-python conversions can be handled by specializing a template. If the type is one of the types handled by a built-in conversion (builtin_converters.hpp), the corresponding template specialization of to_python_value gets used. Otherwise, to_python_value uses the m_to_python function in the registration for the C++ type. Other conversions, like by-reference conversions, are only available for wrapped classes, and are requested explicitly by using ref(...), ptr(...), or by specifying different CallPolicies for a call, which can cause a different to-python converter to be used. These conversions are never registered anywhere, though they do need to use the registration to find the Python class corresponding to the C++ type being referred to. They just build a new Python instance and stick the appropriate Holder instance in it. from python to C++: Once again I think there is a distinction between "return value" and "argument" conversions, and I forget exactly what that is. What happens depends on whether an lvalue conversion is needed (see http://mail.python.org/pipermail/c++-sig/2002-May/001023.html) All lvalue conversions are also registered in a type's rvalue conversion chain, since when an rvalue will do, an lvalue is certainly good enough. An lvalue conversion can be done in one step (just get me the pointer to the object - it can be NULL if no conversion is possible) while an rvalue conversion requires two steps to support wrapped function overloading and multiple converters for a given C++ target type: first tell me if a conversion is possible, then construct the converted object as a second step. > In both of these cases, I'm quite capable of reading code - but the > thing I don't get from scanning the source is a sense of the > architecture, both structurally, and temporally (er, I mean in what > order things go on). I hope this helped. > ps. Take your time to answer these Too late! > -- I am trying to write a paper, and get some foundation > boost_python simulation framework written, so I am happy if we > progress slowly... Well, this should give you plenty to chew on for a while. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Sun Jul 13 00:06:21 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sat, 12 Jul 2003 19:06:21 -0300 Subject: [C++-sig] Pyste: your opinion about some changes Message-ID: <3F10865D.2050101@globalite.com.br> Hi everyone! Prabhu and I have engaged in some discussions on irc about Pyste, and came up with some ideas on how to fix The Order Bug, and the workings of Pyste in general, and would like to know your opinion on this. The Order problem is this: class hierarchies must be exported in order, from the base class to the most-derived class. The naive approach, parse all header files, look up all the bases in the header files and order the classes, occupies too much memory, making it prohibitive with too much classes. The first idea was based on the suggestion by David of using pickle/shelve to hold the declarations in a form that could be easily swaped in/out of disk as needed, solving then the memory problem. We implemented this, it works correctly, but it is too slow, sometimes prohibitive. Plus, Prabhu noted a flaw in Pyste that was always there: you always generate the *entire* wrapper code, there's no support for generating only the wrapper code for a single pyste file. So, he would change something in a Pyste file, like excluding a function, and *all* the wrapper code would be generated again, taking another 10 minutes in his machine. Of course, a more incremental approach is needed. We have thought that a viable solution is that we could lend the responsability of ordering the classes to the users. Ideally, one could do this in a Pyste file: Class('Derived', ...) Class('Base', ...) And Pyste would first instantiate Base, and then Derived. While this is a nice feature, it generates some of complications: - Given Derived, we must know what are its Bases, and we can only do that by calling gccxml. - Given Derived, we must know if Base was exported, so we can put "bases" inside the class_. If the user just exported Derived, "bases" should not be generated. We decided to drop this feature, since while nice, it is not totally necessary, since while exporting hierarchies it is natural to export the bases first. So, the user must write: Class('Base', ...) Class('Derived', ...) as he would if he were writing the wrapper by hand. What do you people feel about this? For Pyste to generate the correct code for a given class, it must know all the other classes that are also being exported, as explained above. So we must pass all pyste files to Pyste somehow before being able to produce code for any class. pyste --module=foo foo1.pyste foo2.pyste This generates a file named foo.cpp, with all the wrapper code on it. While convenient, this is impratical, since compile times can get very high for large libraries. That is why --multiple was created: pyste --multiple --module=foo foo1.pyste foo2.pyste That generates 3 files, _main.cpp, _foo1.cpp and _foo2.cpp. Compiling and linking them together gives the same results as without the --multiple flag. And now, to solve the incrementing generation problem, we came up with 2 approaches, and would like to know the opinions of everyone in the list that are interested. Both of them aim to improve --multiple, and should be faster then the current system. 1. One approach is to add an option like --wrap-only , that would generate just the code related to the pyste file, and --main-only, that would generate just the _main.cpp file: pyste --wrap-only foo1.pyste --multiple --module=foo foo1.pyste foo2.pyste Would generate just _foo1.cpp. Notice that we still pass all pyste files to the command line, because as explained before, Pyste must know all classes that are being exported to be able to generate correct code. pyste --main-only --multiple --module=foo foo1.pyste foo2.pyste Would generate just _main.cpp. The advantage with this approach is that it basically extends the current workings of Pyste, ie, users won't have to change anything to keep using it. The disadvantage of this method is that it looks weird, since you have to pass all pyste files even thought you may be interested in generating code for just one. 2. Another approach is to make the dependencies explicit in the pyste file by using another function, Import. This would make clear that for a given pyste file to be exported, the Imported pyste file would have to be taken in account. Going back to the Base/Derived example, we would have either: all.pyste: Class('Base', ...) Class('Derived', ...) or: base.pyste: Class('Base', ...) derived.pyste: Import('base.pyste') Class('Derived', ...) That way, the dependencies between the files is explicit, and the user is no longer required to pass all the files in the command line: pyste --multiple --module=foo derived.pyste would generate _derived.cpp, and: pyste --multiple --module=foo base.pyste would generate _base.cpp. To generate _main.cpp, the user would have to call: pyste --only-main --multiple --module=foo base.pyste derived.pyste The advantages of this method is that the dependencies between the files are explicit in the pyste files themselves, plus it feels more natural than passing all pyste files in the command line in order to generate code for only one of them. The disadvantages is that it complicates the pyste files a little, and changes the way that Pyste currently works. Whew, that's all. Opinions, anyone? Regards, Nicodemus. From dave at boost-consulting.com Sun Jul 13 00:57:53 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 12 Jul 2003 18:57:53 -0400 Subject: [C++-sig] Re: Pyste: your opinion about some changes References: <3F10865D.2050101@globalite.com.br> Message-ID: Nicodemus writes: > The advantages of this method is that the dependencies between the > files are explicit in the pyste files themselves, plus it feels more > natural than passing all pyste files in the command line in order to > generate code for only one of them. The disadvantages is that it > complicates the pyste files a little, and changes the way that Pyste > currently works. Sounds like all the advantages go to the users and the disadvantages go to the developer. I vote for this one ;-) -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sun Jul 13 05:28:20 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 12 Jul 2003 23:28:20 -0400 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AAC2@berexch.ber.haufemg.com> Message-ID: Gottfried, I could've sworn I replied to this, but now I can't find the reply anywhere. Gottfried.Ganssauge at HAUFE.DE writes: > At times you don't see the forrest, just trees ... > I think this time I have a simple facility which is also easy to use (no > macros). Looks pretty good; I still have a few criticisms. > It could be even simpler with a completely different design but frankly - I > have no clue how to implement that: > We would need a way to somehow derive (in the python sense) a class_<> from > PyExc_Exception (the type of the python Exception class) or any other python > class (PyErr_NewException() has a base parameter, which could be used for > that). > > At the same time an exception_translator should be registered for that > class_<> which uses PyErr_SetObject() to raise a copy of the exception > caught. None of that sounds simpler to me. > This would allow us to have true Python exceptions in a pythonic sense > directly wrapped around the corresponding C++ exception. Doesn't sound like a big advantage to me, but I guess if you had stored data members in the C++ exception type you'd want them to be preserved. Hmm, there's no reason you can't build a BPL extension class which also inherits from Exception, but it seems tough. > /** > * Register an exception translator for the Template argument. > * > * @param name > * the name for the new exception. > * This name is registered in the current scope. > * > * @param base > * An optional base class this exception should be derived from > * > * @return > * A handle to the newly allocated exception > */ > template > handle<> exception_ ( > const char *name, > handle<> base = handle<>(), > boost::type* = 0) { > // Name of the new exception > str exc_name (detail::module_prefix() + "." + name); > // C-Representation of the exception name > const char *cname = extract (exc_name); > > // Allocate a new exception > handle<> e ( > PyErr_NewException (const_cast (cname), base.get(), 0)); > > // Register a handler for it with the library > register_exception_translator ( > detail::translated_exception_handler (e)); > > // and make it visible in the scope's namespace > scope().attr (name) = e; > return (e); > } > }} // namespace boost::python > # endif // BOOST_PYTHON_EXCEPTION_HPP_ > BOOST_PYTHON_MODULE(exception_ext) { > handle<> e (exception_ ("exc")); > exception_ ("bad_exc"); > exception_ ("obj_exc"); > exception_ ("derived_exc", e); > > def ("throw_exc", &throw_exc); > def ("throw_bad_exc", &throw_bad_exc); > def ("throw_exc3", &throw_exc3); > def ("throw_derived", &throw_derived); > > { > scope x (class_ ("exc_def")); > > // a nested exception within class exc_def > exception_ ("exc3"); > } > > class_ ("obj_exception") > .def ("throw", &obj_exc::raise) > .def ("what", &obj_exc::what) > ; > } This is a big improvement. What I don't like about this is: a. the need for users to mess with handle<>s. handle<> can be nil, so is less safe than object. b. a name in the public interface ("exception_") which needlessly ends in an underscore c. Formatting inconsistent with the library and goofy @directives in the comments I'd prefer an interface where boost::python::exception was a class derived from object: exception e("exc"); exception("bad_exc"); exception("obj_exc"); exception("derived_exc", e); -- Dave Abrahams Boost Consulting www.boost-consulting.com From prabhu at aero.iitm.ernet.in Sun Jul 13 09:12:45 2003 From: prabhu at aero.iitm.ernet.in (Prabhu Ramachandran) Date: Sun, 13 Jul 2003 12:42:45 +0530 Subject: [C++-sig] Re: Pyste: your opinion about some changes In-Reply-To: References: <3F10865D.2050101@globalite.com.br> Message-ID: <16145.1645.920915.454966@monster.linux.in> >>>>> "DA" == David Abrahams writes: DA> Nicodemus writes: >> The advantages of this method is that the dependencies between >> the files are explicit in the pyste files themselves, plus it >> feels more natural than passing all pyste files in the command >> line in order to generate code for only one of them. The >> disadvantages is that it complicates the pyste files a little, >> and changes the way that Pyste currently works. DA> Sounds like all the advantages go to the users and the DA> disadvantages go to the developer. I vote for this one ;-) I'm very glad that you do! It does make life much easier when wrapping multiple Pyste files. I don't think this feature would be hard to implement either. I think what Nicodemus was referring to in, "complicates the pyste file a little, and changes the way that Pyste currently works." was that users now need to remember to add an Import('base.pyste') before they wrap Class('Derived') inside derived.pyste. If not, the bases will not be right. However, I think thats quite OK since users will know the bases that they wrap -- atleast they will know what bases the currently wrapped classes are derived from. The scheme also is similar to what one would expect in C++. The Import function is similar to the %import directive in SWIG. So SWIG users will also be comfortable with this function. Best of all, the import directive is optional, so all current users of Pyste will not notice any difference since the original behavior will be unchanged. Its only when one needs to wrap the library incrementally that this function helps heaps. It is also useful when you need to split the library into small sub-packages where if you have classes in one sub-package derived from bases in another sub-package. The second issue is that it changes the internals of Pyste a little, but I think it will not be a big change at all. We've made much bigger ones in the past week. So I'm not sure there are serious disadvantages to the developer either. :) Nicodemus, please do let us know if I am seriously mistaken about something here. cheers, prabhu From dominique.devriese at student.kuleuven.ac.be Sun Jul 13 12:54:07 2003 From: dominique.devriese at student.kuleuven.ac.be (Dominique Devriese) Date: Sun, 13 Jul 2003 12:54:07 +0200 Subject: [C++-sig] plans for a bugfix release ? Message-ID: <873chau27k.fsf@student.kuleuven.ac.be> Hi, I'm the main developer of Kig [1]. I have just committed the code for python scripting to the CVS repository, but I'm receiving bug reports from people not able to compile the new code because of the small typename problem that was fixed in Boost.Python some time ago [2] ( the fix is in CVS, right ? ). Are there any plans to release a fixed version of Boost.Python any time soon, and what is the policy on Boost.Python releases in general ? thanks domi Footnotes: [1] http://edu.kde.org/kig [2] http://mail.python.org/pipermail/c++-sig/2003-May/003889.html and http://mail.python.org/pipermail/c++-sig/2003-May/003896.html From ganssauge at gmx.de Sun Jul 13 13:59:17 2003 From: ganssauge at gmx.de (=?iso-8859-1?Q?Gottfried_Gan=DFauge?=) Date: Sun, 13 Jul 2003 13:59:17 +0200 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AAC2@berexch.ber.haufemg.com> Message-ID: <001201c34936$303e0b60$44a837c2@gieke> ... > > It could be even simpler with a completely different design but frankly - I > > have no clue how to implement that: > > We would need a way to somehow derive (in the python sense) a class_<> from > > PyExc_Exception (the type of the python Exception class) or any other python > > class (PyErr_NewException() has a base parameter, which could be used for > > that). > > > > At the same time an exception_translator should be registered for that > > class_<> which uses PyErr_SetObject() to raise a copy of the exception > > caught. > > None of that sounds simpler to me. > > > This would allow us to have true Python exceptions in a pythonic sense > > directly wrapped around the corresponding C++ exception. > > Doesn't sound like a big advantage to me, but I guess if you had > stored data members in the C++ exception type you'd want them to be > preserved. Hmm, there's no reason you can't build a BPL extension > class which also inherits from Exception, but it seems tough. Maybe an example is in order: // this is the exception to wrap struct some_exception { some_exception (const char *description, int error_number); const char *what() const; int get_additional_errorinfo() const; }; // This is how it could be wrapped BOOST_PYTHON_MODULE(exception_test) { class_ > ("some_exception") .def ("what", &some_exception::what) .def ("get_additional_errorinfo", &some_exception::get_additional_errorinfo) ; } This should be sufficient to fully automatically wrap the "some_exception" class including exception translation. Key to this automatism is the exception_base<> template, which by some magic could determine that our wrapper needs to derived from PyExc_Exception and that exception translation for "some_exception" is needed. exception_base<> would be templated by the python exception type our new exception is to be derived from. When an instance of "some_exception" is thrown and caught by the library it would then raise the associated python exception passing a python version of the "some_exception" instance as the exception argument. The exception handler in the python script could look like try: do_something_eventually_raising_some_exception() except exception_test.some_exception, e: print "Caught some_exception (%s, %d)" % (e.what(), e.get_additional_errorinfo()) I think this *is* easier for the user of the library but as I said: I have no clue how to implement something like that. ... > This is a big improvement. What I don't like about this is: > > a. the need for users to mess with handle<>s. handle<> can be > nil, so is less safe than object. I'm not using null_ok(), so I thought that the handle can't be nil because in that case the constructor would have thrown :-) > > b. a name in the public interface ("exception_") which > needlessly ends in an underscore This is true. > > c. Formatting inconsistent with the library and goofy @directives > in the comments ok. my post was not meant as a submission but as a concept. > > I'd prefer an interface where boost::python::exception was a class > derived from object: > > exception e("exc"); > exception("bad_exc"); > exception("obj_exc"); > exception("derived_exc", e); I'll do it. Cheers, Gottfried > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com > > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > > > From Vincenzo.Innocente at cern.ch Sun Jul 13 15:18:32 2003 From: Vincenzo.Innocente at cern.ch (Vincenzo Innocente) Date: Sun, 13 Jul 2003 15:18:32 +0200 (W. Europe Daylight Time) Subject: [C++-sig] Re: Pyste: your opinion about some changes Message-ID: Hi Nicodemus, in our project we badly need support for multiple files, multiple packages and inheritance from base classes defined in a different package. We have already implemented some work-arounds and at the moment the support of multiple files IS a show-stopper. I definetively vote for an "Import" statement in Pyste. I consider the explicit dependency through the import statement more clear and exportable than the implicit one through the list of files on the command line. I hope you will be able to provide an implementation (whatever solution you decide to adopt) soon in cvs. We do not mind to break backward compatibility... cheers, Vincenzo From nicodemus at globalite.com.br Sun Jul 13 18:34:19 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Sun, 13 Jul 2003 13:34:19 -0300 Subject: [C++-sig] Re: Pyste: your opinion about some changes In-Reply-To: <16145.1645.920915.454966@monster.linux.in> References: <3F10865D.2050101@globalite.com.br> <16145.1645.920915.454966@monster.linux.in> Message-ID: <3F118A0B.7050102@globalite.com.br> Prabhu Ramachandran wrote: >>>>>>"DA" == David Abrahams writes: >>>>>> >>>>>> > DA> Sounds like all the advantages go to the users and the > DA> disadvantages go to the developer. I vote for this one ;-) > >I'm very glad that you do! It does make life much easier when >wrapping multiple Pyste files. I don't think this feature would be >hard to implement either. I think what Nicodemus was referring to in, > > "complicates the pyste file a little, and changes the way that Pyste > currently works." > >was that users now need to remember to add an Import('base.pyste') >before they wrap Class('Derived') inside derived.pyste. > Exactly, the internals will change very little, I meant how the users would use Pyste that would change. 8) Regards, Nicodemus. From dave at boost-consulting.com Sun Jul 13 19:34:41 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sun, 13 Jul 2003 13:34:41 -0400 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AAC2@berexch.ber.haufemg.com> <001201c34936$303e0b60$44a837c2@gieke> Message-ID: Gottfried Gan?auge writes: > ... >> > It could be even simpler with a completely different design but > frankly - I >> > have no clue how to implement that: >> > We would need a way to somehow derive (in the python sense) a class_<> > from >> > PyExc_Exception (the type of the python Exception class) or any other > python >> > class (PyErr_NewException() has a base parameter, which could be used > for >> > that). >> > >> > At the same time an exception_translator should be registered for that >> > class_<> which uses PyErr_SetObject() to raise a copy of the exception >> > caught. >> >> None of that sounds simpler to me. >> >> > This would allow us to have true Python exceptions in a pythonic sense >> > directly wrapped around the corresponding C++ exception. >> >> Doesn't sound like a big advantage to me, but I guess if you had >> stored data members in the C++ exception type you'd want them to be >> preserved. Hmm, there's no reason you can't build a BPL extension >> class which also inherits from Exception, but it seems tough. > > Maybe an example is in order: > > // this is the exception to wrap > struct some_exception { > some_exception (const char *description, int error_number); > > const char *what() const; > int get_additional_errorinfo() const; > }; > > // This is how it could be wrapped > BOOST_PYTHON_MODULE(exception_test) > { > class_ > ("some_exception") > .def ("what", &some_exception::what) > .def ("get_additional_errorinfo", > &some_exception::get_additional_errorinfo) > ; > } Yes, I understood it to be something like that. What about: BOOST_PYTHON_MODULE(exception_test) { exception ("some_exception") .def ("what", &some_exception::what) .def ("get_additional_errorinfo", &some_exception::get_additional_errorinfo) ; } This is actually quite straightforward to implement, I think. Basically: * exception<...> is derived from class<...> * we extend class_ with a protected constructor which takes an object which represents an additional base class to use. This argument is passed on to the class_base constructor and used as an additional base class. * exception<...> reproduces the class_ constructor signatures and forwards to the new class_ constructor, with the object referring to python's builtin Exception type. > When an instance of "some_exception" is thrown and caught by the library it > would then raise the associated python exception passing a python version of > the "some_exception" instance as the exception argument. > The exception handler in the python script could look like > try: > do_something_eventually_raising_some_exception() > except exception_test.some_exception, e: > print "Caught some_exception (%s, %d)" % (e.what(), > e.get_additional_errorinfo()) > > I think this *is* easier for the user of the library but as I said: I have > no clue how to implement something like that. OK, I agree that it's easier. Why don't you poke around a bit more based on my hints? I'm sure you can make it work. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dholth at fastmail.fm Sun Jul 13 21:36:17 2003 From: dholth at fastmail.fm (Daniel Holth) Date: 13 Jul 2003 15:36:17 -0400 Subject: [C++-sig] boost::python docstrings Message-ID: <1058124976.13724.30.camel@bluefish> Hello. I'm working on a module that exposes xmms_remote_* to Python. It's mostly done and in pypi but I would like help(xmms) to be more informative. What's the best way to change jump_to_time(...) Seek to a number of milliseconds past the beginning of the current file. to jump_to_time(t) Seek ... file. ? Thanks, Daniel Holth http://dingoskidneys.com -------------- next part -------------- A non-text attachment was scrubbed... Name: not available Type: application/pgp-signature Size: 189 bytes Desc: This is a digitally signed message part URL: From dave at boost-consulting.com Sun Jul 13 22:17:35 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sun, 13 Jul 2003 16:17:35 -0400 Subject: [C++-sig] Re: boost::python docstrings References: <1058124976.13724.30.camel@bluefish> Message-ID: Daniel Holth writes: > What's the best way to change > > jump_to_time(...) > Seek to a number of milliseconds past the beginning of the current > file. > > to > > jump_to_time(t) > Seek ... file. > > ? There's so much information missing I doubt anyone is going to understand your question. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sun Jul 13 23:40:12 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sun, 13 Jul 2003 17:40:12 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F0865D9.6040401@pobox.com> <1057968744.5534.139.camel@river.vlad1.com> Message-ID: Vladimir Vukicevic writes: > On Mon, 2003-07-07 at 13:13, David Abrahams wrote: >> Vladimir Vukicevic writes: >> [...] > >> >> This is all very complicated sounding, and I can't tell whether it's >> still an issue in light of the guard object idea, and I have so much >> to catch up on I don't think I have time to analyze. If there's >> still an issue here, could you boil it down a bit? > > Sorry 'bout that, I was in a hurry when I wrote that and didn't manage > to explain concisely. > > Essentially what I think needs to happen is the following: > > 1. The GIL needs to be acquired at every point that python calls into > boost::python glue code. I don't think so! When Python calls boost::python it *always* has the GIL already. It looks like you have way too many detail::gil_lock instances in your patch. GUI acquisition needs to be done when C++ code calls back into python. > (Any such acquisition should be optional, such that extensions that > don't care about threads don't have to deal with the overhead.) Which is why I don't understand the need for call_with_gil<>. What's wrong with asking the user to create a local gil_lock of his own? He might need one anyway, since he may need to use the Boost.Python/Python API himself. void my_callback() { x = call(make_tuple("a", "b", "c")); } > 2. The GIL needs to be released (threads "allowed") around every call to > a native C++ function wrapped by boost::python. (This function should, > if it needs to call Python or boost::python API calls, acquire the GIL > itself.) No way. That incurs way too much overhead for small wrapped functions. Releasing the GIL when we call a wrapped C++ function needs to be optional (possibly globally settable). In any case, even if it's not optional you have a problem because you're releasing the GIL when calling into functions that accept, e.g. python::object parameters. You haven't patched object::object(object const&) to acquire the gil. You'd need to find *every* PyXXXX in the library and make sure the GIL is acquired. All that aqcuiring/releasing could get expensive, and I'm not comfortable with that. -- Dave Abrahams Boost Consulting www.boost-consulting.com From vladimir at pobox.com Mon Jul 14 02:18:03 2003 From: vladimir at pobox.com (Vladimir Vukicevic) Date: 13 Jul 2003 17:18:03 -0700 Subject: [C++-sig] Re: boost::python and threads In-Reply-To: References: <3F068544.10204@pobox.com> <3F0865D9.6040401@pobox.com> <1057968744.5534.139.camel@river.vlad1.com> Message-ID: <1058141883.5534.198.camel@river.vlad1.com> On Sun, 2003-07-13 at 14:40, David Abrahams wrote: > Vladimir Vukicevic writes: > > > Sorry 'bout that, I was in a hurry when I wrote that and didn't manage > > to explain concisely. > > > > Essentially what I think needs to happen is the following: > > > > 1. The GIL needs to be acquired at every point that python calls into > > boost::python glue code. > > I don't think so! > > When Python calls boost::python it *always* has the GIL already. It > looks like you have way too many detail::gil_lock instances in your > patch. GUI acquisition needs to be done when C++ code calls back into > python. Hmm.. you're right. There were a few problems that I had going on that made me put in a lot of gil_lock's, more so than what are needed. I'll have to go through and examine again exactly where they need to go. > > (Any such acquisition should be optional, such that extensions that > > don't care about threads don't have to deal with the overhead.) > > Which is why I don't understand the need for call_with_gil<>. What's > wrong with asking the user to create a local gil_lock of his own? He > might need one anyway, since he may need to use the > Boost.Python/Python API himself. Sure, sounds good. > > 2. The GIL needs to be released (threads "allowed") around every call to > > a native C++ function wrapped by boost::python. (This function should, > > if it needs to call Python or boost::python API calls, acquire the GIL > > itself.) > > No way. That incurs way too much overhead for small wrapped > functions. Releasing the GIL when we call a wrapped C++ function > needs to be optional (possibly globally settable). Are you thinking settable at runtime or at compile time? If at compile time, then defining BOOST_PYTHON_NO_THREADING causes gil_lock/thread_block to just be dummy stubs. I don't see how you'd do it for some methods and not for others, without adding extra logic to the path that leads to invoke() -- which I guess may be the right thing to do for a fully general solution. > In any case, even if it's not optional you have a problem because > you're releasing the GIL when calling into functions that accept, > e.g. python::object parameters. You haven't patched > object::object(object const&) to acquire the gil. You'd need to find > *every* PyXXXX in the library and make sure the GIL is acquired. All > that aqcuiring/releasing could get expensive, and I'm not comfortable > with that. Yup, there's still a bunch of places where the locks aren't correct. Expensive or not though, I don't see a way around it -- you're either not thread safe (in which case you go the BOOST_PYTHON_NO_THREADING route at compile time), or you are -- eventually one could probably build separate boost_python .so with and without thread safety so that extensions can choose which version to link/build with. Thanks for the feedback, - Vlad From dave at boost-consulting.com Mon Jul 14 02:51:07 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sun, 13 Jul 2003 20:51:07 -0400 Subject: [C++-sig] Re: boost::python and threads References: <3F068544.10204@pobox.com> <3F0865D9.6040401@pobox.com> <1057968744.5534.139.camel@river.vlad1.com> <1058141883.5534.198.camel@river.vlad1.com> Message-ID: Vladimir Vukicevic writes: > On Sun, 2003-07-13 at 14:40, David Abrahams wrote: >> Vladimir Vukicevic writes: >> >> > Sorry 'bout that, I was in a hurry when I wrote that and didn't manage >> > to explain concisely. >> > >> > Essentially what I think needs to happen is the following: >> > >> > 1. The GIL needs to be acquired at every point that python calls into >> > boost::python glue code. >> >> I don't think so! >> >> When Python calls boost::python it *always* has the GIL already. It >> looks like you have way too many detail::gil_lock instances in your >> patch. GUI acquisition needs to be done when C++ code calls back into >> python. > > Hmm.. you're right. There were a few problems that I had going on that > made me put in a lot of gil_lock's, more so than what are needed. I'll > have to go through and examine again exactly where they need to go. > >> > (Any such acquisition should be optional, such that extensions that >> > don't care about threads don't have to deal with the overhead.) >> >> Which is why I don't understand the need for call_with_gil<>. What's >> wrong with asking the user to create a local gil_lock of his own? He >> might need one anyway, since he may need to use the >> Boost.Python/Python API himself. > > Sure, sounds good. > >> > 2. The GIL needs to be released (threads "allowed") around every call to >> > a native C++ function wrapped by boost::python. (This function should, >> > if it needs to call Python or boost::python API calls, acquire the GIL >> > itself.) >> >> No way. That incurs way too much overhead for small wrapped >> functions. Releasing the GIL when we call a wrapped C++ function >> needs to be optional (possibly globally settable). > > Are you thinking settable at runtime or at compile time? I was thinking the latter, but we do need to watch out for potential ODR problems in that case. > If at compile time, then defining BOOST_PYTHON_NO_THREADING causes > gil_lock/thread_block to just be dummy stubs. I don't see how you'd > do it for some methods and not for others I think we should; the Lua people for example want to be able to do threading *and* not pay for things they won't use. Shouldn't Python users have the same privilege? Releasing the GIL just to set an integer data member on a wrapped object seems like overkill. Am I being silly? > , without adding extra logic to the path that leads to invoke() -- > which I guess may be the right thing to do for a fully general > solution. As I said earlier, I think the solution is to wrap the *function* being def'd in a functor which releases the GIL, something like: def("foobar", threaded(foobar)) >> In any case, even if it's not optional you have a problem because >> you're releasing the GIL when calling into functions that accept, >> e.g. python::object parameters. You haven't patched >> object::object(object const&) to acquire the gil. You'd need to find >> *every* PyXXXX in the library and make sure the GIL is acquired. All >> that aqcuiring/releasing could get expensive, and I'm not comfortable >> with that. > > Yup, there's still a bunch of places where the locks aren't correct. > Expensive or not though, I don't see a way around it -- you're > either not thread safe (in which case you go the > BOOST_PYTHON_NO_THREADING route at compile time), or you are -- No, it's not that simple. If you never release the GIL and never try to acquire it, you're perfectly thread-safe, so long as you don't need Python code to execute concurrently with your C++ code. Once you release the GIL then you have to worry about Python calling into your C++ on another thread, so the thread-safety of your C++ code is at issue. You also have to make sure you acquire the GIL before you touch the Python API again. But there's no reason we can't ask users to manage the latter issue themselves if they've explicitly released the GIL. There are two use-cases when Python calls into C++: 1. The user writes a thin wrapper function, and can simply put the Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS (or some smarter C++ RAII equivalent in his wrapper) 2. The user wants to wrap the function directly without a thin wrapper. In that case the function is highly unlikely to have any manipulation of the Python API in it anyway. > eventually one could probably build separate boost_python .so with > and without thread safety so that extensions can choose which > version to link/build with. I dunno, I think we need to discuss this some more until we can reach a common understanding. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dholth at fastmail.fm Mon Jul 14 06:21:33 2003 From: dholth at fastmail.fm (Daniel Holth) Date: 14 Jul 2003 00:21:33 -0400 Subject: [C++-sig] Re: boost::python docstrings In-Reply-To: References: <1058124976.13724.30.camel@bluefish> Message-ID: <1058156493.345.10.camel@bluefish> On Sun, 2003-07-13 at 16:17, David Abrahams wrote: > a(b,c): > foo? > There's so much information missing I doubt anyone is going to > understand your question. Whoops, sorry. Second try: I'm working on a Python extension that controls xmms. It's written in pure C++ and boost::python. This is an excerpt from 'pydoc xmms': Python Library Documentation: module xmms NAME xmms ... | get_playlist_file(...) | Return the filename of a playlist item. | | get_playlist_time(...) | Return length (milliseconds) of a playlist item | | get_playlist_title(...) | Return the title of a playlist item. ... This is an excerpt from 'pydoc urllib': | get_user_passwd(self, host, realm, clear_cache=0) | | http_error_301(self, url, fp, errcode, errmsg, headers, data=None) | Error 301 -- also relocated (permanently). Notice how the Python module (urllib) has its argument list in the pydoc documentation like so: get_user_passwd(self, host, realm, clear_cache=0), while the boost::python module (or __builtins__, for that matter) is presented as functionname(...). My question: Is there an argument to .def() that will tell pydoc what to put in place of the ... in e.g. get_playlist_file(...). The alternative, taken by __builtins__, is to phrase the docstring as methodcall(example) -> result Second Question --------------- I'm also writing an xmms plugin, under the latest Debian Linux, i386, that runs Python code but I get errors about internal Python symbols not being found when I try to import other Python modules (like time). Can someone point me to an existing project that includes a dynamically loaded Python embedding? Thanks, Daniel Holth http://dingoskidneys.com -------------- next part -------------- A non-text attachment was scrubbed... Name: not available Type: application/pgp-signature Size: 189 bytes Desc: This is a digitally signed message part URL: From dave at boost-consulting.com Mon Jul 14 14:52:07 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 14 Jul 2003 08:52:07 -0400 Subject: [C++-sig] Re: boost::python docstrings References: <1058124976.13724.30.camel@bluefish> <1058156493.345.10.camel@bluefish> Message-ID: Daniel Holth writes: > On Sun, 2003-07-13 at 16:17, David Abrahams wrote: >> a(b,c): >> foo? >> There's so much information missing I doubt anyone is going to >> understand your question. > > Whoops, sorry. Second try: > > I'm working on a Python extension that controls xmms. It's written in > pure C++ and boost::python. This is an excerpt from 'pydoc xmms': > > Python Library Documentation: module xmms > > NAME > xmms > > ... > > | get_playlist_file(...) > | Return the filename of a playlist item. > | > | get_playlist_time(...) > | Return length (milliseconds) of a playlist item > | > | get_playlist_title(...) > | Return the title of a playlist item. > > ... > > This is an excerpt from 'pydoc urllib': > | get_user_passwd(self, host, realm, clear_cache=0) > | > | http_error_301(self, url, fp, errcode, errmsg, headers, data=None) > | Error 301 -- also relocated (permanently). > > > Notice how the Python module (urllib) has its argument list in the pydoc > documentation like so: get_user_passwd(self, host, realm, > clear_cache=0), while the boost::python module (or __builtins__, for > that matter) is presented as functionname(...). Well, Python has a lot more to go on when introspecting about a pure Python function than about a callable "extension function" object. > My question: Is there an argument to .def() that will tell pydoc what > to put in place of the ... in e.g. get_playlist_file(...). Well, http://www.boost.org/libs/python/doc/v2/args.html ought to work, but I'm pretty sure it doesn't. If you can tell us what information pydoc uses to format that info we might be able to help. [Nicodemus, I think pyste should take an option to generate "args(...)" for those people who want to use keywords in their function calls] > The alternative, taken by __builtins__, is to phrase the docstring as > methodcall(example) -> result > > Second Question > --------------- > I'm also writing an xmms plugin, under the latest Debian Linux, i386, > that runs Python code but I get errors about internal Python symbols not > being found when I try to import other Python modules (like time). Can > someone point me to an existing project that includes a dynamically > loaded Python embedding? I don't know what you mean by "a dynamically loaded Python embedding?", but this sounds like a question for comp.lang.python to me anyway. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 14 20:18:52 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 14 Jul 2003 14:18:52 -0400 Subject: [C++-sig] Re: plans for a bugfix release ? References: <873chau27k.fsf@student.kuleuven.ac.be> Message-ID: Dominique Devriese writes: > Hi, > > I'm the main developer of Kig [1]. I have just committed the code for > python scripting to the CVS repository Using Boost.Python? Cool! > but I'm receiving bug reports from people not able to compile the > new code because of the small typename problem that was fixed in > Boost.Python some time ago [2] ( the fix is in CVS, right ? ). Yes. > Are there any plans to release a fixed version of Boost.Python any > time soon No specific plans, no. > and what is the policy on Boost.Python releases in general ? In general, they are released when all of Boost is ready. I think it would be a *really* good idea for Boost to do at least one minor version release shortly after any major version release. Now that we have a reasonable testing strategy it should be relatively easy. Boost 1.30.0 went out with several bugs IIRC. > thanks > domi > > Footnotes: > [1] http://edu.kde.org/kig > > [2] http://mail.python.org/pipermail/c++-sig/2003-May/003889.html and > http://mail.python.org/pipermail/c++-sig/2003-May/003896.html Until we get our act together, I would suggest you supply people with a Boost patch. Use "BOOST_DEDUCED_TYPENAME" instead of "typename" so you don't break VC6. Sorry, -- Dave Abrahams Boost Consulting www.boost-consulting.com From stefan.seefeld at orthosoft.ca Mon Jul 14 21:34:28 2003 From: stefan.seefeld at orthosoft.ca (Stefan Seefeld) Date: Mon, 14 Jul 2003 15:34:28 -0400 Subject: [C++-sig] compile time error triggered by gcc's '-pedantic' flag Message-ID: hi there, I'm compiling a python extension containing a method returning an internal pointer, so I use: namespace { class Foo {}; class Bar { public: Foo *foo() { return &my_foo;} private: Foo my_foo; }; } BOOST_PYTHON_MODULE(Sandbox) { python::class_ foo("Foo", python::no_init); python::class_ bar("Bar", python::no_init); bar.def("foo", &Bar::foo, python::return_internal_reference<>()); } Whenever I try to compile that with gcc -pedantic, I get an error which ends with the lines ... /usr/local/ORTHOsoft/include/boost/python/class.hpp:253: instantiated from `boost::python::class_& boost::python::class_::def(const char*, A1, const A2&) [with A1 = ::Foo*(::Bar::*)(), A2 = boost::python::return_internal_reference<1, boost::python::default_call_policies>, T = ::Bar, X1 = boost::noncopyable, X2 = boost::python::detail::not_specified, X3 = boost::python::detail::not_specified]' /homes/Developer/sseefel/error.cc:22: instantiated from here /usr/local/ORTHOsoft/include/boost/python/object/make_ptr_instance.hpp:37: invalid use of member `boost::mpl::bool_::type' As a quick fix I'll just drop the '-pedantic' flag but I'm curious as to whether this is a problem with the boost::python code or with gcc. I'm using boost 1.30 and gcc 3.2, by the way. Thanks a lot, Stefan From stefan.seefeld at orthosoft.ca Mon Jul 14 23:11:09 2003 From: stefan.seefeld at orthosoft.ca (Stefan Seefeld) Date: Mon, 14 Jul 2003 17:11:09 -0400 Subject: [C++-sig] more problems with python::return_internal_reference<> Message-ID: <2c1741b3e6559b448421480a32ea72b53f13193b@Orthosoft.ca> hi there, I'm compiling the following code with gcc 3.2: #include namespace python = boost::python; namespace { class Bar {}; Bar *BarFactory() { static Bar bar; return &bar; } } BOOST_PYTHON_MODULE(Sandbox) { python::class_ foo("Foo", python::no_init); python::class_ bar("Bar", python::no_init); bar.def("foo", &Bar::foo, python::return_internal_reference<>()); python::def("Bar", BarFactory, python::return_internal_reference<>()); //python::return_value_policy()); } That compiles fine, but when I call the 'Bar' constructor from python, I get >>> from Sandbox import * >>> bar = Bar() Traceback (most recent call last): File "", line 1, in ? IndexError: tuple index out of range What is going on here ? What does the boost::python runtime do with the returned value that involves a tuple ? When I replace the 'return_internal_reference<>' policy by 'return_value_policy' the function call returns successfully. But of course, that would crash at the end of the application... Thanks again, Stefan From dave at boost-consulting.com Mon Jul 14 23:49:27 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 14 Jul 2003 17:49:27 -0400 Subject: [C++-sig] Re: compile time error triggered by gcc's '-pedantic' flag References: Message-ID: Stefan Seefeld writes: > As a quick fix I'll just drop the '-pedantic' flag but I'm curious as to > whether this is a problem with the boost::python code or with gcc. > I'm using boost 1.30 and gcc 3.2, by the way. This was fixed in the CVS shortly after 1.30 went out. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 14 23:52:22 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 14 Jul 2003 17:52:22 -0400 Subject: [C++-sig] Re: more problems with python::return_internal_reference<> References: <2c1741b3e6559b448421480a32ea72b53f13193b@Orthosoft.ca> Message-ID: Stefan Seefeld writes: > hi there, > > I'm compiling the following code with gcc 3.2: > > #include > namespace python = boost::python; > > namespace > { > > class Bar {}; > > Bar *BarFactory() > { > static Bar bar; > return &bar; > } > > } > > BOOST_PYTHON_MODULE(Sandbox) > { > python::class_ foo("Foo", python::no_init); > > python::class_ bar("Bar", python::no_init); > bar.def("foo", &Bar::foo, python::return_internal_reference<>()); > > python::def("Bar", BarFactory, > python::return_internal_reference<>()); > //python::return_value_policy()); > } > > That compiles fine, but when I call the 'Bar' constructor from python, > I get > > >>> from Sandbox import * > >>> bar = Bar() > Traceback (most recent call last): > File "", line 1, in ? > IndexError: tuple index out of range > > What is going on here ? return_internal_reference tries to bind the lifetime of the function's first argument to that of the result. Where's the first argument to Bar()? > What does the boost::python runtime do with the > returned value that involves a tuple ? Indexes into the argument tuple to do the lifetime binding. > When I replace the 'return_internal_reference<>' policy by > 'return_value_policy' the function call returns > successfully. But of course, that would crash at the end of the > application... See C:\boost\libs\python\doc\v2\reference_existing_object.html -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Tue Jul 15 00:17:44 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 14 Jul 2003 18:17:44 -0400 Subject: [C++-sig] Re: more problems with python::return_internal_reference<> References: <2c1741b3e6559b448421480a32ea72b53f13193b@Orthosoft.ca> Message-ID: David Abrahams writes: > See C:\boost\libs\python\doc\v2\reference_existing_object.html Whoops, sorry: http://www.boost.org/libs/python/doc/v2/reference_existing_object.html -- Dave Abrahams Boost Consulting www.boost-consulting.com From seefeld at sympatico.ca Tue Jul 15 02:03:01 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Mon, 14 Jul 2003 20:03:01 -0400 Subject: [C++-sig] Re: compile time error triggered by gcc's '-pedantic' flag In-Reply-To: References: Message-ID: <3F1344B5.7090109@sympatico.ca> David Abrahams wrote: > This was fixed in the CVS shortly after 1.30 went out. ok, thanks, I'll update. Regards, Stefan From dominique.devriese at student.kuleuven.ac.be Tue Jul 15 15:34:09 2003 From: dominique.devriese at student.kuleuven.ac.be (Dominique Devriese) Date: Tue, 15 Jul 2003 15:34:09 +0200 Subject: [C++-sig] Re: plans for a bugfix release ? In-Reply-To: (David Abrahams's message of "Mon, 14 Jul 2003 14:18:52 -0400") References: <873chau27k.fsf@student.kuleuven.ac.be> Message-ID: <87oezvrk1a.fsf@student.kuleuven.ac.be> David Abrahams writes: >> Hi, >> >> I'm the main developer of Kig [1]. I have just committed the code >> for python scripting to the CVS repository > Using Boost.Python? Cool! Yups, I was going to post something separately about including it on the "projects using boost.python" page if you want, but well, erm.. if you want, feel free to include it on that page.. :) ( There's no released version with the scripting yet, but I consider the code itself to be pretty stable.. ) If you need more information, feel free to ask. >> Are there any plans to release a fixed version of Boost.Python any >> time soon > No specific plans, no. >> and what is the policy on Boost.Python releases in general ? > In general, they are released when all of Boost is ready. I think > it would be a *really* good idea for Boost to do at least one minor > version release shortly after any major version release. Now that > we have a reasonable testing strategy it should be relatively easy. > Boost 1.30.0 went out with several bugs IIRC. > Until we get our act together, I would suggest you supply people > with a Boost patch. Use "BOOST_DEDUCED_TYPENAME" instead of > "typename" so you don't break VC6. Sorry, A fixed release would be great indeed. In the mean time, I'm going to provide the patch as you suggest, although it's far from a perfect solution of course.. Thanks a lot domi From dave at boost-consulting.com Tue Jul 15 16:26:43 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 15 Jul 2003 10:26:43 -0400 Subject: [C++-sig] Re: plans for a bugfix release ? References: <873chau27k.fsf@student.kuleuven.ac.be> <87oezvrk1a.fsf@student.kuleuven.ac.be> Message-ID: Dominique Devriese writes: >> In general, they are released when all of Boost is ready. I think >> it would be a *really* good idea for Boost to do at least one minor >> version release shortly after any major version release. Now that >> we have a reasonable testing strategy it should be relatively easy. >> Boost 1.30.0 went out with several bugs IIRC. > >> Until we get our act together, I would suggest you supply people >> with a Boost patch. Use "BOOST_DEDUCED_TYPENAME" instead of >> "typename" so you don't break VC6. Sorry, > > A fixed release would be great indeed. In the mean time, I'm going to > provide the patch as you suggest, although it's far from a perfect > solution of course.. What does everybody think about doing a 1.30.1 release "RSN?" I don't think there's much to it, unless people have been checking things into the 1.30 branch unintentionally. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dominique.devriese at student.kuleuven.ac.be Tue Jul 15 20:58:05 2003 From: dominique.devriese at student.kuleuven.ac.be (Dominique Devriese) Date: Tue, 15 Jul 2003 20:58:05 +0200 Subject: [C++-sig] Re: plans for a bugfix release ? In-Reply-To: (David Abrahams's message of "Tue, 15 Jul 2003 10:26:43 -0400") References: <873chau27k.fsf@student.kuleuven.ac.be> <87oezvrk1a.fsf@student.kuleuven.ac.be> Message-ID: <878yqzr51e.fsf@student.kuleuven.ac.be> David Abrahams writes: > Dominique Devriese > writes: >>> In general, they are released when all of Boost is ready. I think >>> it would be a *really* good idea for Boost to do at least one >>> minor version release shortly after any major version release. >>> Now that we have a reasonable testing strategy it should be >>> relatively easy. Boost 1.30.0 went out with several bugs IIRC. >> >>> Until we get our act together, I would suggest you supply people >>> with a Boost patch. Use "BOOST_DEDUCED_TYPENAME" instead of >>> "typename" so you don't break VC6. Sorry, >> >> A fixed release would be great indeed. In the mean time, I'm going >> to provide the patch as you suggest, although it's far from a >> perfect solution of course.. > What does everybody think about doing a 1.30.1 release "RSN?" > I don't think there's much to it, unless people have been checking > things into the 1.30 branch unintentionally. If I might ask another thing: Would it be possible to include this patch too in the new release ? http://mail.python.org/pipermail/c++-sig/2003-April/003804.html thanks domi From dave at boost-consulting.com Tue Jul 15 21:33:20 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 15 Jul 2003 15:33:20 -0400 Subject: [C++-sig] Re: plans for a bugfix release ? In-Reply-To: <878yqzr51e.fsf@student.kuleuven.ac.be> (Dominique Devriese's message of "Tue, 15 Jul 2003 20:58:05 +0200") References: <873chau27k.fsf@student.kuleuven.ac.be> <87oezvrk1a.fsf@student.kuleuven.ac.be> <878yqzr51e.fsf@student.kuleuven.ac.be> Message-ID: Dominique Devriese writes: > If I might ask another thing: > Would it be possible to include this patch too in the new release ? > http://mail.python.org/pipermail/c++-sig/2003-April/003804.html Your patch is backwards, but in any case, it's already in the CVS trunk and I just applied it to RC_1_30_0. -- Dave Abrahams Boost Consulting www.boost-consulting.com From d.frey at gmx.de Tue Jul 15 23:38:12 2003 From: d.frey at gmx.de (Daniel Frey) Date: Tue, 15 Jul 2003 23:38:12 +0200 Subject: [C++-sig] Re: plans for a bugfix release ? References: <873chau27k.fsf@student.kuleuven.ac.be> <87oezvrk1a.fsf@student.kuleuven.ac.be> Message-ID: On Tue, 15 Jul 2003 16:26:43 +0200, David Abrahams wrote: > What does everybody think about doing a 1.30.1 release "RSN?" I think it's too late, let's go for a 1.31.0. I think that we'll hear about problems with the 1.31.0 really soon after release and probably a 1.31.1 can follow shortly after. For 1.30.0, we IMHO missed the opportunity do to a 1.30.1 without lots of pain/work. As Beman already said there is too much in CVS to "backport" it to a 1.30.1. The question is, whether we learn from it for a 1.31.1 :) My 2 cents... Regards, Daniel From dave at boost-consulting.com Wed Jul 16 02:32:24 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 15 Jul 2003 20:32:24 -0400 Subject: [C++-sig] Re: plans for a bugfix release ? References: <873chau27k.fsf@student.kuleuven.ac.be> <87oezvrk1a.fsf@student.kuleuven.ac.be> Message-ID: Daniel Frey writes: > On Tue, 15 Jul 2003 16:26:43 +0200, David Abrahams wrote: > >> What does everybody think about doing a 1.30.1 release "RSN?" > > I think it's too late, let's go for a 1.31.0. I think that we'll hear > about problems with the 1.31.0 really soon after release and probably a > 1.31.1 can follow shortly after. For 1.30.0, we IMHO missed the > opportunity do to a 1.30.1 without lots of pain/work. As Beman already > said there is too much in CVS to "backport" it to a 1.30.1. The question > is, whether we learn from it for a 1.31.1 :) I wouldn't dream of backporting everything we've done since 1.30.0. That would be pointless. There are just a few errors which prevent major portions of 1.30.0 from compiling. I backported all the important post-1.30.0 fixes immediately after hearing about them, but I'm not sure everyone else did. Note that 1.31.0 is going to be a code-breaking release for anyone who uses iterator adaptors, so it might be important for them to get a working 1.30.1. But anyway, I don't care that much. A .1 release is more work, and I'm all for avoiding work. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dholth at fastmail.fm Wed Jul 16 05:58:45 2003 From: dholth at fastmail.fm (Daniel Holth) Date: 15 Jul 2003 23:58:45 -0400 Subject: [C++-sig] introspecting functions Message-ID: <1058327924.12657.57.camel@bluefish> C++-siggers, I have looked into how pydoc works. It doesn't look too bad. Pydoc does a large part of its work using the inspect module to look at code objects. 'Real' Python functions have a func_code property. Example: >>> urlparse.urlsplit.func_code.co_varnames ('url', 'scheme', 'allow_fragments', 'i', 'cached', 'c', 'netloc', 'fragment', 'tuple', 'key', 'query') And the code for urlsplit is: def urlsplit(url, scheme='', allow_fragments=1): key = url, scheme, allow_fragments cached = _parse_cache.get(key, None) if cached: return cached if len(_parse_cache) >= MAX_CACHE_SIZE: # avoid runaway growth clear_cache() netloc = query = fragment = '' i = url.find(':') if i > 0: if url[:i] == 'http': # optimize the common case scheme = url[:i].lower() url = url[i+1:] if url[:2] == '//': i = url.find('/', 2) ...... and on it goes. Anyway, the first expression gives me all the variable names in the function. The first three .co_varnames appear to be the function argument names (.co_argcount). You can also retrieve the filename the function was compiled from and the bytecode for the function. I don't know what the consequences of using a fake func_code are and I would have played with it more but I don't know how to best add a func_code to my boost::python classes, but it's an interesting idea. You could probably figure out how to implement the equivalent of def foo(bar=1, baz=2) for the C++ for example. Whoah! Pydoc actually parses the bytecodes for classes in order to document what the default variable values are (not what the variable names are though). It mightn't be outrageous to compile lots of little def wrappedfunction(a, b=None): pass in order to make some bytecode though, or even replace : pass with : call_boost_function(). - Daniel Holth -------------- next part -------------- A non-text attachment was scrubbed... Name: not available Type: application/pgp-signature Size: 189 bytes Desc: This is a digitally signed message part URL: From lutz_p at gmx.net Wed Jul 16 15:11:17 2003 From: lutz_p at gmx.net (Lutz Paelike) Date: Wed, 16 Jul 2003 15:11:17 +0200 Subject: [C++-sig] debug version of boost.python loads the wrong python dll Message-ID: <3F154EF5.6060502@gmx.net> Hi all, i have the following problem: I use boost.python 1.30.0 to embed python into my program. I use VC++ 6 on windows 2000. Works great if i build a Release version , but if i want to use a debug version my program crashes with the following error: Fatal Python error: Interpreter not initialized (version mismatch?) i tracked this down and noticed that during loading the wrong dll is loaded. it doesn't matter if debug version or not it always loads python22.dll instead of python22_d.dll for the debug version. i guess that's causing the problem, but how can i solve it ? cheers, lutz From stefan.seefeld at orthosoft.ca Wed Jul 16 15:28:49 2003 From: stefan.seefeld at orthosoft.ca (Stefan Seefeld) Date: Wed, 16 Jul 2003 09:28:49 -0400 Subject: [C++-sig] implicit_convertible extension Message-ID: <95fd68aa739fde4901d8b23596d6bc5d3f155007@Orthosoft.ca> hi there, I'm browsing through the documentation as well as the mailing list archive to find the best way to convert between a C++ type (boost::posix_time::time_duration) and a python type (double). Conversion should happen implicitely, i.e. I have a bunch of functions taking a time_duration argument, which I want to be able to call in python passing simple doubles. Looking at the documentation for implicit_convertible, I find the requirements a bit restrictive. I think it may be convenient to be able to provide converter functions that do the conversion even if the two types themselfs are totally unaware of each other (i.e. no cast operators, no special constructors required). Then, instead of saying implicitly_convertible(); implicitly_convertible(); I would expect to say X double_to_X(double); double X_to_double(const X &); ... implicitly_convertible(X_to_double); implicitly_convertible(double_to_X); Does this make any sense ? Does something like this already exist ? Thanks, Stefan From stefan.seefeld at orthosoft.ca Wed Jul 16 16:17:30 2003 From: stefan.seefeld at orthosoft.ca (Stefan Seefeld) Date: Wed, 16 Jul 2003 10:17:30 -0400 Subject: [C++-sig] def() vs. add_property() Message-ID: hi there, I'v got a class that holds a reference to an external object, which is accessible through a simple method: class Origin {}; class Event { public: Event(const Origin *o) : my_origin(o) {} const Origin *GetOrigin() { return my_origin;} private: const Origin *my_origin; }; I can expose the 'Event' and 'Origin' classes, as well as &Event::GetOrigin, to python. However, I'd rather like to make the origin accessible as a (read-only) property. The problem is that the 'add_property' method doesn't take a return value policy, so I have no way of telling python how to wrap the pointer. What is the suggested way to do that ? Regards, Stefan From dave at boost-consulting.com Wed Jul 16 17:18:22 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 16 Jul 2003 11:18:22 -0400 Subject: [C++-sig] Re: debug version of boost.python loads the wrong python dll References: <3F154EF5.6060502@gmx.net> Message-ID: Lutz Paelike writes: > Hi all, > > i have the following problem: > > I use boost.python 1.30.0 to embed python into my program. I use VC++ 6 on windows 2000. > Works great if i build a Release version , but if i want to use a debug version my program > crashes with the following error: > > Fatal Python error: Interpreter not initialized (version mismatch?) > > i tracked this down and noticed that during loading the wrong dll is loaded. > it doesn't matter if debug version or not it always loads python22.dll instead of python22_d.dll > for the debug version. i guess that's causing the problem, but how can i solve it ? Does this answer your question? http://www.boost.org/libs/python/doc/building.html#variants -- Dave Abrahams Boost Consulting www.boost-consulting.com From lutz_p at gmx.net Wed Jul 16 17:52:56 2003 From: lutz_p at gmx.net (Lutz Paelike) Date: Wed, 16 Jul 2003 17:52:56 +0200 Subject: [C++-sig] Re: debug version of boost.python loads the wrong python dll In-Reply-To: References: <3F154EF5.6060502@gmx.net> Message-ID: <3F1574D8.6010903@gmx.net> > Does this answer your question? > > http://www.boost.org/libs/python/doc/building.html#variants > ah great. rtfm again. sorry for asking such an obviously documented thing. i was irritated by the fact that a debug version is generated even without extra build switches. thanks, lutz From rwgk at yahoo.com Wed Jul 16 18:11:03 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Wed, 16 Jul 2003 09:11:03 -0700 (PDT) Subject: [C++-sig] implicit_convertible extension In-Reply-To: <95fd68aa739fde4901d8b23596d6bc5d3f155007@Orthosoft.ca> Message-ID: <20030716161103.11132.qmail@web20208.mail.yahoo.com> --- Stefan Seefeld wrote: > I think it may be convenient to be able to provide converter > functions that do the conversion even if the two types themselfs > are totally unaware of each other (i.e. no cast operators, no > special constructors required). I believe currently the only solution is to use custom rvalue converters. Here is an example: http://mail.python.org/pipermail/c++-sig/2003-May/004133.html The recipe is a bit tedious but very powerful. > Then, instead of saying > > implicitly_convertible(); > implicitly_convertible(); > > I would expect to say > > X double_to_X(double); > double X_to_double(const X &); > > ... > > implicitly_convertible(X_to_double); > implicitly_convertible(double_to_X); > > Does this make any sense ? Does something like this already exist ? Very interesting idea. But I am not sure how the "convertible" test could work (see the custom rvalue converter example.) Ralf __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From dave at boost-consulting.com Wed Jul 16 18:07:27 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 16 Jul 2003 12:07:27 -0400 Subject: [C++-sig] Re: implicit_convertible extension References: <95fd68aa739fde4901d8b23596d6bc5d3f155007@Orthosoft.ca> Message-ID: Stefan Seefeld writes: > hi there, > > I'm browsing through the documentation as well as > the mailing list archive to find the best way to > convert between a C++ type (boost::posix_time::time_duration) > and a python type (double). > > Conversion should happen implicitely, i.e. I have a bunch > of functions taking a time_duration argument, which I want > to be able to call in python passing simple doubles. You mean floats, I think. That's the name of the Python floating-point type. > Looking at the documentation for implicit_convertible, > I find the requirements a bit restrictive. > > I think it may be convenient to be able to provide converter > functions that do the conversion even if the two types themselfs > are totally unaware of each other (i.e. no cast operators, no > special constructors required). That's what explicit converter registration is for. You want an rvalue from-python converter for time_duration which accepts Python floats. This is an undocumented feature, but if you investigate, http://www.boost.org/libs/python/doc/v2/faq.html#question2 will tell you how to go about doing it. > Does this make any sense ? Does something like this already exist ? Sorta. See above. -- Dave Abrahams Boost Consulting www.boost-consulting.com From rwgk at yahoo.com Wed Jul 16 18:15:31 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Wed, 16 Jul 2003 09:15:31 -0700 (PDT) Subject: [C++-sig] def() vs. add_property() In-Reply-To: Message-ID: <20030716161531.73175.qmail@web20203.mail.yahoo.com> --- Stefan Seefeld wrote: > However, I'd rather like to make the origin accessible > as a (read-only) property. The problem is that the > 'add_property' method doesn't take a return value policy, > so I have no way of telling python how to wrap the pointer. make_getter supports return-value policies: .add_property("origin", make_getter(&Event::origin, return_value_policy())) Ralf __________________________________ Do you Yahoo!? SBC Yahoo! DSL - Now only $29.95 per month! http://sbc.yahoo.com From sf.lists at web.de Wed Jul 16 18:15:18 2003 From: sf.lists at web.de (Stefan Fleiter) Date: Wed, 16 Jul 2003 18:15:18 +0200 Subject: [C++-sig] global variable Message-ID: <3F157A16.3080505@web.de> Hi, I am using pyste of boost.python to wrap a library. This library has an init function 'init' which allocates an object and sets a global pointer 'ptr' to it. This function can only be called once, so 'ptr' can or should never be changed. 1. How can I access 'ptr' or '*ptr'? 2. I have a function returning this 'ptr', what is the right call-Policy? Many thanks, Stefan From dave at boost-consulting.com Wed Jul 16 18:09:59 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 16 Jul 2003 12:09:59 -0400 Subject: [C++-sig] Re: def() vs. add_property() References: Message-ID: Stefan Seefeld writes: > hi there, > > I'v got a class that holds a reference to an external > object, which is accessible through a simple method: > > class Origin {}; > > class Event > { > public: > Event(const Origin *o) : my_origin(o) {} > const Origin *GetOrigin() { return my_origin;} > private: > const Origin *my_origin; > }; > > I can expose the 'Event' and 'Origin' classes, as well > as &Event::GetOrigin, to python. > However, I'd rather like to make the origin accessible > as a (read-only) property. The problem is that the > 'add_property' method doesn't take a return value policy, > so I have no way of telling python how to wrap the pointer. > > What is the suggested way to do that ? See make_getter/make_setter. You can pass their results to add_property. -- Dave Abrahams Boost Consulting www.boost-consulting.com From seefeld at sympatico.ca Wed Jul 16 21:25:37 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Wed, 16 Jul 2003 15:25:37 -0400 Subject: [C++-sig] Re: def() vs. add_property() References: Message-ID: <328c9f5c2be1aefc972ef86052b000d93f15a3ad@Orthosoft.ca> David Abrahams wrote: > Stefan Seefeld writes: > > >>hi there, >> >>I'v got a class that holds a reference to an external >>object, which is accessible through a simple method: >> >>class Origin {}; >> >>class Event >>{ >>public: >> Event(const Origin *o) : my_origin(o) {} >> const Origin *GetOrigin() { return my_origin;} >>private: >> const Origin *my_origin; >>}; >> >>I can expose the 'Event' and 'Origin' classes, as well >>as &Event::GetOrigin, to python. >>However, I'd rather like to make the origin accessible >>as a (read-only) property. The problem is that the >>'add_property' method doesn't take a return value policy, >>so I have no way of telling python how to wrap the pointer. >> >>What is the suggested way to do that ? > > > See make_getter/make_setter. You can pass their results to > add_property. > make_getter seems to expect a pointer-to-member, while I want a pointer-to-member-function. Am I missing something ? Stefan From camelo at esss.com.br Wed Jul 16 22:03:41 2003 From: camelo at esss.com.br (Marcelo A. Camelo) Date: Wed, 16 Jul 2003 17:03:41 -0300 Subject: [C++-sig] Compiling boost.python using intel and stlport on linux In-Reply-To: <328c9f5c2be1aefc972ef86052b000d93f15a3ad@Orthosoft.ca> Message-ID: <000001c34bd5$5abc6840$0d00000a@esss.com.br> I'm trying to compile boost.python on Linux using Intel compiler and STLport. Can someone please point me to some references or bjam documentation on how to do it? Any help will be appreciated!!! Marcelo A. Camelo, M. Eng. - Project Leader ESSS - Engineering Simulation and Scientific Software E-mail: camelo at esss.com.br Phone: +55-48-334-8922 From camelo at esss.com.br Wed Jul 16 22:22:28 2003 From: camelo at esss.com.br (Marcelo A. Camelo) Date: Wed, 16 Jul 2003 17:22:28 -0300 Subject: [C++-sig] Compiling boost.python using intel and stlport on linux In-Reply-To: <000001c34bd5$5abc6840$0d00000a@esss.com.br> Message-ID: <000101c34bd7$fa138160$0d00000a@esss.com.br> Hummm... a bit more of information. I can compile boost without problems using the intel-linux toolset. The problem is that I need to compile it using STL (intel's compaining standard library is not 100% conformant and does not implement some features we need in another part of our code base). All I need is a clean way to pass to icc the path to the icl header files. I could not figure it out by my self. I've tried to learn from "intel-win32-stlport-tools.jam" but it didn't help much. I've also tried to add the include directory to STDHDRS var in intel-linux-tools.jam and through bjam command line. No success there also. I know this must be a basic feature of bjam, but I could not learn how to do it. Marcelo A. Camelo, M. Eng. - Project Leader ESSS - Engineering Simulation and Scientific Software E-mail: camelo at esss.com.br Phone: +55-48-334-8922 -----Original Message----- From: c++-sig-admin at python.org [mailto:c++-sig-admin at python.org] On Behalf Of Marcelo A. Camelo Sent: quarta-feira, 16 de julho de 2003 17:04 To: c++-sig at python.org Subject: [C++-sig] Compiling boost.python using intel and stlport on linux I'm trying to compile boost.python on Linux using Intel compiler and STLport. Can someone please point me to some references or bjam documentation on how to do it? Any help will be appreciated!!! Marcelo A. Camelo, M. Eng. - Project Leader ESSS - Engineering Simulation and Scientific Software E-mail: camelo at esss.com.br Phone: +55-48-334-8922 _______________________________________________ C++-sig mailing list C++-sig at python.org http://mail.python.org/mailman/listinfo/c++-sig From dave at boost-consulting.com Wed Jul 16 22:55:55 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 16 Jul 2003 16:55:55 -0400 Subject: [C++-sig] Re: def() vs. add_property() References: <328c9f5c2be1aefc972ef86052b000d93f15a3ad@Orthosoft.ca> Message-ID: Stefan Seefeld writes: > David Abrahams wrote: >> Stefan Seefeld writes: >> >>>hi there, >>> >>>I'v got a class that holds a reference to an external >>>object, which is accessible through a simple method: >>> >>>class Origin {}; >>> >>>class Event >>>{ >>>public: >>> Event(const Origin *o) : my_origin(o) {} >>> const Origin *GetOrigin() { return my_origin;} >>>private: >>> const Origin *my_origin; >>>}; >>> >>>I can expose the 'Event' and 'Origin' classes, as well >>>as &Event::GetOrigin, to python. >>>However, I'd rather like to make the origin accessible >>>as a (read-only) property. The problem is that the >>>'add_property' method doesn't take a return value policy, >>>so I have no way of telling python how to wrap the pointer. >>> >>>What is the suggested way to do that ? >> See make_getter/make_setter. You can pass their results to >> add_property. >> > > make_getter seems to expect a pointer-to-member, while I > want a pointer-to-member-function. Am I missing something ? http://www.boost.org/libs/python/doc/v2/make_function.html? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dominique.devriese at student.kuleuven.ac.be Thu Jul 17 10:50:19 2003 From: dominique.devriese at student.kuleuven.ac.be (Dominique Devriese) Date: Thu, 17 Jul 2003 10:50:19 +0200 Subject: [C++-sig] Re: plans for a bugfix release ? In-Reply-To: (David Abrahams's message of "Tue, 15 Jul 2003 20:32:24 -0400") References: <873chau27k.fsf@student.kuleuven.ac.be> <87oezvrk1a.fsf@student.kuleuven.ac.be> Message-ID: <87znjdlepg.fsf@student.kuleuven.ac.be> David Abrahams writes: > I wouldn't dream of backporting everything we've done since 1.30.0. > That would be pointless. There are just a few errors which prevent > major portions of 1.30.0 from compiling. I backported all the > important post-1.30.0 fixes immediately after hearing about them, > but I'm not sure everyone else did. > Note that 1.31.0 is going to be a code-breaking release for anyone > who uses iterator adaptors, so it might be important for them to get > a working 1.30.1. > But anyway, I don't care that much. A .1 release is more work, and > I'm all for avoiding work. Could you give an estimate of when 1.31.0 will be released, please ? thanks domi From dave at boost-consulting.com Thu Jul 17 14:02:48 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 17 Jul 2003 08:02:48 -0400 Subject: [C++-sig] Re: plans for a bugfix release ? References: <873chau27k.fsf@student.kuleuven.ac.be> <87oezvrk1a.fsf@student.kuleuven.ac.be> <87znjdlepg.fsf@student.kuleuven.ac.be> Message-ID: Dominique Devriese writes: > Could you give an estimate of when 1.31.0 will be released, please ? > thanks > domi I can't do better than "pretty soon, probably". Sorry, -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 17 16:16:13 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 17 Jul 2003 10:16:13 -0400 Subject: [C++-sig] Re: Compiling boost.python using intel and stlport on linux References: <000001c34bd5$5abc6840$0d00000a@esss.com.br> <000101c34bd7$fa138160$0d00000a@esss.com.br> Message-ID: "Marcelo A. Camelo" writes: > Hummm... a bit more of information. > > I can compile boost without problems using the intel-linux > toolset. The problem is that I need to compile it using STL > (intel's compaining standard library is not 100% conformant > and does not implement some features we need in another part > of our code base). > > All I need is a clean way to pass to icc the path to the icl > header files. I could not figure it out by my self. > > I've tried to learn from "intel-win32-stlport-tools.jam" but > it didn't help much. I've also tried to add the include > directory to STDHDRS var in intel-linux-tools.jam and through > bjam command line. No success there also. > > I know this must be a basic feature of bjam, but I could not > learn how to do it. Try making a toolset like this one: # # intel-linux-stlport-tools.jam # extends-toolset intel-linux ; STDHDRS = path/to/stlport/headers $(STDHDRS) ; # I think you need this too LIBPATH += path/to/stlport/lib ; FINDLIBS += stlport- ; That should get you most of the way there. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dleary at ttlc.net Thu Jul 17 21:41:04 2003 From: dleary at ttlc.net (Dusty Leary) Date: Thu, 17 Jul 2003 15:41:04 -0400 Subject: [C++-sig] reference counting pointers References: <000001c34bd5$5abc6840$0d00000a@esss.com.br> <000101c34bd7$fa138160$0d00000a@esss.com.br> Message-ID: <000301c34c9b$5c0e2aa0$4d00a8c0@eigensoft.net> Hi, Can someone give me example of a ResultConvertorGenerator (or whatever is required) so that addref/decref calls get called on an object? Currently, I am using boost::intrusive_ptr, which does almost what I want. All my class bindings are defined like so: class_ >("A"); class_, bases >("B"); etc... The problem is that functions which accept an intrusive_ptr, when called with an intrusive_ptr, cause boost.python errors (no valid type found). So, I would like to replace most of the uses of intrusive_ptr with A* (in method signatures), and just have my C++ implementations use intrusive_ptr internally. This way, the polymorphic thing will work out ok, with boost wrapping B* and calling foo(A*) rather than wrapping intrusive_ptr and failing to call foo(intrusive_ptr). From dave at boost-consulting.com Fri Jul 18 01:57:04 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 17 Jul 2003 19:57:04 -0400 Subject: [C++-sig] Re: reference counting pointers References: <000001c34bd5$5abc6840$0d00000a@esss.com.br> <000101c34bd7$fa138160$0d00000a@esss.com.br> <000301c34c9b$5c0e2aa0$4d00a8c0@eigensoft.net> Message-ID: "Dusty Leary" writes: > Hi, > > Can someone give me example of a ResultConvertorGenerator (or whatever is > required) so that addref/decref calls get called on an object? > > Currently, I am using boost::intrusive_ptr, which does almost what I want. > > All my class bindings are defined like so: class_ >>("A"); class_, bases >("B"); etc... > > The problem is that functions which accept an intrusive_ptr, when called > with an intrusive_ptr, cause boost.python errors (no valid type found). Try implicitly_convertible, intrusive_ptr >(); Of course, if you just use shared_ptr instead, none of that is needed ;-) > So, I would like to replace most of the uses of intrusive_ptr > with A* (in method signatures), and just have my C++ implementations > use intrusive_ptr internally. This way, the polymorphic thing will > work out ok, with boost wrapping B* and calling foo(A*) rather than > wrapping intrusive_ptr and failing to call foo(intrusive_ptr). If you really want to do that, the only way is to write thin wrapper functions for each [member] function you're wrapping. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dleary at ttlc.net Fri Jul 18 06:46:44 2003 From: dleary at ttlc.net (Dusty Leary) Date: Fri, 18 Jul 2003 00:46:44 -0400 Subject: [C++-sig] Re: reference counting pointers References: <000001c34bd5$5abc6840$0d00000a@esss.com.br> <000101c34bd7$fa138160$0d00000a@esss.com.br> <000301c34c9b$5c0e2aa0$4d00a8c0@eigensoft.net> Message-ID: <000401c34ce7$96d28040$c82aa8c0@dust2k> > > Try > > implicitly_convertible, intrusive_ptr >(); > > Of course, if you just use shared_ptr instead, none of that is needed > ;-) > why does it work automatically with shared_ptr and not with intrusive_ptr? From pierre.barbier at cirad.fr Fri Jul 18 14:51:25 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Fri, 18 Jul 2003 14:51:25 +0200 Subject: [C++-sig] Segfault when calling python method from C++ Message-ID: <3F17ED4D.9010303@cirad.fr> I have an embedded python in a C++ program. I extend python using boost in order to interact with C++. Some of my methods makes use of C++ function-object. So I implemented this class to encapsulate Python methods : ***************************************************** struct PyCenterComp { PyCenterComp( boost::python::object o ); PyCenterComp( const PyCenterComp& copy ); vertex_type operator()( Delaunay2D::cell_descriptor cell ); boost::python::object method; }; PyCenterComp::PyCenterComp( object o ) : method( o ) { } PyCenterComp::PyCenterComp( const PyCenterComp& copy ) : method( copy.method ) { } vertex_type PyCenterComp::operator()( Delaunay2D::cell_descriptor cell ) { std::cerr << "Call method ... " << endl; boost::python::object o( method( cell_descriptor( cell ) ) ); std::cerr << "Called" << endl; extract v( o ); std::cerr << "Converted" << endl; if( v.check() ) { return v(); } return vertex_type(); } ******************************************* The Delaunay2D::cell_descriptor being implemented as void*, it's encapsulated in a cell_descriptor structure which is exported in Python. In the python interpreter I created a function object with this code : ******************************************* class ProdMean: def __init__(self, walls): self.walls = walls def __call__(self,cell): poly = self.walls.getCell(cell) return self.mean(poly) def mean(self, poly): dx = 1 dy = 1 for i in poly: dx = dx * i.x() dy = dy * i.y() dx = dx ** (1.0/len(poly)) dy = dy ** (1.0/len(poly)) return vertex_type(dx,dy) ******************************************* Then I can use this class with : p = ProdMean(walls) l = [p(i) for i in walls] walls is a C++ object (a graph) and the getCell method returns a polygon (a vector of vertex). This little python code works well. But now, if I try to call p from C++ using the PyCenterComp object I get a segmentation fault when calling the method (I got this output: Call method ... zsh: segmentation fault ) If you want, I can give you the callstack when the crash occure, but it's quite huge (~50 elements ... ) so I'll do only if it's needed. Thanks, -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From pierre.barbier at cirad.fr Fri Jul 18 16:32:07 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Fri, 18 Jul 2003 16:32:07 +0200 Subject: [C++-sig] Segfault when calling python method from C++ In-Reply-To: <3F17ED4D.9010303@cirad.fr> References: <3F17ED4D.9010303@cirad.fr> Message-ID: <3F1804E7.4080800@cirad.fr> Some more details ... I made some experiment and it appears that if I use an ob ject of the class : ****************************** class EmptyMean: def __init__(self,walls): self.walls = walls def __call__(self,cell): poly = self.walls.getCell(cell) l = len(poly) return vertex_type(l,l) *********************************** as a parameter for my C++ method, it works. But if I use : ****************************** class EmptyMean: def __init__(self,walls): self.walls = walls def __call__(self,cell): poly = self.walls.getCell(cell) return poly[0] *********************************** it crashes ! poly is an exported vector. I exported it so that it has the same behaviour as a python list. Here is the code of the __getitem__ method used to export the vector to python : *************************************************************************** template typename container_trait::value_type list_getItem(ToExport* exp, typename container_trait::difference_type i) { typename container_trait::iterator it; it = PosInRange(exp, i); return *it; } template typename container_trait::iterator PosInRange(ToExport *l, typename container_trait::difference_type i) { typename container_trait::difference_type size = l->size(); if((i >= size) || (i < -size)) { PythonExc_IndexError ind; ind.error_str = "assignment index out of range"; throw ind; } if(i < 0) { typename container_trait::difference_type size = l->size(); i += size; } typename container_trait::iterator it = l->begin(); advance(it, i); return it; } ********************************************************************* The template parameter ToExport is here std::vector. container_trait >::iterator is std::vector::iterator container_trait >::difference_type is std::vector::difference_type container_trait >::iterator is std::vector::iterator I'm still looking for more precise information, but I still have absolutely no clue abour what is going on ... -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From dave at boost-consulting.com Fri Jul 18 18:16:55 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 18 Jul 2003 12:16:55 -0400 Subject: [C++-sig] Re: reference counting pointers References: <000001c34bd5$5abc6840$0d00000a@esss.com.br> <000101c34bd7$fa138160$0d00000a@esss.com.br> <000301c34c9b$5c0e2aa0$4d00a8c0@eigensoft.net> <000401c34ce7$96d28040$c82aa8c0@dust2k> Message-ID: "Dusty Leary" writes: >> >> Try >> >> implicitly_convertible, intrusive_ptr >(); >> >> Of course, if you just use shared_ptr instead, none of that is needed >> ;-) >> > > why does it work automatically with shared_ptr and not with intrusive_ptr? Because shared_ptr is special, and can do so safely. The shared pointer always manages the owning Python object, while intrusive_ptr can't do that, and there's no guarantee that a derived-to-base conversion on intrusive_ptr is safe (there might be no virtual destructor in the base class). -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 18 18:18:27 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 18 Jul 2003 12:18:27 -0400 Subject: [C++-sig] Re: Segfault when calling python method from C++ References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > I'm still looking for more precise information, but I still have > absolutely no clue abour what is going on ... Please post a small reproducible test case. -- Dave Abrahams Boost Consulting www.boost-consulting.com From pierre.barbier at cirad.fr Fri Jul 18 22:42:24 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Fri, 18 Jul 2003 22:42:24 +0200 Subject: [C++-sig] Re: Segfault when calling python method from C++ In-Reply-To: References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> Message-ID: <3F185BB0.6000903@cirad.fr> David Abrahams wrote: >Pierre Barbier de Reuille writes: > > > >>I'm still looking for more precise information, but I still have >>absolutely no clue abour what is going on ... >> >> > >Please post a small reproducible test case. > > > Ok, I did find the problem and it was on my side. My main problem was to locate it because it was within C++ code called by python code called by C++ code called by python code ... and I'm absolutely not used to debug such multi-language system ! If you want to know, the problem was in the class wrapping the cell_descriptor ... By the way, I've made some tools to export my classes, where can I submit them ? Here ? I have come classes using Qt and POSIX pipes to embed python in a C++ environment, some tools to solve Qt non-thread safe problems and templates to export STL containers (not all but most ...). Thanks anyway, -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From dave at boost-consulting.com Sat Jul 19 14:57:54 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 19 Jul 2003 08:57:54 -0400 Subject: [C++-sig] Re: Segfault when calling python method from C++ References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > David Abrahams wrote: > >>Pierre Barbier de Reuille writes: >> >> >>>I'm still looking for more precise information, but I still have >>>absolutely no clue abour what is going on ... >>> >> >>Please post a small reproducible test case. > > Ok, I did find the problem and it was on my side. Works every time > My main problem was to locate it because it was within C++ code > called by python code called by C++ code called by python code ... > and I'm absolutely not used to debug such multi-language system ! If > you want to know, the problem was in the class wrapping the > cell_descriptor ... > > By the way, I've made some tools to export my classes, where can I > submit them ? Here ? I have come classes using Qt and POSIX pipes to > embed python in a C++ environment, some tools to solve Qt non-thread > safe problems and templates to export STL containers (not all but most > ...). You can post them here. After we discuss and get comfortable with your approach, the first things I'll probably ask you for are tests for the Boost.Python test suite and HTML documentation pages. Regards, -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sun Jul 20 01:51:02 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 19 Jul 2003 19:51:02 -0400 Subject: [C++-sig] Re: return_self_policy / return_arg References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> Message-ID: Nikolay, The stuff is checked in. I added your name to the copyright notices and made a few minor changes to the interface. The HTML needed a lot of work; please validate with something like HTMLTidy in the future. Returning 0 from the ResultConverter seemed problematic, so I changed it to return None. Thanks for the contribution! -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Sun Jul 20 01:53:09 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 19 Jul 2003 19:53:09 -0400 Subject: [C++-sig] Re: (return_self_policy / return_arg): Keywors References: <3EF7D45C.7D819158@sitius.com> <3EF85503.38A43BC6@sitius.com> <3EFCAD1B.BFA2AA5B@sitius.com> <3EFCD807.F82FD757@sitius.com> <3EFF5270.788370C2@sitius.com> <3EFF8D49.9492CA00@sitius.com> <3F00B85C.FD8AD186@sitius.com> <3F05B3A9.7B2F29E8@sitius.com> <3F062D00.65E0B4D6@sitius.com> <3F0643ED.2FC59290@sitius.com> Message-ID: David Abrahams writes: >> So, do you feel we have differences left about the keywords? > > Nope. Nikolay, do you have a final set of patches for me? Thanks, Dave -- Dave Abrahams Boost Consulting www.boost-consulting.com From brett.calcott at paradise.net.nz Sun Jul 20 06:43:21 2003 From: brett.calcott at paradise.net.nz (Brett Calcott) Date: Sun, 20 Jul 2003 14:43:21 +1000 Subject: [C++-sig] Re: Explaining the Magic References: Message-ID: Sorry for the late reply, I disappeared to Sydney for a week, with no email access. > I only have time for a "off-the-top-of-my-head" answer at the moment; > I suggest you step through the code with a debugger after reading this > to see how it works, fill in details, and make sure I didn't forget > anything. > The top-of-your-head seems pretty good to me. I'll dig into this over the next week. As Arnie says: "I'll be back". (sorry, just saw T3) > > Well, this should give you plenty to chew on for a while. > Indeed. Just hope I don't get a case of indigestion :) Cheers, Brett From m.kakaris at nki.nl Mon Jul 21 12:37:43 2003 From: m.kakaris at nki.nl (Mattheos Kakaris) Date: 21 Jul 2003 12:37:43 +0200 Subject: [C++-sig] importing module Message-ID: <1058783863.5132.60.camel@spar.nki.nl> while running bjam in the boost_1_30_0/libs/python/example/tutorial folder for the hello.cpp example it creates the following directory structure: /bin/hello.so/gcc/debug/runtime-link-dynamic/shared-linkable-true When running Python and trying to import module hello, it rightfully gives the message: ImportError: No module named hello What should I do so that python will always know were to look for the module? Kind regards Mat From dave at boost-consulting.com Mon Jul 21 16:42:31 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 21 Jul 2003 10:42:31 -0400 Subject: [C++-sig] Re: importing module References: <1058783863.5132.60.camel@spar.nki.nl> Message-ID: Mattheos Kakaris writes: > while running bjam in the boost_1_30_0/libs/python/example/tutorial > folder for the hello.cpp example it creates the following directory > structure: > /bin/hello.so/gcc/debug/runtime-link-dynamic/shared-linkable-true > > When running Python and trying to import module hello, it rightfully gives the > message: > ImportError: No module named hello > > What should I do so that python will always know were to look for > the module? You can set your PYTHONPATH environment variable to contain the directory where the module is created, or you can add the following line to your Jamfile: stage . : hello ; and it will be copied into the current directory. Joel, you probably ought to add this stage line to the tutorial, eh? -- Dave Abrahams Boost Consulting www.boost-consulting.com From nksauter at lbl.gov Mon Jul 21 23:41:49 2003 From: nksauter at lbl.gov (Nicholas K. Sauter) Date: Mon, 21 Jul 2003 14:41:49 -0700 Subject: [C++-sig] voice mail web interface down References: <20030702205350.86160.qmail@web20209.mail.yahoo.com> Message-ID: <3F1C5E1D.BC2585DC@lbl.gov> Ralf, Could you please call me at work? I need the procedure for accessing voice mail by telephone. Nick From djowel at gmx.co.uk Tue Jul 22 00:23:33 2003 From: djowel at gmx.co.uk (Joel de Guzman) Date: Tue, 22 Jul 2003 06:23:33 +0800 Subject: [C++-sig] Re: importing module References: <1058783863.5132.60.camel@spar.nki.nl> Message-ID: "David Abrahams" wrote in message news:uvftwuejs.fsf at boost-consulting.com > The following message is a courtesy copy of an article > that has been posted to gmane.comp.python.c++ as well. > > Mattheos Kakaris writes: > >> while running bjam in the boost_1_30_0/libs/python/example/tutorial >> folder for the hello.cpp example it creates the following directory >> structure: >> /bin/hello.so/gcc/debug/runtime-link-dynamic/shared-linkable-true >> >> When running Python and trying to import module hello, it rightfully gives >> the message: >> ImportError: No module named hello >> >> What should I do so that python will always know were to look for >> the module? > > You can set your PYTHONPATH environment variable to contain the > directory where the module is created, or you can add the following > line to your Jamfile: > > stage . : hello ; > > and it will be copied into the current directory. > > Joel, you probably ought to add this stage line to the tutorial, eh? Ok, great. Thanks. -- -- Joel de Guzman joel at boost-consulting.com http://www.boost-consulting.com http://spirit.sf.net From dave at boost-consulting.com Tue Jul 22 02:11:46 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 21 Jul 2003 20:11:46 -0400 Subject: [C++-sig] GCC type demangling and better error messages Message-ID: Hi, Yesterday I checked in changes which cause types to print in human-readable format with GCC >= 3.1. I have just checked in major changes which provide all the infrastructure for printing readable error messages when no overload matches a call, a project which we are doing under contract to LBL. Expect to see real results in the next couple of days. Major improvements to the health of the CVS state on many different compilers were also made. Greetings, Dave -- Dave Abrahams Boost Consulting www.boost-consulting.com From drlinux at columbus.rr.com Tue Jul 22 04:25:49 2003 From: drlinux at columbus.rr.com (Dave Reed) Date: Mon, 21 Jul 2003 22:25:49 -0400 Subject: [C++-sig] libraries and source install required to use Boost python? Message-ID: <200307212225.49387.drlinux@columbus.rr.com> I've just tried boost last week so I'm not up on all the details yet. First, thanks to all the developers - I'm very impressed and looking forward to using it more. I finally got it to work in a separate directory using a Jamfile with based on the "project" example. My C++ code uses OpenGL so by looking at examples, it seems I need to add: <*>GLU <*>GL Is this the correct way to do it (it appears to work fine)? What if the library is in a non-standard place - do you specify -I and -L compiler flags somehow? I didn't see much documentation on creating Jamfiles. Is there specific documentation on these type of things? I'm also uncertain what the comments in the Jamrules file are saying: # Establish the root of the boost installation. Most targets will want # $(BOOST_ROOT) in their #include path. $(gTOP) is the name of the variable # containing the path from the invocation directory to the project root. path-global BOOST_ROOT : $($(gTOP))/../../.. ; What include path is it talking about? Should I get setting CFLAGS to -I//usr/local/src/boost_1_30_0 Also, I just downloaded the latest Red Hat beta and it now includes boost for the first time (or at least part of it). On my other system where I installed boost from scratch, I've got a boost-build.jam that points to where boost is installed. boost-build.jam # Specify path to the boost build system BOOST_ROOT = /usr/local/src/boost_1_30_0 ; boost-build /usr/local/src/boost_1_30_0/tools/build ; I'm not certain what to do on the Red Hat beta system since there's no source. Here's the RPMS they've split it into: boost-1.30.0-3 boost-devel-1.30.0-3 boost-doc-1.30.0-3 boost-jam-3.1.4-2 boost-python-1.30.0-3 boost-python-devel-1.30.0-3 I can post a list of the files (rpm -ql for each rpm) from the boost RPMS if anyone wants or put them on a web site. Thanks, Dave From dave at boost-consulting.com Tue Jul 22 13:54:28 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 22 Jul 2003 07:54:28 -0400 Subject: [C++-sig] Re: libraries and source install required to use Boost python? References: <200307212225.49387.drlinux@columbus.rr.com> Message-ID: Dave, you're in the wrong group with these questions. Please repost to the Jamboost group (where I've cross-posted this message). Dave Reed writes: > I've just tried boost last week so I'm not up on all the details > yet. First, thanks to all the developers - I'm very impressed and > looking forward to using it more. I finally got it to work in a > separate directory using a Jamfile with based on the "project" > example. > > My C++ code uses OpenGL so by looking at examples, it seems I need to > add: > > <*>GLU > <*>GL > > Is this the correct way to do it (it appears to work fine)? That will put -lGLU and -lGL in your GCC command-line. Not sure if that's what you want to achieve... > What if the library is in a non-standard place - do you specify -I some/path > and -L compiler flags somehow? some/other/path > I didn't see much documentation on creating Jamfiles. Is there > specific documentation on these type of things? I think it's weak and sparse in that area, at best. Check the examples/v1 directory for what you're interested in. > I'm also uncertain what the comments in the Jamrules file are saying: > > # Establish the root of the boost installation. Most targets will want > # $(BOOST_ROOT) in their #include path. $(gTOP) is the name of the > # variable > # containing the path from the invocation directory to the project root. > path-global BOOST_ROOT : $($(gTOP))/../../.. ; > > What include path is it talking about? One that gets specified on the command-line, usually with "-I". Setting up that variable allows you to write: $(BOOST_ROOT) in a target's requirements section in a Jamfile. > Should I get setting CFLAGS to -I//usr/local/src/boost_1_30_0 Nope. CFLAGS doesn't have any effect in Boost Build. > Also, I just downloaded the latest Red Hat beta and it now includes > boost for the first time (or at least part of it). On my other system > where I installed boost from scratch, I've got a boost-build.jam that > points to where boost is installed. > > boost-build.jam > # Specify path to the boost build system > BOOST_ROOT = /usr/local/src/boost_1_30_0 ; > boost-build /usr/local/src/boost_1_30_0/tools/build ; > > I'm not certain what to do on the Red Hat beta system since there's no > source. Here's the RPMS they've split it into: > > boost-1.30.0-3 > boost-devel-1.30.0-3 > boost-doc-1.30.0-3 > boost-jam-3.1.4-2 > boost-python-1.30.0-3 > boost-python-devel-1.30.0-3 > > I can post a list of the files (rpm -ql for each rpm) from the boost > RPMS if anyone wants or put them on a web site. I'm guessing the sources are in the boost-devel package. -- Dave Abrahams Boost Consulting www.boost-consulting.com From spex66 at gmx.net Tue Jul 22 17:54:15 2003 From: spex66 at gmx.net (spex66 at gmx.net) Date: Tue, 22 Jul 2003 17:54:15 +0200 (MEST) Subject: [C++-sig] Re: is_polymorphic and unions (was: Pyste and STL types) Message-ID: <31026.1058889255@www61.gmx.net> Hi Nicodemus Hi Dave I've read all your threads belonging to pyste / boost / union actually I've a project with a lot of such unions as you described. The project is from www.sedris.org for a standardised api for geometric & georeferenced data... and I want to port them as quick as possible to python :) so I'm using pyste--AllFromHeader('xxx.h') approach 36 hours from starting yesterday... I'm stuck with a sort of problems (1) error C1204:Compiler limit:internal structure overflow (as described in boost/faq) (2) error C2664: problem with call_policy (?) (3) error C2504: in ..../type_traits/is_polymorphic.hpp (79) ---> problem of a union solution to (1) is obviously splitting... sigh -> any chance to got this as a feature from pyste, Nicodemus? solution to (2) is pending... detailled description is following (also for (3)): ::::::::::::::::::::::::::::::::::: PYSTE::>> sedris.cpp def("SRM_ChangeCoordinateSRF", &SRM_ChangeCoordinateSRF); ::::::::::::::::::::::::::::::::::: ERROR::>> boost/python/make_function.hpp(77) : error C2664: 'struct boost::mpl::list4 __cdecl boost::python::detail::get_signature( short(__cdecl *)(struct SRM_SRFParamsPair * ,const SRM_Coordinate *,SRM_Coordinate *))' : can not convert parameter 1 from' short (__cdecl *)(struct SRM_SRFParamsPair *const ,const SRM_Coordinate *,SRM_Coordinate *)' in short (__cdecl *)(struct SRM_SRFParamsPair * ,const SRM_Coordinate *,SRM_Coordinate *)' This conversion requires a reinterpret_cast, a C-style cast or function-style cast ::::::::::::::::::::::::::::::::::: SOURCE::>> for (2): **snippet from file:: srm.h & srm_types.h** EXPORT_DLL extern SRM_Status_Code SRM_ChangeCoordinateSRF ( const SRM_SRF_Parameters_Pair coord_op_params_ptr, const SRM_Coordinate *source_coord_ptr, SRM_Coordinate *dest_coord_ptr ); typedef struct SRM_SRFParamsPair *SRM_SRF_Parameters_Pair; typedef struct { SRM_Dimensionality dimensionality; union { SRM_Coordinate_2D two_d; SRM_Coordinate_3D three_d; } coordinate; } SRM_Coordinate; **end of snippet from file:: srm.h & srm_types.h** ::::::::::::::::::::::::::::::::::: PYSTE::>>sedris.cpp class_< SRM_SRF_Parameters >("SRM_SRF_Parameters", init< >()) .def(init< const SRM_SRF_Parameters & >()) .def_readwrite("dimensionality", &SRM_SRF_Parameters::dimensionality) .def_readwrite("parameters", &SRM_SRF_Parameters::parameters) ; ::::::::::::::::::::::::::::::::::: ERROR::>> error C2504: in ..../type_traits/is_polymorphic.hpp (79) ---> problem of a union ::::::::::::::::::::::::::::::::::: SOURCE::>>for (3): **snippet from file:: srm_types.h** typedef struct { SRM_Dimensionality dimensionality; union { SRM_SRF_Parameters_2D two_d; SRM_SRF_Parameters_3D three_d; } parameters; } SRM_SRF_Parameters; **end of snippet from file:: srm_types.h** TRY&ERROR::>> I've tried to adopt Dave's tip from http://mail.python.org/pipermail/c++-sig/2003-March/003607.html > If so, then we have a bug in is_polymorphic. If not, we should > change all uses of is_polymorphic in > > boost/python/class.hpp > boost/python/object/class_converters.hpp > boost/python/object/inheritance.hpp > > to: > mpl::and_, is_polymorphic > putting #include for mpl::_and but boost wan't compile (if you need the error-trace, I will post it on demand) so I'm stuck with UNION, and have no C/C++ wrapper-idea cause of a massive lack of C-knowledge... sorry hot-blood pythonista ;) any hints to direct me to a path to the light is very appreciated! thanks for your patience Peter (=PA=) From dave at boost-consulting.com Tue Jul 22 18:59:11 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 22 Jul 2003 12:59:11 -0400 Subject: [C++-sig] Re: is_polymorphic and unions References: <31026.1058889255@www61.gmx.net> Message-ID: spex66 at gmx.net writes: > Hi Nicodemus > Hi Dave Hi! > I've read all your threads belonging to pyste / boost / union > > actually I've a project with a lot of such unions as you described. > > The project is from www.sedris.org for a standardised api for > geometric & georeferenced data... and I want to port them as quick > as possible to python :) > > so I'm using pyste--AllFromHeader('xxx.h') approach > > 36 hours from starting yesterday... I'm stuck with a sort of problems > > (1) error C1204:Compiler limit:internal structure overflow (as described in > boost/faq) > (2) error C2664: problem with call_policy (?) > (3) error C2504: in ..../type_traits/is_polymorphic.hpp (79) ---> problem of > a union > > solution to (1) is obviously splitting... sigh -> any chance to got this as > a feature from pyste, Nicodemus? The current CVS includes support for "--multiple": http://tinyurl.com/hp3j > solution to (2) is pending... detailled description is following (also for > (3)): > > ::::::::::::::::::::::::::::::::::: > PYSTE::>> sedris.cpp > def("SRM_ChangeCoordinateSRF", &SRM_ChangeCoordinateSRF); > > ::::::::::::::::::::::::::::::::::: > ERROR::>> > boost/python/make_function.hpp(77) : error C2664: > 'struct boost::mpl::list4 struct SRM_SRFParamsPair *, > struct SRM_Coordinate const *, > struct SRM_Coordinate * > > __cdecl boost::python::detail::get_signature( > short(__cdecl *)(struct SRM_SRFParamsPair * ,const SRM_Coordinate > *,SRM_Coordinate *))' : > > can not convert parameter 1 from' > short (__cdecl *)(struct SRM_SRFParamsPair *const ,const SRM_Coordinate > *,SRM_Coordinate *)' > in > short (__cdecl *)(struct SRM_SRFParamsPair * ,const SRM_Coordinate > *,SRM_Coordinate *)' > > This conversion requires a reinterpret_cast, a C-style cast or > function-style cast This is an msvc bug which preserves top-level constness of arguments in function (pointer) types. If you can redeclare the offending function as: short SRM_ChangeCoordinateSRF(SRM_SRF_Parameters_Pair, const SRM_Coordinate *,SRM_Coordinate *); you can still make the first parameter const in the function *definition* without upsetting the compiler. If you can't change the declaration of 'whatever' you'll have to resort to forcibly casting the offending function pointer. I suppose Pyste could be patched to do this for you... > ::::::::::::::::::::::::::::::::::: > ERROR::>> > error C2504: in ..../type_traits/is_polymorphic.hpp (79) ---> problem of a > union What's the complete error message for that line? > > TRY&ERROR::>> > I've tried to adopt Dave's tip from > http://mail.python.org/pipermail/c++-sig/2003-March/003607.html > >> If so, then we have a bug in is_polymorphic. If not, we should >> change all uses of is_polymorphic in >> >> boost/python/class.hpp >> boost/python/object/class_converters.hpp >> boost/python/object/inheritance.hpp >> >> to: >> mpl::and_, is_polymorphic > > > putting #include for mpl::_and > but boost wan't compile (if you need the error-trace, I will post it on > demand) #include works for me. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Tue Jul 22 22:13:57 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 22 Jul 2003 16:13:57 -0400 Subject: [C++-sig] Re: GCC type demangling and better error messages References: Message-ID: David Abrahams writes: > Hi, > > Yesterday I checked in changes which cause types to print in > human-readable format with GCC >= 3.1. I have just checked in major > changes which provide all the infrastructure for printing readable > error messages when no overload matches a call, a project which we are > doing under contract to LBL. Expect to see real results in the next > couple of days. Done and checked into CVS. Please enjoy! -- Dave Abrahams Boost Consulting www.boost-consulting.com From spex66 at gmx.net Wed Jul 23 00:59:56 2003 From: spex66 at gmx.net (spex66 at gmx.net) Date: Wed, 23 Jul 2003 00:59:56 +0200 (MEST) Subject: [C++-sig] Re: is_polymorphic and unions Message-ID: <17713.1058914796@www66.gmx.net> Hi Dave, thanks for your fast helping hand :) (don't know how to respond in thread from a mail-client?!?) >> solution to (1) is obviously splitting... sigh -> any chance to got this as >> a feature from pyste, Nicodemus? > >The current CVS includes support for "--multiple": >http://tinyurl.com/hp3j as far as I could see, its a splitting at header-file level... that's not enough in my case. Maybe a hardcore classlevel would be a nice option, too? >> This conversion requires a reinterpret_cast, a C-style cast or >> function-style cast > >This is an msvc bug which preserves top-level constness of arguments >in function (pointer) types. If you can redeclare the offending >function as: > > short SRM_ChangeCoordinateSRF(SRM_SRF_Parameters_Pair, const SRM_Coordinate *,SRM_Coordinate *); I'm a little bit challenged with C++ actually :/ Do you mean 'redeclare' in its original position in the header-file (srm.h in this case)? If so... in exactly the way you give the example, or the original EXPORT_DLL extern SRM_Status_Code SRM_ChangeCoordinateSRF ( const SRM_SRF_Parameters_Pair coord_op_params_ptr, const SRM_Coordinate *source_coord_ptr, SRM_Coordinate *dest_coord_ptr ); style (deleting first occur of const)? Or have I to redeclare it in the mSedris.cpp (build from pyste)... dumb as I am (belonging to C++ of course), I've tried to include your line in front of BOOST_PYTHON_MODULE(mSedris) but my VC6 told me that's not the right solution sorry for that kind of question-level... I'm happy to make my first steps with boost.python.object... the examples looks terrific!!! > >you can still make the first parameter const in the function >*definition* without upsetting the compiler. If you can't change the >declaration of 'whatever' you'll have to resort to forcibly casting >the offending function pointer. > >I suppose Pyste could be patched to do this for you... This would be great :) >> ::::::::::::::::::::::::::::::::::: >> ERROR::>> >> error C2504: in ..../type_traits/is_polymorphic.hpp (79) ---> problem of a >> union > >What's the complete error message for that line? here it comes (followed by matching pyste-result, and original header-file-snippets) parts translated from german VC6 messages into matching english one: ..\..\..\boost/type_traits/is_polymorphic.hpp(26) : error C2569: 'type' : enum/union cannot be used as a base class C:\arwa\dev\sedris_sdk_3.1.2\include\srm_types.h(5165) : see reference to class template instantiation 'type' being compiled ..\..\..\boost/type_traits/is_polymorphic.hpp(79) : see reference to class template instantiation 'boost::detail::is_polymorphic_imp1' being compiled ..\..\..\boost/type_traits/is_polymorphic.hpp(84) : see reference to class template instantiation 'boost::detail::is_polymorphic_imp' being compiled ..\..\..\boost/python/object/make_ptr_instance.hpp(37) : see reference to class template instantiation 'boost::is_polymorphic' being compiled ..\..\..\boost/python/object/make_ptr_instance.hpp(30) : see reference to class template instantiation 'struct _typeobject *__cdecl boost::python::objects::make_ptr_instance >::get_class_object_impl(volatile const SRM_SRF_Parameters::type *)' being compiled PYSTE-AGAIN::>> class_< SRM_SRF_Parameters >("SRM_SRF_Parameters", init< >()) .def(init< const SRM_SRF_Parameters & >()) .def_readwrite("dimensionality", &SRM_SRF_Parameters::dimensionality) .def_readwrite("parameters", &SRM_SRF_Parameters::parameters) ; SOURCE-AGAIN::>> typedef struct { SRM_Dimensionality dimensionality; union { SRM_SRF_Parameters_2D two_d; SRM_SRF_Parameters_3D three_d; } parameters; } SRM_SRF_Parameters; I have not reproduce the >> mpl::and_, is_polymorphic > stuff. But from my memory, trying this last time... do you mean to replace occurences only from is_polymorphic or also is_polymorphic // is_polymorphic // is_polymorphic in the same style? Thats what I have tried last time (plus # include ) :::::::::::::::::::: And a new kind of compiler-error, maybe time to use boost.array? :::::::::::::::::::::::::::::::::: PYSTE::>> class_< SRM_Matrix_3x3 >("SRM_Matrix_3x3", init< >()) .def(init< const SRM_Matrix_3x3 & >()) .def_readwrite("mat", &SRM_Matrix_3x3::mat) ; :::::::::::::::::::::::::::::::::: ERROR::>> ..\..\..\boost/python/data_members.hpp(68) : error C2440: '=' : 'const double [3][3]' cannot convert in 'double [3][3]' Es gibt keinen Kontext, in dem diese Konvertierung moeglich ist ..\..\..\boost/python/data_members.hpp(55) : Bei der Kompilierung der Member-Funktion 'struct _object *__cdecl boost::python::detail::member< double [3][3], struct SRM_Matrix_3x3, struct boost::python::default_call_policies >::set(double (SRM_Matrix_3x3::*)[3][3], struct _object *, struct _object *, const struct boost::python::default_call_policies &)' der Klassenvorlage :::::::::::::::::::::::::::::::::: SOURCE::>> typedef struct { SRM_Long_Float mat[3][3]; } SRM_Matrix_3x3; thanks again for your help and your time, but as it is in software-project life... time is the REAL bottleneck, *sigh* but building wonders and miracles in zero-time is the real thrill :) Peter (=PA=) From dave at boost-consulting.com Wed Jul 23 02:17:31 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 22 Jul 2003 20:17:31 -0400 Subject: [C++-sig] Re: is_polymorphic and unions References: <17713.1058914796@www66.gmx.net> Message-ID: spex66 at gmx.net writes: > Hi Dave, > > thanks for your fast helping hand :) > (don't know how to respond in thread from a mail-client?!?) Are you asking me if I know how? I use GNUs; it seems to be working. >>> solution to (1) is obviously splitting... sigh -> any chance to got this as >>> a feature from pyste, Nicodemus? >> >>The current CVS includes support for "--multiple": >>http://tinyurl.com/hp3j > > as far as I could see, its a splitting at header-file > level... that's not enough in my case. Maybe a hardcore classlevel > would be a nice option, too? Pyste stuff is up to Nicodemus. >>> This conversion requires a reinterpret_cast, a C-style cast or >>> function-style cast >> >>This is an msvc bug which preserves top-level constness of arguments >>in function (pointer) types. If you can redeclare the offending >>function as: >> >> short SRM_ChangeCoordinateSRF(SRM_SRF_Parameters_Pair, const > SRM_Coordinate *,SRM_Coordinate *); > > I'm a little bit challenged with C++ actually :/ > Do you mean 'redeclare' in its original position in the header-file (srm.h > in this case)? Yes, I mean modify the declaration, if the code is under your control. > If so... in exactly the way you give the example, or the original > > EXPORT_DLL extern SRM_Status_Code > SRM_ChangeCoordinateSRF > ( > const SRM_SRF_Parameters_Pair coord_op_params_ptr, > const SRM_Coordinate *source_coord_ptr, > SRM_Coordinate *dest_coord_ptr > ); > > style (deleting first occur of const)? The latter sounds good. > Or have I to redeclare it in the mSedris.cpp Nope. >>I suppose Pyste could be patched to do this for you... > > This would be great :) Note that I am not volunteering this feature. As ever, it's up to Nicodemus. >>> ::::::::::::::::::::::::::::::::::: >>> ERROR::>> >>> error C2504: in ..../type_traits/is_polymorphic.hpp (79) ---> problem of a >>> union >> >>What's the complete error message for that line? > > here it comes (followed by matching pyste-result, and original > header-file-snippets) parts translated from german VC6 messages into matching english one: > > ..\..\..\boost/type_traits/is_polymorphic.hpp(26) : error C2569: 'type' : > enum/union cannot be used as a base class > C:\arwa\dev\sedris_sdk_3.1.2\include\srm_types.h(5165) : see reference to > class template instantiation 'type' being compiled > ..\..\..\boost/type_traits/is_polymorphic.hpp(79) : see reference to > class template instantiation 'boost::detail::is_polymorphic_imp1 SRM_SRF_Parameters::type>' being compiled > ..\..\..\boost/type_traits/is_polymorphic.hpp(84) : see reference to > class template instantiation 'boost::detail::is_polymorphic_imp SRM_SRF_Parameters::type>' being compiled OK, the easy solution is to specialize is_polymorphic for your union type: #include namespace boost { template <> struct is_polymorphic : mpl::false_ {}; } > ..\..\..\boost/python/object/make_ptr_instance.hpp(37) : see > reference to class template instantiation 'boost::is_polymorphic SRM_SRF_Parameters::type>' being compiled > ..\..\..\boost/python/object/make_ptr_instance.hpp(30) : see > reference to class template instantiation 'struct _typeobject *__cdecl > boost::python::objects::make_ptr_instance boost::python::objects::pointer_holder SRM_SRF_Parameters::type> >::get_class_object_impl(volatile const > SRM_SRF_Parameters::type *)' being compiled > > PYSTE-AGAIN::>> > class_< SRM_SRF_Parameters >("SRM_SRF_Parameters", init< >()) > .def(init< const SRM_SRF_Parameters & >()) > .def_readwrite("dimensionality", &SRM_SRF_Parameters::dimensionality) > .def_readwrite("parameters", &SRM_SRF_Parameters::parameters) > ; > > > SOURCE-AGAIN::>> > typedef struct > { > SRM_Dimensionality dimensionality; > union > { > SRM_SRF_Parameters_2D two_d; > SRM_SRF_Parameters_3D three_d; > } parameters; > } SRM_SRF_Parameters; This doesn't quite add up. According to your declaration of SRM_SRF_Parameters, there is no nested member called 'type'. Is there perhaps #define parameters type somewhere in your source code? > I have not reproduce the >>> mpl::and_, is_polymorphic > > stuff. But from my memory, trying this last time... do you mean to > replace occurences only from is_polymorphic or also > is_polymorphic // is_polymorphic // > is_polymorphic in the same style? Thats what I have tried last > time (plus # include ) No, it won't work, sorry. Try the specialization. > :::::::::::::::::::: > And a new kind of compiler-error, maybe time to use boost.array? > > > :::::::::::::::::::::::::::::::::: > PYSTE::>> > > class_< SRM_Matrix_3x3 >("SRM_Matrix_3x3", init< >()) > .def(init< const SRM_Matrix_3x3 & >()) > .def_readwrite("mat", &SRM_Matrix_3x3::mat) > ; > > :::::::::::::::::::::::::::::::::: > ERROR::>> > ..\..\..\boost/python/data_members.hpp(68) : > error C2440: '=' : 'const double [3][3]' cannot convert in 'double [3][3]' > Es gibt keinen Kontext, in dem diese Konvertierung moeglich ist > ..\..\..\boost/python/data_members.hpp(55) : > Bei der Kompilierung der Member-Funktion > 'struct _object *__cdecl boost::python::detail::member< > double [3][3], > struct SRM_Matrix_3x3, > struct boost::python::default_call_policies > >::set(double (SRM_Matrix_3x3::*)[3][3], > struct _object *, > struct _object *, > const struct boost::python::default_call_policies &)' > der Klassenvorlage > > :::::::::::::::::::::::::::::::::: > SOURCE::>> > typedef struct > { > SRM_Long_Float mat[3][3]; > } SRM_Matrix_3x3; > Boost.Python doesn't convert builtin arrays to/from python automatically. You'll have to decide how you want to represent them. I suggest something like: boost::python::tuple getter(SRM_Matrix_3x3& m) { return boost::python::make_tuple( boost::python::make_tuple(m.mat[0][0], m.mat[0][1], m.mat[0][2]) , boost::python::make_tuple(m.mat[1][0], m.mat[1][1], m.mat[1][2]) , boost::python::make_tuple(m.mat[1][0], m.mat[1][1], m.mat[1][2])); } void setter(SRM_Matrix_3x3& m, boost::python::tuple x) { for (int i = 0; i < 3; ++i) for (int j = 0; i < 3; ++j) m.mat[i][j] = extract(x[i][j]); } class_< SRM_Matrix_3x3 >("SRM_Matrix_3x3", init< >()) .def(init< const SRM_Matrix_3x3 & >()) .add_property("mat", getter, setter) ; > thanks again for your help and your time, but as it is in > software-project life... time is the REAL bottleneck, *sigh* That's why *I* can't afford to do much more as a volunteer ;-) > but building wonders and miracles in zero-time is the real thrill :) Always glad to offer a little thrill... ;-> -- Dave Abrahams Boost Consulting www.boost-consulting.com From mike at nospam.com Wed Jul 23 02:58:23 2003 From: mike at nospam.com (Mike Rovner) Date: Tue, 22 Jul 2003 17:58:23 -0700 Subject: [C++-sig] Re: GCC type demangling and better error messages References: Message-ID: David Abrahams wrote: > Done and checked into CVS. Please enjoy! Hope I missed something, but after updating from CVS (HEAD) I got boost/python/detail/caller.hpp (-r 1.17) trying to #include which is absent. Thanks, Mike From greglandrum at mindspring.com Wed Jul 23 03:22:36 2003 From: greglandrum at mindspring.com (greg Landrum) Date: Tue, 22 Jul 2003 18:22:36 -0700 Subject: [C++-sig] exceptions and multiple modules Message-ID: <5.1.0.14.2.20030722181216.02f60ee8@mail.earthlink.net> [boost 1.30, g++ 3.2, redhat 8.0, python 2.2] We've been having strange order dependence problems when using exceptions and multiple extension modules. I've attached an extremely simplified example that demonstrates the problem. The example includes two small extension modules, moda and modb, each of which defines a single function that throws an IndexError. If I do: >>> import modb >>> import moda >>> modb.tossitb() everything works fine (I get the expected IndexError) If, however, I reverse the import error: >>> import moda >>> import modb >>> modb.tossitb() I get the dreaded "RuntimeError: unidentifiable C++ exception" Any ideas as to what might be going on here? "Jamsegment" includes the lines I added to the $Boost/libs/python/test Jamfile to build things. Thanks -greg -------------- next part -------------- A non-text attachment was scrubbed... Name: cross_mod_problems.zip Type: application/zip Size: 1024 bytes Desc: not available URL: From dave at boost-consulting.com Wed Jul 23 03:32:37 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 22 Jul 2003 21:32:37 -0400 Subject: [C++-sig] Re: GCC type demangling and better error messages References: Message-ID: "Mike Rovner" writes: > David Abrahams wrote: > >> Done and checked into CVS. Please enjoy! > > Hope I missed something, but after updating from CVS (HEAD) > I got boost/python/detail/caller.hpp (-r 1.17) trying to > #include which is absent. Sorry, Mike. I hade a CVS spasm, it looks like. Should be fixed now. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Wed Jul 23 03:44:54 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 22 Jul 2003 21:44:54 -0400 Subject: [C++-sig] Re: exceptions and multiple modules References: <5.1.0.14.2.20030722181216.02f60ee8@mail.earthlink.net> Message-ID: greg Landrum writes: > [boost 1.30, g++ 3.2, redhat 8.0, python 2.2] > > We've been having strange order dependence problems when using > exceptions and multiple extension modules. I've attached an extremely > simplified example that demonstrates the problem. > > The example includes two small extension modules, moda and modb, each > of which defines a single function that throws an IndexError. If I do: > >>> import modb > >>> import moda > >>> modb.tossitb() > everything works fine (I get the expected IndexError) > > If, however, I reverse the import error: > >>> import moda > >>> import modb > >>> modb.tossitb() > I get the dreaded "RuntimeError: unidentifiable C++ exception" > > Any ideas as to what might be going on here? Yeah, some. Could you try the enclosed patch and see whether it helps? -------------- next part -------------- A non-text attachment was scrubbed... Name: bpl.patch Type: text/x-patch Size: 1238 bytes Desc: not available URL: -------------- next part -------------- -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Wed Jul 23 03:59:10 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Tue, 22 Jul 2003 22:59:10 -0300 Subject: [C++-sig] Re: is_polymorphic and unions In-Reply-To: <17713.1058914796@www66.gmx.net> References: <17713.1058914796@www66.gmx.net> Message-ID: <3F1DEBEE.5010501@globalite.com.br> Hi Peter, sorry about the delay, spex66 at gmx.net wrote: >>>solution to (1) is obviously splitting... sigh -> any chance to got this >>> >>> >as > > >>>a feature from pyste, Nicodemus? >>> >>> >>The current CVS includes support for "--multiple": >>http://tinyurl.com/hp3j >> >> >as far as I could see, its a splitting at header-file level... that's not >enough in my case. Maybe a hardcore classlevel would be a nice option, too? > I am about to implement a change in multiple mode, where each pyste file will generate a cpp file. From there, you can split your classes and functions in as many pyste files as necessary. I'm about to implement this change since last week, but haven't got enough time to do it yet. 8( >>>This conversion requires a reinterpret_cast, a C-style cast or >>>function-style cast >>> >>> >>This is an msvc bug which preserves top-level constness of arguments >>in function (pointer) types. If you can redeclare the offending >>function as: >> >> short SRM_ChangeCoordinateSRF(SRM_SRF_Parameters_Pair, const >> >>you can still make the first parameter const in the function >>*definition* without upsetting the compiler. If you can't change the >>declaration of 'whatever' you'll have to resort to forcibly casting >>the offending function pointer. >> >>I suppose Pyste could be patched to do this for you... >> >> > >This would be great :) > I am not very thrilled about the idea, but if more people are having this problem I suppose we should support this hack. >but building wonders and miracles in zero-time is the real thrill :) > Miracles, magic and gnomes are always exciting! ;) Regards, Nicodemus. From dave at boost-consulting.com Wed Jul 23 05:09:51 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 22 Jul 2003 23:09:51 -0400 Subject: [C++-sig] Re: exceptions and multiple modules References: <5.1.0.14.2.20030722181216.02f60ee8@mail.earthlink.net> Message-ID: David Abrahams writes: > Yeah, some. Could you try the enclosed patch and see whether it > helps? Hmm, seems to be working for me. Greg, would you mind sending me those files modified to use a Boost-compatible license/copyright notice in them so that I can check them in as regression tests? Many thanks, Dave -- Dave Abrahams Boost Consulting www.boost-consulting.com From greglandrum at mindspring.com Wed Jul 23 05:40:49 2003 From: greglandrum at mindspring.com (greg Landrum) Date: Tue, 22 Jul 2003 20:40:49 -0700 Subject: [C++-sig] Re: exceptions and multiple modules In-Reply-To: References: <5.1.0.14.2.20030722181216.02f60ee8@mail.earthlink.net> Message-ID: <5.1.0.14.2.20030722204027.050caae0@mail.mindspring.com> At 06:44 PM 7/22/2003, David Abrahams wrote: > > I get the dreaded "RuntimeError: unidentifiable C++ exception" > > > > Any ideas as to what might be going on here? > >Yeah, some. Could you try the enclosed patch and see whether it >helps? Yep, that cleared it right up. Thanks Dave! -greg From rwgk at yahoo.com Wed Jul 23 12:26:39 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Wed, 23 Jul 2003 03:26:39 -0700 (PDT) Subject: [C++-sig] Re: exceptions and multiple modules In-Reply-To: <5.1.0.14.2.20030722204027.050caae0@mail.mindspring.com> Message-ID: <20030723102639.87036.qmail@web20204.mail.yahoo.com> --- greg Landrum wrote: > At 06:44 PM 7/22/2003, David Abrahams wrote: > > > I get the dreaded "RuntimeError: unidentifiable C++ exception" > > > > > > Any ideas as to what might be going on here? > > > >Yeah, some. Could you try the enclosed patch and see whether it > >helps? > > Yep, that cleared it right up. Thanks Dave! Dave, does your trick with the virtual function eliminate the need to use RTLD_GLOBAL? This is what I mean: if (sys.platform == "linux2"): previous_dlopenflags = sys.getdlopenflags() sys.setdlopenflags(0x100|0x2) Ralf __________________________________ Do you Yahoo!? Yahoo! SiteBuilder - Free, easy-to-use web site design software http://sitebuilder.yahoo.com From ben.young at transversal.com Wed Jul 23 13:04:59 2003 From: ben.young at transversal.com (Ben Young) Date: Wed, 23 Jul 2003 11:04:59 +0000 (GMT) Subject: [C++-sig] Re: exceptions and multiple modules In-Reply-To: <20030723102639.87036.qmail@web20204.mail.yahoo.com> References: <20030723102639.87036.qmail@web20204.mail.yahoo.com> Message-ID: We also had to use this trick to import our boost-python wrapped library. I noticed Dave Abrahams thread on python-dev about libraries being able to specify their own dlopen flags for import. Did anything ever come of this Dave? or do you think we (transversal) will have just have to keep a wrapper python script that knows how to do the import correctly? Cheers Ben --- P.S If you want us on your list of projects using boost-python we would be happy to supply our details: Transversal is a company that produces Metafaq, an enterprise level, online, knowledge base management system. boost-python is used in an automated process to generate python bindings to our api which is exposed though multiple backends and frontends. This allows us to write quick tests and bespoke scripts to perform one off tasks without having to go through the full compilation cycle. On Wed, 23 Jul 2003, Ralf W. Grosse-Kunstleve wrote: > --- greg Landrum wrote: > > At 06:44 PM 7/22/2003, David Abrahams wrote: > > > > I get the dreaded "RuntimeError: unidentifiable C++ exception" > > > > > > > > Any ideas as to what might be going on here? > > > > > >Yeah, some. Could you try the enclosed patch and see whether it > > >helps? > > > > Yep, that cleared it right up. Thanks Dave! > > Dave, does your trick with the virtual function eliminate the need to use > RTLD_GLOBAL? > > This is what I mean: > > if (sys.platform == "linux2"): > previous_dlopenflags = sys.getdlopenflags() > sys.setdlopenflags(0x100|0x2) > > Ralf > > > __________________________________ > Do you Yahoo!? > Yahoo! SiteBuilder - Free, easy-to-use web site design software > http://sitebuilder.yahoo.com > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > > From dave at boost-consulting.com Wed Jul 23 13:33:07 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 23 Jul 2003 07:33:07 -0400 Subject: [C++-sig] Re: exceptions and multiple modules References: <5.1.0.14.2.20030722204027.050caae0@mail.mindspring.com> <20030723102639.87036.qmail@web20204.mail.yahoo.com> Message-ID: "Ralf W. Grosse-Kunstleve" writes: > --- greg Landrum wrote: >> At 06:44 PM 7/22/2003, David Abrahams wrote: >> > > I get the dreaded "RuntimeError: unidentifiable C++ exception" >> > > >> > > Any ideas as to what might be going on here? >> > >> >Yeah, some. Could you try the enclosed patch and see whether it >> >helps? >> >> Yep, that cleared it right up. Thanks Dave! > > Dave, does your trick with the virtual function eliminate the need to use > RTLD_GLOBAL? Yes. Of course, that exception is defined in the library. If you want to properly translate a user-defined exception you must either register the exception translator in the same module which throws it or you must link the collaborating modules together somehow. If you don't like direct linking, you can of course put the exception's virtual function in some common shared library -- essentially the trick I just used. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Wed Jul 23 13:36:56 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 23 Jul 2003 07:36:56 -0400 Subject: [C++-sig] Re: exceptions and multiple modules References: <20030723102639.87036.qmail@web20204.mail.yahoo.com> Message-ID: Ben Young writes: > We also had to use this trick to import our boost-python wrapped library. > I noticed Dave Abrahams thread on python-dev about libraries being able > to specify their own dlopen flags for import. Did anything ever come of > this Dave? Nope, it was unfortunately a wrong-headed idea, IMO. > or do you think we (transversal) will have just have to keep a > wrapper python script that knows how to do the import correctly? I don't think using RTLD_GLOBAL for extension modules is a good idea in general, and I'd encourage new users to find alternative approaches. If it's working for you, though, there's no need to change. > Cheers > > Ben > --- > > P.S If you want us on your list of projects using boost-python we would be > happy to supply our details: > > Transversal is a company that produces > Metafaq, an enterprise level, online, knowledge base management system. > boost-python is used in an automated process to generate python bindings > to our api which is exposed though multiple backends and frontends. This > allows us to write quick tests and bespoke scripts to perform one off > tasks without having to go through the full compilation cycle. Thanks! -- Dave Abrahams Boost Consulting www.boost-consulting.com From ben.young at transversal.com Wed Jul 23 14:16:30 2003 From: ben.young at transversal.com (Ben Young) Date: Wed, 23 Jul 2003 12:16:30 +0000 (GMT) Subject: [C++-sig] Re: exceptions and multiple modules In-Reply-To: References: <20030723102639.87036.qmail@web20204.mail.yahoo.com> Message-ID: On Wed, 23 Jul 2003, David Abrahams wrote: > Ben Young writes: > > > We also had to use this trick to import our boost-python wrapped library. > > I noticed Dave Abrahams thread on python-dev about libraries being able > > to specify their own dlopen flags for import. Did anything ever come of > > this Dave? > > Nope, it was unfortunately a wrong-headed idea, IMO. > > > or do you think we (transversal) will have just have to keep a > > wrapper python script that knows how to do the import correctly? > > I don't think using RTLD_GLOBAL for extension modules is a good idea > in general, and I'd encourage new users to find alternative > approaches. If it's working for you, though, there's no need to > change. > The only problem is that the library itself can dynamically import backends which use symbols in the library itself. e.g import mfAPI mfAPI.useBackend("dbserver") # Will import the database backend mfAPI.useBackend("soapclient")# Will import the soapclient backend conn = mfAPI.Connection(...) # Will connect to either the database server # or the soapclient depending on the # connection params Every action from now on will transparently go through SOAP or the database depending on the params. The point is that the mfAPI library doesn't know anything at all about dbserver of soapclient before they are imported, also by dlopen. The c++ code is the same LibraryControl::import("dbserver") LibraryControl::import("soapclient") MF::Connection conn = LibraryControl::connect(...) conn can now be used to transparently use objects through either SOAP or the database. This however works as the c++ code is linked at compile time to the correct base librarys and only "dbserver" or "soapclient" are dlopened. The problem seems to be that when python dlopens mfAPI, because it doesn't use RTLD_GLOBAL tdbserver etc can't see the symbols in mfAPI and you get dynamic_cast failures. Now I think i'm going round in circles explaining this anyway :) I'm sure there is probably a simple solution, but as you say, it works for us, and we only use the python bit internally at the moment. I am slightly worried as the mechanism ( designed here by Richard Smith who is quite active in comp.std.c++ ) allows us to trivially generate bindings to any language ( we have perl and php as well at the moment, though they are mouldering at the moment since I discovered python and pushed it on everyone else!) and I can see these problems reappearing for them. Never mind though. Thanks for the help Ben --- From dave at boost-consulting.com Wed Jul 23 16:32:06 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 23 Jul 2003 10:32:06 -0400 Subject: [C++-sig] Re: exceptions and multiple modules References: <20030723102639.87036.qmail@web20204.mail.yahoo.com> Message-ID: Ben Young writes: > On Wed, 23 Jul 2003, David Abrahams wrote: > >> Ben Young writes: >> >> > We also had to use this trick to import our boost-python wrapped library. >> > I noticed Dave Abrahams thread on python-dev about libraries being able >> > to specify their own dlopen flags for import. Did anything ever come of >> > this Dave? >> >> Nope, it was unfortunately a wrong-headed idea, IMO. >> >> > or do you think we (transversal) will have just have to keep a >> > wrapper python script that knows how to do the import correctly? >> >> I don't think using RTLD_GLOBAL for extension modules is a good idea >> in general, and I'd encourage new users to find alternative >> approaches. If it's working for you, though, there's no need to >> change. >> > > The only problem is that the library itself can dynamically import > backends which use symbols in the library itself. Python itself has a similar relationship with its extension modules. Seems to work out OK without RTLD_GLOBAL. > e.g > > import mfAPI > mfAPI.useBackend("dbserver") # Will import the database backend > mfAPI.useBackend("soapclient")# Will import the soapclient backend > > conn = mfAPI.Connection(...) # Will connect to either the database server > # or the soapclient depending on the > # connection params > > Every action from now on will transparently go through SOAP or the > database depending on the params. > The point is that the mfAPI library doesn't know anything at all about > dbserver of soapclient before they are imported, also by dlopen. > > The c++ code is the same > > LibraryControl::import("dbserver") > LibraryControl::import("soapclient") > > MF::Connection conn = LibraryControl::connect(...) > > conn can now be used to transparently use objects through either SOAP or > the database. This however works as the c++ code is > linked at compile time ^^^^^^^^^^^^^^^^^^^^^^ I think I know what you mean, but something's not right about that. > to the correct base librarys and only "dbserver" or "soapclient" are > dlopened. > > The problem seems to be that when python dlopens mfAPI, because it doesn't > use RTLD_GLOBAL tdbserver etc can't see the symbols in mfAPI and you get > dynamic_cast failures. The way to handle dynamic_cast issues is to instantiate the base class' virtual functions in a common shared library which is linked to in the usual way (not dlopen) by all the other dynamic libraries concerned. > Now I think i'm going round in circles explaining this anyway :) I'm sure > there is probably a simple solution, but as you say, it works for us, and > we only use the python bit internally at the moment. > > I am slightly worried as the mechanism ( designed here by Richard > Smith who is quite active in comp.std.c++ ) allows us to trivially > generate bindings to any language ( we have perl and php as well at the > moment, though they are mouldering at the moment since I discovered python > and pushed it on everyone else!) and I can see these problems reappearing > for them. > > Never mind though. Now you tell me! -- Dave Abrahams Boost Consulting www.boost-consulting.com From ben.young at transversal.com Wed Jul 23 17:30:53 2003 From: ben.young at transversal.com (Ben Young) Date: Wed, 23 Jul 2003 15:30:53 +0000 (GMT) Subject: [C++-sig] Re: exceptions and multiple modules In-Reply-To: References: <20030723102639.87036.qmail@web20204.mail.yahoo.com> Message-ID: > > linked at compile time > ^^^^^^^^^^^^^^^^^^^^^^ > I think I know what you mean, but something's not right about that. Err, yes. It's been a long day! > The way to handle dynamic_cast issues is to instantiate the base > class' virtual functions in a common shared library which is linked to > in the usual way (not dlopen) by all the other dynamic libraries > concerned. > I'll have a look and see if I can do something like this, although worryingly i'm pretty sure the libraries are already laid out something like this. It's all a bit confusing as its a combination of automatically generated files, templates, virtual template tables, multiple libraries ... ;) Thanks for all the help though. I'll get back if/when I fix the problem. Ben --- From dave at boost-consulting.com Wed Jul 23 17:48:55 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 23 Jul 2003 11:48:55 -0400 Subject: [C++-sig] Injected constructors Message-ID: It's already possible to inject new methods into a Python class wrapper that are not in the underlying class: #include struct X { std::vector v; }; int size(X& self) { return self.v.size(); } BOOST_PYTHON_MODULE(test) { class_("X") .def("size", size) ; } >>> x = X() >>> x.size() 0 Currently, there's no easy way to do the same thing for constructors, without intruding on the underlying class or writing a wrapper class which repeats *all* of the base constructors and adds new ones. I am about to add just such a facility: std::auto_ptr x_factory(PyObject* self, int n) { std::auto_ptr x(new X); x->v.resize(n); return x; } BOOST_PYTHON_MODULE(test) { class_("X") .def("size", size) .def("__init__", init_factory(x_factory)) ; } >>> x = X(30) >>> x.size() 30 init_factory creates a python callable object which calls its function argument and injects the resulting object into a holder in the self argument. I'm not in love with the "init_factory" name. Anyone have a better idea? -- Dave Abrahams Boost Consulting www.boost-consulting.com From rwgk at yahoo.com Wed Jul 23 18:47:50 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Wed, 23 Jul 2003 09:47:50 -0700 (PDT) Subject: [C++-sig] Injected constructors In-Reply-To: Message-ID: <20030723164751.46672.qmail@web20205.mail.yahoo.com> --- David Abrahams wrote: > .def("__init__", init_factory(x_factory)) I don't like the "init" duplication. Would this be possible? .def(init_factory(x_factory)) This would also make sense to me: .def("__init__", factory(x_factory)) But I like the first alternative better because it is more formal and prevents frustrating debugging sessions due to stupid typos like .def("_init__", factory(x_factory)). Yet another idea: .def_factory(x_factory) It means expanding the class_<> interface, but I think the purpose is unique enough to warrant the additional member function. Ralf __________________________________ Do you Yahoo!? Yahoo! SiteBuilder - Free, easy-to-use web site design software http://sitebuilder.yahoo.com From dave at boost-consulting.com Wed Jul 23 19:12:04 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 23 Jul 2003 13:12:04 -0400 Subject: [C++-sig] Re: Injected constructors References: <20030723164751.46672.qmail@web20205.mail.yahoo.com> Message-ID: "Ralf W. Grosse-Kunstleve" writes: > --- David Abrahams wrote: >> .def("__init__", init_factory(x_factory)) > > I don't like the "init" duplication. Would this be possible? > > .def(init_factory(x_factory)) yes. > This would also make sense to me: > > .def("__init__", factory(x_factory)) > > But I like the first alternative better because it is more formal > and prevents frustrating debugging sessions due to stupid typos > like .def("_init__", factory(x_factory)). > > Yet another idea: > > .def_factory(x_factory) > > It means expanding the class_<> interface, but I think the purpose > is unique enough to warrant the additional member function. Actually, we're trying to avoid bloating it even more. Joel is about to commit a simple mechanism which even allows us to move the pickle_suite functionality out of class_. -- Dave Abrahams Boost Consulting www.boost-consulting.com From mike at nospam.com Wed Jul 23 19:20:43 2003 From: mike at nospam.com (Mike Rovner) Date: Wed, 23 Jul 2003 10:20:43 -0700 Subject: [C++-sig] Re: is_polymorphic and unions (was: Pyste and STL types) References: <31026.1058889255@www61.gmx.net> Message-ID: spex66 at gmx.net wrote: > (1) error C1204:Compiler limit:internal structure overflow (as > described in boost/faq) I just want to share my positive experience with VS2003 (MSVC++7.1). I had a lot of such problems with versions 6-7, but after upgrading they are gone. FWIW, I worse upgrading (not to mention partial template specialisation, Koenig lookup, etc.) Regards, Mike From mike at nospam.com Wed Jul 23 20:39:41 2003 From: mike at nospam.com (Mike Rovner) Date: Wed, 23 Jul 2003 11:39:41 -0700 Subject: [C++-sig] Re: GCC type demangling and better error messages References: Message-ID: David Abrahams wrote: > "Mike Rovner" writes: > >> David Abrahams wrote: >> >>> Done and checked into CVS. Please enjoy! >> >> Hope I missed something, but after updating from CVS (HEAD) >> I got boost/python/detail/caller.hpp (-r 1.17) trying to >> #include which is absent. > > Sorry, Mike. I hade a CVS spasm, it looks like. Should be fixed now. Thank you, Dave. Works fine. Great addition to the library. From greglandrum at mindspring.com Wed Jul 23 20:28:05 2003 From: greglandrum at mindspring.com (greg Landrum) Date: Wed, 23 Jul 2003 11:28:05 -0700 Subject: [C++-sig] more cross-module problems Message-ID: <5.1.0.14.2.20030723111002.02e37008@mail.earthlink.net> Dave's patch cleared up the exception problems I reported yesterday, but I've got more cross-module problems to report. The attached zip file will create a directory called RDTest. If you extract it in $Boost/libs/python, you'll end up with something that can be built with bjam. I apologize in advance for the names of things here... The Jamfile runs two tests, both of which use multiple modules and explore passing objects between them. One of the tests works on Windows and fails on Linux, the other works on Linux and fails on Windows. The first test (named both_mods in the Jamfile) explores what happens if classes with boost::any data members are passed between modules. This test works fine on Windows but fails on Linux with the error: RuntimeError: boost::bad_any_cast: failed conversion using boost::any_cast The second test (named CM2_test) creates three modules (modulea, moduleb and modulec). modulea and modulec define simple classes (classA and classC) that use STL containers to map std::strings -> integers. classA does this with an std::map and classC does it with an std::vector of std::pairs. As the test demonstrates, both these modules work ok by themselves. moduleb has 2 functions: testCrossA() takes a classA instance and gets a property from it; testCrossC() takes a classC instance and gets a property. moduleb works without problems on Linux, but the test using classA instances (which carry around std::maps) fails on Windows with the dread: RuntimeError: unidentifiable C++ exception error. Platform notes; Windows = [Win2K, MSVC v6, python 2.2, boost 1.30.0] Linux = [RH8.0, g++ 3.2, python 2.2, boost 1.30.0] Thanks, -greg -------------- next part -------------- A non-text attachment was scrubbed... Name: RDTest.zip Type: application/zip Size: 6424 bytes Desc: not available URL: From nicodemus at globalite.com.br Thu Jul 24 00:48:40 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Wed, 23 Jul 2003 19:48:40 -0300 Subject: [C++-sig] Re: Injected constructors In-Reply-To: References: <20030723164751.46672.qmail@web20205.mail.yahoo.com> Message-ID: <3F1F10C8.2000103@globalite.com.br> David Abrahams wrote: >"Ralf W. Grosse-Kunstleve" writes: > > >>Yet another idea: >> >>.def_factory(x_factory) >> >>It means expanding the class_<> interface, but I think the purpose >>is unique enough to warrant the additional member function. >> >> > >Actually, we're trying to avoid bloating it even more. Joel is about >to commit a simple mechanism which even allows us to move the >pickle_suite functionality out of class_. > Hmm, that's a shame. I think that: .def_init(x_factory) would be good enough. If the bloating is really a problem, I think Ralph's suggestion: .def(init_factory(x_factory)) is nice too. Regards, Nicodemus. From dave at boost-consulting.com Thu Jul 24 02:02:11 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 23 Jul 2003 20:02:11 -0400 Subject: [C++-sig] Re: Injected constructors References: <20030723164751.46672.qmail@web20205.mail.yahoo.com> <3F1F10C8.2000103@globalite.com.br> Message-ID: Nicodemus writes: > David Abrahams wrote: > >>"Ralf W. Grosse-Kunstleve" writes: >> >>>Yet another idea: >>> >>>.def_factory(x_factory) >>> >>>It means expanding the class_<> interface, but I think the purpose >>>is unique enough to warrant the additional member function. >>> >> >>Actually, we're trying to avoid bloating it even more. Joel is about >>to commit a simple mechanism which even allows us to move the >>pickle_suite functionality out of class_. >> > > Hmm, that's a shame. Why? It's getting huge! -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Thu Jul 24 02:15:43 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Wed, 23 Jul 2003 21:15:43 -0300 Subject: [C++-sig] Re: Injected constructors In-Reply-To: References: <20030723164751.46672.qmail@web20205.mail.yahoo.com> <3F1F10C8.2000103@globalite.com.br> Message-ID: <3F1F252F.1010504@globalite.com.br> David Abrahams wrote: >Nicodemus writes: > > > >>David Abrahams wrote: >> >> >> >>>"Ralf W. Grosse-Kunstleve" writes: >>> >>> >>> >>>>Yet another idea: >>>> >>>>.def_factory(x_factory) >>>> >>>>It means expanding the class_<> interface, but I think the purpose >>>>is unique enough to warrant the additional member function. >>>> >>>> >>>> >>>Actually, we're trying to avoid bloating it even more. Joel is about >>>to commit a simple mechanism which even allows us to move the >>>pickle_suite functionality out of class_. >>> >>> >>> >>Hmm, that's a shame. >> >> > >Why? It's getting huge! > Sorry, I meant "that's a shame" about "we're trying to avoid bloating it even more", because I think .def_init(x_factory) would be nice, that's all. Another idea: could we expand the init<> interface so that it would accept an optional factory function, allowing the user to write: .def(init<>(x_factory)) ? From romany at actimize.com Thu Jul 24 06:23:51 2003 From: romany at actimize.com (Roman Yakovenko) Date: Thu, 24 Jul 2003 07:23:51 +0300 Subject: FW: [C++-sig] Injected constructors Message-ID: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AF9@exchange.adrembi.com> Just a question what is wrong with static member function or global function make_xxx? The idiom of constructing object and then making additional initialization is already used in Boost.Python - borrowed function for constructing handle. Also in Python code it will be written explicit what programmer is going to do. Did I missed something? Roman. -----Original Message----- From: David Abrahams [mailto:dave at boost-consulting.com] Sent: Wednesday, July 23, 2003 5:49 PM To: c++-sig at python.org Subject: [C++-sig] Injected constructors It's already possible to inject new methods into a Python class wrapper that are not in the underlying class: #include struct X { std::vector v; }; int size(X& self) { return self.v.size(); } BOOST_PYTHON_MODULE(test) { class_("X") .def("size", size) ; } >>> x = X() >>> x.size() 0 Currently, there's no easy way to do the same thing for constructors, without intruding on the underlying class or writing a wrapper class which repeats *all* of the base constructors and adds new ones. I am about to add just such a facility: std::auto_ptr x_factory(PyObject* self, int n) { std::auto_ptr x(new X); x->v.resize(n); return x; } BOOST_PYTHON_MODULE(test) { class_("X") .def("size", size) .def("__init__", init_factory(x_factory)) ; } >>> x = X(30) >>> x.size() 30 init_factory creates a python callable object which calls its function argument and injects the resulting object into a holder in the self argument. I'm not in love with the "init_factory" name. Anyone have a better idea? -- Dave Abrahams Boost Consulting www.boost-consulting.com _______________________________________________ C++-sig mailing list C++-sig at python.org http://mail.python.org/mailman/listinfo/c++-sig From dave at boost-consulting.com Thu Jul 24 12:28:23 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 24 Jul 2003 06:28:23 -0400 Subject: [C++-sig] Re: Injected constructors References: <20030723164751.46672.qmail@web20205.mail.yahoo.com> <3F1F10C8.2000103@globalite.com.br> <3F1F252F.1010504@globalite.com.br> Message-ID: Nicodemus writes: > David Abrahams wrote: > >>Nicodemus writes: >> >> >>>David Abrahams wrote: >>> >>> >>>>"Ralf W. Grosse-Kunstleve" writes: >>>> >>>>>Yet another idea: >>>>> >>>>>.def_factory(x_factory) >>>>> >>>>>It means expanding the class_<> interface, but I think the purpose >>>>>is unique enough to warrant the additional member function. >>>>> >>>>Actually, we're trying to avoid bloating it even more. Joel is about >>>>to commit a simple mechanism which even allows us to move the >>>>pickle_suite functionality out of class_. >>>> >>>> >>> Hmm, that's a shame. >> >>Why? It's getting huge! >> > > Sorry, I meant "that's a shame" about "we're trying to avoid bloating > it even more", because I think > > .def_init(x_factory) > > would be nice, that's all. > > Another idea: could we expand the init<> interface so that it would > accept an optional factory function, allowing the user to write: > > .def(init<>(x_factory)) I thought of that; do you think it would be confusing because of the <>s? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 24 12:32:18 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 24 Jul 2003 06:32:18 -0400 Subject: [C++-sig] Re: FW: Injected constructors References: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AF9@exchange.adrembi.com> Message-ID: "Roman Yakovenko" writes: > Just a question what is wrong with static member function or global > function make_xxx? Good point. init_factory was going to be a global function, but I guess I like "make_init" much better than "init_factory". Thanks! > The idiom of constructing object and then making additional > initialization is already used in Boost.Python - borrowed function > for constructing handle. Sure; that's .def(init_factory(f)) or, I guess: .def(make_init(f)) right? > Also in Python code it will be written explicit what programmer is > going to do. Did I missed something? I don't know. What point are you trying to make with this remark? -- Dave Abrahams Boost Consulting www.boost-consulting.com From romany at actimize.com Thu Jul 24 13:50:10 2003 From: romany at actimize.com (Roman Yakovenko) Date: Thu, 24 Jul 2003 14:50:10 +0300 Subject: [C++-sig] Re: FW: Injected constructors Message-ID: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AFA@exchange.adrembi.com> > -----Original Message----- > From: David Abrahams [mailto:dave at boost-consulting.com] > Sent: Thursday, July 24, 2003 12:32 PM > To: c++-sig at python.org > Subject: [C++-sig] Re: FW: Injected constructors > > > "Roman Yakovenko" writes: > > > Just a question what is wrong with static member function or global > > function make_xxx? > > Good point. init_factory was going to be a global function, but I > guess I like "make_init" much better than "init_factory". Thanks! I think I was misunderstood. I will explain my self using code. > > The idiom of constructing object and then making additional > > initialization is already used in Boost.Python - borrowed function > > for constructing handle. > > Sure; that's > > .def(init_factory(f)) > > or, I guess: > > .def(make_init(f)) > > right? > > > Also in Python code it will be written explicit what programmer is > > going to do. Did I missed something? > > I don't know. What point are you trying to make with this remark? class MyClass { ... MyClass(); //after constructing object stays in state 1 MyClass( int i ); //after constructing object stays in state 2 MyClass( const YourClass &x); //after constructing object stays in state 3 ... }; Now if I understand right there is a need in other state of the MyClass object. MyClass make_myclass_from_other( const SomeOther &y ); BOOST_PYTHON_MODULE(staticmethod_ext) { class_ ... .staticmethod(make_myclass_from_other) ... While in python I'll write obj = MyClass.make_myclass_from_other( third_party_class ) As for me it is much clear then adding an other constructor for the class. At the moment I wrote I thought about class that already has a few constructors. Now I understand that it is not the only case. May be you have nice small class with one constructor and you want to add an other one. I propose those names: make_object / make_instance > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com > > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > From dave at boost-consulting.com Thu Jul 24 14:37:48 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 24 Jul 2003 08:37:48 -0400 Subject: [C++-sig] Re: FW: Injected constructors References: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AFA@exchange.adrembi.com> Message-ID: "Roman Yakovenko" writes: >> > Also in Python code it will be written explicit what programmer is >> > going to do. Did I missed something? >> >> I don't know. What point are you trying to make with this remark? > > class MyClass > { > ... > MyClass(); //after constructing object stays in state 1 > MyClass( int i ); //after constructing object stays in state 2 > MyClass( const YourClass &x); //after constructing object stays in state 3 > ... > }; > > Now if I understand right there is a need in other state of the MyClass object. > > MyClass make_myclass_from_other( const SomeOther &y ); > > BOOST_PYTHON_MODULE(staticmethod_ext) > { > class_ > ... > .staticmethod(make_myclass_from_other) > ... > > While in python I'll write > obj = MyClass.make_myclass_from_other( third_party_class ) > > As for me it is much clear then adding an other constructor for the > class. Here's an example: struct X { X(int a, int b, int c); }; Now, in Python, maybe it's idiomatic to construct X from a tuple of three elements. It would be nice to let people support that directly rather than having to derive a class from X in Python just to support it. > At the moment I wrote I thought about class that already has a few > constructors. Now I understand that it is not the only case. May be > you have nice small class with one constructor and you want to add > an other one. Yup. > I propose those names: make_object / make_instance Those completely break the analogy with "make_function" and "make_getter", though. make_init would not make a new object/instance, but a new __init__ function. Even the __init__ function does not make a new Python object; it just injects a new C++ instance into it. Anyone else have objections to "make_init"? Going once, going twice... -- Dave Abrahams Boost Consulting www.boost-consulting.com From rwgk at yahoo.com Thu Jul 24 15:34:42 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Thu, 24 Jul 2003 06:34:42 -0700 (PDT) Subject: [C++-sig] Re: Injected constructors In-Reply-To: Message-ID: <20030724133442.26374.qmail@web20208.mail.yahoo.com> --- David Abrahams wrote: > > Another idea: could we expand the init<> interface so that it would > > accept an optional factory function, allowing the user to write: > > > > .def(init<>(x_factory)) > > I thought of that; do you think it would be confusing because of the > <>s? I like this best if it is a possibility. Ralf __________________________________ Do you Yahoo!? Yahoo! SiteBuilder - Free, easy-to-use web site design software http://sitebuilder.yahoo.com From dave at boost-consulting.com Thu Jul 24 16:16:15 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 24 Jul 2003 10:16:15 -0400 Subject: [C++-sig] Re: more cross-module problems References: <5.1.0.14.2.20030723111002.02e37008@mail.earthlink.net> Message-ID: greg Landrum writes: > Dave's patch cleared up the exception problems I reported yesterday, > but I've got more cross-module problems to report. > > The attached zip file will create a directory called RDTest. If you > extract it in $Boost/libs/python, you'll end up with something that > can be built with bjam. I apologize in advance for the names of > things here... > > The Jamfile runs two tests, both of which use multiple modules and > explore passing objects between them. One of the tests works on > Windows and fails on Linux, the other works on Linux and fails on > Windows. > > The first test (named both_mods in the Jamfile) explores what happens > if classes with boost::any data members are passed between modules. > This test works fine on Windows but fails on Linux with the error: > RuntimeError: boost::bad_any_cast: failed conversion using > boost::any_cast > > The second test (named CM2_test) creates three modules (modulea, > moduleb and modulec). modulea and modulec define simple classes > (classA and classC) that use STL containers to map std::strings -> > integers. classA does this with an std::map and classC does it with > an std::vector of std::pairs. As the test demonstrates, both these > modules work ok by themselves. moduleb has 2 functions: testCrossA() > takes a classA instance and gets a property from it; testCrossC() > takes a classC instance and gets a property. moduleb works without > problems on Linux, but the test using classA instances (which carry > around std::maps) fails on Windows with the dread: > RuntimeError: unidentifiable C++ exception > error. > > Platform notes; > Windows = [Win2K, MSVC v6, python 2.2, boost 1.30.0] > Linux = [RH8.0, g++ 3.2, python 2.2, boost 1.30.0] OK, Greg: None of these problems with boost::any have anything to do with Boost.Python per-se. I'll try to explain what's going on if you'll agree to write a FAQ entry or other documentation page for Boost.Python which describes the cross-module issues in detail. Deal? The Windows crash, FWIW, is a poor-QOI issue "bug" in the Dinkumware standard library that ships with vc6. vc7 solves it: ***************************** Testing self print for classA ***************************** ***************************** Testing self print for classC ***************************** ***************************** Testing crossing C to B ***************************** ***************************** Testing crossing A to B ***************************** has useless has useless has useless has useless -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 24 16:27:14 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 24 Jul 2003 10:27:14 -0400 Subject: [C++-sig] Re: Injected constructors References: <20030724133442.26374.qmail@web20208.mail.yahoo.com> Message-ID: "Ralf W. Grosse-Kunstleve" writes: > --- David Abrahams wrote: >> > Another idea: could we expand the init<> interface so that it would >> > accept an optional factory function, allowing the user to write: >> > >> > .def(init<>(x_factory)) >> >> I thought of that; do you think it would be confusing because of the >> <>s? > > I like this best if it is a possibility. I resisted it for a long time I guess it is a real possibility. I was going to say that it imposes a small overhead for: .def(init<>()) because that init object needs to include refcount management for a possible factory. If you don't like that overhead, though, you can just let class_("X") give you a default init function without the overhead. Sweet. Nobody thinks it's a case of trying to pack too much functionality into one object? If not, so much the better. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Thu Jul 24 17:02:11 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 24 Jul 2003 12:02:11 -0300 Subject: [C++-sig] Re: Injected constructors In-Reply-To: References: <20030724133442.26374.qmail@web20208.mail.yahoo.com> Message-ID: <3F1FF4F3.4050808@globalite.com.br> David Abrahams wrote: >"Ralf W. Grosse-Kunstleve" writes: > > > >>--- David Abrahams wrote: >> >> >>>>Another idea: could we expand the init<> interface so that it would >>>>accept an optional factory function, allowing the user to write: >>>> >>>>.def(init<>(x_factory)) >>>> >>>> >>>I thought of that; do you think it would be confusing because of the >>><>s? >>> >>> >>I like this best if it is a possibility. >> >> > >I resisted it for a long time I guess it is a real possibility. I was >going to say that it imposes a small overhead for: > > .def(init<>()) > >because that init object needs to include refcount management for a >possible factory. If you don't like that overhead, though, you can >just let class_("X") give you a default init function without the >overhead. > >Sweet. > >Nobody thinks it's a case of trying to pack too much functionality >into one object? If not, so much the better. > Yeah, I agree with Ralf, since it is similar with the current way to export constructors. And I don't think that it's the case of trying to pack too much functionality, since the purpose of init<> is to export constructors... the factory overload would be just another method to accomplish the same thing. From greglandrum at mindspring.com Thu Jul 24 17:07:29 2003 From: greglandrum at mindspring.com (greg Landrum) Date: Thu, 24 Jul 2003 08:07:29 -0700 Subject: [C++-sig] Re: more cross-module problems In-Reply-To: References: <5.1.0.14.2.20030723111002.02e37008@mail.earthlink.net> Message-ID: <5.1.0.14.2.20030724080409.041dcd00@mail.mindspring.com> At 07:16 AM 7/24/2003, David Abrahams wrote: >None of these problems with boost::any have anything to do with >Boost.Python per-se. I'll try to explain what's going on if you'll >agree to write a FAQ entry or other documentation page for >Boost.Python which describes the cross-module issues in detail. Deal? you drive a hard bargain... yeah, it's a deal. >The Windows crash, FWIW, is a poor-QOI issue "bug" in the Dinkumware >standard library that ships with vc6. vc7 solves it: Thanks for that info. We're planning on switching a couple of machines over to vc7 in the beginning of August, so hopefully we'll be able to stop having these problems. thanks, -greg From nicodemus at globalite.com.br Thu Jul 24 17:07:26 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Thu, 24 Jul 2003 12:07:26 -0300 Subject: [C++-sig] Re: FW: Injected constructors In-Reply-To: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AFA@exchange.adrembi.com> References: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AFA@exchange.adrembi.com> Message-ID: <3F1FF62E.2090300@globalite.com.br> Roman Yakovenko wrote: >class MyClass >{ >... > MyClass(); //after constructing object stays in state 1 > MyClass( int i ); //after constructing object stays in state 2 > MyClass( const YourClass &x); //after constructing object stays in state 3 >... >}; > >Now if I understand right there is a need in other state of the MyClass object. > >MyClass make_myclass_from_other( const SomeOther &y ); > >BOOST_PYTHON_MODULE(staticmethod_ext) >{ > class_ > ... > .staticmethod(make_myclass_from_other) >... > >While in python I'll write >obj = MyClass.make_myclass_from_other( third_party_class ) > >As for me it is much clear then adding an other constructor for the class. >At the moment I wrote I thought about class that already has a few constructors. >Now I understand that it is not the only case. May be you have nice small class with >one constructor and you want to add an other one. > > On a side note, this is a good reason to use classmethods in Python: class ConfigurationLoader(object): '''loads configuration from a filename or a file-like object. ''' def __init__(self, file_object): self.file = file_object def FromFileName(cls, filename): self = cls(file(filename)) return self FromFileName = classmethod(FromFileName) # usage config = ConfigurationLoader.FromFileName('test') This avoids having to do type checking in the __init__ method, plus it makes the code a little more readable. 8) From dave at boost-consulting.com Thu Jul 24 17:59:59 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 24 Jul 2003 11:59:59 -0400 Subject: [C++-sig] Re: Injected constructors References: <20030724133442.26374.qmail@web20208.mail.yahoo.com> <3F1FF4F3.4050808@globalite.com.br> Message-ID: Nicodemus writes: > > Yeah, I agree with Ralf, since it is similar with the current way to > export constructors. And I don't think that it's the case of trying to > pack too much functionality, since the purpose of init<> is to export > constructors... the factory overload would be just another method to > accomplish the same thing. Well, it entails a specialization for init<>, not just an overload; I don't want the constructor or more importantly the overhead in the unspecialized version which is used for non-default constructors. -- Dave Abrahams Boost Consulting www.boost-consulting.com From rwgk at yahoo.com Thu Jul 24 19:15:45 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Thu, 24 Jul 2003 10:15:45 -0700 (PDT) Subject: [C++-sig] Re: FW: Injected constructors In-Reply-To: <3F1FF62E.2090300@globalite.com.br> Message-ID: <20030724171545.13690.qmail@web20202.mail.yahoo.com> --- Nicodemus wrote: > On a side note, this is a good reason to use classmethods in Python: > > class ConfigurationLoader(object): > '''loads configuration from a filename or a file-like object. > ''' > > def __init__(self, file_object): > self.file = file_object > > def FromFileName(cls, filename): > self = cls(file(filename)) > return self > > FromFileName = classmethod(FromFileName) > > > # usage > config = ConfigurationLoader.FromFileName('test') > > > This avoids having to do type checking in the __init__ method, plus it > makes the code a little more readable. 8) FWIW: here is my preferred solution: def __init__(self, file_object=None, file_name=None): assert file_object is None or file_name is None assert file_object is not None or file_name is not None Ralf __________________________________ Do you Yahoo!? Yahoo! SiteBuilder - Free, easy-to-use web site design software http://sitebuilder.yahoo.com From mike at nospam.com Thu Jul 24 21:01:55 2003 From: mike at nospam.com (Mike Rovner) Date: Thu, 24 Jul 2003 12:01:55 -0700 Subject: [C++-sig] Re: FW: Injected constructors References: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AF9@exchange.adrembi.com> Message-ID: David Abrahams wrote: > "Roman Yakovenko" writes: > .def(make_init(f)) I suggest .def(init<>(&f)) //for regular use and .def(make_init(&f, call_policy)) // for other; like make_function Mike From dave at boost-consulting.com Thu Jul 24 21:17:23 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 24 Jul 2003 15:17:23 -0400 Subject: [C++-sig] Re: FW: Injected constructors References: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AF9@exchange.adrembi.com> Message-ID: "Mike Rovner" writes: > David Abrahams wrote: >> "Roman Yakovenko" writes: >> .def(make_init(f)) > > I suggest > .def(init<>(&f)) //for regular use > and > .def(make_init(&f, call_policy)) // for other; like make_function Ack! The Zen of Python, by Tim Peters Beautiful is better than ugly. Explicit is better than implicit. Simple is better than complex. Complex is better than complicated. Flat is better than nested. Sparse is better than dense. Readability counts. Special cases aren't special enough to break the rules. Although practicality beats purity. Errors should never pass silently. Unless explicitly silenced. In the face of ambiguity, refuse the temptation to guess. There should be one-- and preferably only one --obvious way to do it. ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ Although that way may not be obvious at first unless you're Dutch. Now is better than never. Although never is often better than *right* now. If the implementation is hard to explain, it's a bad idea. If the implementation is easy to explain, it may be a good idea. Namespaces are one honking great idea -- let's do more of those! -- Dave Abrahams Boost Consulting www.boost-consulting.com From jeff at brewer.com Fri Jul 25 00:35:01 2003 From: jeff at brewer.com (Jeff Brewer) Date: Thu, 24 Jul 2003 15:35:01 -0700 Subject: [C++-sig] def_readonly and const array members Message-ID: <3C609AD34AAF22488364057AA72EAC14019EE474@adsl-64-170-107-114.dsl.snfc21.pacbell.net> I am trying to wrap structs that have character arrays and I'm having problems since I moved from MSVC 7 to MSVC 7.1 (VS .NET 2003). Here is the struct I'm trying to expose the theArray member of using class_::def_readonly: struct testStruct { unsigned char theArray[16]; }; I've created a to_python converter for the unsigned char [16] type but I'm getting a "TypeError: No to_python (by-value) converter found for C++ type: unsigned char const volatile [8]" when I try to access the theArray member in Python. I've tried putting volatile in my typedef for the array, but that doesn't seem to help (how C++ binds these type modifiers always confuses me so maybe I put it in the wrong place). Thank you for the help, Jeff Brewer jeff at purplemagma.com p.s. The full code follows: Python code: import test theStruct = test.getStruct() print theStruct.theArray C++ code: typedef unsigned char uchar16array[16]; struct uchar16array_to_python { static PyObject *convert(uchar16array const &value) { PyObject *result = PyTuple_New(16); for (int i = 0; i < 16; i++) PyTuple_SetItem(result,i,PyInt_FromLong(value[i])); return result; } }; struct testStruct { unsigned char theArray[16]; }; testStruct getStruct() { static testStruct theStruct = {{1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16}}; return theStruct; } BOOST_PYTHON_MODULE(test) { to_python_converter(); class_("testStruct", init<>()) .def_readonly("theArray", &testStruct::theArray); def("getStruct", getStruct); } From rwgk at yahoo.com Fri Jul 25 03:05:35 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Thu, 24 Jul 2003 18:05:35 -0700 (PDT) Subject: [C++-sig] def_readonly and const array members In-Reply-To: <3C609AD34AAF22488364057AA72EAC14019EE474@adsl-64-170-107-114.dsl.snfc21.pacbell.net> Message-ID: <20030725010535.49557.qmail@web20209.mail.yahoo.com> --- Jeff Brewer wrote: > I am trying to wrap structs that have character arrays and I'm having > problems since I moved from MSVC 7 to MSVC 7.1 (VS .NET 2003). Here is > the struct I'm trying to expose the theArray member of using > class_::def_readonly: Are you also moving to a more recent boost? > .def_readonly("theArray", &testStruct::theArray); Try this instead: #include #include .add_property("theArray", make_getter(&testStruct::theArray, return_value_policy())); If you want to support both Boost 1.29 and never versions: #include #if BOOST_VERSION >= 103000 // use add_property #else // use def_readonly or def_readwrite #endif Ralf __________________________________ Do you Yahoo!? Yahoo! SiteBuilder - Free, easy-to-use web site design software http://sitebuilder.yahoo.com From jeff at brewer.com Fri Jul 25 05:48:34 2003 From: jeff at brewer.com (Jeff Brewer) Date: Thu, 24 Jul 2003 20:48:34 -0700 Subject: [C++-sig] def_readonly and const array members Message-ID: <3C609AD34AAF22488364057AA72EAC14019EE476@adsl-64-170-107-114.dsl.snfc21.pacbell.net> I am using Boost 1.30. Sorry I forgot to mention that. def_readonly seems to still in 1.30 and its implementation is: template self& def_readonly(char const* name, D B::*pm_) { D T::*pm = pm_; this->add_property(name, make_getter(pm)); return *this; } Is it deprecated though? However, I tried add_property with make_getter (which I usually use anyway) and I get the same error. Here is my new class_ code: class_("testStruct", init<>()) .add_property("theArray", make_getter(&testStruct::theArray, return_value_policy())); Thank you for the help, Jeff Brewer jeff at brewer.com -----Original Message----- From: Ralf W. Grosse-Kunstleve [mailto:rwgk at yahoo.com] Posted At: Thursday, July 24, 2003 6:06 PM Posted To: c++-sig Conversation: [C++-sig] def_readonly and const array members Subject: Re: [C++-sig] def_readonly and const array members --- Jeff Brewer wrote: > I am trying to wrap structs that have character arrays and I'm having > problems since I moved from MSVC 7 to MSVC 7.1 (VS .NET 2003). Here is > the struct I'm trying to expose the theArray member of using > class_::def_readonly: Are you also moving to a more recent boost? > .def_readonly("theArray", &testStruct::theArray); Try this instead: #include #include .add_property("theArray", make_getter(&testStruct::theArray, return_value_policy())); If you want to support both Boost 1.29 and never versions: #include #if BOOST_VERSION >= 103000 // use add_property #else // use def_readonly or def_readwrite #endif Ralf __________________________________ Do you Yahoo!? Yahoo! SiteBuilder - Free, easy-to-use web site design software http://sitebuilder.yahoo.com _______________________________________________ C++-sig mailing list C++-sig at python.org http://mail.python.org/mailman/listinfo/c++-sig From christoph.wiedemann at daimlerchrysler.com Fri Jul 25 16:55:46 2003 From: christoph.wiedemann at daimlerchrysler.com (christoph.wiedemann at daimlerchrysler.com) Date: Fri, 25 Jul 2003 16:55:46 +0200 Subject: [C++-sig] pure virtual methods with pyste Message-ID: <0057440010259079000002L492*@MHS> Hello, i'm a boost.python / pyste newbie, and what i've seen so far looks very well to me. I am especially interested in using pyste for creating python bindings. However, i've ran into the following problem with pyste: All pure virtual methods of abstract classes are hidden in python, i.e. it's not accessible to use them in python. I've played around with 'normal' boost.python, and managed it to create wrappers for pure virtual methods. Is it planned to produce bindings for pure virtual functions or am i asking for the impossible ? Thanks for the great work ! Christoph From dave at boost-consulting.com Fri Jul 25 17:27:02 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 25 Jul 2003 11:27:02 -0400 Subject: [C++-sig] Re: more cross-module problems References: <5.1.0.14.2.20030723111002.02e37008@mail.earthlink.net> <5.1.0.14.2.20030724080409.041dcd00@mail.mindspring.com> Message-ID: greg Landrum writes: > At 07:16 AM 7/24/2003, David Abrahams wrote: > >>None of these problems with boost::any have anything to do with >>Boost.Python per-se. I'll try to explain what's going on if you'll >>agree to write a FAQ entry or other documentation page for >>Boost.Python which describes the cross-module issues in detail. Deal? > > you drive a hard bargain... > yeah, it's a deal. Now that I think about it, this is going to have to be a FAQ about dynamic linking, RTTI, and exception-handling issues in general. I'll help you get it into shape. OK, here's the skinny. There are three basic dynamic linking models; I'll call these Global - "everything" is shared across the link boundary. This is what usually happens on Unix systems when dynamic linking; it's much like static linking (but not exactly). The global model is not available on Windows (this might be a good thing). Explicit - explicitly marked symbols are shared across the link boundary. This is what Windows compilers do with DLLs using __declspec(dllexport)/__declspec(dllimport). Although the explicit model is technically available on many Unices, it's usually very cumbersome and requires special support from scripts outside the compiler. Insular - This is the model used for plugins where no symbols are shared. Instead, you open the shared library explicitly and get (function) pointers to the symbols you're looking for. Python uses this model to open extension modules, so that extension module writers don't need to know what symbols other extension modules might be using. On Unix systems, Python is an executable which opens extension modules using the Insular model (dlopen), and on most systems the Python symbols used by extension modules are simply left unresolved and, as far as I know, because they are unresolved they automatically get hooked up to the symbols in the Python executable. AIX is a bit different - because it has true insulation Python explicitly hooks all its symbols up to the extension module when it is loaded. On Windows, that implicit back-linking is not available, so the Python executable is just a shell which links Explicitly to the Python DLL. Extension modules are loaded by Python using the Insular model but also link to the Python DLL using the Explicit model. I think Python doesn't do something similar for AIX only because of a failure of the imagination ;-> On Windows, Boost.Python extension modules link to the Boost.Python library using the Explicit model. On Unix systems, they use the Global model. Note, however, that the fact that two extension modules are linked to the same library with the Global model does not mean the extension modules share all symbols. In fact (excepton Tru64 when -tlocal is not used to link -- not recommended), the extension modules will *only* share a symbol which is also present in a library they are both linked to. Most of the subtle problems with dynamic linking C++ have to do with symbols C++ generates implicitly: RTTI and EH information virtual tables static data members of class template instantiations static variables in function template instantiations Typically, in the Global model this information (known as "weak symbols" on Linux) is generated in every translation unit where it is used, and resolved away at link time. Of course, that leaves us with a single copy per link unit (executable or shared library), and which copy is used needs to be resolved at load time.** The solutions generally come down to controlling where those symbols are generated and how they are shared across boundaries. Whether the first two things are a problem for your application depends in part on the ABI (application binary interface) of your compiler. The ABI encompasses issues such as function calling convention, class layout, the format of EH tables, the format of RTTI information, and of course, the procedures the compiler uses to manipulate that information. Your problem with boost::any was an interaction with the compiler's implementation of dynamic_cast. Recent GCCs determine dynamic type equivalence by comparing the *addresses* (not the contents) of their RTTI information. Because your two extension modules are not sharing any symbols other than those in the Boost.Python library, each one gets its own copy of the RTTI for the class in the any object, and the template instantiation of the any_cast on each side of the library boundary uses a different copy. The solution is to get that RTTI information generated in a place that both libraries can see. The best way to achieve that is to link both extension modules to a common shared library using the global model, and put the RTTI information there. For the case in question, you might achieve that by explicitly instantiating the any_cast template there. The problem we had earlier with catching exceptions is an interaction with the compiler's implementation of EH and the behavior of glibc under dynamic linking. Recent glibc implementations have an "inconvenient" (charitably speaking) behavior with weak symbols. The result is that if the symbol appears in both extension modules *and* in the Boost.Python shared library, the first extension module loaded will share a copy with the Boost.Python library and each module loaded thereafter will get its own copy. Fortunately, I knew that classes with non-inline virtual functions are different, and usually a *strong* symbol gets generated in the translation unit containing the class' first non-inline virtual function. By adding a virtual destructor in the Boost.Python library we ensured that both extension modules got the same copy of the exception's EH info. >>The Windows crash, FWIW, is a poor-QOI issue "bug" in the Dinkumware >>standard library that ships with vc6. vc7 solves it: This problem is that the vc6 associative containers use a special static data member representing a "NULL" node, used as a sentinel to tell the container implementation where the "edge" is, so it would stop searching there. Because you instantiated the map<> template in two separate extension modules, each one got it's own copy of the "NULL" node, and a map passed across the boundary would contain the wrong sentinel value for the code on the other side. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Fri Jul 25 17:38:12 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 25 Jul 2003 11:38:12 -0400 Subject: [C++-sig] Re: def_readonly and const array members References: <3C609AD34AAF22488364057AA72EAC14019EE476@adsl-64-170-107-114.dsl.snfc21.pacbell.net> Message-ID: "Jeff Brewer" writes: > I am using Boost 1.30. Sorry I forgot to mention that. > > def_readonly seems to still in 1.30 and its implementation is: > template > self& def_readonly(char const* name, D B::*pm_) > { > D T::*pm = pm_; > this->add_property(name, make_getter(pm)); > return *this; > } > Is it deprecated though? Nope. I don't have time to figure out why this isn't working for you right now, but... > However, I tried add_property with make_getter (which I usually use > anyway) and I get the same error. Here is my new class_ code: > > class_("testStruct", init<>()) > .add_property("theArray", > make_getter(&testStruct::theArray, > return_value_policy())); Why not skip the to_python_converter, and instead build a "get" function for a property, something like: template get_array { static tuple execute(C& c) { list l; for (unsigned i = 0; i < N; ++i) l.append((c.*pm)[N]); return tuple(l); } }; class_("testStruct", init<>()) .add_property( "theArray" , &get_array< unsigned char , 16 , testStruct , &testStruct::theArray >::execute ); -- Dave Abrahams Boost Consulting www.boost-consulting.com From grafik666 at redshift-software.com Fri Jul 25 17:49:28 2003 From: grafik666 at redshift-software.com (Rene Rivera) Date: Fri, 25 Jul 2003 10:49:28 -0500 Subject: [C++-sig] Re: more cross-module problems In-Reply-To: Message-ID: <20030725104929-r01010800-84162a23-0860-0108@12.100.89.43> [2003-07-25] David Abrahams wrote: >On Windows, that implicit back-linking is not available, so the Python >executable is just a shell which links Explicitly to the Python DLL. >Extension modules are loaded by Python using the Insular model but >also link to the Python DLL using the Explicit model. I think Python >doesn't do something similar for AIX only because of a failure of the >imagination ;-> The _option_ to build Python as a shared library is now available in 2.3, for all Unix variants I think. -- Too bad it's not a requirement. -- grafik - Don't Assume Anything -- rrivera (at) acm.org - grafik (at) redshift-software.com -- 102708583 (at) icq From rwgk at yahoo.com Fri Jul 25 17:59:51 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Fri, 25 Jul 2003 08:59:51 -0700 (PDT) Subject: [C++-sig] Re: def_readonly and const array members In-Reply-To: Message-ID: <20030725155951.70954.qmail@web20204.mail.yahoo.com> --- David Abrahams wrote: > "Jeff Brewer" writes: > > > I am using Boost 1.30. Sorry I forgot to mention that. > > > > def_readonly seems to still in 1.30 and its implementation is: > > template > > self& def_readonly(char const* name, D B::*pm_) > > { > > D T::*pm = pm_; > > this->add_property(name, make_getter(pm)); > > return *this; > > } > > Is it deprecated though? > > Nope. I don't have time to figure out why this isn't working for you > right now, but... If David cannot figure it out, maybe it is time to admit that I am lost, too. I am doing all the time what you are trying to do, under many platforms including Visual C++ 7.1. However, I've never tried it with char arrays. What happens if you change your small test to work with, say, int instead of char? I am not sure it will help, but here is my "to_tuple" converter: template struct to_tuple { static PyObject* convert(ContainerType const& a) { boost::python::list result; for(std::size_t i=0;i I'm trying -- and failing miserably. According to bjam -d+2 -a -q (run from boost_1_30_0) the C++ compilation command being used is: g++ -c -Wall -ftemplate-depth-100 -DBOOST_PYTHON_DYNAMIC_LIB -DBOOST_PYTHON_SOURCE -g -O0 -fno-inline -fPIC -I"libs/python/build" -I "/usr/local/include/python2.3" -I "/home/alex/pyr/boost_1_30_0" -o "libs/python/build/bin/libboost_python.so/gcc/debug/runtime-link-dynamic/shared-linkable-true/numeric.o" "libs/python/build/../src/numeric.cpp" This first warns about a redefinition of _POSIX_C_SOURCE (in /usr/local/include/python2.3/pyconfig.h:844:1 , already defined in /usr/include/features.h:131:1 -- hopefully a bening warning...?). Then the killers - a slew of error messages about /home/alex/pyr/boost_1_30_0/boost/python/converter/builtin_converters.hpp:106: of "parse error before & token" followed by "syntax error before & token", then again the same two messages for three more tokens (const > }), then again for lines 107, then for line 112 (and also 113, 114, 115, ...) errors that "to_python_value" is not a template, "detail" is not a class or namespace, etc etc. I've tried peering into the macros and templates involved but so far haven't come anywhere close to any understanding. I hope it's just some silly error on my part -- any suggestions...? Thanks, Alex From dave at boost-consulting.com Fri Jul 25 19:46:42 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 25 Jul 2003 13:46:42 -0400 Subject: [C++-sig] Re: building Boost 1.30 with gcc 3.2.2 on Linux (Mandrake 9.1), w/Python 2.3 References: <200307251904.13711.aleaxit@yahoo.com> Message-ID: Alex Martelli writes: > I'm trying -- and failing miserably. According to bjam -d+2 -a -q (run from > boost_1_30_0) the C++ compilation command being used is: > > g++ -c -Wall -ftemplate-depth-100 -DBOOST_PYTHON_DYNAMIC_LIB > -DBOOST_PYTHON_SOURCE -g -O0 -fno-inline -fPIC -I"libs/python/build" -I > "/usr/local/include/python2.3" -I "/home/alex/pyr/boost_1_30_0" -o > "libs/python/build/bin/libboost_python.so/gcc/debug/runtime-link-dynamic/shared-linkable-true/numeric.o" > "libs/python/build/../src/numeric.cpp" > > This first warns about a redefinition of _POSIX_C_SOURCE (in > /usr/local/include/python2.3/pyconfig.h:844:1 , already defined in > /usr/include/features.h:131:1 -- hopefully a bening warning...?). > > Then the killers - a slew of error messages about > /home/alex/pyr/boost_1_30_0/boost/python/converter/builtin_converters.hpp:106: > of "parse error before & token" followed by "syntax error before & token", > then again the same two messages for three more tokens (const > }), then > again for lines 107, then for line 112 (and also 113, 114, 115, ...) errors > that "to_python_value" is not a template, "detail" is not a class or > namespace, etc etc. I've tried peering into the macros and templates > involved but so far haven't come anywhere close to any understanding. > > I hope it's just some silly error on my part -- any suggestions...? Get the CVS; 1.30.0 doesn't work with Python 2.3. HTH, -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Fri Jul 25 23:59:56 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Fri, 25 Jul 2003 18:59:56 -0300 Subject: [C++-sig] pure virtual methods with pyste In-Reply-To: <0057440010259079000002L492*@MHS> References: <0057440010259079000002L492*@MHS> Message-ID: <3F21A85C.90404@globalite.com.br> Hi Christoph, christoph.wiedemann at daimlerchrysler.com wrote: >Hello, > >i'm a boost.python / pyste newbie, and what i've seen so far looks very well to >me. I am especially interested in using pyste for creating python bindings. > >However, i've ran into the following problem with pyste: All pure virtual >methods of abstract classes are hidden in python, i.e. it's not accessible to >use them in python. I've played around with 'normal' boost.python, and managed >it to create wrappers for pure virtual methods. Is it planned to produce >bindings for pure virtual functions or am i asking for the impossible ? > > Yes, it follows the procedure in the tutorial about abstract virtual functions, ie, it only generates the virtual wrapper. You should still be able to override the abstract member functions in Python, though... is this the problem you're having? Regards, Nicodemus. From dave at boost-consulting.com Sat Jul 26 01:03:19 2003 From: dave at boost-consulting.com (David Abrahams) Date: Fri, 25 Jul 2003 19:03:19 -0400 Subject: [C++-sig] Re: Problem build Boost.Python In-Reply-To: (Bren's message of "Fri, 25 Jul 2003 17:37:44 -0400") References: Message-ID: The following message is a courtesy copy of an article that has been posted to comp.lang.python as well. Bren writes: > Hi, > > Pardon my stupid, but I'm having a problem building Boost.Python as > per the instructions at > http://www.boost.org/libs/python/doc/building.html > > I got boost-build-2.0-m6.zip from sourceforge and build bjam.exe. It is possible to build Boost.Python under Boost.Build-2.0, but not using those instructions. Boost.Build v1 is still the official build system of Boost for the time being. [Boost.Build guys, do we need to rename the BBv2 prerelease so this confusion doesn't recur?] It looks like you're on windows, so you should either get the precompiled executable in bjam-3.1.4-2-ntx86.zip, or visit the tools/build/jam_src subdirectory of your Boost installation and invoke build.bat as per http://www.boost.org/tools/build/jam_src/index.html#installing > I've tried several ways: > > bjam -a > bjam -sTOOLS="msvc" > bjam -sTOOLS=msvc > > I tried with and without the using msvc ; in user-config.jam. > > In every case I get: > > C:/Project/boost/tools\boostbook.jam:86: in boostbook.init > *** argument error > * rule path.make ( native ) > * called with: ( ) > * missing argument native > C:/Project/boost/new\path.jam:42:see definition of rule 'path.make' > being called > > C:/Project/boost/new\toolset.jam:22: in using > C:\Project\boost\new\../new\user-config.jam:58: in modules.load > C:/Project/boost\build-system.jam:55: in load > C:\Project\boost\new\..\kernel\modules.jam:296: in import > C:\Project\boost\new\..\kernel\bootstrap.jam:122: in boost-build > C:\Project\boost\new\boost-build.jam:2: in module scope > > > Can anyone help? > HTH, -- Dave Abrahams Boost Consulting www.boost-consulting.com From alex at glumol.com Sat Jul 26 03:52:35 2003 From: alex at glumol.com (Alex) Date: Sat, 26 Jul 2003 03:52:35 +0200 Subject: [C++-sig] building boost.python with python 2.3 Message-ID: <004201c35318$9667c750$81123951@knar> Hi I try to build boost.python with Visual C++ 7 using the build project given in ..\build\VisualStudio\ The build is ok when I use the python 2.2 includes and libs paths but I get something like 1600 errors when using python 2.3... have I something in particular to do to use python 2.3 ? regards Alex Legrand -------------- next part -------------- An HTML attachment was scrubbed... URL: From drlinux at columbus.rr.com Sat Jul 26 04:14:29 2003 From: drlinux at columbus.rr.com (Dave Reed) Date: Fri, 25 Jul 2003 22:14:29 -0400 Subject: [C++-sig] Re: building boost.python with python 2.3 In-Reply-To: <004201c35318$9667c750$81123951@knar> References: <004201c35318$9667c750$81123951@knar> Message-ID: <200307252214.29932.drlinux@columbus.rr.com> On Friday 25 July 2003 21:52, Alex wrote: > Hi > > I try to build boost.python with Visual C++ 7 using the build project given in ..\build\VisualStudio\ > The build is ok when I use the python 2.2 includes and libs paths but I get something like 1600 errors when using python 2.3... > have I something in particular to do to use python 2.3 ? > > regards > > Alex Legrand > David Abrahams posted this statement 8 hours earlier today: Get the CVS; 1.30.0 doesn't work with Python 2.3. Dave From temas at box5.net Sat Jul 26 09:32:02 2003 From: temas at box5.net (Thomas Muldowney) Date: 26 Jul 2003 02:32:02 -0500 Subject: [C++-sig] Wrapping Just an Abstract Base Message-ID: <1059204722.12031.6.camel@corrosion> I'm having a mental breakdown on this one. I have a factory returning a pointer to an abstract base class that I've wrapped. However, I can't logically wrap the actual derived class because it's generated in a plugin. So, when I go to make a call on one of the abstract functions it fails with an AttributeError exception. Is there anyway to handle this in a clean manner that keeps the API near the C++ API? I've played around with writing wrapper functions (taking the base class pointer) that are defined on the class using the same name as the virtual function. Sadly, from my mailing list searches on this subject it seems this is a bad idea and can possibly lead to lookup loops? It does seem to run properly, though. Would love some feedback or a kick in the head if I'm missing something in the docs and sites. Thanks. --temas From dave at boost-consulting.com Sat Jul 26 13:29:59 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 26 Jul 2003 07:29:59 -0400 Subject: [C++-sig] Re: Wrapping Just an Abstract Base References: <1059204722.12031.6.camel@corrosion> Message-ID: Thomas Muldowney writes: > I'm having a mental breakdown on this one. I have a factory returning a > pointer to an abstract base class that I've wrapped. Abstract* factory(); > However, I can't logically wrap the actual derived class because > it's generated in a plugin. What do you mean by "plugin"? Some other extension module? > So, when I go to make a call on one of the abstract functions it "pure virtual"-------------------^^^^^^^^? > fails with an AttributeError exception. Is there anyway to handle > this in a clean manner that keeps the API near the C++ API? class_("Abstract", no_init) .def("pure_virtual_function1", &Abstract::pure_virtual_function1) .def("pure_virtual_function2", &Abstract::pure_virtual_function2) ... ; ?? > I've played around with writing wrapper functions (taking the base > class pointer) that are defined on the class using the same name as > the virtual function. Sadly, from my mailing list searches on this > subject it seems this is a bad idea and can possibly lead to lookup > loops? Please post some code which illustrates what you're doing. I'm sure it's unneccessary, but I can't quite understand it either. > It does seem to run properly, though. Would love some feedback or a > kick in the head if I'm missing something in the docs and sites. Sorry, remote cranial kicks cost extra. -- Dave Abrahams Boost Consulting www.boost-consulting.com From temas at box5.net Sat Jul 26 19:05:44 2003 From: temas at box5.net (Thomas Muldowney) Date: 26 Jul 2003 12:05:44 -0500 Subject: [C++-sig] Re: Wrapping Just an Abstract Base In-Reply-To: References: <1059204722.12031.6.camel@corrosion> Message-ID: <1059239144.12979.7.camel@corrosion> *sigh* no more 2am emails. Here's some code that is similar: #include #include using namespace boost::python; class Base { public: virtual void foo() = 0; }; class Base_Wrap : public Base { public: void foo() { std::cout << "Base_Wrap foo()" << std::endl; } }; class Deriv : public Base { public: void foo() { std::cout << "Deriv foo()" << std::endl; } }; Base* createBase() { Base* b = new Deriv; return b; } BOOST_PYTHON_MODULE(testA) { class_("Base", no_init); def("createBase", createBase, return_value_policy()); } It seemed implied to me by the docs and some other emails that foo should not be defined in Base. I had done that in the past, but changed on this refactoring of the code. Although not demonstrated in this code, when I say plugin I mean a dynamic library/shared object that is loaded using dynlib. It actually provides the implementation of the factory. --temas On Sat, 2003-07-26 at 06:29, David Abrahams wrote: > Thomas Muldowney writes: > > > I'm having a mental breakdown on this one. I have a factory returning a > > pointer to an abstract base class that I've wrapped. > > > Abstract* factory(); > > > However, I can't logically wrap the actual derived class because > > it's generated in a plugin. > > What do you mean by "plugin"? Some other extension module? > > > So, when I go to make a call on one of the abstract functions it > "pure virtual"-------------------^^^^^^^^? > > fails with an AttributeError exception. Is there anyway to handle > > this in a clean manner that keeps the API near the C++ API? > > > class_("Abstract", no_init) > .def("pure_virtual_function1", &Abstract::pure_virtual_function1) > .def("pure_virtual_function2", &Abstract::pure_virtual_function2) > ... > ; > > ?? > > > I've played around with writing wrapper functions (taking the base > > class pointer) that are defined on the class using the same name as > > the virtual function. Sadly, from my mailing list searches on this > > subject it seems this is a bad idea and can possibly lead to lookup > > loops? > > Please post some code which illustrates what you're doing. I'm sure > it's unneccessary, but I can't quite understand it either. > > > It does seem to run properly, though. Would love some feedback or a > > kick in the head if I'm missing something in the docs and sites. > > Sorry, remote cranial kicks cost extra. From dave at boost-consulting.com Sat Jul 26 20:31:47 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 26 Jul 2003 14:31:47 -0400 Subject: [C++-sig] Re: Wrapping Just an Abstract Base References: <1059204722.12031.6.camel@corrosion> <1059239144.12979.7.camel@corrosion> Message-ID: Thomas Muldowney writes: > *sigh* no more 2am emails. > > Here's some code that is similar: > > #include > #include > > using namespace boost::python; > > class Base > { > public: > virtual void foo() = 0; > }; > > class Base_Wrap : public Base > { > public: > void foo() > { std::cout << "Base_Wrap foo()" << std::endl; } > }; > > class Deriv : public Base > { > public: > void foo() > { std::cout << "Deriv foo()" << std::endl; } > }; > > Base* createBase() > { > Base* b = new Deriv; > return b; > } > > BOOST_PYTHON_MODULE(testA) > { > class_("Base", no_init); > > def("createBase", createBase, > return_value_policy()); > } This code won't compile, will it? > It seemed implied to me by the docs and some other emails that foo > should not be defined in Base. What implied that? Ideally Boost.Python shouldn't have any effect on the design of the classes that it wraps. Base_Wrap should only be used to dispatch virtual functions to Python with call_method. > I had done that in the past, but changed on this refactoring of the > code. Although not demonstrated in this code, when I say plugin I > mean a dynamic library/shared object that is loaded using dynlib. > It actually provides the implementation of the factory. Your code isn't demonstrating much at all, since it doesn't show an example of what you're trying to accomplish. Maybe someone else can help you; I have no clue what you're after, sorry! P.S. Did you try what I suggested in my previous reply? class_("Abstract", no_init) .def("pure_virtual_function1", &Abstract::pure_virtual_function1) .def("pure_virtual_function2", &Abstract::pure_virtual_function2) ... ; -- Dave Abrahams Boost Consulting www.boost-consulting.com From temas at box5.net Sat Jul 26 22:16:47 2003 From: temas at box5.net (Thomas Muldowney) Date: 26 Jul 2003 15:16:47 -0500 Subject: [C++-sig] Re: Wrapping Just an Abstract Base In-Reply-To: References: <1059204722.12031.6.camel@corrosion> <1059239144.12979.7.camel@corrosion> Message-ID: <1059250607.12979.10.camel@corrosion> On Sat, 2003-07-26 at 13:31, David Abrahams wrote: > This code won't compile, will it? > It does. > Your code isn't demonstrating much at all, since it doesn't show an > example of what you're trying to accomplish. Maybe someone else can > help you; I have no clue what you're after, sorry! > > P.S. Did you try what I suggested in my previous reply? > > class_("Abstract", no_init) > .def("pure_virtual_function1", &Abstract::pure_virtual_function1) > .def("pure_virtual_function2", &Abstract::pure_virtual_function2) > ... > ; Apologies for the unclear code, and the suggestion does work, so thanks. --temas From dave at boost-consulting.com Sun Jul 27 04:03:08 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sat, 26 Jul 2003 22:03:08 -0400 Subject: [C++-sig] Re: introspecting functions References: <1058327924.12657.57.camel@bluefish> Message-ID: Daniel Holth writes: > C++-siggers, > > I have looked into how pydoc works. It doesn't look too bad. Pydoc > does a large part of its work using the inspect module to look at code > objects. > > 'Real' Python functions have a func_code property. Example: > Anyway, the first expression gives me all the variable names in the > function. The first three .co_varnames appear to be the function > argument names (.co_argcount). You can also retrieve the filename the > function was compiled from and the bytecode for the function. > > I don't know what the consequences of using a fake func_code are and I > would have played with it more but I don't know how to best add a > func_code to my boost::python classes, Just try with your own callable object in a new-style class: class bplfunc(object): def __init__(self): self.func_code = ... def __call__(...) ... class myclass(object): some_method = bplfunc() Throw it at PyDoc and see what's needed to get it to respond in a reasonable way. If you can get that sorted out I'm sure we can implement something equivalent in Boost.Python. A note: I think I'd want to represent the C++ argument types in func_code.co_varnames. When no arg(...) expressions are used in wrapping to supply variable names, it'd be just the types. Otherwise, it'd be the types + names. Seeing the types would at least give a very strong hint about usage. > but it's an interesting idea. > You could probably figure out how to implement the equivalent of def > foo(bar=1, baz=2) for the C++ for example. > > Whoah! Pydoc actually parses the bytecodes for classes in order to > document what the default variable values are You're kidding! Why not just use func_defaults?? > (not what the variable names are though). It mightn't be outrageous > to compile lots of little def wrappedfunction(a, b=None): pass in > order to make some bytecode though, or even replace : pass with : > call_boost_function(). I'd be shocked if there was actually any bytecode needed. -- Dave Abrahams Boost Consulting www.boost-consulting.com From jeff at brewer.com Sun Jul 27 06:43:14 2003 From: jeff at brewer.com (Jeff Brewer) Date: Sat, 26 Jul 2003 21:43:14 -0700 Subject: [C++-sig] Re: def_readonly and const array members Message-ID: <3C609AD34AAF22488364057AA72EAC14019EE47C@adsl-64-170-107-114.dsl.snfc21.pacbell.net> Sorry about the error message difference - nothing funny is going on. I tested with an 8 character array first and then a 16. I included the error message from the 8 try. I'll try it with an int array and post the results. Jeff Brewer -----Original Message----- From: Ralf W. Grosse-Kunstleve [mailto:rwgk at yahoo.com] Posted At: Friday, July 25, 2003 9:00 AM Posted To: c++-sig Conversation: [C++-sig] Re: def_readonly and const array members Subject: Re: [C++-sig] Re: def_readonly and const array members --- David Abrahams wrote: > "Jeff Brewer" writes: > > > I am using Boost 1.30. Sorry I forgot to mention that. > > > > def_readonly seems to still in 1.30 and its implementation is: > > template > > self& def_readonly(char const* name, D B::*pm_) > > { > > D T::*pm = pm_; > > this->add_property(name, make_getter(pm)); > > return *this; > > } > > Is it deprecated though? > > Nope. I don't have time to figure out why this isn't working for you > right now, but... If David cannot figure it out, maybe it is time to admit that I am lost, too. I am doing all the time what you are trying to do, under many platforms including Visual C++ 7.1. However, I've never tried it with char arrays. What happens if you change your small test to work with, say, int instead of char? I am not sure it will help, but here is my "to_tuple" converter: template struct to_tuple { static PyObject* convert(ContainerType const& a) { boost::python::list result; for(std::size_t i=0;i Message-ID: "Jeff Brewer" writes: > Sorry about the error message difference - nothing funny is going on. I > tested with an 8 character array first and then a 16. I included the > error message from the 8 try. I'll try it with an int array and post the > results. Did you try my suggestion? -- Dave Abrahams Boost Consulting www.boost-consulting.com From nickm at sitius.com Sun Jul 27 23:15:19 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Sun, 27 Jul 2003 17:15:19 -0400 Subject: [C++-sig] args patch Message-ID: <3F2440E7.C2000F56@sitius.com> Dave, I am posting the diffs from 1.29.0 plus the test and doc files. Sorry for the delay. I hope you won't have problems applying the diffs. Nikolay -------------- next part -------------- 44a45,52 > keywords operator , (const keywords<1> &k) const > { > python::detail::keywords res; > std::copy(elements, elements+size, res.elements); > res.elements[size] = k.elements[0]; > return res; > } > keywords operator , (const char *name) const; 46a55,57 > > > 97a109,129 > struct arg : detail::keywords<1> > { > template > arg &operator = (T const &value) > { > elements[0].default_value = handle<>(python::borrowed(object(value).ptr())); > return *this; > } > explicit arg (char const *name){elements[0].name = name;} > operator detail::keyword const &()const {return elements[0];} > }; > > namespace detail > { > template > inline keywords< keywords::size+1 > keywords::operator , (const char *name) const > { > return this->operator , (arg(name)); > } > } > -------------- next part -------------- 21a22 > keyword(char const* n=0):name(n){} -------------- next part -------------- 57a58 > unsigned m_nkeyword_values; -------------- next part -------------- 35a36 > , m_nkeyword_values(0) 42d42 < 48a49,52 > object tpl (handle<>( > PyTuple_New(names_and_defaults[i].default_value ? 2 : 1) > )); > 50,51c54,55 < m_arg_names.ptr() < , i + keyword_offset --- > tpl.ptr() > , 0 55a60,77 > > if(names_and_defaults[i].default_value) > { > PyTuple_SET_ITEM( > tpl.ptr() > , 1 > , incref(names_and_defaults[i].default_value.get()) > ); > > ++m_nkeyword_values; > } > > > PyTuple_SET_ITEM( > m_arg_names.ptr() > , i + keyword_offset > , incref(tpl.ptr()) > ); 82c104 < if (total_args >= f->m_min_arity && total_args <= f->m_max_arity) --- > if (total_args + f->m_nkeyword_values >= f->m_min_arity && total_args <= f->m_max_arity) 85c107 < if (nkeywords > 0) --- > if (nkeywords > 0 || total_args < f->m_min_arity) 94,95c116,117 < // build a new arg tuple < args2 = handle<>(PyTuple_New(total_args)); --- > // build a new arg tuple, will adjust its size later > args2 = handle<>(PyTuple_New(f->m_max_arity)); 102c124,128 < for (std::size_t j = nargs; j < total_args; ++j) --- > std::size_t j = nargs; > std::size_t k = nargs; > std::size_t size = PyTuple_GET_SIZE(f->m_arg_names.ptr()); > > for (; j < f->m_max_arity && j < size ; ++j) 104,105c130,138 < PyObject* value = PyDict_GetItem( < keywords, PyTuple_GET_ITEM(f->m_arg_names.ptr(), j)); --- > PyObject* kwd = PyTuple_GET_ITEM(f->m_arg_names.ptr(), j); > > PyObject* value = nkeywords ? PyDict_GetItem( > keywords, PyTuple_GET_ITEM(kwd, 0)) : 0; > > if (!value) > { > if (PyTuple_GET_SIZE(kwd) > 1) > value = PyTuple_GET_ITEM(kwd, 1); 113c146,170 < PyTuple_SET_ITEM(args2.get(), j, incref(value)); --- > }else > ++k; > > PyTuple_SET_ITEM(args2.get(), j, incref(value) > ); > } > > if (args2.get()) > { > //check if we proccessed all the arguments > if(k < total_args) > args2 = handle<>(); > > //adjust the parameter tuple size > if(jm_max_arity) > { > handle<> args3( PyTuple_New(j) ); > > for (size_t l = 0; l != j; ++ l) > { > PyTuple_SET_ITEM(args3.get(), l, PyTuple_GET_ITEM(args3.get(), l) ); > PyTuple_SET_ITEM(args2.get(), l, 0); > } > args2 = args3; > } -------------- next part -------------- ''' >>> from keywords import * >>> f = Foo() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> f = Foo(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f = Foo(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> f = Foo(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') >>> f = Foo(a=1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f = Foo(b=1) >>> f.a(), f.b(), f.n() (0, 1.0, '') >>> f = Foo(n="1") >>> f.a(), f.b(), f.n() (0, 0.0, '1') >>> f = Foo(1,n="1") >>> f.a(), f.b(), f.n() (1, 0.0, '1') >>> f.set() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> f.set(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f.set(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> f.set(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') >>> f.set(a=1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f.set(b=1) >>> f.a(), f.b(), f.n() (0, 1.0, '') >>> f.set(n="1") >>> f.a(), f.b(), f.n() (0, 0.0, '1') >>> f.set(1,n="1") >>> f.a(), f.b(), f.n() (1, 0.0, '1') ''' def run(args = None): import sys import doctest if args is not None: sys.argv = args return doctest.testmod(sys.modules.get(__name__)) if __name__ == '__main__': print "running..." import sys sys.exit(run()[0]) -------------- next part -------------- A non-text attachment was scrubbed... Name: keywords.cpp Type: application/x-unknown-content-type-cppfile Size: 1533 bytes Desc: not available URL: From nickm at sitius.com Sun Jul 27 23:38:52 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Sun, 27 Jul 2003 17:38:52 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> Message-ID: <3F24466C.908B316A@sitius.com> And here is "HTMLTidy" - version of the html file:) -------------- next part -------------- An HTML attachment was scrubbed... URL: From dave at boost-consulting.com Mon Jul 28 01:14:09 2003 From: dave at boost-consulting.com (David Abrahams) Date: Sun, 27 Jul 2003 19:14:09 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> Message-ID: Nikolay Mladenov writes: > Dave, > > I am posting the diffs from 1.29.0 plus the test and doc files. > Sorry for the delay. I hope you won't have problems applying the diffs. Hmm, it seems likely that I will. 1.29.0 is two releases old and we have made a lot of changes since then. Is there any chance you can give me a patch against the current CVS state? -- Dave Abrahams Boost Consulting www.boost-consulting.com From pierre.barbier at cirad.fr Mon Jul 28 10:31:19 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 28 Jul 2003 10:31:19 +0200 Subject: [C++-sig] Re: Segfault when calling python method from C++ In-Reply-To: References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> Message-ID: <3F24DF57.90904@cirad.fr> > > >You can post them here. After we discuss and get comfortable with >your approach, the first things I'll probably ask you for are tests >for the Boost.Python test suite and HTML documentation pages. > >Regards, > > Sorry for the delay but I was on vacation ... I begin by sending the three files used to export STL containers. By the time, it only works with g++-3.2 or later, but it's just a question of namespace and include locations. There is a _small_ help at the beginning. The only thing not written is for the handling of the exceptions: you have to call define_stl_exceptions() in your module function. The wcc files correspond to your hpp ones and the hh is here for tiled compilation only. My main concern about what you said is about the Boost.Python test suite ... how to document myself about how it works ? Thanks, -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 -------------- next part -------------- An embedded and charset-unspecified text was scrubbed... Name: stl2dict.wcc URL: -------------- next part -------------- An embedded and charset-unspecified text was scrubbed... Name: stl2list.wcc URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: exception.hh Type: text/x-c++hdr Size: 1794 bytes Desc: not available URL: -------------- next part -------------- An embedded and charset-unspecified text was scrubbed... Name: exception.wcc URL: From pierre.barbier at cirad.fr Mon Jul 28 10:37:37 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 28 Jul 2003 10:37:37 +0200 Subject: [C++-sig] Qt class to embed python in a c++ application Message-ID: <3F24E0D1.4030006@cirad.fr> Ok, here I send some files with classes to embed python. The use should be quite simple : you just have to instanciate the class PythonWnd and give it the module name and the module main function (which should be init#modulename). It should open another window in which you can enter python commands. It should even work without modules (but it's not tested). Thanks for your future comments :) -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 -------------- next part -------------- A non-text attachment was scrubbed... Name: embed_python.cc Type: text/x-c++src Size: 19751 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: embed_python.hh Type: text/x-c++hdr Size: 5108 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: edithistory.cc Type: text/x-c++src Size: 2246 bytes Desc: not available URL: -------------- next part -------------- A non-text attachment was scrubbed... Name: edithistory.hh Type: text/x-c++hdr Size: 1899 bytes Desc: not available URL: From pierre.barbier at cirad.fr Mon Jul 28 10:45:14 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 28 Jul 2003 10:45:14 +0200 Subject: [C++-sig] Qt class to embed python in a c++ application In-Reply-To: <3F24E0D1.4030006@cirad.fr> References: <3F24E0D1.4030006@cirad.fr> Message-ID: <3F24E29A.1020103@cirad.fr> I just forgot one thing : as I use pipes to get python outputs I really don't know if it can work on Windows .... -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From wiedeman at gmx.net Mon Jul 28 11:01:16 2003 From: wiedeman at gmx.net (wiedeman at gmx.net) Date: Mon, 28 Jul 2003 11:01:16 +0200 (MEST) Subject: [C++-sig] Re: pure virtual methods with pyste Message-ID: <27031.1059382876@www60.gmx.net> Hi Nicodemus, >Yes, it follows the procedure in the tutorial about abstract virtual >functions, ie, it only generates the virtual wrapper. You should still >be able to override the abstract member functions in Python, though... >is this the problem you're having? No, that's not my problem. I want to be able to use pointers to abstract classes within python without wrapping all the derived classes (in fact, they are plugins), and, if possible, without writing a call_f function for every pure virtual method. I've played around with boost.python and found the solution below (Test.cpp). With pyste, i'd get an empty class Abstract. I wonder, if my solution is dangerous or even wrong ? Thanks in advance, Christoph /* Test.cpp */ struct Abstract { virtual void a() = 0; }; #include using namespace boost::python; BOOST_PYTHON_MODULE(myclasses) { class_("Abstract") .def("a", &Abstract::a) ; } From dave at boost-consulting.com Mon Jul 28 13:42:54 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 07:42:54 -0400 Subject: [C++-sig] Re: Segfault when calling python method from C++ References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> <3F24DF57.90904@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: >> >> >>You can post them here. After we discuss and get comfortable with >>your approach, the first things I'll probably ask you for are tests >>for the Boost.Python test suite and HTML documentation pages. >> >>Regards, >> > Sorry for the delay but I was on vacation ... > I begin by sending the three files used to export STL containers. Hmm, Joel just checked in some support for this. See http://tinyurl.com/i9gv. > By the time, it only works with g++-3.2 or later, but it's just a > question of namespace and include locations. There is a _small_ > help at the beginning. The only thing not written is for the > handling of the exceptions: you have to call define_stl_exceptions() > in your module function. The wcc files correspond to your hpp ones > and the hh is here for tiled compilation only. The first thing I'd need in order to evaluate this is some examples and documentation which describe what it does. > My main concern about what you said is about the Boost.Python test > suite ... how to document myself about how it works ? I can't understand what you mean. Can you rephrase? Testing and documentation are two separate things; I want tests for libs/python/test and documentation for libs/python/doc. Oh, and BTW, the GPL is not Boost-compatible. http://www.boost.org/more/lib_guide.htm#License -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 13:48:56 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 07:48:56 -0400 Subject: [C++-sig] Re: pure virtual methods with pyste References: <27031.1059382876@www60.gmx.net> Message-ID: wiedeman at gmx.net writes: > Hi Nicodemus, > >>Yes, it follows the procedure in the tutorial about abstract virtual >>functions, ie, it only generates the virtual wrapper. You should still >>be able to override the abstract member functions in Python, though... >>is this the problem you're having? > > No, that's not my problem. I want to be able to use pointers to abstract > classes within python without wrapping all the derived classes (in fact, they > are plugins), and, if possible, without writing a call_f function for every > pure virtual method. > I've played around with boost.python and found the solution below > (Test.cpp). With pyste, i'd get an empty class Abstract. I wonder, if my solution is > dangerous or even wrong ? > > Thanks in advance, > Christoph > > /* Test.cpp */ > > struct Abstract { > virtual void a() = 0; > }; > > #include > > using namespace boost::python; > > BOOST_PYTHON_MODULE(myclasses) { > class_("Abstract") ^^^^^^^^^^^^ This part is wrong. > .def("a", &Abstract::a) > ; > } http://aspn.activestate.com/ASPN/Mail/Message/c++-sig/1748053 I'm not sure why people keep doing that; perhaps we need to fix the tutorial somehow? If you can, Christoph, it would be a big help if you could explain why you thought that was the right thing to do. Thanks, Dave -- Dave Abrahams Boost Consulting www.boost-consulting.com From alex at glumol.com Mon Jul 28 13:49:00 2003 From: alex at glumol.com (Alex) Date: Mon, 28 Jul 2003 13:49:00 +0200 Subject: [C++-sig] Virtual Functions with Default Implementations code sample Message-ID: <000501c354fe$3ca46920$81123951@knar> I can't build the "Virtual Functions with Default Implementations" code sample from the online tutorial : struct Base { virtual int f() { return 0; } }; struct BaseWrap : Base { BaseWrap(PyObject* self_) : self(self_) {} int f() { return call_method(self, "f"); } int default_f() { return Base::f(); } // <<=== ***ADDED*** PyObject* self; }; ------- class_("Base") .def("f", &Base::f, &BaseWrap::default_f) --> get the error "value_holder.hpp(131) : error C2661: 'BaseWrap::BaseWrap' : no overloaded function takes 2 parameters" ??? (btw I can build all the other code samples from the tutorial) ------- other newbie questions : Is there a place on the web where all the c++-sig at python mails are archived ? Does pyste can convert C++ function arguments to python keyword arguments ? From pierre.barbier at cirad.fr Mon Jul 28 15:02:13 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 28 Jul 2003 15:02:13 +0200 Subject: [C++-sig] Re: Segfault when calling python method from C++ In-Reply-To: References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> <3F24DF57.90904@cirad.fr> Message-ID: <3F251ED5.5050505@cirad.fr> David Abrahams wrote: >Hmm, Joel just checked in some support for this. See >http://tinyurl.com/i9gv. > > I didn't know this project. My goal, even if close, is somehow different: I want to be able to use the STL containers as if there were python list. At best, anybody should be able to export its own container as a python list. But it could be a good idea to use what Joel did ... > > >>By the time, it only works with g++-3.2 or later, but it's just a >>question of namespace and include locations. There is a _small_ >>help at the beginning. The only thing not written is for the >>handling of the exceptions: you have to call define_stl_exceptions() >>in your module function. The wcc files correspond to your hpp ones >>and the hh is here for tiled compilation only. >> >> > >The first thing I'd need in order to evaluate this is some examples >and documentation which describe what it does. > > Ok, I join an example of module along with a python test file. You just need to execute ths python file to test ... For the documentation I'm writing it and I'll send it to you as soon as possible. > > >>My main concern about what you said is about the Boost.Python test >>suite ... how to document myself about how it works ? >> >> > >I can't understand what you mean. Can you rephrase? Testing and >documentation are two separate things; I want tests for >libs/python/test and documentation for libs/python/doc. > I just wondered if you had any rule to write test suite. But if the kind of test I send you with this mail is ok ... > >Oh, and BTW, the GPL is not Boost-compatible. >http://www.boost.org/more/lib_guide.htm#License > > > Oh ... I didn't notice that ! By the way, what is the licence of Boost.Python ? I don't see any licence ! I think the best is to include my work (if you do include it) with the same licence as Boost.Python. Thanks, PS : I just noticed an error ... so I resend the stl2list.wcc file ... I can't assure it's totally unbugged -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 -------------- next part -------------- A non-text attachment was scrubbed... Name: stl2py.tgz Type: application/x-gtar Size: 5347 bytes Desc: not available URL: From wiedeman at gmx.net Mon Jul 28 15:08:47 2003 From: wiedeman at gmx.net (wiedeman at gmx.net) Date: Mon, 28 Jul 2003 15:08:47 +0200 (MEST) Subject: [C++-sig] Re: pure virtual methods with pyste References: Message-ID: <5999.1059397727@www46.gmx.net> Hello Dave, sorry for the error in the posted code. This wasn't due to misunderstanding of the tutorial, but due to copy & paste. In fact, i got the code working with 'normal' boost.python, but wondered, why pyste doesn't provide a wrapper for the pure virtual function a(). Here is the code: struct Abstract { virtual void a() = 0; }; #include using namespace boost::python; BOOST_PYTHON_MODULE(wrap_Test) { class_("Abstract", no_init) .def("a", &Abstract::a) ; } As far as i can tell, this code works fine, and Dave Abrahams suggested to do so in the thread he was pointing me on. Though the tutorial doesn't provide wrappers around pure virtual functions, the above code was quite obvious - but maybe it would be better to show how to wrap the pure virtual function f() of class Base. Christoph > > Hi Nicodemus, > > > >>Yes, it follows the procedure in the tutorial about abstract virtual > >>functions, ie, it only generates the virtual wrapper. You should still > >>be able to override the abstract member functions in Python, though... > >>is this the problem you're having? > > > > No, that's not my problem. I want to be able to use pointers to abstract > > classes within python without wrapping all the derived classes (in fact, > they > > are plugins), and, if possible, without writing a call_f function for > every > > pure virtual method. > > I've played around with boost.python and found the solution below > > (Test.cpp). With pyste, i'd get an empty class Abstract. I wonder, if my > solution is > > dangerous or even wrong ? > > > > Thanks in advance, > > Christoph > > > > /* Test.cpp */ > > > > struct Abstract { > > virtual void a() = 0; > > }; > > > > #include > > > > using namespace boost::python; > > > > BOOST_PYTHON_MODULE(myclasses) { > > class_("Abstract") > ^^^^^^^^^^^^ > This part is wrong. > > .def("a", &Abstract::a) > > ; > > } > > http://aspn.activestate.com/ASPN/Mail/Message/c++-sig/1748053 > > I'm not sure why people keep doing that; perhaps we need to fix the > tutorial somehow? If you can, Christoph, it would be a big help if > you could explain why you thought that was the right thing to do. > > Thanks, > Dave > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com > > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > From wiedeman at gmx.net Mon Jul 28 15:08:45 2003 From: wiedeman at gmx.net (wiedeman at gmx.net) Date: Mon, 28 Jul 2003 15:08:45 +0200 (MEST) Subject: [C++-sig] Re: pure virtual methods with pyste References: Message-ID: <12693.1059397725@www59.gmx.net> Hello Dave, sorry for the error in the posted code. This wasn't due to misunderstanding of the tutorial, but due to copy & paste. In fact, i got the code working with 'normal' boost.python, but wondered, why pyste doesn't provide a wrapper for the pure virtual function a(). Here is the code: struct Abstract { virtual void a() = 0; }; #include using namespace boost::python; BOOST_PYTHON_MODULE(wrap_Test) { class_("Abstract", no_init) .def("a", &Abstract::a) ; } As far as i can tell, this code works fine, and Dave Abrahams suggested to do so in the thread he was pointing me on. Though the tutorial doesn't provide wrappers around pure virtual functions, the above code was quite obvious - but maybe it would be better to show how to wrap the pure virtual function f() of class Base. Christoph > > Hi Nicodemus, > > > >>Yes, it follows the procedure in the tutorial about abstract virtual > >>functions, ie, it only generates the virtual wrapper. You should still > >>be able to override the abstract member functions in Python, though... > >>is this the problem you're having? > > > > No, that's not my problem. I want to be able to use pointers to abstract > > classes within python without wrapping all the derived classes (in fact, > they > > are plugins), and, if possible, without writing a call_f function for > every > > pure virtual method. > > I've played around with boost.python and found the solution below > > (Test.cpp). With pyste, i'd get an empty class Abstract. I wonder, if my > solution is > > dangerous or even wrong ? > > > > Thanks in advance, > > Christoph > > > > /* Test.cpp */ > > > > struct Abstract { > > virtual void a() = 0; > > }; > > > > #include > > > > using namespace boost::python; > > > > BOOST_PYTHON_MODULE(myclasses) { > > class_("Abstract") > ^^^^^^^^^^^^ > This part is wrong. > > .def("a", &Abstract::a) > > ; > > } > > http://aspn.activestate.com/ASPN/Mail/Message/c++-sig/1748053 > > I'm not sure why people keep doing that; perhaps we need to fix the > tutorial somehow? If you can, Christoph, it would be a big help if > you could explain why you thought that was the right thing to do. > > Thanks, > Dave > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com > > > _______________________________________________ > C++-sig mailing list > C++-sig at python.org > http://mail.python.org/mailman/listinfo/c++-sig > From dave at boost-consulting.com Mon Jul 28 15:31:52 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 09:31:52 -0400 Subject: [C++-sig] Re: Segfault when calling python method from C++ In-Reply-To: <3F24DF57.90904@cirad.fr> (Pierre Barbier de Reuille's message of "Mon, 28 Jul 2003 10:31:19 +0200") References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> <3F24DF57.90904@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: >> >> >>You can post them here. After we discuss and get comfortable with >>your approach, the first things I'll probably ask you for are tests >>for the Boost.Python test suite and HTML documentation pages. >> >>Regards, >> > Sorry for the delay but I was on vacation ... > I begin by sending the three files used to export STL containers. Hmm, Joel just checked in some support for this. See http://tinyurl.com/i9gv. > By the time, it only works with g++-3.2 or later, but it's just a > question of namespace and include locations. There is a _small_ > help at the beginning. The only thing not written is for the > handling of the exceptions: you have to call define_stl_exceptions() > in your module function. The wcc files correspond to your hpp ones > and the hh is here for tiled compilation only. The first thing I'd need in order to evaluate this is some examples and documentation which describe what it does. > My main concern about what you said is about the Boost.Python test > suite ... how to document myself about how it works ? I can't understand what you mean. Can you rephrase? Testing and documentation are two separate things; I want tests for libs/python/test and documentation for libs/python/doc. Oh, and BTW, the GPL is not Boost-compatible. http://www.boost.org/more/lib_guide.htm#License -- Dave Abrahams Boost Consulting www.boost-consulting.com From nickm at sitius.com Mon Jul 28 15:41:16 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Mon, 28 Jul 2003 09:41:16 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> Message-ID: <3F2527FC.50969E27@sitius.com> David Abrahams wrote: > > Nikolay Mladenov writes: > > > Dave, > > > > I am posting the diffs from 1.29.0 plus the test and doc files. > > Sorry for the delay. I hope you won't have problems applying the diffs. > > Hmm, it seems likely that I will. 1.29.0 is two releases old and we > have made a lot of changes since then. I noticed. > Is there any chance you can > give me a patch against the current CVS state? I can't get the cvs commands to work for me: $ cvs -d:pserver:anonymous at cvs.boost.sourceforge.net:/cvsroot/boost login (Logging in to anonymous at cvs.boost.sourceforge.net) CVS password: cvs [login aborted]: recv() from server cvs.boost.sourceforge.net: EOF This is what I always get back from the cvs. Do you know what is wrong with my cvs line? > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 15:46:31 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 09:46:31 -0400 Subject: [C++-sig] Re: Segfault when calling python method from C++ References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> <3F24DF57.90904@cirad.fr> <3F251ED5.5050505@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > David Abrahams wrote: > >>Hmm, Joel just checked in some support for this. See >>http://tinyurl.com/i9gv. >> > I didn't know this project. My goal, even if close, is somehow > different: I want to be able to use the STL containers as if there > were python list. How is that different from what Joel did? > At best, anybody should be able to export its own container as a > python list. But it could be a good idea to use what Joel did ... What you did does not appear to export the container "as a python list", but as a Python sequence. Exporting "as a list" would be more along the lines of the custom rvalue converters described in http://www.boost.org/libs/python/doc/v2/faq.html#question2, I think. >>>By the time, it only works with g++-3.2 or later, but it's just a >>>question of namespace and include locations. There is a _small_ >>>help at the beginning. The only thing not written is for the >>>handling of the exceptions: you have to call define_stl_exceptions() >>>in your module function. The wcc files correspond to your hpp ones >>>and the hh is here for tiled compilation only. >>> >> >>The first thing I'd need in order to evaluate this is some examples >>and documentation which describe what it does. >> > Ok, I join an example of module along with a python test file. You > just need to execute ths python file to test ... > For the documentation I'm writing it and I'll send it to you as soon > as possible. > >> >>>My main concern about what you said is about the Boost.Python test >>>suite ... how to document myself about how it works ? >>> >> >>I can't understand what you mean. Can you rephrase? Testing and >>documentation are two separate things; I want tests for >>libs/python/test and documentation for libs/python/doc. >> > I just wondered if you had any rule to write test suite. But if the > kind of test I send you with this mail is ok ... Actually, I would strongly prefer a test using the same format as all of the other tests, with doctest or using the unittest module as polymorphism.py does. >>Oh, and BTW, the GPL is not Boost-compatible. >>http://www.boost.org/more/lib_guide.htm#License >> >> > Oh ... I didn't notice that ! By the way, what is the licence of > Boost.Python ? I don't see any licence ! Permission to copy, use, modify, sell and distribute this software is granted provided this copyright notice appears in all copies. This software is provided "as is" without express or implied warranty, and with no claim as to its suitability for any purpose. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 15:46:41 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 09:46:41 -0400 Subject: [C++-sig] Re: Segfault when calling python method from C++ In-Reply-To: <3F251ED5.5050505@cirad.fr> (Pierre Barbier de Reuille's message of "Mon, 28 Jul 2003 15:02:13 +0200") References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> <3F24DF57.90904@cirad.fr> <3F251ED5.5050505@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > David Abrahams wrote: > >>Hmm, Joel just checked in some support for this. See >>http://tinyurl.com/i9gv. >> > I didn't know this project. My goal, even if close, is somehow > different: I want to be able to use the STL containers as if there > were python list. How is that different from what Joel did? > At best, anybody should be able to export its own container as a > python list. But it could be a good idea to use what Joel did ... What you did does not appear to export the container "as a python list", but as a Python sequence. Exporting "as a list" would be more along the lines of the custom rvalue converters described in http://www.boost.org/libs/python/doc/v2/faq.html#question2, I think. >>>By the time, it only works with g++-3.2 or later, but it's just a >>>question of namespace and include locations. There is a _small_ >>>help at the beginning. The only thing not written is for the >>>handling of the exceptions: you have to call define_stl_exceptions() >>>in your module function. The wcc files correspond to your hpp ones >>>and the hh is here for tiled compilation only. >>> >> >>The first thing I'd need in order to evaluate this is some examples >>and documentation which describe what it does. >> > Ok, I join an example of module along with a python test file. You > just need to execute ths python file to test ... > For the documentation I'm writing it and I'll send it to you as soon > as possible. > >> >>>My main concern about what you said is about the Boost.Python test >>>suite ... how to document myself about how it works ? >>> >> >>I can't understand what you mean. Can you rephrase? Testing and >>documentation are two separate things; I want tests for >>libs/python/test and documentation for libs/python/doc. >> > I just wondered if you had any rule to write test suite. But if the > kind of test I send you with this mail is ok ... Actually, I would strongly prefer a test using the same format as all of the other tests, with doctest or using the unittest module as polymorphism.py does. >>Oh, and BTW, the GPL is not Boost-compatible. >>http://www.boost.org/more/lib_guide.htm#License >> >> > Oh ... I didn't notice that ! By the way, what is the licence of > Boost.Python ? I don't see any licence ! Permission to copy, use, modify, sell and distribute this software is granted provided this copyright notice appears in all copies. This software is provided "as is" without express or implied warranty, and with no claim as to its suitability for any purpose. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 15:47:25 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 09:47:25 -0400 Subject: [C++-sig] Re: Qt class to embed python in a c++ application References: <3F24E0D1.4030006@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > Ok, here I send some files with classes to embed python. The use > should be quite simple : you just have to instanciate the class > PythonWnd and give it the module name and the module main function > (which should be init#modulename). It should open another window in > which you can enter python commands. It should even work without > modules (but it's not tested). > > Thanks for your future comments :) All the same questions about examples, documentation, and tests apply here as well. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 15:59:01 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 09:59:01 -0400 Subject: [C++-sig] Re: Virtual Functions with Default Implementations code sample References: <000501c354fe$3ca46920$81123951@knar> Message-ID: "Alex" writes: > I can't build the "Virtual Functions with Default Implementations" code > sample from the online tutorial : > > struct Base > { > virtual int f() { return 0; } > }; > > struct BaseWrap : Base > { > BaseWrap(PyObject* self_) > : self(self_) {} > int f() { return call_method(self, "f"); } > int default_f() { return Base::f(); } // <<=== ***ADDED*** > PyObject* self; > }; > > ------- > > class_("Base") > .def("f", &Base::f, &BaseWrap::default_f) > > > --> get the error "value_holder.hpp(131) : error C2661: 'BaseWrap::BaseWrap' > : no overloaded function takes 2 parameters" This is a tutorial bug. We need to either: 1. Add a copying constructor: BaseWrap(PyObject* self_, Base const& rhs) : Base(rhs), self(self_) {} 2. Use noncopyable in the wrapper: class_("Base") .def("f", &Base::f, &BaseWrap::default_f) ; [Joel, could you choose an appropriate fix?] > (btw I can build all the other code samples from the tutorial) That's a relief! > ------- > > other newbie questions : > > Is there a place on the web where all the c++-sig at python mails are archived > ? http://www.boost.org/more/mailing_lists.htm#cplussig lists two archives in addition to http://mail.python.org/pipermail/c++-sig/.. > Does pyste can convert C++ function arguments to python keyword arguments ? I don't think so; IIRC GCC_XML doesn't give us the declared argument names (if any). Nicodemus? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 16:20:59 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 10:20:59 -0400 Subject: [C++-sig] Re: boost::python> exposing instances from c++ In-Reply-To: <20030727162245.07099.00000480@mb-m12.aol.com> (thedustbustr@aol.com's message of "27 Jul 2003 20:22:45 GMT") References: <20030727162245.07099.00000480@mb-m12.aol.com> Message-ID: The following message is a courtesy copy of an article that has been posted to comp.lang.python as well. Dear Mr. Handheld Vacuum, You will probably get better answers to your Boost.Python questions if you post them to the C++-sig. See http://www.boost.org/more/mailing_lists.htm#Cplussig. thedustbustr at aol.com (TheDustbustr) writes: > I'm writing a game in C++ which calls out to python for scripting. I'd like to > expose the instance of my Game class (a singleton) to python (so that the > instances of Clock, Camera, etc are available to the scripts). > > I ran into trouble trying to expose a specific instance (or even a function > returning the instance). Here is a simplification of my problem in code (c++): > > > class A{ > public: > int i; > }; > class B{ > public: > A a; > }; > B b; > B getb() {return b;} //return the instance > > int main() { > getb().a.i = 42; > return 0;} > #include > #include > #include > using namespace boost::python; > BOOST_PYTHON_MODULE(hello) > { > class_("A",init<>()) > .def("i", &A::i); > class_("B",init<>()) > .def("a", &B::a); > def("getb", getb); > } > > > Of course, I would be calling any python script using these classes from within > main(). > > This doesn't compile (using bjam with msvc). If I return by reference or > pointers in getb it gets ugly (like pages and pages of error messages). Am I > doing this the right way? How do I expose an instance to python? -- Dave Abrahams Boost Consulting www.boost-consulting.com From nicodemus at globalite.com.br Mon Jul 28 16:29:10 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 28 Jul 2003 11:29:10 -0300 Subject: [C++-sig] Re: pure virtual methods with pyste In-Reply-To: <5999.1059397727@www46.gmx.net> References: <5999.1059397727@www46.gmx.net> Message-ID: <3F253336.1020806@globalite.com.br> wiedeman at gmx.net wrote: >Hello Dave, > >sorry for the error in the posted code. This wasn't due to misunderstanding >of the tutorial, but due to copy & paste. In fact, i got the code working >with 'normal' boost.python, but wondered, why pyste doesn't provide a wrapper >for the pure virtual function a(). Here is the code: > >struct Abstract { > virtual void a() = 0; >}; > >#include >using namespace boost::python; > >BOOST_PYTHON_MODULE(wrap_Test) { > class_("Abstract", no_init) > .def("a", &Abstract::a) > ; >} > > But this code won't work if the user wants to override a() in Python, right? We have two use cases regarding abstract classes, AFAIK: - The user doesn't want to override the abstract class in Python: it will use factory functions that create instances of derived classes. - The user wants to be able to override the methods of the abstract class in Python. Here is an attempt to support both: #include using namespace boost::python; struct Abstract { virtual void a() = 0; }; struct AbstractWrap: Abstract { AbstractWrap(PyObject* self_): self(self_) {} void a(){ call_method(self, "a"); } PyObject* self; }; void call(Abstract* a) { a->a(); } BOOST_PYTHON_MODULE(test) { class_("Abstract") .def("a", &Abstract::a) ; def("call", call); } It works, i.e., we can use instances of derived classes in C++ and we can override a() in Python, but it is not safe, because you can instantiate Abstract, and calling its a method will make Python crash. Adding no_init prevents the class from being instantiated, even in a derived class, so that does not work. There's a way to support both usages at the same time? Regards, Nicodemus. From nicodemus at globalite.com.br Mon Jul 28 16:39:48 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 28 Jul 2003 11:39:48 -0300 Subject: [C++-sig] Re: Virtual Functions with Default Implementations code sample In-Reply-To: References: <000501c354fe$3ca46920$81123951@knar> Message-ID: <3F2535B4.2070103@globalite.com.br> David Abrahams wrote: >"Alex" writes: > > >>Does pyste can convert C++ function arguments to python keyword arguments ? >> >> > >I don't think so; IIRC GCC_XML doesn't give us the declared argument >names (if any). Nicodemus? > That's correct, GCCXML doesn't provide this information. We could allow the user to specify the args() in the pyste file: C = Class(...) set_args(C.foo, 'arg1', 'arg2') # or just "args(C.foo, ...)"? ? From pierre.barbier at cirad.fr Mon Jul 28 16:56:30 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 28 Jul 2003 16:56:30 +0200 Subject: [C++-sig] Re: Segfault when calling python method from C++ In-Reply-To: References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> <3F24DF57.90904@cirad.fr> <3F251ED5.5050505@cirad.fr> Message-ID: <3F25399E.8020502@cirad.fr> David Abrahams wrote: >How is that different from what Joel did? > Joel "just" did the hardest part ... what's missing are methods like append, extend, sort, revert ... By the way, I cannot successfully compile his example and it only handle the vector container. (But it's better than what I did, mainly with his reference thing that allows you to delete the object without having dangling pointers and still permits to modify the list using the __getitem__ method, and probably because he seems to use a method more "boost-like") Then, there is also the exportation of mapping objects with the same behaviour as dict objects. >>At best, anybody should be able to export its own container as a >>python list. But it could be a good idea to use what Joel did ... >> >> > >What you did does not appear to export the container "as a python >list", but as a Python sequence. Exporting "as a list" would be more >along the lines of the custom rvalue converters described in >http://www.boost.org/libs/python/doc/v2/faq.html#question2, I think. > You're right, but a more correct assertion would be that I want to export STL container so that they behave as close as possible to python lists. >Actually, I would strongly prefer a test using the same format as all >of the other tests, with doctest or using the unittest module as >polymorphism.py does. > > Ok, that was what I wanted to know :o) -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From pierre.barbier at cirad.fr Mon Jul 28 17:32:09 2003 From: pierre.barbier at cirad.fr (Pierre Barbier de Reuille) Date: Mon, 28 Jul 2003 17:32:09 +0200 Subject: [C++-sig] Problem with std::vector Message-ID: <3F2541F9.30500@cirad.fr> I'd want to know why I can't compile this: void insert( vector* o, object obj ) { insert_iterator > ii( *o, o->end() ); *ii = obj; } I use g++-3.2 and the output is: /usr/include/c++/3.2/bits/stl_vector.h:550: conversion from ` boost::python::api::object' to non-scalar type ` __gnu_cxx::__normal_iterator > >' requested Thansk, -- Pierre Barbier de Reuille INRA - UMR Cirad/Inra/Cnrs/Univ.MontpellierII AMAP Botanique et Bio-informatique de l'Architecture des Plantes TA40/PSII, Boulevard de la Lironde 34398 MONTPELLIER CEDEX 5, France tel : (33) 4 67 61 65 77 fax : (33) 4 67 61 56 68 From dave at boost-consulting.com Mon Jul 28 18:01:10 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 12:01:10 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> Message-ID: Nikolay Mladenov writes: > David Abrahams wrote: >> >> Nikolay Mladenov writes: >> >> > Dave, >> > >> > I am posting the diffs from 1.29.0 plus the test and doc files. >> > Sorry for the delay. I hope you won't have problems applying the diffs. >> >> Hmm, it seems likely that I will. 1.29.0 is two releases old and we >> have made a lot of changes since then. > > I noticed. > >> Is there any chance you can >> give me a patch against the current CVS state? > > I can't get the cvs commands to work for me: > $ cvs -d:pserver:anonymous at cvs.boost.sourceforge.net:/cvsroot/boost > login > (Logging in to anonymous at cvs.boost.sourceforge.net) > CVS password: > cvs [login aborted]: recv() from server cvs.boost.sourceforge.net: EOF > > This is what I always get back from the cvs. > Do you know what is wrong with my cvs line? Nothing; SF cvs is just really bad for anonymous CVS (until next month, when they promise it will be fixed). I use this little python script to do all my anonymous SF CVS: #!/bin/python # cvsx script - tries CVS commands until they succeed. import sys import os while os.system('cvs ' + ' '.join(sys.argv[1:])): print '.', sys.stdout.flush() -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 18:03:27 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 12:03:27 -0400 Subject: [C++-sig] Re: Segfault when calling python method from C++ References: <3F17ED4D.9010303@cirad.fr> <3F1804E7.4080800@cirad.fr> <3F185BB0.6000903@cirad.fr> <3F24DF57.90904@cirad.fr> <3F251ED5.5050505@cirad.fr> <3F25399E.8020502@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > David Abrahams wrote: > >>How is that different from what Joel did? >> > Joel "just" did the hardest part ... what's missing are methods like > append, extend, sort, revert ... > By the way, I cannot successfully compile his example and it only > handle the vector container. (But it's better than what I did, mainly > with his reference thing that allows you to delete the object without > having dangling pointers and still permits to modify the list using > the __getitem__ method, and probably because he seems to use a method > more "boost-like") > Then, there is also the exportation of mapping objects with the same > behaviour as dict objects. OK; if you could find a way to integrate with Joel's work, it would be great. Perhaps the two of you could discuss the design and come up with something? >>>At best, anybody should be able to export its own container as a >>>python list. But it could be a good idea to use what Joel did ... >>> >> >>What you did does not appear to export the container "as a python >>list", but as a Python sequence. Exporting "as a list" would be more >>along the lines of the custom rvalue converters described in >>http://www.boost.org/libs/python/doc/v2/faq.html#question2, I think. >> > You're right, but a more correct assertion would be that I want to > export STL container so that they behave as close as possible to > python lists. Yeah; since Guido refuses to define "sequence" I guess what I said was meaningless ;-> -- Dave Abrahams Boost Consulting www.boost-consulting.com From wiedeman at gmx.net Mon Jul 28 18:08:18 2003 From: wiedeman at gmx.net (wiedeman at gmx.net) Date: Mon, 28 Jul 2003 18:08:18 +0200 (MEST) Subject: [C++-sig] Re: pure virtual methods with pyste References: <3F253336.1020806@globalite.com.br> Message-ID: <31436.1059408498@www28.gmx.net> > #include > using namespace boost::python; > > struct Abstract { > virtual void a() = 0; > }; > > struct AbstractWrap: Abstract > { > AbstractWrap(PyObject* self_): self(self_) {} > void a(){ > call_method(self, "a"); > } > PyObject* self; > }; > > void call(Abstract* a) ^^^^^^^^^^^^^^^^^ let's say void call_a(...). Naming the method 'call' results in a Internal Compiler Error with gcc 2.95.2 and with gcc 3.2 :-) build/WrapTest.cpp: In function `void init_module_wrap_Test()': build/WrapTest.cpp:28: no matching function for call to `def(const char[5], )' > { > a->a(); > } > > BOOST_PYTHON_MODULE(test) > { > class_("Abstract") > .def("a", &Abstract::a) > ; > def("call", call); > } > > > It works, i.e., we can use instances of derived classes in C++ and we > can override a() in Python, but it is not safe, because you can > instantiate Abstract, and calling its a method will make Python crash. > Adding no_init prevents the class from being instantiated, even in a > derived class, so that does not work. There's a way to support both > usages at the same time? Now i see what's going wrong - an infinite recursion if the derived class doesn't implement a(). I suppose, that there is some way to check this, but cannot i'm not sure how to achieve it. Thanks for the clarification. Christoph From dave at boost-consulting.com Mon Jul 28 18:15:06 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 12:15:06 -0400 Subject: [C++-sig] Re: pure virtual methods with pyste References: <5999.1059397727@www46.gmx.net> <3F253336.1020806@globalite.com.br> Message-ID: Nicodemus writes: > > It works, i.e., we can use instances of derived classes in C++ and we > can override a() in Python, but it is not safe, because you can > instantiate Abstract, and calling its a method will make Python > crash. Adding no_init prevents the class from being instantiated, even > in a derived class, so that does not work. There's a way to support > both usages at the same time? Not without changes to Boost.Python. We need a "default implementation" of a() which raises a Python exception or a version of call_method<> which refuses to call the method if it's actually in the same class... possibly also a smarter version of no_init would help, though I am sure it is not enough. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 18:18:29 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 12:18:29 -0400 Subject: [C++-sig] Re: Problem with std::vector References: <3F2541F9.30500@cirad.fr> Message-ID: Pierre Barbier de Reuille writes: > I'd want to know why I can't compile this: > > void insert( vector* o, object obj ) > { > insert_iterator > ii( *o, o->end() ); > *ii = obj; > } > > I use g++-3.2 and the output is: > > /usr/include/c++/3.2/bits/stl_vector.h:550: conversion from ` > boost::python::api::object' to non-scalar type ` > __gnu_cxx::__normal_iterator std::vector std::allocator > >' requested A number of obscure reasons having to do with argument-dependent lookup and the templated operators on boost::python::object contribute. A fix is possible by using enable_if, is_object >, ...> to restrict the templated operators' applicability. Patches welcomed. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nickm at sitius.com Mon Jul 28 19:01:23 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Mon, 28 Jul 2003 13:01:23 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> Message-ID: <3F2556E3.3F4C0A8C@sitius.com> This is insane. I was just pressing enter for 10 minutes trying to login. Can you set up a real read-only account(if it is going to help)? Is there any other "nice" way to get good diffs agains the current cvs state? Nick David Abrahams wrote: > > Nikolay Mladenov writes: > > > David Abrahams wrote: > >> > >> Nikolay Mladenov writes: > >> > >> > Dave, > >> > > >> > I am posting the diffs from 1.29.0 plus the test and doc files. > >> > Sorry for the delay. I hope you won't have problems applying the diffs. > >> > >> Hmm, it seems likely that I will. 1.29.0 is two releases old and we > >> have made a lot of changes since then. > > > > I noticed. > > > >> Is there any chance you can > >> give me a patch against the current CVS state? > > > > I can't get the cvs commands to work for me: > > $ cvs -d:pserver:anonymous at cvs.boost.sourceforge.net:/cvsroot/boost > > login > > (Logging in to anonymous at cvs.boost.sourceforge.net) > > CVS password: > > cvs [login aborted]: recv() from server cvs.boost.sourceforge.net: EOF > > > > This is what I always get back from the cvs. > > Do you know what is wrong with my cvs line? > > Nothing; SF cvs is just really bad for anonymous CVS (until next > month, when they promise it will be fixed). I use this little python > script to do all my anonymous SF CVS: > > #!/bin/python > # cvsx script - tries CVS commands until they succeed. > import sys > import os > while os.system('cvs ' + ' '.join(sys.argv[1:])): > print '.', > sys.stdout.flush() > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 18:45:07 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 12:45:07 -0400 Subject: [C++-sig] Re: pure virtual methods with pyste References: <5999.1059397727@www46.gmx.net> <3F253336.1020806@globalite.com.br> Message-ID: David Abrahams writes: > Nicodemus writes: > >> >> It works, i.e., we can use instances of derived classes in C++ and we >> can override a() in Python, but it is not safe, because you can >> instantiate Abstract, and calling its a method will make Python >> crash. Adding no_init prevents the class from being instantiated, even >> in a derived class, so that does not work. There's a way to support >> both usages at the same time? > > Not without changes to Boost.Python. We need a "default > implementation" of a() which raises a Python exception or a version > of call_method<> which refuses to call the method if it's actually in > the same class... possibly also a smarter version of no_init would > help, though I am sure it is not enough. Ah, wait, try this: struct Abstract { virtual void a() = 0; }; struct AbstractWrap: Abstract { AbstractWrap(PyObject* self_): self(self_) {} void a(){ call_method(self, "a"); } void default_a() { PyErr_SetString(PyExc_RuntimeError, "pure virtual called"); throw error_already_set(); } PyObject* self; }; void call(Abstract* a) { a->a(); } BOOST_PYTHON_MODULE(test) { class_("Abstract") .def("a", &Abstract::a) .def("a", &AbstractWrap::default_a) ; def("call", call); } I just wish I knew a way to detect that a function was pure-virtual so we could have Boost.Python generate that default_a automatically. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 20:51:26 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 14:51:26 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> Message-ID: Nikolay Mladenov writes: > This is insane. I was just pressing enter for 10 minutes trying to > login. > Can you set up a real read-only account(if it is going to help)? > Is there any other "nice" way to get good diffs agains the current cvs > state? You can download the entire nightly CVS tarball here: http://cvs.sourceforge.net/cvstarballs/boost-cvsroot.tar.gz :( -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 20:54:12 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 14:54:12 -0400 Subject: [C++-sig] Re: pure virtual methods with pyste References: <5999.1059397727@www46.gmx.net> <3F253336.1020806@globalite.com.br> Message-ID: David Abrahams writes: > BOOST_PYTHON_MODULE(test) > { > class_("Abstract") > .def("a", &Abstract::a) > .def("a", &AbstractWrap::default_a) > ; > > def("call", call); > } > > I just wish I knew a way to detect that a function was pure-virtual so > we could have Boost.Python generate that default_a automatically. Perhaps this interface would be nice: BOOST_PYTHON_MODULE(test) { class_("Abstract") .def("a", pure_virtual(&Abstract::a)) ; def("call", call); } ?? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 21:00:57 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 15:00:57 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> Message-ID: David Abrahams writes: > Nikolay Mladenov writes: > >> This is insane. I was just pressing enter for 10 minutes trying to >> login. >> Can you set up a real read-only account(if it is going to help)? >> Is there any other "nice" way to get good diffs agains the current cvs >> state? > > You can download the entire nightly CVS tarball here: > > http://cvs.sourceforge.net/cvstarballs/boost-cvsroot.tar.gz or http://www.boost-consulting.com/boost-cvsroot.tar.gz :( -- Dave Abrahams Boost Consulting www.boost-consulting.com From dalwan01 at student.umu.se Mon Jul 28 21:11:25 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Mon, 28 Jul 2003 21:11:25 +0200 Subject: [C++-sig] Re: pure virtual methods with pyste In-Reply-To: References: <5999.1059397727@www46.gmx.net> <3F253336.1020806@globalite.com.br> Message-ID: <5.1.0.14.0.20030728210808.04287d78@student.umu.se> At 20:54 2003-07-28, David Abrahams wrote: >David Abrahams writes: > > > BOOST_PYTHON_MODULE(test) > > { > > class_("Abstract") > > .def("a", &Abstract::a) > > .def("a", &AbstractWrap::default_a) > > ; > > > > def("call", call); > > } > > > > I just wish I knew a way to detect that a function was pure-virtual so > > we could have Boost.Python generate that default_a automatically. > >Perhaps this interface would be nice: > > BOOST_PYTHON_MODULE(test) > { > class_("Abstract") > .def("a", pure_virtual(&Abstract::a)) > ; > > def("call", call); > } > >?? FWIW, we had a similar problem in luabind, where we needed to specify if a function was going to yield from a coroutine. We solved this by introducing a placeholder in the policy list, like this: .def("a", &Abstract::a, yield) This solution could also apply to this problem .def("a", &Abstract::a, pure_virtual) --- Daniel Wallin From conanb at STCG.net Mon Jul 28 21:34:01 2003 From: conanb at STCG.net (Conan Brink) Date: Mon, 28 Jul 2003 12:34:01 -0700 Subject: [C++-sig] Arbitrary argument lists, Python style? Message-ID: Forgive me if I'm just being dense, but in hours of searching multiple archives, I have not been able to find a way to implement the following Python code in C++ via BPL (simplified somewhat for purposes of this discussion): class BackCaller: def SetCallback(self, action, *args): self.cb = (action, args) def CallItBack(self): if self.cb: (action, args) = self.cb return action(*args) The thing that's causing me to pull foot-long hairs from my head is that little *args Is such a thing possible, or do I need to do one of the following: 1) Tell my Python users that they have to explicitly wrap their args in a tuple? 2) Write a Python wrapper that does the translation back and forth between the variable arg list and a tuple that can be passed explicitly to and from my BPL-wrapped class? (and no, I'm not just doing this for fun - I've got some existing Python code that is being redone in C++ because it needs to live closer to the wire) -Conan This message contains information that may be confidential and privileged. Unless you are the addressee (or authorized to receive messages for the addressee), you may not use, copy, or disclose to anyone the message or any information contained in the message. If you have received the message in error, please advise the sender by reply e-mail and delete the message. Nothing in this message should be interpreted as a digital or electronic signature that can be used to authenticate a contract or any other legal document. -------------- next part -------------- An HTML attachment was scrubbed... URL: From dave at boost-consulting.com Mon Jul 28 21:42:05 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 15:42:05 -0400 Subject: [C++-sig] Re: pure virtual methods with pyste References: <5999.1059397727@www46.gmx.net> <3F253336.1020806@globalite.com.br> <5.1.0.14.0.20030728210808.04287d78@student.umu.se> Message-ID: Daniel Wallin writes: > At 20:54 2003-07-28, David Abrahams wrote: >>David Abrahams writes: >> >> > BOOST_PYTHON_MODULE(test) >> > { >> > class_("Abstract") >> > .def("a", &Abstract::a) >> > .def("a", &AbstractWrap::default_a) >> > ; >> > >> > def("call", call); >> > } >> > >> > I just wish I knew a way to detect that a function was pure-virtual so >> > we could have Boost.Python generate that default_a automatically. >> >>Perhaps this interface would be nice: >> >> BOOST_PYTHON_MODULE(test) >> { >> class_("Abstract") >> .def("a", pure_virtual(&Abstract::a)) >> ; >> >> def("call", call); >> } >> >>?? > > FWIW, we had a similar problem in luabind, where we needed to specify > if a function > was going to yield from a coroutine. We solved this by introducing a > placeholder > in the policy list, like this: > > .def("a", &Abstract::a, yield) > > This solution could also apply to this problem > > .def("a", &Abstract::a, pure_virtual) The deal here, though, is that I want to use the def_arg visitation trick to avoid expanding the def(...) interface (which is already way too big!) template <...> struct class_ { ... // Generic visitation template self& def(def_arg const& visitor) { static_cast(visitor).visit(*this); return *this; } ... }; -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Mon Jul 28 21:45:20 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 15:45:20 -0400 Subject: [C++-sig] Re: Arbitrary argument lists, Python style? References: Message-ID: "Conan Brink" writes: > Forgive me if I'm just being dense, but in hours of searching multiple > archives, I have not been able to find a way to implement the following > Python code in C++ via BPL (simplified somewhat for purposes of this > discussion): > > > > class BackCaller: > > def SetCallback(self, action, *args): > > self.cb = (action, args) > > > > def CallItBack(self): > > if self.cb: > > (action, args) = self.cb > > return action(*args) > > > > The thing that's causing me to pull foot-long hairs from my head is that > little *args Does http://tinyurl.com/ibc6 help? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dalwan01 at student.umu.se Mon Jul 28 22:33:50 2003 From: dalwan01 at student.umu.se (Daniel Wallin) Date: Mon, 28 Jul 2003 22:33:50 +0200 Subject: [C++-sig] Re: pure virtual methods with pyste In-Reply-To: References: <5999.1059397727@www46.gmx.net> <3F253336.1020806@globalite.com.br> <5.1.0.14.0.20030728210808.04287d78@student.umu.se> Message-ID: <5.1.0.14.0.20030728222725.041d6a38@student.umu.se> At 21:42 2003-07-28, David Abrahams wrote: >Daniel Wallin writes: > > > At 20:54 2003-07-28, David Abrahams wrote: > >>David Abrahams writes: > >> > >> > BOOST_PYTHON_MODULE(test) > >> > { > >> > class_("Abstract") > >> > .def("a", &Abstract::a) > >> > .def("a", &AbstractWrap::default_a) > >> > ; > >> > > >> > def("call", call); > >> > } > >> > > >> > I just wish I knew a way to detect that a function was pure-virtual so > >> > we could have Boost.Python generate that default_a automatically. > >> > >>Perhaps this interface would be nice: > >> > >> BOOST_PYTHON_MODULE(test) > >> { > >> class_("Abstract") > >> .def("a", pure_virtual(&Abstract::a)) > >> ; > >> > >> def("call", call); > >> } > >> > >>?? > > > > FWIW, we had a similar problem in luabind, where we needed to specify > > if a function > > was going to yield from a coroutine. We solved this by introducing a > > placeholder > > in the policy list, like this: > > > > .def("a", &Abstract::a, yield) > > > > This solution could also apply to this problem > > > > .def("a", &Abstract::a, pure_virtual) > >The deal here, though, is that I want to use the def_arg visitation >trick to avoid expanding the def(...) interface (which is already way >too big!) > >template <...> >struct class_ >{ > ... > // Generic visitation > template > self& def(def_arg const& visitor) > { > static_cast(visitor).visit(*this); > return *this; > } > ... >}; Ok, that's pretty cool. Our way doesn't expand the interface either though, since yield (or pure_virtual) is just a placeholder in the policy list. The implementation just does a search for yield in the policy list. But it's kind of nice with a non-intrusive approach too. --- Daniel Wallin From rwgk at yahoo.com Tue Jul 29 01:28:25 2003 From: rwgk at yahoo.com (Ralf W. Grosse-Kunstleve) Date: Mon, 28 Jul 2003 16:28:25 -0700 (PDT) Subject: [C++-sig] Re: Virtual Functions with Default Implementations code sample In-Reply-To: <3F2535B4.2070103@globalite.com.br> Message-ID: <20030728232825.68003.qmail@web20207.mail.yahoo.com> --- Nicodemus wrote: > >I don't think so; IIRC GCC_XML doesn't give us the declared argument > >names (if any). Nicodemus? > > > > That's correct, GCCXML doesn't provide this information. What a pitty. It is a bit unfortunate that keyword support for wrapped C++ functions isn't automatic. In practice I tend to help myself with Python wrappers for the wrapped C++ functions. Not very elegant. Is there hope that GCCXML will provide the declared arguments names at some point in the future? Ralf __________________________________ Do you Yahoo!? Yahoo! SiteBuilder - Free, easy-to-use web site design software http://sitebuilder.yahoo.com From nickm at sitius.com Tue Jul 29 01:46:28 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Mon, 28 Jul 2003 19:46:28 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> Message-ID: <3F25B5D4.5B24C625@sitius.com> I got it. But ... There are lots of conflicts, so some work must be done again. David Abrahams wrote: > > David Abrahams writes: > > > Nikolay Mladenov writes: > > > >> This is insane. I was just pressing enter for 10 minutes trying to > >> login. > >> Can you set up a real read-only account(if it is going to help)? > >> Is there any other "nice" way to get good diffs agains the current cvs > >> state? > > > > You can download the entire nightly CVS tarball here: > > > > http://cvs.sourceforge.net/cvstarballs/boost-cvsroot.tar.gz > > or http://www.boost-consulting.com/boost-cvsroot.tar.gz > > :( > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com From conanb at STCG.net Tue Jul 29 02:35:19 2003 From: conanb at STCG.net (Conan Brink) Date: Mon, 28 Jul 2003 17:35:19 -0700 Subject: [C++-sig] Re: Arbitrary argument lists, Python style? Message-ID: David Abrahams sez: > "Conan Brink" writes: > > Forgive me if I'm just being dense [snip] > > > > class BackCaller: > > def SetCallback(self, action, *args): > > self.cb = (action, args) > > def CallItBack(self): > > if self.cb: > > (action, args) = self.cb > > return action(*args) > > > > The thing that's causing me to pull foot-long hairs from my head is that > > little *args > Does http://tinyurl.com/ibc6 help? It does somewhat, but not to the extent that I was hoping for. raw_function, of course, only wants an unbound function, not a member of a class. If I try to give it a class member, g++ 3.2 is more than pleased to give me the error messages you might expect about how one must use .* or ->* to call pointer-to-member function. Are there plans for a raw_method or something similar that I can use for wrapping a C++ class's member functions for this, or should I just go with the Python wrapper approach? Might be nice if the published version on www.boost.org included the documentation for raw_function.hpp (I get 404 errors for http://www.boost.org/libs/python/doc/v2/raw_function.html, which is linked from http://www.boost.org/libs/python/doc/v2/reference.html). -Conan This message contains information that may be confidential and privileged. Unless you are the addressee (or authorized to receive messages for the addressee), you may not use, copy, or disclose to anyone the message or any information contained in the message. If you have received the message in error, please advise the sender by reply e-mail and delete the message. Nothing in this message should be interpreted as a digital or electronic signature that can be used to authenticate a contract or any other legal document. From nicodemus at globalite.com.br Tue Jul 29 03:22:37 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 28 Jul 2003 22:22:37 -0300 Subject: [C++-sig] Re: pure virtual methods with pyste In-Reply-To: References: <5999.1059397727@www46.gmx.net> <3F253336.1020806@globalite.com.br> Message-ID: <3F25CC5D.1020800@globalite.com.br> David Abrahams wrote: >David Abrahams writes: > > > >> BOOST_PYTHON_MODULE(test) >> { >> class_("Abstract") >> .def("a", &Abstract::a) >> .def("a", &AbstractWrap::default_a) >> ; >> >> def("call", call); >> } >> >>I just wish I knew a way to detect that a function was pure-virtual so >>we could have Boost.Python generate that default_a automatically. >> >> > >Perhaps this interface would be nice: > > BOOST_PYTHON_MODULE(test) > { > class_("Abstract") > .def("a", pure_virtual(&Abstract::a)) > ; > > def("call", call); > } > >?? > Seems nice enough for me. 8) From nicodemus at globalite.com.br Tue Jul 29 03:23:44 2003 From: nicodemus at globalite.com.br (Nicodemus) Date: Mon, 28 Jul 2003 22:23:44 -0300 Subject: [C++-sig] Re: Virtual Functions with Default Implementations code sample In-Reply-To: <20030728232825.68003.qmail@web20207.mail.yahoo.com> References: <20030728232825.68003.qmail@web20207.mail.yahoo.com> Message-ID: <3F25CCA0.6000807@globalite.com.br> Ralf W. Grosse-Kunstleve wrote: >--- Nicodemus wrote: > > >>>I don't think so; IIRC GCC_XML doesn't give us the declared argument >>>names (if any). Nicodemus? >>> >>> >>> >>That's correct, GCCXML doesn't provide this information. >> >> > >What a pitty. It is a bit unfortunate that keyword support for wrapped C++ >functions isn't automatic. In practice I tend to help myself with Python >wrappers for the wrapped C++ functions. Not very elegant. Is there hope that >GCCXML will provide the declared arguments names at some point in the future? > I will ask Brad in the GCCXML list about it. From nickm at sitius.com Tue Jul 29 04:05:55 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Mon, 28 Jul 2003 22:05:55 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> Message-ID: <3F25D683.B25CBCAF@sitius.com> Dave, I think I have all the conflicts resolved, but my build failed. Can you help me out (MSVC 6.0 - STLPort 4.5.3)? Nick -------------- next part -------------- --------------------Configuration: boost_python - Win32 Debug-------------------- Compiling... inheritance.cpp D:\Program Files\Microsoft Visual Studio\VC98\INCLUDE\../include/new(35) : warning C4290: C++ Exception Specification ignored D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2039: 'distance_type' : is not a member of 'iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::propert y > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc _impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc _impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_ Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_iterator.hpp(69) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _ST L::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_imp l,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2110) : see reference to class template instantiation 'boost::adjacency_iterator_generator >,struct boost::no_prop erty,struct boost::listS>,unsigned int,struct boost::detail::out_edge_iter > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2146: syntax error : missing ';' before identifier 'difference_type' D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc _impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc _impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_ Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_iterator.hpp(69) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _ST L::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_imp l,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2110) : see reference to class template instantiation 'boost::adjacency_iterator_generator >,struct boost::no_prop erty,struct boost::listS>,unsigned int,struct boost::detail::out_edge_iter > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2868: 'difference_type' : illegal syntax for using-declaration; expected qualified-name D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc _impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc _impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_ Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_iterator.hpp(69) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _ST L::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_imp l,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2110) : see reference to class template instantiation 'boost::adjacency_iterator_generator >,struct boost::no_prop erty,struct boost::listS>,unsigned int,struct boost::detail::out_edge_iter > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2039: 'distance_type' : is not a member of 'iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _ STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_i mpl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_N onconst_traits > > > > ,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_iterator.hpp(98) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _STL ::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl ,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2122) : see reference to class template instantiation 'boost::inv_adjacency_iterator_generator >,struct boost::no_ property,struct boost::listS>,unsigned int,struct boost::detail::in_edge_iter > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2146: syntax error : missing ';' before identifier 'difference_type' D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _ STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_i mpl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_N onconst_traits > > > > ,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_iterator.hpp(98) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _STL ::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl ,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2122) : see reference to class template instantiation 'boost::inv_adjacency_iterator_generator >,struct boost::no_ property,struct boost::listS>,unsigned int,struct boost::detail::in_edge_iter > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2868: 'difference_type' : illegal syntax for using-declaration; expected qualified-name D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _ STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_i mpl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_ impl,int> >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_N onconst_traits > > > > ,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_iterator.hpp(98) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _STL ::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl ,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2122) : see reference to class template instantiation 'boost::inv_adjacency_iterator_generator >,struct boost::no_ property,struct boost::listS>,unsigned int,struct boost::detail::in_edge_iter > >,struct _STL::_Nonconst_traits > > > >,struct boost::property > > *,unsigned int,class boost::detail::edge_desc_impl,int> >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2039: 'distance_type' : is not a member of 'iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2127) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2146: syntax error : missing ';' before identifier 'difference_type' D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2127) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(294) : error C2868: 'difference_type' : illegal syntax for using-declaration; expected qualified-name D:\Shared Projects\a\boost\boost/detail/iterator.hpp(336) : see reference to class template instantiation 'boost::detail::msvc_stdlib_mutable_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(357) : see reference to class template instantiation 'boost::detail::msvc_stdlib_iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(367) : see reference to class template instantiation 'boost::detail::non_pointer_iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/detail/iterator.hpp(387) : see reference to class template instantiation 'boost::detail::iterator_traits_aux > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/graph/detail/adjacency_list.hpp(2127) : see reference to class template instantiation 'boost::detail::iterator_traits > >,struct _STL::_Nonconst_traits > > > > >' being compiled D:\Shared Projects\a\boost\boost/graph/adjacency_list.hpp(314) : see reference to class template instantiation 'boost::detail::adj_list_gen >,struct boost::no_property,struct boos t::listS>,struct boost::vecS,struct boost::vecS,struct boost::bidirectionalS,struct boost::no_property,struct boost::property >,struct boost::no_property,struct boost::listS>' being compiled D:\Shared Projects\a\boost\libs\python\src\object\inheritance.cpp(75) : see reference to class template instantiation 'boost::adjacency_list >,struct boost::no_property,struct boost::listS>' being compiled Error executing cl.exe. Creating browse info file... boost_python.dll - 9 error(s), 1 warning(s) From dave at boost-consulting.com Tue Jul 29 05:26:53 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 23:26:53 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> <3F25D683.B25CBCAF@sitius.com> Message-ID: Nikolay Mladenov writes: > Dave, > > I think I have all the conflicts resolved, but my build failed. > Can you help me out (MSVC 6.0 - STLPort 4.5.3)? Use Boost.Build and install the service packs? Works for me with MSVC 6.5 and STLPort 4.5.3 -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Tue Jul 29 05:30:22 2003 From: dave at boost-consulting.com (David Abrahams) Date: Mon, 28 Jul 2003 23:30:22 -0400 Subject: [C++-sig] Re: Arbitrary argument lists, Python style? References: Message-ID: "Conan Brink" writes: > David Abrahams sez: > >> "Conan Brink" writes: > >> > Forgive me if I'm just being dense > [snip] >> > >> > class BackCaller: >> > def SetCallback(self, action, *args): >> > self.cb = (action, args) >> > def CallItBack(self): >> > if self.cb: >> > (action, args) = self.cb >> > return action(*args) >> > >> > The thing that's causing me to pull foot-long hairs from my head is > that >> > little *args > >> Does http://tinyurl.com/ibc6 help? > > It does somewhat, but not to the extent that I was hoping for. > > raw_function, of course, only wants an unbound function, not a member of > a class. > > If I try to give it a class member, g++ 3.2 is more than pleased to give > me the error messages you might expect about how one must use .* or ->* > to call pointer-to-member function. > > Are there plans for a raw_method or something similar that I can use for > wrapping a C++ class's member functions for this, or should I just go > with the Python wrapper approach? whatever raw_foo_bar(tuple args, dict kw) { return extract(args[0])().bar(args.slice(1,_), kw); } > Might be nice if the published version on www.boost.org included the > documentation for raw_function.hpp (I get 404 errors for > http://www.boost.org/libs/python/doc/v2/raw_function.html, which is > linked from http://www.boost.org/libs/python/doc/v2/reference.html). OK, I'll upload it. -- Dave Abrahams Boost Consulting www.boost-consulting.com From stefano.delliponti at eidosmedia.com Tue Jul 29 12:49:21 2003 From: stefano.delliponti at eidosmedia.com (Stefano Delli Ponti) Date: Tue, 29 Jul 2003 12:49:21 +0200 Subject: [C++-sig] Automatic downcasting (again) Message-ID: I've read about a solution for automatic downcasting in threads from November to December 2002. Dave said he has commited some changes in the CVS. Are these changes going to be inserted in boost 1.30.1? Is it possible to know the affected files? TIA, Sted From jdbrandm at unity.ncsu.edu Tue Jul 29 18:23:15 2003 From: jdbrandm at unity.ncsu.edu (Jonathan Brandmeyer) Date: Tue, 29 Jul 2003 12:23:15 -0400 Subject: [C++-sig] implititly_convertible<>() difficulty Message-ID: <002201c355ed$ea20e3e0$8ee80798@nomadic.ncsu.edu> I have a C++ type that I want to construct from a python tuple, and use python tuples in it's place. implicitly_convertible() looked like the right thing, but it is not giving me the results that I had hoped. A complete example of what I am trying to do follows. This particular run was tested with GCC 3.2.2 (mingw) with Boost.Python 1.30.0 and Python 2.2.2 on WinXP. Thanks for you help, Jonathan Brandmeyer --------------------- tuple_test.cpp------------------------ #include class tuple_type { private: double x; double y; double z; public: tuple_type( double a=0.0, double b=0.0, double c=0.0) : x(a), y(b), z(c) {} tuple_type( boost::python::tuple sequence) { using boost::python::extract; int i = extract( sequence.attr("__len__")); switch (i) { case 3: z = extract( sequence[2]); // FALLTHROUGH case 2: y = extract( sequence[1]); x = extract( sequence[0]); break; default: break; } } tuple_type operator+( const tuple_type& t) const { return tuple_type( x+t.x, y+t.y, z+t.z); } }; BOOST_PYTHON_MODULE( tuple_test) { using namespace boost::python; class_( "tuple_type", init()) .def( self + self) ; implicitly_convertible(); } ------------ and this is what I want to accomplish ---------------- Python 2.2.2 (#37, Oct 14 2002, 17:02:34) [MSC 32 bit (Intel)] on win32 Type "help", "copyright", "credits" or "license" for more information. >>> from tuple_test import tuple_type >>> x = tuple_type( 0.1, 3, 4) >>> y = (2, 3, 4) >>> z = tuple_type(y) Traceback (most recent call last): File "", line 1, in ? TypeError: bad argument type for built-in operation >>> z = x+y Traceback (most recent call last): File "", line 1, in ? TypeError: unsupported operand types for +: 'tuple_type' and 'tuple' From dave at boost-consulting.com Tue Jul 29 18:40:17 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 29 Jul 2003 12:40:17 -0400 Subject: [C++-sig] Re: Automatic downcasting (again) References: Message-ID: "Stefano Delli Ponti" writes: > I've read about a solution for automatic downcasting in threads from > November to December 2002. > Dave said he has commited some changes in the CVS. > Are these changes going to be inserted in boost 1.30.1? > Is it possible to know the affected files? No, 1.30.1 will have no new features; only bugfixes. 1.31.0 will include the changes and should be released shortly thereafter, though. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Tue Jul 29 21:44:12 2003 From: dave at boost-consulting.com (David Abrahams) Date: Tue, 29 Jul 2003 15:44:12 -0400 Subject: [C++-sig] Re: implititly_convertible<>() difficulty References: <002201c355ed$ea20e3e0$8ee80798@nomadic.ncsu.edu> Message-ID: "Jonathan Brandmeyer" writes: > I have a C++ type that I want to construct from a python tuple, and use > python tuples in it's place. implicitly_convertible() > looked like the right thing, but it is not giving me the results that I had > hoped. A complete example of what I am trying to do follows. > > This particular run was tested with GCC 3.2.2 (mingw) with Boost.Python > 1.30.0 and Python 2.2.2 on WinXP. > > Thanks for you help, > Jonathan Brandmeyer > > --------------------- tuple_test.cpp------------------------ > #include > > class tuple_type > { > private: > double x; > double y; > double z; > public: > tuple_type( double a=0.0, double b=0.0, double c=0.0) > : x(a), y(b), z(c) {} > > tuple_type( boost::python::tuple sequence) > { > using boost::python::extract; > > int i = extract( sequence.attr("__len__")); > switch (i) { > case 3: > z = extract( sequence[2]); > // FALLTHROUGH > case 2: > y = extract( sequence[1]); > x = extract( sequence[0]); > break; > default: > break; > } > } > > tuple_type > operator+( const tuple_type& t) const > { return tuple_type( x+t.x, y+t.y, z+t.z); } > }; > > BOOST_PYTHON_MODULE( tuple_test) > { > using namespace boost::python; > > class_( "tuple_type", init()) > .def( self + self) > ; > > implicitly_convertible(); > } I'm not sure what's going wrong here, but could you try this instead? #include class tuple_type { private: double x; double y; double z; public: tuple_type( double a=0.0, double b=0.0, double c=0.0) : x(a), y(b), z(c) {} tuple_type( boost::python::tuple sequence) { using boost::python::extract; int i = extract( sequence.attr("__len__")); switch (i) { case 3: z = extract( sequence[2]); // FALLTHROUGH case 2: y = extract( sequence[1]); x = extract( sequence[0]); break; default: break; } } tuple_type operator+( const tuple_type& t) const { return tuple_type( x+t.x, y+t.y, z+t.z); } }; BOOST_PYTHON_MODULE( tuple_test) { using namespace boost::python; class_( "tuple_type", init()) .def( self + self) .def( self + other()) ; } -- Dave Abrahams Boost Consulting www.boost-consulting.com From stefano.delliponti at eidosmedia.com Wed Jul 30 10:17:29 2003 From: stefano.delliponti at eidosmedia.com (Stefano Delli Ponti) Date: Wed, 30 Jul 2003 10:17:29 +0200 Subject: [C++-sig] Re: Automatic downcasting (again) References: Message-ID: Ok, thanks. Do you remember which the affected files were? boost/python/object/make_instance.hpp? Sted "David Abrahams" wrote in message news:u8yqhffri.fsf at boost-consulting.com... > "Stefano Delli Ponti" writes: > > > I've read about a solution for automatic downcasting in threads from > > November to December 2002. > > Dave said he has commited some changes in the CVS. > > Are these changes going to be inserted in boost 1.30.1? > > Is it possible to know the affected files? > > No, 1.30.1 will have no new features; only bugfixes. 1.31.0 will > include the changes and should be released shortly thereafter, though. > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com From dave at boost-consulting.com Wed Jul 30 14:15:47 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 30 Jul 2003 08:15:47 -0400 Subject: [C++-sig] Re: Automatic downcasting (again) References: Message-ID: "Stefano Delli Ponti" writes: > Ok, thanks. > Do you remember which the affected files were? Nope. You could check the CVS logs. > boost/python/object/make_instance.hpp? Doubtful. Sorry, -- Dave Abrahams Boost Consulting www.boost-consulting.com From romany at actimize.com Wed Jul 30 14:50:18 2003 From: romany at actimize.com (Roman Yakovenko) Date: Wed, 30 Jul 2003 15:50:18 +0300 Subject: [C++-sig] cvs anonymous user access denied Message-ID: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AFC@exchange.adrembi.com> Hi. Is there is easy way to get all current files from cvs ? Thanks From dave at boost-consulting.com Wed Jul 30 15:22:36 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 30 Jul 2003 09:22:36 -0400 Subject: [C++-sig] Re: cvs anonymous user access denied References: <91BFE89EFFA2904E9A4C3ACB4E5F2DF5027AFC@exchange.adrembi.com> Message-ID: "Roman Yakovenko" writes: > Hi. Is there is easy way to get all current files from cvs ? Nothing; SF cvs is just really bad for anonymous CVS (until next month, when they promise it will be fixed). I use this little python script to do all my anonymous SF CVS: #!/bin/python # cvsx script - tries CVS commands until they succeed. import sys import os while os.system('cvs ' + ' '.join(sys.argv[1:])): print '.', sys.stdout.flush() Alternatively, you can download last night's CVS tarball and use local CVS on your machine: http://cvs.sourceforge.net/cvstarballs/boost-cvsroot.tar.gz or, from two nights ago: http://www.boost-consulting.com/boost-cvsroot.tar.gz Good luck, -- Dave Abrahams Boost Consulting www.boost-consulting.com From jdbrandm at unity.ncsu.edu Wed Jul 30 19:29:03 2003 From: jdbrandm at unity.ncsu.edu (Jonathan Brandmeyer) Date: Wed, 30 Jul 2003 13:29:03 -0400 Subject: [C++-sig] Re: implititly_convertible<>() difficulty References: <20030730160009.8448.22662.Mailman@mail.python.org> Message-ID: <000501c356c0$13e41490$8ee80798@nomadic.ncsu.edu> > To: c++-sig at python.org > From: David Abrahams <> > Date: Tue, 29 Jul 2003 15:44:12 -0400 > Subject: [C++-sig] Re: implititly_convertible<>() difficulty > Reply-To: c++-sig at python.org > > > I'm not sure what's going wrong here, but could you try this instead? > > #include > > class tuple_type > { > private: > double x; > double y; > double z; > public: > tuple_type( double a=0.0, double b=0.0, double c=0.0) > : x(a), y(b), z(c) {} > > tuple_type( boost::python::tuple sequence) > { > using boost::python::extract; > > int i = extract( sequence.attr("__len__")); > switch (i) { > case 3: > z = extract( sequence[2]); > // FALLTHROUGH > case 2: > y = extract( sequence[1]); > x = extract( sequence[0]); > break; > default: > break; > } > } > > tuple_type > operator+( const tuple_type& t) const > { return tuple_type( x+t.x, y+t.y, z+t.z); } > }; > > BOOST_PYTHON_MODULE( tuple_test) > { > using namespace boost::python; > > class_( "tuple_type", init()) > .def( self + self) > .def( self + other()) > ; > } > > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com > GCC rejected that with this error: tupletest.cpp: In function `void init_module_tuple_test()': tupletest.cpp:42: ambiguous overload for `boost::python::self_ns::self_t& + boost::python::other' operator c:/msys/local/include/boost/python/operators.hpp:184: candidates are: boost::python::detail::operator_ boost::python::self_ns::operator+(const L&, const R&) [with L = boost::python::self_ns::self_t, R = boost::python::other] c:/msys/local/include/boost/python/object_operators.hpp:60: boost::python::api::object boost::python::api::operator+(const L&, const R&) [with L = boost::python::self_ns::self_t, R = boost::python::other] Thanks, Jonathan Brandmeyer P.S. Please CC me in all replies on this thread. From dave at boost-consulting.com Thu Jul 31 01:49:07 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 30 Jul 2003 19:49:07 -0400 Subject: [C++-sig] Re: implititly_convertible<>() difficulty References: <20030730160009.8448.22662.Mailman@mail.python.org> <000501c356c0$13e41490$8ee80798@nomadic.ncsu.edu> Message-ID: "Jonathan Brandmeyer" writes: > GCC rejected that with this error: > tupletest.cpp: In function `void init_module_tuple_test()': > tupletest.cpp:42: ambiguous overload for `boost::python::self_ns::self_t& + > boost::python::other' operator > c:/msys/local/include/boost/python/operators.hpp:184: candidates are: > boost::python::detail::operator_ > boost::python::self_ns::operator+(const L&, const R&) [with L = > boost::python::self_ns::self_t, R = > boost::python::other] > c:/msys/local/include/boost/python/object_operators.hpp:60: > boost::python::api::object boost::python::api::operator+(const L&, const > R&) > > [with L = boost::python::self_ns::self_t, R = > boost::python::other] For recent GCCs, that should now be fixed in CVS. The enclosed patch should also address the problem -------------- next part -------------- A non-text attachment was scrubbed... Name: object_operators.hpp.patch Type: text/x-patch Size: 2800 bytes Desc: not available URL: -------------- next part -------------- -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 31 01:50:08 2003 From: dave at boost-consulting.com (David Abrahams) Date: Wed, 30 Jul 2003 19:50:08 -0400 Subject: [C++-sig] Re: Problem with std::vector References: <3F2541F9.30500@cirad.fr> Message-ID: David Abrahams writes: > A number of obscure reasons having to do with argument-dependent > lookup and the templated operators on boost::python::object > contribute. > > A fix is possible by using > > enable_if, is_object >, ...> > > to restrict the templated operators' applicability. Patches welcomed. I have now made the fix in the CVS; you can also apply the enclosed patch. Please let me know if it fails for you. -------------- next part -------------- A non-text attachment was scrubbed... Name: object_operators.hpp.patch Type: text/x-patch Size: 2800 bytes Desc: not available URL: -------------- next part -------------- -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 31 15:07:34 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 31 Jul 2003 09:07:34 -0400 Subject: [C++-sig] Re: Automatic PyUnicode to 'const char*' References: <000d01c357be$feffb700$0200a8c0@barrack> Message-ID: "Lijun Qin" writes: > Hi all, > > I'm using boost.python to wrap the WTL (Windows Template Libaray), using VC > 7.1 and porting some old code previously use win32ui.pyd. > Basically it is easy to do, though gccxml failed to parse the ATL/WTL code > so I can not use Pyste. > But there is a trouble, does anybody know how to automaticly convert > PyUnicode to 'const char *'? Without this, I have to change lot of code > lines to explictly use str() function. I'm not an expert in it, but I thought Unicode used 16- or 32- byte wchar_t characters. How would you convert it to char const*? -- Dave Abrahams Boost Consulting www.boost-consulting.com From seefeld at sympatico.ca Thu Jul 31 14:55:53 2003 From: seefeld at sympatico.ca (Stefan Seefeld) Date: Thu, 31 Jul 2003 08:55:53 -0400 Subject: [C++-sig] Re: Automatic PyUnicode to 'const char*' References: <000d01c357be$feffb700$0200a8c0@barrack> Message-ID: David Abrahams wrote: > "Lijun Qin" writes: > > >>Hi all, >> >>I'm using boost.python to wrap the WTL (Windows Template Libaray), using VC >>7.1 and porting some old code previously use win32ui.pyd. >>Basically it is easy to do, though gccxml failed to parse the ATL/WTL code >>so I can not use Pyste. >>But there is a trouble, does anybody know how to automaticly convert >>PyUnicode to 'const char *'? Without this, I have to change lot of code >>lines to explictly use str() function. > > > I'm not an expert in it, but I thought Unicode used 16- or 32- byte > wchar_t characters. How would you convert it to char const*? unicode allows different encodings, some (such as utf-8) with variably sized character representations. This means that conversions usually can't be done on-the-fly without helper constructs, i.e. some memory management is needed. As an example, I'm doing such conversions in a xml library. The C implementation uses 'xmlChar *', which is just an alias for 'char *', but really holds utf-8 encoded text. I convert it to various string types (the public API is parametrized for the string type): Here is the conversion between xmlChar * and std::string: struct string_convert { static std::string in(const xmlChar *buffer) { return buffer ? std::string((char *)buffer) : std::string(); } static xmlChar *out(const std::string &buffer) { return (xmlChar *)buffer.c_str(); } }; And here is the conversion between xmlChar * and Qt's QString: struct QStringConvert { struct Converter { Converter(const QCString &s) : utf8(s) {} operator const xmlChar *() const { return (const xmlChar *)static_cast(utf8);} QCString utf8; }; static QString in(const xmlChar *buffer) { return buffer ? QString::fromUtf8((const char *)buffer) : QString(); } static Converter out(const QString &buffer) { return Converter(buffer.utf8()); } }; Regards, Stefan From nickm at sitius.com Thu Jul 31 17:45:52 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Thu, 31 Jul 2003 11:45:52 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> <3F25D683.B25CBCAF@sitius.com> Message-ID: <3F2939B0.4B8047E8@sitius.com> Interestingly the difference in the cl.exe options that leads to the errors is /vmg (use general purpose pointer-to-members) I need to use this option im my projects, but I will test the args patch without it. Can the /vmg problem be resolved in some way? Nick David Abrahams wrote: > > Nikolay Mladenov writes: > > > Dave, > > > > I think I have all the conflicts resolved, but my build failed. > > Can you help me out (MSVC 6.0 - STLPort 4.5.3)? > > Use Boost.Build and install the service packs? > Works for me with MSVC 6.5 and STLPort 4.5.3 > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com From dave at boost-consulting.com Thu Jul 31 18:05:33 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 31 Jul 2003 12:05:33 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> <3F25D683.B25CBCAF@sitius.com> <3F2939B0.4B8047E8@sitius.com> Message-ID: Nikolay Mladenov writes: > Interestingly the difference in the cl.exe options that leads > to the errors is /vmg (use general purpose pointer-to-members) > I need to use this option im my projects, but I will test the args patch > without it. > Can the /vmg problem be resolved in some way? If you reduce the problem to a small test case I may be able to find a workaround. That's all I can think of. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 31 18:18:34 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 31 Jul 2003 12:18:34 -0400 Subject: [C++-sig] Re: Automatic PyUnicode to 'const char*' References: <000d01c357be$feffb700$0200a8c0@barrack> Message-ID: Stefan Seefeld writes: > David Abrahams wrote: >> "Lijun Qin" writes: >> >>>Hi all, >>> >>>I'm using boost.python to wrap the WTL (Windows Template Libaray), using VC >>>7.1 and porting some old code previously use win32ui.pyd. >>>Basically it is easy to do, though gccxml failed to parse the ATL/WTL code >>>so I can not use Pyste. >>>But there is a trouble, does anybody know how to automaticly convert >>>PyUnicode to 'const char *'? Without this, I have to change lot of code >>>lines to explictly use str() function. >> I'm not an expert in it, but I thought Unicode used 16- or 32- byte >> wchar_t characters. How would you convert it to char const*? > > unicode allows different encodings, some (such as utf-8) with variably > sized character representations. This means that conversions usually > can't be done on-the-fly without helper constructs, i.e. some memory > management is needed. > > As an example, I'm doing such conversions in a xml library. The C > implementation uses 'xmlChar *', which is just an alias for 'char *', > but really holds utf-8 encoded text. > I convert it to various string types (the public API is parametrized > for the string type): To do that kind of narrowing, at the moment, the only way would be to write a thin wrapper function: void f(char const*); void f_thin_wrapper(object unicode) { str narrowed(unicode); f(extract(str)); } we may have some support for doing this automatically in the version of Boost.Python which integrates with Luabind, but that's a ways off yet. -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 31 18:28:16 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 31 Jul 2003 12:28:16 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> <3F25D683.B25CBCAF@sitius.com> <3F2939B0.4B8047E8@sitius.com> Message-ID: Nikolay Mladenov writes: > Interestingly the difference in the cl.exe options that leads > to the errors is /vmg (use general purpose pointer-to-members) > I need to use this option im my projects, but I will test the args patch > without it. > Can the /vmg problem be resolved in some way? Hmm, I can't even get the embedding test to compile with that switch in the existing codebase. I have no clue. As far as I can tell the /vmg feature was completely broken for vc6 and vc7. They seem to have fixed it for vc7.1. You might see if you can make something useful out of: http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vccelng/htm/pragm_23.asp Good luck, Dave -- Dave Abrahams Boost Consulting www.boost-consulting.com From nickm at sitius.com Thu Jul 31 19:17:41 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Thu, 31 Jul 2003 13:17:41 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> Message-ID: <3F294F35.A6988D6A@sitius.com> Diffs to the cvs from before couple of days: David Abrahams wrote: > > Nikolay Mladenov ?nickm at sitius.com? writes: > > ? Dave, > ? > ? I am posting the diffs from 1.29.0 plus the test and doc files. > ? Sorry for the delay. I hope you won't have problems applying the diffs. > > Hmm, it seems likely that I will. 1.29.0 is two releases old and we > have made a lot of changes since then. Is there any chance you can > give me a patch against the current CVS state? > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com -------------- next part -------------- Index: args.hpp =================================================================== RCS file: /d/Downloads/boost/boost/boost/python/args.hpp,v retrieving revision 1.14 diff -c -r1.14 args.hpp *** args.hpp 31 May 2003 14:53:01 -0000 1.14 --- args.hpp 28 Jul 2003 21:47:00 -0000 *************** *** 44,51 **** --- 44,62 ---- } keyword elements[nkeywords]; + keywords operator , (const keywords<1> &k) const + { + python::detail::keywords res; + std::copy(elements, elements+size, res.elements); + res.elements[size] = k.elements[0]; + return res; + } + keywords operator , (const char *name) const; }; + + + # ifndef BOOST_NO_TEMPLATE_PARTIAL_SPECIALIZATION template struct is_keywords *************** *** 95,100 **** --- 106,132 ---- BOOST_PYTHON_MPL_LAMBDA_SUPPORT(1,is_reference_to_keywords,(T)) }; # endif + } + + struct arg : detail::keywords<1> + { + template + arg &operator = (T const &value) + { + elements[0].default_value = handle<>(python::borrowed(object(value).ptr())); + return *this; + } + explicit arg (char const *name){elements[0].name = name;} + operator detail::keyword const &()const {return elements[0];} + }; + + namespace detail + { + template + inline keywords< keywords::size+1 > keywords::operator , (const char *name) const + { + return this->operator , (arg(name)); + } } # define BOOST_PYTHON_ASSIGN_NAME(z, n, _) result.elements[n].name = name##n; -------------- next part -------------- Index: args_fwd.hpp =================================================================== RCS file: /d/Downloads/boost/boost/boost/python/args_fwd.hpp,v retrieving revision 1.3 diff -c -r1.3 args_fwd.hpp *** args_fwd.hpp 31 May 2003 14:53:01 -0000 1.3 --- args_fwd.hpp 28 Jul 2003 21:47:01 -0000 *************** *** 21,26 **** --- 21,27 ---- { char const* name; handle<> default_value; + keyword(char const* n=0):name(n){} }; template struct keywords; -------------- next part -------------- Index: function.hpp =================================================================== RCS file: /d/Downloads/boost/boost/boost/python/object/function.hpp,v retrieving revision 1.18 diff -c -r1.18 function.hpp *** function.hpp 23 Jul 2003 13:08:59 -0000 1.18 --- function.hpp 28 Jul 2003 21:48:13 -0000 *************** *** 51,56 **** --- 51,57 ---- object m_namespace; object m_doc; object m_arg_names; + unsigned m_nkeyword_values; }; // -------------- next part -------------- Index: function.cpp =================================================================== RCS file: /d/Downloads/boost/boost/libs/python/src/object/function.cpp,v retrieving revision 1.33 diff -b -c -r1.33 function.cpp *** function.cpp 23 Jul 2003 17:04:05 -0000 1.33 --- function.cpp 31 Jul 2003 17:07:21 -0000 *************** *** 47,52 **** --- 47,53 ---- , unsigned num_keywords ) : m_fn(implementation) + , m_nkeyword_values(0) { if (names_and_defaults != 0) { *************** *** 66,78 **** for (unsigned i = 0; i < num_keywords; ++i) { PyTuple_SET_ITEM( ! m_arg_names.ptr() ! , i + keyword_offset , expect_non_null( PyString_FromString(const_cast(names_and_defaults[i].name)) ) ); } } --- 67,101 ---- for (unsigned i = 0; i < num_keywords; ++i) { + object tpl (handle<>( + PyTuple_New(names_and_defaults[i].default_value ? 2 : 1) + )); + PyTuple_SET_ITEM( ! tpl.ptr() ! , 0 , expect_non_null( PyString_FromString(const_cast(names_and_defaults[i].name)) ) ); + + if(names_and_defaults[i].default_value) + { + PyTuple_SET_ITEM( + tpl.ptr() + , 1 + , incref(names_and_defaults[i].default_value.get()) + ); + + ++m_nkeyword_values; + } + + + PyTuple_SET_ITEM( + m_arg_names.ptr() + , i + keyword_offset + , incref(tpl.ptr()) + ); } } *************** *** 101,114 **** do { // Check for a plausible number of arguments ! if (total_args >= f->m_fn.min_arity() ! && total_args <= f->m_fn.max_arity()) { // This will be the args that actually get passed handle<> args2(allow_null(borrowed(args))); ! if (nkeywords > 0) // Keyword arguments were supplied ! { if (f->m_arg_names.ptr() == Py_None) // this overload doesn't accept keywords { args2 = handle<>(); // signal failure --- 124,140 ---- do { // Check for a plausible number of arguments ! unsigned min_arity = f->m_fn.min_arity(); ! unsigned max_arity = f->m_fn.max_arity(); ! ! if (total_args + f->m_nkeyword_values >= min_arity ! && total_args <= max_arity) { // This will be the args that actually get passed handle<> args2(allow_null(borrowed(args))); ! if (nkeywords > 0 || total_args < min_arity) // Keyword arguments were supplied ! { // or default keyword values are needed if (f->m_arg_names.ptr() == Py_None) // this overload doesn't accept keywords { args2 = handle<>(); // signal failure *************** *** 131,148 **** } else { ! // build a new arg tuple ! args2 = handle<>(PyTuple_New(total_args)); // Fill in the positional arguments for (std::size_t i = 0; i < nargs; ++i) PyTuple_SET_ITEM(args2.get(), i, incref(PyTuple_GET_ITEM(args, i))); // Grab remaining arguments by name from the keyword dictionary ! for (std::size_t j = nargs; j < total_args; ++j) { ! PyObject* value = PyDict_GetItem( ! keywords, PyTuple_GET_ITEM(f->m_arg_names.ptr(), j)); if (!value) { --- 157,185 ---- } else { ! // build a new arg tuple, will adjust its size later ! args2 = handle<>(PyTuple_New(max_arity)); // Fill in the positional arguments for (std::size_t i = 0; i < nargs; ++i) PyTuple_SET_ITEM(args2.get(), i, incref(PyTuple_GET_ITEM(args, i))); // Grab remaining arguments by name from the keyword dictionary ! std::size_t j = nargs; ! std::size_t k = nargs; ! std::size_t size = PyTuple_GET_SIZE(f->m_arg_names.ptr()); ! ! for (; j < max_arity && j < size ; ++j) ! { ! PyObject* kwd = PyTuple_GET_ITEM(f->m_arg_names.ptr(), j); ! ! PyObject* value = nkeywords ? PyDict_GetItem( ! keywords, PyTuple_GET_ITEM(kwd, 0)) : 0; ! ! if (!value) { ! if (PyTuple_GET_SIZE(kwd) > 1) ! value = PyTuple_GET_ITEM(kwd, 1); if (!value) { *************** *** 150,156 **** args2 = handle<>(); break; } ! PyTuple_SET_ITEM(args2.get(), j, incref(value)); } } } --- 187,217 ---- args2 = handle<>(); break; } ! }else ! ++k; ! ! PyTuple_SET_ITEM(args2.get(), j, incref(value) ! ); ! } ! ! if (args2.get()) ! { ! //check if we proccessed all the arguments ! if(k < total_args) ! args2 = handle<>(); ! ! //adjust the parameter tuple size ! if(j args3( PyTuple_New(j) ); ! ! for (size_t l = 0; l != j; ++ l) ! { ! PyTuple_SET_ITEM(args3.get(), l, PyTuple_GET_ITEM(args3.get(), l) ); ! PyTuple_SET_ITEM(args2.get(), l, 0); ! } ! args2 = args3; ! } } } } -------------- next part -------------- A non-text attachment was scrubbed... Name: keywords.cpp Type: application/x-unknown-content-type-cppfile Size: 2489 bytes Desc: not available URL: -------------- next part -------------- ''' >>> from keywords import * >>> f = Foo() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> f = Foo(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f = Foo(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> f = Foo(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') >>> f = Foo(a=1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f = Foo(b=1) >>> f.a(), f.b(), f.n() (0, 1.0, '') >>> f = Foo(n="1") >>> f.a(), f.b(), f.n() (0, 0.0, '1') >>> f = Foo(1,n="1") >>> f.a(), f.b(), f.n() (1, 0.0, '1') >>> f.set() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> f.set(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f.set(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> f.set(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') >>> f.set(a=1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f.set(b=1) >>> f.a(), f.b(), f.n() (0, 1.0, '') >>> f.set(n="1") >>> f.a(), f.b(), f.n() (0, 0.0, '1') >>> f.set(1,n="1") >>> f.a(), f.b(), f.n() (1, 0.0, '1') # lets see how badly we've broken the 'regular' functions >>> f = Bar() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> f = Bar(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f = Bar(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> f = Bar(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') >>> f.set() >>> f.a(), f.b(), f.n() (0, 0.0, '') >>> f.set(1) >>> f.a(), f.b(), f.n() (1, 0.0, '') >>> f.set(1,1.0) >>> f.a(), f.b(), f.n() (1, 1.0, '') >>> f.set(1,1.0,"1") >>> f.a(), f.b(), f.n() (1, 1.0, '1') ''' def run(args = None): import sys import doctest if args is not None: sys.argv = args return doctest.testmod(sys.modules.get(__name__)) if __name__ == '__main__': print "running..." import sys sys.exit(run()[0]) From nickm at sitius.com Thu Jul 31 19:26:37 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Thu, 31 Jul 2003 13:26:37 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> <3F25D683.B25CBCAF@sitius.com> <3F2939B0.4B8047E8@sitius.com> Message-ID: <3F29514D.506729DF@sitius.com> I can't get boost_python to compile with this swich, and I have 1.29.0 compiled with it. The problem is that one generally shouldn't mix binaries compiled with different pointer_to_member option and we have everiting built with /vmg which acording to the ms docs is the safest, since all the pointer-to-members have the same "sizeof". Can the problem be that some "trait" switches because of the sizeof(pointer_to_member)? Nikolay David Abrahams wrote: > > Nikolay Mladenov ?nickm at sitius.com? writes: > > ? Interestingly the difference in the cl.exe options that leads > ? to the errors is /vmg (use general purpose pointer-to-members) > ? I need to use this option im my projects, but I will test the args patch > ? without it. > ? Can the /vmg problem be resolved in some way? > > Hmm, I can't even get the embedding test to compile with that switch > in the existing codebase. I have no clue. > > As far as I can tell the /vmg feature was completely broken for vc6 > and vc7. They seem to have fixed it for vc7.1. > > You might see if you can make something useful out of: > > http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vccelng/htm/pragm_23.asp > > Good luck, > Dave > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com From jdbrandm at unity.ncsu.edu Thu Jul 31 19:32:00 2003 From: jdbrandm at unity.ncsu.edu (Jonathan Brandmeyer) Date: Thu, 31 Jul 2003 13:32:00 -0400 Subject: [C++-sig] Re: C++-sig digest, Vol 1 #658 - 7 msgs References: <20030731160008.11018.98975.Mailman@mail.python.org> Message-ID: <000e01c35789$a7396b40$8ee80798@nomadic.ncsu.edu> ----- Original Message ----- > To: c++-sig at python.org > From: David Abrahams <> > Date: Wed, 30 Jul 2003 19:49:07 -0400 > Subject: [C++-sig] Re: implititly_convertible<>() difficulty > Reply-To: c++-sig at python.org > > --=-=-= > For recent GCCs, that should now be fixed in CVS. The enclosed patch > should also address the problem > > snipped patch to boost/python/object_operators.hpp As far as recent GCC's go, I tested this with GCC 3.3.1 (Debian prerelease dated last week) and it failed there too. My other environment is on Debian Sid with GCC 3.3.1, GCC 3.2.3 (tested using both) Boost.Python 1.30.0-4 (includes debian patches for gcc 3.3) and Python 2.2.3. The patch depends on some stuff in boost/iterator/ that is not present in Boost 1.30.0, so it did not work for me. Even if it did, the example I posted is only one of the areas that this fails. I am attempting to apply this implicit conversion to several dozen functions, member functions, and setters (all for the same tuple-like type), so the method of manually providing overloads isn't really scalable. Nor is it obvious to me how that would work for setters. I apologize for the lag time. I'm not on daily digest anymore, so hopefully this discussion will proceed better. Thanks, Jonathan Brandmeyer From dave at boost-consulting.com Thu Jul 31 19:43:23 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 31 Jul 2003 13:43:23 -0400 Subject: [C++-sig] Re: First pass at exception translator template References: <3EDBDDF8.9030105@anim.dreamworks.com> Message-ID: David Abrahams writes: > Gavin Doughtie writes: > >> So, this is probably gross or non thread-safe in some manner that I'm >> not clued into yet. I'd appreciate any elegant refactorings, but this >> seems to work and will allow me to just specify a bunch of >> "REGISTER_EXCEPTION" lines in my module. > > Gavin, > > Thanks for your post; I'll try to look at it in the next couple of > days. Gavin, did this ever go anywhere, or did I drop it on the floor? -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 31 19:47:53 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 31 Jul 2003 13:47:53 -0400 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AAC2@berexch.ber.haufemg.com> <001201c34936$303e0b60$44a837c2@gieke> Message-ID: Hi Gottfried, Any progress on this front? David Abrahams writes: > Gottfried Gan?auge writes: > >> ... >>> > It could be even simpler with a completely different design but >> frankly - I >>> > have no clue how to implement that: >>> > We would need a way to somehow derive (in the python sense) a class_<> >> from >>> > PyExc_Exception (the type of the python Exception class) or any other >> python >>> > class (PyErr_NewException() has a base parameter, which could be used >> for >>> > that). >>> > >>> > At the same time an exception_translator should be registered for that >>> > class_<> which uses PyErr_SetObject() to raise a copy of the exception >>> > caught. >>> >>> None of that sounds simpler to me. >>> >>> > This would allow us to have true Python exceptions in a pythonic sense >>> > directly wrapped around the corresponding C++ exception. >>> >>> Doesn't sound like a big advantage to me, but I guess if you had >>> stored data members in the C++ exception type you'd want them to be >>> preserved. Hmm, there's no reason you can't build a BPL extension >>> class which also inherits from Exception, but it seems tough. >> >> Maybe an example is in order: >> >> // this is the exception to wrap >> struct some_exception { >> some_exception (const char *description, int error_number); >> >> const char *what() const; >> int get_additional_errorinfo() const; >> }; >> >> // This is how it could be wrapped >> BOOST_PYTHON_MODULE(exception_test) >> { >> class_ > ("some_exception") >> .def ("what", &some_exception::what) >> .def ("get_additional_errorinfo", >> &some_exception::get_additional_errorinfo) >> ; >> } > > Yes, I understood it to be something like that. What about: > > BOOST_PYTHON_MODULE(exception_test) > { > exception ("some_exception") > .def ("what", &some_exception::what) > .def ("get_additional_errorinfo", > &some_exception::get_additional_errorinfo) > ; > } > > This is actually quite straightforward to implement, I think. > Basically: > > * exception<...> is derived from class<...> > > * we extend class_ with a protected constructor which takes an > object which represents an additional base class to use. This > argument is passed on to the class_base constructor and used as > an additional base class. > > * exception<...> reproduces the class_ constructor signatures and > forwards to the new class_ constructor, with the object > referring to python's builtin Exception type. > > >> When an instance of "some_exception" is thrown and caught by the library it >> would then raise the associated python exception passing a python version of >> the "some_exception" instance as the exception argument. >> The exception handler in the python script could look like >> try: >> do_something_eventually_raising_some_exception() >> except exception_test.some_exception, e: >> print "Caught some_exception (%s, %d)" % (e.what(), >> e.get_additional_errorinfo()) >> >> I think this *is* easier for the user of the library but as I said: I have >> no clue how to implement something like that. > > OK, I agree that it's easier. Why don't you poke around a bit more > based on my hints? I'm sure you can make it work. > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com -- Dave Abrahams Boost Consulting www.boost-consulting.com From dave at boost-consulting.com Thu Jul 31 20:28:00 2003 From: dave at boost-consulting.com (David Abrahams) Date: Thu, 31 Jul 2003 14:28:00 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> <3F25D683.B25CBCAF@sitius.com> <3F2939B0.4B8047E8@sitius.com> <3F29514D.506729DF@sitius.com> Message-ID: Nikolay Mladenov writes: > I can't get boost_python to compile with this swich, and I have > 1.29.0 compiled with it. You're saying Boost.Python 1.29.0 used to compile with /vmg? > The problem is that one generally shouldn't mix binaries compiled > with different pointer_to_member option and we have everiting built > with /vmg which acording to the ms docs is the safest, since all the > pointer-to-members have the same "sizeof". Can the problem be that > some "trait" switches because of the sizeof(pointer_to_member)? I seriously doubt it. This code is designed to be portable and agnostic to how the compiler represents member pointers. The errors we see are all of the form: "error C2039: 'member_name' : is not a member of 'some_template'" But if you look at the definition of 'some_template', the member is certainly there. This is compiler insanity, plain and simple. If indeed it used to compile, all I can suggest is that you do what I did this morning: a binary search through time for the CVS change which caused /vmg to start failing. Tedious but effective. -- Dave Abrahams Boost Consulting www.boost-consulting.com From nickm at sitius.com Thu Jul 31 21:18:03 2003 From: nickm at sitius.com (Nikolay Mladenov) Date: Thu, 31 Jul 2003 15:18:03 -0400 Subject: [C++-sig] Re: args patch References: <3F2440E7.C2000F56@sitius.com> <3F2527FC.50969E27@sitius.com> <3F2556E3.3F4C0A8C@sitius.com> <3F25D683.B25CBCAF@sitius.com> <3F2939B0.4B8047E8@sitius.com> <3F29514D.506729DF@sitius.com> Message-ID: <3F296B6B.BDB7991A@sitius.com> David Abrahams wrote: > > Nikolay Mladenov ?nickm at sitius.com? writes: > > ? I can't get boost_python to compile with this swich, and I have > ? 1.29.0 compiled with it. > > You're saying Boost.Python 1.29.0 used to compile with /vmg? Yes. Without a problem. > This is compiler insanity, plain and > simple. I can easily believe that:). Though the error seems to come from some msvc workaround code. > > If indeed it used to compile, all I can suggest is that you do what I > did this morning: a binary search through time for the CVS change > which caused /vmg to start failing. Tedious but effective. Okey, I 'll try that. From ganssauge at gmx.de Thu Jul 31 23:01:04 2003 From: ganssauge at gmx.de (=?iso-8859-1?Q?Gottfried_Gan=DFauge?=) Date: Thu, 31 Jul 2003 23:01:04 +0200 Subject: [C++-sig] Re: Wrapper for exception translation References: <2040C0A1CA23D51181A30050BAAC990274AAC2@berexch.ber.haufemg.com> <001201c34936$303e0b60$44a837c2@gieke> Message-ID: <013401c357a6$db402e70$44a837c2@gieke> Hi Dave, I digged through the class_<> implementation and I think I know what I must do to implement it. Like you suggested I would add another argument to the class_base constructor which is used as another base class for the newly created class. The only problem I'm having is the programming interface for the user: I could the simply pass a const pointer to the python exception type to the protected class_<> constructor. This would - at least for my feeling - look a bit strange because this would be the only low level python detail on this level. Additionally it would require from the programmer that he knows the low level name of the exception type. Alternatively I could create an object wrapper around the exception types and pass a const reference to one of those. This is not too complicated but it takes it's time. Furthermore I'm not sure about your reaction to my plans being too complicated :-(. I'm on vacation this week and the next so I currently work only sporadically. I think I could have a first prototype by monday, august 18. Cheers, Gottfried ----- Original Message ----- From: "David Abrahams" Newsgroups: gmane.comp.python.c++ Cc: Sent: Thursday, July 31, 2003 7:47 PM Subject: Re: Wrapper for exception translation > > Hi Gottfried, > > Any progress on this front? > > David Abrahams writes: > > > Gottfried Gan?auge writes: > > > >> ... > >>> > It could be even simpler with a completely different design but > >> frankly - I > >>> > have no clue how to implement that: > >>> > We would need a way to somehow derive (in the python sense) a class_<> > >> from > >>> > PyExc_Exception (the type of the python Exception class) or any other > >> python > >>> > class (PyErr_NewException() has a base parameter, which could be used > >> for > >>> > that). > >>> > > >>> > At the same time an exception_translator should be registered for that > >>> > class_<> which uses PyErr_SetObject() to raise a copy of the exception > >>> > caught. > >>> > >>> None of that sounds simpler to me. > >>> > >>> > This would allow us to have true Python exceptions in a pythonic sense > >>> > directly wrapped around the corresponding C++ exception. > >>> > >>> Doesn't sound like a big advantage to me, but I guess if you had > >>> stored data members in the C++ exception type you'd want them to be > >>> preserved. Hmm, there's no reason you can't build a BPL extension > >>> class which also inherits from Exception, but it seems tough. > >> > >> Maybe an example is in order: > >> > >> // this is the exception to wrap > >> struct some_exception { > >> some_exception (const char *description, int error_number); > >> > >> const char *what() const; > >> int get_additional_errorinfo() const; > >> }; > >> > >> // This is how it could be wrapped > >> BOOST_PYTHON_MODULE(exception_test) > >> { > >> class_ > ("some_exception") > >> .def ("what", &some_exception::what) > >> .def ("get_additional_errorinfo", > >> &some_exception::get_additional_errorinfo) > >> ; > >> } > > > > Yes, I understood it to be something like that. What about: > > > > BOOST_PYTHON_MODULE(exception_test) > > { > > exception ("some_exception") > > .def ("what", &some_exception::what) > > .def ("get_additional_errorinfo", > > &some_exception::get_additional_errorinfo) > > ; > > } > > > > This is actually quite straightforward to implement, I think. > > Basically: > > > > * exception<...> is derived from class<...> > > > > * we extend class_ with a protected constructor which takes an > > object which represents an additional base class to use. This > > argument is passed on to the class_base constructor and used as > > an additional base class. > > > > * exception<...> reproduces the class_ constructor signatures and > > forwards to the new class_ constructor, with the object > > referring to python's builtin Exception type. > > > > > >> When an instance of "some_exception" is thrown and caught by the library it > >> would then raise the associated python exception passing a python version of > >> the "some_exception" instance as the exception argument. > >> The exception handler in the python script could look like > >> try: > >> do_something_eventually_raising_some_exception() > >> except exception_test.some_exception, e: > >> print "Caught some_exception (%s, %d)" % (e.what(), > >> e.get_additional_errorinfo()) > >> > >> I think this *is* easier for the user of the library but as I said: I have > >> no clue how to implement something like that. > > > > OK, I agree that it's easier. Why don't you poke around a bit more > > based on my hints? I'm sure you can make it work. > > > > -- > > Dave Abrahams > > Boost Consulting > > www.boost-consulting.com > > -- > Dave Abrahams > Boost Consulting > www.boost-consulting.com