STL Containers and Binary Interface Compatibility

二次信任 提交于 2019-12-04 15:49:33
Emilio Garavaglia

I think the problem preceeds your theory: C++ doesn't specify the ABI (application binary interface).

In fact even C doesn't, but being a C library just a collection of functions (and may be global variables) the ABI is just the name of the functions themselves. Depending on the platform, names can be mangled somehow, but, since every compiler must be able to place system calss, everything ends up using the same convention of the operating system builder (in windows, _cdecl just result in prepending a _ to the function name.

But C++ has overloading, hence more complex mangling scheme are required. As far as of today, no agreement exists between compiler manufacturers about how such mangling must be done. It is technically impossible to compile a C++ static library and link it to a C++ OBJ coming from another compiler. The same is for DLLs.

And since compilers are all different even for compiled overloaded member functions, no one is actually affording the problem of templates.

It CAN technically be afforded by introducing a redirection for every parametric type, and introducing dispatch tables but ... this makes templated function not different (in terms of call dispatching) than virtual functions of virtual bases, thus making the template performance to become similar to classic OOP dispatching (although it can limit code bloating ... the trade-off is not always obvious)

Right now, it seems there is no interest between compiler manufacturers to agree to a common standard since it will sacrifice all the performance differences every manufacturer can have with his own optimization.

C++ templates are compile-time generated code.
This means that if you want to use a templated class, you have to include its header (declaration) so the compiler can generate the right code for the templated class you need.

So, templates can't be pre-compiled to binary files.

What other libraries give you is pre-compiled base-utility classes that aren't templated.

C# generics for example are compiled into IL code in the form of dlls or executables.
But IL code is just like another programming language so this allows the compiler to read generics information from the included library.

.Net IL code is compiled into actual binary code at runtime, so the compiler at runtime has all the definitions it needs in IL to generate the right code for the generics.

I'm curious to know if anyone is working on compatible interface layers for STL objects across multiple compilers and platforms for C++.

Yes, I am. I am working on a layer of standardized interfaces which you can (among other things) use to pass binary safe "managed" references to instances of STL, Boost or other C++ types across component boundaries. The library (called 'Vex') will provide implementations of these interfaces plus proper factories to wrap and unwrap popular std:: or boost:: types. Additionally the library provides LINQ-like query operators to filter and manipulate contents of what I call Range and RangeSource. The library is not yet ready to "go public" but I intend to publish an early "preview" version as soon as possible...

Example:

com1 passes a reference to std::vector<uint32_t> to com2:

com1:

class Com2 : public ICom1 {
    std::vector<int> mVector;

    virtual void Com2::SendDataTo(ICom1* pI)
    {
        pI->ReceiveData(Vex::Query::From(mVector) | Vex::Query::ToInterface());
    }
};

com2:

class Com2 : public ICom2 {
    virtual void Com2::ReceiveData(Vex::Ranges::IRandomAccessRange<uint32_t>* pItf)
    {
        std::deque<uint32_t> tTmp;
        // filter even numbers, reverse order and process data with STL or Boost algorithms
        Vex::Query::From(pItf)
            | Vex::Query::Where([](uint32_t _) -> { return _ % 2 == 0; })
            | Vex::Query::Reverse
            | Vex::ToStlSequence(std::back_inserter(tTmp));
        // use tTmp...
    }
};

You will recognize the relationship to various familiar concepts: LINQ, Boost.Range, any_iterator and D's Ranges... One of the basic intents of 'Vex' is not to reinvent wheel - it only adds that interface layer plus some required infrastructures and syntactic sugar for queries.

Cheers,

Paul

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!