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_io_mgr.h"
17094332d3Sopenharmony_ci#include "usbd_wrapper.h"
18094332d3Sopenharmony_ci
19094332d3Sopenharmony_ci#define HDF_LOG_TAG usbfn_io_mgr
20094332d3Sopenharmony_ci
21094332d3Sopenharmony_cistatic int32_t ReqToIoData(struct UsbFnRequest *req, struct IoData *ioData, uint32_t aio, uint32_t timeout)
22094332d3Sopenharmony_ci{
23094332d3Sopenharmony_ci    if (req == NULL || ioData == NULL) {
24094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
25094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
26094332d3Sopenharmony_ci    }
27094332d3Sopenharmony_ci    struct ReqList *reqList = (struct ReqList *)req;
28094332d3Sopenharmony_ci    ioData->aio = aio;
29094332d3Sopenharmony_ci    if (req->type == USB_REQUEST_TYPE_PIPE_WRITE) {
30094332d3Sopenharmony_ci        ioData->read = 0;
31094332d3Sopenharmony_ci    } else if (req->type == USB_REQUEST_TYPE_PIPE_READ) {
32094332d3Sopenharmony_ci        ioData->read = 1;
33094332d3Sopenharmony_ci    }
34094332d3Sopenharmony_ci    ioData->buf = reqList->buf;
35094332d3Sopenharmony_ci    ioData->len = req->length;
36094332d3Sopenharmony_ci    ioData->timeout = timeout;
37094332d3Sopenharmony_ci
38094332d3Sopenharmony_ci    return 0;
39094332d3Sopenharmony_ci}
40094332d3Sopenharmony_ci
41094332d3Sopenharmony_ciint32_t OpenEp0AndMapAddr(struct UsbFnFuncMgr *funcMgr)
42094332d3Sopenharmony_ci{
43094332d3Sopenharmony_ci    int32_t ret;
44094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
45094332d3Sopenharmony_ci    funcMgr->fd = fnOps->openPipe(funcMgr->name, 0);
46094332d3Sopenharmony_ci    if (funcMgr->fd <= 0) {
47094332d3Sopenharmony_ci        HDF_LOGE("%{public}s:%{public}d openPipe failed", __func__, __LINE__);
48094332d3Sopenharmony_ci        return HDF_ERR_IO;
49094332d3Sopenharmony_ci    }
50094332d3Sopenharmony_ci
51094332d3Sopenharmony_ci    ret = fnOps->queueInit(funcMgr->fd);
52094332d3Sopenharmony_ci    if (ret) {
53094332d3Sopenharmony_ci        HDF_LOGE("%{public}s:%{public}d queueInit failed", __func__, __LINE__);
54094332d3Sopenharmony_ci        return HDF_ERR_IO;
55094332d3Sopenharmony_ci    }
56094332d3Sopenharmony_ci    return 0;
57094332d3Sopenharmony_ci}
58094332d3Sopenharmony_ci
59094332d3Sopenharmony_cistatic UsbFnRequestType GetReqType(struct UsbHandleMgr *handle, uint8_t pipe)
60094332d3Sopenharmony_ci{
61094332d3Sopenharmony_ci    struct UsbFnPipeInfo info = {0};
62094332d3Sopenharmony_ci    UsbFnRequestType type = USB_REQUEST_TYPE_INVALID;
63094332d3Sopenharmony_ci    if (pipe > 0) {
64094332d3Sopenharmony_ci        int32_t ret = UsbFnIoMgrInterfaceGetPipeInfo(&(handle->intfMgr->interface), pipe - 1, &info);
65094332d3Sopenharmony_ci        if (ret) {
66094332d3Sopenharmony_ci            HDF_LOGE("%{public}s:%{public}d UsbFnMgrInterfaceGetPipeInfo err", __func__, __LINE__);
67094332d3Sopenharmony_ci            type = USB_REQUEST_TYPE_INVALID;
68094332d3Sopenharmony_ci        }
69094332d3Sopenharmony_ci        if (info.dir == USB_PIPE_DIRECTION_IN) {
70094332d3Sopenharmony_ci            type = USB_REQUEST_TYPE_PIPE_WRITE;
71094332d3Sopenharmony_ci        } else if (info.dir == USB_PIPE_DIRECTION_OUT) {
72094332d3Sopenharmony_ci            type = USB_REQUEST_TYPE_PIPE_READ;
73094332d3Sopenharmony_ci        }
74094332d3Sopenharmony_ci    }
75094332d3Sopenharmony_ci    return type;
76094332d3Sopenharmony_ci}
77094332d3Sopenharmony_ci
78094332d3Sopenharmony_cistruct UsbFnRequest *UsbFnIoMgrRequestAlloc(struct UsbHandleMgr *handle, uint8_t pipe, uint32_t len)
79094332d3Sopenharmony_ci{
80094332d3Sopenharmony_ci    int32_t ep;
81094332d3Sopenharmony_ci    struct UsbFnInterfaceMgr *intfMgr = handle->intfMgr;
82094332d3Sopenharmony_ci    struct UsbFnFuncMgr *funcMgr = intfMgr->funcMgr;
83094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
84094332d3Sopenharmony_ci    if (pipe == 0) {
85094332d3Sopenharmony_ci        if (funcMgr->fd <= 0) {
86094332d3Sopenharmony_ci            int32_t ret = OpenEp0AndMapAddr(funcMgr);
87094332d3Sopenharmony_ci            if (ret) {
88094332d3Sopenharmony_ci                return NULL;
89094332d3Sopenharmony_ci            }
90094332d3Sopenharmony_ci        }
91094332d3Sopenharmony_ci        ep = funcMgr->fd;
92094332d3Sopenharmony_ci    } else if (pipe <= MAX_EP) {
93094332d3Sopenharmony_ci        ep = handle->fds[pipe - 1];
94094332d3Sopenharmony_ci    } else {
95094332d3Sopenharmony_ci        return NULL;
96094332d3Sopenharmony_ci    }
97094332d3Sopenharmony_ci    uint8_t *mapAddr = fnOps->mapAddr(ep, len);
98094332d3Sopenharmony_ci    if (mapAddr == NULL) {
99094332d3Sopenharmony_ci        HDF_LOGE("%{public}s:%{public}d mapAddr failed", __func__, __LINE__);
100094332d3Sopenharmony_ci        return NULL;
101094332d3Sopenharmony_ci    }
102094332d3Sopenharmony_ci
103094332d3Sopenharmony_ci    struct ReqList *reqList = UsbFnMemCalloc(sizeof(struct ReqList));
104094332d3Sopenharmony_ci    if (reqList == NULL) {
105094332d3Sopenharmony_ci        HDF_LOGE("%{public}s:%{public}d UsbFnMemCalloc err", __func__, __LINE__);
106094332d3Sopenharmony_ci        return NULL;
107094332d3Sopenharmony_ci    }
108094332d3Sopenharmony_ci    struct UsbFnRequest *req = &reqList->req;
109094332d3Sopenharmony_ci
110094332d3Sopenharmony_ci    if (pipe == 0) {
111094332d3Sopenharmony_ci        DListInsertTail(&reqList->entry, &funcMgr->reqEntry);
112094332d3Sopenharmony_ci    } else {
113094332d3Sopenharmony_ci        DListInsertTail(&reqList->entry, &handle->reqEntry);
114094332d3Sopenharmony_ci    }
115094332d3Sopenharmony_ci    reqList->handle = handle;
116094332d3Sopenharmony_ci    reqList->fd = ep;
117094332d3Sopenharmony_ci    reqList->buf = (uintptr_t)mapAddr;
118094332d3Sopenharmony_ci    reqList->pipe = pipe;
119094332d3Sopenharmony_ci    reqList->bufLen = len;
120094332d3Sopenharmony_ci    req->length = len;
121094332d3Sopenharmony_ci    req->obj = handle->intfMgr->interface.object;
122094332d3Sopenharmony_ci    req->buf = mapAddr;
123094332d3Sopenharmony_ci    req->type = GetReqType(handle, pipe);
124094332d3Sopenharmony_ci
125094332d3Sopenharmony_ci    return req;
126094332d3Sopenharmony_ci}
127094332d3Sopenharmony_ci
128094332d3Sopenharmony_ciint32_t UsbFnIoMgrRequestFree(struct UsbFnRequest *req)
129094332d3Sopenharmony_ci{
130094332d3Sopenharmony_ci    struct GenericMemory mem;
131094332d3Sopenharmony_ci    int32_t ret;
132094332d3Sopenharmony_ci    if (req == NULL) {
133094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
134094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
135094332d3Sopenharmony_ci    }
136094332d3Sopenharmony_ci
137094332d3Sopenharmony_ci    struct ReqList *reqList = (struct ReqList *)req;
138094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
139094332d3Sopenharmony_ci
140094332d3Sopenharmony_ci    ret = fnOps->unmapAddr(req->buf, reqList->bufLen);
141094332d3Sopenharmony_ci    if (ret) {
142094332d3Sopenharmony_ci        HDF_LOGE("%{public}s:%{public}d ummapAddr failed, ret=%{public}d ", __func__, __LINE__, ret);
143094332d3Sopenharmony_ci        return HDF_ERR_DEVICE_BUSY;
144094332d3Sopenharmony_ci    }
145094332d3Sopenharmony_ci    mem.size = reqList->bufLen;
146094332d3Sopenharmony_ci    mem.buf = (uint64_t)req->buf;
147094332d3Sopenharmony_ci    ret = fnOps->releaseBuf(reqList->fd, &mem);
148094332d3Sopenharmony_ci    if (ret) {
149094332d3Sopenharmony_ci        HDF_LOGE("%{public}s releaseBuf err::%{public}d", __func__, ret);
150094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
151094332d3Sopenharmony_ci    }
152094332d3Sopenharmony_ci
153094332d3Sopenharmony_ci    DListRemove(&reqList->entry);
154094332d3Sopenharmony_ci    UsbFnMemFree(reqList);
155094332d3Sopenharmony_ci    return 0;
156094332d3Sopenharmony_ci}
157094332d3Sopenharmony_ci
158094332d3Sopenharmony_ciint32_t UsbFnIoMgrRequestSubmitAsync(struct UsbFnRequest *req)
159094332d3Sopenharmony_ci{
160094332d3Sopenharmony_ci    int32_t ret;
161094332d3Sopenharmony_ci    struct IoData ioData = {0};
162094332d3Sopenharmony_ci    struct ReqList *reqList = NULL;
163094332d3Sopenharmony_ci    if (req == NULL) {
164094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
165094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
166094332d3Sopenharmony_ci    }
167094332d3Sopenharmony_ci    reqList = (struct ReqList *)req;
168094332d3Sopenharmony_ci    if (ReqToIoData(req, &ioData, 1, 0)) {
169094332d3Sopenharmony_ci        return HDF_ERR_IO;
170094332d3Sopenharmony_ci    }
171094332d3Sopenharmony_ci
172094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
173094332d3Sopenharmony_ci    ret = fnOps->pipeIo(reqList->fd, &ioData);
174094332d3Sopenharmony_ci    if (ret != HDF_SUCCESS) {
175094332d3Sopenharmony_ci        HDF_LOGE("%{public}s pipeIo failed fd:%{public}d read:%{public}u", __func__, reqList->fd, ioData.read);
176094332d3Sopenharmony_ci    }
177094332d3Sopenharmony_ci
178094332d3Sopenharmony_ci    return ret;
179094332d3Sopenharmony_ci}
180094332d3Sopenharmony_ci
181094332d3Sopenharmony_ciint32_t UsbFnIoMgrRequestCancel(struct UsbFnRequest *req)
182094332d3Sopenharmony_ci{
183094332d3Sopenharmony_ci    int32_t ret;
184094332d3Sopenharmony_ci    struct IoData ioData = {0};
185094332d3Sopenharmony_ci    struct ReqList *reqList = NULL;
186094332d3Sopenharmony_ci    if (req == NULL) {
187094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
188094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
189094332d3Sopenharmony_ci    }
190094332d3Sopenharmony_ci    reqList = (struct ReqList *)req;
191094332d3Sopenharmony_ci    if (ReqToIoData(req, &ioData, 1, 0)) {
192094332d3Sopenharmony_ci        return HDF_ERR_IO;
193094332d3Sopenharmony_ci    }
194094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
195094332d3Sopenharmony_ci    ret = fnOps->cancelIo(reqList->fd, &ioData);
196094332d3Sopenharmony_ci
197094332d3Sopenharmony_ci    return ret;
198094332d3Sopenharmony_ci}
199094332d3Sopenharmony_ci
200094332d3Sopenharmony_ciint32_t UsbFnIoMgrRequestGetStatus(struct UsbFnRequest *req, UsbRequestStatus *status)
201094332d3Sopenharmony_ci{
202094332d3Sopenharmony_ci    struct IoData ioData = {0};
203094332d3Sopenharmony_ci    struct ReqList *reqList;
204094332d3Sopenharmony_ci    if (req == NULL) {
205094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
206094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
207094332d3Sopenharmony_ci    }
208094332d3Sopenharmony_ci    reqList = (struct ReqList *)req;
209094332d3Sopenharmony_ci    if (ReqToIoData(req, &ioData, 1, 0)) {
210094332d3Sopenharmony_ci        return HDF_ERR_IO;
211094332d3Sopenharmony_ci    }
212094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
213094332d3Sopenharmony_ci    *status = -(fnOps->getReqStatus(reqList->fd, &ioData));
214094332d3Sopenharmony_ci
215094332d3Sopenharmony_ci    return 0;
216094332d3Sopenharmony_ci}
217094332d3Sopenharmony_ci
218094332d3Sopenharmony_ciint32_t UsbFnIoMgrRequestSubmitSync(struct UsbFnRequest *req, uint32_t timeout)
219094332d3Sopenharmony_ci{
220094332d3Sopenharmony_ci    int32_t ret;
221094332d3Sopenharmony_ci    struct IoData ioData = {0};
222094332d3Sopenharmony_ci    struct ReqList *reqList;
223094332d3Sopenharmony_ci
224094332d3Sopenharmony_ci    if (req == NULL) {
225094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
226094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
227094332d3Sopenharmony_ci    }
228094332d3Sopenharmony_ci    reqList = (struct ReqList *)req;
229094332d3Sopenharmony_ci    if (ReqToIoData(req, &ioData, 0, timeout)) {
230094332d3Sopenharmony_ci        return HDF_ERR_IO;
231094332d3Sopenharmony_ci    }
232094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
233094332d3Sopenharmony_ci    ret = fnOps->pipeIo(reqList->fd, &ioData);
234094332d3Sopenharmony_ci    if (ret > 0) {
235094332d3Sopenharmony_ci        req->status = USB_REQUEST_COMPLETED;
236094332d3Sopenharmony_ci        req->actual = (uint32_t)ret;
237094332d3Sopenharmony_ci        return 0;
238094332d3Sopenharmony_ci    }
239094332d3Sopenharmony_ci
240094332d3Sopenharmony_ci    return ret;
241094332d3Sopenharmony_ci}
242094332d3Sopenharmony_ci
243094332d3Sopenharmony_cistatic int32_t HandleInit(struct UsbHandleMgr *handle, struct UsbFnInterfaceMgr *interfaceMgr)
244094332d3Sopenharmony_ci{
245094332d3Sopenharmony_ci    int32_t ret;
246094332d3Sopenharmony_ci    uint32_t i, j;
247094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
248094332d3Sopenharmony_ci
249094332d3Sopenharmony_ci    DListHeadInit(&handle->reqEntry);
250094332d3Sopenharmony_ci    handle->numFd = interfaceMgr->interface.info.numPipes;
251094332d3Sopenharmony_ci    for (i = 0; i < handle->numFd; i++) {
252094332d3Sopenharmony_ci        handle->fds[i] = fnOps->openPipe(interfaceMgr->funcMgr->name, interfaceMgr->startEpId + i);
253094332d3Sopenharmony_ci        if (handle->fds[i] <= 0) {
254094332d3Sopenharmony_ci            return HDF_ERR_IO;
255094332d3Sopenharmony_ci        }
256094332d3Sopenharmony_ci
257094332d3Sopenharmony_ci        ret = fnOps->queueInit(handle->fds[i]);
258094332d3Sopenharmony_ci        if (ret) {
259094332d3Sopenharmony_ci            HDF_LOGE("%{public}s: queueInit failed ret = %{public}d", __func__, ret);
260094332d3Sopenharmony_ci            return HDF_ERR_IO;
261094332d3Sopenharmony_ci        }
262094332d3Sopenharmony_ci
263094332d3Sopenharmony_ci        handle->reqEvent[i] = UsbFnMemCalloc(sizeof(struct UsbFnReqEvent) * MAX_REQUEST);
264094332d3Sopenharmony_ci        if (handle->reqEvent[i] == NULL) {
265094332d3Sopenharmony_ci            HDF_LOGE("%{public}s: UsbFnMemCalloc failed", __func__);
266094332d3Sopenharmony_ci            goto FREE_EVENT;
267094332d3Sopenharmony_ci        }
268094332d3Sopenharmony_ci    }
269094332d3Sopenharmony_ci    handle->intfMgr = interfaceMgr;
270094332d3Sopenharmony_ci    return 0;
271094332d3Sopenharmony_ci
272094332d3Sopenharmony_ciFREE_EVENT:
273094332d3Sopenharmony_ci    for (j = 0; j < i; j++) {
274094332d3Sopenharmony_ci        UsbFnMemFree(handle->reqEvent[j]);
275094332d3Sopenharmony_ci    }
276094332d3Sopenharmony_ci    return HDF_ERR_IO;
277094332d3Sopenharmony_ci}
278094332d3Sopenharmony_ci
279094332d3Sopenharmony_cistruct UsbHandleMgr *UsbFnIoMgrInterfaceOpen(struct UsbFnInterface *interface)
280094332d3Sopenharmony_ci{
281094332d3Sopenharmony_ci    int32_t ret;
282094332d3Sopenharmony_ci    if (interface == NULL) {
283094332d3Sopenharmony_ci        return NULL;
284094332d3Sopenharmony_ci    }
285094332d3Sopenharmony_ci    struct UsbFnInterfaceMgr *interfaceMgr = (struct UsbFnInterfaceMgr *)interface;
286094332d3Sopenharmony_ci    if (interfaceMgr->isOpen) {
287094332d3Sopenharmony_ci        HDF_LOGE("%{public}s: interface has opened", __func__);
288094332d3Sopenharmony_ci        return NULL;
289094332d3Sopenharmony_ci    }
290094332d3Sopenharmony_ci    struct UsbHandleMgr *handle = UsbFnMemCalloc(sizeof(struct UsbHandleMgr));
291094332d3Sopenharmony_ci    if (handle == NULL) {
292094332d3Sopenharmony_ci        HDF_LOGE("%{public}s: malloc UsbHandleMgr failed", __func__);
293094332d3Sopenharmony_ci        return NULL;
294094332d3Sopenharmony_ci    }
295094332d3Sopenharmony_ci
296094332d3Sopenharmony_ci    ret = HandleInit(handle, interfaceMgr);
297094332d3Sopenharmony_ci    if (ret) {
298094332d3Sopenharmony_ci        HDF_LOGE("%{public}s: HandleInit failed", __func__);
299094332d3Sopenharmony_ci        UsbFnMemFree(handle);
300094332d3Sopenharmony_ci        return NULL;
301094332d3Sopenharmony_ci    }
302094332d3Sopenharmony_ci
303094332d3Sopenharmony_ci    interfaceMgr->isOpen = true;
304094332d3Sopenharmony_ci    interfaceMgr->handle = handle;
305094332d3Sopenharmony_ci    return handle;
306094332d3Sopenharmony_ci}
307094332d3Sopenharmony_ci
308094332d3Sopenharmony_ciint32_t UsbFnIoMgrInterfaceClose(struct UsbHandleMgr *handle)
309094332d3Sopenharmony_ci{
310094332d3Sopenharmony_ci    if (handle == NULL) {
311094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
312094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
313094332d3Sopenharmony_ci    }
314094332d3Sopenharmony_ci
315094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
316094332d3Sopenharmony_ci    struct UsbFnInterfaceMgr *interfaceMgr = handle->intfMgr;
317094332d3Sopenharmony_ci    if (interfaceMgr == NULL || interfaceMgr->isOpen == false) {
318094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
319094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
320094332d3Sopenharmony_ci    }
321094332d3Sopenharmony_ci    for (uint32_t i = 0; i < handle->numFd; i++) {
322094332d3Sopenharmony_ci        int32_t ret = fnOps->queueDel(handle->fds[i]);
323094332d3Sopenharmony_ci        if (ret) {
324094332d3Sopenharmony_ci            HDF_LOGE("%{public}s:%{public}d queueDel failed, ret=%{public}d ", __func__, __LINE__, ret);
325094332d3Sopenharmony_ci            return HDF_ERR_DEVICE_BUSY;
326094332d3Sopenharmony_ci        }
327094332d3Sopenharmony_ci
328094332d3Sopenharmony_ci        ret = fnOps->closePipe(handle->fds[i]);
329094332d3Sopenharmony_ci        if (ret) {
330094332d3Sopenharmony_ci            HDF_LOGE("%{public}s:%{public}d closePipe failed, ret=%{public}d ", __func__, __LINE__, ret);
331094332d3Sopenharmony_ci            return HDF_ERR_DEVICE_BUSY;
332094332d3Sopenharmony_ci        }
333094332d3Sopenharmony_ci        handle->fds[i] = -1;
334094332d3Sopenharmony_ci        UsbFnMemFree(handle->reqEvent[i]);
335094332d3Sopenharmony_ci        handle->reqEvent[i] = NULL;
336094332d3Sopenharmony_ci    }
337094332d3Sopenharmony_ci
338094332d3Sopenharmony_ci    UsbFnMemFree(handle);
339094332d3Sopenharmony_ci    handle = NULL;
340094332d3Sopenharmony_ci    interfaceMgr->isOpen = false;
341094332d3Sopenharmony_ci    interfaceMgr->handle = NULL;
342094332d3Sopenharmony_ci    return 0;
343094332d3Sopenharmony_ci}
344094332d3Sopenharmony_ci
345094332d3Sopenharmony_ciint32_t UsbFnIoMgrInterfaceGetPipeInfo(struct UsbFnInterface *interface, uint8_t pipeId, struct UsbFnPipeInfo *info)
346094332d3Sopenharmony_ci{
347094332d3Sopenharmony_ci    int32_t ret;
348094332d3Sopenharmony_ci    int32_t fd;
349094332d3Sopenharmony_ci    if (info == NULL || interface == NULL || pipeId >= interface->info.numPipes) {
350094332d3Sopenharmony_ci        HDF_LOGE("%{public}s invalid param", __func__);
351094332d3Sopenharmony_ci        return HDF_ERR_INVALID_PARAM;
352094332d3Sopenharmony_ci    }
353094332d3Sopenharmony_ci    struct UsbFnAdapterOps *fnOps = UsbFnAdapterGetOps();
354094332d3Sopenharmony_ci    struct UsbFnInterfaceMgr *interfaceMgr = (struct UsbFnInterfaceMgr *)interface;
355094332d3Sopenharmony_ci    if (interfaceMgr->isOpen) {
356094332d3Sopenharmony_ci        if (pipeId >= MAX_EP) {
357094332d3Sopenharmony_ci            HDF_LOGE("%{public}s pipeId overflow", __func__);
358094332d3Sopenharmony_ci            return HDF_ERR_INVALID_PARAM;
359094332d3Sopenharmony_ci        }
360094332d3Sopenharmony_ci        fd = interfaceMgr->handle->fds[pipeId];
361094332d3Sopenharmony_ci        ret = fnOps->getPipeInfo(fd, info);
362094332d3Sopenharmony_ci        if (ret) {
363094332d3Sopenharmony_ci            HDF_LOGE("%{public}s: getPipeInfo failed", __func__);
364094332d3Sopenharmony_ci            return HDF_ERR_DEVICE_BUSY;
365094332d3Sopenharmony_ci        }
366094332d3Sopenharmony_ci    } else {
367094332d3Sopenharmony_ci        fd = fnOps->openPipe(interfaceMgr->funcMgr->name, interfaceMgr->startEpId + pipeId);
368094332d3Sopenharmony_ci        if (fd <= 0) {
369094332d3Sopenharmony_ci            HDF_LOGE("%{public}s: openPipe failed", __func__);
370094332d3Sopenharmony_ci            return HDF_ERR_IO;
371094332d3Sopenharmony_ci        }
372094332d3Sopenharmony_ci        ret = fnOps->getPipeInfo(fd, info);
373094332d3Sopenharmony_ci        if (ret) {
374094332d3Sopenharmony_ci            fnOps->closePipe(fd);
375094332d3Sopenharmony_ci            HDF_LOGE("%{public}s: getPipeInfo failed", __func__);
376094332d3Sopenharmony_ci            return HDF_ERR_DEVICE_BUSY;
377094332d3Sopenharmony_ci        }
378094332d3Sopenharmony_ci        fnOps->closePipe(fd);
379094332d3Sopenharmony_ci    }
380094332d3Sopenharmony_ci
381094332d3Sopenharmony_ci    info->id = pipeId;
382094332d3Sopenharmony_ci    return ret;
383094332d3Sopenharmony_ci}
384