1094332d3Sopenharmony_ci/* 2094332d3Sopenharmony_ci * Copyright (c) 2021 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_cfg_mgr.h" 17094332d3Sopenharmony_ci#include "usbfn_dev_mgr.h" 18094332d3Sopenharmony_ci#include "usbfn_device.h" 19094332d3Sopenharmony_ci#include "usbfn_interface.h" 20094332d3Sopenharmony_ci#include "usbfn_io_mgr.h" 21094332d3Sopenharmony_ci#include "usbfn_request.h" 22094332d3Sopenharmony_ci#include "usbd_wrapper.h" 23094332d3Sopenharmony_ci 24094332d3Sopenharmony_ci#define HDF_LOG_TAG usbfn_sdk_if 25094332d3Sopenharmony_ci 26094332d3Sopenharmony_cistatic struct UsbDeviceFunctionsInfo g_functionsInfo[] = { 27094332d3Sopenharmony_ci {"f_generic.a", 1 }, 28094332d3Sopenharmony_ci {"f_generic.e", 1 << 1}, 29094332d3Sopenharmony_ci {"f_generic.mtp", 1 << 3}, 30094332d3Sopenharmony_ci {"f_generic.ptp", 1 << 4}, 31094332d3Sopenharmony_ci {NULL, 0 }, 32094332d3Sopenharmony_ci}; 33094332d3Sopenharmony_ci 34094332d3Sopenharmony_cistatic int32_t IsDescriptorOk(struct UsbFnDeviceDesc *des) 35094332d3Sopenharmony_ci{ 36094332d3Sopenharmony_ci int32_t i, j; 37094332d3Sopenharmony_ci struct UsbFnStrings **strings = NULL; 38094332d3Sopenharmony_ci struct UsbFnFunction *functions = NULL; 39094332d3Sopenharmony_ci if (des == NULL) { 40094332d3Sopenharmony_ci HDF_LOGE("%{public}s: des null", __func__); 41094332d3Sopenharmony_ci goto ERR_DES; 42094332d3Sopenharmony_ci } 43094332d3Sopenharmony_ci if (des->deviceDesc == NULL || des->deviceStrings == NULL || des->configs == NULL) { 44094332d3Sopenharmony_ci HDF_LOGE("%{public}s: deviceDesc deviceStrings configs null", __func__); 45094332d3Sopenharmony_ci goto ERR_DES; 46094332d3Sopenharmony_ci } 47094332d3Sopenharmony_ci 48094332d3Sopenharmony_ci strings = des->deviceStrings; 49094332d3Sopenharmony_ci if (strings[0] == NULL) { 50094332d3Sopenharmony_ci HDF_LOGE("%{public}s: strings null", __func__); 51094332d3Sopenharmony_ci goto ERR_DES; 52094332d3Sopenharmony_ci } 53094332d3Sopenharmony_ci 54094332d3Sopenharmony_ci for (i = 0; des->configs[i] != NULL; i++) { 55094332d3Sopenharmony_ci for (j = 0; des->configs[i]->functions[j] != NULL; j++) { 56094332d3Sopenharmony_ci functions = des->configs[i]->functions[j]; 57094332d3Sopenharmony_ci if (strncmp(functions->funcName, FUNCTION_GENERIC, strlen(FUNCTION_GENERIC)) != 0) { 58094332d3Sopenharmony_ci continue; 59094332d3Sopenharmony_ci } 60094332d3Sopenharmony_ci if (functions->fsDescriptors == NULL) { 61094332d3Sopenharmony_ci HDF_LOGE("%{public}s: fsDescriptors null", __func__); 62094332d3Sopenharmony_ci goto ERR_DES; 63094332d3Sopenharmony_ci } 64094332d3Sopenharmony_ci } 65094332d3Sopenharmony_ci } 66094332d3Sopenharmony_ci if (i == 0 || j == 0) { 67094332d3Sopenharmony_ci HDF_LOGE("%{public}s: configs functions null", __func__); 68094332d3Sopenharmony_ci goto ERR_DES; 69094332d3Sopenharmony_ci } 70094332d3Sopenharmony_ci 71094332d3Sopenharmony_ci return 0; 72094332d3Sopenharmony_ciERR_DES: 73094332d3Sopenharmony_ci HDF_LOGE("%{public}s: DeviceDesc bad", __func__); 74094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 75094332d3Sopenharmony_ci} 76094332d3Sopenharmony_ci 77094332d3Sopenharmony_cistatic void DoChangeFunction(struct UsbFnFunction * const function, struct UsbFnDescriptorData * const descriptor) 78094332d3Sopenharmony_ci{ 79094332d3Sopenharmony_ci uint32_t i; 80094332d3Sopenharmony_ci struct UsbDeviceFunctionsInfo *funcInfo = g_functionsInfo; 81094332d3Sopenharmony_ci for (i = 0; funcInfo[i].functionName != NULL; i++) { 82094332d3Sopenharmony_ci if (strncmp(function->funcName, funcInfo[i].functionName, strlen(funcInfo[i].functionName)) == 0) { 83094332d3Sopenharmony_ci if ((descriptor->functionMask & funcInfo[i].numberMask) != 0) { 84094332d3Sopenharmony_ci function->enable = true; 85094332d3Sopenharmony_ci HDF_LOGI("%{public}s: enable function = %{public}s", __func__, funcInfo[i].functionName); 86094332d3Sopenharmony_ci } else { 87094332d3Sopenharmony_ci function->enable = false; 88094332d3Sopenharmony_ci HDF_LOGI("%{public}s: disable function = %{public}s", __func__, funcInfo[i].functionName); 89094332d3Sopenharmony_ci } 90094332d3Sopenharmony_ci } 91094332d3Sopenharmony_ci } 92094332d3Sopenharmony_ci} 93094332d3Sopenharmony_ci 94094332d3Sopenharmony_cistatic void UsbFnChangeFunction(struct UsbFnDeviceDesc * const des, struct UsbFnDescriptorData * const descriptor) 95094332d3Sopenharmony_ci{ 96094332d3Sopenharmony_ci uint32_t i; 97094332d3Sopenharmony_ci uint32_t j; 98094332d3Sopenharmony_ci if (des == NULL || descriptor == NULL) { 99094332d3Sopenharmony_ci HDF_LOGE("%{public}s: param is null", __func__); 100094332d3Sopenharmony_ci return; 101094332d3Sopenharmony_ci } 102094332d3Sopenharmony_ci for (i = 0; des->configs[i] != NULL; i++) { 103094332d3Sopenharmony_ci for (j = 0; des->configs[i]->functions[j] != NULL; j++) { 104094332d3Sopenharmony_ci DoChangeFunction(des->configs[i]->functions[j], descriptor); 105094332d3Sopenharmony_ci } 106094332d3Sopenharmony_ci } 107094332d3Sopenharmony_ci} 108094332d3Sopenharmony_ci 109094332d3Sopenharmony_ciconst struct UsbFnDevice *UsbFnCreateDevice(const char *udcName, struct UsbFnDescriptorData *descriptor) 110094332d3Sopenharmony_ci{ 111094332d3Sopenharmony_ci int32_t ret; 112094332d3Sopenharmony_ci const struct DeviceResourceNode *property = NULL; 113094332d3Sopenharmony_ci struct UsbFnDeviceDesc *des = NULL; 114094332d3Sopenharmony_ci 115094332d3Sopenharmony_ci if (udcName == NULL || descriptor == NULL) { 116094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 117094332d3Sopenharmony_ci return NULL; 118094332d3Sopenharmony_ci } 119094332d3Sopenharmony_ci if (UsbFnMgrDeviceGet(udcName) != NULL) { 120094332d3Sopenharmony_ci HDF_LOGE("%{public}s: udc %{public}s haved create", __func__, udcName); 121094332d3Sopenharmony_ci return NULL; 122094332d3Sopenharmony_ci } 123094332d3Sopenharmony_ci HDF_LOGD("%{public}s: type=%{public}d, fMask=%{public}d", __func__, descriptor->type, descriptor->functionMask); 124094332d3Sopenharmony_ci if (descriptor->type == USBFN_DESC_DATA_TYPE_PROP) { 125094332d3Sopenharmony_ci property = descriptor->property; 126094332d3Sopenharmony_ci HDF_LOGD("%{public}s: use descriptor in HCS", __func__); 127094332d3Sopenharmony_ci des = UsbFnCfgMgrGetInstanceFromHCS(property); 128094332d3Sopenharmony_ci if (des == NULL) { 129094332d3Sopenharmony_ci HDF_LOGE("%{public}s: get descriptors from HCS failed", __func__); 130094332d3Sopenharmony_ci return NULL; 131094332d3Sopenharmony_ci } 132094332d3Sopenharmony_ci } else { 133094332d3Sopenharmony_ci des = descriptor->descriptor; 134094332d3Sopenharmony_ci } 135094332d3Sopenharmony_ci UsbFnChangeFunction(des, descriptor); 136094332d3Sopenharmony_ci ret = IsDescriptorOk(des); 137094332d3Sopenharmony_ci if (ret) { 138094332d3Sopenharmony_ci return NULL; 139094332d3Sopenharmony_ci } 140094332d3Sopenharmony_ci 141094332d3Sopenharmony_ci return (struct UsbFnDevice *)UsbFnMgrDeviceCreate(udcName, des, property); 142094332d3Sopenharmony_ci} 143094332d3Sopenharmony_ci 144094332d3Sopenharmony_ciint32_t UsbFnRemoveDevice(struct UsbFnDevice *fnDevice) 145094332d3Sopenharmony_ci{ 146094332d3Sopenharmony_ci if (fnDevice == NULL) { 147094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 148094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 149094332d3Sopenharmony_ci } 150094332d3Sopenharmony_ci return UsbFnMgrDeviceRemove(fnDevice); 151094332d3Sopenharmony_ci} 152094332d3Sopenharmony_ci 153094332d3Sopenharmony_ciconst struct UsbFnDevice *UsbFnGetDevice(const char *udcName) 154094332d3Sopenharmony_ci{ 155094332d3Sopenharmony_ci if (udcName == NULL) { 156094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 157094332d3Sopenharmony_ci return NULL; 158094332d3Sopenharmony_ci } 159094332d3Sopenharmony_ci return (struct UsbFnDevice *)UsbFnMgrDeviceGet((const char *)udcName); 160094332d3Sopenharmony_ci} 161094332d3Sopenharmony_ci 162094332d3Sopenharmony_ciint32_t UsbFnGetDeviceState(struct UsbFnDevice *fnDevice, UsbFnDeviceState *devState) 163094332d3Sopenharmony_ci{ 164094332d3Sopenharmony_ci if (fnDevice == NULL || devState == NULL) { 165094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 166094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 167094332d3Sopenharmony_ci } 168094332d3Sopenharmony_ci return UsbFnMgrDeviceGetState(fnDevice, devState); 169094332d3Sopenharmony_ci} 170094332d3Sopenharmony_ci 171094332d3Sopenharmony_ciconst struct UsbFnInterface *UsbFnGetInterface(struct UsbFnDevice *fnDevice, uint8_t interfaceIndex) 172094332d3Sopenharmony_ci{ 173094332d3Sopenharmony_ci if (fnDevice == NULL) { 174094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 175094332d3Sopenharmony_ci return NULL; 176094332d3Sopenharmony_ci } 177094332d3Sopenharmony_ci return (struct UsbFnInterface *)UsbFnMgrDeviceGetInterface(fnDevice, interfaceIndex); 178094332d3Sopenharmony_ci} 179094332d3Sopenharmony_ci 180094332d3Sopenharmony_ciint32_t UsbFnStartRecvInterfaceEvent( 181094332d3Sopenharmony_ci struct UsbFnInterface *interface, uint32_t eventMask, UsbFnEventCallback callback, void *context) 182094332d3Sopenharmony_ci{ 183094332d3Sopenharmony_ci if (interface == NULL || eventMask == 0 || callback == NULL) { 184094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID_PARAM", __func__); 185094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 186094332d3Sopenharmony_ci } 187094332d3Sopenharmony_ci return UsbFnMgrStartRecvEvent(interface, eventMask, callback, context); 188094332d3Sopenharmony_ci} 189094332d3Sopenharmony_ci 190094332d3Sopenharmony_ciint32_t UsbFnStopRecvInterfaceEvent(struct UsbFnInterface *interface) 191094332d3Sopenharmony_ci{ 192094332d3Sopenharmony_ci if (interface == NULL) { 193094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 194094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 195094332d3Sopenharmony_ci } 196094332d3Sopenharmony_ci return UsbFnStopRecvEvent(interface); 197094332d3Sopenharmony_ci} 198094332d3Sopenharmony_ci 199094332d3Sopenharmony_ciUsbFnInterfaceHandle UsbFnOpenInterface(struct UsbFnInterface *interface) 200094332d3Sopenharmony_ci{ 201094332d3Sopenharmony_ci if (interface == NULL) { 202094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 203094332d3Sopenharmony_ci return NULL; 204094332d3Sopenharmony_ci } 205094332d3Sopenharmony_ci return (UsbFnInterfaceHandle)UsbFnIoMgrInterfaceOpen(interface); 206094332d3Sopenharmony_ci} 207094332d3Sopenharmony_ci 208094332d3Sopenharmony_ciint32_t UsbFnCloseInterface(UsbFnInterfaceHandle handle) 209094332d3Sopenharmony_ci{ 210094332d3Sopenharmony_ci if (handle == NULL) { 211094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 212094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 213094332d3Sopenharmony_ci } 214094332d3Sopenharmony_ci return UsbFnIoMgrInterfaceClose((struct UsbHandleMgr *)handle); 215094332d3Sopenharmony_ci} 216094332d3Sopenharmony_ci 217094332d3Sopenharmony_ciint32_t UsbFnGetInterfacePipeInfo(struct UsbFnInterface *interface, uint8_t pipeId, struct UsbFnPipeInfo *info) 218094332d3Sopenharmony_ci{ 219094332d3Sopenharmony_ci if (info == NULL || interface == NULL) { 220094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 221094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 222094332d3Sopenharmony_ci } 223094332d3Sopenharmony_ci return UsbFnIoMgrInterfaceGetPipeInfo(interface, pipeId, info); 224094332d3Sopenharmony_ci} 225094332d3Sopenharmony_ci 226094332d3Sopenharmony_ciint32_t UsbFnRegistInterfaceProp(const struct UsbFnInterface *interface, const struct UsbFnRegistInfo *registInfo) 227094332d3Sopenharmony_ci{ 228094332d3Sopenharmony_ci if (registInfo == NULL || interface == NULL) { 229094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 230094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 231094332d3Sopenharmony_ci } 232094332d3Sopenharmony_ci return UsbFnCfgMgrRegisterProp(interface, registInfo); 233094332d3Sopenharmony_ci} 234094332d3Sopenharmony_ci 235094332d3Sopenharmony_ciint32_t UsbFnGetInterfaceProp(const struct UsbFnInterface *interface, const char *name, char *value) 236094332d3Sopenharmony_ci{ 237094332d3Sopenharmony_ci if (name == NULL || interface == NULL || value == NULL) { 238094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 239094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 240094332d3Sopenharmony_ci } 241094332d3Sopenharmony_ci return UsbFnCfgMgrGetProp(interface, name, value); 242094332d3Sopenharmony_ci} 243094332d3Sopenharmony_ci 244094332d3Sopenharmony_ciint32_t UsbFnSetInterfaceProp(const struct UsbFnInterface *interface, const char *name, const char *value) 245094332d3Sopenharmony_ci{ 246094332d3Sopenharmony_ci if (name == NULL || interface == NULL) { 247094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 248094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 249094332d3Sopenharmony_ci } 250094332d3Sopenharmony_ci return UsbFnCfgMgrSetProp(interface, name, value); 251094332d3Sopenharmony_ci} 252094332d3Sopenharmony_ci 253094332d3Sopenharmony_cistruct UsbFnRequest *UsbFnAllocRequest(UsbFnInterfaceHandle handle, uint8_t pipe, uint32_t len) 254094332d3Sopenharmony_ci{ 255094332d3Sopenharmony_ci struct UsbHandleMgr *handleMgr = handle; 256094332d3Sopenharmony_ci if (handle == NULL || len > MAX_BUFLEN || len == 0 || pipe >= handleMgr->numFd) { 257094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 258094332d3Sopenharmony_ci return NULL; 259094332d3Sopenharmony_ci } 260094332d3Sopenharmony_ci return UsbFnIoMgrRequestAlloc(handleMgr, pipe + 1, len); 261094332d3Sopenharmony_ci} 262094332d3Sopenharmony_ci 263094332d3Sopenharmony_cistruct UsbFnRequest *UsbFnAllocCtrlRequest(UsbFnInterfaceHandle handle, uint32_t len) 264094332d3Sopenharmony_ci{ 265094332d3Sopenharmony_ci struct UsbHandleMgr *handleMgr = handle; 266094332d3Sopenharmony_ci if (handle == NULL || len > MAX_BUFLEN || len == 0) { 267094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 268094332d3Sopenharmony_ci return NULL; 269094332d3Sopenharmony_ci } 270094332d3Sopenharmony_ci return UsbFnIoMgrRequestAlloc(handleMgr, 0, len); 271094332d3Sopenharmony_ci} 272094332d3Sopenharmony_ci 273094332d3Sopenharmony_ciint32_t UsbFnFreeRequest(struct UsbFnRequest *req) 274094332d3Sopenharmony_ci{ 275094332d3Sopenharmony_ci if (req == NULL) { 276094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 277094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 278094332d3Sopenharmony_ci } 279094332d3Sopenharmony_ci return UsbFnIoMgrRequestFree(req); 280094332d3Sopenharmony_ci} 281094332d3Sopenharmony_ci 282094332d3Sopenharmony_ciint32_t UsbFnGetRequestStatus(struct UsbFnRequest *req, UsbRequestStatus *status) 283094332d3Sopenharmony_ci{ 284094332d3Sopenharmony_ci if (req == NULL || status == NULL) { 285094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 286094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 287094332d3Sopenharmony_ci } 288094332d3Sopenharmony_ci return UsbFnIoMgrRequestGetStatus(req, status); 289094332d3Sopenharmony_ci} 290094332d3Sopenharmony_ci 291094332d3Sopenharmony_ciint32_t UsbFnSubmitRequestAsync(struct UsbFnRequest *req) 292094332d3Sopenharmony_ci{ 293094332d3Sopenharmony_ci if (req == NULL) { 294094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 295094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 296094332d3Sopenharmony_ci } 297094332d3Sopenharmony_ci return UsbFnIoMgrRequestSubmitAsync(req); 298094332d3Sopenharmony_ci} 299094332d3Sopenharmony_ci 300094332d3Sopenharmony_ciint32_t UsbFnCancelRequest(struct UsbFnRequest *req) 301094332d3Sopenharmony_ci{ 302094332d3Sopenharmony_ci if (req == NULL) { 303094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 304094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 305094332d3Sopenharmony_ci } 306094332d3Sopenharmony_ci return UsbFnIoMgrRequestCancel(req); 307094332d3Sopenharmony_ci} 308094332d3Sopenharmony_ci 309094332d3Sopenharmony_ciint32_t UsbFnSubmitRequestSync(struct UsbFnRequest *req, uint32_t timeout) 310094332d3Sopenharmony_ci{ 311094332d3Sopenharmony_ci if (req == NULL) { 312094332d3Sopenharmony_ci HDF_LOGE("%{public}s: INVALID PARAM", __func__); 313094332d3Sopenharmony_ci return HDF_ERR_INVALID_PARAM; 314094332d3Sopenharmony_ci } 315094332d3Sopenharmony_ci return UsbFnIoMgrRequestSubmitSync(req, timeout); 316094332d3Sopenharmony_ci} 317