1094332d3Sopenharmony_ci/*
2094332d3Sopenharmony_ci * Copyright (c) 2021-2023 Huawei Device Co., Ltd.
3094332d3Sopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
4094332d3Sopenharmony_ci * you may not use this file except in compliance with the License.
5094332d3Sopenharmony_ci * You may obtain a copy of the License at
6094332d3Sopenharmony_ci *
7094332d3Sopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
8094332d3Sopenharmony_ci *
9094332d3Sopenharmony_ci * Unless required by applicable law or agreed to in writing, software
10094332d3Sopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
11094332d3Sopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12094332d3Sopenharmony_ci * See the License for the specific language governing permissions and
13094332d3Sopenharmony_ci * limitations under the License.
14094332d3Sopenharmony_ci */
15094332d3Sopenharmony_ci
16094332d3Sopenharmony_ci#include "audio_pathselect.h"
17094332d3Sopenharmony_ci#include "audio_uhdf_log.h"
18094332d3Sopenharmony_ci#include "cJSON.h"
19094332d3Sopenharmony_ci#include "osal_mem.h"
20094332d3Sopenharmony_ci#include "securec.h"
21094332d3Sopenharmony_ci
22094332d3Sopenharmony_ci#ifdef IDL_MODE
23094332d3Sopenharmony_ci#define HDF_LOG_TAG AUDIO_HDI_IMPL
24094332d3Sopenharmony_ci#else
25094332d3Sopenharmony_ci#define HDF_LOG_TAG HDF_AUDIO_HAL_IMPL
26094332d3Sopenharmony_ci#endif
27094332d3Sopenharmony_ci
28094332d3Sopenharmony_ci#define SPEAKER                   "Speaker"
29094332d3Sopenharmony_ci#define HEADPHONES                "Headphones"
30094332d3Sopenharmony_ci#define MIC                       "MIC"
31094332d3Sopenharmony_ci#define HS_MIC                    "micHs"
32094332d3Sopenharmony_ci#define EARPIECE                  "earpiece"
33094332d3Sopenharmony_ci#define BLUETOOTH_SCO             "Bluetooth"
34094332d3Sopenharmony_ci#define BLUETOOTH_SCO_HEADSET     "Bluetooth_SCO_Headset"
35094332d3Sopenharmony_ci#define JSON_UNPRINT 1
36094332d3Sopenharmony_ci
37094332d3Sopenharmony_ci#define OUTPUT_MASK   0xFFF
38094332d3Sopenharmony_ci#define OUTPUT_OFFSET 12
39094332d3Sopenharmony_ci#define INPUT_MASK    0x80000FF
40094332d3Sopenharmony_ci#define INPUT_OFFSET  27
41094332d3Sopenharmony_ci
42094332d3Sopenharmony_ci#define AUDIO_DEV_ON  1
43094332d3Sopenharmony_ci#define AUDIO_DEV_OFF 0
44094332d3Sopenharmony_ci
45094332d3Sopenharmony_ci#define HDF_PATH_NUM_MAX 32
46094332d3Sopenharmony_ci
47094332d3Sopenharmony_cistatic cJSON *g_cJsonObj = NULL;
48094332d3Sopenharmony_ci
49094332d3Sopenharmony_ciint32_t AudioPathSelGetConfToJsonObj(void)
50094332d3Sopenharmony_ci{
51094332d3Sopenharmony_ci    FILE *fpJson = NULL;
52094332d3Sopenharmony_ci    char *pJsonStr = NULL;
53094332d3Sopenharmony_ci    if (g_cJsonObj != NULL) {
54094332d3Sopenharmony_ci        return HDF_SUCCESS;
55094332d3Sopenharmony_ci    }
56094332d3Sopenharmony_ci    fpJson = fopen(CJSONFILE_CONFIG_PATH, "r");
57094332d3Sopenharmony_ci    if (fpJson == NULL) {
58094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("open %{pulbic}s fail!", CJSONFILE_CONFIG_PATH);
59094332d3Sopenharmony_ci        return HDF_FAILURE;
60094332d3Sopenharmony_ci    }
61094332d3Sopenharmony_ci    if (fseek(fpJson, 0, SEEK_END) != HDF_SUCCESS) {
62094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("fseek fail!");
63094332d3Sopenharmony_ci        (void)fclose(fpJson);
64094332d3Sopenharmony_ci        return HDF_FAILURE;
65094332d3Sopenharmony_ci    }
66094332d3Sopenharmony_ci    int32_t jsonStrSize = ftell(fpJson);
67094332d3Sopenharmony_ci    rewind(fpJson);
68094332d3Sopenharmony_ci    if (jsonStrSize <= 0) {
69094332d3Sopenharmony_ci        (void)fclose(fpJson);
70094332d3Sopenharmony_ci        return HDF_FAILURE;
71094332d3Sopenharmony_ci    }
72094332d3Sopenharmony_ci    pJsonStr = (char *)OsalMemCalloc(jsonStrSize + 1);
73094332d3Sopenharmony_ci    if (pJsonStr == NULL) {
74094332d3Sopenharmony_ci        (void)fclose(fpJson);
75094332d3Sopenharmony_ci        return HDF_FAILURE;
76094332d3Sopenharmony_ci    }
77094332d3Sopenharmony_ci    if (fread(pJsonStr, jsonStrSize, 1, fpJson) != 1) {
78094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("read to file fail!");
79094332d3Sopenharmony_ci        (void)fclose(fpJson);
80094332d3Sopenharmony_ci        fpJson = NULL;
81094332d3Sopenharmony_ci        OsalMemFree(pJsonStr);
82094332d3Sopenharmony_ci        return HDF_FAILURE;
83094332d3Sopenharmony_ci    }
84094332d3Sopenharmony_ci    (void)fclose(fpJson);
85094332d3Sopenharmony_ci    fpJson = NULL;
86094332d3Sopenharmony_ci#ifndef JSON_UNPRINT
87094332d3Sopenharmony_ci    AUDIO_FUNC_LOGI("pJsonStr = %{public}s", pJsonStr);
88094332d3Sopenharmony_ci#endif
89094332d3Sopenharmony_ci    g_cJsonObj = cJSON_Parse(pJsonStr);
90094332d3Sopenharmony_ci    if (g_cJsonObj == NULL) {
91094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("cJSON_GetErrorPtr() = %{public}s", cJSON_GetErrorPtr());
92094332d3Sopenharmony_ci        OsalMemFree(pJsonStr);
93094332d3Sopenharmony_ci        return HDF_FAILURE;
94094332d3Sopenharmony_ci    }
95094332d3Sopenharmony_ci    OsalMemFree(pJsonStr);
96094332d3Sopenharmony_ci    return HDF_SUCCESS;
97094332d3Sopenharmony_ci}
98094332d3Sopenharmony_ci
99094332d3Sopenharmony_cistatic const char *AudioPathSelGetDeviceType(enum AudioPortPin pin)
100094332d3Sopenharmony_ci{
101094332d3Sopenharmony_ci    if (pin < PIN_OUT_SPEAKER || pin > PIN_IN_BLUETOOTH_SCO_HEADSET) {
102094332d3Sopenharmony_ci        return NULL;
103094332d3Sopenharmony_ci    }
104094332d3Sopenharmony_ci    switch (pin) {
105094332d3Sopenharmony_ci        case PIN_OUT_SPEAKER:
106094332d3Sopenharmony_ci        case PIN_OUT_BLUETOOTH_A2DP:
107094332d3Sopenharmony_ci            return SPEAKER;
108094332d3Sopenharmony_ci        case PIN_OUT_HEADSET:
109094332d3Sopenharmony_ci            return HEADPHONES;
110094332d3Sopenharmony_ci        case PIN_IN_MIC:
111094332d3Sopenharmony_ci            return MIC;
112094332d3Sopenharmony_ci        case PIN_IN_HS_MIC:
113094332d3Sopenharmony_ci            return HS_MIC;
114094332d3Sopenharmony_ci        case PIN_OUT_EARPIECE:
115094332d3Sopenharmony_ci            return EARPIECE;
116094332d3Sopenharmony_ci        case PIN_OUT_BLUETOOTH_SCO:
117094332d3Sopenharmony_ci            return BLUETOOTH_SCO;
118094332d3Sopenharmony_ci        case PIN_IN_BLUETOOTH_SCO_HEADSET:
119094332d3Sopenharmony_ci            return BLUETOOTH_SCO_HEADSET;
120094332d3Sopenharmony_ci        default:
121094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("UseCase not support!");
122094332d3Sopenharmony_ci            break;
123094332d3Sopenharmony_ci    }
124094332d3Sopenharmony_ci    return NULL;
125094332d3Sopenharmony_ci}
126094332d3Sopenharmony_ci
127094332d3Sopenharmony_cistatic const char *AudioPathSelGetUseCase(enum AudioCategory type)
128094332d3Sopenharmony_ci{
129094332d3Sopenharmony_ci    static const char *usecaseType[AUDIO_MMAP_NOIRQ + 1] = {
130094332d3Sopenharmony_ci        [AUDIO_IN_MEDIA] = "deep-buffer-playback",
131094332d3Sopenharmony_ci        [AUDIO_IN_COMMUNICATION] = "low-latency-communication",
132094332d3Sopenharmony_ci        [AUDIO_IN_RINGTONE] = "ringtone-playback",
133094332d3Sopenharmony_ci        [AUDIO_IN_CALL] = "voice-call",
134094332d3Sopenharmony_ci        [AUDIO_MMAP_NOIRQ] = "low-latency-noirq-playback",
135094332d3Sopenharmony_ci    };
136094332d3Sopenharmony_ci
137094332d3Sopenharmony_ci    if (type < 0 || type > AUDIO_MMAP_NOIRQ) {
138094332d3Sopenharmony_ci        return NULL;
139094332d3Sopenharmony_ci    }
140094332d3Sopenharmony_ci    return usecaseType[type];
141094332d3Sopenharmony_ci}
142094332d3Sopenharmony_ci
143094332d3Sopenharmony_cistatic int32_t SetRenderPathDefaultValue(cJSON *renderSwObj, struct AudioHwRenderParam *renderParam)
144094332d3Sopenharmony_ci{
145094332d3Sopenharmony_ci    if (renderSwObj == NULL || renderParam == NULL) {
146094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
147094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
148094332d3Sopenharmony_ci    }
149094332d3Sopenharmony_ci    char *devKey = NULL;
150094332d3Sopenharmony_ci    int32_t renderDevNum;
151094332d3Sopenharmony_ci
152094332d3Sopenharmony_ci    renderDevNum = renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceNum;
153094332d3Sopenharmony_ci    int32_t renderPathNum = cJSON_GetArraySize(renderSwObj);
154094332d3Sopenharmony_ci    if (renderPathNum < 0 || renderPathNum > HDF_PATH_NUM_MAX) {
155094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("renderPathNum is invalid!");
156094332d3Sopenharmony_ci        return HDF_FAILURE;
157094332d3Sopenharmony_ci    }
158094332d3Sopenharmony_ci    for (int32_t i = 0; i < renderPathNum; i++) {
159094332d3Sopenharmony_ci        cJSON *tmpValue = cJSON_GetArrayItem(renderSwObj, i);
160094332d3Sopenharmony_ci        cJSON *renderSwName = tmpValue->child;
161094332d3Sopenharmony_ci        cJSON *renderSwVal = renderSwName->next;
162094332d3Sopenharmony_ci        if (renderSwName->valuestring == NULL) {
163094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("renderSwName->valuestring is null!");
164094332d3Sopenharmony_ci            return HDF_FAILURE;
165094332d3Sopenharmony_ci        }
166094332d3Sopenharmony_ci
167094332d3Sopenharmony_ci        devKey = renderSwName->valuestring;
168094332d3Sopenharmony_ci        (void)memset_s(renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[renderDevNum].deviceSwitch,
169094332d3Sopenharmony_ci            PATHPLAN_LEN, 0, PATHPLAN_LEN);
170094332d3Sopenharmony_ci        int32_t ret =
171094332d3Sopenharmony_ci            strncpy_s(renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[renderDevNum].deviceSwitch,
172094332d3Sopenharmony_ci                PATHPLAN_COUNT, devKey, strlen(devKey) + 1);
173094332d3Sopenharmony_ci        if (ret != 0) {
174094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("strcpy_s failed!");
175094332d3Sopenharmony_ci            return HDF_FAILURE;
176094332d3Sopenharmony_ci        }
177094332d3Sopenharmony_ci
178094332d3Sopenharmony_ci        renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[renderDevNum].value = renderSwVal->valueint;
179094332d3Sopenharmony_ci        renderDevNum++;
180094332d3Sopenharmony_ci    }
181094332d3Sopenharmony_ci    renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceNum = renderDevNum;
182094332d3Sopenharmony_ci    return HDF_SUCCESS;
183094332d3Sopenharmony_ci}
184094332d3Sopenharmony_ci
185094332d3Sopenharmony_cistatic int32_t SetCapturePathDefaultValue(cJSON *captureSwObj, struct AudioHwCaptureParam *captureParam)
186094332d3Sopenharmony_ci{
187094332d3Sopenharmony_ci    if (captureSwObj == NULL || captureParam == NULL) {
188094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
189094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
190094332d3Sopenharmony_ci    }
191094332d3Sopenharmony_ci    char *devKey = NULL;
192094332d3Sopenharmony_ci
193094332d3Sopenharmony_ci    int32_t devNum = captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceNum;
194094332d3Sopenharmony_ci    int32_t pathNum = cJSON_GetArraySize(captureSwObj);
195094332d3Sopenharmony_ci    if (pathNum < 0 || pathNum > HDF_PATH_NUM_MAX) {
196094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("pathNum is invalid!");
197094332d3Sopenharmony_ci        return HDF_FAILURE;
198094332d3Sopenharmony_ci    }
199094332d3Sopenharmony_ci    for (int32_t i = 0; i < pathNum; i++) {
200094332d3Sopenharmony_ci        cJSON *tmpValue = cJSON_GetArrayItem(captureSwObj, i);
201094332d3Sopenharmony_ci        cJSON *captureSwName = tmpValue->child;
202094332d3Sopenharmony_ci        cJSON *captureSwVal = captureSwName->next;
203094332d3Sopenharmony_ci        if (captureSwName->valuestring == NULL) {
204094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("captureSwName->valuestring is null!");
205094332d3Sopenharmony_ci            return HDF_FAILURE;
206094332d3Sopenharmony_ci        }
207094332d3Sopenharmony_ci
208094332d3Sopenharmony_ci        devKey = captureSwName->valuestring;
209094332d3Sopenharmony_ci        (void)memset_s(captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].deviceSwitch,
210094332d3Sopenharmony_ci            PATHPLAN_LEN, 0, PATHPLAN_LEN);
211094332d3Sopenharmony_ci        int32_t ret =
212094332d3Sopenharmony_ci            strncpy_s(captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].deviceSwitch,
213094332d3Sopenharmony_ci                PATHPLAN_COUNT, devKey, strlen(devKey) + 1);
214094332d3Sopenharmony_ci        if (ret != 0) {
215094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("strcpy_s failed!");
216094332d3Sopenharmony_ci            return HDF_FAILURE;
217094332d3Sopenharmony_ci        }
218094332d3Sopenharmony_ci        captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].value = captureSwVal->valueint;
219094332d3Sopenharmony_ci
220094332d3Sopenharmony_ci        devNum++;
221094332d3Sopenharmony_ci    }
222094332d3Sopenharmony_ci    captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceNum = devNum;
223094332d3Sopenharmony_ci    return HDF_SUCCESS;
224094332d3Sopenharmony_ci}
225094332d3Sopenharmony_ci
226094332d3Sopenharmony_cistatic int32_t SetRenderPathValue(
227094332d3Sopenharmony_ci    int32_t tpins, cJSON *renderObj, struct AudioHwRenderParam *renderParam, int32_t value)
228094332d3Sopenharmony_ci{
229094332d3Sopenharmony_ci    if (renderObj == NULL || renderParam == NULL) {
230094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
231094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
232094332d3Sopenharmony_ci    }
233094332d3Sopenharmony_ci    char *devKey = NULL;
234094332d3Sopenharmony_ci    int32_t devNum;
235094332d3Sopenharmony_ci    const char *renderDeviceType = AudioPathSelGetDeviceType(tpins);
236094332d3Sopenharmony_ci    if (renderDeviceType == NULL) {
237094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("DeviceType not found.");
238094332d3Sopenharmony_ci        return HDF_FAILURE;
239094332d3Sopenharmony_ci    }
240094332d3Sopenharmony_ci    devNum = renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceNum;
241094332d3Sopenharmony_ci    /* pins = 0, parse default value */
242094332d3Sopenharmony_ci    if (strcasecmp(renderDeviceType, renderObj->string) == 0) {
243094332d3Sopenharmony_ci        int32_t pathNum = cJSON_GetArraySize(renderObj);
244094332d3Sopenharmony_ci        if (pathNum < 0 || pathNum > HDF_PATH_NUM_MAX) {
245094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("pathNum is invalid!");
246094332d3Sopenharmony_ci            return HDF_FAILURE;
247094332d3Sopenharmony_ci        }
248094332d3Sopenharmony_ci        for (int32_t i = 0; i < pathNum; i++) {
249094332d3Sopenharmony_ci            cJSON *tmpValue = cJSON_GetArrayItem(renderObj, i);
250094332d3Sopenharmony_ci            cJSON *swName = tmpValue->child;
251094332d3Sopenharmony_ci            cJSON *swVal = swName->next;
252094332d3Sopenharmony_ci            if (swName->valuestring == NULL) {
253094332d3Sopenharmony_ci                AUDIO_FUNC_LOGE("ValueString is null!");
254094332d3Sopenharmony_ci                return HDF_FAILURE;
255094332d3Sopenharmony_ci            }
256094332d3Sopenharmony_ci
257094332d3Sopenharmony_ci            devKey = swName->valuestring;
258094332d3Sopenharmony_ci            (void)memset_s(renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].deviceSwitch,
259094332d3Sopenharmony_ci                PATHPLAN_LEN, 0, PATHPLAN_LEN);
260094332d3Sopenharmony_ci            int32_t ret =
261094332d3Sopenharmony_ci                strncpy_s(renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].deviceSwitch,
262094332d3Sopenharmony_ci                    PATHPLAN_COUNT, devKey, strlen(devKey) + 1);
263094332d3Sopenharmony_ci            if (ret != 0) {
264094332d3Sopenharmony_ci                AUDIO_FUNC_LOGE("strcpy_s failed!");
265094332d3Sopenharmony_ci                return HDF_FAILURE;
266094332d3Sopenharmony_ci            }
267094332d3Sopenharmony_ci            if (swVal->valueint > AUDIO_DEV_ON) {
268094332d3Sopenharmony_ci                /* alsa Adaptation */
269094332d3Sopenharmony_ci                renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].value = swVal->valueint;
270094332d3Sopenharmony_ci            } else {
271094332d3Sopenharmony_ci                renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].value = value;
272094332d3Sopenharmony_ci            }
273094332d3Sopenharmony_ci            devNum++;
274094332d3Sopenharmony_ci        }
275094332d3Sopenharmony_ci        renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceNum = devNum;
276094332d3Sopenharmony_ci    }
277094332d3Sopenharmony_ci    return HDF_SUCCESS;
278094332d3Sopenharmony_ci}
279094332d3Sopenharmony_ci
280094332d3Sopenharmony_cistatic int32_t SetMatchRenderDevicePath(
281094332d3Sopenharmony_ci    int32_t tpins, struct AudioHwRenderParam *renderParam, cJSON *cJsonObj, const char *deviceType, int32_t value)
282094332d3Sopenharmony_ci{
283094332d3Sopenharmony_ci    if (cJsonObj == NULL || renderParam == NULL) {
284094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
285094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
286094332d3Sopenharmony_ci    }
287094332d3Sopenharmony_ci    if (strcasecmp(cJsonObj->string, deviceType) == 0) {
288094332d3Sopenharmony_ci        int32_t ret = SetRenderPathValue(tpins, cJsonObj, renderParam, value);
289094332d3Sopenharmony_ci        if (ret != HDF_SUCCESS) {
290094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("set value failed!");
291094332d3Sopenharmony_ci            return ret;
292094332d3Sopenharmony_ci        }
293094332d3Sopenharmony_ci    }
294094332d3Sopenharmony_ci    return HDF_SUCCESS;
295094332d3Sopenharmony_ci}
296094332d3Sopenharmony_ci
297094332d3Sopenharmony_cistatic int32_t SetMatchRenderDefaultDevicePath(struct AudioHwRenderParam *renderParam, cJSON *cJsonObj)
298094332d3Sopenharmony_ci{
299094332d3Sopenharmony_ci    int32_t ret;
300094332d3Sopenharmony_ci    if (cJsonObj == NULL || renderParam == NULL) {
301094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
302094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
303094332d3Sopenharmony_ci    }
304094332d3Sopenharmony_ci    for (uint32_t i = PIN_OUT_SPEAKER; i <= PIN_OUT_EARPIECE; i = i << 1) {
305094332d3Sopenharmony_ci        const char *deviceType = AudioPathSelGetDeviceType((int32_t)i);
306094332d3Sopenharmony_ci        if (deviceType == NULL) {
307094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("DeviceType not found.");
308094332d3Sopenharmony_ci            return HDF_FAILURE;
309094332d3Sopenharmony_ci        }
310094332d3Sopenharmony_ci        if (strcasecmp(deviceType, cJsonObj->string) == 0) {
311094332d3Sopenharmony_ci            ret = SetRenderPathDefaultValue(cJsonObj, renderParam);
312094332d3Sopenharmony_ci            if (ret != HDF_SUCCESS) {
313094332d3Sopenharmony_ci                AUDIO_FUNC_LOGE("set default value failed!");
314094332d3Sopenharmony_ci                return ret;
315094332d3Sopenharmony_ci            }
316094332d3Sopenharmony_ci            break;
317094332d3Sopenharmony_ci        }
318094332d3Sopenharmony_ci    }
319094332d3Sopenharmony_ci    return HDF_SUCCESS;
320094332d3Sopenharmony_ci}
321094332d3Sopenharmony_ci
322094332d3Sopenharmony_cistatic int32_t SetMatchRenderOtherDevicePath(
323094332d3Sopenharmony_ci    int32_t tpins, struct AudioHwRenderParam *renderParam, cJSON *cJsonObj, int32_t value)
324094332d3Sopenharmony_ci{
325094332d3Sopenharmony_ci    int32_t ret;
326094332d3Sopenharmony_ci    if (cJsonObj == NULL || renderParam == NULL) {
327094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
328094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
329094332d3Sopenharmony_ci    }
330094332d3Sopenharmony_ci    for (uint32_t j = PIN_OUT_SPEAKER; j <= PIN_OUT_EARPIECE; j = j << 1) {
331094332d3Sopenharmony_ci        if ((j & tpins) == j) {
332094332d3Sopenharmony_ci            ret = SetRenderPathValue((int32_t)j, cJsonObj, renderParam, AUDIO_DEV_ON);
333094332d3Sopenharmony_ci            if (ret != HDF_SUCCESS) {
334094332d3Sopenharmony_ci                AUDIO_FUNC_LOGW("set value failed!");
335094332d3Sopenharmony_ci                continue;
336094332d3Sopenharmony_ci            }
337094332d3Sopenharmony_ci        }
338094332d3Sopenharmony_ci    }
339094332d3Sopenharmony_ci    return HDF_SUCCESS;
340094332d3Sopenharmony_ci}
341094332d3Sopenharmony_ci
342094332d3Sopenharmony_cistatic int32_t AudioRenderParseDevice(struct AudioHwRenderParam *renderParam, cJSON *cJsonObj)
343094332d3Sopenharmony_ci{
344094332d3Sopenharmony_ci    int32_t ret;
345094332d3Sopenharmony_ci    if (cJsonObj == NULL || renderParam == NULL) {
346094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
347094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
348094332d3Sopenharmony_ci    }
349094332d3Sopenharmony_ci    uint32_t pins = renderParam->renderMode.hwInfo.deviceDescript.pins;
350094332d3Sopenharmony_ci
351094332d3Sopenharmony_ci    int32_t tpins = pins & OUTPUT_MASK;
352094332d3Sopenharmony_ci    if ((pins >> OUTPUT_OFFSET) != 0) {
353094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("pins: %d, error!\n", pins);
354094332d3Sopenharmony_ci        return HDF_FAILURE;
355094332d3Sopenharmony_ci    }
356094332d3Sopenharmony_ci
357094332d3Sopenharmony_ci    if (strcasecmp(cJsonObj->string, MIC) == 0 || strcasecmp(cJsonObj->string, HS_MIC) == 0 ||
358094332d3Sopenharmony_ci        strcasecmp(cJsonObj->string, BLUETOOTH_SCO_HEADSET) == 0) {
359094332d3Sopenharmony_ci        return HDF_SUCCESS;
360094332d3Sopenharmony_ci    }
361094332d3Sopenharmony_ci
362094332d3Sopenharmony_ci    switch (tpins) {
363094332d3Sopenharmony_ci        case PIN_NONE:
364094332d3Sopenharmony_ci            /* pins = 0, parse default value */
365094332d3Sopenharmony_ci            ret = SetMatchRenderDefaultDevicePath(renderParam, cJsonObj);
366094332d3Sopenharmony_ci            break;
367094332d3Sopenharmony_ci        case PIN_OUT_SPEAKER:
368094332d3Sopenharmony_ci        case PIN_OUT_BLUETOOTH_A2DP:
369094332d3Sopenharmony_ci            /* 1.open speaker */
370094332d3Sopenharmony_ci            ret = SetMatchRenderDevicePath(tpins, renderParam, cJsonObj, SPEAKER, AUDIO_DEV_ON);
371094332d3Sopenharmony_ci#ifndef ALSA_LIB_MODE
372094332d3Sopenharmony_ci            /* 2.close headphones */
373094332d3Sopenharmony_ci            ret |= SetMatchRenderDevicePath(PIN_OUT_HEADSET, renderParam, cJsonObj, HEADPHONES, AUDIO_DEV_OFF);
374094332d3Sopenharmony_ci#endif
375094332d3Sopenharmony_ci            break;
376094332d3Sopenharmony_ci        case PIN_OUT_HEADSET:
377094332d3Sopenharmony_ci            /* 1、open headphone */
378094332d3Sopenharmony_ci            ret = SetMatchRenderDevicePath(tpins, renderParam, cJsonObj, HEADPHONES, AUDIO_DEV_ON);
379094332d3Sopenharmony_ci#ifndef ALSA_LIB_MODE
380094332d3Sopenharmony_ci            /* 2、close speaker */
381094332d3Sopenharmony_ci            ret |= SetMatchRenderDevicePath(PIN_OUT_SPEAKER, renderParam, cJsonObj, SPEAKER, AUDIO_DEV_OFF);
382094332d3Sopenharmony_ci#endif
383094332d3Sopenharmony_ci            break;
384094332d3Sopenharmony_ci        case PIN_OUT_EARPIECE:
385094332d3Sopenharmony_ci            /* 1、open earpiece */
386094332d3Sopenharmony_ci            ret = SetMatchRenderDevicePath(tpins, renderParam, cJsonObj, EARPIECE, AUDIO_DEV_ON);
387094332d3Sopenharmony_ci            break;
388094332d3Sopenharmony_ci        case PIN_OUT_BLUETOOTH_SCO:
389094332d3Sopenharmony_ci            /* 1、open bluetooth */
390094332d3Sopenharmony_ci            ret = SetMatchRenderDevicePath(tpins, renderParam, cJsonObj, BLUETOOTH_SCO, AUDIO_DEV_ON);
391094332d3Sopenharmony_ci            break;
392094332d3Sopenharmony_ci        default:
393094332d3Sopenharmony_ci            ret = SetMatchRenderOtherDevicePath(tpins, renderParam, cJsonObj, AUDIO_DEV_ON);
394094332d3Sopenharmony_ci            break;
395094332d3Sopenharmony_ci    }
396094332d3Sopenharmony_ci
397094332d3Sopenharmony_ci    return ret;
398094332d3Sopenharmony_ci}
399094332d3Sopenharmony_ci
400094332d3Sopenharmony_cistatic int32_t AudioRenderParseUsecase(struct AudioHwRenderParam *renderParam, const char *useCase)
401094332d3Sopenharmony_ci{
402094332d3Sopenharmony_ci    /* reset path numbers */
403094332d3Sopenharmony_ci    renderParam->renderMode.hwInfo.pathSelect.deviceInfo.deviceNum = 0;
404094332d3Sopenharmony_ci
405094332d3Sopenharmony_ci    cJSON *cardNode = cJSON_GetObjectItem(g_cJsonObj, renderParam->renderMode.hwInfo.cardServiceName);
406094332d3Sopenharmony_ci    if (cardNode == NULL) {
407094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE(
408094332d3Sopenharmony_ci            "failed to check item when [%{public}s] gets object!", renderParam->renderMode.hwInfo.cardServiceName);
409094332d3Sopenharmony_ci        return HDF_FAILURE;
410094332d3Sopenharmony_ci    }
411094332d3Sopenharmony_ci    cJSON *cardList = cardNode->child;
412094332d3Sopenharmony_ci    if (cardList == NULL) {
413094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("no child when [%{public}s] gets object!", renderParam->renderMode.hwInfo.cardServiceName);
414094332d3Sopenharmony_ci        return HDF_FAILURE;
415094332d3Sopenharmony_ci    }
416094332d3Sopenharmony_ci
417094332d3Sopenharmony_ci    cJSON *useCaseNode = cJSON_GetObjectItem(cardList, useCase);
418094332d3Sopenharmony_ci    if (useCaseNode == NULL) {
419094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("failed to check item when [%{public}s] gets object!", useCase);
420094332d3Sopenharmony_ci        return HDF_FAILURE;
421094332d3Sopenharmony_ci    }
422094332d3Sopenharmony_ci
423094332d3Sopenharmony_ci    cJSON *useCaseList = useCaseNode->child;
424094332d3Sopenharmony_ci    if (useCaseList == NULL) {
425094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("no child when [%{public}s] gets object!", useCase);
426094332d3Sopenharmony_ci        return HDF_FAILURE;
427094332d3Sopenharmony_ci    }
428094332d3Sopenharmony_ci
429094332d3Sopenharmony_ci    int32_t len = cJSON_GetArraySize(useCaseList);
430094332d3Sopenharmony_ci    if (len < 0 || len > HDF_PATH_NUM_MAX) {
431094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("len is invalid!");
432094332d3Sopenharmony_ci        return HDF_FAILURE;
433094332d3Sopenharmony_ci    }
434094332d3Sopenharmony_ci    for (int32_t i = 0; i < len; i++) {
435094332d3Sopenharmony_ci        cJSON *tmpValue = cJSON_GetArrayItem(useCaseList, i);
436094332d3Sopenharmony_ci        /* Each device in the incoming scene */
437094332d3Sopenharmony_ci        int32_t ret = AudioRenderParseDevice(renderParam, tmpValue);
438094332d3Sopenharmony_ci        if (ret != HDF_SUCCESS) {
439094332d3Sopenharmony_ci            return ret;
440094332d3Sopenharmony_ci        }
441094332d3Sopenharmony_ci    }
442094332d3Sopenharmony_ci    return HDF_SUCCESS;
443094332d3Sopenharmony_ci}
444094332d3Sopenharmony_ci
445094332d3Sopenharmony_cistatic int32_t AudioPathSelGetPlanRender(struct AudioHwRenderParam *renderParam)
446094332d3Sopenharmony_ci{
447094332d3Sopenharmony_ci    if (renderParam == NULL) {
448094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
449094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
450094332d3Sopenharmony_ci    }
451094332d3Sopenharmony_ci    const char *useCase = AudioPathSelGetUseCase(renderParam->frameRenderMode.attrs.type);
452094332d3Sopenharmony_ci    if (useCase == NULL) {
453094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("useCase not support!");
454094332d3Sopenharmony_ci        return HDF_FAILURE;
455094332d3Sopenharmony_ci    }
456094332d3Sopenharmony_ci    return AudioRenderParseUsecase(renderParam, useCase);
457094332d3Sopenharmony_ci}
458094332d3Sopenharmony_ci
459094332d3Sopenharmony_cistatic int32_t SetCapturePathValue(
460094332d3Sopenharmony_ci    int32_t tpins, cJSON *captureSwitchObj, struct AudioHwCaptureParam *captureParam, int32_t value)
461094332d3Sopenharmony_ci{
462094332d3Sopenharmony_ci    if (captureParam == NULL || captureSwitchObj == NULL) {
463094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
464094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
465094332d3Sopenharmony_ci    }
466094332d3Sopenharmony_ci    const char *captureDeviceType = AudioPathSelGetDeviceType(tpins);
467094332d3Sopenharmony_ci    if (captureDeviceType == NULL) {
468094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("DeviceType not found.");
469094332d3Sopenharmony_ci        return HDF_FAILURE;
470094332d3Sopenharmony_ci    }
471094332d3Sopenharmony_ci
472094332d3Sopenharmony_ci    int32_t devNum = captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceNum;
473094332d3Sopenharmony_ci    if (strcasecmp(captureDeviceType, captureSwitchObj->string) == 0) {
474094332d3Sopenharmony_ci        int32_t pathNum = cJSON_GetArraySize(captureSwitchObj);
475094332d3Sopenharmony_ci        if (pathNum < 0 || pathNum > HDF_PATH_NUM_MAX) {
476094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("pathNum is invalid!");
477094332d3Sopenharmony_ci            return HDF_FAILURE;
478094332d3Sopenharmony_ci        }
479094332d3Sopenharmony_ci        for (int32_t i = 0; i < pathNum; i++) {
480094332d3Sopenharmony_ci            cJSON *captureTmpValue = cJSON_GetArrayItem(captureSwitchObj, i);
481094332d3Sopenharmony_ci            cJSON *swName = captureTmpValue->child;
482094332d3Sopenharmony_ci            cJSON *swVal = swName->next;
483094332d3Sopenharmony_ci            if (swName->valuestring == NULL) {
484094332d3Sopenharmony_ci                AUDIO_FUNC_LOGE("ValueString is null!");
485094332d3Sopenharmony_ci                return HDF_FAILURE;
486094332d3Sopenharmony_ci            }
487094332d3Sopenharmony_ci
488094332d3Sopenharmony_ci            (void)memset_s(captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].deviceSwitch,
489094332d3Sopenharmony_ci                PATHPLAN_LEN, 0, PATHPLAN_LEN);
490094332d3Sopenharmony_ci            int32_t ret =
491094332d3Sopenharmony_ci                strncpy_s(captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].deviceSwitch,
492094332d3Sopenharmony_ci                    PATHPLAN_COUNT, swName->valuestring, strlen(swName->valuestring) + 1);
493094332d3Sopenharmony_ci            if (ret != 0) {
494094332d3Sopenharmony_ci                AUDIO_FUNC_LOGE("strcpy_s failed!");
495094332d3Sopenharmony_ci                return HDF_FAILURE;
496094332d3Sopenharmony_ci            }
497094332d3Sopenharmony_ci            if (swVal->valueint > AUDIO_DEV_ON) {
498094332d3Sopenharmony_ci                /* alsa Adaptation */
499094332d3Sopenharmony_ci                captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].value = swVal->valueint;
500094332d3Sopenharmony_ci            } else {
501094332d3Sopenharmony_ci                captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceSwitchs[devNum].value = value;
502094332d3Sopenharmony_ci            }
503094332d3Sopenharmony_ci
504094332d3Sopenharmony_ci            devNum++;
505094332d3Sopenharmony_ci        }
506094332d3Sopenharmony_ci        captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceNum = devNum;
507094332d3Sopenharmony_ci    }
508094332d3Sopenharmony_ci    return HDF_SUCCESS;
509094332d3Sopenharmony_ci}
510094332d3Sopenharmony_ci
511094332d3Sopenharmony_cistatic int32_t SetMatchCaptureDevicePath(
512094332d3Sopenharmony_ci    struct AudioHwCaptureParam *captureParam, cJSON *cJsonObj, int32_t tpins, char *deviceType, int32_t value)
513094332d3Sopenharmony_ci{
514094332d3Sopenharmony_ci    if (captureParam == NULL || cJsonObj == NULL) {
515094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
516094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
517094332d3Sopenharmony_ci    }
518094332d3Sopenharmony_ci    if (strcasecmp(cJsonObj->string, deviceType) == 0) {
519094332d3Sopenharmony_ci        int32_t ret = SetCapturePathValue(tpins, cJsonObj, captureParam, value);
520094332d3Sopenharmony_ci        if (ret != HDF_SUCCESS) {
521094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("set value failed!");
522094332d3Sopenharmony_ci            return ret;
523094332d3Sopenharmony_ci        }
524094332d3Sopenharmony_ci    }
525094332d3Sopenharmony_ci    return HDF_SUCCESS;
526094332d3Sopenharmony_ci}
527094332d3Sopenharmony_ci
528094332d3Sopenharmony_cistatic int32_t SetMatchCaptureDefaultDevicePath(struct AudioHwCaptureParam *captureParam, cJSON *cJsonObj)
529094332d3Sopenharmony_ci{
530094332d3Sopenharmony_ci    int32_t ret;
531094332d3Sopenharmony_ci    if (captureParam == NULL || cJsonObj == NULL) {
532094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
533094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
534094332d3Sopenharmony_ci    }
535094332d3Sopenharmony_ci    for (uint32_t i = PIN_IN_MIC; i <= PIN_IN_BLUETOOTH_SCO_HEADSET;
536094332d3Sopenharmony_ci         i = (1 << INPUT_OFFSET) | ((i & OUTPUT_MASK) << 1)) {
537094332d3Sopenharmony_ci        const char *deviceType = AudioPathSelGetDeviceType((int32_t)i);
538094332d3Sopenharmony_ci        if (deviceType == NULL) {
539094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("DeviceType not found.");
540094332d3Sopenharmony_ci            return HDF_FAILURE;
541094332d3Sopenharmony_ci        }
542094332d3Sopenharmony_ci
543094332d3Sopenharmony_ci        if (strcasecmp(deviceType, cJsonObj->string) == 0) {
544094332d3Sopenharmony_ci            ret = SetCapturePathDefaultValue(cJsonObj, captureParam);
545094332d3Sopenharmony_ci            if (ret != HDF_SUCCESS) {
546094332d3Sopenharmony_ci                AUDIO_FUNC_LOGE("set default value failed!");
547094332d3Sopenharmony_ci                return ret;
548094332d3Sopenharmony_ci            }
549094332d3Sopenharmony_ci            break;
550094332d3Sopenharmony_ci        }
551094332d3Sopenharmony_ci    }
552094332d3Sopenharmony_ci    return HDF_SUCCESS;
553094332d3Sopenharmony_ci}
554094332d3Sopenharmony_ci
555094332d3Sopenharmony_cistatic int32_t SetMatchCaptureOtherDevicePath(
556094332d3Sopenharmony_ci    struct AudioHwCaptureParam *captureParam, cJSON *cJsonObj, int32_t tpins, int32_t value)
557094332d3Sopenharmony_ci{
558094332d3Sopenharmony_ci    int32_t ret;
559094332d3Sopenharmony_ci    uint32_t i;
560094332d3Sopenharmony_ci    if (captureParam == NULL || cJsonObj == NULL) {
561094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
562094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
563094332d3Sopenharmony_ci    }
564094332d3Sopenharmony_ci    for (i = PIN_IN_MIC; i <= PIN_IN_BLUETOOTH_SCO_HEADSET; i = (1 << INPUT_OFFSET) | ((i & OUTPUT_MASK) << 1)) {
565094332d3Sopenharmony_ci        if ((i & tpins) == i) { /* Select which device to open and get the pin of which device */
566094332d3Sopenharmony_ci            ret = SetCapturePathValue((int32_t)i, cJsonObj, captureParam, value);
567094332d3Sopenharmony_ci            if (ret != HDF_SUCCESS) {
568094332d3Sopenharmony_ci                AUDIO_FUNC_LOGE("set value failed!");
569094332d3Sopenharmony_ci                continue;
570094332d3Sopenharmony_ci            }
571094332d3Sopenharmony_ci        }
572094332d3Sopenharmony_ci    }
573094332d3Sopenharmony_ci    return HDF_SUCCESS;
574094332d3Sopenharmony_ci}
575094332d3Sopenharmony_ci
576094332d3Sopenharmony_cistatic int32_t AudioCaptureParseDevice(struct AudioHwCaptureParam *captureParam, cJSON *cJsonObj)
577094332d3Sopenharmony_ci{
578094332d3Sopenharmony_ci    int32_t ret;
579094332d3Sopenharmony_ci    if (captureParam == NULL || cJsonObj == NULL) {
580094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
581094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
582094332d3Sopenharmony_ci    }
583094332d3Sopenharmony_ci    uint32_t pins = captureParam->captureMode.hwInfo.deviceDescript.pins;
584094332d3Sopenharmony_ci
585094332d3Sopenharmony_ci    if (!((pins >> INPUT_OFFSET) & 0x01)) {
586094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("pins: %{public}d, error!", pins);
587094332d3Sopenharmony_ci        return HDF_FAILURE;
588094332d3Sopenharmony_ci    }
589094332d3Sopenharmony_ci
590094332d3Sopenharmony_ci    if (strcasecmp(cJsonObj->string, SPEAKER) == 0 || strcasecmp(cJsonObj->string, HEADPHONES) == 0 ||
591094332d3Sopenharmony_ci        strcasecmp(cJsonObj->string, EARPIECE) == 0  || strcasecmp(cJsonObj->string, BLUETOOTH_SCO) == 0) {
592094332d3Sopenharmony_ci        return HDF_SUCCESS;
593094332d3Sopenharmony_ci    }
594094332d3Sopenharmony_ci
595094332d3Sopenharmony_ci    int32_t tpins = pins & INPUT_MASK;
596094332d3Sopenharmony_ci    switch (tpins) {
597094332d3Sopenharmony_ci        case (1 << INPUT_OFFSET):
598094332d3Sopenharmony_ci            /* pins = 0, parse default value */
599094332d3Sopenharmony_ci            ret = SetMatchCaptureDefaultDevicePath(captureParam, cJsonObj);
600094332d3Sopenharmony_ci            break;
601094332d3Sopenharmony_ci        case PIN_IN_MIC:
602094332d3Sopenharmony_ci            /* 1.open main mic */
603094332d3Sopenharmony_ci            ret = SetMatchCaptureDevicePath(captureParam, cJsonObj, tpins, MIC, AUDIO_DEV_ON);
604094332d3Sopenharmony_ci#ifndef ALSA_LIB_MODE
605094332d3Sopenharmony_ci            /* 2.close headset mic */
606094332d3Sopenharmony_ci            ret |= SetMatchCaptureDevicePath(captureParam, cJsonObj, PIN_IN_HS_MIC, HS_MIC, AUDIO_DEV_OFF);
607094332d3Sopenharmony_ci#endif
608094332d3Sopenharmony_ci            break;
609094332d3Sopenharmony_ci        case PIN_IN_HS_MIC:
610094332d3Sopenharmony_ci            /* 1、open headset mic */
611094332d3Sopenharmony_ci            ret = SetMatchCaptureDevicePath(captureParam, cJsonObj, tpins, HS_MIC, AUDIO_DEV_ON);
612094332d3Sopenharmony_ci#ifndef ALSA_LIB_MODE
613094332d3Sopenharmony_ci            /* 2、close main mic */
614094332d3Sopenharmony_ci            ret |= SetMatchCaptureDevicePath(captureParam, cJsonObj, PIN_IN_MIC, MIC, AUDIO_DEV_OFF);
615094332d3Sopenharmony_ci#endif
616094332d3Sopenharmony_ci            break;
617094332d3Sopenharmony_ci        case PIN_IN_BLUETOOTH_SCO_HEADSET:
618094332d3Sopenharmony_ci            /* 1、open bluetooth sco headset mic */
619094332d3Sopenharmony_ci            ret = SetMatchCaptureDevicePath(captureParam, cJsonObj, tpins, BLUETOOTH_SCO_HEADSET, AUDIO_DEV_ON);
620094332d3Sopenharmony_ci            break;
621094332d3Sopenharmony_ci        default:
622094332d3Sopenharmony_ci            ret = SetMatchCaptureOtherDevicePath(captureParam, cJsonObj, tpins, AUDIO_DEV_ON);
623094332d3Sopenharmony_ci            break;
624094332d3Sopenharmony_ci    }
625094332d3Sopenharmony_ci    return ret;
626094332d3Sopenharmony_ci}
627094332d3Sopenharmony_ci
628094332d3Sopenharmony_cistatic int32_t AudioCaptureParseUsecase(struct AudioHwCaptureParam *captureParam, const char *useCase)
629094332d3Sopenharmony_ci{
630094332d3Sopenharmony_ci    if (captureParam == NULL || useCase == NULL) {
631094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("param Is NULL");
632094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
633094332d3Sopenharmony_ci    }
634094332d3Sopenharmony_ci    /* reset path numbers */
635094332d3Sopenharmony_ci    captureParam->captureMode.hwInfo.pathSelect.deviceInfo.deviceNum = 0;
636094332d3Sopenharmony_ci
637094332d3Sopenharmony_ci    cJSON *cardNode = cJSON_GetObjectItem(g_cJsonObj, captureParam->captureMode.hwInfo.cardServiceName);
638094332d3Sopenharmony_ci    if (cardNode == NULL) {
639094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE(
640094332d3Sopenharmony_ci            "failed to check item when [%{public}s] gets object!", captureParam->captureMode.hwInfo.cardServiceName);
641094332d3Sopenharmony_ci        return HDF_FAILURE;
642094332d3Sopenharmony_ci    }
643094332d3Sopenharmony_ci    cJSON *cardList = cardNode->child;
644094332d3Sopenharmony_ci    if (cardList == NULL) {
645094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("no child when [%{public}s] gets object!", captureParam->captureMode.hwInfo.cardServiceName);
646094332d3Sopenharmony_ci        return HDF_FAILURE;
647094332d3Sopenharmony_ci    }
648094332d3Sopenharmony_ci
649094332d3Sopenharmony_ci    cJSON *useCaseNode = cJSON_GetObjectItem(cardList, useCase);
650094332d3Sopenharmony_ci    if (useCaseNode == NULL) {
651094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("failed to check item when [%{public}s] gets object!", useCase);
652094332d3Sopenharmony_ci        return HDF_FAILURE;
653094332d3Sopenharmony_ci    }
654094332d3Sopenharmony_ci    cJSON *useCaseList = useCaseNode->child;
655094332d3Sopenharmony_ci    if (useCaseList == NULL) {
656094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("no child when [%{public}s] gets object!", useCase);
657094332d3Sopenharmony_ci        return HDF_FAILURE;
658094332d3Sopenharmony_ci    }
659094332d3Sopenharmony_ci
660094332d3Sopenharmony_ci    int32_t len = cJSON_GetArraySize(useCaseList);
661094332d3Sopenharmony_ci    if (len < 0 || len > HDF_PATH_NUM_MAX) {
662094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("len is invalid!");
663094332d3Sopenharmony_ci        return HDF_FAILURE;
664094332d3Sopenharmony_ci    }
665094332d3Sopenharmony_ci    for (int32_t i = 0; i < len; i++) {
666094332d3Sopenharmony_ci        cJSON *tmpValue = cJSON_GetArrayItem(useCaseList, i);
667094332d3Sopenharmony_ci        int32_t ret = AudioCaptureParseDevice(captureParam, tmpValue);
668094332d3Sopenharmony_ci        if (ret != HDF_SUCCESS) {
669094332d3Sopenharmony_ci            return ret;
670094332d3Sopenharmony_ci        }
671094332d3Sopenharmony_ci    }
672094332d3Sopenharmony_ci    return HDF_SUCCESS;
673094332d3Sopenharmony_ci}
674094332d3Sopenharmony_ci
675094332d3Sopenharmony_cistatic int32_t AudioPathSelGetPlanCapture(struct AudioHwCaptureParam *captureParam)
676094332d3Sopenharmony_ci{
677094332d3Sopenharmony_ci    enum AudioCategory type = captureParam->frameCaptureMode.attrs.type;
678094332d3Sopenharmony_ci
679094332d3Sopenharmony_ci    if (type == AUDIO_IN_RINGTONE) {
680094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("useCase not support!");
681094332d3Sopenharmony_ci        return HDF_ERR_NOT_SUPPORT;
682094332d3Sopenharmony_ci    }
683094332d3Sopenharmony_ci
684094332d3Sopenharmony_ci    if (type == AUDIO_MMAP_NOIRQ) {
685094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("useCase set as AUDIO_IN_MEDIA");
686094332d3Sopenharmony_ci        type = AUDIO_IN_MEDIA;
687094332d3Sopenharmony_ci    }
688094332d3Sopenharmony_ci
689094332d3Sopenharmony_ci    const char *useCase = AudioPathSelGetUseCase(type);
690094332d3Sopenharmony_ci    if (useCase == NULL) {
691094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("useCase not support!");
692094332d3Sopenharmony_ci        return HDF_FAILURE;
693094332d3Sopenharmony_ci    }
694094332d3Sopenharmony_ci
695094332d3Sopenharmony_ci    return AudioCaptureParseUsecase(captureParam, useCase);
696094332d3Sopenharmony_ci}
697094332d3Sopenharmony_ci
698094332d3Sopenharmony_cistatic int32_t AudioPathSelRenderChkScene(struct AudioHwRenderParam *renderSceneParam)
699094332d3Sopenharmony_ci{
700094332d3Sopenharmony_ci    return AudioPathSelGetPlanRender(renderSceneParam);
701094332d3Sopenharmony_ci}
702094332d3Sopenharmony_ci
703094332d3Sopenharmony_cistatic int32_t AudioPathSelCaptureChkScene(struct AudioHwCaptureParam *captureSceneParam)
704094332d3Sopenharmony_ci{
705094332d3Sopenharmony_ci    return AudioPathSelGetPlanCapture(captureSceneParam);
706094332d3Sopenharmony_ci}
707094332d3Sopenharmony_ci
708094332d3Sopenharmony_ciint32_t AudioPathSelAnalysisJson(const AudioHandle adapterParam, enum AudioAdaptType adaptType)
709094332d3Sopenharmony_ci{
710094332d3Sopenharmony_ci    AUDIO_FUNC_LOGI();
711094332d3Sopenharmony_ci    if (adaptType < 0 || adapterParam == NULL) {
712094332d3Sopenharmony_ci        AUDIO_FUNC_LOGE("Param Invaild!");
713094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
714094332d3Sopenharmony_ci    }
715094332d3Sopenharmony_ci    struct AudioHwRenderParam *renderParam = NULL;
716094332d3Sopenharmony_ci    struct AudioHwCaptureParam *captureParam = NULL;
717094332d3Sopenharmony_ci    struct AudioHwRenderParam *renderSceneCheck = NULL;
718094332d3Sopenharmony_ci    struct AudioHwCaptureParam *captureScenceCheck = NULL;
719094332d3Sopenharmony_ci    switch (adaptType) {
720094332d3Sopenharmony_ci        case RENDER_PATH_SELECT:
721094332d3Sopenharmony_ci            renderParam = (struct AudioHwRenderParam *)adapterParam;
722094332d3Sopenharmony_ci            if (strcasecmp(renderParam->renderMode.hwInfo.adapterName, USB) == 0 ||
723094332d3Sopenharmony_ci                strcasecmp(renderParam->renderMode.hwInfo.adapterName, HDMI) == 0) {
724094332d3Sopenharmony_ci                return HDF_SUCCESS;
725094332d3Sopenharmony_ci            }
726094332d3Sopenharmony_ci            return (AudioPathSelGetPlanRender(renderParam));
727094332d3Sopenharmony_ci        case CAPTURE_PATH_SELECT:
728094332d3Sopenharmony_ci            captureParam = (struct AudioHwCaptureParam *)adapterParam;
729094332d3Sopenharmony_ci            if (strcasecmp(captureParam->captureMode.hwInfo.adapterName, USB) == 0 ||
730094332d3Sopenharmony_ci                strcasecmp(captureParam->captureMode.hwInfo.adapterName, HDMI) == 0) {
731094332d3Sopenharmony_ci                return HDF_SUCCESS;
732094332d3Sopenharmony_ci            }
733094332d3Sopenharmony_ci            return (AudioPathSelGetPlanCapture(captureParam));
734094332d3Sopenharmony_ci        /* Scene is supported */
735094332d3Sopenharmony_ci        case CHECKSCENE_PATH_SELECT:
736094332d3Sopenharmony_ci            renderSceneCheck = (struct AudioHwRenderParam *)adapterParam;
737094332d3Sopenharmony_ci            if (strcasecmp(renderSceneCheck->renderMode.hwInfo.adapterName, USB) == 0 ||
738094332d3Sopenharmony_ci                strcasecmp(renderSceneCheck->renderMode.hwInfo.adapterName, HDMI) == 0) {
739094332d3Sopenharmony_ci                return HDF_SUCCESS;
740094332d3Sopenharmony_ci            }
741094332d3Sopenharmony_ci            return (AudioPathSelRenderChkScene(renderSceneCheck));
742094332d3Sopenharmony_ci        case CHECKSCENE_PATH_SELECT_CAPTURE:
743094332d3Sopenharmony_ci            captureScenceCheck = (struct AudioHwCaptureParam *)adapterParam;
744094332d3Sopenharmony_ci            if (strcasecmp(captureScenceCheck->captureMode.hwInfo.adapterName, USB) == 0 ||
745094332d3Sopenharmony_ci                strcasecmp(captureScenceCheck->captureMode.hwInfo.adapterName, HDMI) == 0) {
746094332d3Sopenharmony_ci                return HDF_SUCCESS;
747094332d3Sopenharmony_ci            }
748094332d3Sopenharmony_ci            return (AudioPathSelCaptureChkScene(captureScenceCheck));
749094332d3Sopenharmony_ci        default:
750094332d3Sopenharmony_ci            AUDIO_FUNC_LOGE("Path select mode invalid");
751094332d3Sopenharmony_ci            break;
752094332d3Sopenharmony_ci    }
753094332d3Sopenharmony_ci    return HDF_FAILURE;
754094332d3Sopenharmony_ci}
755