gnustep-dev
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: ABI Compatibility (was Re: Installation woes for the average user...


From: Richard Frith-Macdonald
Subject: Re: ABI Compatibility (was Re: Installation woes for the average user...)
Date: Thu, 5 Mar 2009 17:20:12 +0000


On 5 Mar 2009, at 16:10, Gregory Casamento wrote:

The last collective release was only two months ago.

As far as the ABI is concerned that is certainly an issue. The last time we discussed it we came up with two solutions: • Pad the ivar-structures in the classes out to give space to grow so that it pushes off any ABI compatibility issues as long as possible. This is why in some APIs, including Cocoa, you see things like "reserved..." or "private..." variables. These are there to give room to grow. The disadvantage is that the classes would then take up more memory as a result.

And oftentimes the padding is insufficient for what you want to do. So this mechanism alone can't make the code future-proof.

• Move the ivar-structures out of the classes and replace them with a void pointer to the actual structure. This has the advantage that we will never be able to break ABI compatibilty since the sizes of the structs in the classes will not change... but it also has the disadvantage of adding a layer of complexity to getting and setting variables

True. The code complexity is easily overcome by using the C preprocessor, but it's a real pain trying to examine such classes from within gdb.

as well as potentially causing unpredictable issues due to unforseen incompatibilities such as cases where the wrong data is written into a data structure causing some sort of corruption when using the wrong version of a library.

That can't happen ... if you are using a different version of the library then it's using its own different version of the data structure. The big disadvantage of this approach is (in some cases) performance. You have to do twice as much memory allocation/deallocation sincethe object and the structure holding its ivars are separate. This is really bad news for objects which are created/destroyed frequently, but irrelevant for other objects with long lifetimes.

I, personally, think we should implement the first option. It's the method most APIs follow and it is the method that is the most predictable. It would take some effort to do this, but it's minimal since it's really just padding the structures with a given amount of space.

You missed one of the most common strategies used in Cocoa ... declaring the public API as an abstract base class with no instance variables, and returning instances of privates subclasses. I dislike that as it makes it impossible to properly subclass many classes, but as we are aiming for Apple compatibility it's not really a disadvantege (people can't subclass easily in Cocoa either).

Where apple use class clusters, we may as well do the same thing.
Otherwise, where we are adding new classes we should probably use a pointer to private data for long lived and complex classes with a lot of instance variables, but use padding (reserve a pointer too as part of the padding) for simpler classes with a short lifetime.


With the void* pointer to the structure we might be able to do something clever to help debugging. I haven't tried it, but we could define a preprocessor symbol (eg. GSRESERVED) which normally expands to 'void*' (in the public API) but expands to 'struct foo*' inside the source files, so that the symbol tables in the compiled code know what the internal variable layout actually is, and gdb can therefore make sense of things when examining the an object.






reply via email to

[Prev in Thread] Current Thread [Next in Thread]