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 <unistd.h>
17
18 #include "hdf_base.h"
19 #include "hdf_log.h"
20 #include "hdf_usb_pnp_manage.h"
21 #include "osal_mem.h"
22 #include "osal_time.h"
23 #include "securec.h"
24 #include "usb_serial_rawapi.h"
25
26 #define HDF_LOG_TAG USB_HOST_ACM_RAW_API
27 #define USB_CTRL_REQ_SIZE 64
28 #define USB_IO_THREAD_STACK_SIZE 8192
29 #define USB_RAW_IO_SLEEP_MS_TIME 100
30 #define USB_RAW_IO_STOP_WAIT_MAX_TIME 3
31
32 static struct UsbRawRequest *g_syncRequest = NULL;
33 static UsbRawIoProcessStatusType g_stopIoStatus = USB_RAW_IO_PROCESS_RUNNING;
34 struct OsalMutex g_stopIoLock;
35 static bool g_rawAcmReleaseFlag = false;
36
37 static int32_t SerialSendCtrlMsg(struct AcmDevice *acm, uint8_t request, uint16_t value, void *buf, uint16_t len);
38 static void AcmWriteBulkCallback(const void *requestArg);
39 static int32_t UsbSerialInit(struct AcmDevice *acm);
40 static void UsbSerialRelease(struct AcmDevice *acm);
41
UsbIoThread(void * data)42 static int32_t UsbIoThread(void *data)
43 {
44 int32_t ret;
45 struct AcmDevice *acm = (struct AcmDevice *)data;
46
47 for (;;) {
48 if (acm == NULL) {
49 HDF_LOGE("%{public}s:%{public}d acm is null", __func__, __LINE__);
50 OsalMSleep(USB_RAW_IO_SLEEP_MS_TIME);
51 continue;
52 }
53
54 if (acm->devHandle == NULL) {
55 HDF_LOGE("%{public}s:%{public}d acm->devHandle is null", __func__, __LINE__);
56 OsalMSleep(USB_RAW_IO_SLEEP_MS_TIME);
57 continue;
58 }
59
60 ret = UsbRawHandleRequests(acm->devHandle);
61 if ((ret < 0) || (g_stopIoStatus != USB_RAW_IO_PROCESS_RUNNING)) {
62 HDF_LOGE("%{public}s:%{public}d UsbIoThread failed, g_stopIoStatus=%{public}d ret=%{public}d ",
63 __func__, __LINE__, g_stopIoStatus, ret);
64 break;
65 }
66 }
67
68 OsalMutexLock(&g_stopIoLock);
69 g_stopIoStatus = USB_RAW_IO_PROCESS_STOPED;
70 OsalMutexUnlock(&g_stopIoLock);
71
72 HDF_LOGD("%{public}s:%{public}d exit", __func__, __LINE__);
73
74 return HDF_SUCCESS;
75 }
76
UsbStartIo(struct AcmDevice * acm)77 static int32_t UsbStartIo(struct AcmDevice *acm)
78 {
79 struct OsalThreadParam threadCfg;
80 int32_t ret;
81
82 HDF_LOGI("%{public}s start", __func__);
83
84 OsalMutexInit(&g_stopIoLock);
85
86 OsalMutexLock(&g_stopIoLock);
87 g_stopIoStatus = USB_RAW_IO_PROCESS_RUNNING;
88 OsalMutexUnlock(&g_stopIoLock);
89
90 /* create Io thread */
91 (void)memset_s(&threadCfg, sizeof(threadCfg), 0, sizeof(threadCfg));
92 threadCfg.name = "usb io thread";
93 threadCfg.priority = OSAL_THREAD_PRI_LOW;
94 threadCfg.stackSize = USB_IO_THREAD_STACK_SIZE;
95
96 ret = OsalThreadCreate(&acm->ioThread, (OsalThreadEntry)UsbIoThread, (void *)acm);
97 if (ret != HDF_SUCCESS) {
98 HDF_LOGE("%{public}s:%{public}d OsalThreadCreate failed, ret = %{public}d", __func__, __LINE__, ret);
99 return ret;
100 }
101
102 ret = OsalThreadStart(&acm->ioThread, &threadCfg);
103 if (ret != HDF_SUCCESS) {
104 HDF_LOGE("%{public}s:%{public}d OsalThreadStart failed, ret = %{public}d", __func__, __LINE__, ret);
105 return ret;
106 }
107
108 return HDF_SUCCESS;
109 }
110
UsbStopIo(struct AcmDevice * acm)111 static void UsbStopIo(struct AcmDevice *acm)
112 {
113 int32_t ret;
114 int32_t i = 0;
115
116 if (g_stopIoStatus != USB_RAW_IO_PROCESS_STOPED) {
117 HDF_LOGD("%{public}s:%{public}d not stopped", __func__, __LINE__);
118 OsalMutexLock(&g_stopIoLock);
119 g_stopIoStatus = USB_RAW_IO_PROCESS_STOP;
120 OsalMutexUnlock(&g_stopIoLock);
121 } else {
122 HDF_LOGD("%{public}s:%{public}d stopped", __func__, __LINE__);
123 }
124
125 while (g_stopIoStatus != USB_RAW_IO_PROCESS_STOPED) {
126 i++;
127 OsalMSleep(USB_RAW_IO_SLEEP_MS_TIME);
128 if (i > USB_RAW_IO_STOP_WAIT_MAX_TIME) {
129 HDF_LOGD("%{public}s:%{public}d", __func__, __LINE__);
130 break;
131 }
132 }
133
134 ret = OsalThreadDestroy(&acm->ioThread);
135 if (ret != HDF_SUCCESS) {
136 HDF_LOGE("%{public}s:%{public}d OsalThreadDestroy failed, ret = %{public}d", __func__, __LINE__, ret);
137 }
138
139 OsalMutexDestroy(&g_stopIoLock);
140
141 return;
142 }
143
UsbGetConfigDescriptor(UsbRawHandle * devHandle,struct UsbRawConfigDescriptor ** config)144 static int32_t UsbGetConfigDescriptor(UsbRawHandle *devHandle, struct UsbRawConfigDescriptor **config)
145 {
146 UsbRawDevice *dev = NULL;
147 int32_t activeConfig;
148 int32_t ret;
149
150 if (devHandle == NULL) {
151 HDF_LOGE("%{public}s:%{public}d devHandle is null", __func__, __LINE__);
152 return HDF_ERR_INVALID_PARAM;
153 }
154
155 ret = UsbRawGetConfiguration(devHandle, &activeConfig);
156 if (ret) {
157 HDF_LOGE("%{public}s:%{public}d UsbRawGetConfiguration failed, ret = %{public}d", __func__, __LINE__, ret);
158 return HDF_FAILURE;
159 }
160 HDF_LOGE("%{public}s:%{public}d activeConfig = %{public}d", __func__, __LINE__, activeConfig);
161 dev = UsbRawGetDevice(devHandle);
162 if (dev == NULL) {
163 HDF_LOGE("%{public}s:%{public}d UsbRawGetDevice failed", __func__, __LINE__);
164 return HDF_FAILURE;
165 }
166
167 ret = UsbRawGetConfigDescriptor(dev, activeConfig, config);
168 if (ret) {
169 HDF_LOGE("UsbRawGetConfigDescriptor failed, ret = %{public}d", ret);
170 return HDF_FAILURE;
171 }
172
173 return HDF_SUCCESS;
174 }
175
UsbGetBulkEndpoint(struct AcmDevice * acm,const struct UsbRawEndpointDescriptor * endPoint)176 static int32_t UsbGetBulkEndpoint(struct AcmDevice *acm, const struct UsbRawEndpointDescriptor *endPoint)
177 {
178 if ((endPoint->endpointDescriptor.bEndpointAddress & USB_DDK_ENDPOINT_DIR_MASK) == USB_DDK_DIR_IN) {
179 /* get bulk in endpoint */
180 acm->dataInEp = OsalMemAlloc(sizeof(struct UsbEndpoint));
181 if (acm->dataInEp == NULL) {
182 HDF_LOGE("%{public}s:%{public}d allocate dataInEp failed", __func__, __LINE__);
183 return HDF_FAILURE;
184 }
185 acm->dataInEp->addr = endPoint->endpointDescriptor.bEndpointAddress;
186 acm->dataInEp->interval = endPoint->endpointDescriptor.bInterval;
187 acm->dataInEp->maxPacketSize = endPoint->endpointDescriptor.wMaxPacketSize;
188 } else {
189 /* get bulk out endpoint */
190 acm->dataOutEp = OsalMemAlloc(sizeof(struct UsbEndpoint));
191 if (acm->dataOutEp == NULL) {
192 HDF_LOGE("%{public}s:%{public}d allocate dataOutEp failed", __func__, __LINE__);
193 return HDF_FAILURE;
194 }
195 acm->dataOutEp->addr = endPoint->endpointDescriptor.bEndpointAddress;
196 acm->dataOutEp->interval = endPoint->endpointDescriptor.bInterval;
197 acm->dataOutEp->maxPacketSize = endPoint->endpointDescriptor.wMaxPacketSize;
198 }
199
200 return HDF_SUCCESS;
201 }
202
UsbParseConfigDescriptorProcess(struct AcmDevice * acm,const struct UsbRawInterface * interface,uint8_t interfaceIndex)203 static void UsbParseConfigDescriptorProcess(
204 struct AcmDevice *acm, const struct UsbRawInterface *interface, uint8_t interfaceIndex)
205 {
206 uint8_t ifaceClass = interface->altsetting->interfaceDescriptor.bInterfaceClass;
207 uint8_t numEndpoints = interface->altsetting->interfaceDescriptor.bNumEndpoints;
208
209 switch (ifaceClass) {
210 case USB_DDK_CLASS_COMM:
211 acm->ctrlIface = interfaceIndex;
212 acm->notifyEp = OsalMemAlloc(sizeof(struct UsbEndpoint));
213 if (acm->notifyEp == NULL) {
214 HDF_LOGE("%{public}s:%{public}d allocate endpoint failed", __func__, __LINE__);
215 break;
216 }
217 /* get the first endpoint by default */
218 acm->notifyEp->addr = interface->altsetting->endPoint[0].endpointDescriptor.bEndpointAddress;
219 acm->notifyEp->interval = interface->altsetting->endPoint[0].endpointDescriptor.bInterval;
220 acm->notifyEp->maxPacketSize = interface->altsetting->endPoint[0].endpointDescriptor.wMaxPacketSize;
221 break;
222 case USB_DDK_CLASS_CDC_DATA:
223 acm->dataIface = interfaceIndex;
224 for (uint8_t j = 0; j < numEndpoints; j++) {
225 const struct UsbRawEndpointDescriptor *endPoint = &interface->altsetting->endPoint[j];
226 if (UsbGetBulkEndpoint(acm, endPoint) != HDF_SUCCESS) {
227 break;
228 }
229 }
230 break;
231 default:
232 HDF_LOGE("%{public}s:%{public}d wrong descriptor type", __func__, __LINE__);
233 break;
234 }
235 }
236
UsbParseConfigDescriptor(struct AcmDevice * acm,struct UsbRawConfigDescriptor * config)237 static int32_t UsbParseConfigDescriptor(struct AcmDevice *acm, struct UsbRawConfigDescriptor *config)
238 {
239 if ((acm == NULL) || (config == NULL)) {
240 HDF_LOGE("%{public}s:%{public}d acm or config is null", __func__, __LINE__);
241 return HDF_ERR_INVALID_PARAM;
242 }
243
244 for (uint8_t i = 0; i < acm->interfaceCnt; i++) {
245 uint8_t interfaceIndex = acm->interfaceIndex[i];
246 const struct UsbRawInterface *interface = config->interface[interfaceIndex];
247
248 int32_t ret = UsbRawClaimInterface(acm->devHandle, interfaceIndex);
249 if (ret != HDF_SUCCESS) {
250 HDF_LOGE("%{public}s:%{public}d claim interface %{public}hhu failed", __func__, __LINE__, i);
251 continue;
252 }
253
254 UsbParseConfigDescriptorProcess(acm, interface, interfaceIndex);
255 }
256
257 return HDF_SUCCESS;
258 }
259
UsbReleaseInterfaces(struct AcmDevice * acm)260 static void UsbReleaseInterfaces(struct AcmDevice *acm)
261 {
262 if ((acm == NULL) || (acm->devHandle == NULL)) {
263 HDF_LOGE("%{public}s:%{public}d acm is null", __func__, __LINE__);
264 return;
265 }
266
267 (void)UsbRawReleaseInterface(acm->devHandle, acm->ctrlIface);
268 (void)UsbRawReleaseInterface(acm->devHandle, acm->dataIface);
269
270 if (acm->notifyEp) {
271 OsalMemFree(acm->notifyEp);
272 acm->notifyEp = NULL;
273 }
274 if (acm->dataInEp) {
275 OsalMemFree(acm->dataInEp);
276 acm->dataInEp = NULL;
277 }
278 if (acm->dataOutEp) {
279 OsalMemFree(acm->dataOutEp);
280 acm->dataOutEp = NULL;
281 }
282 }
283
UsbAllocWriteRequests(struct AcmDevice * acm)284 static int32_t UsbAllocWriteRequests(struct AcmDevice *acm)
285 {
286 if (acm == NULL || acm->dataOutEp == NULL) {
287 HDF_LOGE("%{public}s: invalid param", __func__);
288 return HDF_FAILURE;
289 }
290 int32_t i;
291
292 for (i = 0; i < ACM_NW; i++) {
293 struct AcmWb *snd = &acm->wb[i];
294 snd->request = UsbRawAllocRequest(acm->devHandle, 0, acm->dataOutEp->maxPacketSize);
295 snd->instance = acm;
296 if (snd->request == NULL) {
297 HDF_LOGE("%{public}s: UsbRawAllocRequest failed", __func__);
298 return HDF_ERR_MALLOC_FAIL;
299 }
300 }
301
302 return HDF_SUCCESS;
303 }
304
UsbFreeWriteRequests(struct AcmDevice * acm)305 static void UsbFreeWriteRequests(struct AcmDevice *acm)
306 {
307 int32_t i;
308 struct AcmWb *snd = NULL;
309
310 for (i = 0; i < ACM_NW; i++) {
311 snd = &acm->wb[i];
312 if (snd->request != NULL) {
313 UsbRawFreeRequest(snd->request);
314 snd->request = NULL;
315 }
316 }
317 }
318
AcmWbAlloc(const struct AcmDevice * acm)319 static int32_t AcmWbAlloc(const struct AcmDevice *acm)
320 {
321 struct AcmWb *wb = NULL;
322 int32_t i;
323
324 for (i = 0; i < ACM_NW; i++) {
325 wb = (struct AcmWb *)&acm->wb[i];
326 if (!wb->use) {
327 wb->use = 1;
328 wb->len = 0;
329 return i;
330 }
331 }
332 return -1;
333 }
334
UsbSerialAllocFifo(struct DataFifo * fifo,uint32_t size)335 static int32_t UsbSerialAllocFifo(struct DataFifo *fifo, uint32_t size)
336 {
337 if (!DataFifoIsInitialized(fifo)) {
338 void *data = OsalMemAlloc(size);
339 if (data == NULL) {
340 HDF_LOGE("%{public}s:allocate failed", __func__);
341 return HDF_ERR_MALLOC_FAIL;
342 }
343 DataFifoInit(fifo, size, data);
344 }
345 return HDF_SUCCESS;
346 }
347
UsbSerialFreeFifo(const struct DataFifo * fifo)348 static void UsbSerialFreeFifo(const struct DataFifo *fifo)
349 {
350 if (fifo == NULL) {
351 HDF_LOGE("%{public}s:%{public}d fifo is null", __func__, __LINE__);
352 return;
353 }
354
355 if (fifo->data != NULL) {
356 OsalMemFree((void *)fifo->data);
357 }
358
359 DataFifoInit((struct DataFifo *)fifo, 0, NULL);
360 }
361
AcmWbIsAvail(const struct AcmDevice * acm)362 static int32_t AcmWbIsAvail(const struct AcmDevice *acm)
363 {
364 int32_t i;
365 int32_t n = ACM_NW;
366
367 OsalMutexLock((struct OsalMutex *)&acm->writeLock);
368 for (i = 0; i < ACM_NW; i++) {
369 n -= acm->wb[i].use;
370 }
371 OsalMutexUnlock((struct OsalMutex *)&acm->writeLock);
372 return n;
373 }
374
AcmStartWb(struct AcmDevice * acm,struct AcmWb * wb)375 static int32_t AcmStartWb(struct AcmDevice *acm, struct AcmWb *wb)
376 {
377 struct UsbRawFillRequestData reqData;
378 int32_t ret;
379 if ((acm == NULL) || (wb == NULL) || (acm->dataOutEp == NULL) || (acm->devHandle == NULL) ||
380 (wb->request == NULL)) {
381 return HDF_ERR_INVALID_PARAM;
382 }
383
384 acm->transmitting++;
385
386 reqData.endPoint = acm->dataOutEp->addr;
387 reqData.numIsoPackets = 0;
388 reqData.callback = AcmWriteBulkCallback;
389 reqData.userData = (void *)wb;
390 reqData.timeout = USB_CTRL_SET_TIMEOUT;
391 reqData.buffer = wb->buf;
392 reqData.length = wb->len;
393
394 ret = UsbRawFillBulkRequest(wb->request, acm->devHandle, &reqData);
395 if (ret) {
396 HDF_LOGE("%{public}s: FillInterruptRequest failed, ret = %{public}d", __func__, ret);
397 return HDF_FAILURE;
398 }
399
400 acm->writeReq = wb->request;
401 ret = UsbRawSubmitRequest(wb->request);
402 if (ret) {
403 HDF_LOGE("UsbRawSubmitRequest failed, ret = %{public}d", ret);
404 wb->use = 0;
405 acm->transmitting--;
406 }
407
408 return ret;
409 }
410
AcmWriteBufAlloc(const struct AcmDevice * acm)411 static int32_t AcmWriteBufAlloc(const struct AcmDevice *acm)
412 {
413 struct AcmWb *wb = (struct AcmWb *)&acm->wb[0];
414 int32_t i;
415
416 for (i = 0; i < ACM_NW; i++, wb++) {
417 wb->buf = OsalMemCalloc(acm->dataOutEp->maxPacketSize);
418 if (!wb->buf) {
419 while (i > 0) {
420 --i;
421 --wb;
422 OsalMemFree(wb->buf);
423 wb->buf = NULL;
424 }
425 return -HDF_ERR_MALLOC_FAIL;
426 }
427 }
428 return HDF_SUCCESS;
429 }
430
AcmWriteBufFree(struct AcmDevice * acm)431 static void AcmWriteBufFree(struct AcmDevice *acm)
432 {
433 struct AcmWb *wb = &acm->wb[0];
434 int32_t i;
435
436 for (i = 0; i < ACM_NW; i++, wb++) {
437 if (wb->buf) {
438 OsalMemFree(wb->buf);
439 wb->buf = NULL;
440 }
441 }
442 return;
443 }
444
AcmWriteBulkCallback(const void * requestArg)445 static void AcmWriteBulkCallback(const void *requestArg)
446 {
447 struct UsbRawRequest *req = (struct UsbRawRequest *)requestArg;
448 if (req == NULL) {
449 HDF_LOGE("%{public}s:%{public}d req is null!", __func__, __LINE__);
450 return;
451 }
452 struct AcmWb *wb = (struct AcmWb *)req->userData;
453 if (wb == NULL) {
454 HDF_LOGE("%{public}s:%{public}d userData(wb) is null!", __func__, __LINE__);
455 return;
456 }
457
458 if (req->status != USB_REQUEST_COMPLETED) {
459 HDF_LOGE("%{public}s: write req failed, status = %{public}d", __func__, req->status);
460 }
461
462 wb->use = 0;
463 }
464
SerialSendCtrlMsg(struct AcmDevice * acm,uint8_t request,uint16_t value,void * buf,uint16_t len)465 static int32_t SerialSendCtrlMsg(struct AcmDevice *acm, uint8_t request, uint16_t value, void *buf, uint16_t len)
466 {
467 struct UsbControlRequestData ctrlReq;
468 int32_t ret;
469
470 if (acm == NULL || buf == NULL) {
471 HDF_LOGE("%{public}s:invalid param", __func__);
472 return HDF_ERR_INVALID_PARAM;
473 }
474 if (acm->ctrlReq == NULL) {
475 acm->ctrlReq = UsbRawAllocRequest(acm->devHandle, 0, USB_CTRL_REQ_SIZE);
476 if (acm->ctrlReq == NULL) {
477 HDF_LOGE("%{public}s: UsbRawAllocRequest failed", __func__);
478 return HDF_ERR_MALLOC_FAIL;
479 }
480 }
481
482 ctrlReq.requestType = USB_DDK_DIR_OUT | USB_DDK_TYPE_CLASS | USB_DDK_RECIP_INTERFACE;
483 ctrlReq.requestCmd = request;
484 ctrlReq.value = CPU_TO_LE16(value);
485 ctrlReq.index = 0;
486 ctrlReq.data = buf;
487 ctrlReq.length = len;
488 ctrlReq.timeout = USB_CTRL_SET_TIMEOUT;
489
490 ret = UsbRawSendControlRequest(acm->ctrlReq, acm->devHandle, &ctrlReq);
491 if (ret < HDF_SUCCESS) {
492 HDF_LOGE("%{public}s: UsbRawSendControlRequest failed, ret=%{public}d", __func__, ret);
493 return ret;
494 }
495 if (acm->ctrlReq->status) {
496 HDF_LOGE("%{public}s status=%{public}d ", __func__, acm->ctrlReq->status);
497 }
498 return HDF_SUCCESS;
499 }
500
UsbSerialDeviceAlloc(struct AcmDevice * acm)501 static int32_t UsbSerialDeviceAlloc(struct AcmDevice *acm)
502 {
503 struct SerialDevice *port = NULL;
504
505 if (acm == NULL) {
506 HDF_LOGE("%{public}s: acm null pointer", __func__);
507 return HDF_FAILURE;
508 }
509
510 port = (struct SerialDevice *)OsalMemCalloc(sizeof(*port));
511 if (port == NULL) {
512 HDF_LOGE("%{public}s: Alloc usb serial port failed", __func__);
513 return HDF_FAILURE;
514 }
515 if (OsalMutexInit(&port->lock) != HDF_SUCCESS) {
516 HDF_LOGE("%{public}s: init lock fail!", __func__);
517 OsalMemFree(port);
518 return HDF_FAILURE;
519 }
520 port->lineCoding.dwDTERate = CPU_TO_LE32(DATARATE);
521 port->lineCoding.bCharFormat = USB_CDC_1_STOP_BITS;
522 port->lineCoding.bParityType = USB_CDC_NO_PARITY;
523 port->lineCoding.bDataBits = DATA_BITS_LENGTH;
524 acm->lineCoding = port->lineCoding;
525 acm->port = port;
526 port->acm = acm;
527
528 return HDF_SUCCESS;
529 }
530
UsbSeriaDevicelFree(struct AcmDevice * acm)531 static void UsbSeriaDevicelFree(struct AcmDevice *acm)
532 {
533 struct SerialDevice *port = acm->port;
534
535 if (port == NULL) {
536 HDF_LOGE("%{public}s: port is null", __func__);
537 return;
538 }
539 OsalMemFree(port);
540 port = NULL;
541 }
542
UsbSerialRead(struct SerialDevice * port,struct HdfSBuf * reply)543 static int32_t UsbSerialRead(struct SerialDevice *port, struct HdfSBuf *reply)
544 {
545 struct AcmDevice *acm = port->acm;
546 uint8_t *buf = NULL;
547 int32_t ret = HDF_SUCCESS;
548 uint32_t len;
549
550 for (int32_t i = 0; i < ACM_NR; i++) {
551 if (acm->readReq[i]->status != USB_REQUEST_COMPLETED) {
552 HDF_LOGE("%{public}s:%{public}d i=%{public}d status=%{public}d!",
553 __func__, __LINE__, i, acm->readReq[i]->status);
554 return HDF_FAILURE;
555 }
556 }
557
558 if (DataFifoIsEmpty(&port->readFifo)) {
559 if (!HdfSbufWriteString(reply, NULL)) {
560 HDF_LOGE("%{public}s:%{public}d sbuf write buffer failed", __func__, __LINE__);
561 return HDF_ERR_IO;
562 }
563 return HDF_SUCCESS;
564 }
565
566 buf = (uint8_t *)OsalMemCalloc(DataFifoLen(&port->readFifo) + 1);
567 if (buf == NULL) {
568 HDF_LOGE("%{public}s:%{public}d OsalMemCalloc error", __func__, __LINE__);
569 return HDF_ERR_MALLOC_FAIL;
570 }
571
572 OsalMutexLock(&acm->readLock);
573 len = DataFifoRead(&port->readFifo, buf, DataFifoLen(&port->readFifo));
574 if (len == 0) {
575 HDF_LOGE("%{public}s:%{public}d no data", __func__, __LINE__);
576 ret = HDF_SUCCESS;
577 OsalMutexUnlock(&acm->readLock);
578 goto OUT;
579 }
580 OsalMutexUnlock(&acm->readLock);
581
582 if (!HdfSbufWriteString(reply, (const char *)buf)) {
583 HDF_LOGE("%{public}s:%{public}d sbuf write buffer failed", __func__, __LINE__);
584 ret = HDF_ERR_IO;
585 }
586
587 OUT:
588 OsalMemFree(buf);
589 return ret;
590 }
591
SerialSetBaudrate(struct SerialDevice * port,const struct HdfSBuf * data)592 static int32_t SerialSetBaudrate(struct SerialDevice *port, const struct HdfSBuf *data)
593 {
594 struct AcmDevice *acm = port->acm;
595 uint32_t baudRate = 0;
596
597 if (!HdfSbufReadUint32((struct HdfSBuf *)data, &baudRate)) {
598 HDF_LOGE("%{public}s: sbuf read buffer failed", __func__);
599 return HDF_ERR_IO;
600 }
601 port->lineCoding.dwDTERate = CPU_TO_LE32(baudRate);
602 if (memcmp(&acm->lineCoding, &port->lineCoding, sizeof(struct UsbCdcLineCoding))) {
603 int32_t ret =
604 memcpy_s(&acm->lineCoding, sizeof(struct UsbCdcLineCoding), &port->lineCoding, sizeof(port->lineCoding));
605 if (ret != EOK) {
606 HDF_LOGE("memcpy_s fail, ret=%{public}d", ret);
607 return ret;
608 }
609
610 HDF_LOGE("%{public}s - set line: %{public}d %{public}d %{public}d %{public}d",
611 __func__, (port->lineCoding.dwDTERate), port->lineCoding.bCharFormat,
612 port->lineCoding.bParityType, port->lineCoding.bDataBits);
613
614 ret = SerialSendCtrlMsg(
615 acm, USB_DDK_CDC_REQ_SET_LINE_CODING, 0, &acm->lineCoding, sizeof(struct UsbCdcLineCoding));
616 if (ret) {
617 HDF_LOGE("SerialSendCtrlMsg fail");
618 return ret;
619 }
620 }
621 return HDF_SUCCESS;
622 }
623
SerialGetBaudrate(struct SerialDevice * port,struct HdfSBuf * reply)624 static int32_t SerialGetBaudrate(struct SerialDevice *port, struct HdfSBuf *reply)
625 {
626 uint32_t baudRate = LE32_TO_CPU(port->lineCoding.dwDTERate);
627
628 if (!HdfSbufWriteUint32(reply, baudRate)) {
629 HDF_LOGE("%{public}s:%{public}d sbuf write buffer failed", __func__, __LINE__);
630 return HDF_ERR_IO;
631 }
632
633 HDF_LOGE("%{public}s:%{public}d baudRate=%{public}d", __func__, __LINE__, baudRate);
634
635 return HDF_SUCCESS;
636 }
637
SerialOpen(struct SerialDevice * port,struct HdfSBuf * data)638 static int32_t SerialOpen(struct SerialDevice *port, struct HdfSBuf *data)
639 {
640 struct AcmDevice *acm = NULL;
641 int32_t ret;
642 int32_t cmdType = HOST_ACM_ASYNC_READ;
643
644 if ((port == NULL) || (data == NULL)) {
645 HDF_LOGE("%{public}s: invalid parma", __func__);
646 return HDF_ERR_INVALID_PARAM;
647 }
648
649 acm = port->acm;
650 if (acm == NULL) {
651 HDF_LOGE("%{public}s: invalid parma", __func__);
652 return HDF_ERR_INVALID_PARAM;
653 }
654
655 if (!HdfSbufReadInt32(data, &cmdType)) {
656 HDF_LOGE("%{public}s:%{public}d sbuf read cmdType failed", __func__, __LINE__);
657 return HDF_ERR_INVALID_PARAM;
658 }
659
660 ret = UsbSerialInit(acm);
661 if (ret != HDF_SUCCESS) {
662 HDF_LOGE("%{public}s:%{public}d UsbSerialInit failed", __func__, __LINE__);
663 return HDF_FAILURE;
664 }
665
666 if (cmdType != HOST_ACM_ASYNC_READ) {
667 HDF_LOGD("%{public}s:%{public}d asyncRead success", __func__, __LINE__);
668 return HDF_SUCCESS;
669 }
670
671 ret = UsbSerialAllocFifo(&port->readFifo, READ_BUF_SIZE);
672 if (ret != HDF_SUCCESS) {
673 HDF_LOGE("%{public}s: UsbSerialAllocFifo failed", __func__);
674 return HDF_ERR_INVALID_PARAM;
675 }
676 for (int32_t i = 0; i < ACM_NR; i++) {
677 ret = UsbRawSubmitRequest(acm->readReq[i]);
678 if (ret) {
679 HDF_LOGE("%{public}s: UsbRawSubmitRequest failed, ret=%{public}d ", __func__, ret);
680 goto ERR;
681 }
682 }
683 return HDF_SUCCESS;
684
685 ERR:
686 UsbSerialFreeFifo(&port->readFifo);
687 return ret;
688 }
689
SerialClose(struct SerialDevice * port,struct HdfSBuf * data)690 static int32_t SerialClose(struct SerialDevice *port, struct HdfSBuf *data)
691 {
692 int32_t cmdType = HOST_ACM_SYNC_READ;
693
694 if ((port == NULL) || (data == NULL)) {
695 HDF_LOGE("%{public}s:%{public}d invalid parma", __func__, __LINE__);
696 return HDF_ERR_INVALID_PARAM;
697 }
698
699 if (port->acm == NULL) {
700 HDF_LOGE("%{public}s:%{public}d acm is NULL invalid parma", __func__, __LINE__);
701 return HDF_ERR_INVALID_PARAM;
702 }
703
704 if (!HdfSbufReadInt32(data, &cmdType)) {
705 HDF_LOGE("%{public}s:%{public}d sbuf read cmdType failed", __func__, __LINE__);
706 return HDF_ERR_INVALID_PARAM;
707 }
708
709 if ((cmdType == HOST_ACM_SYNC_READ) || (cmdType == HOST_ACM_SYNC_WRITE) || (cmdType == HOST_ACM_ASYNC_WRITE)) {
710 HDF_LOGD("%{public}s:%{public}d cmdType=%{public}d success", __func__, __LINE__, cmdType);
711 return HDF_SUCCESS;
712 }
713
714 OsalMutexLock(&port->acm->readLock);
715 UsbSerialFreeFifo(&port->readFifo);
716 OsalMutexUnlock(&port->acm->readLock);
717
718 UsbSerialRelease(port->acm);
719
720 return HDF_SUCCESS;
721 }
722
SerialWrite(struct SerialDevice * port,struct HdfSBuf * data)723 static int32_t SerialWrite(struct SerialDevice *port, struct HdfSBuf *data)
724 {
725 struct AcmDevice *acm = NULL;
726 struct AcmWb *wb = NULL;
727 const char *tmp = NULL;
728 int32_t size;
729 int32_t wbn;
730
731 if (port == NULL) {
732 HDF_LOGE("%{public}s: port is null", __func__);
733 return HDF_ERR_INVALID_PARAM;
734 }
735 acm = port->acm;
736 if (acm == NULL) {
737 HDF_LOGE("%{public}s: acm is null", __func__);
738 return HDF_ERR_INVALID_PARAM;
739 }
740 if (AcmWbIsAvail(acm)) {
741 wbn = AcmWbAlloc(acm);
742 } else {
743 HDF_LOGE("%{public}s: no write buf", __func__);
744 return HDF_SUCCESS;
745 }
746 if (wbn < 0 || wbn >= ACM_NW) {
747 HDF_LOGE("%{public}s: AcmWbAlloc failed", __func__);
748 return HDF_FAILURE;
749 }
750 wb = &acm->wb[wbn];
751 if (wb == NULL) {
752 return HDF_FAILURE;
753 }
754 tmp = HdfSbufReadString(data);
755 if (tmp == NULL) {
756 HDF_LOGE("%{public}s: sbuf read buffer failed", __func__);
757 return HDF_ERR_IO;
758 }
759 size = (int32_t)strlen(tmp) + 1;
760 if (acm->dataOutEp != NULL) {
761 size = (size > acm->dataOutEp->maxPacketSize) ? acm->dataOutEp->maxPacketSize : size;
762 if (memcpy_s(wb->buf, acm->dataOutEp->maxPacketSize, tmp, size) != EOK) {
763 HDF_LOGE("%{public}s: memcpy_s fail", __func__);
764 }
765 }
766 wb->len = (uint32_t)size;
767
768 if (AcmStartWb(acm, wb) != HDF_SUCCESS) {
769 HDF_LOGE("%{public}s: AcmStartWb failed", __func__);
770 return HDF_FAILURE;
771 }
772 return size;
773 }
774
AcmStartWbSync(struct AcmDevice * acm,struct AcmWb * wb)775 static int32_t AcmStartWbSync(struct AcmDevice *acm, struct AcmWb *wb)
776 {
777 int32_t ret;
778 int32_t size;
779 struct UsbRequestData requestData;
780
781 requestData.endPoint = acm->dataOutEp->addr;
782 requestData.data = wb->buf;
783 requestData.length = wb->len;
784 requestData.requested = &size;
785 requestData.timeout = USB_CTRL_SET_TIMEOUT;
786
787 acm->writeReq = wb->request;
788 ret = UsbRawSendBulkRequest(wb->request, acm->devHandle, &requestData);
789 if (ret) {
790 HDF_LOGE("UsbRawSendBulkRequest failed, ret=%{public}d", ret);
791 }
792
793 wb->use = 0;
794
795 return ret;
796 }
797
SerialWriteSync(const struct SerialDevice * port,const struct HdfSBuf * data)798 static int32_t SerialWriteSync(const struct SerialDevice *port, const struct HdfSBuf *data)
799 {
800 struct AcmDevice *acm = NULL;
801 struct AcmWb *wb = NULL;
802 const char *tmp = NULL;
803 int32_t size;
804 int32_t wbn;
805
806 if (port == NULL) {
807 HDF_LOGE("%{public}s: invalid parma", __func__);
808 return HDF_ERR_INVALID_PARAM;
809 }
810 acm = port->acm;
811 if (acm == NULL) {
812 HDF_LOGE("%{public}s: invalid parma", __func__);
813 return HDF_ERR_INVALID_PARAM;
814 }
815
816 if (AcmWbIsAvail(acm)) {
817 wbn = AcmWbAlloc(acm);
818 } else {
819 HDF_LOGE("%{public}s: no write buf", __func__);
820 return HDF_SUCCESS;
821 }
822
823 if (wbn >= ACM_NW || wbn < 0) {
824 wbn = 0;
825 }
826 wb = &acm->wb[wbn];
827 if ((wb == NULL) || (wb->buf == NULL)) {
828 return HDF_ERR_INVALID_PARAM;
829 }
830 tmp = HdfSbufReadString((struct HdfSBuf *)data);
831 if (tmp == NULL) {
832 HDF_LOGE("%{public}s: sbuf read buffer failed", __func__);
833 return HDF_ERR_IO;
834 }
835 size = (int32_t)strlen(tmp) + 1;
836 if (acm->dataOutEp == NULL) {
837 return HDF_ERR_IO;
838 }
839 size = (size > acm->dataOutEp->maxPacketSize) ? acm->dataOutEp->maxPacketSize : size;
840 if (memcpy_s(wb->buf, acm->dataOutEp->maxPacketSize, tmp, size) != EOK) {
841 HDF_LOGE("%{public}s: memcpy_s failed", __func__);
842 }
843 wb->len = (uint32_t)size;
844
845 if (AcmStartWbSync(acm, wb) != HDF_SUCCESS) {
846 HDF_LOGE("%{public}s: AcmStartWbSync failed", __func__);
847 return HDF_FAILURE;
848 }
849
850 return size;
851 }
852
UsbSerialReadSync(const struct SerialDevice * port,const struct HdfSBuf * reply)853 static int32_t UsbSerialReadSync(const struct SerialDevice *port, const struct HdfSBuf *reply)
854 {
855 int32_t ret;
856 int32_t size;
857 struct AcmDevice *acm = port->acm;
858 uint8_t *data = NULL;
859 struct UsbRequestData requestData;
860
861 if (g_syncRequest == NULL) {
862 g_syncRequest = UsbRawAllocRequest(acm->devHandle, 0, acm->dataInEp->maxPacketSize);
863 if (g_syncRequest == NULL) {
864 HDF_LOGE("UsbRawAllocRequest g_syncRequest failed");
865 return HDF_ERR_MALLOC_FAIL;
866 }
867 }
868 HDF_LOGD("%{public}s:%{public}d g_syncRequest ", __func__, __LINE__);
869
870 requestData.endPoint = acm->dataInEp->addr;
871 requestData.data = g_syncRequest->buffer;
872 requestData.length = acm->dataInEp->maxPacketSize;
873 requestData.requested = &size;
874 requestData.timeout = USB_CTRL_SET_TIMEOUT;
875
876 ret = UsbRawSendBulkRequest(g_syncRequest, acm->devHandle, &requestData);
877 if (ret) {
878 HDF_LOGE("UsbRawSendBulkRequest failed, ret=%{public}d", ret);
879 return ret;
880 }
881
882 uint32_t count = (uint32_t)g_syncRequest->actualLength;
883 data = (uint8_t *)OsalMemCalloc(count + 1);
884 if (data == NULL) {
885 HDF_LOGE("%{public}s: OsalMemCalloc error", __func__);
886 return HDF_ERR_MALLOC_FAIL;
887 }
888 HDF_LOGD("buffer actualLength:%{public}u", count);
889
890 do {
891 ret = memcpy_s(data, g_syncRequest->actualLength, g_syncRequest->buffer, count);
892 if (ret != EOK) {
893 HDF_LOGE("%{public}s: memcpy_s error", __func__);
894 break;
895 }
896
897 if (!HdfSbufWriteString((struct HdfSBuf *)reply, (char *)data)) {
898 HDF_LOGE("%{public}s: sbuf write buffer failed", __func__);
899 ret = HDF_ERR_IO;
900 break;
901 }
902 } while (0);
903
904 OsalMemFree(data);
905 data = NULL;
906 return ret;
907 }
908
SerialAddOrRemoveInterface(int32_t cmd,const struct SerialDevice * port,const struct HdfSBuf * data)909 static int32_t SerialAddOrRemoveInterface(int32_t cmd, const struct SerialDevice *port, const struct HdfSBuf *data)
910 {
911 (void)cmd;
912 (void)port;
913 (void)data;
914
915 return HDF_SUCCESS;
916 }
917
UsbSerialDeviceDispatch(struct HdfDeviceIoClient * client,int32_t cmd,struct HdfSBuf * data,struct HdfSBuf * reply)918 static int32_t UsbSerialDeviceDispatch(
919 struct HdfDeviceIoClient *client, int32_t cmd, struct HdfSBuf *data, struct HdfSBuf *reply)
920 {
921 struct AcmDevice *acm = NULL;
922 struct SerialDevice *port = NULL;
923
924 if ((client == NULL) || (client->device == NULL)) {
925 HDF_LOGE("%{public}s: client or client->device is NULL", __func__);
926 return HDF_ERR_INVALID_OBJECT;
927 }
928
929 if (client->device->service == NULL) {
930 HDF_LOGE("%{public}s: client->device->service is NULL", __func__);
931 return HDF_ERR_INVALID_OBJECT;
932 }
933
934 if (g_rawAcmReleaseFlag == true) {
935 HDF_LOGE("%{public}s: g_rawAcmReleaseFlag is true", __func__);
936 return HDF_FAILURE;
937 }
938
939 acm = (struct AcmDevice *)client->device->service;
940 port = acm->port;
941 if (port == NULL) {
942 return HDF_FAILURE;
943 }
944 switch (cmd) {
945 case CMD_OPEN_PARM:
946 return SerialOpen(port, data);
947 case CMD_CLOSE_PARM:
948 return SerialClose(port, data);
949 case CMD_WRITE_PARM:
950 return SerialWrite(port, data);
951 case CMD_READ_PARM:
952 return UsbSerialRead(port, reply);
953 case CMD_GET_BAUDRATE:
954 return SerialGetBaudrate(port, reply);
955 case CMD_SET_BAUDRATE:
956 return SerialSetBaudrate(port, data);
957 case CMD_WRITE_DATA_SYNC:
958 return SerialWriteSync(port, data);
959 case CMD_READ_DATA_SYNC:
960 return UsbSerialReadSync(port, reply);
961 case CMD_ADD_INTERFACE:
962 case CMD_REMOVE_INTERFACE:
963 return SerialAddOrRemoveInterface(cmd, port, data);
964 default:
965 return HDF_ERR_NOT_SUPPORT;
966 }
967 }
968
969 /* HdfDriverEntry implementations */
UsbSerialDriverBind(struct HdfDeviceObject * device)970 static int32_t UsbSerialDriverBind(struct HdfDeviceObject *device)
971 {
972 struct AcmDevice *acm = NULL;
973 struct UsbPnpNotifyServiceInfo *info = NULL;
974 errno_t err;
975
976 if (device == NULL) {
977 HDF_LOGE("%{public}s: device is null", __func__);
978 return HDF_ERR_INVALID_OBJECT;
979 }
980
981 acm = (struct AcmDevice *)OsalMemCalloc(sizeof(*acm));
982 if (acm == NULL) {
983 HDF_LOGE("%{public}s: Alloc usb serial device failed", __func__);
984 return HDF_FAILURE;
985 }
986 if (OsalMutexInit(&acm->lock) != HDF_SUCCESS) {
987 HDF_LOGE("%{public}s:%{public}d OsalMutexInit fail", __func__, __LINE__);
988 goto ERROR;
989 }
990
991 info = (struct UsbPnpNotifyServiceInfo *)device->priv;
992 if (info != NULL) {
993 acm->busNum = (uint8_t)info->busNum;
994 acm->devAddr = (uint8_t)info->devNum;
995 acm->interfaceCnt = info->interfaceLength;
996 err = memcpy_s((void *)(acm->interfaceIndex), USB_MAX_INTERFACES, (const void *)info->interfaceNumber,
997 info->interfaceLength);
998 if (err != EOK) {
999 HDF_LOGE("%{public}s:%{public}d memcpy_s failed err=%{public}d", __func__, __LINE__, err);
1000 goto LOCK_ERROR;
1001 }
1002 } else {
1003 HDF_LOGE("%{public}s:%{public}d info is NULL!", __func__, __LINE__);
1004 goto LOCK_ERROR;
1005 }
1006
1007 device->service = &(acm->service);
1008 device->service->Dispatch = UsbSerialDeviceDispatch;
1009 acm->device = device;
1010 HDF_LOGD("UsbSerialDriverBind=========================OK");
1011 return HDF_SUCCESS;
1012
1013 LOCK_ERROR:
1014 if (OsalMutexDestroy(&acm->lock)) {
1015 HDF_LOGE("%{public}s:%{public}d OsalMutexDestroy fail", __func__, __LINE__);
1016 }
1017 ERROR:
1018 OsalMemFree(acm);
1019 acm = NULL;
1020 return HDF_FAILURE;
1021 }
1022
AcmProcessNotification(const struct AcmDevice * acm,const unsigned char * buf)1023 static void AcmProcessNotification(const struct AcmDevice *acm, const unsigned char *buf)
1024 {
1025 (void)acm;
1026 if (buf == NULL) {
1027 HDF_LOGE("%{public}s - invalid buffer", __func__);
1028 return;
1029 }
1030 struct UsbCdcNotification *dr = (struct UsbCdcNotification *)buf;
1031
1032 switch (dr->bNotificationType) {
1033 case USB_DDK_CDC_NOTIFY_NETWORK_CONNECTION:
1034 HDF_LOGE("%{public}s - network connection: %{public}d", __func__, dr->wValue);
1035 break;
1036 case USB_DDK_CDC_NOTIFY_SERIAL_STATE:
1037 HDF_LOGE("the serial State change");
1038 break;
1039 default:
1040 HDF_LOGE("%{public}s-%{public}d received: index %{public}d len %{public}d",
1041 __func__, dr->bNotificationType, dr->wIndex, dr->wLength);
1042 }
1043 }
1044
AcmNotificationBufferProcess(const struct UsbRawRequest * req,struct AcmDevice * acm,unsigned int currentSize,unsigned int expectedSize)1045 static int32_t AcmNotificationBufferProcess(
1046 const struct UsbRawRequest *req, struct AcmDevice *acm, unsigned int currentSize, unsigned int expectedSize)
1047 {
1048 if (acm->nbSize < expectedSize) {
1049 if (acm->nbSize) {
1050 OsalMemFree(acm->notificationBuffer);
1051 acm->nbSize = 0;
1052 }
1053 unsigned int allocSize = expectedSize;
1054 acm->notificationBuffer = (uint8_t *)OsalMemCalloc(allocSize);
1055 if (!acm->notificationBuffer) {
1056 return HDF_FAILURE;
1057 }
1058 acm->nbSize = allocSize;
1059 }
1060 unsigned int copySize = MIN(currentSize, expectedSize - acm->nbIndex);
1061 int32_t ret = memcpy_s(&acm->notificationBuffer[acm->nbIndex], acm->nbSize - acm->nbIndex, req->buffer, copySize);
1062 if (ret != EOK) {
1063 HDF_LOGE("memcpy_s fail ret=%{public}d", ret);
1064 }
1065 acm->nbIndex += copySize;
1066
1067 return HDF_SUCCESS;
1068 }
1069
AcmNotifyReqCallback(const void * requestArg)1070 static void AcmNotifyReqCallback(const void *requestArg)
1071 {
1072 struct UsbRawRequest *req = (struct UsbRawRequest *)requestArg;
1073 if (req == NULL) {
1074 HDF_LOGE("%{public}s:%{public}d req is NULL!", __func__, __LINE__);
1075 return;
1076 }
1077 struct AcmDevice *acm = (struct AcmDevice *)req->userData;
1078 if (acm == NULL) {
1079 HDF_LOGE("%{public}s:%{public}d userData(acm) is NULL!", __func__, __LINE__);
1080 return;
1081 }
1082 struct UsbCdcNotification *dr = (struct UsbCdcNotification *)req->buffer;
1083 if (dr == NULL) {
1084 HDF_LOGE("%{public}s:%{public}d req->buffer(dr) is NULL!", __func__, __LINE__);
1085 return;
1086 }
1087 unsigned int currentSize = (unsigned int)req->actualLength;
1088 unsigned int expectedSize = 0;
1089
1090 HDF_LOGD("Irqstatus:%{public}d,actualLength:%{public}u", req->status, currentSize);
1091
1092 if (req->status != USB_REQUEST_COMPLETED) {
1093 goto EXIT;
1094 }
1095
1096 if (acm->nbIndex) {
1097 dr = (struct UsbCdcNotification *)acm->notificationBuffer;
1098 }
1099 if (dr != NULL) {
1100 expectedSize = sizeof(struct UsbCdcNotification) + LE16_TO_CPU(dr->wLength);
1101 } else {
1102 HDF_LOGE("%{public}s:%{public}d dr is NULL!", __func__, __LINE__);
1103 return;
1104 }
1105 if (currentSize < expectedSize) {
1106 if (AcmNotificationBufferProcess(req, acm, currentSize, expectedSize) != HDF_SUCCESS) {
1107 goto EXIT;
1108 }
1109 dr = (struct UsbCdcNotification *)acm->notificationBuffer;
1110 currentSize = acm->nbIndex;
1111 }
1112 if (currentSize >= expectedSize) {
1113 AcmProcessNotification(acm, (unsigned char *)dr);
1114 acm->nbIndex = 0;
1115 }
1116
1117 if (UsbRawSubmitRequest(req) != HDF_SUCCESS) {
1118 HDF_LOGE("%{public}s - UsbRawSubmitRequest failed", __func__);
1119 }
1120
1121 EXIT:
1122 HDF_LOGE("%{public}s:%{public}d exit", __func__, __LINE__);
1123 }
1124
AcmReadBulkCallback(const void * requestArg)1125 static void AcmReadBulkCallback(const void *requestArg)
1126 {
1127 struct UsbRawRequest *req = (struct UsbRawRequest *)requestArg;
1128 if (req == NULL) {
1129 HDF_LOGE("%{public}s:%{public}d req is NULL!", __func__, __LINE__);
1130 return;
1131 }
1132 struct AcmDevice *acm = (struct AcmDevice *)req->userData;
1133 if (acm == NULL || acm->port == NULL) {
1134 HDF_LOGE("%{public}s:%{public}d request userData is NULL!", __func__, __LINE__);
1135 return;
1136 }
1137 size_t size = (size_t)req->actualLength;
1138
1139 if (req->status != USB_REQUEST_COMPLETED) {
1140 HDF_LOGW("%{public}s: the request is failed, status=%{public}d", __func__, req->status);
1141 return;
1142 }
1143 HDF_LOGD("Bulk status: %{public}d+size:%{public}zu", req->status, size);
1144 if (size == 0) {
1145 uint8_t *data = req->buffer;
1146 OsalMutexLock(&acm->readLock);
1147 if (DataFifoIsFull(&acm->port->readFifo)) {
1148 DataFifoSkip(&acm->port->readFifo, size);
1149 }
1150 uint32_t count = DataFifoWrite(&acm->port->readFifo, data, size);
1151 if (count != size) {
1152 HDF_LOGW("%{public}s: write %{public}u less than expected %{public}zu", __func__, count, size);
1153 }
1154 OsalMutexUnlock(&acm->readLock);
1155 }
1156
1157 if (UsbRawSubmitRequest(req) != HDF_SUCCESS) {
1158 HDF_LOGE("%{public}s UsbRawSubmitRequest failed", __func__);
1159 }
1160 }
1161
UsbAllocReadRequests(struct AcmDevice * acm)1162 static int32_t UsbAllocReadRequests(struct AcmDevice *acm)
1163 {
1164 if (acm == NULL || acm->dataInEp == NULL) {
1165 HDF_LOGE("%{public}s: invalid param", __func__);
1166 return HDF_FAILURE;
1167 }
1168 struct UsbRawFillRequestData reqData;
1169 uint32_t size = acm->dataInEp->maxPacketSize;
1170
1171 for (int32_t i = 0; i < ACM_NR; i++) {
1172 acm->readReq[i] = UsbRawAllocRequest(acm->devHandle, 0, size);
1173 if (!acm->readReq[i]) {
1174 HDF_LOGE("readReq request failed");
1175 return HDF_ERR_MALLOC_FAIL;
1176 }
1177
1178 reqData.endPoint = acm->dataInEp->addr;
1179 reqData.numIsoPackets = 0;
1180 reqData.callback = AcmReadBulkCallback;
1181 reqData.userData = (void *)acm;
1182 reqData.timeout = USB_CTRL_SET_TIMEOUT;
1183 reqData.length = size;
1184
1185 int32_t ret = UsbRawFillBulkRequest(acm->readReq[i], acm->devHandle, &reqData);
1186 if (ret != HDF_SUCCESS) {
1187 HDF_LOGE("%{public}s: FillBulkRequest failed, ret=%{public}d", __func__, ret);
1188 return HDF_FAILURE;
1189 }
1190 }
1191
1192 return HDF_SUCCESS;
1193 }
1194
UsbFreeReadRequests(struct AcmDevice * acm)1195 static void UsbFreeReadRequests(struct AcmDevice *acm)
1196 {
1197 int32_t i;
1198
1199 if (acm == NULL) {
1200 HDF_LOGE("%{public}s: acm is NULL", __func__);
1201 return;
1202 }
1203
1204 for (i = 0; i < ACM_NR; i++) {
1205 if (acm->readReq[i]) {
1206 UsbRawFreeRequest(acm->readReq[i]);
1207 acm->readReq[i] = NULL;
1208 }
1209 }
1210 }
1211
UsbAllocNotifyRequest(struct AcmDevice * acm)1212 static int32_t UsbAllocNotifyRequest(struct AcmDevice *acm)
1213 {
1214 struct UsbRawFillRequestData fillRequestData;
1215 if ((acm == NULL) || (acm->notifyEp == NULL)) {
1216 HDF_LOGE("%{public}s: acm or notifyEp is NULL", __func__);
1217 return HDF_ERR_INVALID_OBJECT;
1218 }
1219 uint32_t size = acm->notifyEp->maxPacketSize;
1220 int32_t ret;
1221
1222 acm->notifyReq = UsbRawAllocRequest(acm->devHandle, 0, size);
1223 if (!acm->notifyReq) {
1224 HDF_LOGE("notifyReq request fail");
1225 return HDF_ERR_MALLOC_FAIL;
1226 }
1227
1228 fillRequestData.endPoint = acm->notifyEp->addr;
1229 fillRequestData.length = size;
1230 fillRequestData.numIsoPackets = 0;
1231 fillRequestData.callback = AcmNotifyReqCallback;
1232 fillRequestData.userData = (void *)acm;
1233 fillRequestData.timeout = USB_CTRL_SET_TIMEOUT;
1234
1235 ret = UsbRawFillInterruptRequest(acm->notifyReq, acm->devHandle, &fillRequestData);
1236 if (ret) {
1237 HDF_LOGE("%{public}s: FillInterruptRequest failed, ret=%{public}d", __func__, ret);
1238 return HDF_FAILURE;
1239 }
1240
1241 return HDF_SUCCESS;
1242 }
1243
UsbFreeNotifyReqeust(struct AcmDevice * acm)1244 static void UsbFreeNotifyReqeust(struct AcmDevice *acm)
1245 {
1246 int32_t ret;
1247
1248 if ((acm == NULL) || (acm->notifyReq == NULL)) {
1249 HDF_LOGE("%{public}s: acm or notifyReq is NULL", __func__);
1250 return;
1251 }
1252
1253 ret = UsbRawFreeRequest(acm->notifyReq);
1254 if (ret == HDF_SUCCESS) {
1255 acm->notifyReq = NULL;
1256 } else {
1257 HDF_LOGE("%{public}s: UsbFreeNotifyReqeust failed, ret=%{public}d", __func__, ret);
1258 }
1259 }
1260
UsbAllocRequests(struct AcmDevice * acm,int32_t ret)1261 static void UsbAllocRequests(struct AcmDevice *acm, int32_t ret)
1262 {
1263 ret = UsbAllocWriteRequests(acm);
1264 if (ret < 0) {
1265 HDF_LOGE("%{public}s:%{public}d UsbAllocWriteRequests failed", __func__, __LINE__);
1266 ret = HDF_FAILURE;
1267 goto ERR_ALLOC_WRITE_REQS;
1268 }
1269 ret = UsbAllocNotifyRequest(acm);
1270 if (ret) {
1271 HDF_LOGE("%{public}s:%{public}d UsbAllocNotifyRequests failed", __func__, __LINE__);
1272 goto ERR_ALLOC_NOTIFY_REQ;
1273 }
1274 ret = UsbAllocReadRequests(acm);
1275 if (ret) {
1276 HDF_LOGE("%{public}s:%{public}d UsbAllocReadRequests failed", __func__, __LINE__);
1277 goto ERR_ALLOC_READ_REQS;
1278 }
1279 ret = UsbStartIo(acm);
1280 if (ret) {
1281 HDF_LOGE("%{public}s:%{public}d UsbAllocReadRequests failed", __func__, __LINE__);
1282 goto ERR_START_IO;
1283 }
1284
1285 acm->lineCoding.dwDTERate = CPU_TO_LE32(DATARATE);
1286 acm->lineCoding.bCharFormat = USB_CDC_1_STOP_BITS;
1287 acm->lineCoding.bParityType = USB_CDC_NO_PARITY;
1288 acm->lineCoding.bDataBits = DATA_BITS_LENGTH;
1289
1290 ret = UsbRawSubmitRequest(acm->notifyReq);
1291 if (ret) {
1292 HDF_LOGE("%{public}s:%{public}d UsbRawSubmitRequest failed", __func__, __LINE__);
1293 goto ERR_SUBMIT_REQ;
1294 }
1295 ret = AcmWriteBufAlloc(acm);
1296 if (ret < 0) {
1297 HDF_LOGE("%{public}s:%{public}d AcmWriteBufAlloc failed", __func__, __LINE__);
1298 ret = HDF_FAILURE;
1299 goto ERR_ALLOC_WRITE_BUF;
1300 }
1301 ERR_SUBMIT_REQ:
1302 UsbStopIo(acm);
1303 ERR_START_IO:
1304 UsbFreeReadRequests(acm);
1305 ERR_ALLOC_READ_REQS:
1306 UsbFreeNotifyReqeust(acm);
1307 ERR_ALLOC_NOTIFY_REQ:
1308 UsbFreeWriteRequests(acm);
1309 ERR_ALLOC_WRITE_REQS:
1310 AcmWriteBufFree(acm);
1311 ERR_ALLOC_WRITE_BUF:
1312 UsbReleaseInterfaces(acm);
1313 }
1314
UsbSerialInit(struct AcmDevice * acm)1315 static int32_t UsbSerialInit(struct AcmDevice *acm)
1316 {
1317 struct UsbSession *session = NULL;
1318 UsbRawHandle *devHandle = NULL;
1319 int32_t ret;
1320 if (acm->initFlag) {
1321 HDF_LOGE("%{public}s:%{public}d: initFlag is true", __func__, __LINE__);
1322 return HDF_SUCCESS;
1323 }
1324 ret = UsbRawInit(NULL);
1325 if (ret) {
1326 HDF_LOGE("%{public}s:%{public}d UsbRawInit failed", __func__, __LINE__);
1327 return HDF_ERR_IO;
1328 }
1329 acm->session = session;
1330 devHandle = UsbRawOpenDevice(session, acm->busNum, acm->devAddr);
1331 if (devHandle == NULL) {
1332 HDF_LOGE("%{public}s:%{public}d UsbRawOpenDevice failed", __func__, __LINE__);
1333 ret = HDF_FAILURE;
1334 goto ERR_OPEN_DEVICE;
1335 }
1336 acm->devHandle = devHandle;
1337 ret = UsbGetConfigDescriptor(devHandle, &acm->config);
1338 if (ret) {
1339 HDF_LOGE("%{public}s:%{public}d UsbGetConfigDescriptor failed", __func__, __LINE__);
1340 ret = HDF_FAILURE;
1341 goto ERR_GET_DESC;
1342 }
1343 ret = UsbParseConfigDescriptor(acm, acm->config);
1344 if (ret != HDF_SUCCESS) {
1345 HDF_LOGE("%{public}s:%{public}d UsbParseConfigDescriptor failed", __func__, __LINE__);
1346 ret = HDF_FAILURE;
1347 goto ERR_PARSE_DESC;
1348 }
1349 UsbAllocRequests(acm, ret);
1350 acm->initFlag = true;
1351 HDF_LOGD("%{public}s:%{public}d=========================OK", __func__, __LINE__);
1352 return HDF_SUCCESS;
1353 ERR_PARSE_DESC:
1354 UsbRawFreeConfigDescriptor(acm->config);
1355 acm->config = NULL;
1356 ERR_GET_DESC:
1357 (void)UsbRawCloseDevice(devHandle);
1358 ERR_OPEN_DEVICE:
1359 UsbRawExit(acm->session);
1360 return ret;
1361 }
1362
UsbSerialRelease(struct AcmDevice * acm)1363 static void UsbSerialRelease(struct AcmDevice *acm)
1364 {
1365 if (!(acm->initFlag)) {
1366 HDF_LOGE("%{public}s:%{public}d: initFlag is false", __func__, __LINE__);
1367 return;
1368 }
1369
1370 /* stop io thread and release all resources */
1371 UsbStopIo(acm);
1372 if (g_syncRequest != NULL) {
1373 UsbRawFreeRequest(g_syncRequest);
1374 g_syncRequest = NULL;
1375 }
1376 UsbFreeReadRequests(acm);
1377 UsbFreeNotifyReqeust(acm);
1378 UsbFreeWriteRequests(acm);
1379 AcmWriteBufFree(acm);
1380 UsbReleaseInterfaces(acm);
1381 (void)UsbRawCloseDevice(acm->devHandle);
1382 UsbRawFreeConfigDescriptor(acm->config);
1383 acm->config = NULL;
1384 UsbRawExit(acm->session);
1385
1386 acm->initFlag = false;
1387 }
1388
UsbSerialDriverInit(struct HdfDeviceObject * device)1389 static int32_t UsbSerialDriverInit(struct HdfDeviceObject *device)
1390 {
1391 struct AcmDevice *acm = NULL;
1392 int32_t ret;
1393
1394 if (device == NULL) {
1395 HDF_LOGE("%{public}s:%{public}d device is null", __func__, __LINE__);
1396 return HDF_ERR_INVALID_OBJECT;
1397 }
1398 acm = (struct AcmDevice *)device->service;
1399 if (acm == NULL) {
1400 return HDF_ERR_INVALID_OBJECT;
1401 }
1402 OsalMutexInit(&acm->readLock);
1403 OsalMutexInit(&acm->writeLock);
1404
1405 ret = UsbSerialDeviceAlloc(acm);
1406 if (ret != HDF_SUCCESS) {
1407 HDF_LOGE("%{public}s:%{public}d UsbSerialDeviceAlloc failed", __func__, __LINE__);
1408 }
1409
1410 acm->initFlag = false;
1411 g_rawAcmReleaseFlag = false;
1412
1413 HDF_LOGD("%{public}s:%{public}d init ok!", __func__, __LINE__);
1414
1415 return ret;
1416 }
1417
UsbSerialDriverRelease(struct HdfDeviceObject * device)1418 static void UsbSerialDriverRelease(struct HdfDeviceObject *device)
1419 {
1420 struct AcmDevice *acm = NULL;
1421 if (device == NULL) {
1422 HDF_LOGE("%{public}s: device is null", __func__);
1423 return;
1424 }
1425
1426 acm = (struct AcmDevice *)device->service;
1427 if (acm == NULL) {
1428 HDF_LOGE("%{public}s: acm is null", __func__);
1429 return;
1430 }
1431
1432 g_rawAcmReleaseFlag = true;
1433
1434 if (acm->initFlag) {
1435 HDF_LOGE("%{public}s:%{public}d UsbSerialRelease", __func__, __LINE__);
1436 UsbSerialRelease(acm);
1437 }
1438 UsbSeriaDevicelFree(acm);
1439 OsalMutexDestroy(&acm->writeLock);
1440 OsalMutexDestroy(&acm->readLock);
1441 OsalMutexDestroy(&acm->lock);
1442 OsalMemFree(acm);
1443 acm = NULL;
1444 device->service = NULL;
1445 HDF_LOGD("%{public}s:%{public}d exit", __func__, __LINE__);
1446 }
1447
1448 struct HdfDriverEntry g_usbSerialRawDriverEntry = {
1449 .moduleVersion = 1,
1450 .moduleName = "usbhost_acm_rawapi",
1451 .Bind = UsbSerialDriverBind,
1452 .Init = UsbSerialDriverInit,
1453 .Release = UsbSerialDriverRelease,
1454 };
1455 HDF_INIT(g_usbSerialRawDriverEntry);
1456