On Monday 08 December 2008 20:43:35 you wrote: > And on your second patch: > > +static u16 nl80211_calculate_bitrate(struct rate_info *rate) > > +{ > > + int modulation, streams, bitrate; > > + > > + if (!(rate->flags & RATE_INFO_FLAGS_MCS)) > > + return rate->legacy; > > + > > + modulation = rate->mcs & 7; > > + streams = rate->mcs >> 3; > I don't think this gives correct results for MCS rates 32 through 76, > does it? It should at least not calculate anything then. If we did it in > userspace then programs could also actually calculate the correct rate > as a float, rather than this approximation. Not that it'll matter, I > guess. Doesn't anybody know how to do the actual calculation? It had a small type (corrected in the new patches), but I think the values are good. I have attached a test programm to this mail that outputs the bandwith values calculated by the function. Henning
#include <stdio.h> #define RATE_INFO_FLAGS_MCS 1 #define RATE_INFO_FLAGS_40_MHZ_WIDTH 2 #define RATE_INFO_FLAGS_SHORT_GI 4 struct rate_info { int flags, mcs, legacy; }; int nl80211_calculate_bitrate(struct rate_info *rate) { int modulation, streams, bitrate; if (!(rate->flags & RATE_INFO_FLAGS_MCS)) return rate->legacy; modulation = rate->mcs & 7; streams = (rate->mcs >> 3) + 1; bitrate = (rate->flags & RATE_INFO_FLAGS_40_MHZ_WIDTH) ? 13500000 : 6500000; if (modulation < 4) bitrate *= (modulation + 1); else if (modulation == 4) bitrate *= (modulation + 2); else bitrate *= (modulation + 3); bitrate *= streams; if (rate->flags & RATE_INFO_FLAGS_SHORT_GI) bitrate = (bitrate / 9) * 10; /* do NOT round down here */ return (bitrate + 50000) / 100000; } int main(int argc, char **argv) { struct rate_info ri; int mcs; printf("20 Mhz wide channels\n"); for (mcs = 0; mcs < 72; mcs++) { int r1, r2; ri.mcs = mcs; ri.flags = RATE_INFO_FLAGS_MCS; r1 = nl80211_calculate_bitrate(&ri); ri.flags = RATE_INFO_FLAGS_MCS | RATE_INFO_FLAGS_SHORT_GI; r2 = nl80211_calculate_bitrate(&ri); printf("mcs %d: long gi %4d / short gi %4d\n", mcs, r1, r2); } printf("\n"); printf("40 Mhz wide channels\n"); for (mcs = 0; mcs < 72; mcs++) { int r1, r2; ri.mcs = mcs; ri.flags = RATE_INFO_FLAGS_MCS | RATE_INFO_FLAGS_40_MHZ_WIDTH; r1 = nl80211_calculate_bitrate(&ri); ri.flags = RATE_INFO_FLAGS_MCS | RATE_INFO_FLAGS_SHORT_GI | RATE_INFO_FLAGS_40_MHZ_WIDTH; r2 = nl80211_calculate_bitrate(&ri); printf("mcs %d: long gi %4d / short gi %4d\n", mcs, r1, r2); } }
Attachment:
signature.asc
Description: This is a digitally signed message part.