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 "usbfn_dev_mgr.h" 17094332d3Sopenharmony_ci#include "hdf_base.h" 18094332d3Sopenharmony_ci#include "hdf_log.h" 19094332d3Sopenharmony_ci#include "osal_thread.h" 20094332d3Sopenharmony_ci#include "osal_time.h" 21094332d3Sopenharmony_ci#include "securec.h" 22094332d3Sopenharmony_ci#include "usbfn_cfg_mgr.h" 23094332d3Sopenharmony_ci#include "usbfn_io_mgr.h" 24094332d3Sopenharmony_ci#include "usbd_wrapper.h" 25094332d3Sopenharmony_ci 26094332d3Sopenharmony_ci#define HDF_LOG_TAG usbfn_dev_mgr 27094332d3Sopenharmony_ci#define SLEEP_TIME_OUT 100 28094332d3Sopenharmony_ci#define SLEEP_TIMES 20 29094332d3Sopenharmony_ci 30094332d3Sopenharmony_cistatic struct DListHead g_devEntry = {0}; 31094332d3Sopenharmony_cistatic uint32_t g_intfCnt = 0; 32094332d3Sopenharmony_cistatic uint32_t g_epCnt = 1; 33094332d3Sopenharmony_cistatic uint32_t g_fnCntOld = 0; 34094332d3Sopenharmony_cistatic void GetInterfaceInfo(const struct UsbInterfaceDescriptor *intf, struct UsbFnDeviceMgr *devMgr, uint32_t fnCnt, 35094332d3Sopenharmony_ci const struct UsbFnConfiguration *config) 36094332d3Sopenharmony_ci{ 37094332d3Sopenharmony_ci if (g_fnCntOld != fnCnt) { 38094332d3Sopenharmony_ci g_fnCntOld = fnCnt; 39094332d3Sopenharmony_ci g_epCnt = 1; 40094332d3Sopenharmony_ci } 41094332d3Sopenharmony_ci struct UsbFnInterfaceInfo *info = NULL; 42094332d3Sopenharmony_ci if (intf->bDescriptorType == USB_DDK_DT_INTERFACE && intf->bNumEndpoints > 0) { 43094332d3Sopenharmony_ci if (g_intfCnt >= devMgr->fnDev.numInterfaces) { 44094332d3Sopenharmony_ci HDF_LOGE("%{public}s: GetInterfaceInfo failed", __func__); 45094332d3Sopenharmony_ci return; 46094332d3Sopenharmony_ci } 47094332d3Sopenharmony_ci info = &devMgr->interfaceMgr[g_intfCnt].interface.info; 48094332d3Sopenharmony_ci info->index = intf->bInterfaceNumber; 49094332d3Sopenharmony_ci info->interfaceClass = intf->bInterfaceClass; 50094332d3Sopenharmony_ci info->subclass = intf->bInterfaceSubClass; 51094332d3Sopenharmony_ci info->protocol = intf->bInterfaceProtocol; 52094332d3Sopenharmony_ci info->numPipes = intf->bNumEndpoints; 53094332d3Sopenharmony_ci info->configIndex = config->configurationValue; 54094332d3Sopenharmony_ci 55094332d3Sopenharmony_ci devMgr->interfaceMgr[g_intfCnt].interface.object = &devMgr->fnDev.object; 56094332d3Sopenharmony_ci devMgr->interfaceMgr[g_intfCnt].funcMgr = &devMgr->funcMgr[fnCnt]; 57094332d3Sopenharmony_ci devMgr->interfaceMgr[g_intfCnt].startEpId = (uint8_t)g_epCnt; 58094332d3Sopenharmony_ci g_epCnt += intf->bNumEndpoints; 59094332d3Sopenharmony_ci g_intfCnt++; 60094332d3Sopenharmony_ci } 61094332d3Sopenharmony_ci} 62094332d3Sopenharmony_ci 63094332d3Sopenharmony_cistatic void CreateInterface(struct UsbFnDeviceDesc *des, struct UsbFnDeviceMgr *devMgr) 64094332d3Sopenharmony_ci{ 65094332d3Sopenharmony_ci uint32_t fnCnt = 0; 66094332d3Sopenharmony_ci struct UsbInterfaceDescriptor *intf = NULL; 67094332d3Sopenharmony_ci g_intfCnt = 0; 68094332d3Sopenharmony_ci g_epCnt = 1; 69094332d3Sopenharmony_ci g_fnCntOld = 0; 70094332d3Sopenharmony_ci 71094332d3Sopenharmony_ci for (uint32_t i = 0; des->configs[i] != NULL; i++) { 72094332d3Sopenharmony_ci for (uint32_t j = 0; des->configs[i]->functions[j] != NULL; j++) { 73094332d3Sopenharmony_ci if (strncmp(des->configs[i]->functions[j]->funcName, FUNCTION_GENERIC, strlen(FUNCTION_GENERIC))) { 74094332d3Sopenharmony_ci continue; 75094332d3Sopenharmony_ci } 76094332d3Sopenharmony_ci if (des->configs[i]->functions[j]->enable == false) { 77094332d3Sopenharmony_ci continue; 78094332d3Sopenharmony_ci } 79094332d3Sopenharmony_ci DListHeadInit(&devMgr->funcMgr[fnCnt].reqEntry); 80094332d3Sopenharmony_ci devMgr->funcMgr[fnCnt].object = &devMgr->fnDev.object; 81094332d3Sopenharmony_ci int32_t ret = snprintf_s(devMgr->funcMgr[fnCnt].name, MAX_NAMELEN, MAX_NAMELEN - 1, "%s", 82094332d3Sopenharmony_ci des->configs[i]->functions[j]->funcName); 83094332d3Sopenharmony_ci if (ret < 0) { 84094332d3Sopenharmony_ci HDF_LOGE("%{public}s: snprintf_s failed", __func__); 85094332d3Sopenharmony_ci return; 86094332d3Sopenharmony_ci } 87094332d3Sopenharmony_ci 88094332d3Sopenharmony_ci for (uint32_t k = 0; des->configs[i]->functions[j]->fsDescriptors[k] != NULL; k++) { 89094332d3Sopenharmony_ci intf = (struct UsbInterfaceDescriptor *)des->configs[i]->functions[j]->fsDescriptors[k]; 90094332d3Sopenharmony_ci GetInterfaceInfo(intf, devMgr, fnCnt, des->configs[i]); 91094332d3Sopenharmony_ci } 92094332d3Sopenharmony_ci fnCnt++; 93094332d3Sopenharmony_ci } 94094332d3Sopenharmony_ci } 95094332d3Sopenharmony_ci} 96094332d3Sopenharmony_ci 97094332d3Sopenharmony_ci#define MAX_LIST 32 98094332d3Sopenharmony_cistatic int32_t FindEmptyId(void) 99094332d3Sopenharmony_ci{ 100094332d3Sopenharmony_ci int32_t devCnt = 1; 101094332d3Sopenharmony_ci struct UsbObject *obj = NULL; 102094332d3Sopenharmony_ci struct UsbObject *temp = NULL; 103094332d3Sopenharmony_ci if (g_devEntry.next != 0 && !DListIsEmpty(&g_devEntry)) { 104094332d3Sopenharmony_ci int32_t i; 105094332d3Sopenharmony_ci for (i = 1; i < MAX_LIST; i++) { 106094332d3Sopenharmony_ci int32_t isUse = 0; 107094332d3Sopenharmony_ci DLIST_FOR_EACH_ENTRY_SAFE(obj, temp, &g_devEntry, struct UsbObject, entry) { 108094332d3Sopenharmony_ci if (obj->objectId == i) { 109094332d3Sopenharmony_ci isUse = 1; 110094332d3Sopenharmony_ci break; 111094332d3Sopenharmony_ci } 112094332d3Sopenharmony_ci } 113094332d3Sopenharmony_ci if (isUse == 0) { 114094332d3Sopenharmony_ci break; 115094332d3Sopenharmony_ci } 116094332d3Sopenharmony_ci } 117094332d3Sopenharmony_ci if (i == MAX_LIST) { 118094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d too much device created", __func__, __LINE__); 119094332d3Sopenharmony_ci return -1; 120094332d3Sopenharmony_ci } 121094332d3Sopenharmony_ci devCnt = i; 122094332d3Sopenharmony_ci } 123094332d3Sopenharmony_ci return devCnt; 124094332d3Sopenharmony_ci} 125094332d3Sopenharmony_ci 126094332d3Sopenharmony_cistatic int32_t CreatDev(const char *udcName, struct UsbFnDeviceDesc *des, struct UsbFnDeviceMgr *fnDevMgr) 127094332d3Sopenharmony_ci{ 128094332d3Sopenharmony_ci int32_t ret, devCnt; 129094332d3Sopenharmony_ci struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps(); 130094332d3Sopenharmony_ci devCnt = FindEmptyId(); 131094332d3Sopenharmony_ci if (devCnt < 0) { 132094332d3Sopenharmony_ci return HDF_ERR_IO; 133094332d3Sopenharmony_ci } 134094332d3Sopenharmony_ci 135094332d3Sopenharmony_ci fnDevMgr->fnDev.object.objectId = devCnt; 136094332d3Sopenharmony_ci ret = sprintf_s(fnDevMgr->name, MAX_NAMELEN, "g%d", devCnt); 137094332d3Sopenharmony_ci if (ret < 0) { 138094332d3Sopenharmony_ci return HDF_ERR_IO; 139094332d3Sopenharmony_ci } 140094332d3Sopenharmony_ci ret = strcpy_s(fnDevMgr->udcName, MAX_NAMELEN, udcName); 141094332d3Sopenharmony_ci if (ret != EOK) { 142094332d3Sopenharmony_ci return HDF_ERR_IO; 143094332d3Sopenharmony_ci } 144094332d3Sopenharmony_ci ret = fnOps->createDevice(udcName, fnDevMgr->name, des); 145094332d3Sopenharmony_ci if (ret) { 146094332d3Sopenharmony_ci return HDF_ERR_IO; 147094332d3Sopenharmony_ci } 148094332d3Sopenharmony_ci return 0; 149094332d3Sopenharmony_ci} 150094332d3Sopenharmony_ci 151094332d3Sopenharmony_cistatic uint32_t GetInterfaceNum(struct UsbDescriptorHeader **intf) 152094332d3Sopenharmony_ci{ 153094332d3Sopenharmony_ci uint32_t i; 154094332d3Sopenharmony_ci uint32_t num = 0; 155094332d3Sopenharmony_ci struct UsbInterfaceDescriptor *interface = NULL; 156094332d3Sopenharmony_ci for (i = 0; intf[i] != NULL; i++) { 157094332d3Sopenharmony_ci if (intf[i]->bDescriptorType == USB_DDK_DT_INTERFACE) { 158094332d3Sopenharmony_ci interface = (struct UsbInterfaceDescriptor *)intf[i]; 159094332d3Sopenharmony_ci if (interface->bNumEndpoints > 0) { 160094332d3Sopenharmony_ci num++; 161094332d3Sopenharmony_ci } 162094332d3Sopenharmony_ci } 163094332d3Sopenharmony_ci } 164094332d3Sopenharmony_ci return num; 165094332d3Sopenharmony_ci} 166094332d3Sopenharmony_ci 167094332d3Sopenharmony_cistatic int32_t AllocInterfaceAndFuncMgr(struct UsbFnDeviceMgr *fnDevMgr, struct UsbFnDeviceDesc *des) 168094332d3Sopenharmony_ci{ 169094332d3Sopenharmony_ci uint32_t i, j; 170094332d3Sopenharmony_ci for (i = 0; des->configs[i] != NULL; i++) { 171094332d3Sopenharmony_ci for (j = 0; des->configs[i]->functions[j] != NULL; j++) { 172094332d3Sopenharmony_ci if (strncmp(des->configs[i]->functions[j]->funcName, FUNCTION_GENERIC, strlen(FUNCTION_GENERIC))) { 173094332d3Sopenharmony_ci continue; 174094332d3Sopenharmony_ci } 175094332d3Sopenharmony_ci if (des->configs[i]->functions[j]->enable == false) { 176094332d3Sopenharmony_ci continue; 177094332d3Sopenharmony_ci } 178094332d3Sopenharmony_ci fnDevMgr->numFunc++; 179094332d3Sopenharmony_ci fnDevMgr->fnDev.numInterfaces += GetInterfaceNum(des->configs[i]->functions[j]->fsDescriptors); 180094332d3Sopenharmony_ci } 181094332d3Sopenharmony_ci } 182094332d3Sopenharmony_ci if (fnDevMgr->fnDev.numInterfaces == 0) { 183094332d3Sopenharmony_ci HDF_LOGE("%{public}s functions is null", __func__); 184094332d3Sopenharmony_ci return HDF_DEV_ERR_NO_DEVICE; 185094332d3Sopenharmony_ci } 186094332d3Sopenharmony_ci 187094332d3Sopenharmony_ci fnDevMgr->interfaceMgr = UsbFnMemCalloc(fnDevMgr->fnDev.numInterfaces * sizeof(struct UsbFnInterfaceMgr)); 188094332d3Sopenharmony_ci if (fnDevMgr->interfaceMgr == NULL) { 189094332d3Sopenharmony_ci HDF_LOGE("%{public}s UsbFnMemCalloc failed", __func__); 190094332d3Sopenharmony_ci return HDF_ERR_IO; 191094332d3Sopenharmony_ci } 192094332d3Sopenharmony_ci 193094332d3Sopenharmony_ci fnDevMgr->funcMgr = UsbFnMemCalloc(fnDevMgr->numFunc * sizeof(struct UsbFnFuncMgr)); 194094332d3Sopenharmony_ci if (fnDevMgr->funcMgr == NULL) { 195094332d3Sopenharmony_ci HDF_LOGE("%{public}s UsbFnMemCalloc failed", __func__); 196094332d3Sopenharmony_ci UsbFnMemFree(fnDevMgr->interfaceMgr); 197094332d3Sopenharmony_ci return HDF_ERR_IO; 198094332d3Sopenharmony_ci } 199094332d3Sopenharmony_ci return 0; 200094332d3Sopenharmony_ci} 201094332d3Sopenharmony_ci 202094332d3Sopenharmony_cistatic int32_t StartThreadIo(struct UsbFnDeviceMgr *fnDevMgr); 203094332d3Sopenharmony_ciconst struct UsbFnDeviceMgr *UsbFnMgrDeviceCreate( 204094332d3Sopenharmony_ci const char *udcName, struct UsbFnDeviceDesc *des, const struct DeviceResourceNode *node) 205094332d3Sopenharmony_ci{ 206094332d3Sopenharmony_ci int32_t ret; 207094332d3Sopenharmony_ci 208094332d3Sopenharmony_ci struct UsbFnDeviceMgr *fnDevMgr = NULL; 209094332d3Sopenharmony_ci if (udcName == NULL || des == NULL) { 210094332d3Sopenharmony_ci HDF_LOGE("%{public}s invalid param.", __func__); 211094332d3Sopenharmony_ci return NULL; 212094332d3Sopenharmony_ci } 213094332d3Sopenharmony_ci 214094332d3Sopenharmony_ci fnDevMgr = UsbFnMemCalloc(sizeof(struct UsbFnDeviceMgr)); 215094332d3Sopenharmony_ci if (fnDevMgr == NULL) { 216094332d3Sopenharmony_ci HDF_LOGE("%{public}s UsbFnMemCalloc failed", __func__); 217094332d3Sopenharmony_ci return NULL; 218094332d3Sopenharmony_ci } 219094332d3Sopenharmony_ci 220094332d3Sopenharmony_ci ret = CreatDev(udcName, des, fnDevMgr); 221094332d3Sopenharmony_ci if (ret) { 222094332d3Sopenharmony_ci HDF_LOGE("%{public}s CreatDev failed", __func__); 223094332d3Sopenharmony_ci goto FREE_DEVMGR; 224094332d3Sopenharmony_ci } 225094332d3Sopenharmony_ci if (g_devEntry.next == 0) { 226094332d3Sopenharmony_ci DListHeadInit(&g_devEntry); 227094332d3Sopenharmony_ci } 228094332d3Sopenharmony_ci DListInsertTail(&fnDevMgr->fnDev.object.entry, &g_devEntry); 229094332d3Sopenharmony_ci fnDevMgr->node = node; 230094332d3Sopenharmony_ci fnDevMgr->des = des; 231094332d3Sopenharmony_ci 232094332d3Sopenharmony_ci ret = AllocInterfaceAndFuncMgr(fnDevMgr, des); 233094332d3Sopenharmony_ci if (ret == HDF_DEV_ERR_NO_DEVICE) { 234094332d3Sopenharmony_ci return fnDevMgr; 235094332d3Sopenharmony_ci } else if (ret != 0) { 236094332d3Sopenharmony_ci HDF_LOGE("%{public}s AllocInterfaceAndFuncMgr failed", __func__); 237094332d3Sopenharmony_ci goto FREE_DEVMGR; 238094332d3Sopenharmony_ci } 239094332d3Sopenharmony_ci 240094332d3Sopenharmony_ci CreateInterface(des, fnDevMgr); 241094332d3Sopenharmony_ci fnDevMgr->running = true; 242094332d3Sopenharmony_ci ret = StartThreadIo(fnDevMgr); 243094332d3Sopenharmony_ci if (ret) { 244094332d3Sopenharmony_ci HDF_LOGE("%{public}s: StartThreadIo failed", __func__); 245094332d3Sopenharmony_ci goto FREE_INTF_FUNC_MGR; 246094332d3Sopenharmony_ci } 247094332d3Sopenharmony_ci return fnDevMgr; 248094332d3Sopenharmony_ci 249094332d3Sopenharmony_ciFREE_INTF_FUNC_MGR: 250094332d3Sopenharmony_ci UsbFnMemFree(fnDevMgr->interfaceMgr); 251094332d3Sopenharmony_ci UsbFnMemFree(fnDevMgr->funcMgr); 252094332d3Sopenharmony_ciFREE_DEVMGR: 253094332d3Sopenharmony_ci UsbFnMemFree(fnDevMgr); 254094332d3Sopenharmony_ci return NULL; 255094332d3Sopenharmony_ci} 256094332d3Sopenharmony_ci 257094332d3Sopenharmony_ciint32_t UsbFnMgrDeviceRemove(struct UsbFnDevice *fnDevice) 258094332d3Sopenharmony_ci{ 259094332d3Sopenharmony_ci int32_t ret; 260094332d3Sopenharmony_ci int32_t i = 0; 261094332d3Sopenharmony_ci if (fnDevice == NULL) { 262094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 263094332d3Sopenharmony_ci } 264094332d3Sopenharmony_ci struct UsbFnDeviceMgr *fnDevMgr = (struct UsbFnDeviceMgr *)fnDevice; 265094332d3Sopenharmony_ci struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps(); 266094332d3Sopenharmony_ci 267094332d3Sopenharmony_ci fnDevMgr->running = false; 268094332d3Sopenharmony_ci while (!fnDevMgr->running) { 269094332d3Sopenharmony_ci i++; 270094332d3Sopenharmony_ci OsalMSleep(SLEEP_TIME_OUT); 271094332d3Sopenharmony_ci if (i > SLEEP_TIMES) { 272094332d3Sopenharmony_ci HDF_LOGE("%{public}s: wait thread exit timeout", __func__); 273094332d3Sopenharmony_ci break; 274094332d3Sopenharmony_ci } 275094332d3Sopenharmony_ci } 276094332d3Sopenharmony_ci 277094332d3Sopenharmony_ci ret = OsalThreadDestroy(&fnDevMgr->thread); 278094332d3Sopenharmony_ci if (ret != HDF_SUCCESS) { 279094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d OsalThreadDestroy failed, ret = %{public}d", __func__, __LINE__, ret); 280094332d3Sopenharmony_ci return ret; 281094332d3Sopenharmony_ci } 282094332d3Sopenharmony_ci ret = fnOps->delDevice(fnDevMgr->name, fnDevMgr->udcName, fnDevMgr->des); 283094332d3Sopenharmony_ci if (ret) { 284094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d UsbFnMgrDeviceRemove failed", __func__, __LINE__); 285094332d3Sopenharmony_ci return ret; 286094332d3Sopenharmony_ci } 287094332d3Sopenharmony_ci DListRemove(&fnDevice->object.entry); 288094332d3Sopenharmony_ci UsbFnCfgMgrUnRegisterAllProp(); 289094332d3Sopenharmony_ci 290094332d3Sopenharmony_ci if (fnDevMgr->funcMgr != NULL) { 291094332d3Sopenharmony_ci UsbFnMemFree(fnDevMgr->funcMgr); 292094332d3Sopenharmony_ci fnDevMgr->funcMgr = NULL; 293094332d3Sopenharmony_ci } 294094332d3Sopenharmony_ci if (fnDevMgr->interfaceMgr != NULL) { 295094332d3Sopenharmony_ci UsbFnMemFree(fnDevMgr->interfaceMgr); 296094332d3Sopenharmony_ci fnDevMgr->interfaceMgr = NULL; 297094332d3Sopenharmony_ci } 298094332d3Sopenharmony_ci if (fnDevMgr->node) { 299094332d3Sopenharmony_ci UsbFnCfgMgrFreeUsbFnDeviceDesc(fnDevMgr->des); 300094332d3Sopenharmony_ci fnDevMgr->des = NULL; 301094332d3Sopenharmony_ci } 302094332d3Sopenharmony_ci UsbFnMemFree(fnDevMgr); 303094332d3Sopenharmony_ci fnDevMgr = NULL; 304094332d3Sopenharmony_ci return 0; 305094332d3Sopenharmony_ci} 306094332d3Sopenharmony_ci 307094332d3Sopenharmony_ciconst struct UsbFnDeviceMgr *UsbFnMgrDeviceGet(const char *udcName) 308094332d3Sopenharmony_ci{ 309094332d3Sopenharmony_ci if (udcName == NULL) { 310094332d3Sopenharmony_ci HDF_LOGE("%{public}s invalid param.", __func__); 311094332d3Sopenharmony_ci return NULL; 312094332d3Sopenharmony_ci } 313094332d3Sopenharmony_ci if (g_devEntry.next == 0 || DListIsEmpty(&g_devEntry)) { 314094332d3Sopenharmony_ci HDF_LOGE("%{public}s no device created", __func__); 315094332d3Sopenharmony_ci return NULL; 316094332d3Sopenharmony_ci } 317094332d3Sopenharmony_ci 318094332d3Sopenharmony_ci struct UsbObject *obj = NULL; 319094332d3Sopenharmony_ci struct UsbObject *temp = NULL; 320094332d3Sopenharmony_ci DLIST_FOR_EACH_ENTRY_SAFE(obj, temp, &g_devEntry, struct UsbObject, entry) { 321094332d3Sopenharmony_ci struct UsbFnDeviceMgr *fnDevMgr = (struct UsbFnDeviceMgr *)obj; 322094332d3Sopenharmony_ci if (strcmp(udcName, fnDevMgr->udcName) == 0) { 323094332d3Sopenharmony_ci return fnDevMgr; 324094332d3Sopenharmony_ci } 325094332d3Sopenharmony_ci } 326094332d3Sopenharmony_ci return NULL; 327094332d3Sopenharmony_ci} 328094332d3Sopenharmony_ci 329094332d3Sopenharmony_ciint32_t UsbFnMgrDeviceGetState(struct UsbFnDevice *fnDevice, UsbFnDeviceState *devState) 330094332d3Sopenharmony_ci{ 331094332d3Sopenharmony_ci if (fnDevice == NULL || devState == NULL) { 332094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d invalid param.", __func__, __LINE__); 333094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 334094332d3Sopenharmony_ci } 335094332d3Sopenharmony_ci struct UsbFnDeviceMgr *fnDevMgr = (struct UsbFnDeviceMgr *)fnDevice; 336094332d3Sopenharmony_ci *devState = fnDevMgr->devState; 337094332d3Sopenharmony_ci return 0; 338094332d3Sopenharmony_ci} 339094332d3Sopenharmony_ci 340094332d3Sopenharmony_ciconst struct UsbFnInterfaceMgr *UsbFnMgrDeviceGetInterface(struct UsbFnDevice *fnDevice, uint8_t interfaceIndex) 341094332d3Sopenharmony_ci{ 342094332d3Sopenharmony_ci if (fnDevice == NULL) { 343094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d fnDevice is null", __func__, __LINE__); 344094332d3Sopenharmony_ci return NULL; 345094332d3Sopenharmony_ci } 346094332d3Sopenharmony_ci struct UsbFnDeviceMgr *fnDevMgr = (struct UsbFnDeviceMgr *)fnDevice; 347094332d3Sopenharmony_ci if (interfaceIndex >= fnDevMgr->fnDev.numInterfaces) { 348094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d invalid param.", __func__, __LINE__); 349094332d3Sopenharmony_ci return NULL; 350094332d3Sopenharmony_ci } 351094332d3Sopenharmony_ci return &(fnDevMgr->interfaceMgr[interfaceIndex]); 352094332d3Sopenharmony_ci} 353094332d3Sopenharmony_ci 354094332d3Sopenharmony_cistatic void CollectEventHandle(struct UsbFnEventAll *event, struct UsbFnDeviceMgr *devMgr) 355094332d3Sopenharmony_ci{ 356094332d3Sopenharmony_ci uint8_t i, j; 357094332d3Sopenharmony_ci struct UsbFnFuncMgr *funcMgr = NULL; 358094332d3Sopenharmony_ci struct UsbFnInterfaceMgr *intfMgr = NULL; 359094332d3Sopenharmony_ci struct UsbHandleMgr *handle = NULL; 360094332d3Sopenharmony_ci event->ep0Num = 0; 361094332d3Sopenharmony_ci event->epNum = 0; 362094332d3Sopenharmony_ci for (i = 0; i < devMgr->numFunc; i++) { 363094332d3Sopenharmony_ci funcMgr = devMgr->funcMgr + i; 364094332d3Sopenharmony_ci 365094332d3Sopenharmony_ci if (funcMgr->fd > 0 && funcMgr->callback != NULL) { 366094332d3Sopenharmony_ci event->ep0[event->ep0Num] = funcMgr->fd; 367094332d3Sopenharmony_ci event->ep0Event[event->ep0Num].type = USB_EP0_INVALID; 368094332d3Sopenharmony_ci event->ep0Num++; 369094332d3Sopenharmony_ci } 370094332d3Sopenharmony_ci } 371094332d3Sopenharmony_ci for (i = 0; i < devMgr->fnDev.numInterfaces; i++) { 372094332d3Sopenharmony_ci intfMgr = devMgr->interfaceMgr + i; 373094332d3Sopenharmony_ci if (intfMgr == NULL || intfMgr->isOpen == false || intfMgr->handle == NULL) { 374094332d3Sopenharmony_ci continue; 375094332d3Sopenharmony_ci } 376094332d3Sopenharmony_ci handle = intfMgr->handle; 377094332d3Sopenharmony_ci for (j = 0; j < handle->numFd; j++) { 378094332d3Sopenharmony_ci if (handle->fds[j] <= 0) { 379094332d3Sopenharmony_ci continue; 380094332d3Sopenharmony_ci } 381094332d3Sopenharmony_ci event->epx[event->epNum] = handle->fds[j]; 382094332d3Sopenharmony_ci event->reqEvent[event->epNum] = handle->reqEvent[j]; 383094332d3Sopenharmony_ci event->numEvent[event->epNum] = 0; 384094332d3Sopenharmony_ci event->epNum++; 385094332d3Sopenharmony_ci } 386094332d3Sopenharmony_ci } 387094332d3Sopenharmony_ci} 388094332d3Sopenharmony_ci 389094332d3Sopenharmony_cistatic void HandleEp0IoEvent(const struct UsbFnFuncMgr *funcMgr, const struct UsbFnReqEvent *reqEvent) 390094332d3Sopenharmony_ci{ 391094332d3Sopenharmony_ci struct ReqList *reqList = NULL; 392094332d3Sopenharmony_ci struct ReqList *temp = NULL; 393094332d3Sopenharmony_ci 394094332d3Sopenharmony_ci DLIST_FOR_EACH_ENTRY_SAFE(reqList, temp, &funcMgr->reqEntry, struct ReqList, entry) { 395094332d3Sopenharmony_ci if (reqList->buf == reqEvent->buf) { 396094332d3Sopenharmony_ci HDF_LOGD("%{public}s: req.actual = %{public}d", __func__, reqList->req.actual); 397094332d3Sopenharmony_ci reqList->req.actual = reqEvent->actual; 398094332d3Sopenharmony_ci reqList->req.status = -reqEvent->status; 399094332d3Sopenharmony_ci if (reqList->req.complete) { 400094332d3Sopenharmony_ci reqList->req.complete(reqList->pipe, &reqList->req); 401094332d3Sopenharmony_ci } else { 402094332d3Sopenharmony_ci HDF_LOGE("no complete callback find"); 403094332d3Sopenharmony_ci } 404094332d3Sopenharmony_ci break; 405094332d3Sopenharmony_ci } 406094332d3Sopenharmony_ci } 407094332d3Sopenharmony_ci} 408094332d3Sopenharmony_ci 409094332d3Sopenharmony_cistatic void HandleEp0CtrlEvent(const struct UsbFnFuncMgr *funcMgr, struct UsbFnCtrlEvent *ctrlEvent) 410094332d3Sopenharmony_ci{ 411094332d3Sopenharmony_ci struct UsbFnDeviceMgr *devMgr = (struct UsbFnDeviceMgr *)funcMgr->object; 412094332d3Sopenharmony_ci struct UsbFnEvent fnEvnet; 413094332d3Sopenharmony_ci if (((funcMgr->eventMask) & (1 << ctrlEvent->type)) == 0) { 414094332d3Sopenharmony_ci return; 415094332d3Sopenharmony_ci } 416094332d3Sopenharmony_ci fnEvnet.setup = &ctrlEvent->u.setup; 417094332d3Sopenharmony_ci fnEvnet.type = ctrlEvent->type; 418094332d3Sopenharmony_ci fnEvnet.context = funcMgr->context; 419094332d3Sopenharmony_ci devMgr->devState = ctrlEvent->type; 420094332d3Sopenharmony_ci if (funcMgr->callback) { 421094332d3Sopenharmony_ci funcMgr->callback(&fnEvnet); 422094332d3Sopenharmony_ci } else { 423094332d3Sopenharmony_ci HDF_LOGE("%{public}s: no callback find event=%{public}d", __func__, fnEvnet.type); 424094332d3Sopenharmony_ci } 425094332d3Sopenharmony_ci} 426094332d3Sopenharmony_ci 427094332d3Sopenharmony_cistatic void HandleEpsIoEvent(const struct UsbFnReqEvent *reqEvent, const struct UsbHandleMgr *handle) 428094332d3Sopenharmony_ci{ 429094332d3Sopenharmony_ci struct ReqList *reqList = NULL; 430094332d3Sopenharmony_ci struct ReqList *temp = NULL; 431094332d3Sopenharmony_ci DLIST_FOR_EACH_ENTRY_SAFE(reqList, temp, &handle->reqEntry, struct ReqList, entry) { 432094332d3Sopenharmony_ci if (reqList->buf == reqEvent->buf) { 433094332d3Sopenharmony_ci reqList->req.actual = reqEvent->actual; 434094332d3Sopenharmony_ci reqList->req.status = -reqEvent->status; 435094332d3Sopenharmony_ci if (reqList->req.complete) { 436094332d3Sopenharmony_ci reqList->req.complete(reqList->pipe, &reqList->req); 437094332d3Sopenharmony_ci } else { 438094332d3Sopenharmony_ci HDF_LOGE("no complete callback find"); 439094332d3Sopenharmony_ci } 440094332d3Sopenharmony_ci break; 441094332d3Sopenharmony_ci } 442094332d3Sopenharmony_ci } 443094332d3Sopenharmony_ci} 444094332d3Sopenharmony_ci 445094332d3Sopenharmony_cistatic struct UsbFnFuncMgr *GetFuncMgr(const struct UsbFnDeviceMgr *devMgr, int32_t ep0) 446094332d3Sopenharmony_ci{ 447094332d3Sopenharmony_ci uint8_t i; 448094332d3Sopenharmony_ci 449094332d3Sopenharmony_ci if (devMgr == NULL) { 450094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d devMgr is null.", __func__, __LINE__); 451094332d3Sopenharmony_ci return NULL; 452094332d3Sopenharmony_ci } 453094332d3Sopenharmony_ci struct UsbFnFuncMgr *funcMgr = NULL; 454094332d3Sopenharmony_ci for (i = 0; i < devMgr->numFunc; i++) { 455094332d3Sopenharmony_ci funcMgr = devMgr->funcMgr + i; 456094332d3Sopenharmony_ci if (funcMgr->fd == ep0) { 457094332d3Sopenharmony_ci break; 458094332d3Sopenharmony_ci } 459094332d3Sopenharmony_ci } 460094332d3Sopenharmony_ci return funcMgr; 461094332d3Sopenharmony_ci} 462094332d3Sopenharmony_ci 463094332d3Sopenharmony_cistatic struct UsbHandleMgr *GetHandleMgr(const struct UsbFnDeviceMgr *devMgr, int32_t epx) 464094332d3Sopenharmony_ci{ 465094332d3Sopenharmony_ci uint8_t i, j; 466094332d3Sopenharmony_ci struct UsbHandleMgr *handle = NULL; 467094332d3Sopenharmony_ci struct UsbFnInterfaceMgr *intfMgr = NULL; 468094332d3Sopenharmony_ci 469094332d3Sopenharmony_ci if (devMgr == NULL) { 470094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d devMgr is null.", __func__, __LINE__); 471094332d3Sopenharmony_ci return NULL; 472094332d3Sopenharmony_ci } 473094332d3Sopenharmony_ci for (i = 0; i < devMgr->fnDev.numInterfaces; i++) { 474094332d3Sopenharmony_ci intfMgr = devMgr->interfaceMgr + i; 475094332d3Sopenharmony_ci if (!intfMgr->isOpen) { 476094332d3Sopenharmony_ci continue; 477094332d3Sopenharmony_ci } 478094332d3Sopenharmony_ci handle = intfMgr->handle; 479094332d3Sopenharmony_ci for (j = 0; j < handle->numFd; j++) { 480094332d3Sopenharmony_ci if (epx == handle->fds[j]) { 481094332d3Sopenharmony_ci return handle; 482094332d3Sopenharmony_ci } 483094332d3Sopenharmony_ci } 484094332d3Sopenharmony_ci } 485094332d3Sopenharmony_ci return handle; 486094332d3Sopenharmony_ci} 487094332d3Sopenharmony_ci 488094332d3Sopenharmony_cistatic void HandleEp0Event(const struct UsbFnDeviceMgr *devMgr, struct UsbFnEventAll event) 489094332d3Sopenharmony_ci{ 490094332d3Sopenharmony_ci uint8_t i; 491094332d3Sopenharmony_ci struct UsbFnFuncMgr *funcMgr = NULL; 492094332d3Sopenharmony_ci for (i = 0; i < event.ep0Num; i++) { 493094332d3Sopenharmony_ci funcMgr = GetFuncMgr(devMgr, event.ep0[i]); 494094332d3Sopenharmony_ci if (funcMgr == NULL) { 495094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d GetFuncMgr failed.", __func__, __LINE__); 496094332d3Sopenharmony_ci return; 497094332d3Sopenharmony_ci } 498094332d3Sopenharmony_ci if (event.ep0Event[i].type == USB_EP0_CTRL_EVENT) { 499094332d3Sopenharmony_ci HandleEp0CtrlEvent(funcMgr, &event.ep0Event[i].ctrlEvent); 500094332d3Sopenharmony_ci } else if (event.ep0Event[i].type == USB_EP0_IO_COMPLETED) { 501094332d3Sopenharmony_ci HandleEp0IoEvent(funcMgr, &event.ep0Event[i].reqEvent); 502094332d3Sopenharmony_ci } 503094332d3Sopenharmony_ci } 504094332d3Sopenharmony_ci} 505094332d3Sopenharmony_ci 506094332d3Sopenharmony_cistatic int32_t UsbFnEventProcess(void *arg) 507094332d3Sopenharmony_ci{ 508094332d3Sopenharmony_ci struct UsbFnDeviceMgr *devMgr = (struct UsbFnDeviceMgr *)arg; 509094332d3Sopenharmony_ci struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps(); 510094332d3Sopenharmony_ci struct UsbFnEventAll event; 511094332d3Sopenharmony_ci struct UsbHandleMgr *handle = NULL; 512094332d3Sopenharmony_ci int32_t timeout = SLEEP_TIME_OUT; 513094332d3Sopenharmony_ci 514094332d3Sopenharmony_ci while (true) { 515094332d3Sopenharmony_ci if (devMgr == NULL || !devMgr->running) { 516094332d3Sopenharmony_ci break; 517094332d3Sopenharmony_ci } 518094332d3Sopenharmony_ci if (memset_s(&event, sizeof(event), 0, sizeof(event)) != EOK) { 519094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d memset_s failed", __func__, __LINE__); 520094332d3Sopenharmony_ci return HDF_FAILURE; 521094332d3Sopenharmony_ci } 522094332d3Sopenharmony_ci 523094332d3Sopenharmony_ci CollectEventHandle(&event, devMgr); 524094332d3Sopenharmony_ci if (event.ep0Num + event.epNum == 0) { 525094332d3Sopenharmony_ci continue; 526094332d3Sopenharmony_ci } 527094332d3Sopenharmony_ci int32_t ret = fnOps->pollEvent(&event, timeout); 528094332d3Sopenharmony_ci if (ret != 0) { 529094332d3Sopenharmony_ci if (devMgr == NULL || !devMgr->running) { 530094332d3Sopenharmony_ci break; 531094332d3Sopenharmony_ci } 532094332d3Sopenharmony_ci OsalMSleep(1); 533094332d3Sopenharmony_ci continue; 534094332d3Sopenharmony_ci } 535094332d3Sopenharmony_ci HandleEp0Event(devMgr, event); 536094332d3Sopenharmony_ci for (uint8_t i = 0; i < event.epNum; i++) { 537094332d3Sopenharmony_ci handle = GetHandleMgr(devMgr, event.epx[i]); 538094332d3Sopenharmony_ci if (handle == NULL) { 539094332d3Sopenharmony_ci continue; 540094332d3Sopenharmony_ci } 541094332d3Sopenharmony_ci for (uint8_t j = 0; j < event.numEvent[i]; j++) { 542094332d3Sopenharmony_ci HandleEpsIoEvent(&event.reqEvent[i][j], handle); 543094332d3Sopenharmony_ci } 544094332d3Sopenharmony_ci } 545094332d3Sopenharmony_ci } 546094332d3Sopenharmony_ci if (devMgr) { 547094332d3Sopenharmony_ci devMgr->running = true; 548094332d3Sopenharmony_ci } 549094332d3Sopenharmony_ci HDF_LOGI("%{public}s, exit", __func__); 550094332d3Sopenharmony_ci return 0; 551094332d3Sopenharmony_ci} 552094332d3Sopenharmony_ci 553094332d3Sopenharmony_cistatic int32_t StartThreadIo(struct UsbFnDeviceMgr *fnDevMgr) 554094332d3Sopenharmony_ci{ 555094332d3Sopenharmony_ci int32_t ret; 556094332d3Sopenharmony_ci struct OsalThreadParam threadCfg; 557094332d3Sopenharmony_ci ret = memset_s(&threadCfg, sizeof(threadCfg), 0, sizeof(threadCfg)); 558094332d3Sopenharmony_ci if (ret != EOK) { 559094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d memset_s failed", __func__, __LINE__); 560094332d3Sopenharmony_ci return ret; 561094332d3Sopenharmony_ci } 562094332d3Sopenharmony_ci threadCfg.name = "usbfn process"; 563094332d3Sopenharmony_ci threadCfg.priority = OSAL_THREAD_PRI_LOW; 564094332d3Sopenharmony_ci threadCfg.stackSize = HDF_PROCESS_STACK_SIZE; 565094332d3Sopenharmony_ci 566094332d3Sopenharmony_ci ret = OsalThreadCreate(&fnDevMgr->thread, (OsalThreadEntry)UsbFnEventProcess, (void *)fnDevMgr); 567094332d3Sopenharmony_ci if (ret != HDF_SUCCESS) { 568094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d OsalThreadCreate failed, ret = %{public}d ", __func__, __LINE__, ret); 569094332d3Sopenharmony_ci return HDF_ERR_DEVICE_BUSY; 570094332d3Sopenharmony_ci } 571094332d3Sopenharmony_ci HDF_LOGD("%{public}s: Usb device OsalThreadCreate", __func__); 572094332d3Sopenharmony_ci ret = OsalThreadStart(&fnDevMgr->thread, &threadCfg); 573094332d3Sopenharmony_ci if (ret != HDF_SUCCESS) { 574094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d OsalThreadStart failed, ret = %{public}d ", __func__, __LINE__, ret); 575094332d3Sopenharmony_ci return HDF_ERR_DEVICE_BUSY; 576094332d3Sopenharmony_ci } 577094332d3Sopenharmony_ci return 0; 578094332d3Sopenharmony_ci} 579094332d3Sopenharmony_ci 580094332d3Sopenharmony_ciint32_t UsbFnMgrStartRecvEvent( 581094332d3Sopenharmony_ci struct UsbFnInterface *interface, uint32_t eventMask, UsbFnEventCallback callback, void *context) 582094332d3Sopenharmony_ci{ 583094332d3Sopenharmony_ci struct UsbFnInterfaceMgr *interfaceMgr = (struct UsbFnInterfaceMgr *)interface; 584094332d3Sopenharmony_ci struct UsbFnFuncMgr *funcMgr = interfaceMgr->funcMgr; 585094332d3Sopenharmony_ci if (funcMgr->callback != NULL) { 586094332d3Sopenharmony_ci HDF_LOGE("%{public}s: callback has Register", __func__); 587094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 588094332d3Sopenharmony_ci } 589094332d3Sopenharmony_ci funcMgr->context = context; 590094332d3Sopenharmony_ci funcMgr->eventMask = eventMask; 591094332d3Sopenharmony_ci funcMgr->callback = callback; 592094332d3Sopenharmony_ci if (funcMgr->fd <= 0) { 593094332d3Sopenharmony_ci int32_t ret = OpenEp0AndMapAddr(funcMgr); 594094332d3Sopenharmony_ci if (ret != HDF_SUCCESS) { 595094332d3Sopenharmony_ci HDF_LOGE("%{public}s: OpenEp0AndMapAddr failed, ret = %{public}d ", __func__, ret); 596094332d3Sopenharmony_ci return HDF_ERR_IO; 597094332d3Sopenharmony_ci } 598094332d3Sopenharmony_ci } 599094332d3Sopenharmony_ci return 0; 600094332d3Sopenharmony_ci} 601094332d3Sopenharmony_ci 602094332d3Sopenharmony_ciint32_t UsbFnStopRecvEvent(struct UsbFnInterface *interface) 603094332d3Sopenharmony_ci{ 604094332d3Sopenharmony_ci int32_t ret; 605094332d3Sopenharmony_ci struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps(); 606094332d3Sopenharmony_ci struct UsbFnInterfaceMgr *interfaceMgr = (struct UsbFnInterfaceMgr *)interface; 607094332d3Sopenharmony_ci struct UsbFnFuncMgr *funcMgr = interfaceMgr->funcMgr; 608094332d3Sopenharmony_ci ret = fnOps->queueDel(funcMgr->fd); 609094332d3Sopenharmony_ci if (ret) { 610094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d queueDel failed, ret = %{public}d ", __func__, __LINE__, ret); 611094332d3Sopenharmony_ci return HDF_ERR_DEVICE_BUSY; 612094332d3Sopenharmony_ci } 613094332d3Sopenharmony_ci ret = fnOps->closePipe(funcMgr->fd); 614094332d3Sopenharmony_ci if (ret) { 615094332d3Sopenharmony_ci HDF_LOGE("%{public}s:%{public}d closePipe failed, ret = %{public}d ", __func__, __LINE__, ret); 616094332d3Sopenharmony_ci return HDF_ERR_DEVICE_BUSY; 617094332d3Sopenharmony_ci } 618094332d3Sopenharmony_ci funcMgr->fd = -1; 619094332d3Sopenharmony_ci funcMgr->callback = NULL; 620094332d3Sopenharmony_ci return 0; 621094332d3Sopenharmony_ci} 622