On 09/23/2015 04:34 AM, Ahmed S. Darwish wrote:
### Anonymous unions

Used to provide the mempool with polymorphic memory region access
regardless of the type of memory used:

     union {
         pa_mem mem;
         union {
             pa_shm shm;
             pa_memfd memfd;
             pa_privatemem privatemem;
         } per_type;
     };

This kind of usage looks good.

### Anonymous structs

They are also used in the memfd patches, but they're really used
to minimize code repetitions and make relationships explicit.

Basically, we want to build an inheritance relationship: pa_shm,
pa_memfd, and pa_privatemem has the common parent pa_mem. We also
want to make this relationship explicit since it's at the core of
the anonymous polymorphic union mentioned above.

To do so without introducing extra (compile-time) dereferences,
the following patten is used:

/* Parent anonymous structure representing a plain memory
  * area and its size. Different structures inherit from this,
  * representing different memory area types (e.g. Posix SHM,
  * Linux memfds, or private mallocs).
  *
  * To inherit from this object, just include PA_MEM_STRUCT as
  * the very first element of your structure definition. */
#define PA_MEM_STRUCT struct {   \
     void *ptr;                   \
     size_t size;                 \
} PA_GCC_PACKED

typedef struct pa_mem {
     PA_MEM_STRUCT;
} pa_mem;

This way, children pa_shm, pa_memfd, and pa_privatemem can be
defined as follows:

typedef struct pa_shm {
     PA_MEM_STRUCT;
     unsigned id;
     bool do_unlink;
} pa_shm;

typedef struct pa_memfd {
     PA_MEM_STRUCT;
     int fd;
} pa_memfd;

typedef struct pa_privatemem {
     PA_MEM_STRUCT;
} pa_privatemem;


I don't like that (on a purely subjective basis).


..

So to summarize, such annotation explicitly shows the inheritance
relationship, minimize code repeition in the struct defintions, and
also saves us an extra compile-time dereference in shm.c, memfd.c,
and privatemem.c code. It also really works in tandem with the
earlier polymorphic union:

     union {
         pa_mem mem;
         union {
             pa_shm shm;
             pa_memfd memfd;
             pa_privatemem privatemem;
         } per_type;
     };

Hopefully these patterns will be OK from your side :-)

Regards,



--
Alexander E. Patrakov
_______________________________________________
pulseaudio-discuss mailing list
[email protected]
http://lists.freedesktop.org/mailman/listinfo/pulseaudio-discuss

Reply via email to