/* * 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 #include "4a-hal-utilities-data.h" #include "4a-hal-utilities-alsa-data.h" /******************************************************************************* * Specfic Hal controller streams data handling functions * ******************************************************************************/ struct CtlHalMixerData *HalUtlAddMixerDataToMixerDataList(struct CtlHalMixerData **firstMixerData) { struct CtlHalMixerData *currentMixerData; if(! firstMixerData) return NULL; currentMixerData = *firstMixerData; if(! currentMixerData) { currentMixerData = (struct CtlHalMixerData *) calloc(1, sizeof(struct CtlHalMixerData)); if(! currentMixerData) return NULL; *firstMixerData = currentMixerData; } else { while(currentMixerData->next) currentMixerData = currentMixerData->next; currentMixerData->next = calloc(1, sizeof(struct CtlHalMixerData)); if(! currentMixerData) return NULL; currentMixerData = currentMixerData->next; } return currentMixerData; } int8_t HalUtlRemoveSelectedMixerData(struct CtlHalMixerData **firstMixerData, struct CtlHalMixerData *mixerDataToRemove) { struct CtlHalMixerData *currentMixerData, *matchingMixerData; if(! firstMixerData || ! mixerDataToRemove) return -1; currentMixerData = *firstMixerData; if(currentMixerData == mixerDataToRemove) { *firstMixerData = currentMixerData->next; matchingMixerData = currentMixerData; } else { while(currentMixerData && currentMixerData->next != mixerDataToRemove) currentMixerData = currentMixerData->next; if(currentMixerData) { matchingMixerData = currentMixerData->next; currentMixerData->next = currentMixerData->next->next; } else { return -2; } } free(matchingMixerData->verb); free(matchingMixerData->verbToCall); free(matchingMixerData->streamCardId); free(matchingMixerData); return 0; } int64_t HalUtlRemoveAllMixerData(struct CtlHalMixerData **firstMixerData) { int8_t ret; int64_t mixerDataRemoved = 0; while(*firstMixerData) { ret = HalUtlRemoveSelectedMixerData(firstMixerData, *firstMixerData); if(ret) return (int64_t) ret; mixerDataRemoved++; } return mixerDataRemoved; } int64_t HalUtlGetNumberOfMixerDataInList(struct CtlHalMixerData **firstMixerData) { int64_t numberOfMixerData = 0; struct CtlHalMixerData *currentMixerData; if(! firstMixerData) return -1; currentMixerData = *firstMixerData; while(currentMixerData) { currentMixerData = currentMixerData->next; numberOfMixerData++; } return numberOfMixerData; } struct CtlHalMixerData *HalUtlSearchMixerDataByProperties(struct CtlHalMixerData **firstMixerData, char *verb, char *verbToCall, char *streamCardId) { struct CtlHalMixerData *currentMixerData; if(! firstMixerData || ! verb) return NULL; currentMixerData = *firstMixerData; while(currentMixerData) { if((! strcmp(verb, currentMixerData->verb)) && (! strcmp(verbToCall, currentMixerData->verbToCall)) && (! strcmp(streamCardId, currentMixerData->streamCardId))) return currentMixerData; currentMixerData = currentMixerData->next; } return NULL; } /******************************************************************************* * Specfic Hal data handling functions * ******************************************************************************/ struct SpecificHalData *HalUtlAddHalApiToHalList(struct SpecificHalData **firstHalData) { struct SpecificHalData *currentApi; if(! firstHalData) return NULL; currentApi = *firstHalData; if(! currentApi) { currentApi = (struct SpecificHalData *) calloc(1, sizeof(struct SpecificHalData)); if(! currentApi) return NULL; *firstHalData = currentApi; } else { while(currentApi->next) currentApi = currentApi->next; currentApi->next = calloc(1, sizeof(struct SpecificHalData)); if(! currentApi) return NULL; currentApi = currentApi->next; } return currentApi; } int8_t HalUtlRemoveSelectedHalFromList(struct SpecificHalData **firstHalData, struct SpecificHalData *apiToRemove) { struct SpecificHalData *currentApi, *matchingApi; if(! firstHalData || ! apiToRemove) return -1; currentApi = *firstHalData; if(currentApi == apiToRemove) { *firstHalData = currentApi->next; matchingApi = currentApi; } else { while(currentApi && currentApi->next != apiToRemove) currentApi = currentApi->next; if(currentApi) { matchingApi = currentApi->next; currentApi->next = currentApi->next->next; } else { return -2; } } free(matchingApi->apiName); free(matchingApi->sndCardPath); free(matchingApi->info); free(matchingApi->author); free(matchingApi->version); free(matchingApi->date); if(matchingApi->internal) { HalUtlRemoveAllMixerData(&matchingApi->ctlHalSpecificData->ctlHalStreamsData); HalUtlRemoveAllMixerData(&matchingApi->ctlHalSpecificData->ctlHalPlaybacksData); HalUtlRemoveAllMixerData(&matchingApi->ctlHalSpecificData->ctlHalCapturesData); HalUtlFreeAlsaCtlsMap(matchingApi->ctlHalSpecificData->ctlHalAlsaMapT); free(matchingApi->ctlHalSpecificData); } free(matchingApi); return 0; } int64_t HalUtlRemoveAllHalFromList(struct SpecificHalData **firstHalData) { int8_t ret; int64_t CtlHalApiRemoved = 0; while(*firstHalData) { ret = HalUtlRemoveSelectedHalFromList(firstHalData, *firstHalData); if(ret) return (int64_t) ret; CtlHalApiRemoved++; } return CtlHalApiRemoved; } int64_t HalUtlGetNumberOfHalInList(struct SpecificHalData **firstHalData) { int64_t numberOfCtlHal = 0; struct SpecificHalData *currentApi; if(! firstHalData) return -1; currentApi = *firstHalData; while(currentApi) { currentApi = currentApi->next; numberOfCtlHal++; } return numberOfCtlHal; } struct SpecificHalData *HalUtlSearchHalDataByApiName(struct SpecificHalData **firstHalData, char *apiName) { struct SpecificHalData *currentApi; if(! firstHalData || ! apiName) return NULL; currentApi = *firstHalData; while(currentApi) { if(! strcmp(apiName, currentApi->apiName)) return currentApi; currentApi = currentApi->next; } return NULL; } struct SpecificHalData *HalUtlSearchReadyHalDataByCarId(struct SpecificHalData **firstHalData, int cardId) { struct SpecificHalData *currentApi; if(! firstHalData) return NULL; currentApi = *firstHalData; while(currentApi) { if(currentApi->status == HAL_STATUS_READY && currentApi->sndCardId == cardId) return currentApi; currentApi = currentApi->next; } return NULL; } /******************************************************************************* * Hal Manager data handling functions * ******************************************************************************/ uint8_t HalUtlInitializeHalMgrData(afb_api_t apiHandle, struct HalMgrData *HalMgrGlobalData, char *apiName, char *info) { if(! apiHandle || ! HalMgrGlobalData || ! apiName || ! info) return -1; // Allocate and fill apiName and info strings HalMgrGlobalData->apiName = strdup(apiName); if(! HalMgrGlobalData->apiName) return -2; HalMgrGlobalData->info = strdup(info); if(! HalMgrGlobalData->apiName) return -3; HalMgrGlobalData->apiHandle = apiHandle; return 0; } void HalUtlRemoveHalMgrData(struct HalMgrData *HalMgrGlobalData) { if(! HalMgrGlobalData) return; if(HalMgrGlobalData->first) HalUtlRemoveAllHalFromList(&HalMgrGlobalData->first); free(HalMgrGlobalData->apiName); free(HalMgrGlobalData->info); free(HalMgrGlobalData); }