summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--lib/4a-hal-utilities/4a-hal-utilities-alsa-data.c117
-rw-r--r--lib/4a-hal-utilities/4a-hal-utilities-alsa-data.h19
-rw-r--r--lib/4a-hal-utilities/4a-hal-utilities-data.c133
-rw-r--r--lib/4a-hal-utilities/4a-hal-utilities-data.h15
-rw-r--r--lib/4a-hal-utilities/CMakeLists.txt1
-rw-r--r--src/4a-internals-hal/4a-internals-hal-api-loader.c1
-rw-r--r--src/4a-internals-hal/4a-internals-hal-cb.c253
-rw-r--r--src/4a-internals-hal/4a-internals-hal-cb.h2
8 files changed, 276 insertions, 265 deletions
diff --git a/lib/4a-hal-utilities/4a-hal-utilities-alsa-data.c b/lib/4a-hal-utilities/4a-hal-utilities-alsa-data.c
deleted file mode 100644
index 5d37c0a..0000000
--- a/lib/4a-hal-utilities/4a-hal-utilities-alsa-data.c
+++ /dev/null
@@ -1,117 +0,0 @@
-/*
- * Copyright (C) 2019 "IoT.bzh"
- * Author Jonathan Aillet <jonathan.aillet@iot.bzh>
- *
- * 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 <stdio.h>
-
-#include <wrap-json.h>
-
-#include <afb/afb-binding.h>
-
-#include "4a-hal-utilities-alsa-data.h"
-
-/*******************************************************************************
- * Internal Hal - ALSA controls data handling functions *
- ******************************************************************************/
-
-json_object *HalUtGetJsonArrayForSpecificControl(afb_api_t apiHandle, struct InternalHalAlsaMap *currentAlsaMapData)
-{
- int wrapRet;
-
- json_object *currentAlsaMapDataJ;
-
- if(! apiHandle) {
- AFB_API_ERROR(apiHandle, "Can't get current internal hal api handle");
- return NULL;
- }
-
- if(! currentAlsaMapData) {
- AFB_API_ERROR(apiHandle, "ALSA control data to use to generate json object are empty");
- return NULL;
- }
-
- wrapRet = wrap_json_pack(&currentAlsaMapDataJ,
- "{s:s s:s}",
- "name", currentAlsaMapData->uid,
- "info", currentAlsaMapData->info ? currentAlsaMapData->info : "none");
- if(wrapRet) {
- AFB_API_ERROR(apiHandle, "Didn't succeed to allocate current streams json object");
- return NULL;
- }
-
- return currentAlsaMapDataJ;
-}
-
-json_object *HalUtGetJsonArrayForAllControls(afb_api_t apiHandle, struct InternalHalAlsaMapT *currentAlsaMapDataT)
-{
- unsigned int idx;
-
- json_object *alsaMapDataArrayJ, *currentAlsaMapDataJ;
-
- if(! apiHandle) {
- AFB_API_ERROR(apiHandle, "Can't get current internal hal api handle");
- return NULL;
- }
-
- if(! currentAlsaMapDataT) {
- AFB_API_ERROR(apiHandle, "Can't get Alsa map data table to handle");
- return NULL;
- }
-
- alsaMapDataArrayJ = json_object_new_array();
- if(! alsaMapDataArrayJ) {
- AFB_API_ERROR(apiHandle, "Didn't succeed to allocate ALSA controls data json array");
- return NULL;
- }
-
- for(idx = 0; idx < currentAlsaMapDataT->ctlsCount; idx++) {
- currentAlsaMapDataJ = HalUtGetJsonArrayForSpecificControl(apiHandle, &currentAlsaMapDataT->ctls[idx]);
- if(! currentAlsaMapDataJ) {
- AFB_API_ERROR(apiHandle, "Didn't succeed to generate current ALSA control data json object");
- json_object_put(alsaMapDataArrayJ);
- return NULL;
- }
-
- json_object_array_add(alsaMapDataArrayJ, currentAlsaMapDataJ);
- }
-
- return alsaMapDataArrayJ;
-}
-
-int HalUtlFreeAlsaCtlsMap(struct InternalHalAlsaMapT *alsaCtlsMap)
-{
- int idx;
-
- if(! alsaCtlsMap)
- return -1;
-
- if(alsaCtlsMap->ctlsCount > 0 && ! alsaCtlsMap->ctls)
- return -2;
-
- for(idx = 0; idx < alsaCtlsMap->ctlsCount; idx++) {
- free(alsaCtlsMap->ctls[idx].action);
- free(alsaCtlsMap->ctls[idx].ctl.alsaCtlProperties.enums);
- free(alsaCtlsMap->ctls[idx].ctl.alsaCtlProperties.dbscale);
- }
-
- free(alsaCtlsMap->ctls);
-
- free(alsaCtlsMap);
-
- return 0;
-} \ No newline at end of file
diff --git a/lib/4a-hal-utilities/4a-hal-utilities-alsa-data.h b/lib/4a-hal-utilities/4a-hal-utilities-alsa-data.h
index 3a4c885..88b3e44 100644
--- a/lib/4a-hal-utilities/4a-hal-utilities-alsa-data.h
+++ b/lib/4a-hal-utilities/4a-hal-utilities-alsa-data.h
@@ -20,6 +20,8 @@
#include <stdio.h>
+#include <urcu/list.h>
+
#include <json-c/json.h>
#include <alsa/asoundlib.h>
@@ -50,27 +52,24 @@ struct InternalHalAlsaCtl {
char *name;
int numid;
int value;
+
struct InternalHalAlsaCtlProperties alsaCtlProperties;
struct InternalHalAlsaCtlProperties *alsaCtlCreation;
};
struct InternalHalAlsaMap {
- const char *uid;
+ char *uid;
char *info;
+
afb_event_t alsaControlEvent;
+
struct InternalHalAlsaCtl ctl;
+
json_object *actionJ;
+
CtlActionT *action;
-};
-struct InternalHalAlsaMapT {
- struct InternalHalAlsaMap *ctls;
- unsigned int ctlsCount;
+ struct cds_list_head node;
};
-// Internal Hal - ALSA controls data handling functions
-json_object *HalUtGetJsonArrayForSpecificControl(afb_api_t apiHandle, struct InternalHalAlsaMap *currentAlsaMapData);
-json_object *HalUtGetJsonArrayForAllControls(afb_api_t apiHandle, struct InternalHalAlsaMapT *currentAlsaMapDataT);
-int HalUtlFreeAlsaCtlsMap(struct InternalHalAlsaMapT *alsaCtlsMap);
-
#endif /* _HAL_UTILITIES_ALSA_DATA_INCLUDE_ */ \ No newline at end of file
diff --git a/lib/4a-hal-utilities/4a-hal-utilities-data.c b/lib/4a-hal-utilities/4a-hal-utilities-data.c
index 6121b33..d7ae1f6 100644
--- a/lib/4a-hal-utilities/4a-hal-utilities-data.c
+++ b/lib/4a-hal-utilities/4a-hal-utilities-data.c
@@ -33,6 +33,7 @@
void HalUtlFreeSelectedProbedDeviceAllocation(struct InternalHalProbedDevice *probedDeviceToFree);
void HalUtlFreeSelectedMixerDataAllocation(struct InternalHalMixerData *mixerDataToFree);
+void HalUtlFreeSelectedHalMapDataAllocation(struct InternalHalAlsaMap *halMapDataToFree);
void HalUtlFreeSelectedHalAllocation(struct HalData *halDataToFree);
/*******************************************************************************
@@ -62,6 +63,13 @@ void *HalUtlAddNodeInList(struct cds_list_head *listHead, enum LinkedListType li
nodeToAdd = &((struct InternalHalMixerData *) returned)->node;
break;
+ case LINKED_LIST_FOR_HALMAP_DATA:
+ returned = calloc(1, sizeof(struct InternalHalAlsaMap));
+ if(! returned)
+ return NULL;
+ nodeToAdd = &((struct InternalHalAlsaMap *) returned)->node;
+ break;
+
case LINKED_LIST_FOR_HAL_DATA:
returned = calloc(1, sizeof(struct HalData));
if(! returned)
@@ -96,6 +104,12 @@ int HalUtlRemoveNodeFromList(struct cds_list_head *listHead, void *dataToRemove,
HalUtlFreeSelectedMixerDataAllocation((struct InternalHalMixerData *) dataToRemove);
break;
+ case LINKED_LIST_FOR_HALMAP_DATA:
+ cds_list_del(&((struct InternalHalAlsaMap *) dataToRemove)->node);
+
+ HalUtlFreeSelectedHalMapDataAllocation((struct InternalHalAlsaMap *) dataToRemove);
+ break;
+
case LINKED_LIST_FOR_HAL_DATA:
cds_list_del(&((struct HalData *) dataToRemove)->node);
@@ -135,14 +149,20 @@ int HalUtlRemoveAllNodeFromList(struct cds_list_head *listHead, enum LinkedListT
return -3;
break;
+ case LINKED_LIST_FOR_HALMAP_DATA:
+ if(HalUtlRemoveSelectedHalMapData(listHead,
+ cds_list_entry(nodeToRemove, struct InternalHalAlsaMap, node)))
+ return -4;
+ break;
+
case LINKED_LIST_FOR_HAL_DATA:
if(HalUtlRemoveSelectedHalFromList(listHead,
cds_list_entry(nodeToRemove, struct HalData, node)))
- return -4;
+ return -5;
break;
default:
- return -5;
+ return -6;
}
nodesRemoved++;
@@ -820,6 +840,11 @@ json_object *HalUtlGetJsonArrayForAllMixersData(afb_api_t apiHandle, struct cds_
return NULL;
}
+ if(cds_list_empty(mixerDataListHead)) {
+ AFB_API_ERROR(apiHandle, "Mixer data list is empty");
+ return NULL;
+ }
+
mixerDataArrayJ = json_object_new_array();
if(! mixerDataArrayJ) {
AFB_API_ERROR(apiHandle, "Didn't succeed to allocate requested mixer data json array");
@@ -841,6 +866,108 @@ json_object *HalUtlGetJsonArrayForAllMixersData(afb_api_t apiHandle, struct cds_
}
/*******************************************************************************
+ * Internal Hal - Alsa Map data handling functions *
+ ******************************************************************************/
+
+void HalUtlFreeSelectedHalMapDataAllocation(struct InternalHalAlsaMap *halMapDataToFree)
+{
+ free(halMapDataToFree->uid);
+ free(halMapDataToFree->info);
+
+ free(halMapDataToFree->action);
+
+ free(halMapDataToFree->ctl.name);
+
+ free(halMapDataToFree);
+}
+
+struct InternalHalAlsaMap *HalUtlAddHalMapDataToHalMapDataList(struct cds_list_head *halMapListHead)
+{
+ return (struct InternalHalAlsaMap *) HalUtlAddNodeInList(halMapListHead, LINKED_LIST_FOR_HALMAP_DATA);
+}
+
+int HalUtlRemoveSelectedHalMapData(struct cds_list_head *halMapListHead,
+ struct InternalHalAlsaMap *halMapDataToRemove)
+{
+ return HalUtlRemoveNodeFromList(halMapListHead, (void *) halMapDataToRemove, LINKED_LIST_FOR_HALMAP_DATA);
+}
+
+int HalUtlRemoveAllHalMapData(struct cds_list_head *halMapListHead)
+{
+ return HalUtlRemoveAllNodeFromList(halMapListHead, LINKED_LIST_FOR_HALMAP_DATA);
+}
+
+int HalUtlGetNumberOfHalMapDataInList(struct cds_list_head *halMapListHead)
+{
+ return HalUtlGetNumberOfNodesInList(halMapListHead);
+}
+
+json_object *HalUtGetJsonArrayForSpecificHalMapControl(afb_api_t apiHandle,
+ struct InternalHalAlsaMap *currentHalMapData)
+{
+ int wrapRet;
+
+ json_object *currentAlsaMapDataJ;
+
+ if(! apiHandle) {
+ AFB_API_ERROR(apiHandle, "Can't get current internal hal api handle");
+ return NULL;
+ }
+
+ if(! currentHalMapData) {
+ AFB_API_ERROR(apiHandle, "ALSA control data to use to generate json object are empty");
+ return NULL;
+ }
+
+ wrapRet = wrap_json_pack(&currentAlsaMapDataJ,
+ "{s:s s:s}",
+ "name", currentHalMapData->uid,
+ "info", currentHalMapData->info ? currentHalMapData->info : "none");
+ if(wrapRet) {
+ AFB_API_ERROR(apiHandle, "Didn't succeed to allocate current streams json object");
+ return NULL;
+ }
+
+ return currentAlsaMapDataJ;
+}
+
+json_object *HalUtGetJsonArrayForAllHalMapControls(afb_api_t apiHandle, struct cds_list_head *halMapListHead)
+{
+ struct InternalHalAlsaMap *currentHalMapData;
+
+ json_object *halMapDataArrayJ, *currentHalMapDataJ;
+
+ if(! apiHandle) {
+ AFB_API_ERROR(apiHandle, "Can't get current internal hal api handle");
+ return NULL;
+ }
+
+ if(! halMapListHead || cds_list_empty(halMapListHead)) {
+ AFB_API_ERROR(apiHandle, "HalMap data list is empty");
+ return NULL;
+ }
+
+ halMapDataArrayJ = json_object_new_array();
+ if(! halMapDataArrayJ) {
+ AFB_API_ERROR(apiHandle, "Didn't succeed to allocate ALSA controls data json array");
+ return NULL;
+ }
+
+ cds_list_for_each_entry(currentHalMapData, halMapListHead, node) {
+ currentHalMapDataJ = HalUtGetJsonArrayForSpecificHalMapControl(apiHandle, currentHalMapData);
+ if(! currentHalMapDataJ) {
+ AFB_API_ERROR(apiHandle, "Didn't succeed to generate current HalMap data json object");
+ json_object_put(halMapDataArrayJ);
+ return NULL;
+ }
+
+ json_object_array_add(halMapDataArrayJ, currentHalMapDataJ);
+ }
+
+ return halMapDataArrayJ;
+}
+
+/*******************************************************************************
* Hal data handling functions *
******************************************************************************/
@@ -857,7 +984,7 @@ void HalUtlFreeSelectedHalAllocation(struct HalData *halDataToFree)
HalUtlRemoveAllMixerData(&halDataToFree->internalHalData->streamsDataListHead);
- HalUtlFreeAlsaCtlsMap(halDataToFree->internalHalData->alsaMapT);
+ HalUtlRemoveAllHalMapData(&halDataToFree->internalHalData->halMapListHead);
free(halDataToFree->internalHalData);
}
diff --git a/lib/4a-hal-utilities/4a-hal-utilities-data.h b/lib/4a-hal-utilities/4a-hal-utilities-data.h
index 1571485..1ecfe00 100644
--- a/lib/4a-hal-utilities/4a-hal-utilities-data.h
+++ b/lib/4a-hal-utilities/4a-hal-utilities-data.h
@@ -38,7 +38,8 @@
enum LinkedListType {
LINKED_LIST_FOR_DEPENDENCIES_DATA = 0,
LINKED_LIST_FOR_MIXER_DATA = 1,
- LINKED_LIST_FOR_HAL_DATA = 2
+ LINKED_LIST_FOR_HALMAP_DATA = 2,
+ LINKED_LIST_FOR_HAL_DATA = 3
};
// Enum for hal status
@@ -116,7 +117,7 @@ struct InternalHalData {
struct cds_list_head streamsDataListHead;
afb_event_t streamUpdates;
- struct InternalHalAlsaMapT *alsaMapT;
+ struct cds_list_head halMapListHead;
afb_api_t apiHandle;
CtlConfigT *ctrlConfig;
@@ -191,6 +192,16 @@ struct InternalHalMixerData *HalUtlSearchMixerDataByProperties(struct cds_list_h
json_object *HalUtlGetJsonArrayForSpecificMixerData(afb_api_t apiHandle, struct InternalHalMixerData *mixerData);
json_object *HalUtlGetJsonArrayForAllMixersData(afb_api_t apiHandle, struct cds_list_head *mixerDataListHead);
+// Internal Hal - Alsa Map data handling functions
+struct InternalHalAlsaMap *HalUtlAddHalMapDataToHalMapDataList(struct cds_list_head *halMapListHead);
+int HalUtlRemoveSelectedHalMapData(struct cds_list_head *halMapListHead,
+ struct InternalHalAlsaMap *halMapDataToRemove);
+int HalUtlRemoveAllHalMapData(struct cds_list_head *halMapListHead);
+int HalUtlGetNumberOfHalMapDataInList(struct cds_list_head *halMapListHead);
+json_object *HalUtGetJsonArrayForSpecificHalMapControl(afb_api_t apiHandle,
+ struct InternalHalAlsaMap *currentHalMapData);
+json_object *HalUtGetJsonArrayForAllHalMapControls(afb_api_t apiHandle, struct cds_list_head *halMapListHead);
+
// Hal data handling functions
struct HalData *HalUtlAddHalToHalList(struct cds_list_head *halDataListHead);
int HalUtlRemoveSelectedHalFromList(struct cds_list_head *halDataListHead, struct HalData *halToRemove);
diff --git a/lib/4a-hal-utilities/CMakeLists.txt b/lib/4a-hal-utilities/CMakeLists.txt
index 8eb2c62..9689565 100644
--- a/lib/4a-hal-utilities/CMakeLists.txt
+++ b/lib/4a-hal-utilities/CMakeLists.txt
@@ -22,7 +22,6 @@ PROJECT_TARGET_ADD(4a-hal-utilities)
# Define project Targets
ADD_LIBRARY(${TARGET_NAME} STATIC
- 4a-hal-utilities-alsa-data.c
4a-hal-utilities-data.c
4a-hal-utilities-hal-streams-handler.c)
diff --git a/src/4a-internals-hal/4a-internals-hal-api-loader.c b/src/4a-internals-hal/4a-internals-hal-api-loader.c
index 6f09d4a..4fffe01 100644
--- a/src/4a-internals-hal/4a-internals-hal-api-loader.c
+++ b/src/4a-internals-hal/4a-internals-hal-api-loader.c
@@ -213,6 +213,7 @@ int InternalHalCreateApi(afb_api_t apiHandle, char *path, struct HalMgrData *hal
CDS_INIT_LIST_HEAD(&currentHalData->internalHalData->probedDevicesListHead);
CDS_INIT_LIST_HEAD(&currentHalData->internalHalData->streamsDataListHead);
+ CDS_INIT_LIST_HEAD(&currentHalData->internalHalData->halMapListHead);
// Create one API
if(! afb_api_new_api(apiHandle, ctrlConfig->api, ctrlConfig->info, 1, InternalHalLoadOneApi, ctrlConfig)) {
diff --git a/src/4a-internals-hal/4a-internals-hal-cb.c b/src/4a-internals-hal/4a-internals-hal-cb.c
index 1749131..0050f11 100644
--- a/src/4a-internals-hal/4a-internals-hal-cb.c
+++ b/src/4a-internals-hal/4a-internals-hal-cb.c
@@ -43,7 +43,7 @@ void InternalHalDispatchApiEvent(afb_api_t apiHandle, const char *evtLabel, json
CtlSourceT source;
struct HalData *currentHalData;
- struct InternalHalAlsaMapT *currentHalAlsaCtlsT;
+ struct InternalHalAlsaMap *currentHalMapControl;
json_object *valuesJ, *normalizedValuesJ;
@@ -66,8 +66,7 @@ void InternalHalDispatchApiEvent(afb_api_t apiHandle, const char *evtLabel, json
idx++;
if(evtLabel[idx] != '\0' &&
- (sscanf(&evtLabel[idx + 1], "%d", &cardidx) == 1) &&
- currentHalData->sndCardId == cardidx) {
+ (sscanf(&evtLabel[idx + 1], "%d", &cardidx) == 1)) {
if(wrap_json_unpack(eventJ, "{s:i s:o !}", "id", &numid, "val", &valuesJ)) {
AFB_API_ERROR(apiHandle,
"Invalid alsacore event received label=%s value=%s",
@@ -76,26 +75,31 @@ void InternalHalDispatchApiEvent(afb_api_t apiHandle, const char *evtLabel, json
return;
}
- if(! currentHalData->internalHalData->alsaMapT ||
- currentHalData->internalHalData->alsaMapT->ctlsCount <= 0 ||
- ! currentHalData->internalHalData->alsaMapT->ctls) {
- AFB_API_ERROR(apiHandle, "No halmap data is available, cannot handle alsacore event");
+ if(currentHalData->sndCardId != cardidx) {
+ AFB_API_NOTICE(apiHandle,
+ "The received alsacore event does not concern "
+ "current hal soundcard %i (it was about card %i)",
+ currentHalData->sndCardId,
+ cardidx);
return;
}
- currentHalAlsaCtlsT = currentHalData->internalHalData->alsaMapT;
+ if(cds_list_empty(&currentHalData->internalHalData->halMapListHead)) {
+ AFB_API_ERROR(apiHandle, "No halmap data is available, cannot handle alsacore event");
+ return;
+ }
// Search for corresponding numid in ALSA controls list, if found, launch callback (if available)
- for(idx = 0; idx < currentHalAlsaCtlsT->ctlsCount; idx++) {
- if(currentHalAlsaCtlsT->ctls[idx].ctl.numid == numid) {
- if(currentHalAlsaCtlsT->ctls[idx].action) {
+ cds_list_for_each_entry(currentHalMapControl, &currentHalData->internalHalData->halMapListHead, node) {
+ if(currentHalMapControl->ctl.numid == numid) {
+ if(currentHalMapControl->action) {
memset(&source, 0, sizeof(CtlSourceT));
- source.uid = currentHalAlsaCtlsT->ctls[idx].action->uid;
- source.api = currentHalAlsaCtlsT->ctls[idx].action->api;
+ source.uid = currentHalMapControl->action->uid;
+ source.api = currentHalMapControl->action->api;
- (void) ActionExecOne(&source, currentHalAlsaCtlsT->ctls[idx].action, valuesJ);
+ (void) ActionExecOne(&source, currentHalMapControl->action, valuesJ);
}
- else if(currentHalAlsaCtlsT->ctls[idx].actionJ) {
+ else if(currentHalMapControl->actionJ) {
AFB_API_WARNING(apiHandle,
"The alsa control id '%i' is corresponding to a known control which "
"has a registered action, but action is not ready to be executed",
@@ -109,17 +113,17 @@ void InternalHalDispatchApiEvent(afb_api_t apiHandle, const char *evtLabel, json
numid);
}
- if(! currentHalAlsaCtlsT->ctls[idx].alsaControlEvent ||
+ if(! currentHalMapControl->alsaControlEvent ||
InternalHalConvertJsonValues(apiHandle,
- &currentHalAlsaCtlsT->ctls[idx].ctl.alsaCtlProperties,
+ &currentHalMapControl->ctl.alsaCtlProperties,
valuesJ,
&normalizedValuesJ,
CONVERSION_ALSACORE_TO_NORMALIZED) ||
- (afb_event_push(currentHalAlsaCtlsT->ctls[idx].alsaControlEvent, normalizedValuesJ) < 0)) {
+ (afb_event_push(currentHalMapControl->alsaControlEvent, normalizedValuesJ) < 0)) {
AFB_API_ERROR(apiHandle,
"Couldn't generate an event for known halmap %s (alsa control id %i)",
- currentHalAlsaCtlsT->ctls[idx].uid,
- currentHalAlsaCtlsT->ctls[idx].ctl.numid);
+ currentHalMapControl->uid,
+ currentHalMapControl->ctl.numid);
}
return;
@@ -202,32 +206,32 @@ int InternalHalHalMixerConfig(afb_api_t apiHandle, CtlSectionT *section, json_ob
* Internals HAL - 'halmap' section parsing/handling functions *
******************************************************************************/
-int InternalHalProcessOneHalMapObject(afb_api_t apiHandle, struct InternalHalAlsaMap *alsaMap, json_object *AlsaMapJ)
+int InternalHalProcessOneHalMapObject(afb_api_t apiHandle, struct InternalHalAlsaMap *halMapData, json_object *halMapJ)
{
char *uid, *info = NULL, *action = NULL, *name = NULL, *typename = NULL;
json_object *alsaJ = NULL, *createAlsaCtlJ = NULL;
- AFB_API_DEBUG(apiHandle, "AlsaMapJ=%s", json_object_get_string(AlsaMapJ));
+ AFB_API_DEBUG(apiHandle, "halMapJ=%s", json_object_get_string(halMapJ));
- if(wrap_json_unpack(AlsaMapJ, "{s:s s?:s s:o s?:s !}",
+ if(wrap_json_unpack(halMapJ, "{s:s s?:s s:o s?:s !}",
"uid", &uid,
"info", &info,
"alsa", &alsaJ,
"action", &action)) {
- AFB_API_ERROR(apiHandle, "Parsing error, map should only contains [label]|[uid]|[tag]|[info]|[alsa]|[action] in : '%s'", json_object_get_string(AlsaMapJ));
+ AFB_API_ERROR(apiHandle, "Parsing error, map should only contains [label]|[uid]|[tag]|[info]|[alsa]|[action] in : '%s'", json_object_get_string(halMapJ));
return -1;
}
- alsaMap->uid = strdup(uid);
- if(! alsaMap->uid) {
+ halMapData->uid = strdup(uid);
+ if(! halMapData->uid) {
AFB_API_ERROR(apiHandle, "Didn't succeed to store (allocate) control 'uid' string");
return -2;
}
if(info) {
- alsaMap->info = strdup(info);
- if(! alsaMap->info) {
+ halMapData->info = strdup(info);
+ if(! halMapData->info) {
AFB_API_ERROR(apiHandle, "Didn't succeed to store (allocate) control 'info' string");
return -3;
}
@@ -235,38 +239,38 @@ int InternalHalProcessOneHalMapObject(afb_api_t apiHandle, struct InternalHalAls
if(wrap_json_unpack(alsaJ, "{s?:s s?:i s?:i s?:o !}",
"name", &name,
- "numid", &alsaMap->ctl.numid,
- "value", &alsaMap->ctl.value,
+ "numid", &halMapData->ctl.numid,
+ "value", &halMapData->ctl.value,
"create", &createAlsaCtlJ)) {
AFB_API_ERROR(apiHandle, "Parsing error, alsa json should only contains [name]|[numid]||[value]|[create] in : '%s'", json_object_get_string(alsaJ));
return -4;
}
if(name) {
- alsaMap->ctl.name = strdup(name);
- if(! alsaMap->ctl.name) {
+ halMapData->ctl.name = strdup(name);
+ if(! halMapData->ctl.name) {
AFB_API_ERROR(apiHandle, "Didn't succeed to store (allocate) control 'info' string");
return -5;
}
}
if(createAlsaCtlJ) {
- alsaMap->ctl.alsaCtlCreation = &alsaMap->ctl.alsaCtlProperties;
+ halMapData->ctl.alsaCtlCreation = &halMapData->ctl.alsaCtlProperties;
if(wrap_json_unpack(createAlsaCtlJ,
"{s:s s:i s:i s:i s:i !}",
"type", &typename,
- "count", &alsaMap->ctl.alsaCtlCreation->count,
- "minval", &alsaMap->ctl.alsaCtlCreation->minval,
- "maxval", &alsaMap->ctl.alsaCtlCreation->maxval,
- "step", &alsaMap->ctl.alsaCtlCreation->step)) {
+ "count", &halMapData->ctl.alsaCtlCreation->count,
+ "minval", &halMapData->ctl.alsaCtlCreation->minval,
+ "maxval", &halMapData->ctl.alsaCtlCreation->maxval,
+ "step", &halMapData->ctl.alsaCtlCreation->step)) {
AFB_API_ERROR(apiHandle, "Parsing error, alsa creation json should only contains [type]|[count]|[minval]|[maxval]|[step] in : '%s'", json_object_get_string(alsaJ));
return -6;
}
if(typename) {
- alsaMap->ctl.alsaCtlCreation->type = InternalHalMapsAlsaTypeToEnum(typename);
- if(alsaMap->ctl.alsaCtlCreation->type == SND_CTL_ELEM_TYPE_NONE) {
+ halMapData->ctl.alsaCtlCreation->type = InternalHalMapsAlsaTypeToEnum(typename);
+ if(halMapData->ctl.alsaCtlCreation->type == SND_CTL_ELEM_TYPE_NONE) {
AFB_API_ERROR(apiHandle,
"Couldn't get alsa type from string %s in : '%s'",
typename,
@@ -275,18 +279,18 @@ int InternalHalProcessOneHalMapObject(afb_api_t apiHandle, struct InternalHalAls
}
}
- if(! alsaMap->ctl.name)
- alsaMap->ctl.name = (char *) alsaMap->uid;
+ if(! halMapData->ctl.name)
+ halMapData->ctl.name = (char *) halMapData->uid;
}
- else if(alsaMap->ctl.name && alsaMap->ctl.numid > 0) {
+ else if(halMapData->ctl.name && halMapData->ctl.numid > 0) {
AFB_API_ERROR(apiHandle,
"Can't have both a control name (%s) and a control uid (%i) in alsa object : '%s'",
- alsaMap->ctl.name,
- alsaMap->ctl.numid,
+ halMapData->ctl.name,
+ halMapData->ctl.numid,
json_object_get_string(alsaJ));
return -8;
}
- else if(! alsaMap->ctl.name && alsaMap->ctl.numid <= 0) {
+ else if(! halMapData->ctl.name && halMapData->ctl.numid <= 0) {
AFB_API_ERROR(apiHandle,
"Need at least a control name or a control uid in alsa object : '%s'",
json_object_get_string(alsaJ));
@@ -294,62 +298,57 @@ int InternalHalProcessOneHalMapObject(afb_api_t apiHandle, struct InternalHalAls
}
if(action)
- alsaMap->actionJ = json_object_get(AlsaMapJ);
+ halMapData->actionJ = json_object_get(halMapJ);
return 0;
}
-int InternalHalProcessAllHalMap(afb_api_t apiHandle, json_object *AlsaMapJ, struct InternalHalAlsaMapT *currentInternalHalAlsaMapT)
+int InternalHalProcessAllHalMap(afb_api_t apiHandle, json_object *halMapJ, struct cds_list_head *halMapListHead)
{
- int idx, err = 0;
+ int idx, count, err = 0, halMapJsonIsAnArray = 0;
- struct InternalHalAlsaMap *ctlMaps;
+ struct InternalHalAlsaMap *currentHalMapData;
- json_object *currentAlsaMapJ;
+ json_object *currentHalMapJ;
json_type alsaMapType;
- alsaMapType = json_object_get_type(AlsaMapJ);
+ alsaMapType = json_object_get_type(halMapJ);
switch(alsaMapType) {
case json_type_array:
- currentInternalHalAlsaMapT->ctlsCount = (unsigned int) json_object_array_length(AlsaMapJ);
+ count = (int) json_object_array_length(halMapJ);
+ halMapJsonIsAnArray = 1;
break;
case json_type_object:
- currentInternalHalAlsaMapT->ctlsCount = 1;
+ count = 1;
break;
default:
- currentInternalHalAlsaMapT->ctlsCount = 0;
- currentInternalHalAlsaMapT->ctls = NULL;
- AFB_API_ERROR(apiHandle, "Content of 'halmap' section is not valid ('%s')", json_object_get_string(AlsaMapJ));
+ AFB_API_ERROR(apiHandle, "Content of 'halmap' section is not valid ('%s')", json_object_get_string(halMapJ));
return -1;
}
- ctlMaps = calloc(currentInternalHalAlsaMapT->ctlsCount, sizeof(struct InternalHalAlsaMap));
- if(! ctlMaps) {
- AFB_API_ERROR(apiHandle, "Didn't succeed to allocate halmap data table");
- return -2;
- }
+ for(idx = 0; idx < count; idx++) {
+ currentHalMapJ = halMapJsonIsAnArray ? json_object_array_get_idx(halMapJ, idx) : halMapJ;
+
+ currentHalMapData = HalUtlAddHalMapDataToHalMapDataList(halMapListHead);
- for(idx = 0; idx < currentInternalHalAlsaMapT->ctlsCount; idx++) {
- currentAlsaMapJ = (alsaMapType == json_type_array) ? json_object_array_get_idx(AlsaMapJ, idx) : AlsaMapJ;
- err = InternalHalProcessOneHalMapObject(apiHandle, &ctlMaps[idx], currentAlsaMapJ);
+ err = InternalHalProcessOneHalMapObject(apiHandle, currentHalMapData, currentHalMapJ);
if(err) {
AFB_API_ERROR(apiHandle,
- "Didn't succeed to proccess halmap object %i ('%s')",
+ "Error %i was returned when tried to proccess halmap object %i ('%s')",
+ err,
idx,
- json_object_get_string(currentAlsaMapJ));
- HalUtlFreeAlsaCtlsMap(currentInternalHalAlsaMapT);
- return -3;
+ json_object_get_string(currentHalMapJ));
+ HalUtlRemoveAllHalMapData(halMapListHead);
+ return -2;
}
}
- currentInternalHalAlsaMapT->ctls = ctlMaps;
-
- return err;
+ return 0;
}
-int InternalHalHandleOneHalMapObject(afb_api_t apiHandle, char *cardId, struct InternalHalAlsaMap *alsaMap)
+int InternalHalHandleOneHalMapObject(afb_api_t apiHandle, char *cardId, struct InternalHalAlsaMap *halMapData)
{
int err;
@@ -357,26 +356,26 @@ int InternalHalHandleOneHalMapObject(afb_api_t apiHandle, char *cardId, struct I
CtlActionT *toLoadAction;
- alsaMap->alsaControlEvent = afb_api_make_event(apiHandle, alsaMap->uid);
- if(! alsaMap->alsaControlEvent) {
+ halMapData->alsaControlEvent = afb_api_make_event(apiHandle, halMapData->uid);
+ if(! halMapData->alsaControlEvent) {
AFB_API_ERROR(apiHandle,
"Didn't succeed to create event for current alsa control to load action using alsa object : '%s'",
- json_object_get_string(alsaMap->actionJ));
+ json_object_get_string(halMapData->actionJ));
return -1;
}
- if(alsaMap->ctl.alsaCtlCreation) {
- if(InternalHalCreateAlsaCtl(apiHandle, cardId, &alsaMap->ctl)) {
+ if(halMapData->ctl.alsaCtlCreation) {
+ if(InternalHalCreateAlsaCtl(apiHandle, cardId, &halMapData->ctl)) {
AFB_API_ERROR(apiHandle, "An error happened when trying to create a new alsa control");
return -2;
}
}
- else if(InternalHalUpdateAlsaCtlProperties(apiHandle, cardId, &alsaMap->ctl)) {
+ else if(InternalHalUpdateAlsaCtlProperties(apiHandle, cardId, &halMapData->ctl)) {
AFB_API_ERROR(apiHandle, "An error happened when trying to get existing alsa control info");
return -3;
}
- if(alsaMap->actionJ) {
+ if(halMapData->actionJ) {
toLoadAction = calloc(1, sizeof(CtlActionT));
if(! toLoadAction) {
AFB_API_ERROR(apiHandle,
@@ -385,15 +384,15 @@ int InternalHalHandleOneHalMapObject(afb_api_t apiHandle, char *cardId, struct I
return -4;
}
- if(ActionLoadOne(apiHandle, toLoadAction, alsaMap->actionJ, 0)) {
+ if(ActionLoadOne(apiHandle, toLoadAction, halMapData->actionJ, 0)) {
AFB_API_ERROR(apiHandle,
"Didn't succeed to load action using alsa object : '%s'",
- json_object_get_string(alsaMap->actionJ));
+ json_object_get_string(halMapData->actionJ));
free(toLoadAction);
return -5;
}
- alsaMap->action = toLoadAction;
+ halMapData->action = toLoadAction;
}
if(InternalHalSubscribeToAlsaCardEvent(apiHandle, cardId)) {
@@ -401,9 +400,9 @@ int InternalHalHandleOneHalMapObject(afb_api_t apiHandle, char *cardId, struct I
return -6;
}
- if(alsaMap->ctl.value) {
+ if(halMapData->ctl.value) {
// TBD JAI : handle alsa controls type
- valueJ = json_object_new_int(alsaMap->ctl.value);
+ valueJ = json_object_new_int(halMapData->ctl.value);
if(! valueJ) {
AFB_API_ERROR(apiHandle, "Didn't succeed to allocate ALSA control value json string");
return -7;
@@ -411,14 +410,14 @@ int InternalHalHandleOneHalMapObject(afb_api_t apiHandle, char *cardId, struct I
err = 0;
- if(InternalHalConvertJsonValues(apiHandle, &alsaMap->ctl.alsaCtlProperties, valueJ, &convertedValueJ, CONVERSION_NORMALIZED_TO_ALSACORE)) {
+ if(InternalHalConvertJsonValues(apiHandle, &halMapData->ctl.alsaCtlProperties, valueJ, &convertedValueJ, CONVERSION_NORMALIZED_TO_ALSACORE)) {
AFB_API_ERROR(apiHandle, "Error when trying to convert initiate value json '%s'", json_object_get_string(valueJ));
err = -8;
}
- else if(InternalHalSetAlsaCtlValue(apiHandle, cardId, alsaMap->ctl.numid, convertedValueJ)) {
+ else if(InternalHalSetAlsaCtlValue(apiHandle, cardId, halMapData->ctl.numid, convertedValueJ)) {
AFB_API_ERROR(apiHandle,
"Error while trying to set initial value on alsa control %i, device '%s', value '%s'",
- alsaMap->ctl.numid,
+ halMapData->ctl.numid,
cardId,
json_object_get_string(valueJ));
err = -9;
@@ -433,36 +432,43 @@ int InternalHalHandleOneHalMapObject(afb_api_t apiHandle, char *cardId, struct I
return err;
}
- if(afb_api_add_verb(apiHandle, alsaMap->uid, alsaMap->info, InternalHalActionOnAlsaCtl, (void *) alsaMap, NULL, 0, 0)) {
+ if(afb_api_add_verb(apiHandle, halMapData->uid, halMapData->info, InternalHalActionOnAlsaCtl, (void *) halMapData, NULL, 0, 0)) {
AFB_API_ERROR(apiHandle,
"Didn't succeed to create verb for current alsa control : '%s'",
- json_object_get_string(alsaMap->actionJ));
+ json_object_get_string(halMapData->actionJ));
return -10;
}
return 0;
}
-int InternalHalHandleAllHalMap(afb_api_t apiHandle, int sndCardId, struct InternalHalAlsaMapT *currentInternalHalAlsaMapT)
+int InternalHalHandleAllHalMap(afb_api_t apiHandle, int sndCardId, struct cds_list_head *halMapListHead)
{
- int idx, err = 0;
+ int err = 0;
char cardIdString[6];
+ struct InternalHalAlsaMap *currentHalMapData;
+
snprintf(cardIdString, 6, "hw:%i", sndCardId);
- for(idx = 0; idx < currentInternalHalAlsaMapT->ctlsCount; idx++) {
- err = InternalHalHandleOneHalMapObject(apiHandle, cardIdString, &currentInternalHalAlsaMapT->ctls[idx]);
+ if(cds_list_empty(halMapListHead)) {
+ AFB_API_ERROR(apiHandle, "HalMap list is empty, nothing to handle");
+ return 0;
+ }
+
+ cds_list_for_each_entry(currentHalMapData, halMapListHead, node) {
+ err = InternalHalHandleOneHalMapObject(apiHandle, cardIdString, currentHalMapData);
if(err) {
AFB_API_ERROR(apiHandle,
- "Didn't succeed to handle halmap object %i ('%s')",
- idx,
- json_object_get_string(currentInternalHalAlsaMapT->ctls[idx].actionJ));
- return -3;
+ "Error %i was returned when tried to handle halmap object :' %s'",
+ err,
+ json_object_get_string(currentHalMapData->actionJ));
+ return -1;
}
}
- return err;
+ return 0;
}
int InternalHalHalMapConfig(afb_api_t apiHandle, CtlSectionT *section, json_object *AlsaMapJ)
@@ -479,15 +485,9 @@ int InternalHalHalMapConfig(afb_api_t apiHandle, CtlSectionT *section, json_obje
return -2;
if(AlsaMapJ) {
- currentHalData->internalHalData->alsaMapT = calloc(1, sizeof(struct InternalHalAlsaMapT));
- if(! currentHalData->internalHalData->alsaMapT) {
- AFB_API_ERROR(apiHandle, "Didn't succeed to allocate data structure used to store halmap data table");
- return -3;
- }
-
- if(InternalHalProcessAllHalMap(apiHandle, AlsaMapJ, currentHalData->internalHalData->alsaMapT)) {
+ if(InternalHalProcessAllHalMap(apiHandle, AlsaMapJ, &currentHalData->internalHalData->halMapListHead)) {
AFB_API_ERROR(apiHandle, "Failed to process 'halmap' section");
- HalUtlFreeAlsaCtlsMap(currentHalData->internalHalData->alsaMapT);
+ HalUtlRemoveAllHalMapData(&currentHalData->internalHalData->halMapListHead);
return -4;
}
}
@@ -499,15 +499,11 @@ int InternalHalHalMapConfig(afb_api_t apiHandle, CtlSectionT *section, json_obje
AFB_API_ERROR(apiHandle, "Hal alsa card id is not valid, 'halmap' section data can't be handle");
return -5;
}
- else if(! currentHalData->internalHalData->alsaMapT) {
- AFB_API_WARNING(apiHandle, "'halmap' section data is empty");
- return 2;
- }
- else if(! (currentHalData->internalHalData->alsaMapT->ctlsCount > 0)) {
+ else if(cds_list_empty(&currentHalData->internalHalData->halMapListHead)) {
AFB_API_WARNING(apiHandle, "No alsa controls defined in 'halmap' section");
- return 3;
+ return 2;
}
- else if(InternalHalHandleAllHalMap(apiHandle, currentHalData->sndCardId, currentHalData->internalHalData->alsaMapT)) {
+ else if(InternalHalHandleAllHalMap(apiHandle, currentHalData->sndCardId, &currentHalData->internalHalData->halMapListHead)) {
AFB_API_ERROR(apiHandle, "Failed to handle 'halmap' section");
return -6;
}
@@ -1153,8 +1149,8 @@ void InternalHalInfo(afb_req_t request)
return;
}
- controlsArray = HalUtGetJsonArrayForAllControls(apiHandle,
- currentHalData->internalHalData->alsaMapT);
+ controlsArray = HalUtGetJsonArrayForAllHalMapControls(apiHandle,
+ &currentHalData->internalHalData->halMapListHead);
if(! controlsArray) {
afb_req_fail(request, "controls_data", "Didn't succeed to generate controls data array");
return;
@@ -1179,7 +1175,7 @@ void InternalHalInfo(afb_req_t request)
void InternalHalSubscribeUnsubscribe(afb_req_t request, enum SubscribeUnsubscribeType subscribeUnsubscribeType)
{
- int arrayIdx, searchIdx, count, subscriptionFound, subscriptionDoneNb = 0;
+ int arrayIdx, count, subscriptionFound, subscriptionDoneNb = 0;
char *currentSubscriptionString;
@@ -1188,7 +1184,7 @@ void InternalHalSubscribeUnsubscribe(afb_req_t request, enum SubscribeUnsubscrib
struct HalData *currentHalData;
struct InternalHalMixerData *currentStreamData;
- struct InternalHalAlsaMapT *InternalHalAlsaMapT;
+ struct InternalHalAlsaMap *currentHalMapData;
json_object *requestJson,
*requestedSubscriptionsJ,
@@ -1219,8 +1215,6 @@ void InternalHalSubscribeUnsubscribe(afb_req_t request, enum SubscribeUnsubscrib
return;
}
- InternalHalAlsaMapT = currentHalData->internalHalData->alsaMapT;
-
requestJson = afb_req_json(request);
if(! requestJson) {
afb_req_fail(request, "request_json", "Can't get request json");
@@ -1310,26 +1304,25 @@ void InternalHalSubscribeUnsubscribe(afb_req_t request, enum SubscribeUnsubscrib
}
}
- searchIdx = 0;
- while((searchIdx < (InternalHalAlsaMapT ? InternalHalAlsaMapT->ctlsCount : 0)) &&
- ! subscriptionFound) {
- if(! strcasecmp(currentSubscriptionString, InternalHalAlsaMapT->ctls[searchIdx].uid)) {
- if(InternalHalAlsaMapT->ctls[searchIdx].alsaControlEvent &&
+ cds_list_for_each_entry(currentHalMapData, &currentHalData->internalHalData->halMapListHead, node) {
+ if(! subscriptionFound &&
+ ! strcasecmp(currentSubscriptionString, currentHalMapData->uid)) {
+ if(currentHalMapData->alsaControlEvent &&
subscribeUnsubscribeType == SUBSCRIPTION &&
- afb_req_subscribe(request, InternalHalAlsaMapT->ctls[searchIdx].alsaControlEvent)) {
+ afb_req_subscribe(request, currentHalMapData->alsaControlEvent)) {
afb_req_fail_f(request,
"request_control_event",
"Error while trying to subscribe to %s halmap controls events",
- InternalHalAlsaMapT->ctls[searchIdx].uid);
+ currentHalMapData->uid);
return;
}
- else if(InternalHalAlsaMapT->ctls[searchIdx].alsaControlEvent &&
+ else if(currentHalMapData->alsaControlEvent &&
subscribeUnsubscribeType == UNSUBSCRIPTION &&
- afb_req_unsubscribe(request, InternalHalAlsaMapT->ctls[searchIdx].alsaControlEvent)) {
+ afb_req_unsubscribe(request, currentHalMapData->alsaControlEvent)) {
afb_req_fail_f(request,
"request_stream_event",
"Error while trying to unsubscribe to %s halmap controls events",
- InternalHalAlsaMapT->ctls[searchIdx].uid);
+ currentHalMapData->uid);
return;
}
@@ -1337,8 +1330,6 @@ void InternalHalSubscribeUnsubscribe(afb_req_t request, enum SubscribeUnsubscrib
subscriptionDoneNb++;
break;
}
-
- searchIdx++;
}
}
diff --git a/src/4a-internals-hal/4a-internals-hal-cb.h b/src/4a-internals-hal/4a-internals-hal-cb.h
index ac09ef1..671abbb 100644
--- a/src/4a-internals-hal/4a-internals-hal-cb.h
+++ b/src/4a-internals-hal/4a-internals-hal-cb.h
@@ -43,7 +43,7 @@ void InternalHalDispatchApiEvent(afb_api_t apiHandle, const char *evtLabel, json
int InternalHalHalMixerConfig(afb_api_t apiHandle, CtlSectionT *section, json_object *MixerJ);
// Internals HAL - 'halmap' section parsing/handling functions
-int InternalHalHalMapConfig(afb_api_t apiHandle, CtlSectionT *section, json_object *AlsaMapJ);
+int InternalHalHalMapConfig(afb_api_t apiHandle, CtlSectionT *section, json_object *halMapJ);
// Internals HAL - 'haldependencies' section parsing/handling functions
int InternalHalHandleHalDependencies(afb_api_t apiHandle,