diff --git a/flight/UAVObjects/uavobjectmanager.c b/flight/UAVObjects/uavobjectmanager.c index c339af0fe..7938f99c3 100644 --- a/flight/UAVObjects/uavobjectmanager.c +++ b/flight/UAVObjects/uavobjectmanager.c @@ -41,6 +41,17 @@ // Macros #define SET_BITS(var, shift, value, mask) var = (var & ~(mask << shift)) | (value << shift); +/* Table of UAVO handles registered at compile time */ +extern struct UAVOData * __start__uavo_handles __attribute__((weak)); +extern struct UAVOData * __stop__uavo_handles __attribute__((weak)); + +#define UAVO_LIST_ITERATE(_item) \ +for (struct UAVOData ** _uavo_slot = &__start__uavo_handles; \ + _uavo_slot <= &__stop__uavo_handles; \ + _uavo_slot++) { \ + struct UAVOData * _item = *_uavo_slot; \ + if (_item == NULL) continue; + /** * List of event queues and the eventmask associated with the queue. */ @@ -98,7 +109,6 @@ struct UAVOData { * inside the payload for this UAVO. */ struct UAVOMeta metaObj; - struct UAVOData * next; uint16_t instance_size; } __attribute__((packed)); @@ -164,7 +174,6 @@ static void customSPrintf(uint8_t * buffer, uint8_t * format, ...); #endif // Private variables -static struct UAVOData * uavo_list; static xSemaphoreHandle mutex; static const UAVObjMetadata defMetadata = { .flags = (ACCESS_READWRITE << UAVOBJ_ACCESS_SHIFT | @@ -188,7 +197,6 @@ static UAVObjStats stats; int32_t UAVObjInitialize() { // Initialize variables - uavo_list = NULL; memset(&stats, 0, sizeof(UAVObjStats)); // Create mutex @@ -338,9 +346,6 @@ UAVObjHandle UAVObjRegister(uint32_t id, /* Initialize the embedded meta UAVO */ UAVObjInitMetaData (&uavo_data->metaObj); - /* Add the newly created object to the global list of objects */ - LL_APPEND(uavo_list, uavo_data); - /* Initialize object fields and metadata to default values */ if (initCb) initCb((UAVObjHandle) uavo_data, 0); @@ -374,8 +379,7 @@ UAVObjHandle UAVObjGetByID(uint32_t id) xSemaphoreTakeRecursive(mutex, portMAX_DELAY); // Look for object - struct UAVOData * tmp_obj; - LL_FOREACH(uavo_list, tmp_obj) { + UAVO_LIST_ITERATE(tmp_obj) if (tmp_obj->id == id) { found_obj = (UAVObjHandle *)tmp_obj; goto unlock_exit; @@ -1019,15 +1023,13 @@ int32_t UAVObjDelete(UAVObjHandle obj_handle, uint16_t instId) */ int32_t UAVObjSaveSettings() { - struct UAVOData *obj; - // Get lock xSemaphoreTakeRecursive(mutex, portMAX_DELAY); int32_t rc = -1; // Save all settings objects - LL_FOREACH(uavo_list, obj) { + UAVO_LIST_ITERATE(obj) // Check if this is a settings object if (UAVObjIsSettings(obj)) { // Save object @@ -1051,15 +1053,13 @@ unlock_exit: */ int32_t UAVObjLoadSettings() { - struct UAVOData *obj; - // Get lock xSemaphoreTakeRecursive(mutex, portMAX_DELAY); int32_t rc = -1; // Load all settings objects - LL_FOREACH(uavo_list, obj) { + UAVO_LIST_ITERATE(obj) // Check if this is a settings object if (UAVObjIsSettings(obj)) { // Load object @@ -1083,15 +1083,13 @@ unlock_exit: */ int32_t UAVObjDeleteSettings() { - struct UAVOData *obj; - // Get lock xSemaphoreTakeRecursive(mutex, portMAX_DELAY); int32_t rc = -1; // Save all settings objects - LL_FOREACH(uavo_list, obj) { + UAVO_LIST_ITERATE(obj) // Check if this is a settings object if (UAVObjIsSettings(obj)) { // Save object @@ -1115,15 +1113,13 @@ unlock_exit: */ int32_t UAVObjSaveMetaobjects() { - struct UAVOData *obj; - // Get lock xSemaphoreTakeRecursive(mutex, portMAX_DELAY); int32_t rc = -1; // Save all settings objects - LL_FOREACH(uavo_list, obj) { + UAVO_LIST_ITERATE(obj) // Save object if (UAVObjSave( (UAVObjHandle) MetaObjectPtr(obj), 0) == -1) { @@ -1144,15 +1140,13 @@ unlock_exit: */ int32_t UAVObjLoadMetaobjects() { - struct UAVOData *obj; - // Get lock xSemaphoreTakeRecursive(mutex, portMAX_DELAY); int32_t rc = -1; // Load all settings objects - LL_FOREACH(uavo_list, obj) { + UAVO_LIST_ITERATE(obj) // Load object if (UAVObjLoad((UAVObjHandle) MetaObjectPtr(obj), 0) == -1) { @@ -1173,15 +1167,13 @@ unlock_exit: */ int32_t UAVObjDeleteMetaobjects() { - struct UAVOData *obj; - // Get lock xSemaphoreTakeRecursive(mutex, portMAX_DELAY); int32_t rc = -1; // Load all settings objects - LL_FOREACH(uavo_list, obj) { + UAVO_LIST_ITERATE(obj) // Load object if (UAVObjDelete((UAVObjHandle) MetaObjectPtr(obj), 0) == -1) { @@ -1787,8 +1779,7 @@ void UAVObjIterate(void (*iterator) (UAVObjHandle obj)) xSemaphoreTakeRecursive(mutex, portMAX_DELAY); // Iterate through the list and invoke iterator for each object - struct UAVOData *obj; - LL_FOREACH(uavo_list, obj) { + UAVO_LIST_ITERATE(obj) (*iterator) ((UAVObjHandle) obj); (*iterator) ((UAVObjHandle) &obj->metaObj); } diff --git a/flight/UAVObjects/uavobjecttemplate.c b/flight/UAVObjects/uavobjecttemplate.c index f8db8a024..d2e0e8f34 100644 --- a/flight/UAVObjects/uavobjecttemplate.c +++ b/flight/UAVObjects/uavobjecttemplate.c @@ -40,7 +40,7 @@ #include "$(NAMELC).h" // Private variables -static UAVObjHandle handle = NULL; +static UAVObjHandle handle __attribute__((section("_uavo_handles"))); /** * Initialize object.