usb: gadget: Add network gadget driver for dun and rmnet

This gadget driver works as independent data and control pass
through between modem device connected over USB or HSIC
and host/laptop.This driver communicates with modem device
using network bridge host driver.

Change-Id: Iaffdeaa6b5dbd601b73cba721a8f062d69912908
Signed-off-by: Hemant Kumar <hemantk@codeaurora.org>
Signed-off-by: Jack Pham <jackp@codeaurora.org>
diff --git a/drivers/usb/gadget/f_rmnet.c b/drivers/usb/gadget/f_rmnet.c
index 2c6a31c..32791d9 100644
--- a/drivers/usb/gadget/f_rmnet.c
+++ b/drivers/usb/gadget/f_rmnet.c
@@ -64,7 +64,9 @@
 #define NR_RMNET_PORTS	1
 static unsigned int nr_rmnet_ports;
 static unsigned int no_ctrl_smd_ports;
+static unsigned int no_ctrl_hsic_ports;
 static unsigned int no_data_bam_ports;
+static unsigned int no_data_hsic_ports;
 static struct rmnet_ports {
 	enum transport_type		data_xport;
 	enum transport_type		ctrl_xport;
@@ -235,11 +237,14 @@
 
 static int rmnet_gport_setup(void)
 {
-	int ret;
+	int	ret;
+	int	port_idx;
+	int	i;
 
-	pr_debug("%s: bam ports: %u smd ports: %u nr_rmnet_ports: %u\n",
-			__func__, no_data_bam_ports, no_ctrl_smd_ports,
-			nr_rmnet_ports);
+	pr_debug("%s: bam ports: %u data hsic ports: %u smd ports: %u"
+			" ctrl hsic ports: %u nr_rmnet_ports: %u\n",
+			__func__, no_data_bam_ports, no_data_hsic_ports,
+			no_ctrl_smd_ports, no_ctrl_hsic_ports, nr_rmnet_ports);
 
 	if (no_data_bam_ports) {
 		ret = gbam_setup(no_data_bam_ports);
@@ -253,6 +258,34 @@
 			return ret;
 	}
 
+	if (no_data_hsic_ports) {
+		port_idx = ghsic_data_setup(no_data_hsic_ports,
+				USB_GADGET_RMNET);
+		if (port_idx < 0)
+			return port_idx;
+		for (i = 0; i < nr_rmnet_ports; i++) {
+			if (rmnet_ports[i].data_xport ==
+					USB_GADGET_XPORT_HSIC) {
+				rmnet_ports[i].data_xport_num = port_idx;
+				port_idx++;
+			}
+		}
+	}
+
+	if (no_ctrl_hsic_ports) {
+		port_idx = ghsic_ctrl_setup(no_ctrl_hsic_ports,
+				USB_GADGET_RMNET);
+		if (port_idx < 0)
+			return port_idx;
+		for (i = 0; i < nr_rmnet_ports; i++) {
+			if (rmnet_ports[i].ctrl_xport ==
+					USB_GADGET_XPORT_HSIC) {
+				rmnet_ports[i].ctrl_xport_num = port_idx;
+				port_idx++;
+			}
+		}
+	}
+
 	return 0;
 }
 
@@ -277,6 +310,14 @@
 			return ret;
 		}
 		break;
+	case USB_GADGET_XPORT_HSIC:
+		ret = ghsic_ctrl_connect(&dev->port, port_num);
+		if (ret) {
+			pr_err("%s: ghsic_ctrl_connect failed: err:%d\n",
+					__func__, ret);
+			return ret;
+		}
+		break;
 	case USB_GADGET_XPORT_NONE:
 		break;
 	default:
@@ -296,6 +337,15 @@
 			return ret;
 		}
 		break;
+	case USB_GADGET_XPORT_HSIC:
+		ret = ghsic_data_connect(&dev->port, port_num);
+		if (ret) {
+			pr_err("%s: ghsic_data_connect failed: err:%d\n",
+					__func__, ret);
+			ghsic_ctrl_disconnect(&dev->port, port_num);
+			return ret;
+		}
+		break;
 	case USB_GADGET_XPORT_NONE:
 		 break;
 	default:
@@ -322,6 +372,9 @@
 	case USB_GADGET_XPORT_SMD:
 		gsmd_ctrl_disconnect(&dev->port, port_num);
 		break;
+	case USB_GADGET_XPORT_HSIC:
+		ghsic_ctrl_disconnect(&dev->port, port_num);
+		break;
 	case USB_GADGET_XPORT_NONE:
 		break;
 	default:
@@ -335,6 +388,9 @@
 	case USB_GADGET_XPORT_BAM:
 		gbam_disconnect(&dev->port, port_num);
 		break;
+	case USB_GADGET_XPORT_HSIC:
+		ghsic_data_disconnect(&dev->port, port_num);
+		break;
 	case USB_GADGET_XPORT_NONE:
 		break;
 	default:
@@ -898,6 +954,8 @@
 	nr_rmnet_ports = 0;
 	no_ctrl_smd_ports = 0;
 	no_data_bam_ports = 0;
+	no_ctrl_hsic_ports = 0;
+	no_data_hsic_ports = 0;
 }
 
 static int frmnet_init_port(const char *ctrl_name, const char *data_name)
@@ -937,6 +995,10 @@
 		rmnet_port->ctrl_xport_num = no_ctrl_smd_ports;
 		no_ctrl_smd_ports++;
 		break;
+	case USB_GADGET_XPORT_HSIC:
+		rmnet_port->ctrl_xport_num = no_ctrl_hsic_ports;
+		no_ctrl_hsic_ports++;
+		break;
 	case USB_GADGET_XPORT_NONE:
 		break;
 	default:
@@ -951,6 +1013,10 @@
 		rmnet_port->data_xport_num = no_data_bam_ports;
 		no_data_bam_ports++;
 		break;
+	case USB_GADGET_XPORT_HSIC:
+		rmnet_port->data_xport_num = no_data_hsic_ports;
+		no_data_hsic_ports++;
+		break;
 	case USB_GADGET_XPORT_NONE:
 		break;
 	default:
@@ -970,6 +1036,8 @@
 	nr_rmnet_ports = 0;
 	no_ctrl_smd_ports = 0;
 	no_data_bam_ports = 0;
+	no_ctrl_hsic_ports = 0;
+	no_data_hsic_ports = 0;
 
 	return ret;
 }