0001
0002
0003
0004 #include "../include/HalPwrSeqCmd.h"
0005
0006 #define PWR_CMD_WRITE 0x01
0007
0008
0009
0010
0011
0012 #define PWR_CMD_POLLING 0x02
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022 #define PWR_CMD_DELAY 0x03
0023
0024
0025
0026
0027 struct wl_pwr_cfg {
0028 u16 offset;
0029 u8 cmd:4;
0030 u8 msk;
0031 u8 value;
0032 };
0033
0034 #define GET_PWR_CFG_OFFSET(__PWR_CMD) __PWR_CMD.offset
0035 #define GET_PWR_CFG_CMD(__PWR_CMD) __PWR_CMD.cmd
0036 #define GET_PWR_CFG_MASK(__PWR_CMD) __PWR_CMD.msk
0037 #define GET_PWR_CFG_VALUE(__PWR_CMD) __PWR_CMD.value
0038
0039 static struct wl_pwr_cfg rtl8188E_power_on_flow[] = {
0040 { 0x0006, PWR_CMD_POLLING, BIT(1), BIT(1) },
0041 { 0x0002, PWR_CMD_WRITE, BIT(0) | BIT(1), 0 },
0042 { 0x0026, PWR_CMD_WRITE, BIT(7), BIT(7) },
0043 { 0x0005, PWR_CMD_WRITE, BIT(7), 0 },
0044 { 0x0005, PWR_CMD_WRITE, BIT(4) | BIT(3), 0 },
0045 { 0x0005, PWR_CMD_WRITE, BIT(0), BIT(0) },
0046 { 0x0005, PWR_CMD_POLLING, BIT(0), 0 },
0047 { 0x0023, PWR_CMD_WRITE, BIT(4), 0 },
0048 };
0049
0050 static struct wl_pwr_cfg rtl8188E_card_disable_flow[] = {
0051 { 0x001F, PWR_CMD_WRITE, 0xFF, 0 },
0052 { 0x0023, PWR_CMD_WRITE, BIT(4), BIT(4) },
0053 { 0x0005, PWR_CMD_WRITE, BIT(1), BIT(1) },
0054 { 0x0005, PWR_CMD_POLLING, BIT(1), 0 },
0055 { 0x0026, PWR_CMD_WRITE, BIT(7), BIT(7) },
0056 { 0x0005, PWR_CMD_WRITE, BIT(3) | BIT(4), BIT(3) },
0057 { 0x0007, PWR_CMD_WRITE, 0xFF, 0 },
0058 { 0x0041, PWR_CMD_WRITE, BIT(4), 0 },
0059 { 0xfe10, PWR_CMD_WRITE, BIT(4), BIT(4) },
0060 };
0061
0062
0063 static struct wl_pwr_cfg rtl8188E_enter_lps_flow[] = {
0064 { 0x0522, PWR_CMD_WRITE, 0xFF, 0x7F },
0065 { 0x05F8, PWR_CMD_POLLING, 0xFF, 0 },
0066 { 0x05F9, PWR_CMD_POLLING, 0xFF, 0 },
0067 { 0x05FA, PWR_CMD_POLLING, 0xFF, 0 },
0068 { 0x05FB, PWR_CMD_POLLING, 0xFF, 0 },
0069 { 0x0002, PWR_CMD_WRITE, BIT(0), 0 },
0070 { 0x0002, PWR_CMD_DELAY, 0, 0 },
0071 { 0x0100, PWR_CMD_WRITE, 0xFF, 0x3F },
0072 { 0x0101, PWR_CMD_WRITE, BIT(1), 0 },
0073 { 0x0553, PWR_CMD_WRITE, BIT(5), BIT(5) },
0074 };
0075
0076 u8 HalPwrSeqCmdParsing(struct adapter *padapter, enum r8188eu_pwr_seq seq)
0077 {
0078 struct wl_pwr_cfg pwrcfgcmd = {0};
0079 struct wl_pwr_cfg *pwrseqcmd;
0080 u8 poll_bit = false;
0081 u8 idx, num_steps;
0082 u8 value = 0;
0083 u32 offset = 0;
0084 u32 poll_count = 0;
0085 u32 max_poll_count = 5000;
0086 int res;
0087
0088 switch (seq) {
0089 case PWR_ON_FLOW:
0090 pwrseqcmd = rtl8188E_power_on_flow;
0091 num_steps = ARRAY_SIZE(rtl8188E_power_on_flow);
0092 break;
0093 case DISABLE_FLOW:
0094 pwrseqcmd = rtl8188E_card_disable_flow;
0095 num_steps = ARRAY_SIZE(rtl8188E_card_disable_flow);
0096 break;
0097 case LPS_ENTER_FLOW:
0098 pwrseqcmd = rtl8188E_enter_lps_flow;
0099 num_steps = ARRAY_SIZE(rtl8188E_enter_lps_flow);
0100 break;
0101 default:
0102 return false;
0103 }
0104
0105 for (idx = 0; idx < num_steps; idx++) {
0106 pwrcfgcmd = pwrseqcmd[idx];
0107
0108 switch (GET_PWR_CFG_CMD(pwrcfgcmd)) {
0109 case PWR_CMD_WRITE:
0110 offset = GET_PWR_CFG_OFFSET(pwrcfgcmd);
0111
0112
0113 res = rtw_read8(padapter, offset, &value);
0114 if (res)
0115 return false;
0116
0117 value &= ~(GET_PWR_CFG_MASK(pwrcfgcmd));
0118 value |= (GET_PWR_CFG_VALUE(pwrcfgcmd) & GET_PWR_CFG_MASK(pwrcfgcmd));
0119
0120
0121 rtw_write8(padapter, offset, value);
0122 break;
0123 case PWR_CMD_POLLING:
0124 poll_bit = false;
0125 offset = GET_PWR_CFG_OFFSET(pwrcfgcmd);
0126 do {
0127 res = rtw_read8(padapter, offset, &value);
0128 if (res)
0129 return false;
0130
0131 value &= GET_PWR_CFG_MASK(pwrcfgcmd);
0132 if (value == (GET_PWR_CFG_VALUE(pwrcfgcmd) & GET_PWR_CFG_MASK(pwrcfgcmd)))
0133 poll_bit = true;
0134 else
0135 udelay(10);
0136
0137 if (poll_count++ > max_poll_count)
0138 return false;
0139 } while (!poll_bit);
0140 break;
0141 case PWR_CMD_DELAY:
0142 udelay(GET_PWR_CFG_OFFSET(pwrcfgcmd));
0143 break;
0144 default:
0145 break;
0146 }
0147 }
0148 return true;
0149 }