Loading drivers/usb/gadget/android.c +9 −1 Original line number Diff line number Diff line Loading @@ -1057,6 +1057,14 @@ static int ecm_function_init(struct android_usb_function *f, return 0; } static int ecm_qc_function_init(struct android_usb_function *f, struct usb_composite_dev *cdev) { f->config = kzalloc(sizeof(struct ecm_function_config), GFP_KERNEL); if (!f->config) return -ENOMEM; return ecm_qc_init(); } static void ecm_function_cleanup(struct android_usb_function *f) { kfree(f->config); Loading Loading @@ -1154,7 +1162,7 @@ static struct device_attribute *ecm_function_attributes[] = { static struct android_usb_function ecm_qc_function = { .name = "ecm_qc", .init = ecm_function_init, .init = ecm_qc_function_init, .cleanup = ecm_function_cleanup, .bind_config = ecm_qc_function_bind_config, .unbind_config = ecm_qc_function_unbind_config, Loading drivers/usb/gadget/f_mbim.c +13 −7 Original line number Diff line number Diff line Loading @@ -67,6 +67,7 @@ struct mbim_ipa_ep_info { #define NR_MBIM_PORTS 1 #define MBIM_DEFAULT_PORT 0 /* ID for Microsoft OS String */ #define MBIM_OS_STRING_ID 0xEE Loading Loading @@ -780,6 +781,12 @@ static int mbim_bam_connect(struct f_mbim *dev) pr_info("dev:%p portno:%d\n", dev, dev->port_num); ret = bam2bam_data_port_select(MBIM_DEFAULT_PORT); if (ret) { pr_err("mbim port select failed err: %d\n", ret); return ret; } src_connection_idx = usb_bam_get_connection_idx(gadget->name, bam_name, USB_TO_PEER_PERIPHERAL, USB_BAM_DEVICE, dev->port_num); dst_connection_idx = usb_bam_get_connection_idx(gadget->name, bam_name, Loading Loading @@ -1721,7 +1728,6 @@ static void mbim_unbind(struct usb_configuration *c, struct usb_function *f) usb_ep_free_request(mbim->not_port.notify, mbim->not_port.notify_req); mbim_ext_config_desc.function.subCompatibleID[0] = 0; bam_work_destroy(); } /** Loading @@ -1745,12 +1751,6 @@ int mbim_bind_config(struct usb_configuration *c, unsigned portno, return -ENODEV; } status = mbim_bam_setup(nr_mbim_ports); if (status) { pr_err("bam setup failed\n"); return status; } /* maybe allocate device-global string IDs */ if (mbim_string_defs[0].id == 0) { Loading Loading @@ -2148,6 +2148,12 @@ static int mbim_init(int instances) pr_info("Initialized %d ports\n", nr_mbim_ports); ret = mbim_bam_setup(nr_mbim_ports); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return ret; fail_probe: Loading drivers/usb/gadget/f_qc_ecm.c +22 −20 Original line number Diff line number Diff line Loading @@ -117,6 +117,7 @@ static inline unsigned ecm_qc_bitrate(struct usb_gadget *g) /* Currently only one std ecm instance is supported - port index 0. */ #define ECM_QC_NO_PORTS 1 #define ECM_QC_DEFAULT_PORT 0 #define ECM_QC_ACTIVE_PORT 0 /* interface descriptor: */ Loading Loading @@ -441,19 +442,6 @@ static void ecm_qc_notify(struct f_ecm_qc *ecm) ecm_qc_do_notify(ecm); } static int ecm_qc_bam_setup(void) { int ret; ret = bam_data_setup(ECM_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return 0; } static int ecm_qc_bam_connect(struct f_ecm_qc *dev) { int ret; Loading @@ -463,6 +451,12 @@ static int ecm_qc_bam_connect(struct f_ecm_qc *dev) enum peer_bam peer_bam = (dev->xport == USB_GADGET_XPORT_BAM2BAM_IPA) ? IPA_P_BAM : A2_P_BAM; ret = bam2bam_data_port_select(ECM_QC_DEFAULT_PORT); if (ret) { pr_err("ecm_qc port select failed with err:%d\n", ret); return ret; } dev->bam_port.cdev = cdev; dev->bam_port.func = &dev->port.func; dev->bam_port.in = dev->port.in_ep; Loading Loading @@ -1031,7 +1025,6 @@ ecm_qc_unbind(struct usb_configuration *c, struct usb_function *f) ecm_ipa_cleanup(ipa_params.private); kfree(ecm); bam_work_destroy(); } /** Loading @@ -1057,12 +1050,6 @@ ecm_qc_bind_config(struct usb_configuration *c, u8 ethaddr[ETH_ALEN], if (!can_support_ecm(c->cdev->gadget) || !ethaddr) return -EINVAL; status = ecm_qc_bam_setup(); if (status) { pr_err("bam setup failed\n"); return status; } pr_debug("data transport type is %s\n", xport_name); /* maybe allocate device-global string IDs */ Loading Loading @@ -1153,3 +1140,18 @@ ecm_qc_bind_config(struct usb_configuration *c, u8 ethaddr[ETH_ALEN], return status; } static int ecm_qc_init(void) { int ret; pr_debug("initialize ecm qc port instance\n"); ret = bam_data_setup(ECM_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return ret; } drivers/usb/gadget/f_qc_rndis.c +12 −21 Original line number Diff line number Diff line Loading @@ -413,20 +413,6 @@ static inline void rndis_qc_unlock(atomic_t *excl) } /* MSM bam support */ static int rndis_qc_bam_setup(void) { int ret; ret = bam_data_setup(RNDIS_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return 0; } static int rndis_qc_bam_connect(struct f_rndis_qc *dev) { int ret; Loading @@ -441,6 +427,12 @@ static int rndis_qc_bam_connect(struct f_rndis_qc *dev) dev->bam_port.in = dev->port.in_ep; dev->bam_port.out = dev->port.out_ep; ret = bam2bam_data_port_select(RNDIS_QC_ACTIVE_PORT); if (ret) { pr_err("qc rndis bam port setup failed err:%d\n", ret); return ret; } /* currently we use the first connection */ src_connection_idx = usb_bam_get_connection_idx(gadget->name, peer_bam, USB_TO_PEER_PERIPHERAL, USB_BAM_DEVICE, 0); Loading Loading @@ -1044,7 +1036,6 @@ rndis_qc_unbind(struct usb_configuration *c, struct usb_function *f) } kfree(rndis); bam_work_destroy(); } bool is_rndis_ipa_supported(void) Loading Loading @@ -1097,12 +1088,6 @@ rndis_qc_bind_config_vendor(struct usb_configuration *c, u8 ethaddr[ETH_ALEN], if (status < 0) return status; status = rndis_qc_bam_setup(); if (status) { pr_err("%s: bam setup failed\n", __func__); return status; } /* maybe allocate device-global string IDs */ if (rndis_qc_string_defs[0].id == 0) { Loading Loading @@ -1318,6 +1303,12 @@ static int rndis_qc_init(void) if (ret) pr_err("rndis QC driver failed to register\n"); ret = bam_data_setup(RNDIS_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return ret; } Loading drivers/usb/gadget/u_bam_data.c +48 −83 Original line number Diff line number Diff line Loading @@ -114,7 +114,6 @@ struct bam_data_port { bool is_connected; unsigned port_num; spinlock_t port_lock_ul; unsigned int ref_count; struct data_port *port_usb; struct bam_data_ch_info data_ch; Loading @@ -134,7 +133,6 @@ static struct rndis_data_ch_info rndis_data; static void bam2bam_data_suspend_work(struct work_struct *w); static void bam2bam_data_resume_work(struct work_struct *w); static void bam2bam_data_port_free(int portno); /*----- sys2bam towards the IPA (UL workaround) --------------- */ Loading Loading @@ -676,12 +674,8 @@ static void bam2bam_data_disconnect_work(struct work_struct *w) } ret = usb_bam_disconnect_ipa(&d->ipa_params); if (!ret) { pr_debug("%s(): freeing bam2bam_data_port\n", __func__); bam2bam_data_port_free(0); } else { if (ret) pr_err("usb_bam_disconnect_ipa failed: err:%d\n", ret); } if (d->func_type == USB_FUNC_MBIM) teth_bridge_disconnect(d->ipa_params.src_client); Loading Loading @@ -1030,33 +1024,13 @@ static void bam2bam_data_connect_work(struct work_struct *w) pr_debug("Connect workqueue done (port %p)", port); } static void bam2bam_data_port_free(int portno) { struct bam_data_port *port = bam2bam_data_ports[portno]; if (port == NULL) { pr_debug("port %d already free\n", portno); return; } if (--port->ref_count == 0) { kfree(port); bam2bam_data_ports[portno] = NULL; n_bam2bam_data_ports--; pr_debug("freed port %d\n", portno); } } static int bam2bam_data_port_alloc(int portno) { struct bam_data_port *port = NULL; struct bam_data_ch_info *d = NULL; if (bam2bam_data_ports[portno] != NULL) { pr_debug("port %d already allocated. incremeting ref_count\n", portno); bam2bam_data_ports[portno]->ref_count++; goto done; pr_debug("port %d already allocated.\n", portno); return 0; } port = kzalloc(sizeof(struct bam_data_port), GFP_KERNEL); Loading @@ -1065,8 +1039,18 @@ static int bam2bam_data_port_alloc(int portno) return -ENOMEM; } bam2bam_data_ports[portno] = port; return 0; } int bam2bam_data_port_select(int portno) { struct bam_data_port *port = NULL; struct bam_data_ch_info *d = NULL; pr_debug("Inside: portno:%d\n", portno); port = bam2bam_data_ports[portno]; port->port_num = portno; port->ref_count = 1; port->is_connected = false; spin_lock_init(&port->port_lock_ul); Loading @@ -1090,7 +1074,6 @@ static int bam2bam_data_port_alloc(int portno) rndis_disconn_w = &port->disconnect_w; done: pr_debug("port:%p portno:%d\n", port, portno); return 0; Loading Loading @@ -1188,7 +1171,6 @@ int bam_data_connect(struct data_port *gr, u8 port_num, unsigned long flags; pr_debug("dev:%p port#%d\n", gr, port_num); if (port_num >= n_bam2bam_data_ports) { pr_err("invalid portno#%d\n", port_num); return -ENODEV; Loading Loading @@ -1288,30 +1270,6 @@ exit: return ret; } int bam_data_destroy(unsigned int no_bam2bam_port) { struct bam_data_ch_info *d; struct bam_data_port *port; port = bam2bam_data_ports[no_bam2bam_port]; d = &port->data_ch; pr_debug("bam_data_destroy: Freeing ports\n"); bam2bam_data_port_free(no_bam2bam_port); if (bam_data_wq) destroy_workqueue(bam_data_wq); bam_data_wq = NULL; return 0; } void bam_work_destroy(void) { if (bam_data_wq) destroy_workqueue(bam_data_wq); bam_data_wq = NULL; } int bam_data_setup(unsigned int no_bam2bam_port) { int i; Loading @@ -1324,8 +1282,20 @@ int bam_data_setup(unsigned int no_bam2bam_port) return -EINVAL; } for (i = 0; i < no_bam2bam_port; i++) { n_bam2bam_data_ports++; ret = bam2bam_data_port_alloc(i); if (ret) { n_bam2bam_data_ports--; pr_err("Failed to alloc port:%d\n", i); goto free_bam_ports; } } pr_debug("n_bam2bam_data_ports:%d\n", n_bam2bam_data_ports); if (bam_data_wq) { pr_debug("bam_data is already setup"); pr_debug("bam_data is already setup."); return 0; } Loading @@ -1333,25 +1303,21 @@ int bam_data_setup(unsigned int no_bam2bam_port) WQ_UNBOUND | WQ_MEM_RECLAIM, 1); if (!bam_data_wq) { pr_err("Failed to create workqueue\n"); return -ENOMEM; } for (i = 0; i < no_bam2bam_port; i++) { n_bam2bam_data_ports++; ret = bam2bam_data_port_alloc(i); if (ret) { n_bam2bam_data_ports--; pr_err("Failed to alloc port:%d\n", i); ret = -ENOMEM; goto free_bam_ports; } } return 0; free_bam_ports: for (i = 0; i < n_bam2bam_data_ports; i++) bam2bam_data_port_free(i); for (i = 0; i < n_bam2bam_data_ports; i++) { kfree(bam2bam_data_ports[i]); bam2bam_data_ports[i] = NULL; if (bam_data_wq) { destroy_workqueue(bam_data_wq); bam_data_wq = NULL; } } return ret; } Loading Loading @@ -1442,28 +1408,27 @@ static void bam_data_stop(void *param, enum usb_bam_pipe_dir dir) void bam_data_suspend(u8 port_num) { struct bam_data_port *port; struct bam_data_ch_info *d; port = bam2bam_data_ports[port_num]; d = &port->data_ch; pr_debug("%s: suspended port %d\n", __func__, port_num); port = bam2bam_data_ports[port_num]; if (port) queue_work(bam_data_wq, &port->suspend_w); else pr_err("%s(): Port is NULL.\n", __func__); } void bam_data_resume(u8 port_num) { struct bam_data_port *port; struct bam_data_ch_info *d; port = bam2bam_data_ports[port_num]; d = &port->data_ch; pr_debug("%s: resumed port %d\n", __func__, port_num); port = bam2bam_data_ports[port_num]; if (port) queue_work(bam_data_wq, &port->resume_w); else pr_err("%s(): Port is NULL.\n", __func__); } static void bam2bam_data_suspend_work(struct work_struct *w) Loading Loading
drivers/usb/gadget/android.c +9 −1 Original line number Diff line number Diff line Loading @@ -1057,6 +1057,14 @@ static int ecm_function_init(struct android_usb_function *f, return 0; } static int ecm_qc_function_init(struct android_usb_function *f, struct usb_composite_dev *cdev) { f->config = kzalloc(sizeof(struct ecm_function_config), GFP_KERNEL); if (!f->config) return -ENOMEM; return ecm_qc_init(); } static void ecm_function_cleanup(struct android_usb_function *f) { kfree(f->config); Loading Loading @@ -1154,7 +1162,7 @@ static struct device_attribute *ecm_function_attributes[] = { static struct android_usb_function ecm_qc_function = { .name = "ecm_qc", .init = ecm_function_init, .init = ecm_qc_function_init, .cleanup = ecm_function_cleanup, .bind_config = ecm_qc_function_bind_config, .unbind_config = ecm_qc_function_unbind_config, Loading
drivers/usb/gadget/f_mbim.c +13 −7 Original line number Diff line number Diff line Loading @@ -67,6 +67,7 @@ struct mbim_ipa_ep_info { #define NR_MBIM_PORTS 1 #define MBIM_DEFAULT_PORT 0 /* ID for Microsoft OS String */ #define MBIM_OS_STRING_ID 0xEE Loading Loading @@ -780,6 +781,12 @@ static int mbim_bam_connect(struct f_mbim *dev) pr_info("dev:%p portno:%d\n", dev, dev->port_num); ret = bam2bam_data_port_select(MBIM_DEFAULT_PORT); if (ret) { pr_err("mbim port select failed err: %d\n", ret); return ret; } src_connection_idx = usb_bam_get_connection_idx(gadget->name, bam_name, USB_TO_PEER_PERIPHERAL, USB_BAM_DEVICE, dev->port_num); dst_connection_idx = usb_bam_get_connection_idx(gadget->name, bam_name, Loading Loading @@ -1721,7 +1728,6 @@ static void mbim_unbind(struct usb_configuration *c, struct usb_function *f) usb_ep_free_request(mbim->not_port.notify, mbim->not_port.notify_req); mbim_ext_config_desc.function.subCompatibleID[0] = 0; bam_work_destroy(); } /** Loading @@ -1745,12 +1751,6 @@ int mbim_bind_config(struct usb_configuration *c, unsigned portno, return -ENODEV; } status = mbim_bam_setup(nr_mbim_ports); if (status) { pr_err("bam setup failed\n"); return status; } /* maybe allocate device-global string IDs */ if (mbim_string_defs[0].id == 0) { Loading Loading @@ -2148,6 +2148,12 @@ static int mbim_init(int instances) pr_info("Initialized %d ports\n", nr_mbim_ports); ret = mbim_bam_setup(nr_mbim_ports); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return ret; fail_probe: Loading
drivers/usb/gadget/f_qc_ecm.c +22 −20 Original line number Diff line number Diff line Loading @@ -117,6 +117,7 @@ static inline unsigned ecm_qc_bitrate(struct usb_gadget *g) /* Currently only one std ecm instance is supported - port index 0. */ #define ECM_QC_NO_PORTS 1 #define ECM_QC_DEFAULT_PORT 0 #define ECM_QC_ACTIVE_PORT 0 /* interface descriptor: */ Loading Loading @@ -441,19 +442,6 @@ static void ecm_qc_notify(struct f_ecm_qc *ecm) ecm_qc_do_notify(ecm); } static int ecm_qc_bam_setup(void) { int ret; ret = bam_data_setup(ECM_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return 0; } static int ecm_qc_bam_connect(struct f_ecm_qc *dev) { int ret; Loading @@ -463,6 +451,12 @@ static int ecm_qc_bam_connect(struct f_ecm_qc *dev) enum peer_bam peer_bam = (dev->xport == USB_GADGET_XPORT_BAM2BAM_IPA) ? IPA_P_BAM : A2_P_BAM; ret = bam2bam_data_port_select(ECM_QC_DEFAULT_PORT); if (ret) { pr_err("ecm_qc port select failed with err:%d\n", ret); return ret; } dev->bam_port.cdev = cdev; dev->bam_port.func = &dev->port.func; dev->bam_port.in = dev->port.in_ep; Loading Loading @@ -1031,7 +1025,6 @@ ecm_qc_unbind(struct usb_configuration *c, struct usb_function *f) ecm_ipa_cleanup(ipa_params.private); kfree(ecm); bam_work_destroy(); } /** Loading @@ -1057,12 +1050,6 @@ ecm_qc_bind_config(struct usb_configuration *c, u8 ethaddr[ETH_ALEN], if (!can_support_ecm(c->cdev->gadget) || !ethaddr) return -EINVAL; status = ecm_qc_bam_setup(); if (status) { pr_err("bam setup failed\n"); return status; } pr_debug("data transport type is %s\n", xport_name); /* maybe allocate device-global string IDs */ Loading Loading @@ -1153,3 +1140,18 @@ ecm_qc_bind_config(struct usb_configuration *c, u8 ethaddr[ETH_ALEN], return status; } static int ecm_qc_init(void) { int ret; pr_debug("initialize ecm qc port instance\n"); ret = bam_data_setup(ECM_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return ret; }
drivers/usb/gadget/f_qc_rndis.c +12 −21 Original line number Diff line number Diff line Loading @@ -413,20 +413,6 @@ static inline void rndis_qc_unlock(atomic_t *excl) } /* MSM bam support */ static int rndis_qc_bam_setup(void) { int ret; ret = bam_data_setup(RNDIS_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return 0; } static int rndis_qc_bam_connect(struct f_rndis_qc *dev) { int ret; Loading @@ -441,6 +427,12 @@ static int rndis_qc_bam_connect(struct f_rndis_qc *dev) dev->bam_port.in = dev->port.in_ep; dev->bam_port.out = dev->port.out_ep; ret = bam2bam_data_port_select(RNDIS_QC_ACTIVE_PORT); if (ret) { pr_err("qc rndis bam port setup failed err:%d\n", ret); return ret; } /* currently we use the first connection */ src_connection_idx = usb_bam_get_connection_idx(gadget->name, peer_bam, USB_TO_PEER_PERIPHERAL, USB_BAM_DEVICE, 0); Loading Loading @@ -1044,7 +1036,6 @@ rndis_qc_unbind(struct usb_configuration *c, struct usb_function *f) } kfree(rndis); bam_work_destroy(); } bool is_rndis_ipa_supported(void) Loading Loading @@ -1097,12 +1088,6 @@ rndis_qc_bind_config_vendor(struct usb_configuration *c, u8 ethaddr[ETH_ALEN], if (status < 0) return status; status = rndis_qc_bam_setup(); if (status) { pr_err("%s: bam setup failed\n", __func__); return status; } /* maybe allocate device-global string IDs */ if (rndis_qc_string_defs[0].id == 0) { Loading Loading @@ -1318,6 +1303,12 @@ static int rndis_qc_init(void) if (ret) pr_err("rndis QC driver failed to register\n"); ret = bam_data_setup(RNDIS_QC_NO_PORTS); if (ret) { pr_err("bam_data_setup failed err: %d\n", ret); return ret; } return ret; } Loading
drivers/usb/gadget/u_bam_data.c +48 −83 Original line number Diff line number Diff line Loading @@ -114,7 +114,6 @@ struct bam_data_port { bool is_connected; unsigned port_num; spinlock_t port_lock_ul; unsigned int ref_count; struct data_port *port_usb; struct bam_data_ch_info data_ch; Loading @@ -134,7 +133,6 @@ static struct rndis_data_ch_info rndis_data; static void bam2bam_data_suspend_work(struct work_struct *w); static void bam2bam_data_resume_work(struct work_struct *w); static void bam2bam_data_port_free(int portno); /*----- sys2bam towards the IPA (UL workaround) --------------- */ Loading Loading @@ -676,12 +674,8 @@ static void bam2bam_data_disconnect_work(struct work_struct *w) } ret = usb_bam_disconnect_ipa(&d->ipa_params); if (!ret) { pr_debug("%s(): freeing bam2bam_data_port\n", __func__); bam2bam_data_port_free(0); } else { if (ret) pr_err("usb_bam_disconnect_ipa failed: err:%d\n", ret); } if (d->func_type == USB_FUNC_MBIM) teth_bridge_disconnect(d->ipa_params.src_client); Loading Loading @@ -1030,33 +1024,13 @@ static void bam2bam_data_connect_work(struct work_struct *w) pr_debug("Connect workqueue done (port %p)", port); } static void bam2bam_data_port_free(int portno) { struct bam_data_port *port = bam2bam_data_ports[portno]; if (port == NULL) { pr_debug("port %d already free\n", portno); return; } if (--port->ref_count == 0) { kfree(port); bam2bam_data_ports[portno] = NULL; n_bam2bam_data_ports--; pr_debug("freed port %d\n", portno); } } static int bam2bam_data_port_alloc(int portno) { struct bam_data_port *port = NULL; struct bam_data_ch_info *d = NULL; if (bam2bam_data_ports[portno] != NULL) { pr_debug("port %d already allocated. incremeting ref_count\n", portno); bam2bam_data_ports[portno]->ref_count++; goto done; pr_debug("port %d already allocated.\n", portno); return 0; } port = kzalloc(sizeof(struct bam_data_port), GFP_KERNEL); Loading @@ -1065,8 +1039,18 @@ static int bam2bam_data_port_alloc(int portno) return -ENOMEM; } bam2bam_data_ports[portno] = port; return 0; } int bam2bam_data_port_select(int portno) { struct bam_data_port *port = NULL; struct bam_data_ch_info *d = NULL; pr_debug("Inside: portno:%d\n", portno); port = bam2bam_data_ports[portno]; port->port_num = portno; port->ref_count = 1; port->is_connected = false; spin_lock_init(&port->port_lock_ul); Loading @@ -1090,7 +1074,6 @@ static int bam2bam_data_port_alloc(int portno) rndis_disconn_w = &port->disconnect_w; done: pr_debug("port:%p portno:%d\n", port, portno); return 0; Loading Loading @@ -1188,7 +1171,6 @@ int bam_data_connect(struct data_port *gr, u8 port_num, unsigned long flags; pr_debug("dev:%p port#%d\n", gr, port_num); if (port_num >= n_bam2bam_data_ports) { pr_err("invalid portno#%d\n", port_num); return -ENODEV; Loading Loading @@ -1288,30 +1270,6 @@ exit: return ret; } int bam_data_destroy(unsigned int no_bam2bam_port) { struct bam_data_ch_info *d; struct bam_data_port *port; port = bam2bam_data_ports[no_bam2bam_port]; d = &port->data_ch; pr_debug("bam_data_destroy: Freeing ports\n"); bam2bam_data_port_free(no_bam2bam_port); if (bam_data_wq) destroy_workqueue(bam_data_wq); bam_data_wq = NULL; return 0; } void bam_work_destroy(void) { if (bam_data_wq) destroy_workqueue(bam_data_wq); bam_data_wq = NULL; } int bam_data_setup(unsigned int no_bam2bam_port) { int i; Loading @@ -1324,8 +1282,20 @@ int bam_data_setup(unsigned int no_bam2bam_port) return -EINVAL; } for (i = 0; i < no_bam2bam_port; i++) { n_bam2bam_data_ports++; ret = bam2bam_data_port_alloc(i); if (ret) { n_bam2bam_data_ports--; pr_err("Failed to alloc port:%d\n", i); goto free_bam_ports; } } pr_debug("n_bam2bam_data_ports:%d\n", n_bam2bam_data_ports); if (bam_data_wq) { pr_debug("bam_data is already setup"); pr_debug("bam_data is already setup."); return 0; } Loading @@ -1333,25 +1303,21 @@ int bam_data_setup(unsigned int no_bam2bam_port) WQ_UNBOUND | WQ_MEM_RECLAIM, 1); if (!bam_data_wq) { pr_err("Failed to create workqueue\n"); return -ENOMEM; } for (i = 0; i < no_bam2bam_port; i++) { n_bam2bam_data_ports++; ret = bam2bam_data_port_alloc(i); if (ret) { n_bam2bam_data_ports--; pr_err("Failed to alloc port:%d\n", i); ret = -ENOMEM; goto free_bam_ports; } } return 0; free_bam_ports: for (i = 0; i < n_bam2bam_data_ports; i++) bam2bam_data_port_free(i); for (i = 0; i < n_bam2bam_data_ports; i++) { kfree(bam2bam_data_ports[i]); bam2bam_data_ports[i] = NULL; if (bam_data_wq) { destroy_workqueue(bam_data_wq); bam_data_wq = NULL; } } return ret; } Loading Loading @@ -1442,28 +1408,27 @@ static void bam_data_stop(void *param, enum usb_bam_pipe_dir dir) void bam_data_suspend(u8 port_num) { struct bam_data_port *port; struct bam_data_ch_info *d; port = bam2bam_data_ports[port_num]; d = &port->data_ch; pr_debug("%s: suspended port %d\n", __func__, port_num); port = bam2bam_data_ports[port_num]; if (port) queue_work(bam_data_wq, &port->suspend_w); else pr_err("%s(): Port is NULL.\n", __func__); } void bam_data_resume(u8 port_num) { struct bam_data_port *port; struct bam_data_ch_info *d; port = bam2bam_data_ports[port_num]; d = &port->data_ch; pr_debug("%s: resumed port %d\n", __func__, port_num); port = bam2bam_data_ports[port_num]; if (port) queue_work(bam_data_wq, &port->resume_w); else pr_err("%s(): Port is NULL.\n", __func__); } static void bam2bam_data_suspend_work(struct work_struct *w) Loading