Jump to page: 1 2 3
Thread overview
H1 2015 - C++ integration
Feb 13, 2015
Guillaume Chatelet
Feb 13, 2015
Kagamin
Feb 13, 2015
Guillaume Chatelet
Feb 13, 2015
Kagamin
Feb 13, 2015
Guillaume Chatelet
Feb 13, 2015
Daniel Murphy
Feb 14, 2015
Guillaume Chatelet
Feb 14, 2015
Guillaume Chatelet
Feb 14, 2015
Paolo Invernizzi
Feb 14, 2015
Daniel Murphy
Feb 14, 2015
Guillaume Chatelet
Feb 14, 2015
Guillaume Chatelet
Feb 15, 2015
Guillaume Chatelet
Feb 15, 2015
Paolo Invernizzi
Feb 15, 2015
Guillaume Chatelet
Feb 15, 2015
Paolo Invernizzi
Feb 17, 2015
Guillaume Chatelet
Feb 17, 2015
Guillaume Chatelet
Feb 17, 2015
Benjamin Thaut
Feb 17, 2015
Guillaume Chatelet
Feb 17, 2015
Paolo Invernizzi
Jul 05, 2015
Guillaume Chatelet
February 13, 2015
I'm working on integration of D with the C++ STL (at least the linux gnu one).

* You can have a look at a current draft implementation (1).

* There is a name mangling issue in dmd related to the compression of usual stl types when the type is const
eg. dmd will mangle 'std::vector<int>::size() const' as '_ZNK3std6vectorIiSaIiEE4sizeEv' where it should be mangled '_ZNKSt6vectorIiSaIiEE4sizeEv'. Note 'std' is being compressed into 'St'.

I believe this is coming from https://github.com/D-Programming-Language/dmd/blob/master/src/cppmangle.c#L453 which tests only the non const type pattern.
According to (2) this substitution seems illegal "Note that substitutable components are the represented symbolic constructs, not their associated mangling character strings."
This lead to undefined reference when linking and that's why my code overrides the name mangling.

* In the video Walter posted recently (3), he states that one should use a class to represent a std::string or std::vector in D because most of the time we want to have reference semantic. I find this a bit counter intuitive for people coming from C++ since they are clearly value semantic. std::string and std::vector should behave the same in C++ and D to confirm the principle of least astonishment.

I started implementing them as struct (4) but then I can only have @disable default constructors.

I would like to gather opinions on struct vs class. Any ideas ?

Guillaume
---
1. https://github.com/gchatelet/dlang_cpp_std
2. http://mentorembedded.github.io/cxx-abi/abi.html#mangling-compression
3. https://www.youtube.com/watch?v=IkwaV6k6BmM
4. https://github.com/gchatelet/dlang_cpp_std/blob/master/std_string.d
February 13, 2015
It's not like you're free to choose, because struct and class can use different mangling.
February 13, 2015
On Friday, 13 February 2015 at 13:03:18 UTC, Kagamin wrote:
> It's not like you're free to choose, because struct and class can use different mangling.

I'm not sure I get your point. In C++ classes without vtables are exactly like structs. Also I don't see any difference between a struct or a class name mangling on Gnu Linux.

class/struct S{};
S foo();

foo gets mangled "_Z3foov" if S is a struct or a class.

What did I miss ? Do you have compelling examples ?
February 13, 2015
On Friday, 13 February 2015 at 14:07:44 UTC, Guillaume Chatelet wrote:
> I'm not sure I get your point. In C++ classes without vtables are exactly like structs. Also I don't see any difference between a struct or a class name mangling on Gnu Linux.

Do you want it to be compatible with Gnu Linux only?

> What did I miss ? Do you have compelling examples ?

AFAIK, MSVC++. There are other C++ compilers too.
February 13, 2015
On Friday, 13 February 2015 at 14:15:10 UTC, Kagamin wrote:
> On Friday, 13 February 2015 at 14:07:44 UTC, Guillaume Chatelet wrote:
>> I'm not sure I get your point. In C++ classes without vtables are exactly like structs. Also I don't see any difference between a struct or a class name mangling on Gnu Linux.
>
> Do you want it to be compatible with Gnu Linux only?
>
>> What did I miss ? Do you have compelling examples ?
>
> AFAIK, MSVC++. There are other C++ compilers too.

Thx, according to wikipedia (http://en.wikipedia.org/wiki/Visual_C%2B%2B_name_mangling#Data_Type) VisualC++ is indeed encoding struct and class with U anv V.
February 13, 2015
"Guillaume Chatelet"  wrote in message news:gvnxmwplwkyfrydwrulq@forum.dlang.org...

> I'm not sure I get your point. In C++ classes without vtables are exactly like structs. Also I don't see any difference between a struct or a class name mangling on Gnu Linux.
>
> class/struct S{};
> S foo();
>
> foo gets mangled "_Z3foov" if S is a struct or a class.
>
> What did I miss ? Do you have compelling examples ?

This is not a good example, because the return type is clearly not mangled into the function name.  (Because you can't overload on return type.)

void foo(S); should show the problem with some mangling schemes. 

February 14, 2015
On Friday, 13 February 2015 at 18:47:53 UTC, Daniel Murphy wrote:
> "Guillaume Chatelet"  wrote in message news:gvnxmwplwkyfrydwrulq@forum.dlang.org...
>
>> I'm not sure I get your point. In C++ classes without vtables are exactly like structs. Also I don't see any difference between a struct or a class name mangling on Gnu Linux.
>>
>> class/struct S{};
>> S foo();
>>
>> foo gets mangled "_Z3foov" if S is a struct or a class.
>>
>> What did I miss ? Do you have compelling examples ?
>
> This is not a good example, because the return type is clearly not mangled into the function name.  (Because you can't overload on return type.)
>
> void foo(S); should show the problem with some mangling schemes.

You're absolutely right, my bad.

class/struct S {};
void foo(S s){}

foo gets mangled "_Z3foo1S" if S is a struct or a class.
February 14, 2015
I did a few tests. Using a class doesn't work because of the added vptr.
The data would be managed at the same time on the D and the C++ side.

Structs work however because we can add something like this :

struct std_string {
  void[8] _ = void; // to match sizeof(std::string) and pad the object correctly.
}

The padding will be left untouched on the D side because of void initializer and will be managed entirely on the C++ side.

Using a class crashes (C++ and D step on each others toes).

Structs work expect for :
- name mangling on linux (bug reported in my first message)
- name mangling on Windows at least (name would be mangled as a struct instead of class)
- disabled default constructor.

Mangling on Linux is fixable as well as default construction : we can provide a special function that would create a new instance.

But for the windows name mangling, I don't see a way out in the language as it is right now.

Any ideas ?
February 14, 2015
On Saturday, 14 February 2015 at 17:24:51 UTC, Guillaume Chatelet wrote:
> I did a few tests. Using a class doesn't work because of the added vptr.
> The data would be managed at the same time on the D and the C++ side.
>
> Structs work however because we can add something like this :
>
> struct std_string {
>   void[8] _ = void; // to match sizeof(std::string) and pad the object correctly.
> }
>
> The padding will be left untouched on the D side because of void initializer and will be managed entirely on the C++ side.
>
> Using a class crashes (C++ and D step on each others toes).
>
> Structs work expect for :
> - name mangling on linux (bug reported in my first message)
> - name mangling on Windows at least (name would be mangled as a struct instead of class)
> - disabled default constructor.
>
> Mangling on Linux is fixable as well as default construction : we can provide a special function that would create a new instance.
>
> But for the windows name mangling, I don't see a way out in the language as it is right now.
>
> Any ideas ?

I'm also using pragma(mangle) and struct with a fake virtual table...

;-(

I think that another problem is that, if you use a class in D instead of a struct, it's a mess with C++ functions taking a reference:

    D - class vector .....
    C++ - foo(const vector& a) ...
    C++ - foo(const vector* a) ...

How do we specify the right mangling for the reference?
---
/P
February 14, 2015
On 2/13/15 4:23 AM, Guillaume Chatelet wrote:
> * In the video Walter posted recently (3), he states that one should use
> a class to represent a std::string or std::vector in D because most of
> the time we want to have reference semantic. I find this a bit counter
> intuitive for people coming from C++ since they are clearly value
> semantic. std::string and std::vector should behave the same in C++ and
> D to confirm the principle of least astonishment.

Yah, this is still a bit in the air. The point here is that the simplest route to getting std::vector working in D is to avoid the many little difference between C++ copy ctors and D's postblit. As such, we say: pass std::vector by reference from/to C++, and never construct or copy one on the D side.

I think that's a usable policy - most of the time containers are not supposed to be copied and people must carefully pass them by reference everywhere. The annoying part is having one as a member in a D type.

Clearly we need to think this through carefully.

> I started implementing them as struct (4) but then I can only have
> @disable default constructors.

I think that can be made to work, too.

> I would like to gather opinions on struct vs class. Any ideas ?

To also reply to your more recent message:

> I did a few tests. Using a class doesn't work because of the added vptr.
> The data would be managed at the same time on the D and the C++ side.

That should work. You don't need any layout information at all for std::vector on the D side; all you do is pass a pointer to std::vector around D code, and when you want to mess with it you pass the pointer to "this" appropriately. It all works; there's no need for D to know the layout, only the correct pointer and method signatures.

I think a gating issue right now is handling C++ exceptions in D code. C++ stdlib types are not really usable without exceptions.


Andrei

« First   ‹ Prev
1 2 3