Browse Source

[ecm] Use generic USB network device framework

Signed-off-by: Michael Brown <mcb30@ipxe.org>
tags/v1.20.1
Michael Brown 9 years ago
parent
commit
5b9b5ced4e
2 changed files with 35 additions and 211 deletions
  1. 32
    187
      src/drivers/net/ecm.c
  2. 3
    24
      src/drivers/net/ecm.h

+ 32
- 187
src/drivers/net/ecm.c View File

@@ -126,7 +126,8 @@ int ecm_fetch_mac ( struct usb_device *usb,
126 126
  */
127 127
 static void ecm_intr_complete ( struct usb_endpoint *ep,
128 128
 				struct io_buffer *iobuf, int rc ) {
129
-	struct ecm_device *ecm = container_of ( ep, struct ecm_device, intr );
129
+	struct ecm_device *ecm = container_of ( ep, struct ecm_device,
130
+						usbnet.intr );
130 131
 	struct net_device *netdev = ecm->netdev;
131 132
 	struct usb_setup_packet *message;
132 133
 	size_t len = iob_len ( iobuf );
@@ -197,43 +198,6 @@ static struct usb_endpoint_driver_operations ecm_intr_operations = {
197 198
 	.complete = ecm_intr_complete,
198 199
 };
199 200
 
200
-/**
201
- * Open communications interface
202
- *
203
- * @v ecm		CDC-ECM device
204
- * @ret rc		Return status code
205
- */
206
-static int ecm_comms_open ( struct ecm_device *ecm ) {
207
-	int rc;
208
-
209
-	/* Open interrupt endpoint */
210
-	if ( ( rc = usb_endpoint_open ( &ecm->intr ) ) != 0 ) {
211
-		DBGC ( ecm, "ECM %p could not open interrupt: %s\n",
212
-		       ecm, strerror ( rc ) );
213
-		goto err_open;
214
-	}
215
-
216
-	/* Refill interrupt endpoint */
217
-	usb_refill ( &ecm->intr );
218
-
219
-	return 0;
220
-
221
-	usb_endpoint_close ( &ecm->intr );
222
- err_open:
223
-	return rc;
224
-}
225
-
226
-/**
227
- * Close communications interface
228
- *
229
- * @v ecm		CDC-ECM device
230
- */
231
-static void ecm_comms_close ( struct ecm_device *ecm ) {
232
-
233
-	/* Close interrupt endpoint */
234
-	usb_endpoint_close ( &ecm->intr );
235
-}
236
-
237 201
 /******************************************************************************
238 202
  *
239 203
  * CDC-ECM data interface
@@ -250,7 +214,8 @@ static void ecm_comms_close ( struct ecm_device *ecm ) {
250 214
  */
251 215
 static void ecm_in_complete ( struct usb_endpoint *ep, struct io_buffer *iobuf,
252 216
 			      int rc ) {
253
-	struct ecm_device *ecm = container_of ( ep, struct ecm_device, in );
217
+	struct ecm_device *ecm = container_of ( ep, struct ecm_device,
218
+						usbnet.in );
254 219
 	struct net_device *netdev = ecm->netdev;
255 220
 
256 221
 	/* Profile receive completions */
@@ -299,7 +264,7 @@ static int ecm_out_transmit ( struct ecm_device *ecm,
299 264
 	profile_start ( &ecm_out_profiler );
300 265
 
301 266
 	/* Enqueue I/O buffer */
302
-	if ( ( rc = usb_stream ( &ecm->out, iobuf, 1 ) ) != 0 )
267
+	if ( ( rc = usb_stream ( &ecm->usbnet.out, iobuf, 1 ) ) != 0 )
303 268
 		return rc;
304 269
 
305 270
 	profile_stop ( &ecm_out_profiler );
@@ -315,7 +280,8 @@ static int ecm_out_transmit ( struct ecm_device *ecm,
315 280
  */
316 281
 static void ecm_out_complete ( struct usb_endpoint *ep, struct io_buffer *iobuf,
317 282
 			       int rc ) {
318
-	struct ecm_device *ecm = container_of ( ep, struct ecm_device, out );
283
+	struct ecm_device *ecm = container_of ( ep, struct ecm_device,
284
+						usbnet.out );
319 285
 	struct net_device *netdev = ecm->netdev;
320 286
 
321 287
 	/* Report TX completion */
@@ -327,68 +293,6 @@ static struct usb_endpoint_driver_operations ecm_out_operations = {
327 293
 	.complete = ecm_out_complete,
328 294
 };
329 295
 
330
-/**
331
- * Open data interface
332
- *
333
- * @v ecm		CDC-ECM device
334
- * @ret rc		Return status code
335
- */
336
-static int ecm_data_open ( struct ecm_device *ecm ) {
337
-	struct usb_device *usb = ecm->usb;
338
-	int rc;
339
-
340
-	/* Select alternate setting for data interface */
341
-	if ( ( rc = usb_set_interface ( usb, ecm->data,
342
-					ECM_DATA_ALTERNATE ) ) != 0 ) {
343
-		DBGC ( ecm, "ECM %p could not set alternate interface: %s\n",
344
-		       ecm, strerror ( rc ) );
345
-		goto err_set_interface;
346
-	}
347
-
348
-	/* Open bulk IN endpoint */
349
-	if ( ( rc = usb_endpoint_open ( &ecm->in ) ) != 0 ) {
350
-		DBGC ( ecm, "ECM %p could not open bulk IN: %s\n",
351
-		       ecm, strerror ( rc ) );
352
-		goto err_open_in;
353
-	}
354
-
355
-	/* Open bulk OUT endpoint */
356
-	if ( ( rc = usb_endpoint_open ( &ecm->out ) ) != 0 ) {
357
-		DBGC ( ecm, "ECM %p could not open bulk OUT: %s\n",
358
-		       ecm, strerror ( rc ) );
359
-		goto err_open_out;
360
-	}
361
-
362
-	/* Refill bulk IN endpoint */
363
-	usb_refill ( &ecm->in );
364
-
365
-	return 0;
366
-
367
-	usb_endpoint_close ( &ecm->out );
368
- err_open_out:
369
-	usb_endpoint_close ( &ecm->in );
370
- err_open_in:
371
-	usb_set_interface ( usb, ecm->data, 0 );
372
- err_set_interface:
373
-	return rc;
374
-}
375
-
376
-/**
377
- * Close data interface
378
- *
379
- * @v ecm		CDC-ECM device
380
- */
381
-static void ecm_data_close ( struct ecm_device *ecm ) {
382
-	struct usb_device *usb = ecm->usb;
383
-
384
-	/* Close endpoints */
385
-	usb_endpoint_close ( &ecm->out );
386
-	usb_endpoint_close ( &ecm->in );
387
-
388
-	/* Reset data interface */
389
-	usb_set_interface ( usb, ecm->data, 0 );
390
-}
391
-
392 296
 /******************************************************************************
393 297
  *
394 298
  * Network device interface
@@ -408,13 +312,12 @@ static int ecm_open ( struct net_device *netdev ) {
408 312
 	unsigned int filter;
409 313
 	int rc;
410 314
 
411
-	/* Open communications interface */
412
-	if ( ( rc = ecm_comms_open ( ecm ) ) != 0 )
413
-		goto err_comms_open;
414
-
415
-	/* Open data interface */
416
-	if ( ( rc = ecm_data_open ( ecm ) ) != 0 )
417
-		goto err_data_open;
315
+	/* Open USB network device */
316
+	if ( ( rc = usbnet_open ( &ecm->usbnet ) ) != 0 ) {
317
+		DBGC ( ecm, "ECM %p could not open: %s\n",
318
+		       ecm, strerror ( rc ) );
319
+		goto err_open;
320
+	}
418 321
 
419 322
 	/* Set packet filter */
420 323
 	filter = ( ECM_PACKET_TYPE_PROMISCUOUS |
@@ -422,7 +325,7 @@ static int ecm_open ( struct net_device *netdev ) {
422 325
 		   ECM_PACKET_TYPE_DIRECTED |
423 326
 		   ECM_PACKET_TYPE_BROADCAST );
424 327
 	if ( ( rc = usb_control ( usb, ECM_SET_ETHERNET_PACKET_FILTER,
425
-				  filter, ecm->comms, NULL, 0 ) ) != 0 ) {
328
+				  filter, ecm->usbnet.comms, NULL, 0 ) ) != 0 ){
426 329
 		DBGC ( ecm, "ECM %p could not set packet filter: %s\n",
427 330
 		       ecm, strerror ( rc ) );
428 331
 		goto err_set_filter;
@@ -431,10 +334,8 @@ static int ecm_open ( struct net_device *netdev ) {
431 334
 	return 0;
432 335
 
433 336
  err_set_filter:
434
-	ecm_data_close ( ecm );
435
- err_data_open:
436
-	ecm_comms_close ( ecm );
437
- err_comms_open:
337
+	usbnet_close ( &ecm->usbnet );
338
+ err_open:
438 339
 	return rc;
439 340
 }
440 341
 
@@ -446,11 +347,8 @@ static int ecm_open ( struct net_device *netdev ) {
446 347
 static void ecm_close ( struct net_device *netdev ) {
447 348
 	struct ecm_device *ecm = netdev->priv;
448 349
 
449
-	/* Close data interface */
450
-	ecm_data_close ( ecm );
451
-
452
-	/* Close communications interface */
453
-	ecm_comms_close ( ecm );
350
+	/* Close USB network device */
351
+	usbnet_close ( &ecm->usbnet );
454 352
 }
455 353
 
456 354
 /**
@@ -484,12 +382,8 @@ static void ecm_poll ( struct net_device *netdev ) {
484 382
 	/* Poll USB bus */
485 383
 	usb_poll ( ecm->bus );
486 384
 
487
-	/* Refill interrupt endpoint */
488
-	if ( ( rc = usb_refill ( &ecm->intr ) ) != 0 )
489
-		netdev_rx_err ( netdev, NULL, rc );
490
-
491
-	/* Refill bulk IN endpoint */
492
-	if ( ( rc = usb_refill ( &ecm->in ) ) != 0 )
385
+	/* Refill endpoints */
386
+	if ( ( rc = usbnet_refill ( &ecm->usbnet ) ) != 0 )
493 387
 		netdev_rx_err ( netdev, NULL, rc );
494 388
 }
495 389
 
@@ -521,7 +415,6 @@ static int ecm_probe ( struct usb_function *func,
521 415
 	struct net_device *netdev;
522 416
 	struct ecm_device *ecm;
523 417
 	struct usb_interface_descriptor *comms;
524
-	struct usb_interface_descriptor *data;
525 418
 	struct ecm_ethernet_descriptor *ethernet;
526 419
 	int rc;
527 420
 
@@ -538,65 +431,22 @@ static int ecm_probe ( struct usb_function *func,
538 431
 	ecm->usb = usb;
539 432
 	ecm->bus = usb->port->hub->bus;
540 433
 	ecm->netdev = netdev;
541
-	usb_endpoint_init ( &ecm->intr, usb, &ecm_intr_operations );
542
-	usb_endpoint_init ( &ecm->in, usb, &ecm_in_operations );
543
-	usb_endpoint_init ( &ecm->out, usb, &ecm_out_operations );
544
-	usb_refill_init ( &ecm->intr, 0, ECM_INTR_MAX_FILL );
545
-	usb_refill_init ( &ecm->in, ECM_IN_MTU, ECM_IN_MAX_FILL );
434
+	usbnet_init ( &ecm->usbnet, func, &ecm_intr_operations,
435
+		      &ecm_in_operations, &ecm_out_operations );
436
+	usb_refill_init ( &ecm->usbnet.intr, 0, ECM_INTR_MAX_FILL );
437
+	usb_refill_init ( &ecm->usbnet.in, ECM_IN_MTU, ECM_IN_MAX_FILL );
546 438
 	DBGC ( ecm, "ECM %p on %s\n", ecm, func->name );
547 439
 
548
-	/* Identify interfaces */
549
-	if ( func->count < ECM_INTERFACE_COUNT ) {
550
-		DBGC ( ecm, "ECM %p has only %d interfaces\n",
551
-		       ecm, func->count );
552
-		rc = -EINVAL;
553
-		goto err_count;
554
-	}
555
-	ecm->comms = func->interface[ECM_INTERFACE_COMMS];
556
-	ecm->data = func->interface[ECM_INTERFACE_DATA];
557
-
558
-	/* Locate communications interface descriptor */
559
-	comms = usb_interface_descriptor ( config, ecm->comms, 0 );
560
-	if ( ! comms ) {
561
-		DBGC ( ecm, "ECM %p has no communications interface\n", ecm );
562
-		rc = -EINVAL;
563
-		goto err_comms;
564
-	}
565
-
566
-	/* Locate data interface descriptor */
567
-	data = usb_interface_descriptor ( config, ecm->data,
568
-					  ECM_DATA_ALTERNATE );
569
-	if ( ! data ) {
570
-		DBGC ( ecm, "ECM %p has no data interface\n", ecm );
571
-		rc = -EINVAL;
572
-		goto err_data;
573
-	}
574
-
575
-	/* Describe interrupt endpoint */
576
-	if ( ( rc = usb_endpoint_described ( &ecm->intr, config, comms,
577
-					     USB_INTERRUPT, 0 ) ) != 0 ) {
578
-		DBGC ( ecm, "ECM %p could not describe interrupt endpoint: "
579
-		       "%s\n", ecm, strerror ( rc ) );
580
-		goto err_interrupt;
581
-	}
582
-
583
-	/* Describe bulk IN endpoint */
584
-	if ( ( rc = usb_endpoint_described ( &ecm->in, config, data,
585
-					     USB_BULK_IN, 0 ) ) != 0 ) {
586
-		DBGC ( ecm, "ECM %p could not describe bulk IN endpoint: "
587
-		       "%s\n", ecm, strerror ( rc ) );
588
-		goto err_bulk_in;
589
-	}
590
-
591
-	/* Describe bulk OUT endpoint */
592
-	if ( ( rc = usb_endpoint_described ( &ecm->out, config, data,
593
-					     USB_BULK_OUT, 0 ) ) != 0 ) {
594
-		DBGC ( ecm, "ECM %p could not describe bulk OUT endpoint: "
595
-		       "%s\n", ecm, strerror ( rc ) );
596
-		goto err_bulk_out;
440
+	/* Describe USB network device */
441
+	if ( ( rc = usbnet_describe ( &ecm->usbnet, config ) ) != 0 ) {
442
+		DBGC ( ecm, "ECM %p could not describe: %s\n",
443
+		       ecm, strerror ( rc ) );
444
+		goto err_describe;
597 445
 	}
598 446
 
599 447
 	/* Locate Ethernet descriptor */
448
+	comms = usb_interface_descriptor ( config, ecm->usbnet.comms, 0 );
449
+	assert ( comms != NULL );
600 450
 	ethernet = ecm_ethernet_descriptor ( config, comms );
601 451
 	if ( ! ethernet ) {
602 452
 		DBGC ( ecm, "ECM %p has no Ethernet descriptor\n", ecm );
@@ -622,12 +472,7 @@ static int ecm_probe ( struct usb_function *func,
622 472
  err_register:
623 473
  err_fetch_mac:
624 474
  err_ethernet:
625
- err_bulk_out:
626
- err_bulk_in:
627
- err_interrupt:
628
- err_data:
629
- err_comms:
630
- err_count:
475
+ err_describe:
631 476
 	netdev_nullify ( netdev );
632 477
 	netdev_put ( netdev );
633 478
  err_alloc:

+ 3
- 24
src/drivers/net/ecm.h View File

@@ -10,23 +10,12 @@
10 10
 FILE_LICENCE ( GPL2_OR_LATER );
11 11
 
12 12
 #include <ipxe/usb.h>
13
+#include <ipxe/usbnet.h>
13 14
 #include <ipxe/cdc.h>
14 15
 
15 16
 /** CDC-ECM subclass */
16 17
 #define USB_SUBCLASS_CDC_ECM 0x06
17 18
 
18
-/** CDC-ECM interfaces */
19
-enum ecm_interfaces {
20
-	/** Communications interface */
21
-	ECM_INTERFACE_COMMS = 0,
22
-	/** Data interface */
23
-	ECM_INTERFACE_DATA,
24
-	ECM_INTERFACE_COUNT
25
-};
26
-
27
-/** Alternate setting for CDC-ECM data interface */
28
-#define ECM_DATA_ALTERNATE 1
29
-
30 19
 /** Set Ethernet packet filter */
31 20
 #define ECM_SET_ETHERNET_PACKET_FILTER					\
32 21
 	( USB_DIR_OUT | USB_TYPE_CLASS | USB_RECIP_INTERFACE |		\
@@ -72,18 +61,8 @@ struct ecm_device {
72 61
 	struct usb_bus *bus;
73 62
 	/** Network device */
74 63
 	struct net_device *netdev;
75
-
76
-	/** Communications interface */
77
-	unsigned int comms;
78
-	/** Data interface */
79
-	unsigned int data;
80
-
81
-	/** Interrupt endpoint */
82
-	struct usb_endpoint intr;
83
-	/** Bulk IN endpoint */
84
-	struct usb_endpoint in;
85
-	/** Bulk OUT endpoint */
86
-	struct usb_endpoint out;
64
+	/** USB network device */
65
+	struct usbnet_device usbnet;
87 66
 };
88 67
 
89 68
 /** Interrupt maximum fill level

Loading…
Cancel
Save