Skip to content

Commit

Permalink
rtw88: fix potential read outside array boundary
Browse files Browse the repository at this point in the history
The level of cckpd is from 0 to 4, and it is the index of
array pd_lvl[] and cs_lvl[]. However, the length of both arrays
are 4, which is smaller than the possible maximum input index.
Enumerate cck level to make sure the max level will not be wrong
if new level is added in future.

Fixes: 479c4ee ("rtw88: add dynamic cck pd mechanism")
Signed-off-by: Tzu-En Huang <tehuang@realtek.com>
Signed-off-by: Yan-Hsuan Chuang <yhchuang@realtek.com>
Signed-off-by: Kalle Valo <kvalo@codeaurora.org>
  • Loading branch information
Tzu-En Huang authored and Kalle Valo committed Oct 31, 2019
1 parent ff0dfe5 commit 18a0696
Show file tree
Hide file tree
Showing 3 changed files with 19 additions and 11 deletions.
17 changes: 8 additions & 9 deletions drivers/net/wireless/realtek/rtw88/phy.c
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ static void rtw_phy_cck_pd_init(struct rtw_dev *rtwdev)

for (i = 0; i <= RTW_CHANNEL_WIDTH_40; i++) {
for (j = 0; j < RTW_RF_PATH_MAX; j++)
dm_info->cck_pd_lv[i][j] = 0;
dm_info->cck_pd_lv[i][j] = CCK_PD_LV0;
}

dm_info->cck_fa_avg = CCK_FA_AVG_RESET;
Expand Down Expand Up @@ -461,7 +461,6 @@ static void rtw_phy_dpk_track(struct rtw_dev *rtwdev)
chip->ops->dpk_track(rtwdev);
}

#define CCK_PD_LV_MAX 5
#define CCK_PD_FA_LV1_MIN 1000
#define CCK_PD_FA_LV0_MAX 500

Expand All @@ -471,10 +470,10 @@ static u8 rtw_phy_cck_pd_lv_unlink(struct rtw_dev *rtwdev)
u32 cck_fa_avg = dm_info->cck_fa_avg;

if (cck_fa_avg > CCK_PD_FA_LV1_MIN)
return 1;
return CCK_PD_LV1;

if (cck_fa_avg < CCK_PD_FA_LV0_MAX)
return 0;
return CCK_PD_LV0;

return CCK_PD_LV_MAX;
}
Expand All @@ -494,15 +493,15 @@ static u8 rtw_phy_cck_pd_lv_link(struct rtw_dev *rtwdev)
u32 cck_fa_avg = dm_info->cck_fa_avg;

if (igi > CCK_PD_IGI_LV4_VAL && rssi > CCK_PD_RSSI_LV4_VAL)
return 4;
return CCK_PD_LV4;
if (igi > CCK_PD_IGI_LV3_VAL && rssi > CCK_PD_RSSI_LV3_VAL)
return 3;
return CCK_PD_LV3;
if (igi > CCK_PD_IGI_LV2_VAL || rssi > CCK_PD_RSSI_LV2_VAL)
return 2;
return CCK_PD_LV2;
if (cck_fa_avg > CCK_PD_FA_LV1_MIN)
return 1;
return CCK_PD_LV1;
if (cck_fa_avg < CCK_PD_FA_LV0_MAX)
return 0;
return CCK_PD_LV0;

return CCK_PD_LV_MAX;
}
Expand Down
9 changes: 9 additions & 0 deletions drivers/net/wireless/realtek/rtw88/phy.h
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,15 @@ rtw_get_tx_power_params(struct rtw_dev *rtwdev, u8 path,
u8 rate, u8 bw, u8 ch, u8 regd,
struct rtw_power_params *pwr_param);

enum rtw_phy_cck_pd_lv {
CCK_PD_LV0,
CCK_PD_LV1,
CCK_PD_LV2,
CCK_PD_LV3,
CCK_PD_LV4,
CCK_PD_LV_MAX,
};

#define MASKBYTE0 0xff
#define MASKBYTE1 0xff00
#define MASKBYTE2 0xff0000
Expand Down
4 changes: 2 additions & 2 deletions drivers/net/wireless/realtek/rtw88/rtw8822c.c
Original file line number Diff line number Diff line change
Expand Up @@ -3295,8 +3295,8 @@ rtw8822c_phy_cck_pd_set_reg(struct rtw_dev *rtwdev,
static void rtw8822c_phy_cck_pd_set(struct rtw_dev *rtwdev, u8 new_lvl)
{
struct rtw_dm_info *dm_info = &rtwdev->dm_info;
s8 pd_lvl[4] = {2, 4, 6, 8};
s8 cs_lvl[4] = {2, 2, 2, 4};
s8 pd_lvl[CCK_PD_LV_MAX] = {0, 2, 4, 6, 8};
s8 cs_lvl[CCK_PD_LV_MAX] = {0, 2, 2, 2, 4};
u8 cur_lvl;
u8 nrx, bw;

Expand Down

0 comments on commit 18a0696

Please sign in to comment.