extern(C++, ns) is wrong

Jonathan M Davis newsgroup.d at jmdavisprog.com
Wed Sep 5 13:53:15 UTC 2018


On Wednesday, September 5, 2018 7:03:26 AM MDT Nicholas Wilson via 
Digitalmars-d wrote:
> This is a prime example of an industry blocker if ever there was.
> Yes there has been a lot of talking past each other, but surely
> you understand _what_  Manu is wanting even if you seem to think
> that your workarounds (which you called solutions) are
> sufficient. It is backwards compatible and solves a clear need, I
> don't see why this is such a contentious issue.

Based on everything Walter said in the previous thread, it honestly seems to
me to be primarily like he just can't give up on the idea that D has to
worry about modeling C++ namespaces. Pretty much all of the extra
complications that come from the current approach stem from insisting on
modeling namespaces in D instead of just treating the namespace as part of
the information that you give to the compiler to indicate what the symbol in
D is supposed to correspond to in C++ when the compiler goes to mangle it.

What Walter did makes perfect sense if you assume that D needs to care about
namespaces when using the C++ symbol in D, but the conclusion of the rest of
us when looking at the problem has been that D really doesn't need to care
about the namespaces beyond mangling, because D modules already solve the
problem. In actuality, there's no more need to worry about a C++ symbol's
namespace when using it in D than there is to have to care about which
header file a C symbol lives in when you use it in D. The module you put it
in will likely relate to the header file that it comes from, and in the case
of a C++ symbol, it may even relate to the namespace that it's in in C++,
but that's just a matter of sanely organizing your bindings in D so that
folks using the code will have an easy time finding the symbols if they know
where they live in C/C++. It's not required for actually differentiating the
symbols when using them in D. The modules already take care of that quite
well.

And if you really have a situation where multiple namespaces with the same
symbol name live in a C++ header, and you want to put them in the same
module in D, it should be trivial to stick them in structs, classes, or
templates to namespace them like folks already sometimes do with D code when
they want to emulate namespaces in D. Or if we left the current
implementation in addition to what Manu wants, then the current approach
could be used in those cases. So, the primary situation that Walter brought
up with using the module system to differentiate symbols rather than having
the compiler emulate the namespace like it currently does should be very
solvable with what Manu wants, whereas every issue that Manu and Atila
brought up required jumping through hoops in order to get it working with
the current solution, and it frequently ends up not only being much harder
to implement, but it's less user-friendly for the programmers using the
bindings.

So, if you can accept the idea that there really is no need to emulate C++
namespaces in D - even if you want to be able to stick multiple namespaces
in the same module - then I really don't see any reason to prefer the
current approach to extern(C++, "namespace") like Manu wants. But for
whatever reason, Walter just doesn't seem to accept the idea that it's
unnecessary to emulate namespaces in D in order to link to them, and he
thinks that all of the hoops that it causes you to jump through are worse
than the extra hoops that you would have to jump through to get multiple
namespaces in the same file if extern(C++, namespace) weren't a thing. I can
understand that from the standpoint that extern(C++, namespace) has already
been implemented, whereas extern(C++, "namespace") has not been. So, even if
we were to then have both instead of replacing one with the other, there's
definitely work involved. However, I fail to understand why extern(C++,
namespace) is superior from a technical perspective. Rather, it clearly has
some serious drawbacks in comparison to extern(C++, "namespace"). But be it
because of the effort involved with implementing a new solution, or because
the current solution was his idea, or because of some other reason, thus
far, Walter just doesn't seem to want to come around to the idea that all we
need is the mangling, and then we should be able to do everything else we
need with what D already provides. Worst case, we might need to make
adjustments to make sure that something like

static Namespace
{
    extern(C++, "Namespace") static bool freeFunc(int foo);
}

can compile without expecting freeFunc to be part of a struct. But I'm
pretty sure that even if that wouldn't work, a template could be used
as the namespace isnead, and we could even choose to leave in

extern(C++, Namespace) bool freeFunc(int foo);

for the rare case where that makes more sense than simply letting the module
system do its job.

But regardless, I'm with you and Manu at this point in that I don't
understand why extern(C++, "Namespace") isn't a clearly better (and simpler)
solution overall. But maybe we'll get lucky and after Walter has thought
about it long enough, he'll come around. Either way, per the current
process, we would clearly need a DIP even if Walter already agreed. So, the
next step is to write a DIP, and hopefully it can be written well enough
that it's appropriately convincing unlike everything that has been argued
thus far.

- Jonathan M Davis





More information about the Digitalmars-d mailing list