4 Function: InterfaceIdleModeWakeup
6 Description: This is the hardware specific Function for waking up HW device from Idle mode.
7 A software abort pattern is written to the device to wake it and necessary power state
8 transitions from host are performed here.
10 Input parameters: IN PMINI_ADAPTER Adapter - Miniport Adapter Context
13 Return: BCM_STATUS_SUCCESS - If Wakeup of the HW Interface was successful.
14 Other - If an error occurred.
19 Function: InterfaceIdleModeRespond
21 Description: This is the hardware specific Function for responding to Idle mode request from target.
22 Necessary power state transitions from host for idle mode or other device specific
23 initializations are performed here.
25 Input parameters: IN PMINI_ADAPTER Adapter - Miniport Adapter Context
28 Return: BCM_STATUS_SUCCESS - If Idle mode response related HW configuration was successful.
29 Other - If an error occurred.
33 "dmem bfc02f00 100" tells how many time device went in Idle mode.
34 this value will be at address bfc02fa4.just before value d0ea1dle.
36 Set time value by writing at bfc02f98 7d0
38 checking the Ack timer expire on kannon by running command
39 d qcslog .. if it shows e means host has not send response to f/w with in 200 ms. Response should be
40 send to f/w with in 200 ms after the Idle/Shutdown req issued
45 int InterfaceIdleModeRespond(PMINI_ADAPTER Adapter
, unsigned int* puiBuffer
)
47 int status
= STATUS_SUCCESS
;
48 unsigned int uiRegRead
= 0;
50 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"SubType of Message :0x%X", ntohl(*puiBuffer
));
52 if(ntohl(*puiBuffer
) == GO_TO_IDLE_MODE_PAYLOAD
)
54 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
," Got GO_TO_IDLE_MODE_PAYLOAD(210) Msg Subtype");
55 if(ntohl(*(puiBuffer
+1)) == 0 )
57 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"Got IDLE MODE WAKE UP Response From F/W");
59 status
= wrmalt (Adapter
,SW_ABORT_IDLEMODE_LOC
, &uiRegRead
, sizeof(uiRegRead
));
62 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0, "wrm failed while clearing Idle Mode Reg");
66 if(Adapter
->ulPowerSaveMode
== DEVICE_POWERSAVE_MODE_AS_MANUAL_CLOCK_GATING
)
68 uiRegRead
= 0x00000000 ;
69 status
= wrmalt (Adapter
,DEBUG_INTERRUPT_GENERATOR_REGISTOR
, &uiRegRead
, sizeof(uiRegRead
));
72 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0, "wrm failed while clearing Idle Mode Reg");
76 //Below Register should not br read in case of Manual and Protocol Idle mode.
77 else if(Adapter
->ulPowerSaveMode
!= DEVICE_POWERSAVE_MODE_AS_PROTOCOL_IDLE_MODE
)
79 //clear on read Register
80 status
= rdmalt(Adapter
, DEVICE_INT_OUT_EP_REG0
, &uiRegRead
, sizeof(uiRegRead
));
83 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0, "rdm failed while clearing H/W Abort Reg0");
86 //clear on read Register
87 status
= rdmalt (Adapter
, DEVICE_INT_OUT_EP_REG1
, &uiRegRead
, sizeof(uiRegRead
));
90 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0, "rdm failed while clearing H/W Abort Reg1");
94 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "Device Up from Idle Mode");
96 // Set Idle Mode Flag to False and Clear IdleMode reg.
97 Adapter
->IdleMode
= FALSE
;
98 Adapter
->bTriedToWakeUpFromlowPowerMode
= FALSE
;
100 wake_up(&Adapter
->lowpower_mode_wait_queue
);
105 if(TRUE
== Adapter
->IdleMode
)
107 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"Device is already in Idle mode....");
112 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "Got Req from F/W to go in IDLE mode \n");
114 if (Adapter
->chip_id
== BCS220_2
||
115 Adapter
->chip_id
== BCS220_2BC
||
116 Adapter
->chip_id
== BCS250_BC
||
117 Adapter
->chip_id
== BCS220_3
)
120 status
= rdmalt(Adapter
, HPM_CONFIG_MSW
, &uiRegRead
, sizeof(uiRegRead
));
123 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "rdm failed while Reading HPM_CONFIG_LDO145 Reg 0\n");
128 uiRegRead
|= (1<<17);
130 status
= wrmalt (Adapter
,HPM_CONFIG_MSW
, &uiRegRead
, sizeof(uiRegRead
));
133 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0, "wrm failed while clearing Idle Mode Reg\n");
138 SendIdleModeResponse(Adapter
);
141 else if(ntohl(*puiBuffer
) == IDLE_MODE_SF_UPDATE_MSG
)
143 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "OverRiding Service Flow Params");
144 OverrideServiceFlowParams(Adapter
,puiBuffer
);
149 static int InterfaceAbortIdlemode(PMINI_ADAPTER Adapter
, unsigned int Pattern
)
151 int status
= STATUS_SUCCESS
;
153 unsigned int chip_id
;
154 unsigned long timeout
= 0 ,itr
= 0;
157 unsigned char aucAbortPattern
[8]={0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF,0xFF};
158 PS_INTERFACE_ADAPTER psInterfaceAdapter
= Adapter
->pvInterfaceAdapter
;
160 //Abort Bus suspend if its already suspended
161 if((TRUE
== psInterfaceAdapter
->bSuspended
) && (TRUE
== Adapter
->bDoSuspend
))
163 status
= usb_autopm_get_interface(psInterfaceAdapter
->interface
);
164 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"Bus got wakeup..Aborting Idle mode... status:%d \n",status
);
168 if((Adapter
->ulPowerSaveMode
== DEVICE_POWERSAVE_MODE_AS_MANUAL_CLOCK_GATING
)
170 (Adapter
->ulPowerSaveMode
== DEVICE_POWERSAVE_MODE_AS_PROTOCOL_IDLE_MODE
))
172 //write the SW abort pattern.
173 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "Writing pattern<%d> to SW_ABORT_IDLEMODE_LOC\n", Pattern
);
174 status
= wrmalt(Adapter
,SW_ABORT_IDLEMODE_LOC
, &Pattern
, sizeof(Pattern
));
177 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"WRM to Register SW_ABORT_IDLEMODE_LOC failed..");
182 if(Adapter
->ulPowerSaveMode
== DEVICE_POWERSAVE_MODE_AS_MANUAL_CLOCK_GATING
)
185 status
= wrmalt(Adapter
,DEBUG_INTERRUPT_GENERATOR_REGISTOR
, &value
, sizeof(value
));
188 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"WRM to DEBUG_INTERRUPT_GENERATOR_REGISTOR Register failed");
192 else if(Adapter
->ulPowerSaveMode
!= DEVICE_POWERSAVE_MODE_AS_PROTOCOL_IDLE_MODE
)
195 * Get a Interrupt Out URB and send 8 Bytes Down
196 * To be Done in Thread Context.
197 * Not using Asynchronous Mechanism.
199 status
= usb_interrupt_msg (psInterfaceAdapter
->udev
,
200 usb_sndintpipe(psInterfaceAdapter
->udev
,
201 psInterfaceAdapter
->sIntrOut
.int_out_endpointAddr
),
208 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "Sending Abort pattern down fails with status:%d..\n",status
);
213 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "NOB Sent down :%d", lenwritten
);
218 timeout
= jiffies
+ msecs_to_jiffies(50) ;
219 while( timeout
> jiffies
)
222 rdmalt(Adapter
, CHIP_ID_REG
, &chip_id
, sizeof(UINT
));
223 if(0xbece3200==(chip_id
&~(0xF0)))
225 chip_id
= chip_id
&~(0xF0);
227 if(chip_id
== Adapter
->chip_id
)
230 if(timeout
< jiffies
)
232 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"Not able to read chip-id even after 25 msec");
236 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"Number of completed iteration to read chip-id :%lu", itr
);
239 status
= wrmalt(Adapter
,SW_ABORT_IDLEMODE_LOC
, &Pattern
, sizeof(status
));
242 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0,"WRM to Register SW_ABORT_IDLEMODE_LOC failed..");
248 int InterfaceIdleModeWakeup(PMINI_ADAPTER Adapter
)
251 if(Adapter
->bTriedToWakeUpFromlowPowerMode
)
253 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
, "Wake up already attempted.. ignoring\n");
257 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_OTHERS
, IDLE_MODE
, DBG_LVL_ALL
,"Writing Low Power Mode Abort pattern to the Device\n");
258 Adapter
->bTriedToWakeUpFromlowPowerMode
= TRUE
;
259 InterfaceAbortIdlemode(Adapter
, Adapter
->usIdleModePattern
);
265 void InterfaceHandleShutdownModeWakeup(PMINI_ADAPTER Adapter
)
267 unsigned int uiRegVal
= 0;
269 if(Adapter
->ulPowerSaveMode
== DEVICE_POWERSAVE_MODE_AS_MANUAL_CLOCK_GATING
)
271 // clear idlemode interrupt.
273 Status
=wrmalt(Adapter
,DEBUG_INTERRUPT_GENERATOR_REGISTOR
, &uiRegVal
, sizeof(uiRegVal
));
276 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0,"WRM to DEBUG_INTERRUPT_GENERATOR_REGISTOR Failed with err :%d", Status
);
284 //clear Interrupt EP registers.
285 Status
= rdmalt(Adapter
,DEVICE_INT_OUT_EP_REG0
, &uiRegVal
, sizeof(uiRegVal
));
288 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0,"RDM of DEVICE_INT_OUT_EP_REG0 failed with Err :%d", Status
);
292 Status
= rdmalt(Adapter
,DEVICE_INT_OUT_EP_REG1
, &uiRegVal
, sizeof(uiRegVal
));
295 BCM_DEBUG_PRINT(Adapter
,DBG_TYPE_PRINTK
, 0, 0,"RDM of DEVICE_INT_OUT_EP_REG1 failed with Err :%d", Status
);