1

I was looking into creation of DLL's using C++ lately and stumbled by accident into the discussion of "Abstract Base Classes vs. Pimpl Idiom" when it comes to ABI compatibility. I'm pretty new to dealing with DLLs so please be patient if I get a term/concept wrong. Here's my story:

I've read in this article here over at CodeProject.com where the author states that using an abstract interface is the way to go.

To summarize: You have an abstract base class class IFoo, a factory method extern "C" __declspec(dllexport/dllimport) IFoo* createFoo(); and an actual implementation class FooImpl of the IFoo interface which is what is actually instantiated and returned by createFoo().

So far so good.

Now I found some people argue that only the Pimpl-Idiom could preserve ABI compatibility (What's is the point of PImpl pattern while we can use interface for the same purpose in C++?, Pimpl idiom vs Pure virtual class interface ) and I'm a bit confused:

The way I understand pimpl: You have a class Bar holding a pointer to class BarImpl which contains all implementation detail.

My questions:

  1. If I only change the internal workings in both cases (change either class FooImpl or class BarImpl) the ABI of code "facing the user" in both cases does not change, or does it ?

  2. On the other hand both approaches break clearly ABI compatibility if I make changes to class Foo or class Bar, right ?

  3. In case my assumptions of ABI compatibility using abstract base classes are wrong. Do I have to use a mixture of abstract base classes in DLLs to truly keep ABI compatible if I only perform changes to internal stuff of the libraries code ?

I hope I could clearly formulate what's unclear to me ;)

EDIT: By "changing internals" I also refer to adding/removing of members/methods in the implementation classes FooImpl and BarImpl.

Rafael Pasquay
  • 199
  • 2
  • 9
  • 2
    Conceptually, if any change in the interface exposed by your DLL is getting changed then compatibility will break. If you modify internally like function body then it doesn't matter. But you should also keep in mind the future possibility during design. – Sanjeev Sep 26 '18 at 11:25
  • @Sanjeev Thanks for your comment! I've edited by answer to point out that I not only refer to a change in e.g. function bodies but also adding removing stuff (methods and members alike) in the implementation classes which do not directly change the respective "interfaces" (class the users sees). – Rafael Pasquay Sep 26 '18 at 11:31
  • 1
    have a look on this link, it will provide you some light on this https://stackoverflow.com/questions/52494130/how-dynamic-linking-reacts-on-a-change-in-object/52494228#52494228 – Sanjeev Sep 26 '18 at 11:35
  • 1
    1. Yes you are fine. 2. Yes if you change the API you break compatibility. – drescherjm Sep 26 '18 at 11:40
  • ***he author states that using an abstract interface is the way to go*** He did not address pimpl at all. There is even a question in the comments of his article asking about that. – drescherjm Sep 26 '18 at 11:44
  • I'm aware of the author not talking about pimpl. While looking _more into the topic of ABI compatibility etc._ I stumbled upon some people mentioning this idiom and came here for an answer regarding **why pimple can achieve ABI independency and not the use of an abstract base class like outlined in my question above**. I did not see the comment regarding pimpl in the article I linked. Thank you for pointing that out. – Rafael Pasquay Sep 26 '18 at 15:47
  • @drescherjm The question you mentioned below the CodeProject article linked by me is unfortunately lacking an answer. – Rafael Pasquay Sep 26 '18 at 15:53

0 Answers0