Loading drivers/usb/gadget/f_qc_rndis.c +16 −0 Original line number Diff line number Diff line Loading @@ -827,6 +827,14 @@ static void rndis_qc_suspend(struct usb_function *f) if (remote_wakeup_allowed) { bam_data_suspend(RNDIS_QC_ACTIVE_PORT); } else { /* This is required as Linux host side RNDIS driver doesn't * send RNDIS_MESSAGE_PACKET_FILTER before suspending USB bus. * Hence we perform same operations explicitly here for Linux * host case. In case of windows, this RNDIS state machine is * already updated due to receiving of PACKET_FILTER. */ rndis_flow_control(rndis->config, true); /* * When remote wakeup is disabled, IPA BAM is disconnected * because it cannot send new data until the USB bus is resumed. Loading Loading @@ -874,6 +882,14 @@ static void rndis_qc_resume(struct usb_function *f) rndis->bam_port.in->desc = rndis->in_ep_desc_backup; rndis->bam_port.out->desc = rndis->out_ep_desc_backup; rndis_qc_bam_connect(rndis); /* * Linux Host doesn't sends RNDIS_MSG_INIT or non-zero value * set with RNDIS_MESSAGE_PACKET_FILTER after performing bus * resume. Hence trigger USB IPA transfer functionality * explicitly here. For Windows host case is also being * handle with RNDIS state machine. */ rndis_flow_control(rndis->config, false); } pr_debug("%s: RNDIS resume completed\n", __func__); Loading drivers/usb/gadget/rndis.c +39 −17 Original line number Diff line number Diff line Loading @@ -544,24 +544,11 @@ static int gen_ndis_set_resp(u8 configNr, u32 OID, u8 *buf, u32 buf_len, */ retval = 0; if (*params->filter) { if (!is_rndis_ipa_supported()) { netif_carrier_on(params->dev); if (netif_running(params->dev)) netif_wake_queue(params->dev); pr_debug("%s(): disable flow control\n", __func__); rndis_flow_control(configNr, false); } else { if (params->state != RNDIS_DATA_INITIALIZED) u_bam_data_start_rndis_ipa(); } params->state = RNDIS_DATA_INITIALIZED; } else { if (!is_rndis_ipa_supported()) { netif_carrier_off(params->dev); netif_stop_queue(params->dev); } else { if (params->state == RNDIS_DATA_INITIALIZED) u_bam_data_stop_rndis_ipa(); } params->state = RNDIS_INITIALIZED; pr_debug("%s(): enable flow control\n", __func__); rndis_flow_control(configNr, true); } break; Loading Loading @@ -1013,6 +1000,41 @@ void rndis_set_pkt_alignment_factor(u8 configNr, u8 pkt_alignment_factor) rndis_per_dev_params[configNr].pkt_alignment_factor = pkt_alignment_factor; } /** * rndis_flow_control: enable/disable flow control with USB RNDIS interface * confignr - RNDIS network interface number * enable_flow_control - true: perform flow control, false: disable flow control * * In BAM2BAM IPA mode, this function triggers functionality to start/stop * endless transfers, otherwise it enables/disables RNDIS network interface. */ void rndis_flow_control(u8 confignr, bool enable_flow_control) { struct rndis_params *params; params = &rndis_per_dev_params[confignr]; pr_debug("%s(): params->state:%x\n", __func__, params->state); if (enable_flow_control) { if (is_rndis_ipa_supported() && params->state == RNDIS_DATA_INITIALIZED) { u_bam_data_stop_rndis_ipa(); } else { netif_carrier_off(params->dev); netif_stop_queue(params->dev); } params->state = RNDIS_INITIALIZED; } else { if (is_rndis_ipa_supported() && params->state != RNDIS_DATA_INITIALIZED) { u_bam_data_start_rndis_ipa(); } else { netif_carrier_on(params->dev); if (netif_running(params->dev)) netif_wake_queue(params->dev); } params->state = RNDIS_DATA_INITIALIZED; } } void rndis_add_hdr(struct sk_buff *skb) { Loading drivers/usb/gadget/rndis.h +1 −1 Original line number Diff line number Diff line Loading @@ -228,5 +228,5 @@ extern void rndis_set_host_mac (int configNr, const u8 *addr); extern bool is_rndis_ipa_supported(void); int rndis_init(void); void rndis_exit (void); void rndis_flow_control(u8 confignr, bool enable_flow_control); #endif /* _LINUX_RNDIS_H */ Loading
drivers/usb/gadget/f_qc_rndis.c +16 −0 Original line number Diff line number Diff line Loading @@ -827,6 +827,14 @@ static void rndis_qc_suspend(struct usb_function *f) if (remote_wakeup_allowed) { bam_data_suspend(RNDIS_QC_ACTIVE_PORT); } else { /* This is required as Linux host side RNDIS driver doesn't * send RNDIS_MESSAGE_PACKET_FILTER before suspending USB bus. * Hence we perform same operations explicitly here for Linux * host case. In case of windows, this RNDIS state machine is * already updated due to receiving of PACKET_FILTER. */ rndis_flow_control(rndis->config, true); /* * When remote wakeup is disabled, IPA BAM is disconnected * because it cannot send new data until the USB bus is resumed. Loading Loading @@ -874,6 +882,14 @@ static void rndis_qc_resume(struct usb_function *f) rndis->bam_port.in->desc = rndis->in_ep_desc_backup; rndis->bam_port.out->desc = rndis->out_ep_desc_backup; rndis_qc_bam_connect(rndis); /* * Linux Host doesn't sends RNDIS_MSG_INIT or non-zero value * set with RNDIS_MESSAGE_PACKET_FILTER after performing bus * resume. Hence trigger USB IPA transfer functionality * explicitly here. For Windows host case is also being * handle with RNDIS state machine. */ rndis_flow_control(rndis->config, false); } pr_debug("%s: RNDIS resume completed\n", __func__); Loading
drivers/usb/gadget/rndis.c +39 −17 Original line number Diff line number Diff line Loading @@ -544,24 +544,11 @@ static int gen_ndis_set_resp(u8 configNr, u32 OID, u8 *buf, u32 buf_len, */ retval = 0; if (*params->filter) { if (!is_rndis_ipa_supported()) { netif_carrier_on(params->dev); if (netif_running(params->dev)) netif_wake_queue(params->dev); pr_debug("%s(): disable flow control\n", __func__); rndis_flow_control(configNr, false); } else { if (params->state != RNDIS_DATA_INITIALIZED) u_bam_data_start_rndis_ipa(); } params->state = RNDIS_DATA_INITIALIZED; } else { if (!is_rndis_ipa_supported()) { netif_carrier_off(params->dev); netif_stop_queue(params->dev); } else { if (params->state == RNDIS_DATA_INITIALIZED) u_bam_data_stop_rndis_ipa(); } params->state = RNDIS_INITIALIZED; pr_debug("%s(): enable flow control\n", __func__); rndis_flow_control(configNr, true); } break; Loading Loading @@ -1013,6 +1000,41 @@ void rndis_set_pkt_alignment_factor(u8 configNr, u8 pkt_alignment_factor) rndis_per_dev_params[configNr].pkt_alignment_factor = pkt_alignment_factor; } /** * rndis_flow_control: enable/disable flow control with USB RNDIS interface * confignr - RNDIS network interface number * enable_flow_control - true: perform flow control, false: disable flow control * * In BAM2BAM IPA mode, this function triggers functionality to start/stop * endless transfers, otherwise it enables/disables RNDIS network interface. */ void rndis_flow_control(u8 confignr, bool enable_flow_control) { struct rndis_params *params; params = &rndis_per_dev_params[confignr]; pr_debug("%s(): params->state:%x\n", __func__, params->state); if (enable_flow_control) { if (is_rndis_ipa_supported() && params->state == RNDIS_DATA_INITIALIZED) { u_bam_data_stop_rndis_ipa(); } else { netif_carrier_off(params->dev); netif_stop_queue(params->dev); } params->state = RNDIS_INITIALIZED; } else { if (is_rndis_ipa_supported() && params->state != RNDIS_DATA_INITIALIZED) { u_bam_data_start_rndis_ipa(); } else { netif_carrier_on(params->dev); if (netif_running(params->dev)) netif_wake_queue(params->dev); } params->state = RNDIS_DATA_INITIALIZED; } } void rndis_add_hdr(struct sk_buff *skb) { Loading
drivers/usb/gadget/rndis.h +1 −1 Original line number Diff line number Diff line Loading @@ -228,5 +228,5 @@ extern void rndis_set_host_mac (int configNr, const u8 *addr); extern bool is_rndis_ipa_supported(void); int rndis_init(void); void rndis_exit (void); void rndis_flow_control(u8 confignr, bool enable_flow_control); #endif /* _LINUX_RNDIS_H */