@@ -1610,6 +1610,138 @@ void usbnet_device_suggests_idle(struct usbnet *dev)
1610
1610
}
1611
1611
EXPORT_SYMBOL (usbnet_device_suggests_idle );
1612
1612
1613
+ /*-------------------------------------------------------------------------*/
1614
+ int usbnet_read_cmd (struct usbnet * dev , u8 cmd , u8 reqtype ,
1615
+ u16 value , u16 index , void * data , u16 size )
1616
+ {
1617
+ void * buf = NULL ;
1618
+ int err = - ENOMEM ;
1619
+
1620
+ netdev_dbg (dev -> net , "usbnet_read_cmd cmd=0x%02x reqtype=%02x"
1621
+ " value=0x%04x index=0x%04x size=%d\n" ,
1622
+ cmd , reqtype , value , index , size );
1623
+
1624
+ if (data ) {
1625
+ buf = kmalloc (size , GFP_KERNEL );
1626
+ if (!buf )
1627
+ goto out ;
1628
+ }
1629
+
1630
+ err = usb_control_msg (dev -> udev , usb_rcvctrlpipe (dev -> udev , 0 ),
1631
+ cmd , reqtype , value , index , buf , size ,
1632
+ USB_CTRL_GET_TIMEOUT );
1633
+ if (err > 0 && err <= size )
1634
+ memcpy (data , buf , err );
1635
+ kfree (buf );
1636
+ out :
1637
+ return err ;
1638
+ }
1639
+ EXPORT_SYMBOL_GPL (usbnet_read_cmd );
1640
+
1641
+ int usbnet_write_cmd (struct usbnet * dev , u8 cmd , u8 reqtype ,
1642
+ u16 value , u16 index , const void * data , u16 size )
1643
+ {
1644
+ void * buf = NULL ;
1645
+ int err = - ENOMEM ;
1646
+
1647
+ netdev_dbg (dev -> net , "usbnet_write_cmd cmd=0x%02x reqtype=%02x"
1648
+ " value=0x%04x index=0x%04x size=%d\n" ,
1649
+ cmd , reqtype , value , index , size );
1650
+
1651
+ if (data ) {
1652
+ buf = kmemdup (data , size , GFP_KERNEL );
1653
+ if (!buf )
1654
+ goto out ;
1655
+ }
1656
+
1657
+ err = usb_control_msg (dev -> udev , usb_sndctrlpipe (dev -> udev , 0 ),
1658
+ cmd , reqtype , value , index , buf , size ,
1659
+ USB_CTRL_SET_TIMEOUT );
1660
+ kfree (buf );
1661
+
1662
+ out :
1663
+ return err ;
1664
+ }
1665
+ EXPORT_SYMBOL_GPL (usbnet_write_cmd );
1666
+
1667
+ static void usbnet_async_cmd_cb (struct urb * urb )
1668
+ {
1669
+ struct usb_ctrlrequest * req = (struct usb_ctrlrequest * )urb -> context ;
1670
+ int status = urb -> status ;
1671
+
1672
+ if (status < 0 )
1673
+ dev_dbg (& urb -> dev -> dev , "%s failed with %d" ,
1674
+ __func__ , status );
1675
+
1676
+ kfree (req );
1677
+ usb_free_urb (urb );
1678
+ }
1679
+
1680
+ int usbnet_write_cmd_async (struct usbnet * dev , u8 cmd , u8 reqtype ,
1681
+ u16 value , u16 index , const void * data , u16 size )
1682
+ {
1683
+ struct usb_ctrlrequest * req = NULL ;
1684
+ struct urb * urb ;
1685
+ int err = - ENOMEM ;
1686
+ void * buf = NULL ;
1687
+
1688
+ netdev_dbg (dev -> net , "usbnet_write_cmd cmd=0x%02x reqtype=%02x"
1689
+ " value=0x%04x index=0x%04x size=%d\n" ,
1690
+ cmd , reqtype , value , index , size );
1691
+
1692
+ urb = usb_alloc_urb (0 , GFP_ATOMIC );
1693
+ if (!urb ) {
1694
+ netdev_err (dev -> net , "Error allocating URB in"
1695
+ " %s!\n" , __func__ );
1696
+ goto fail ;
1697
+ }
1698
+
1699
+ if (data ) {
1700
+ buf = kmemdup (data , size , GFP_ATOMIC );
1701
+ if (!buf ) {
1702
+ netdev_err (dev -> net , "Error allocating buffer"
1703
+ " in %s!\n" , __func__ );
1704
+ goto fail_free ;
1705
+ }
1706
+ }
1707
+
1708
+ req = kmalloc (sizeof (struct usb_ctrlrequest ), GFP_ATOMIC );
1709
+ if (!req ) {
1710
+ netdev_err (dev -> net , "Failed to allocate memory for %s\n" ,
1711
+ __func__ );
1712
+ goto fail_free_buf ;
1713
+ }
1714
+
1715
+ req -> bRequestType = reqtype ;
1716
+ req -> bRequest = cmd ;
1717
+ req -> wValue = cpu_to_le16 (value );
1718
+ req -> wIndex = cpu_to_le16 (index );
1719
+ req -> wLength = cpu_to_le16 (size );
1720
+
1721
+ usb_fill_control_urb (urb , dev -> udev ,
1722
+ usb_sndctrlpipe (dev -> udev , 0 ),
1723
+ (void * )req , buf , size ,
1724
+ usbnet_async_cmd_cb , req );
1725
+ urb -> transfer_flags |= URB_FREE_BUFFER ;
1726
+
1727
+ err = usb_submit_urb (urb , GFP_ATOMIC );
1728
+ if (err < 0 ) {
1729
+ netdev_err (dev -> net , "Error submitting the control"
1730
+ " message: status=%d\n" , err );
1731
+ goto fail_free ;
1732
+ }
1733
+ return 0 ;
1734
+
1735
+ fail_free_buf :
1736
+ kfree (buf );
1737
+ fail_free :
1738
+ kfree (req );
1739
+ usb_free_urb (urb );
1740
+ fail :
1741
+ return err ;
1742
+
1743
+ }
1744
+ EXPORT_SYMBOL_GPL (usbnet_write_cmd_async );
1613
1745
/*-------------------------------------------------------------------------*/
1614
1746
1615
1747
static int __init usbnet_init (void )
0 commit comments