1 /*
2 * Copyright (c) 2021 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "liteos_adapter.h"
17 #include "los_spinlock.h"
18 #ifdef LOSCFG_DRIVERS_HDF_USB_PNP_NOTIFY
19 #include "usb_pnp_notify.h"
20 #endif
21
22 #define HDF_LOG_TAG USB_LITEOS_ADAPTER
23
24 #define PATH_LEN 24
25 #define DESC_READ_LEN 256
26 #define EP_NUM_MAX 30
27
28 static bool g_CompleteExit;
29
30 enum UrbState {
31 URB_INIT_STATE,
32 URB_SUBMIT_STATE,
33 URB_REAP_STATE,
34 };
35
36 struct Async {
37 struct DListHead asynclist;
38 enum UrbState state;
39 struct UsbDevice *dev;
40 struct UsbAdapterUrb urb;
41 };
42
43 struct OsDev {
44 struct DListHead asyncCompleted;
45 struct UsbAdapterDevice *adapterDevice;
46 SPIN_LOCK_S completeLock;
47 struct OsalMutex completeMux;
48 struct OsalSem cvWait;
49 };
50
OsAdapterRealloc(void * ptr,size_t oldSize,size_t newSize)51 static void *OsAdapterRealloc(void *ptr, size_t oldSize, size_t newSize)
52 {
53 void *mem;
54
55 mem = RawUsbMemAlloc(newSize);
56 if (mem == NULL) {
57 HDF_LOGE("%s:%d", __func__, __LINE__);
58 goto OUT;
59 }
60
61 if (oldSize > 0) {
62 if (memmove_s(mem, newSize, ptr, oldSize) != HDF_SUCCESS) {
63 HDF_LOGE("%s:%d", __func__, __LINE__);
64 RawUsbMemFree(mem);
65 mem = NULL;
66 goto OUT;
67 }
68 }
69
70 RawUsbMemFree(ptr);
71 OUT:
72 return mem;
73 }
74
UsbFindUrb(struct Async * urb,struct DListHead * list)75 static bool UsbFindUrb(struct Async *urb, struct DListHead *list)
76 {
77 bool findFlag = false;
78 struct OsDev *osDev = CONTAINER_OF(list, struct OsDev, asyncCompleted);
79 struct Async *asPos = NULL;
80 struct Async *asTemp = NULL;
81 if (DListIsEmpty(&osDev->asyncCompleted)) {
82 return false;
83 }
84 DLIST_FOR_EACH_ENTRY_SAFE(asPos, asTemp, list, struct Async, asynclist) {
85 if (asPos == urb) {
86 findFlag = true;
87 break;
88 }
89 }
90 return findFlag;
91 }
92
OsUrbComplete(struct UsbAdapterUrb * urb)93 static void OsUrbComplete(struct UsbAdapterUrb *urb)
94 {
95 uint32_t save;
96 struct Async *as = CONTAINER_OF(urb, struct Async, urb);
97 struct UsbDevice *dev = as->dev;
98 if (dev == NULL) {
99 DPRINTFN(0, "--dev:%p\n", dev);
100 return;
101 }
102 struct OsDev *osDev = (struct OsDev *)dev->privateData;
103 if (osDev == NULL) {
104 DPRINTFN(0, "--osDev:%p\n", osDev);
105 return;
106 }
107 as->state = URB_REAP_STATE;
108 LOS_SpinLockSave(&osDev->completeLock, &save);
109 if (UsbFindUrb(as, &osDev->asyncCompleted) == false) {
110 DListInsertTail(&as->asynclist, &osDev->asyncCompleted);
111 LOS_SpinUnlockRestore(&osDev->completeLock, save);
112 OsalSemPost(&osDev->cvWait);
113 } else {
114 LOS_SpinUnlockRestore(&osDev->completeLock, save);
115 }
116 }
117
OsSubmitUrb(struct UsbAdapterUrb * urb,struct UsbAdapterDevice * adapterDevice,struct UsbAdapterHostEndpoint * uhe)118 static int32_t OsSubmitUrb(
119 struct UsbAdapterUrb *urb, struct UsbAdapterDevice *adapterDevice, struct UsbAdapterHostEndpoint *uhe)
120 {
121 int32_t err;
122
123 if ((uhe == NULL) || (urb == NULL) || (adapterDevice == NULL)) {
124 DPRINTFN(0, "invalid param\n");
125 return (-EINVAL);
126 }
127
128 err = usb_setup_endpoint(adapterDevice, uhe, 1024);
129 if (err) {
130 DPRINTFN(0, "setup failed err:%d\n", err);
131 return (err);
132 }
133 err = usb_submit_urb(urb, 0);
134 return (err);
135 }
136
OsControlMsg(struct UsbAdapterUrb * urb)137 static int32_t OsControlMsg(struct UsbAdapterUrb *urb)
138 {
139 int32_t err;
140 uint16_t actLen = 0;
141 struct UsbAdapterDevice *adapterDevice = urb->dev;
142 void *buffer = urb->transfer_buffer;
143 struct UsbAdapterDeviceRequest req;
144
145 err = memcpy_s(&req, sizeof(struct UsbAdapterDeviceRequest), buffer, sizeof(req));
146 if (err != EOK) {
147 DPRINTFN(0, "%s:%d err=%d\n", __func__, __LINE__, err);
148 err = HDF_ERR_IO;
149 return err;
150 }
151 err = usbd_do_request_flags(adapterDevice, NULL, &req, (char *)buffer + sizeof(req),
152 USB_SHORT_XFER_OK, &actLen, urb->timeout);
153 if (err) {
154 DPRINTFN(1, "OsControlMsg!err:%d\n", err);
155 }
156 urb->actual_length = actLen;
157 if (urb->complete) {
158 (urb->complete)(urb);
159 }
160 return err;
161 }
162
OsWaitUrb(struct OsDev * osDev)163 static int32_t OsWaitUrb(struct OsDev *osDev)
164 {
165 if (osDev == NULL) {
166 return HDF_FAILURE;
167 }
168 do {
169 OsalSemWait(&osDev->cvWait, HDF_WAIT_FOREVER);
170 } while (!g_CompleteExit && DListIsEmpty(&osDev->asyncCompleted));
171 return HDF_SUCCESS;
172 }
173
OsReapUrb(const struct UsbDeviceHandle * handle,struct Async ** urb)174 static int32_t OsReapUrb(const struct UsbDeviceHandle *handle, struct Async **urb)
175 {
176 if ((handle == NULL) || (handle->dev == NULL) || (handle->dev->privateData == NULL)) {
177 PRINTK("invalid parmater\n");
178 return HDF_ERR_INVALID_PARAM;
179 }
180 int32_t err = 0;
181 uint32_t save;
182 struct Async *as = NULL;
183 struct UsbDevice *dev = handle->dev;
184 if (dev->privateData == NULL) {
185 PRINTK("invalid parmater\n");
186 return HDF_ERR_INVALID_PARAM;
187 }
188 struct OsDev *osDev = (struct OsDev *)dev->privateData;
189 err = OsWaitUrb(osDev);
190 LOS_SpinLockSave(&osDev->completeLock, &save);
191 if (!DListIsEmpty(&osDev->asyncCompleted)) {
192 as = DLIST_FIRST_ENTRY(&osDev->asyncCompleted, struct Async, asynclist);
193 DListRemove(&as->asynclist);
194 }
195 LOS_SpinUnlockRestore(&osDev->completeLock, save);
196 *urb = as;
197 return err;
198 }
199
OsDeviceCompare(struct HdfSListNode * listEntry,uint32_t searchKey)200 static bool OsDeviceCompare(struct HdfSListNode *listEntry, uint32_t searchKey)
201 {
202 struct UsbDevice *dev = (struct UsbDevice *)listEntry;
203 if (dev == NULL) {
204 return false;
205 }
206
207 if ((dev->busNum == (searchKey >> BUS_OFFSET)) &&
208 (dev->devAddr == (searchKey & 0xFF))) {
209 return true;
210 }
211
212 return false;
213 }
214
OsGetDeviceHandle(struct UsbSession * session,uint8_t busNum,uint8_t usbAddr)215 static struct UsbDeviceHandle *OsGetDeviceHandle(struct UsbSession *session, uint8_t busNum, uint8_t usbAddr)
216 {
217 struct UsbDevice *dev = NULL;
218 struct UsbDeviceHandle *handle = NULL;
219
220 if (session == NULL) {
221 DPRINTFN(0, "%s:invalid param\n", __func__);
222 return NULL;
223 }
224
225 OsalMutexLock(&session->lock);
226 dev = (struct UsbDevice *)HdfSListSearch(
227 &session->usbDevs, (busNum << BUS_OFFSET) | usbAddr, OsDeviceCompare);
228 if (dev != NULL) {
229 handle = dev->devHandle;
230 AdapterAtomicInc(&dev->refcnt);
231 }
232 OsalMutexUnlock(&session->lock);
233
234 return handle;
235 }
236
OsCallocDeviceHandle(void)237 static struct UsbDeviceHandle *OsCallocDeviceHandle(void)
238 {
239 struct UsbDeviceHandle *handle = NULL;
240
241 handle = RawUsbMemCalloc(sizeof(*handle));
242 if (handle == NULL) {
243 DPRINTFN(0, "%s: allocate handle failed", __func__);
244 return NULL;
245 }
246
247 OsalMutexInit(&handle->lock);
248
249 return handle;
250 }
251
OsAllocDevice(struct UsbSession * session,struct UsbDeviceHandle * handle)252 static struct UsbDevice *OsAllocDevice(struct UsbSession *session, struct UsbDeviceHandle *handle)
253 {
254 struct UsbDevice *dev = RawUsbMemCalloc(sizeof(*dev));
255 if (dev == NULL) {
256 DPRINTFN(0, "%s:%d no memory", __func__, __LINE__);
257 return NULL;
258 }
259
260 dev->session = session;
261 dev->devHandle = handle;
262
263 RawRequestListInit(dev);
264
265 handle->dev = dev;
266 return dev;
267 }
268
OsReadDescriptors(struct UsbDevice * dev)269 static int32_t OsReadDescriptors(struct UsbDevice *dev)
270 {
271 size_t allocLen = 0;
272 uint8_t *ptr = NULL;
273 int32_t ret;
274 size_t count;
275 if (dev == NULL) {
276 HDF_LOGE("%s:%d dev is NULL!", __func__, __LINE__);
277 return HDF_ERR_INVALID_PARAM;
278 }
279 struct OsDev *osDev = (struct OsDev *)dev->privateData;
280 if ((osDev == NULL) || (osDev->adapterDevice == NULL) || (osDev->adapterDevice->cdesc == NULL)) {
281 HDF_LOGE("%s:%d is NULL!", __func__, __LINE__);
282 return HDF_ERR_INVALID_PARAM;
283 }
284
285 do {
286 size_t oldLen = allocLen;
287 allocLen += DESC_READ_LEN;
288 dev->descriptors = OsAdapterRealloc(dev->descriptors, oldLen, allocLen);
289 if ((dev->descriptors == NULL) || (dev->descriptorsLength > allocLen)) {
290 DPRINTFN(0, "%s:%d\n", __func__, __LINE__);
291 return HDF_ERR_MALLOC_FAIL;
292 }
293 ptr = (uint8_t *)dev->descriptors + dev->descriptorsLength;
294 if (ptr == NULL) {
295 DPRINTFN(0, "%s:%d ptr is NULL\n", __func__, __LINE__);
296 ret = HDF_ERR_INVALID_PARAM;
297 return ret;
298 }
299 ret = memset_s(ptr, DESC_READ_LEN, 0, DESC_READ_LEN);
300 if (ret != HDF_SUCCESS) {
301 HDF_LOGE("%{public}s:%{public}d memset_s failed", __func__, __LINE__);
302 return HDF_FAILURE;
303 }
304
305 count = UGETW(osDev->adapterDevice->cdesc->wTotalLength);
306 if (count > DESC_READ_LEN) {
307 ret = HDF_ERR_IO;
308 return ret;
309 }
310 ret = memcpy_s(ptr, DESC_READ_LEN, osDev->adapterDevice->cdesc, count);
311 if (ret != EOK) {
312 DPRINTFN(0, "%s:%d ret=%d\n", __func__, __LINE__, ret);
313 ret = HDF_ERR_IO;
314 return ret;
315 }
316 DPRINTFN(0, "%s:+configdes_size:%d+type:%d\n", __func__,
317 UGETW(osDev->adapterDevice->cdesc->wTotalLength), osDev->adapterDevice->cdesc->bDescriptorType);
318 dev->descriptorsLength += count;
319 } while (dev->descriptorsLength == allocLen);
320
321 return HDF_SUCCESS;
322 }
323
OsParseConfigDescriptors(struct UsbDevice * dev)324 static int32_t OsParseConfigDescriptors(struct UsbDevice *dev)
325 {
326 uint8_t i;
327 uint8_t numConfigs;
328 uint8_t *buffer = NULL;
329 size_t descLen;
330 struct UsbAdapterDeviceDescriptor *deviceDesc = NULL;
331 struct OsDev *osDev = (struct OsDev *)dev->privateData;
332 deviceDesc = &osDev->adapterDevice->ddesc;
333 numConfigs = deviceDesc->bNumConfigurations;
334 if (numConfigs == 0) {
335 return HDF_SUCCESS;
336 }
337 dev->configDescriptors = RawUsbMemAlloc(numConfigs * sizeof(struct UsbDeviceConfigDescriptor));
338 if (dev->configDescriptors == NULL) {
339 DPRINTFN(0, "%s:%d\n", __func__, __LINE__);
340 return HDF_ERR_MALLOC_FAIL;
341 }
342 buffer = (uint8_t *)dev->descriptors;
343 descLen = dev->descriptorsLength;
344
345 for (i = 0; i < numConfigs; i++) {
346 struct UsbConfigDescriptor *configDesc = NULL;
347 uint16_t configLen;
348
349 if (descLen < USB_DDK_DT_CONFIG_SIZE) {
350 DPRINTFN(0, "%s:%d read %zu", __func__, __LINE__, descLen);
351 return HDF_ERR_IO;
352 }
353 configDesc = (struct UsbConfigDescriptor *)buffer;
354 if ((configDesc->bDescriptorType != USB_DDK_DT_CONFIG) ||
355 (configDesc->bLength < USB_DDK_DT_CONFIG_SIZE)) {
356 DPRINTFN(0, "%s:%d config desc error: type 0x%02x, length %u\n",
357 __func__, __LINE__, configDesc->bDescriptorType, configDesc->bLength);
358 return HDF_ERR_IO;
359 }
360 configLen = Le16ToCpu(configDesc->wTotalLength);
361 if (configLen < USB_DDK_DT_CONFIG_SIZE) {
362 DPRINTFN(0, "invalid wTotalLength value %u\n", configLen);
363 return HDF_ERR_IO;
364 }
365 if (configLen > descLen) {
366 DPRINTFN(0, "%s:%d read %zu/%u\n",
367 __func__, __LINE__, descLen, configLen);
368 configLen = (uint16_t)descLen;
369 }
370 dev->configDescriptors[i].desc = configDesc;
371 dev->configDescriptors[i].actualLen = configLen;
372 buffer += configLen;
373 descLen -= configLen;
374 }
375 return HDF_SUCCESS;
376 }
377
OsDevAllocInit(void)378 static struct OsDev *OsDevAllocInit(void)
379 {
380 struct OsDev *osDev = NULL;
381 osDev = RawUsbMemCalloc(sizeof(*osDev));
382 if (osDev == NULL) {
383 return NULL;
384 }
385 DListHeadInit(&osDev->asyncCompleted);
386 OsalSemInit(&osDev->cvWait, 0);
387 LOS_SpinInit(&osDev->completeLock);
388 OsalMutexInit(&osDev->completeMux);
389 return osDev;
390 }
391
OsDevDestory(struct OsDev * osDev)392 static void OsDevDestory(struct OsDev *osDev)
393 {
394 if (osDev == NULL) {
395 DPRINTFN(0, "invalid parma\n");
396 return;
397 }
398 OsalSemDestroy(&osDev->cvWait);
399 OsalMutexDestroy(&osDev->completeMux);
400 RawUsbMemFree(osDev);
401 }
402
OsInitDevice(struct UsbDevice * dev,uint8_t busNum,uint8_t devAddr)403 static int32_t OsInitDevice(struct UsbDevice *dev, uint8_t busNum, uint8_t devAddr)
404 {
405 struct OsDev *osDev = NULL;
406 int32_t ret;
407
408 dev->busNum = busNum;
409 dev->devAddr = devAddr;
410 osDev = OsDevAllocInit();
411 if (osDev == NULL) {
412 DPRINTFN(0, "%s:%d osDev is NULL\n", __func__, __LINE__);
413 return HDF_DEV_ERR_NO_DEVICE;
414 }
415 g_CompleteExit = false;
416 #ifdef LOSCFG_DRIVERS_HDF_USB_PNP_NOTIFY
417 struct UsbGetDevicePara paraData;
418 paraData.type = USB_PNP_DEVICE_ADDRESS_TYPE;
419 paraData.busNum = dev->busNum;
420 paraData.devNum = dev->devAddr;
421 osDev->adapterDevice = UsbPnpNotifyGetUsbDevice(paraData);
422 #else
423 osDev->adapterDevice = NULL;
424 #endif
425 if (osDev->adapterDevice == NULL) {
426 DPRINTFN(0, "%s:%d osDev->adapterDevice is NULL\n", __func__, __LINE__);
427 return HDF_DEV_ERR_NO_DEVICE;
428 }
429
430 dev->privateData = (void *)osDev;
431 dev->descriptorsLength = 0;
432 ret = OsReadDescriptors(dev);
433 if (ret != HDF_SUCCESS) {
434 DPRINTFN(0, "%s:%d ret=%d\n", __func__, __LINE__, ret);
435 return ret;
436 }
437 ret = OsParseConfigDescriptors(dev);
438 if (ret != HDF_SUCCESS) {
439 DPRINTFN(0, "%s:%d ret=%d\n", __func__, __LINE__, ret);
440 return ret;
441 }
442 ret = memcpy_s(&dev->deviceDescriptor, sizeof(struct UsbDeviceDescriptor),
443 &osDev->adapterDevice->ddesc, USB_DDK_DT_DEVICE_SIZE);
444 if (ret != HDF_SUCCESS) {
445 DPRINTFN(0, "%s:%d ret=%d\n", __func__, __LINE__, ret);
446 ret = HDF_ERR_IO;
447 }
448 return ret;
449 }
450
OsFreeIsoUrbs(struct UsbHostRequest * request)451 static void OsFreeIsoUrbs(struct UsbHostRequest *request)
452 {
453 struct Async *urb = NULL;
454
455 for (int32_t i = 0; i < request->numUrbs; i++) {
456 urb = request->isoUrbs[i];
457 if (urb == NULL) {
458 break;
459 }
460 RawUsbMemFree(urb);
461 request->isoUrbs[i] = NULL;
462 }
463
464 RawUsbMemFree(request->isoUrbs);
465 request->isoUrbs = NULL;
466 }
467
OsDiscardUrbs(const struct UsbHostRequest * request,int32_t first,int32_t last)468 static void OsDiscardUrbs(const struct UsbHostRequest *request, int32_t first, int32_t last)
469 {
470 struct UsbAdapterUrb *urb = NULL;
471 struct Async *as = NULL;
472
473 if ((request == NULL) || (request->devHandle == NULL) ||
474 (first > URBS_PER_REQUEST) || (first > last)) {
475 DPRINTFN(0, "%s:%d invalid param", __func__, __LINE__);
476 return;
477 }
478
479 for (int32_t i = last - 1; i >= first; i--) {
480 if (request->requestType == USB_REQUEST_TYPE_ISOCHRONOUS) {
481 as = (struct Async *)request->isoUrbs[i];
482 } else {
483 as = &(((struct Async *)request->urbs)[i]);
484 }
485 if (as == NULL) {
486 DPRINTFN(0, "discard as null\n");
487 return;
488 }
489 urb = &as->urb;
490 if (as->state == URB_SUBMIT_STATE) {
491 DPRINTFN(0, "usb kill urb\n");
492 usb_kill_urb(urb);
493 DPRINTFN(0, "%s:%d discard request%p+as:%p\n", __func__, __LINE__, request, as);
494 }
495 }
496 }
497
OsSubmitControlMsg(struct UsbHostRequest * const request,const struct UsbAdapterDevice * adapterDevice,const struct UsbDevice * dev)498 static int32_t OsSubmitControlMsg(
499 struct UsbHostRequest * const request, const struct UsbAdapterDevice *adapterDevice, const struct UsbDevice *dev)
500 {
501 int32_t ret;
502 struct Async *as = NULL;
503 struct UsbAdapterUrb *urb = NULL;
504 struct UsbAdapterHostEndpoint *uhe = NULL;
505 if ((request == NULL) || (request->length > MAX_BULK_DATA_BUFFER_LENGTH)
506 || (request->buffer == NULL) || (adapterDevice == NULL) || (dev == NULL)) {
507 return HDF_ERR_INVALID_PARAM;
508 }
509 uhe = usb_find_host_endpoint((struct UsbAdapterDevice *)adapterDevice, request->requestType, request->endPoint);
510 if (uhe == NULL) {
511 DPRINTFN(0, "no found endpoint\n");
512 return -1;
513 }
514 if (request->urbs == NULL) {
515 as = RawUsbMemCalloc(sizeof(*as));
516 request->urbs = (void *)as;
517 request->numUrbs = 1;
518 }
519
520 if (request->urbs == NULL) {
521 DPRINTFN(0, "%s:%d no mem", __func__, __LINE__);
522 return HDF_ERR_MALLOC_FAIL;
523 }
524 as = (struct Async *)request->urbs;
525 DListHeadInit(&as->asynclist);
526 as->dev = (struct UsbDevice *)dev;
527 as->state = URB_SUBMIT_STATE;
528 urb = &as->urb;
529 ret = memset_s(urb, sizeof(*urb), 0, sizeof(*urb));
530 if (ret != HDF_SUCCESS) {
531 HDF_LOGE("%{public}s:%{public}d memset_s failed", __func__, __LINE__);
532 return HDF_FAILURE;
533 }
534
535 urb->dev = (struct UsbAdapterDevice *)adapterDevice;
536 urb->endpoint = uhe;
537 urb->timeout = 500;
538 urb->transfer_buffer = request->buffer;
539 urb->context = (void *)request;
540 urb->complete = OsUrbComplete;
541 ret = OsControlMsg(urb);
542 DPRINTFN(0, "OsSubmitControlRequest:ret:%d\n", ret);
543 if (ret) {
544 DPRINTFN(0, "submiturb failed, errno=%d\n", errno);
545 return HDF_ERR_IO;
546 }
547
548 return HDF_SUCCESS;
549 }
550
OsSubmitControlRequest(struct UsbHostRequest * request)551 static int32_t OsSubmitControlRequest(struct UsbHostRequest *request)
552 {
553 struct OsDev *osDev = NULL;
554 struct UsbAdapterDevice *adapterDevice = NULL;
555
556 if ((request == NULL) || (request->length > MAX_BULK_DATA_BUFFER_LENGTH)
557 || (request->devHandle == NULL) || (request->buffer == NULL)) {
558 return HDF_ERR_INVALID_PARAM;
559 }
560 struct UsbDeviceHandle *handle = request->devHandle;
561 struct UsbDevice *dev = handle->dev;
562 if (dev) {
563 osDev = (struct OsDev *)dev->privateData;
564 }
565 if (osDev) {
566 adapterDevice = osDev->adapterDevice;
567 }
568
569 return OsSubmitControlMsg(request, adapterDevice, dev);
570 }
571
OsSubmitBulkRequestHandleUrb(struct Async * pas,struct UsbHostRequest * request,int32_t bulkBufferLen,int32_t number)572 static int32_t OsSubmitBulkRequestHandleUrb(struct Async *pas, struct UsbHostRequest *request,
573 int32_t bulkBufferLen, int32_t number)
574 {
575 struct UsbAdapterUrb *urb = NULL;
576
577 if (bulkBufferLen == 0) {
578 HDF_LOGE("%s:%d bulkBufferLen can not be zero", __func__, __LINE__);
579 return HDF_ERR_INVALID_PARAM;
580 }
581
582 urb = &pas->urb;
583 urb->context = (void *)request;
584 switch (request->requestType) {
585 case USB_REQUEST_TYPE_BULK:
586 break;
587 case USB_REQUEST_TYPE_INTERRUPT:
588 urb->interval = 50;
589 break;
590 default:
591 DPRINTFN(0, "%s:%d unknown requestType=%u\n", __func__, __LINE__,
592 request->requestType);
593 return HDF_ERR_INVALID_PARAM;
594 }
595 urb->transfer_buffer = request->buffer + (number * bulkBufferLen);
596 urb->complete = OsUrbComplete;
597 if (number == request->numUrbs - 1) {
598 uint32_t len = (uint32_t)(request->length % bulkBufferLen);
599 urb->transfer_buffer_length = (len == 0) ? (uint32_t)bulkBufferLen : len;
600 } else {
601 urb->transfer_buffer_length = (uint32_t)bulkBufferLen;
602 }
603
604 return HDF_SUCCESS;
605 }
606
OsSubmitBulkRequestHandle(struct UsbHostRequest * const request,struct Async * const as,int32_t bulkBufferLen)607 static int32_t OsSubmitBulkRequestHandle(
608 struct UsbHostRequest * const request, struct Async * const as, int32_t bulkBufferLen)
609 {
610 struct Async *pas = NULL;
611 int32_t numUrbs = request->numUrbs;
612 int32_t i;
613 int32_t ret;
614 struct UsbDevice *dev = request->devHandle->dev;
615 struct OsDev *osDev = (struct OsDev *)dev->privateData;
616 struct UsbAdapterDevice *adapterDevice = osDev->adapterDevice;
617 struct UsbAdapterHostEndpoint *uhe = NULL;
618 struct UsbAdapterUrb *urb = NULL;
619
620 uhe = usb_find_host_endpoint(adapterDevice, request->requestType, request->endPoint);
621 if (uhe == NULL) {
622 DPRINTFN(0, "no found endpoint\n");
623 return HDF_DEV_ERR_NO_DEVICE;
624 }
625
626 for (i = 0, pas = as; i < numUrbs; i++, pas++) {
627 urb = &pas->urb;
628 ret = memset_s(urb, sizeof(*urb), 0, sizeof(*urb));
629 if (ret != HDF_SUCCESS) {
630 HDF_LOGE("%{public}s:%{public}d memset_s failed", __func__, __LINE__);
631 return HDF_FAILURE;
632 }
633
634 ret = OsSubmitBulkRequestHandleUrb(pas, request, bulkBufferLen, i);
635 if (ret != HDF_SUCCESS) {
636 return ret;
637 }
638 pas->state = URB_SUBMIT_STATE;
639 DListHeadInit(&pas->asynclist);
640 pas->dev = dev;
641 urb->dev = adapterDevice;
642 urb->endpoint = uhe;
643
644 ret = OsSubmitUrb(urb, urb->dev, urb->endpoint);
645 if (ret == 0) {
646 continue;
647 }
648 if (i == 0) {
649 DPRINTFN(0, "the first urb failed\n");
650 return HDF_ERR_IO;
651 }
652 OsalMutexLock(&request->lock);
653 request->numRetired += numUrbs - i;
654 if (errno != EREMOTEIO) {
655 request->reqStatus = USB_REQUEST_ERROR;
656 }
657 OsDiscardUrbs(request, 0, i);
658 OsalMutexUnlock(&request->lock);
659 return HDF_SUCCESS;
660 }
661
662 return HDF_SUCCESS;
663 }
664
OsSubmitBulkRequest(struct UsbHostRequest * const request)665 static int32_t OsSubmitBulkRequest(struct UsbHostRequest * const request)
666 {
667 struct Async *as = NULL;
668 uint32_t bulkBufferLen;
669 int32_t numUrbs;
670
671 if ((request == NULL) || (request->devHandle == NULL)) {
672 DPRINTFN(0, "%s: invalid param", __func__);
673 return HDF_ERR_INVALID_PARAM;
674 }
675
676 if (request->length > MAX_BULK_DATA_BUFFER_LENGTH || request->length <= 0) {
677 DPRINTFN(0, "Bulk request size err\n");
678 return HDF_FAILURE;
679 }
680
681 if (request->devHandle->caps & USB_ADAPTER_CAP_BULK_SCATTER_GATHER) {
682 bulkBufferLen = request->length ? request->length : 1;
683 } else {
684 bulkBufferLen = MAX_BULK_DATA_BUFFER_LENGTH;
685 }
686 if (request->length < bulkBufferLen) {
687 numUrbs = 1;
688 } else {
689 numUrbs = (request->length + bulkBufferLen - 1) / bulkBufferLen;
690 }
691 if (request->urbs == NULL) {
692 as = RawUsbMemCalloc(sizeof(*as));
693 request->urbs = (void *)as;
694 } else if (numUrbs > 1) {
695 RawUsbMemFree(request->urbs);
696 as = RawUsbMemCalloc(numUrbs * sizeof(*as));
697 request->urbs = (void *)as;
698 }
699 if (request->urbs == NULL) {
700 DPRINTFN(0, "%s:%d no mem", __func__, __LINE__);
701 return HDF_ERR_MALLOC_FAIL;
702 }
703 as = (struct Async *)request->urbs;
704 request->numUrbs = numUrbs;
705 request->numRetired = 0;
706 request->reqStatus = USB_REQUEST_COMPLETED;
707
708 return OsSubmitBulkRequestHandle(request, as, bulkBufferLen);
709 }
710
OsAllocIsoUrbs(struct UsbHostRequest * request,int32_t numUrbs,struct Async ** ass)711 static int32_t OsAllocIsoUrbs(struct UsbHostRequest *request, int32_t numUrbs, struct Async **ass)
712 {
713 struct Async *as = NULL;
714 unsigned char *urbBuffer = request->buffer;
715 int32_t numPacketsLeft = request->numIsoPackets;
716 int32_t packetIdx = 0;
717 int32_t i, j;
718
719 UsbPipeType pipeType = request->requestType;
720 unsigned char endPoint = request->endPoint;
721 struct UsbDeviceHandle *handle = request->devHandle;
722 struct UsbDevice *dev = handle->dev;
723 struct OsDev *osDev = (struct OsDev *)dev->privateData;
724 struct UsbAdapterDevice *adapterDevice = osDev->adapterDevice;
725 struct UsbAdapterHostEndpoint *uhe = NULL;
726 uhe = usb_find_host_endpoint(adapterDevice, pipeType, endPoint);
727 if (uhe == NULL) {
728 DPRINTFN(0, "no found endpoint\n");
729 return HDF_DEV_ERR_NO_DEVICE;
730 }
731
732 for (i = 0; i < numUrbs; i++) {
733 struct UsbAdapterUrb *urb = NULL;
734 int32_t numPackets = MIN(numPacketsLeft, MAX_ISO_PACKETS_PER_URB);
735 as = RawUsbMemCalloc(sizeof(struct Async));
736 if (as == NULL) {
737 OsFreeIsoUrbs(request);
738 return HDF_ERR_MALLOC_FAIL;
739 }
740 ass[i] = as;
741 urb = &as->urb;
742 for (j = 0; j < numPackets; j++) {
743 unsigned int packetLen = request->isoPacketDesc[packetIdx++].length;
744 urb->transfer_buffer_length += packetLen;
745 urb->iso_frame_desc[j].length = packetLen;
746 }
747 urb->endpoint = uhe;
748 urb->number_of_packets = (unsigned int)numPackets;
749 urb->transfer_buffer = urbBuffer;
750 urb->context = request;
751 urbBuffer += urb->transfer_buffer_length;
752 numPacketsLeft -= numPackets;
753 }
754
755 return HDF_SUCCESS;
756 }
757
OsSubmitIsoUrbs(struct UsbHostRequest * request,int32_t numUrbs,struct Async ** pUrbs)758 static int32_t OsSubmitIsoUrbs(struct UsbHostRequest *request, int32_t numUrbs, struct Async **pUrbs)
759 {
760 int32_t i;
761 int32_t ret;
762
763 for (i = 0; i < numUrbs; i++) {
764 struct UsbAdapterUrb *urb = &(pUrbs[i]->urb);
765 ret = OsSubmitUrb(urb, urb->dev, urb->endpoint);
766 DPRINTFN(0, "submitUrb:%d errno=%d\n", ret, errno);
767 if (ret == 0) {
768 continue;
769 }
770
771 if (errno == ENODEV) {
772 ret = HDF_DEV_ERR_NO_DEVICE;
773 } else {
774 DPRINTFN(0, "%s:%d submit iso urb failed errno=%d\n", __func__, __LINE__, errno);
775 ret = HDF_ERR_IO;
776 }
777
778 if (i == 0) {
779 DPRINTFN(0, "first URB failed");
780 OsFreeIsoUrbs(request);
781 return ret;
782 }
783
784 OsalMutexLock(&request->lock);
785 request->reqStatus = USB_REQUEST_ERROR;
786 request->numRetired += numUrbs - i;
787 if (request->numRetired == numUrbs) {
788 RawUsbMemFree(pUrbs);
789 request->isoUrbs = NULL;
790 }
791 OsalMutexUnlock(&request->lock);
792
793 break;
794 }
795
796 return HDF_SUCCESS;
797 }
798
OsSubmitIsoRequest(struct UsbHostRequest * request)799 static int32_t OsSubmitIsoRequest(struct UsbHostRequest *request)
800 {
801 struct Async **pUrbs = NULL;
802 int32_t numUrbs;
803 unsigned int packetLen;
804 unsigned int totalLen = 0;
805 int32_t ret;
806
807 if ((request == NULL) || (request->devHandle == NULL) || (request->numIsoPackets < 1)) {
808 DPRINTFN(0, "%s:%d invalid param", __func__, __LINE__);
809 return HDF_ERR_INVALID_PARAM;
810 }
811
812 if (request->length > MAX_ISO_DATA_BUFFER_LEN) {
813 DPRINTFN(0, "%s:%d request length exceed the maximum", __func__, __LINE__);
814 return HDF_ERR_NOT_SUPPORT;
815 }
816
817 for (int32_t i = 0; i < request->numIsoPackets; i++) {
818 packetLen = request->isoPacketDesc[i].length;
819 if (packetLen > MAX_ISO_DATA_BUFFER_LEN) {
820 DPRINTFN(0, "%s:%d packet length: %u exceeds maximum: %u\n",
821 __func__, __LINE__, packetLen, MAX_ISO_DATA_BUFFER_LEN);
822 return HDF_ERR_INVALID_PARAM;
823 }
824 totalLen += packetLen;
825 }
826 if (request->length < totalLen) {
827 DPRINTFN(0, "%s:%d invalid param", __func__, __LINE__);
828 return HDF_ERR_INVALID_PARAM;
829 }
830 numUrbs = (request->numIsoPackets + (MAX_ISO_PACKETS_PER_URB - 1)) / MAX_ISO_PACKETS_PER_URB;
831 pUrbs = RawUsbMemCalloc(numUrbs * sizeof(struct Async*));
832 if (pUrbs == NULL) {
833 DPRINTFN(0, "%s:%d RawUsbMemCalloc pUrbs failed", __func__, __LINE__);
834 return HDF_ERR_MALLOC_FAIL;
835 }
836 request->isoUrbs = (void **)pUrbs;
837 request->numUrbs = numUrbs;
838 request->numRetired = 0;
839 request->isoPacketOffset = 0;
840 ret = OsAllocIsoUrbs(request, numUrbs, pUrbs);
841 if (ret != HDF_SUCCESS) {
842 DPRINTFN(0, "%s:%d alloc iso urbs failed", __func__, __LINE__);
843 return ret;
844 }
845
846 return OsSubmitIsoUrbs(request, numUrbs, pUrbs);
847 }
848
OsControlCompletion(struct UsbHostRequest * request,struct Async * as)849 static int32_t OsControlCompletion(struct UsbHostRequest *request, struct Async *as)
850 {
851 int32_t status;
852 struct UsbAdapterUrb *urb = &as->urb;
853
854 OsalMutexLock(&request->lock);
855 request->numRetired++;
856 request->actualLength += (int)urb->actual_length;
857 if (request->reqStatus == USB_REQUEST_CANCELLED) {
858 OsalMutexUnlock(&request->lock);
859 as->state = URB_INIT_STATE;
860 return RawHandleRequestCompletion(request, USB_REQUEST_CANCELLED);
861 }
862
863 switch (urb->status) {
864 case 0:
865 status = USB_REQUEST_COMPLETED;
866 break;
867 case -ENOENT:
868 status = USB_REQUEST_CANCELLED;
869 break;
870 case -EPIPE:
871 DPRINTFN(0, "%s:%d unsupported control request", __func__, __LINE__);
872 status = USB_REQUEST_STALL;
873 break;
874 case -EOVERFLOW:
875 DPRINTFN(0, "%s:%d overflow actualLength=%d\n", __func__, __LINE__, urb->actual_length);
876 status = USB_REQUEST_OVERFLOW;
877 break;
878 case -ENODEV:
879 case -ESHUTDOWN:
880 DPRINTFN(0, "device removed");
881 status = USB_REQUEST_NO_DEVICE;
882 break;
883 default:
884 DPRINTFN(0, "%s:%d urb status=%d\n", __func__, __LINE__, urb->status);
885 status = USB_REQUEST_ERROR;
886 break;
887 }
888 OsalMutexUnlock(&request->lock);
889 as->state = URB_INIT_STATE;
890 return RawHandleRequestCompletion(request, status);
891 }
892
OsIsoRequestDesStatus(struct UsbHostRequest * request,struct UsbAdapterUrb * urb)893 static void OsIsoRequestDesStatus(struct UsbHostRequest *request, struct UsbAdapterUrb *urb)
894 {
895 uint32_t i;
896 struct UsbAdapterIsoPacketDescriptor *urbDesc = NULL;
897 struct UsbIsoPacketDesc *requestDesc = NULL;
898
899 for (i = 0; i < urb->number_of_packets; i++) {
900 urbDesc = &urb->iso_frame_desc[i];
901 requestDesc = &request->isoPacketDesc[request->isoPacketOffset++];
902
903 switch (urbDesc->status) {
904 case HDF_SUCCESS:
905 requestDesc->status = USB_REQUEST_COMPLETED;
906 break;
907 case -ENODEV:
908 case -ESHUTDOWN:
909 requestDesc->status = USB_REQUEST_NO_DEVICE;
910 break;
911 case -EPIPE:
912 requestDesc->status = USB_REQUEST_STALL;
913 break;
914 case -EOVERFLOW:
915 requestDesc->status = USB_REQUEST_OVERFLOW;
916 break;
917 default:
918 requestDesc->status = USB_REQUEST_ERROR;
919 break;
920 }
921 DPRINTFN(0, "%s:%d urb status=%d-%d\n", __func__, __LINE__, i, urbDesc->status);
922
923 requestDesc->actualLength = urbDesc->actual_length;
924 }
925 }
926
OsIsoCompletion(struct UsbHostRequest * request,struct Async * as)927 static int32_t OsIsoCompletion(struct UsbHostRequest *request, struct Async *as)
928 {
929 UsbRequestStatus status;
930 int32_t urbIndex = 0;
931 int32_t numUrbs;
932 struct UsbAdapterUrb *urb = &as->urb;
933
934 if (request == NULL) {
935 DPRINTFN(0, "%s:%d invalid param", __func__, __LINE__);
936 return HDF_ERR_INVALID_PARAM;
937 }
938
939 numUrbs = request->numUrbs;
940 OsalMutexLock(&request->lock);
941 for (int32_t i = 0; i < numUrbs; i++) {
942 if (urb == request->isoUrbs[i]) {
943 urbIndex = i + 1;
944 break;
945 }
946 }
947 if (urbIndex == 0) {
948 DPRINTFN(0, "%s:%d urbIndex is zero", __func__, __LINE__);
949 OsalMutexUnlock(&request->lock);
950 return HDF_ERR_BAD_FD;
951 }
952
953 OsIsoRequestDesStatus(request, urb);
954 request->numRetired++;
955 if (request->reqStatus != USB_REQUEST_COMPLETED) {
956 DPRINTFN(0, "%s:%d urb status=%d\n", __func__, __LINE__, urb->status);
957 if (request->numRetired == numUrbs) {
958 OsFreeIsoUrbs(request);
959 OsalMutexUnlock(&request->lock);
960 return RawHandleRequestCompletion(request, USB_REQUEST_ERROR);
961 }
962 goto OUT;
963 }
964
965 DPRINTFN(0, "%s:%d urb status is %d\n", __func__, __LINE__, urb->status);
966 if (urb->status == -ESHUTDOWN) {
967 status = USB_REQUEST_NO_DEVICE;
968 } else if (!((urb->status == HDF_SUCCESS) || (urb->status == -ENOENT) ||
969 (urb->status == -ECONNRESET))) {
970 status = USB_REQUEST_ERROR;
971 } else {
972 status = USB_REQUEST_COMPLETED;
973 }
974
975 if (request->numRetired == numUrbs) {
976 DPRINTFN(0, "%s:%d all URBs reaped for complete", __func__, __LINE__);
977 OsFreeIsoUrbs(request);
978 OsalMutexUnlock(&request->lock);
979 return RawHandleRequestCompletion(request, status);
980 }
981 OUT:
982 OsalMutexUnlock(&request->lock);
983 return HDF_SUCCESS;
984 }
985
OsProcessAbnormalReap(struct UsbHostRequest * request,const struct UsbAdapterUrb * urb)986 static int32_t OsProcessAbnormalReap(struct UsbHostRequest *request, const struct UsbAdapterUrb *urb)
987 {
988 int32_t ret;
989
990 if (urb->actual_length > 0) {
991 unsigned char *target = request->buffer + request->actualLength;
992 if (urb->transfer_buffer != target) {
993 ret = memmove_s(target, urb->actual_length, urb->transfer_buffer, urb->actual_length);
994 if (ret != EOK) {
995 DPRINTFN(0, "%s: memmove_s failed, ret=%d", __func__, ret);
996 }
997 }
998 request->actualLength += urb->actual_length;
999 }
1000 if (request->numRetired == request->numUrbs) {
1001 return HDF_SUCCESS;
1002 }
1003
1004 return HDF_ERR_IO;
1005 }
1006
OsUrbStatusToRequestStatus(struct UsbHostRequest * request,const struct UsbAdapterUrb * urb)1007 static int32_t OsUrbStatusToRequestStatus(struct UsbHostRequest *request, const struct UsbAdapterUrb *urb)
1008 {
1009 int32_t ret;
1010
1011 switch (urb->status) {
1012 case 0:
1013 ret = HDF_SUCCESS;
1014 break;
1015 case -ESHUTDOWN:
1016 DPRINTFN(0, "%s:%d device is removed", __func__, __LINE__);
1017 request->reqStatus = USB_REQUEST_NO_DEVICE;
1018 ret = HDF_DEV_ERR_NO_DEVICE;
1019 break;
1020 case -EPIPE:
1021 if (request->reqStatus == USB_REQUEST_COMPLETED) {
1022 request->reqStatus = USB_REQUEST_STALL;
1023 }
1024 ret = HDF_DEV_ERR_NO_DEVICE;
1025 break;
1026 case -EOVERFLOW:
1027 DPRINTFN(0, "%s:%d overflow error, actualLength=%d\n",
1028 __func__, __LINE__, urb->actual_length);
1029 if (request->reqStatus == USB_REQUEST_COMPLETED) {
1030 request->reqStatus = USB_REQUEST_OVERFLOW;
1031 }
1032 ret = HDF_FAILURE;
1033 break;
1034 case -ECONNRESET:
1035 ret = HDF_DEV_ERR_OP;
1036 if (request->reqStatus == USB_REQUEST_COMPLETED) {
1037 request->reqStatus = USB_REQUEST_CANCELLED;
1038 }
1039 break;
1040 default:
1041 DPRINTFN(0, "unknown urb status %d\n", urb->status);
1042 if (request->reqStatus == USB_REQUEST_COMPLETED) {
1043 request->reqStatus = USB_REQUEST_ERROR;
1044 }
1045 ret = HDF_FAILURE;
1046 break;
1047 }
1048
1049 return ret;
1050 }
1051
OsBulkCompletion(struct UsbHostRequest * const request,struct Async * const as)1052 static int32_t OsBulkCompletion(struct UsbHostRequest * const request, struct Async * const as)
1053 {
1054 int32_t ret;
1055 int32_t urbIdx = as - (struct Async *)request->urbs;
1056 const struct UsbAdapterUrb *urb = &as->urb;
1057
1058 OsalMutexLock(&request->lock);
1059 request->numRetired++;
1060 if (request->reqStatus != USB_REQUEST_COMPLETED) {
1061 if (OsProcessAbnormalReap(request, urb) == HDF_SUCCESS) {
1062 goto COMPLETED;
1063 } else {
1064 goto OUT;
1065 }
1066 }
1067 request->actualLength += urb->actual_length;
1068 ret = OsUrbStatusToRequestStatus(request, urb);
1069 if (ret == HDF_DEV_ERR_NO_DEVICE) {
1070 goto CANCEL;
1071 } else if (ret == HDF_FAILURE) {
1072 goto COMPLETED;
1073 }
1074
1075 if (request->numRetired == request->numUrbs) {
1076 goto COMPLETED;
1077 } else if (urb->actual_length < urb->transfer_buffer_length) {
1078 if (request->reqStatus == USB_REQUEST_COMPLETED) {
1079 request->reqStatus = USB_REQUEST_COMPLETED_SHORT;
1080 }
1081 } else {
1082 goto OUT;
1083 }
1084
1085 CANCEL:
1086 if (request->numRetired == request->numUrbs) {
1087 goto COMPLETED;
1088 }
1089 OsDiscardUrbs(request, urbIdx + 1, request->numUrbs);
1090
1091 OUT:
1092 OsalMutexUnlock(&request->lock);
1093 return HDF_SUCCESS;
1094
1095 COMPLETED:
1096 OsalMutexUnlock(&request->lock);
1097 as->state = URB_INIT_STATE;
1098 return RawHandleRequestCompletion(request, request->reqStatus);
1099 }
1100
OsFreeRequest(const struct UsbHostRequest * request)1101 static int32_t OsFreeRequest(const struct UsbHostRequest *request)
1102 {
1103 int32_t retry = 0;
1104 if (request == NULL) {
1105 DPRINTFN(0, "%s:%d invalid param", __func__, __LINE__);
1106 return HDF_ERR_INVALID_PARAM;
1107 }
1108
1109 while (true) {
1110 OsalMSleep(20);
1111 if (request->numUrbs != request->numRetired) {
1112 if (++retry > 10) {
1113 DPRINTFN(0, "request busy numUrbs:%d+numretired:%d\n", request->numUrbs, request->numRetired);
1114 return HDF_ERR_DEVICE_BUSY;
1115 }
1116 continue;
1117 } else {
1118 break;
1119 }
1120 }
1121
1122 return HDF_SUCCESS;
1123 }
1124
AdapterInit(const struct UsbSession * session)1125 static int32_t AdapterInit(const struct UsbSession *session)
1126 {
1127 return HDF_SUCCESS;
1128 }
1129
AdapterExit(const struct UsbSession * session)1130 static void AdapterExit(const struct UsbSession *session)
1131 {
1132 return;
1133 }
1134
AdapterOpenDevice(struct UsbSession * session,uint8_t busNum,uint8_t usbAddr)1135 static struct UsbDeviceHandle *AdapterOpenDevice(struct UsbSession *session, uint8_t busNum, uint8_t usbAddr)
1136 {
1137 int32_t ret;
1138 struct UsbDevice *dev = NULL;
1139 struct UsbDeviceHandle *handle = NULL;
1140
1141 handle = OsGetDeviceHandle(session, busNum, usbAddr);
1142 if (handle != NULL) {
1143 return handle;
1144 }
1145 handle = OsCallocDeviceHandle();
1146 if (handle == NULL) {
1147 DPRINTFN(0, "%s: Calloc Device Handle failed", __func__);
1148 return NULL;
1149 }
1150 dev = OsAllocDevice(session, handle);
1151 if (dev == NULL) {
1152 DPRINTFN(0, "%s: OsAllocDevice failed\n", __func__);
1153 goto ERR;
1154 }
1155 ret = OsInitDevice(dev, busNum, usbAddr);
1156 if (ret) {
1157 DPRINTFN(0, "%s: OsInitDevice failed ret=%d\n", __func__, ret);
1158 RawUsbMemFree(dev);
1159 goto ERR;
1160 }
1161 OsalAtomicSet(&dev->refcnt, 1);
1162 OsalMutexLock(&session->lock);
1163 HdfSListAdd(&session->usbDevs, &dev->list);
1164 OsalMutexUnlock(&session->lock);
1165 return handle;
1166 ERR:
1167 OsalMutexDestroy(&handle->lock);
1168 RawUsbMemFree(handle);
1169 return NULL;
1170 }
1171
AdapterCloseDevice(struct UsbDeviceHandle * handle)1172 static void AdapterCloseDevice(struct UsbDeviceHandle *handle)
1173 {
1174 struct UsbDevice *dev = NULL;
1175
1176 if ((handle == NULL) || (handle->dev == NULL)) {
1177 DPRINTFN(0, "%s:%d invalid param", __func__, __LINE__);
1178 return;
1179 }
1180 if (RawKillSignal(handle, 0) != HDF_SUCCESS) {
1181 HDF_LOGE("%s:%d RawKillSignal failed", __func__, __LINE__);
1182 }
1183 dev = handle->dev;
1184 if (AdapterAtomicDec(&dev->refcnt)) {
1185 return;
1186 }
1187 if (dev->session == NULL) {
1188 return;
1189 }
1190 OsalMutexLock(&dev->session->lock);
1191 HdfSListRemove(&dev->session->usbDevs, &dev->list);
1192 OsalMutexUnlock(&dev->session->lock);
1193
1194 if (dev->configDescriptors) {
1195 RawUsbMemFree(dev->configDescriptors);
1196 }
1197 if (dev->descriptors) {
1198 RawUsbMemFree(dev->descriptors);
1199 }
1200 if (dev->privateData) {
1201 OsDevDestory(dev->privateData);
1202 dev->privateData = NULL;
1203 }
1204 RawUsbMemFree(dev);
1205
1206 OsalMutexDestroy(&handle->lock);
1207 RawUsbMemFree(handle);
1208 }
1209
AdapterGetConfigDescriptor(const struct UsbDevice * dev,uint8_t configIndex,void * buffer,size_t len)1210 static int32_t AdapterGetConfigDescriptor(const struct UsbDevice *dev,
1211 uint8_t configIndex, void *buffer, size_t len)
1212 {
1213 struct OsDev *osDev = (struct OsDev *)dev->privateData;
1214 struct UsbAdapterDevice *adapterDevice = osDev->adapterDevice;
1215 size_t count;
1216 if ((buffer == NULL) || (len == 0) || (adapterDevice == NULL) || (adapterDevice->cdesc == NULL)) {
1217 DPRINTFN(0, "invalid param is NULL");
1218 return HDF_ERR_INVALID_PARAM;
1219 }
1220 count = UGETW(adapterDevice->cdesc->wTotalLength);
1221 if (count > len) {
1222 DPRINTFN(0, "count length is error");
1223 return HDF_ERR_IO;
1224 }
1225 if (memcpy_s(buffer, len, adapterDevice->cdesc, count) != EOK) {
1226 DPRINTFN(0, "memcpy_s fail");
1227 return HDF_ERR_IO;
1228 }
1229 return len;
1230 }
1231
AdapterGetConfiguration(const struct UsbDeviceHandle * handle,uint8_t * activeConfig)1232 static int32_t AdapterGetConfiguration(const struct UsbDeviceHandle *handle, uint8_t *activeConfig)
1233 {
1234 struct UsbDevice *dev = handle->dev;
1235 struct OsDev *osDev = (struct OsDev *)dev->privateData;
1236 struct UsbAdapterDevice *adapterDevice = osDev->adapterDevice;
1237
1238 if (adapterDevice != NULL) {
1239 *activeConfig = adapterDevice->curr_config_index;
1240 }
1241
1242 return HDF_SUCCESS;
1243 }
1244
AdapterSetConfiguration(struct UsbDeviceHandle * handle,int32_t activeConfig)1245 static int32_t AdapterSetConfiguration(struct UsbDeviceHandle *handle, int32_t activeConfig)
1246 {
1247 struct UsbDevice *dev = handle->dev;
1248 struct OsDev *osDev = (struct OsDev *)dev->privateData;
1249 struct UsbAdapterDevice *adapterDevice = osDev->adapterDevice;
1250
1251 if (adapterDevice->flags.usb_mode != USB_MODE_HOST) {
1252 return HDF_DEV_ERR_DEV_INIT_FAIL;
1253 }
1254 if ((activeConfig < 0) || (activeConfig >= (int)adapterDevice->curr_config_no)) {
1255 return HDF_ERR_INVALID_PARAM;
1256 }
1257 if (activeConfig == adapterDevice->curr_config_index) {
1258 return HDF_SUCCESS;
1259 }
1260 if (usbd_set_config_index(adapterDevice, activeConfig) != 0) {
1261 return HDF_ERR_IO;
1262 }
1263
1264 return HDF_SUCCESS;
1265 }
1266
AdapterClaimInterface(const struct UsbDeviceHandle * handle,unsigned int interfaceNumber)1267 static int32_t AdapterClaimInterface(const struct UsbDeviceHandle *handle, unsigned int interfaceNumber)
1268 {
1269 return HDF_SUCCESS;
1270 }
1271
AdapterReleaseInterface(const struct UsbDeviceHandle * handle,unsigned int interfaceNumber)1272 static int32_t AdapterReleaseInterface(const struct UsbDeviceHandle *handle, unsigned int interfaceNumber)
1273 {
1274 return HDF_SUCCESS;
1275 }
1276
AdapterSetInterface(const struct UsbDeviceHandle * handle,uint8_t interface,uint8_t altSetting)1277 static int32_t AdapterSetInterface(const struct UsbDeviceHandle *handle, uint8_t interface, uint8_t altSetting)
1278 {
1279 struct UsbDevice *dev = handle->dev;
1280 struct OsDev *osDev = (struct OsDev *)dev->privateData;
1281 struct UsbAdapterDevice *adapterDevice = osDev->adapterDevice;
1282
1283 if (adapterDevice->flags.usb_mode != USB_MODE_HOST) {
1284 return HDF_DEV_ERR_DEV_INIT_FAIL;
1285 }
1286 DPRINTFN(0, "altSetting interfaceId:%d+altSetting:%d\n", interface, altSetting);
1287 if (usb_set_interface(adapterDevice, interface, altSetting)) {
1288 return HDF_ERR_IO;
1289 }
1290
1291 return HDF_SUCCESS;
1292 }
1293
AdapterClearHalt(const struct UsbDeviceHandle * handle,unsigned int endPoint)1294 static int32_t AdapterClearHalt(const struct UsbDeviceHandle *handle, unsigned int endPoint)
1295 {
1296 struct UsbDevice *dev = handle->dev;
1297 struct OsDev *osDev = (struct OsDev *)dev->privateData;
1298 struct UsbAdapterDevice *adapterDevice = osDev->adapterDevice;
1299 int32_t ret;
1300 struct UsbAdapterHostEndpoint *uhe = usb_find_host_endpoint(adapterDevice, PIPE_BULK, endPoint);
1301 if (uhe == NULL) {
1302 printf("no found uhe\n");
1303 return -1;
1304 }
1305 ret = usb_clear_halt(adapterDevice, uhe);
1306 return ret;
1307 }
1308
AdapterResetDevice(const struct UsbDeviceHandle * handle)1309 static int32_t AdapterResetDevice(const struct UsbDeviceHandle *handle)
1310 {
1311 return HDF_SUCCESS;
1312 }
1313
AdapterAllocRequest(const struct UsbDeviceHandle * handle,int32_t isoPackets,size_t length)1314 static struct UsbHostRequest *AdapterAllocRequest(
1315 const struct UsbDeviceHandle *handle, int32_t isoPackets, size_t length)
1316 {
1317 size_t allocSize;
1318 struct UsbHostRequest *request = NULL;
1319
1320 allocSize = sizeof(struct UsbHostRequest)
1321 + (sizeof(struct UsbIsoPacketDesc) * (size_t)isoPackets)
1322 + (sizeof(unsigned char) * length);
1323 request = RawUsbMemCalloc(allocSize);
1324 if (request == NULL) {
1325 HDF_LOGE("%s RawMemAlloc fail", __func__);
1326 return NULL;
1327 }
1328 request->numIsoPackets = isoPackets;
1329 request->buffer = (unsigned char *)request + allocSize - length;
1330 request->bufLen = (int)length;
1331 return request;
1332 }
1333
AdapterFreeRequest(struct UsbHostRequest * request)1334 static int32_t AdapterFreeRequest(struct UsbHostRequest *request)
1335 {
1336 int32_t ret;
1337 if (request == NULL) {
1338 DPRINTFN(0, "%s:%d invalid param", __func__, __LINE__);
1339 return HDF_ERR_INVALID_PARAM;
1340 }
1341 if (request->numUrbs > request->numRetired) {
1342 OsDiscardUrbs(request, request->numRetired, request->numUrbs);
1343 ret = OsFreeRequest(request);
1344 if (ret != HDF_SUCCESS) {
1345 return ret;
1346 }
1347 }
1348 if (request->urbs) {
1349 RawUsbMemFree(request->urbs);
1350 request->urbs = NULL;
1351 }
1352 RawUsbMemFree((void *)request);
1353 return HDF_SUCCESS;
1354 }
1355
AdapterSubmitRequest(struct UsbHostRequest * request)1356 static int32_t AdapterSubmitRequest(struct UsbHostRequest *request)
1357 {
1358 int32_t ret;
1359
1360 if (request == NULL) {
1361 DPRINTFN(0, "%s:%d request is NULL", __func__, __LINE__);
1362 return HDF_FAILURE;
1363 }
1364 OsalMutexInit(&(request->lock));
1365 request->actualLength = 0;
1366 request->numRetired = 0;
1367 request->numUrbs = 0;
1368 switch (request->requestType) {
1369 case USB_REQUEST_TYPE_CONTROL:
1370 ret = OsSubmitControlRequest(request);
1371 break;
1372 case USB_REQUEST_TYPE_ISOCHRONOUS:
1373 ret = OsSubmitIsoRequest(request);
1374 break;
1375 case USB_REQUEST_TYPE_BULK:
1376 case USB_REQUEST_TYPE_INTERRUPT:
1377 ret = OsSubmitBulkRequest(request);
1378 break;
1379 default:
1380 DPRINTFN(0, "%s:%d unknown requestType=%u\n", __func__, __LINE__, request->requestType);
1381 ret = HDF_ERR_INVALID_PARAM;
1382 break;
1383 }
1384
1385 return ret;
1386 }
1387
AdapterCancelRequest(const struct UsbHostRequest * request)1388 static int32_t AdapterCancelRequest(const struct UsbHostRequest *request)
1389 {
1390 if (!request->urbs) {
1391 DPRINTFN(0, "adapter cancel urb null\n");
1392 goto END;
1393 }
1394
1395 OsDiscardUrbs(request, 0, request->numUrbs);
1396 END:
1397 return HDF_SUCCESS;
1398 }
1399
AdapterUrbCompleteHandle(const struct UsbDeviceHandle * devHandle)1400 static int32_t AdapterUrbCompleteHandle(const struct UsbDeviceHandle *devHandle)
1401 {
1402 int32_t ret;
1403 struct UsbDevice *dev = NULL;
1404 struct OsDev *osDev = NULL;
1405 struct UsbAdapterUrb *urb = NULL;
1406 struct Async *as = NULL;
1407 struct UsbHostRequest *request = NULL;
1408 if ((devHandle == NULL) || (devHandle->dev == NULL) || (devHandle->dev->privateData == NULL)) {
1409 HDF_LOGE("%s:%d invalid parameter", __func__, __LINE__);
1410 return HDF_ERR_INVALID_PARAM;
1411 }
1412 dev = devHandle->dev;
1413 osDev = (struct OsDev *)dev->privateData;
1414 ret = OsReapUrb(devHandle, &as);
1415 if (as == NULL) {
1416 HDF_LOGE("as is null\n");
1417 return HDF_FAILURE;
1418 }
1419 urb = &as->urb;
1420 request = urb->context;
1421 switch (request->requestType) {
1422 case USB_REQUEST_TYPE_CONTROL:
1423 ret = OsControlCompletion(request, as);
1424 break;
1425 case USB_REQUEST_TYPE_ISOCHRONOUS:
1426 ret = OsIsoCompletion(request, as);
1427 break;
1428 case USB_REQUEST_TYPE_BULK:
1429 case USB_REQUEST_TYPE_INTERRUPT:
1430 ret = OsBulkCompletion(request, as);
1431 break;
1432 default:
1433 DPRINTFN(0, "%s:%d unrecognised requestType %u\n", __func__, __LINE__, request->requestType);
1434 ret = HDF_FAILURE;
1435 break;
1436 }
1437 return ret;
1438 }
1439
1440 static struct UsbOsAdapterOps g_usbAdapter = {
1441 .init = AdapterInit,
1442 .exit = AdapterExit,
1443 .openDevice = AdapterOpenDevice,
1444 .closeDevice = AdapterCloseDevice,
1445 .getConfigDescriptor = AdapterGetConfigDescriptor,
1446 .getConfiguration = AdapterGetConfiguration,
1447 .setConfiguration = AdapterSetConfiguration,
1448 .claimInterface = AdapterClaimInterface,
1449 .releaseInterface = AdapterReleaseInterface,
1450 .setInterfaceAltsetting = AdapterSetInterface,
1451 .clearHalt = AdapterClearHalt,
1452 .resetDevice = AdapterResetDevice,
1453 .allocRequest = AdapterAllocRequest,
1454 .freeRequest = AdapterFreeRequest,
1455 .submitRequest = AdapterSubmitRequest,
1456 .cancelRequest = AdapterCancelRequest,
1457 .urbCompleteHandle = AdapterUrbCompleteHandle,
1458 };
1459
UsbAdapterGetOps(void)1460 struct UsbOsAdapterOps *UsbAdapterGetOps(void)
1461 {
1462 return &g_usbAdapter;
1463 }
1464
UsbAdapterGetTid(void)1465 UsbRawTidType UsbAdapterGetTid(void)
1466 {
1467 return HDF_FAILURE;
1468 }
1469
UsbAdapterRegisterSignal(void)1470 int32_t UsbAdapterRegisterSignal(void)
1471 {
1472 return HDF_SUCCESS;
1473 }
1474
UsbAdapterKillSignal(struct UsbDeviceHandle * handle,UsbRawTidType tid)1475 int32_t UsbAdapterKillSignal(struct UsbDeviceHandle *handle, UsbRawTidType tid)
1476 {
1477 if ((handle != NULL) && (handle->dev != NULL)) {
1478 struct UsbDevice *dev = handle->dev;
1479 struct OsDev *osDev = (struct OsDev *)dev->privateData;
1480 if (osDev != NULL) {
1481 g_CompleteExit = true;
1482 OsalSemPost(&osDev->cvWait);
1483 HDF_LOGD("%s:%d sigal post", __func__, __LINE__);
1484 return HDF_SUCCESS;
1485 } else {
1486 return HDF_FAILURE;
1487 }
1488 } else {
1489 return HDF_FAILURE;
1490 }
1491 }
1492
AdapterAtomicInc(OsalAtomic * v)1493 int32_t AdapterAtomicInc(OsalAtomic *v)
1494 {
1495 int32_t valOld;
1496 int32_t val;
1497 uint32_t status = 0;
1498 Atomic *p = NULL;
1499 if (v) {
1500 p = (Atomic *)&(v)->counter;
1501 } else {
1502 return HDF_FAILURE;
1503 }
1504 do {
1505 __asm__ __volatile__("ldrex %1, [%4]\n"
1506 "mov %0, %1\n"
1507 "add %1, %1, #1\n"
1508 "strex %2, %1, [%4]"
1509 : "=&r"(valOld), "=&r"(val), "=&r"(status), "+m"(*p)
1510 : "r"(p)
1511 : "cc");
1512 } while (__builtin_expect(status != 0, 0));
1513
1514 return valOld;
1515 }
1516
AdapterAtomicDec(OsalAtomic * v)1517 int32_t AdapterAtomicDec(OsalAtomic *v)
1518 {
1519 if (v) {
1520 return LOS_AtomicDecRet((Atomic *)&(v)->counter);
1521 } else {
1522 return HDF_FAILURE;
1523 }
1524 }
1525