diff options
Diffstat (limited to 'drivers/net/wireless/brcm80211/brcmutil/d11.c')
| -rw-r--r-- | drivers/net/wireless/brcm80211/brcmutil/d11.c | 93 | 
1 files changed, 76 insertions, 17 deletions
diff --git a/drivers/net/wireless/brcm80211/brcmutil/d11.c b/drivers/net/wireless/brcm80211/brcmutil/d11.c index 30e54e2c6c9..2b2522bdd8e 100644 --- a/drivers/net/wireless/brcm80211/brcmutil/d11.c +++ b/drivers/net/wireless/brcm80211/brcmutil/d11.c @@ -21,19 +21,46 @@  #include <brcmu_wifi.h>  #include <brcmu_d11.h> -static void brcmu_d11n_encchspec(struct brcmu_chan *ch) +static u16 d11n_sb(enum brcmu_chan_sb sb)  { -	ch->chspec = ch->chnum & BRCMU_CHSPEC_CH_MASK; +	switch (sb) { +	case BRCMU_CHAN_SB_NONE: +		return BRCMU_CHSPEC_D11N_SB_N; +	case BRCMU_CHAN_SB_L: +		return BRCMU_CHSPEC_D11N_SB_L; +	case BRCMU_CHAN_SB_U: +		return BRCMU_CHSPEC_D11N_SB_U; +	default: +		WARN_ON(1); +	} +	return 0; +} -	switch (ch->bw) { +static u16 d11n_bw(enum brcmu_chan_bw bw) +{ +	switch (bw) {  	case BRCMU_CHAN_BW_20: -		ch->chspec |= BRCMU_CHSPEC_D11N_BW_20 | BRCMU_CHSPEC_D11N_SB_N; -		break; +		return BRCMU_CHSPEC_D11N_BW_20;  	case BRCMU_CHAN_BW_40: +		return BRCMU_CHSPEC_D11N_BW_40;  	default: -		WARN_ON_ONCE(1); -		break; +		WARN_ON(1);  	} +	return 0; +} + +static void brcmu_d11n_encchspec(struct brcmu_chan *ch) +{ +	if (ch->bw == BRCMU_CHAN_BW_20) +		ch->sb = BRCMU_CHAN_SB_NONE; + +	ch->chspec = 0; +	brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_CH_MASK, +			BRCMU_CHSPEC_CH_SHIFT, ch->chnum); +	brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11N_SB_MASK, +			0, d11n_sb(ch->sb)); +	brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11N_BW_MASK, +			0, d11n_bw(ch->bw));  	if (ch->chnum <= CH_MAX_2G_CHANNEL)  		ch->chspec |= BRCMU_CHSPEC_D11N_BND_2G; @@ -41,23 +68,34 @@ static void brcmu_d11n_encchspec(struct brcmu_chan *ch)  		ch->chspec |= BRCMU_CHSPEC_D11N_BND_5G;  } -static void brcmu_d11ac_encchspec(struct brcmu_chan *ch) +static u16 d11ac_bw(enum brcmu_chan_bw bw)  { -	ch->chspec = ch->chnum & BRCMU_CHSPEC_CH_MASK; - -	switch (ch->bw) { +	switch (bw) {  	case BRCMU_CHAN_BW_20: -		ch->chspec |= BRCMU_CHSPEC_D11AC_BW_20; -		break; +		return BRCMU_CHSPEC_D11AC_BW_20;  	case BRCMU_CHAN_BW_40: +		return BRCMU_CHSPEC_D11AC_BW_40;  	case BRCMU_CHAN_BW_80: -	case BRCMU_CHAN_BW_80P80: -	case BRCMU_CHAN_BW_160: +		return BRCMU_CHSPEC_D11AC_BW_80;  	default: -		WARN_ON_ONCE(1); -		break; +		WARN_ON(1);  	} +	return 0; +} +static void brcmu_d11ac_encchspec(struct brcmu_chan *ch) +{ +	if (ch->bw == BRCMU_CHAN_BW_20 || ch->sb == BRCMU_CHAN_SB_NONE) +		ch->sb = BRCMU_CHAN_SB_L; + +	brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_CH_MASK, +			BRCMU_CHSPEC_CH_SHIFT, ch->chnum); +	brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11AC_SB_MASK, +			BRCMU_CHSPEC_D11AC_SB_SHIFT, ch->sb); +	brcmu_maskset16(&ch->chspec, BRCMU_CHSPEC_D11AC_BW_MASK, +			0, d11ac_bw(ch->bw)); + +	ch->chspec &= ~BRCMU_CHSPEC_D11AC_BND_MASK;  	if (ch->chnum <= CH_MAX_2G_CHANNEL)  		ch->chspec |= BRCMU_CHSPEC_D11AC_BND_2G;  	else @@ -73,6 +111,7 @@ static void brcmu_d11n_decchspec(struct brcmu_chan *ch)  	switch (ch->chspec & BRCMU_CHSPEC_D11N_BW_MASK) {  	case BRCMU_CHSPEC_D11N_BW_20:  		ch->bw = BRCMU_CHAN_BW_20; +		ch->sb = BRCMU_CHAN_SB_NONE;  		break;  	case BRCMU_CHSPEC_D11N_BW_40:  		ch->bw = BRCMU_CHAN_BW_40; @@ -112,6 +151,7 @@ static void brcmu_d11ac_decchspec(struct brcmu_chan *ch)  	switch (ch->chspec & BRCMU_CHSPEC_D11AC_BW_MASK) {  	case BRCMU_CHSPEC_D11AC_BW_20:  		ch->bw = BRCMU_CHAN_BW_20; +		ch->sb = BRCMU_CHAN_SB_NONE;  		break;  	case BRCMU_CHSPEC_D11AC_BW_40:  		ch->bw = BRCMU_CHAN_BW_40; @@ -128,6 +168,25 @@ static void brcmu_d11ac_decchspec(struct brcmu_chan *ch)  		break;  	case BRCMU_CHSPEC_D11AC_BW_80:  		ch->bw = BRCMU_CHAN_BW_80; +		ch->sb = brcmu_maskget16(ch->chspec, BRCMU_CHSPEC_D11AC_SB_MASK, +					 BRCMU_CHSPEC_D11AC_SB_SHIFT); +		switch (ch->sb) { +		case BRCMU_CHAN_SB_LL: +			ch->chnum -= CH_30MHZ_APART; +			break; +		case BRCMU_CHAN_SB_LU: +			ch->chnum -= CH_10MHZ_APART; +			break; +		case BRCMU_CHAN_SB_UL: +			ch->chnum += CH_10MHZ_APART; +			break; +		case BRCMU_CHAN_SB_UU: +			ch->chnum += CH_30MHZ_APART; +			break; +		default: +			WARN_ON_ONCE(1); +			break; +		}  		break;  	case BRCMU_CHSPEC_D11AC_BW_8080:  	case BRCMU_CHSPEC_D11AC_BW_160:  | 
