1beacf11bSopenharmony_ci/* ----------------------------------------------------------------------------
2beacf11bSopenharmony_ci * Copyright (c) Huawei Technologies Co., Ltd. 2016-2019. All rights reserved.
3beacf11bSopenharmony_ci * Description: LiteOS USB Driver RNDIS Protocol
4beacf11bSopenharmony_ci * Author: huangjieliang
5beacf11bSopenharmony_ci * Create: 2016-07-13
6beacf11bSopenharmony_ci * Redistribution and use in source and binary forms, with or without modification,
7beacf11bSopenharmony_ci * are permitted provided that the following conditions are met:
8beacf11bSopenharmony_ci * 1. Redistributions of source code must retain the above copyright notice, this list of
9beacf11bSopenharmony_ci * conditions and the following disclaimer.
10beacf11bSopenharmony_ci * 2. Redistributions in binary form must reproduce the above copyright notice, this list
11beacf11bSopenharmony_ci * of conditions and the following disclaimer in the documentation and/or other materials
12beacf11bSopenharmony_ci * provided with the distribution.
13beacf11bSopenharmony_ci * 3. Neither the name of the copyright holder nor the names of its contributors may be used
14beacf11bSopenharmony_ci * to endorse or promote products derived from this software without specific prior written
15beacf11bSopenharmony_ci * permission.
16beacf11bSopenharmony_ci * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
17beacf11bSopenharmony_ci * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
18beacf11bSopenharmony_ci * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
19beacf11bSopenharmony_ci * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
20beacf11bSopenharmony_ci * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
21beacf11bSopenharmony_ci * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
22beacf11bSopenharmony_ci * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
23beacf11bSopenharmony_ci * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
24beacf11bSopenharmony_ci * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
25beacf11bSopenharmony_ci * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
26beacf11bSopenharmony_ci * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27beacf11bSopenharmony_ci * --------------------------------------------------------------------------- */
28beacf11bSopenharmony_ci/* ----------------------------------------------------------------------------
29beacf11bSopenharmony_ci * Notice of Export Control Law
30beacf11bSopenharmony_ci * ===============================================
31beacf11bSopenharmony_ci * Huawei LiteOS may be subject to applicable export control laws and regulations, which might
32beacf11bSopenharmony_ci * include those applicable to Huawei LiteOS of U.S. and the country in which you are located.
33beacf11bSopenharmony_ci * Import, export and usage of Huawei LiteOS in any manner by you shall be in compliance with such
34beacf11bSopenharmony_ci * applicable export control laws and regulations.
35beacf11bSopenharmony_ci * --------------------------------------------------------------------------- */
36beacf11bSopenharmony_ci
37beacf11bSopenharmony_ci#include <lwip/netifapi.h>
38beacf11bSopenharmony_ci#include "gadget/f_ether.h"
39beacf11bSopenharmony_ci#include "gadget/rndis.h"
40beacf11bSopenharmony_ci#include "gadget/composite.h"
41beacf11bSopenharmony_ci#include "implementation/global_implementation.h"
42beacf11bSopenharmony_ci#include "controller/usb_device/dwc_otg_pcd.h"
43beacf11bSopenharmony_ci#include "controller/usb_device/dwc_otg_pcd_intr.h"
44beacf11bSopenharmony_ci#include "net/usb_eth_drv.h"
45beacf11bSopenharmony_ci
46beacf11bSopenharmony_ci#ifdef __cplusplus
47beacf11bSopenharmony_ci#if __cplusplus
48beacf11bSopenharmony_ciextern "C" {
49beacf11bSopenharmony_ci#endif /* __cplusplus */
50beacf11bSopenharmony_ci#endif /* __cplusplus */
51beacf11bSopenharmony_ci
52beacf11bSopenharmony_ciconst struct netif *g_ether_usb0;
53beacf11bSopenharmony_ci
54beacf11bSopenharmony_ci/* device driver structure definition */
55beacf11bSopenharmony_ci
56beacf11bSopenharmony_cistatic const driver_t g_fethernet_driver_t =
57beacf11bSopenharmony_ci{
58beacf11bSopenharmony_ci  .name     = "fethernet",
59beacf11bSopenharmony_ci  .methods  = NULL,
60beacf11bSopenharmony_ci  .size     = 0
61beacf11bSopenharmony_ci};
62beacf11bSopenharmony_ci
63beacf11bSopenharmony_ci/* private device class information */
64beacf11bSopenharmony_ci
65beacf11bSopenharmony_cistatic devclass_t g_fethernet_devclass;
66beacf11bSopenharmony_ciDRIVER_MODULE(fethernet, simple, g_fethernet_driver_t, g_fethernet_devclass, usbdev_rndis_initialize, 0);
67beacf11bSopenharmony_ci
68beacf11bSopenharmony_ci#define DEIVICE_VENDOR_ID    0x0525
69beacf11bSopenharmony_ci#define DEIVICE_PRODUCT_ID   0xa4a2
70beacf11bSopenharmony_ci
71beacf11bSopenharmony_ci#define ETHER_NCONFIGS       1
72beacf11bSopenharmony_ci#define ETHER_CONFIGID       0
73beacf11bSopenharmony_ci#define ETHER_NINTERFACES    2
74beacf11bSopenharmony_ci#define ETHER_NSTRIDS        5
75beacf11bSopenharmony_ci#define ETHER_NUM_EPS        3
76beacf11bSopenharmony_ci
77beacf11bSopenharmony_ci#define RNDIS_STRING_ID_LEN      4
78beacf11bSopenharmony_ci#define RNDIS_STRING_PID_LEN     44
79beacf11bSopenharmony_ci#define RNDIS_VERSION_STRING_LEN 62
80beacf11bSopenharmony_ci#define RNDIS_STRING_LEN         58
81beacf11bSopenharmony_ci#define RNDIS_TYPE_LEN           40
82beacf11bSopenharmony_ci
83beacf11bSopenharmony_cistatic const char g_rndis_string_id[RNDIS_STRING_ID_LEN] =
84beacf11bSopenharmony_ci{
85beacf11bSopenharmony_ci  RNDIS_STRING_ID_LEN, UDESC_STRING, 0x09, 0x04
86beacf11bSopenharmony_ci};
87beacf11bSopenharmony_ci
88beacf11bSopenharmony_cistatic const char g_rndis_string_pid[RNDIS_STRING_PID_LEN] =
89beacf11bSopenharmony_ci{
90beacf11bSopenharmony_ci  RNDIS_STRING_PID_LEN, UDESC_STRING, 'R', 0, 'N', 0, 'D', 0, 'I',
91beacf11bSopenharmony_ci  0, 'S', 0, '/', 0, 'E', 0, 't', 0, 'h', 0, 'e', 0, 'r', 0, 'n',
92beacf11bSopenharmony_ci  0, 'e', 0, 't', 0, ' ', 0, 'G', 0, 'a', 0, 'd', 0, 'g', 0, 'e',
93beacf11bSopenharmony_ci  0, 't', 0
94beacf11bSopenharmony_ci};
95beacf11bSopenharmony_ci
96beacf11bSopenharmony_cistatic const char g_version_string[RNDIS_VERSION_STRING_LEN] =
97beacf11bSopenharmony_ci{
98beacf11bSopenharmony_ci  RNDIS_VERSION_STRING_LEN, UDESC_STRING, 0x4c, 0x00, 0x69, 0x00,
99beacf11bSopenharmony_ci  0x6e, 0x00, 0x75, 0x00, 0x78, 0x00, 0x20, 0x00, 0x33, 0x00, 0x2e,
100beacf11bSopenharmony_ci  0x00, 0x31, 0x00, 0x38, 0x00, 0x2e, 0x00, 0x32, 0x00, 0x30, 0x00,
101beacf11bSopenharmony_ci  0x20, 0x00, 0x77, 0x00, 0x69, 0x00, 0x74, 0x00, 0x68, 0x00, 0x20,
102beacf11bSopenharmony_ci  0x00, 0x64, 0x00, 0x77, 0x00, 0x63, 0x00, 0x5f, 0x00, 0x6f, 0x00,
103beacf11bSopenharmony_ci  0x74, 0x00, 0x67, 0x00, 0x5f, 0x00, 0x70, 0x00, 0x63, 0x00, 0x64,
104beacf11bSopenharmony_ci  0x00
105beacf11bSopenharmony_ci};
106beacf11bSopenharmony_ci
107beacf11bSopenharmony_cistatic const char g_rndis_string[RNDIS_STRING_LEN] =
108beacf11bSopenharmony_ci{
109beacf11bSopenharmony_ci  RNDIS_STRING_LEN, UDESC_STRING, 0x52, 0x00, 0x4e, 0x00, 0x44, 0x00,
110beacf11bSopenharmony_ci  0x49, 0x00, 0x53, 0x00, 0x20, 0x00, 0x43, 0x00, 0x6f, 0x00, 0x6d,
111beacf11bSopenharmony_ci  0x00, 0x6d, 0x00, 0x75, 0x00, 0x6e, 0x00, 0x69, 0x00, 0x63, 0x00,
112beacf11bSopenharmony_ci  0x61, 0x00, 0x74, 0x00, 0x69, 0x00, 0x6f, 0x00, 0x6e, 0x00, 0x73,
113beacf11bSopenharmony_ci  0x00, 0x20, 0x00, 0x43, 0x00, 0x6f, 0x00, 0x6e, 0x00, 0x74, 0x00,
114beacf11bSopenharmony_ci  0x72, 0x00, 0x6f, 0x00, 0x6c, 0x00
115beacf11bSopenharmony_ci};
116beacf11bSopenharmony_ci
117beacf11bSopenharmony_cistatic const char g_rndis_type_string[RNDIS_TYPE_LEN] =
118beacf11bSopenharmony_ci{
119beacf11bSopenharmony_ci  RNDIS_TYPE_LEN, UDESC_STRING, 0x52, 0x00, 0x4e, 0x00, 0x44, 0x00,
120beacf11bSopenharmony_ci  0x49, 0x00, 0x53, 0x00, 0x20, 0x00, 0x45, 0x00, 0x74, 0x00, 0x68,
121beacf11bSopenharmony_ci  0x00, 0x65, 0x00, 0x72, 0x00, 0x6e, 0x00, 0x65, 0x00, 0x74, 0x00,
122beacf11bSopenharmony_ci  0x20, 0x00, 0x44, 0x00, 0x61, 0x00, 0x74, 0x00, 0x61, 0x00
123beacf11bSopenharmony_ci};
124beacf11bSopenharmony_ci
125beacf11bSopenharmony_cistatic const struct usb_device_descriptor g_fether_device_desc =
126beacf11bSopenharmony_ci{
127beacf11bSopenharmony_ci  .bLength            = sizeof(struct usb_device_descriptor),
128beacf11bSopenharmony_ci  .bDescriptorType    = UDESC_DEVICE,
129beacf11bSopenharmony_ci  HSETW(.bcdUSB,      UD_BCD_USB),         /* USB version */
130beacf11bSopenharmony_ci  .bDeviceClass       = UDCLASS_COMM,
131beacf11bSopenharmony_ci  .bDeviceSubClass    = 0,
132beacf11bSopenharmony_ci  .bDeviceProtocol    = 0,
133beacf11bSopenharmony_ci  .bMaxPacketSize     = UD_USB_MPS,
134beacf11bSopenharmony_ci  HSETW(.idVendor,    DEIVICE_VENDOR_ID),  /* vendor */
135beacf11bSopenharmony_ci  HSETW(.idProduct,   DEIVICE_PRODUCT_ID), /* product */
136beacf11bSopenharmony_ci  HSETW(.bcdDevice,   0x0318),             /* device version */
137beacf11bSopenharmony_ci  .iManufacturer      = 1,
138beacf11bSopenharmony_ci  .iProduct           = 2,
139beacf11bSopenharmony_ci  .iSerialNumber      = 0,
140beacf11bSopenharmony_ci  .bNumConfigurations = 1,
141beacf11bSopenharmony_ci};
142beacf11bSopenharmony_ci
143beacf11bSopenharmony_cistatic struct usbd_string g_fether_device_strings[] =
144beacf11bSopenharmony_ci{
145beacf11bSopenharmony_ci  {0, g_rndis_string_id},
146beacf11bSopenharmony_ci  {1, g_version_string},
147beacf11bSopenharmony_ci  {2, g_rndis_string_pid},
148beacf11bSopenharmony_ci  {4, g_rndis_string},
149beacf11bSopenharmony_ci  {5, g_rndis_type_string},
150beacf11bSopenharmony_ci  USBD_DEVICE_STRINGS_END
151beacf11bSopenharmony_ci};
152beacf11bSopenharmony_ci
153beacf11bSopenharmony_ci
154beacf11bSopenharmony_cistatic inline int is_multicast_eth_addr(const uint8_t *addr)
155beacf11bSopenharmony_ci{
156beacf11bSopenharmony_ci  return (0x01 & addr[0]);
157beacf11bSopenharmony_ci}
158beacf11bSopenharmony_ci
159beacf11bSopenharmony_ciuint8_t eth_set_hwaddr(struct netif *usb_netif, uint8_t *addr, uint8_t len)
160beacf11bSopenharmony_ci{
161beacf11bSopenharmony_ci  errno_t err;
162beacf11bSopenharmony_ci
163beacf11bSopenharmony_ci  if (is_multicast_eth_addr(addr))
164beacf11bSopenharmony_ci    {
165beacf11bSopenharmony_ci      usb_err("config a multicast mac address, please check!\n");
166beacf11bSopenharmony_ci      return 1;
167beacf11bSopenharmony_ci    }
168beacf11bSopenharmony_ci
169beacf11bSopenharmony_ci  if (len != NETIF_MAX_HWADDR_LEN)
170beacf11bSopenharmony_ci    {
171beacf11bSopenharmony_ci      usb_err("config wrong mac address len=%u\n", len);
172beacf11bSopenharmony_ci      return 1;
173beacf11bSopenharmony_ci    }
174beacf11bSopenharmony_ci
175beacf11bSopenharmony_ci  err = memcpy_s(usb_netif->hwaddr, NETIF_MAX_HWADDR_LEN, addr, len);
176beacf11bSopenharmony_ci  if (err != EOK)
177beacf11bSopenharmony_ci    {
178beacf11bSopenharmony_ci      usb_err("memcpy_s fail, err:%d\n", err);
179beacf11bSopenharmony_ci      return 1;
180beacf11bSopenharmony_ci    }
181beacf11bSopenharmony_ci
182beacf11bSopenharmony_ci  return 0;
183beacf11bSopenharmony_ci}
184beacf11bSopenharmony_ci
185beacf11bSopenharmony_civoid eth_random_addr(uint8_t *addr)
186beacf11bSopenharmony_ci{
187beacf11bSopenharmony_ci  uint32_t rand_val;
188beacf11bSopenharmony_ci  uint32_t nowclocks;
189beacf11bSopenharmony_ci
190beacf11bSopenharmony_ci  msleep(200);
191beacf11bSopenharmony_ci  nowclocks = hi_sched_clock() & 0xffffffff;  /* Get low 32-bit value */
192beacf11bSopenharmony_ci  srand(nowclocks);
193beacf11bSopenharmony_ci  rand_val = (uint32_t)rand();
194beacf11bSopenharmony_ci  addr[0]  = rand_val & 0xff;
195beacf11bSopenharmony_ci  addr[1]  = (rand_val >> 8) & 0xff;
196beacf11bSopenharmony_ci  addr[2]  = (rand_val >> 16) & 0xff;
197beacf11bSopenharmony_ci  addr[3]  = (rand_val >> 24) & 0xff;
198beacf11bSopenharmony_ci
199beacf11bSopenharmony_ci  msleep(200);
200beacf11bSopenharmony_ci  nowclocks = hi_sched_clock() & 0xffffffff;  /* Get low 32-bit value */
201beacf11bSopenharmony_ci  srand(nowclocks);
202beacf11bSopenharmony_ci  rand_val = (uint32_t)rand();
203beacf11bSopenharmony_ci  addr[4]  = rand_val & 0xff;
204beacf11bSopenharmony_ci  addr[5]  = (rand_val >> 8) & 0xff;
205beacf11bSopenharmony_ci  addr[0] &= 0xfe;  /* clear multicast bit */
206beacf11bSopenharmony_ci  addr[0] |= 0x02;  /* set local assignment bit (IEEE802) */
207beacf11bSopenharmony_ci}
208beacf11bSopenharmony_ci
209beacf11bSopenharmony_cistatic void eth_tx(struct netif *usb_netif, struct pbuf *p)
210beacf11bSopenharmony_ci{
211beacf11bSopenharmony_ci  struct los_eth_driver *sc = (struct los_eth_driver *)usb_netif->state;
212beacf11bSopenharmony_ci  struct eth_drv_sg sg_list[MAX_ETH_DRV_SG];
213beacf11bSopenharmony_ci  struct pbuf *q;
214beacf11bSopenharmony_ci  int sg_len = 0;
215beacf11bSopenharmony_ci
216beacf11bSopenharmony_ci  for (q = p; q != NULL; q = q->next)
217beacf11bSopenharmony_ci    {
218beacf11bSopenharmony_ci      sg_list[sg_len].buf = (UINTPTR)q->payload;
219beacf11bSopenharmony_ci      sg_list[sg_len++].len = q->len;
220beacf11bSopenharmony_ci    }
221beacf11bSopenharmony_ci
222beacf11bSopenharmony_ci  rndis_tx(sc, sg_list, sg_len, p->tot_len, (UINTPTR)p);
223beacf11bSopenharmony_ci}
224beacf11bSopenharmony_ci
225beacf11bSopenharmony_civoid eth_rx(struct los_eth_driver *sc, const struct usbdev_req_s *req)
226beacf11bSopenharmony_ci{
227beacf11bSopenharmony_ci  struct netif *usb_netif = &sc->ac_if;
228beacf11bSopenharmony_ci  uint32_t total_len      = req->xfrd - RNDIS_PACKET_HDR_SIZE;
229beacf11bSopenharmony_ci  struct pbuf *p;
230beacf11bSopenharmony_ci
231beacf11bSopenharmony_ci  if (total_len > MAX_ETH_MSG)
232beacf11bSopenharmony_ci    {
233beacf11bSopenharmony_ci      total_len = MAX_ETH_MSG;
234beacf11bSopenharmony_ci    }
235beacf11bSopenharmony_ci
236beacf11bSopenharmony_ci  p = pbuf_alloc(PBUF_RAW, (uint16_t)(total_len + ETH_PAD_SIZE), PBUF_RAM);
237beacf11bSopenharmony_ci  if (p == NULL)
238beacf11bSopenharmony_ci    {
239beacf11bSopenharmony_ci      usb_err("eth_drv_recv : pbuf_alloc failed\n");
240beacf11bSopenharmony_ci      return;
241beacf11bSopenharmony_ci    }
242beacf11bSopenharmony_ci
243beacf11bSopenharmony_ci#if ETH_PAD_SIZE
244beacf11bSopenharmony_ci  (void)pbuf_header(p, -ETH_PAD_SIZE); /* drop the padding word */
245beacf11bSopenharmony_ci#endif
246beacf11bSopenharmony_ci
247beacf11bSopenharmony_ci  (void)memcpy_s(p->payload, total_len, &req->buf[RNDIS_PACKET_HDR_SIZE], total_len);
248beacf11bSopenharmony_ci
249beacf11bSopenharmony_ci#if ETH_PAD_SIZE
250beacf11bSopenharmony_ci  (void)pbuf_header(p, ETH_PAD_SIZE); /* reclaim the padding word */
251beacf11bSopenharmony_ci#endif
252beacf11bSopenharmony_ci
253beacf11bSopenharmony_ci  driverif_input(usb_netif, p);
254beacf11bSopenharmony_ci}
255beacf11bSopenharmony_ci
256beacf11bSopenharmony_ci#if PF_PKT_SUPPORT
257beacf11bSopenharmony_cistatic void eth_drv_config(struct netif *usb_netif, uint32_t cflags, uint8_t set_bit)
258beacf11bSopenharmony_ci{
259beacf11bSopenharmony_ci  LWIP_UNUSED_ARG(usb_netif);
260beacf11bSopenharmony_ci  LWIP_UNUSED_ARG(cflags);
261beacf11bSopenharmony_ci  LWIP_UNUSED_ARG(set_bit);
262beacf11bSopenharmony_ci
263beacf11bSopenharmony_ci  /* Nothing to be done for now */
264beacf11bSopenharmony_ci
265beacf11bSopenharmony_ci}
266beacf11bSopenharmony_ci#endif
267beacf11bSopenharmony_ci
268beacf11bSopenharmony_civoid netdev_register(struct los_eth_driver *sc)
269beacf11bSopenharmony_ci{
270beacf11bSopenharmony_ci  struct netif *usb_netif = &sc->ac_if;
271beacf11bSopenharmony_ci  ip4_addr_t ipaddr, netmask, gw;
272beacf11bSopenharmony_ci  uint8_t dev_addr[NETIF_MAX_HWADDR_LEN];
273beacf11bSopenharmony_ci  err_t ret;
274beacf11bSopenharmony_ci
275beacf11bSopenharmony_ci  IP4_ADDR(&gw, 10, 67, 233, 1);
276beacf11bSopenharmony_ci  IP4_ADDR(&ipaddr, 10, 67, 233, 3);
277beacf11bSopenharmony_ci  IP4_ADDR(&netmask, 255, 255, 255, 0);
278beacf11bSopenharmony_ci
279beacf11bSopenharmony_ci  usb_netif->state           = sc;
280beacf11bSopenharmony_ci  usb_netif->drv_send        = eth_tx;
281beacf11bSopenharmony_ci  usb_netif->drv_set_hwaddr  = eth_set_hwaddr;
282beacf11bSopenharmony_ci  usb_netif->link_layer_type = ETHERNET_DRIVER_IF;
283beacf11bSopenharmony_ci  usb_netif->hwaddr_len      = NETIF_MAX_HWADDR_LEN;
284beacf11bSopenharmony_ci
285beacf11bSopenharmony_ci#if PF_PKT_SUPPORT
286beacf11bSopenharmony_ci  usb_netif->drv_config = eth_drv_config;
287beacf11bSopenharmony_ci#endif
288beacf11bSopenharmony_ci
289beacf11bSopenharmony_ci#if LWIP_NETIF_ETHTOOL
290beacf11bSopenharmony_ci  usb_netif->ethtool_ops = NULL;
291beacf11bSopenharmony_ci#endif
292beacf11bSopenharmony_ci
293beacf11bSopenharmony_ci  eth_random_addr(dev_addr);
294beacf11bSopenharmony_ci  (void)memcpy_s(usb_netif->hwaddr, NETIF_MAX_HWADDR_LEN, dev_addr, NETIF_MAX_HWADDR_LEN);
295beacf11bSopenharmony_ci
296beacf11bSopenharmony_ci  ret = netifapi_netif_add(usb_netif, &ipaddr, &netmask, &gw);
297beacf11bSopenharmony_ci  if (ret)
298beacf11bSopenharmony_ci    {
299beacf11bSopenharmony_ci      usb_err("%s %d, add netif failed, ret:%d\n", __FUNCTION__, __LINE__, ret);
300beacf11bSopenharmony_ci      return;
301beacf11bSopenharmony_ci    }
302beacf11bSopenharmony_ci
303beacf11bSopenharmony_ci  (void)netifapi_netif_set_link_down(usb_netif);
304beacf11bSopenharmony_ci
305beacf11bSopenharmony_ci  g_ether_usb0 = usb_netif;
306beacf11bSopenharmony_ci}
307beacf11bSopenharmony_ci
308beacf11bSopenharmony_civoid netdev_unregister(struct los_eth_driver *sc)
309beacf11bSopenharmony_ci{
310beacf11bSopenharmony_ci  struct netif *usb_netif = &sc->ac_if;
311beacf11bSopenharmony_ci
312beacf11bSopenharmony_ci  if (netifapi_netif_remove(usb_netif) != ERR_OK)
313beacf11bSopenharmony_ci    {
314beacf11bSopenharmony_ci      usb_err("%s %d, remove netif failed!\n", __FUNCTION__, __LINE__);
315beacf11bSopenharmony_ci    }
316beacf11bSopenharmony_ci}
317beacf11bSopenharmony_ci
318beacf11bSopenharmony_civoid rndis_mkdevdesc(uint8_t *buf)
319beacf11bSopenharmony_ci{
320beacf11bSopenharmony_ci  errno_t ret = memcpy_s(buf, USB_COMP_EP0_BUFSIZ, &g_fether_device_desc, sizeof(g_fether_device_desc));
321beacf11bSopenharmony_ci  if (ret != EOK)
322beacf11bSopenharmony_ci    {
323beacf11bSopenharmony_ci      usb_err("memcpy_s fail!, ret:%d\n", ret);
324beacf11bSopenharmony_ci      return;
325beacf11bSopenharmony_ci    }
326beacf11bSopenharmony_ci}
327beacf11bSopenharmony_ci
328beacf11bSopenharmony_ciint16_t rndis_mkcfgdesc(uint8_t *buf, struct usbdev_devinfo_s *devinfo)
329beacf11bSopenharmony_ci{
330beacf11bSopenharmony_ci  int16_t total_len = 0;
331beacf11bSopenharmony_ci  int16_t len       = USB_CONFIG_DESC_SIZE;
332beacf11bSopenharmony_ci  errno_t ret;
333beacf11bSopenharmony_ci
334beacf11bSopenharmony_ci  (void)devinfo;
335beacf11bSopenharmony_ci
336beacf11bSopenharmony_ci  /* Copy RNDIS device configure descriptor. */
337beacf11bSopenharmony_ci
338beacf11bSopenharmony_ci  ret = memcpy_s(buf, USB_COMP_EP0_BUFSIZ, g_rndis_hs_desc.rndis_config, (uint16_t)len);
339beacf11bSopenharmony_ci  if (ret != EOK)
340beacf11bSopenharmony_ci    {
341beacf11bSopenharmony_ci      usb_err("memcpy_s fail, ret:%d\n", ret);
342beacf11bSopenharmony_ci      return -1;
343beacf11bSopenharmony_ci    }
344beacf11bSopenharmony_ci  total_len += len;
345beacf11bSopenharmony_ci
346beacf11bSopenharmony_ci  /* Copy RNDIS device configure descriptor. */
347beacf11bSopenharmony_ci
348beacf11bSopenharmony_ci  buf += USB_CONFIG_DESC_SIZE;
349beacf11bSopenharmony_ci  len  = sizeof(g_rndis_hs_func_desc);
350beacf11bSopenharmony_ci  ret  = memcpy_s(buf, USB_COMP_EP0_BUFSIZ - (uint16_t)total_len, g_rndis_hs_desc.rndis_func, (uint16_t)len);
351beacf11bSopenharmony_ci  if (ret != EOK)
352beacf11bSopenharmony_ci    {
353beacf11bSopenharmony_ci      usb_err("memcpy_s fail, ret:%d\n", ret);
354beacf11bSopenharmony_ci      return -1;
355beacf11bSopenharmony_ci    }
356beacf11bSopenharmony_ci  total_len += len;
357beacf11bSopenharmony_ci
358beacf11bSopenharmony_ci  return total_len;
359beacf11bSopenharmony_ci}
360beacf11bSopenharmony_ci
361beacf11bSopenharmony_ciint rndis_mkstrdesc(uint8_t id, uint8_t *buf)
362beacf11bSopenharmony_ci{
363beacf11bSopenharmony_ci  const char *str;
364beacf11bSopenharmony_ci  errno_t ret;
365beacf11bSopenharmony_ci  int i;
366beacf11bSopenharmony_ci
367beacf11bSopenharmony_ci  for (i = 0; g_fether_device_strings[i].s != NULL; i++)
368beacf11bSopenharmony_ci    {
369beacf11bSopenharmony_ci      str = g_fether_device_strings[i].s;
370beacf11bSopenharmony_ci      if (g_fether_device_strings[i].id == id)
371beacf11bSopenharmony_ci        {
372beacf11bSopenharmony_ci          ret = memcpy_s(buf, USB_COMP_EP0_BUFSIZ, str, str[0]);
373beacf11bSopenharmony_ci          if (ret != EOK)
374beacf11bSopenharmony_ci            {
375beacf11bSopenharmony_ci              usb_err("memcpy_s failed, ret = %d\n", ret);
376beacf11bSopenharmony_ci              return -1;
377beacf11bSopenharmony_ci            }
378beacf11bSopenharmony_ci          return str[0];
379beacf11bSopenharmony_ci        }
380beacf11bSopenharmony_ci    }
381beacf11bSopenharmony_ci
382beacf11bSopenharmony_ci  usb_err("Can not find the id = %u of string\n", id);
383beacf11bSopenharmony_ci  return -1;
384beacf11bSopenharmony_ci}
385beacf11bSopenharmony_ci
386beacf11bSopenharmony_civoid rndis_get_composite_devdesc(struct composite_devdesc_s *dev)
387beacf11bSopenharmony_ci{
388beacf11bSopenharmony_ci  (void)memset_s(dev, sizeof(struct composite_devdesc_s), 0, sizeof(struct composite_devdesc_s));
389beacf11bSopenharmony_ci
390beacf11bSopenharmony_ci  dev->mkdevdesc  = rndis_mkdevdesc;
391beacf11bSopenharmony_ci  dev->mkconfdesc = rndis_mkcfgdesc;
392beacf11bSopenharmony_ci  dev->mkstrdesc  = rndis_mkstrdesc;
393beacf11bSopenharmony_ci  dev->nconfigs   = ETHER_NCONFIGS; /* Number of configurations supported */
394beacf11bSopenharmony_ci  dev->configid   = ETHER_CONFIGID; /* The only supported configuration ID */
395beacf11bSopenharmony_ci
396beacf11bSopenharmony_ci  /* Interfaces.
397beacf11bSopenharmony_ci   *
398beacf11bSopenharmony_ci   * ifnobase must be provided by board-specific logic
399beacf11bSopenharmony_ci   */
400beacf11bSopenharmony_ci
401beacf11bSopenharmony_ci  dev->devinfo.ninterfaces = ETHER_NINTERFACES; /* Number of interfaces in the configuration */
402beacf11bSopenharmony_ci
403beacf11bSopenharmony_ci  /* Strings.
404beacf11bSopenharmony_ci   *
405beacf11bSopenharmony_ci   * strbase must be provided by board-specific logic
406beacf11bSopenharmony_ci   */
407beacf11bSopenharmony_ci
408beacf11bSopenharmony_ci  dev->devinfo.nstrings = ETHER_NSTRIDS;  /* Number of Strings */
409beacf11bSopenharmony_ci
410beacf11bSopenharmony_ci  /* Endpoints.
411beacf11bSopenharmony_ci   *
412beacf11bSopenharmony_ci   * Endpoint numbers must be provided by board-specific logic.
413beacf11bSopenharmony_ci   */
414beacf11bSopenharmony_ci
415beacf11bSopenharmony_ci  dev->devinfo.nendpoints = ETHER_NUM_EPS;
416beacf11bSopenharmony_ci}
417beacf11bSopenharmony_ci
418beacf11bSopenharmony_ci#ifdef __cplusplus
419beacf11bSopenharmony_ci#if __cplusplus
420beacf11bSopenharmony_ci}
421beacf11bSopenharmony_ci#endif /* __cplusplus */
422beacf11bSopenharmony_ci#endif /* __cplusplus */