Search code examples
cframeworksinitializationheader-files

Array members defined as constants


I'm trying to implement a framework, where I would need to declare (in .h file) the list of available "drivers" (struct variables) which would be defined in specific .c modules. As the list would probably grow in the future I would like to have it all in one place in the .h file to keep it easily extensible.

E.g. let's have "driver.h"

typedef struct driver {
    int id;
    char name[10];
    int(*init)();
    void (*deinit)();
    int (*doTheJob)(int);
} driver_t;

#define DRIVERLIST driver1, driver2, driver3
#define DRIVERS extern driver_t DRIVERLIST;

DRIVERS

Then the specific drivers (driver1, driver2, driver3) would be defined in dedicated modules.. e.g. driver1.c, driver2.c .. etc...

But then I would like to have a module e.g. manager.c where I would like to define the array of available drivers as declared in driver.h so that I'm able to iterate the array and get the drivers for usage in other parts of the framework..

So in manager.c I would need something like:

driver_t drivers[MAX_DRIVERS] = {DRIVERS}

But obviously it does not compile this way.. The main idea is to edit only driver.h when I need to add declaration for additional driver in the future and then just implement it in dedicated module, whithout the necessity to edit e.g. manager.c or other parts of the framework.. Do you have any idea, how to implement such mechanism in c?


Solution

  • I think I found a solution. I took the inspiration from the rtl_433 project https://github.com/merbanan/rtl_433/blob/master/include/rtl_433_devices.h where they defined something similar for the devices declarations.

    So it should be in header file:

    /* driver.h */
    #define DRIVERS \
        DECL(driver1) \
        DECL(driver2) 
    
    
    #define DECL(name) extern driver_t name;
        DRIVERS
    #undef DECL
    

    And then in module:

    /* driver.c */
    
    driver_t* drivers[] = {  
    #define DECL(name) &name,
        DRIVERS
    #undef DECL
    };