/* * Copyright (C) 2018 "IoT.bzh" * Author Jonathan Aillet * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #define _GNU_SOURCE #include #include #include #include "../4a-hal-utilities/4a-hal-utilities-data.h" #include "../4a-hal-utilities/4a-hal-utilities-verbs-loader.h" #include "../4a-hal-controllers/4a-hal-controllers-api-loader.h" #include "4a-hal-manager.h" #include "4a-hal-manager-cb.h" // Default api to print log when apihandle not available AFB_ApiT AFB_default; // Local (static) Hal manager data structure static struct HalMgrData localHalMgrGlobalData; /******************************************************************************* * HAL Manager verbs table * ******************************************************************************/ // Hal manager exported verbs AFB_ApiVerbs HalManagerApiStaticVerbs[] = { /* VERB'S NAME FUNCTION TO CALL SHORT DESCRIPTION */ { .verb = "ping", .callback = HalMgrPing, .info = "Ping test"}, { .verb = "loaded", .callback = HalMgrLoaded, .info = "Show loaded HAL"}, { .verb = "load", .callback = HalMgrLoad, .info = "Load an external HAL to HAL Manager"}, { .verb = "unload", .callback = HalMgrUnload, .info = "Unload an external HAL to HAL Manager"}, { .verb = "subscribe", .callback = HalMgrSubscribeEvent, .info = "Subscribe to an event"}, { .verb = "unsuscribe", .callback = HalMgrUnsubscribeEvent, .info = "Unsubscribe to an event"}, { .verb = NULL } // Marker for end of the array }; /******************************************************************************* * HAL Manager get first 'SpecificHalData' structure * from HAL list function * ******************************************************************************/ struct SpecificHalData **HalMngGetFirstHalData(void) { return &localHalMgrGlobalData.first; } /******************************************************************************* * Dynamic API functions for hal manager * * TBD JAI : Use API-V3 instead of API-PRE-V3 * ******************************************************************************/ static int HalMgrInitApi(AFB_ApiT apiHandle) { struct SpecificHalData *currentCtlHalData; struct HalMgrData *HalMgrGlobalData; if(! apiHandle) return -1; // Hugely hack to make all V2 AFB_DEBUG to work in fileutils AFB_default = apiHandle; // Retrieve section config from api handle HalMgrGlobalData = (struct HalMgrData *) AFB_ApiGetUserData(apiHandle); if(! HalMgrGlobalData) return -2; if(HalUtlInitializeHalMgrData(apiHandle, HalMgrGlobalData, HAL_MANAGER_API_NAME, HAL_MANAGER_API_INFO)) return -3; currentCtlHalData = HalMgrGlobalData->first; while(currentCtlHalData) { if(! currentCtlHalData->apiName) return -4; else if(AFB_RequireApi(apiHandle, currentCtlHalData->apiName, 1)) return -5; currentCtlHalData = currentCtlHalData->next; } return 0; } static int HalMgrLoadApi(void *cbdata, AFB_ApiT apiHandle) { struct HalMgrData *HalMgrGlobalData; if(! cbdata || ! apiHandle) return -1; HalMgrGlobalData = (struct HalMgrData *) cbdata; // Save closure as api's data context AFB_ApiSetUserData(apiHandle, HalMgrGlobalData); // Add static controls verbs if(HalUtlLoadVerbs(apiHandle, HalManagerApiStaticVerbs)) { AFB_ApiError(apiHandle, "Load section : fail to register static verbs"); return 1; } // Declare an event manager for Hal Manager AFB_ApiOnEvent(apiHandle, HalMgrDispatchApiEvent); // Init Api function (does not receive user closure ???) AFB_ApiOnInit(apiHandle, HalMgrInitApi); AFB_ApiSeal(apiHandle); return 0; } int HalMgrCreateApi(AFB_ApiT apiHandle, struct HalMgrData *HalMgrGlobalData) { if(! apiHandle || ! HalMgrGlobalData) return -1; // Create one API return AFB_NewApi(apiHandle, HAL_MANAGER_API_NAME, HAL_MANAGER_API_INFO, 1, HalMgrLoadApi, HalMgrGlobalData) ? 0 : -1; } /******************************************************************************* * Startup function * ******************************************************************************/ int afbBindingEntry(AFB_ApiT apiHandle) { int status = 0, rc; if(! apiHandle) return -1; // Hugely hack to make all V2 AFB_DEBUG to work in fileutils AFB_default = apiHandle; AFB_ApiNotice(apiHandle, "Binding start"); // Load Hal-Manager using Api v3 rc = HalMgrCreateApi(apiHandle, &localHalMgrGlobalData); if(rc < 0) status--; // Load Hal-Ctls using Api v3 rc = HalCtlsCreateAllApi(apiHandle, &localHalMgrGlobalData); if(rc < 0) status -= rc; return status; }