
On Fri, May 25, 2018 at 09:13:51AM +0200, Andrea Bolognani wrote:
On Wed, 2018-05-23 at 18:05 +0200, Pavel Hrdina wrote:
I liked the way how GLib is solving the issue so we can simply use the same approach since it looks reasonable.
There would be three different macros that would be used to annotate variable with attribute cleanup:
VIR_AUTOFREE char *str = NULL;
- this would call virFree on that variable
VIR_AUTOPTR(virDomain) domain = NULL;
- this would call registered free function on that variable - to register the free function you would use:
VIR_DEFINE_AUTOPTR_FUNC(virDomain, virDomainFree);
VIR_AUTOCLEAR(virDomain) domain = { 0 };
- this would call registered clear function to free the content of that structure - to register that clear function you would use:
VIR_DEFINE_AUTOCLEAR_FUNC(virDomain, virDomainClear);
I assume you would get a compilation error when trying to eg. use VIR_AUTOCLEAR() with a type that doesn't have a clear function registered?
Yes, because the macro would call non existing function.
As for VIR_AUTOFREE() and VIR_AUTOPTR(), I'd very much prefer if we could have a single macro, since from the high-level point of view they're both doing the same thing, that is, freeing memory that was allocated on the heap.
It would be nice but I don't think it's worth it.
However, I realize it might not be possible to register free functions for a native type without having to introduce something like
typedef char * virString;
thus causing massive churn. How does GLib deal with that?
If you would look into GLib documentation you would see that this design basically copies the one in GLib: GLib libvirt g_autofree VIR_AUTOFREE g_autoptr VIR_AUTOPTR g_auto VIR_AUTOCLEAR In GLib you are using them like this: g_autofree char *string = NULL; g_autoptr(virDomain) dom = NULL; g_auto(virDomain) dom = { 0 }; So yes it would require to introduce a lot of typedefs for basic types and that is not worth it. In libvirt we would have: VIR_AUTOFREE char *string = NULL; VIR_AUTOPTR(virDomainPtr) dom = NULL; VIR_AUTOCLEAR(virDomain) dom = { 0 }; If you notice the difference, in libvirt we can use virDomainPtr directly because we have these typedefs, in GLib macro G_DEFINE_AUTOPTR_CLEANUP_FUNC creates similar typedef. Pavel