Merge git://git.kernel.org/pub/scm/linux/kernel/git/steve/gfs2-3.0-nmw
[GitHub/mt8127/android_kernel_alcatel_ttab.git] / drivers / staging / bcm / InterfaceTx.c
CommitLineData
f8942e07
SH
1#include "headers.h"
2
f8942e07
SH
3/*this is transmit call-back(BULK OUT)*/
4static void write_bulk_callback(struct urb *urb/*, struct pt_regs *regs*/)
5{
6 PUSB_TCB pTcb= (PUSB_TCB)urb->context;
7 PS_INTERFACE_ADAPTER psIntfAdapter = pTcb->psIntfAdapter;
8 CONTROL_MESSAGE *pControlMsg = (CONTROL_MESSAGE *)urb->transfer_buffer;
9 PMINI_ADAPTER psAdapter = psIntfAdapter->psAdapter ;
10 BOOLEAN bpowerDownMsg = FALSE ;
11 PMINI_ADAPTER Adapter = GET_BCM_ADAPTER(gblpnetdev);
9ec4475b
SH
12
13 if (unlikely(netif_msg_tx_done(Adapter)))
14 pr_info(PFX "%s: transmit status %d\n", Adapter->dev->name, urb->status);
15
f8942e07
SH
16 if(urb->status != STATUS_SUCCESS)
17 {
18 if(urb->status == -EPIPE)
19 {
20 psIntfAdapter->psAdapter->bEndPointHalted = TRUE ;
21 wake_up(&psIntfAdapter->psAdapter->tx_packet_wait_queue);
22 }
23 else
24 {
25 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL,"Tx URB has got cancelled. status :%d", urb->status);
26 }
27 }
28
29 pTcb->bUsed = FALSE;
30 atomic_dec(&psIntfAdapter->uNumTcbUsed);
31
32
33
34 if(TRUE == psAdapter->bPreparingForLowPowerMode)
35 {
f8942e07
SH
36
37 if(((pControlMsg->szData[0] == GO_TO_IDLE_MODE_PAYLOAD) &&
38 (pControlMsg->szData[1] == TARGET_CAN_GO_TO_IDLE_MODE)))
39
40 {
41 bpowerDownMsg = TRUE ;
42 //This covers the bus err while Idle Request msg sent down.
43 if(urb->status != STATUS_SUCCESS)
44 {
45 psAdapter->bPreparingForLowPowerMode = FALSE ;
46 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL,"Idle Mode Request msg failed to reach to Modem");
47 //Signalling the cntrl pkt path in Ioctl
48 wake_up(&psAdapter->lowpower_mode_wait_queue);
49 StartInterruptUrb(psIntfAdapter);
50 goto err_exit;
51 }
52
53 if(psAdapter->bDoSuspend == FALSE)
54 {
55 psAdapter->IdleMode = TRUE;
56 //since going in Idle mode completed hence making this var false;
57 psAdapter->bPreparingForLowPowerMode = FALSE ;
58
59 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL, "Host Entered in Idle Mode State...");
60 //Signalling the cntrl pkt path in Ioctl
61 wake_up(&psAdapter->lowpower_mode_wait_queue);
62 }
63
64 }
65 else if((pControlMsg->Leader.Status == LINK_UP_CONTROL_REQ) &&
66 (pControlMsg->szData[0] == LINK_UP_ACK) &&
67 (pControlMsg->szData[1] == LINK_SHUTDOWN_REQ_FROM_FIRMWARE) &&
68 (pControlMsg->szData[2] == SHUTDOWN_ACK_FROM_DRIVER))
69 {
70 //This covers the bus err while shutdown Request msg sent down.
71 if(urb->status != STATUS_SUCCESS)
72 {
73 psAdapter->bPreparingForLowPowerMode = FALSE ;
74 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL,"Shutdown Request Msg failed to reach to Modem");
75 //Signalling the cntrl pkt path in Ioctl
76 wake_up(&psAdapter->lowpower_mode_wait_queue);
77 StartInterruptUrb(psIntfAdapter);
78 goto err_exit;
79 }
80
81 bpowerDownMsg = TRUE ;
82 if(psAdapter->bDoSuspend == FALSE)
83 {
84 psAdapter->bShutStatus = TRUE;
85 //since going in shutdown mode completed hence making this var false;
86 psAdapter->bPreparingForLowPowerMode = FALSE ;
87 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL,"Host Entered in shutdown Mode State...");
88 //Signalling the cntrl pkt path in Ioctl
89 wake_up(&psAdapter->lowpower_mode_wait_queue);
90 }
91 }
92
93 if(psAdapter->bDoSuspend && bpowerDownMsg)
94 {
95 //issuing bus suspend request
96 BCM_DEBUG_PRINT(Adapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL,"Issuing the Bus suspend request to USB stack");
97 psIntfAdapter->bPreparingForBusSuspend = TRUE;
98 schedule_work(&psIntfAdapter->usbSuspendWork);
99
100 }
101
102 }
103
104err_exit :
f8942e07
SH
105 usb_free_coherent(urb->dev, urb->transfer_buffer_length,
106 urb->transfer_buffer, urb->transfer_dma);
f8942e07
SH
107}
108
109
20f48653 110static PUSB_TCB GetBulkOutTcb(PS_INTERFACE_ADAPTER psIntfAdapter)
f8942e07
SH
111{
112 PUSB_TCB pTcb = NULL;
113 UINT index = 0;
114
115 if((atomic_read(&psIntfAdapter->uNumTcbUsed) < MAXIMUM_USB_TCB) &&
116 (psIntfAdapter->psAdapter->StopAllXaction ==FALSE))
117 {
118 index = atomic_read(&psIntfAdapter->uCurrTcb);
119 pTcb = &psIntfAdapter->asUsbTcb[index];
120 pTcb->bUsed = TRUE;
121 pTcb->psIntfAdapter= psIntfAdapter;
122 BCM_DEBUG_PRINT(psIntfAdapter->psAdapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL, "Got Tx desc %d used %d",
123 index, atomic_read(&psIntfAdapter->uNumTcbUsed));
124 index = (index + 1) % MAXIMUM_USB_TCB;
125 atomic_set(&psIntfAdapter->uCurrTcb, index);
126 atomic_inc(&psIntfAdapter->uNumTcbUsed);
127 }
128 return pTcb;
129}
130
20f48653 131static int TransmitTcb(PS_INTERFACE_ADAPTER psIntfAdapter, PUSB_TCB pTcb, PVOID data, int len)
f8942e07
SH
132{
133
134 struct urb *urb = pTcb->urb;
135 int retval = 0;
136
f8942e07
SH
137 urb->transfer_buffer = usb_alloc_coherent(psIntfAdapter->udev, len,
138 GFP_ATOMIC, &urb->transfer_dma);
f8942e07
SH
139 if (!urb->transfer_buffer)
140 {
141 BCM_DEBUG_PRINT(psIntfAdapter->psAdapter,DBG_TYPE_PRINTK, 0, 0, "Error allocating memory\n");
142 return -ENOMEM;
143 }
144 memcpy(urb->transfer_buffer, data, len);
145 urb->transfer_buffer_length = len;
146
147 BCM_DEBUG_PRINT(psIntfAdapter->psAdapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL, "Sending Bulk out packet\n");
148 //For T3B,INT OUT end point will be used as bulk out end point
149 if((psIntfAdapter->psAdapter->chip_id == T3B) && (psIntfAdapter->bHighSpeedDevice == TRUE))
150 {
151 usb_fill_int_urb(urb, psIntfAdapter->udev,
152 psIntfAdapter->sBulkOut.bulk_out_pipe,
153 urb->transfer_buffer, len, write_bulk_callback, pTcb,
154 psIntfAdapter->sBulkOut.int_out_interval);
155 }
156 else
157 {
158 usb_fill_bulk_urb(urb, psIntfAdapter->udev,
159 psIntfAdapter->sBulkOut.bulk_out_pipe,
160 urb->transfer_buffer, len, write_bulk_callback, pTcb);
161 }
162 urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; /* For DMA transfer */
163
164 if(FALSE == psIntfAdapter->psAdapter->device_removed &&
165 FALSE == psIntfAdapter->psAdapter->bEndPointHalted &&
166 FALSE == psIntfAdapter->bSuspended &&
167 FALSE == psIntfAdapter->bPreparingForBusSuspend)
168 {
169 retval = usb_submit_urb(urb, GFP_ATOMIC);
170 if (retval)
171 {
172 BCM_DEBUG_PRINT(psIntfAdapter->psAdapter,DBG_TYPE_TX, NEXT_SEND, DBG_LVL_ALL, "failed submitting write urb, error %d", retval);
173 if(retval == -EPIPE)
174 {
175 psIntfAdapter->psAdapter->bEndPointHalted = TRUE ;
176 wake_up(&psIntfAdapter->psAdapter->tx_packet_wait_queue);
177 }
178 }
179 }
180 return retval;
181}
182
183int InterfaceTransmitPacket(PVOID arg, PVOID data, UINT len)
184{
185 PUSB_TCB pTcb= NULL;
186
187 PS_INTERFACE_ADAPTER psIntfAdapter = (PS_INTERFACE_ADAPTER)arg;
188 pTcb= GetBulkOutTcb(psIntfAdapter);
189 if(pTcb == NULL)
190 {
191 BCM_DEBUG_PRINT(psIntfAdapter->psAdapter,DBG_TYPE_PRINTK, 0, 0, "No URB to transmit packet, dropping packet");
192 return -EFAULT;
193 }
194 return TransmitTcb(psIntfAdapter, pTcb, data, len);
195}
196
f8942e07 197