1
/* TODO: stop #including, move into wireless.c
2
* until then, keep in sync copies in prism54/ and acx111/ dirs
3
* code+data size: less than 1k */
29
static const u8 ratelist[] = { 1,2,5,11,22,33,6,9,12,18,24,36,48,54 };
30
static const u8 dot11ratebyte[] = { 1*2,2*2,11,11*2,22*2,33*2,6*2,9*2,12*2,18*2,24*2,36*2,48*2,54*2 };
31
static const u8 default_modulation[] = {
48
static /* TODO: remove 'static' when moved to wireless.c */
50
rate_mbit2enum(int n) {
52
while(i<sizeof(ratelist)) {
53
if(n==ratelist[i]) return i;
60
get_modulation(int r_enum, char suffix) {
61
if(suffix==',' || suffix==' ' || suffix=='\0') {
62
/* could shorten default_mod by 8 bytes:
63
if(r_enum>=DOT11_RATE_6) return DOT11_MOD_OFDM; */
64
return default_modulation[r_enum];
67
if(r_enum<DOT11_RATE_5 || r_enum>DOT11_RATE_11) return -EINVAL;
71
if(r_enum<DOT11_RATE_5 || r_enum>DOT11_RATE_33) return -EINVAL;
72
return DOT11_MOD_PBCC;
75
if(r_enum<DOT11_RATE_6) return -EINVAL;
76
return DOT11_MOD_OFDM;
79
if(r_enum<DOT11_RATE_6) return -EINVAL;
80
return DOT11_MOD_CCKOFDM;
87
fill_ratevector(const char **pstr, u8 *vector, int size,
88
int (*supported)(int mbit, int mod, void *opaque), void *opaque, int or_mask)
90
unsigned long rate_mbit;
92
const char *str = *pstr;
96
rate_mbit = simple_strtoul(str, (char**)&str, 10);
97
if(rate_mbit>INT_MAX) return -EINVAL;
99
rate_enum = rate_mbit2enum(rate_mbit);
100
if(rate_enum<0) return rate_enum;
103
mod = get_modulation(rate_enum, c);
104
if(mod<0) return mod;
106
if(c>='a' && c<='z') c = *++str;
107
if(c!=',' && c!=' ' && c!='\0') return -EINVAL;
110
int r = supported(rate_mbit, mod, opaque);
114
*vector++ = dot11ratebyte[rate_enum] | or_mask;
118
} while(size>0 && c==',');
120
if(size<1) return -E2BIG;
121
*vector=0; /* TODO: sort, remove dups? */
127
static /* TODO: remove 'static' when moved to wireless.c */
129
fill_ratevectors(const char *str, u8 *brate, u8 *orate, int size,
130
int (*supported)(int mbit, int mod, void *opaque), void *opaque)
134
r = fill_ratevector(&str, brate, size, supported, opaque, 0x80);
140
r = fill_ratevector(&str, orate, size, supported, opaque, 0);
142
/* TODO: sanitize, e.g. remove/error on rates already in basic rate set? */
151
/* TODO: use u64 masks? */
154
fill_ratemask(const char **pstr, u32* mask,
155
int (*supported)(int mbit, int mod,void *opaque),
156
u32 (*gen_mask)(int mbit, int mod,void *opaque),
159
unsigned long rate_mbit;
162
const char *str = *pstr;
166
rate_mbit = simple_strtoul(str, (char**)&str, 10);
167
if(rate_mbit>INT_MAX) return -EINVAL;
169
rate_enum = rate_mbit2enum(rate_mbit);
170
if(rate_enum<0) return rate_enum;
173
mod = get_modulation(rate_enum, c);
174
if(mod<0) return mod;
176
if(c>='a' && c<='z') c = *++str;
177
if(c!=',' && c!=' ' && c!='\0') return -EINVAL;
180
int r = supported(rate_mbit, mod, opaque);
184
m |= gen_mask(rate_mbit, mod, opaque);
193
static /* TODO: remove 'static' when moved to wireless.c */
195
fill_ratemasks(const char *str, u32 *bmask, u32 *omask,
196
int (*supported)(int mbit, int mod,void *opaque),
197
u32 (*gen_mask)(int mbit, int mod,void *opaque),
202
r = fill_ratemask(&str, bmask, supported, gen_mask, opaque);
207
r = fill_ratemask(&str, omask, supported, gen_mask, opaque);