Hi all,
I was really hoping to be able to access 802.11 headers of received
packets on a BCM4329 chip embedded on my HTC Incredible. ?However, the
further and further I dug in to the source code for the kernel and
BCM4329 driver, the more and more I became less hopeful. ?But, I'm
hoping someone with some more knowledge on this chipset might be able
to help (especially you, Howard!).
The HTC Incredible has the wireless driver loaded as a module, and
builds it straight from the kernel tree:
http://android.git.kernel.org/?p=kernel/msm.git;a=tree;f=drivers/net/wireless/bcm4329;h=01f09252ff9b80379e6db6dbb22af4fcba004982;hb=HEAD
After digging through the driver code, it seemed like stripped 802.11
packets come from the BCM4329 with some custom software header
(SDPCM??). Once the driver receives a packet, it has been stripped of
the 802.11 header, but contains little data such as the channel it was
received on, and the sequence number. I was hoping to dig up the
entire 802.11 header, or at least the per-packet RSSI.
Next, I was thinking I could kick the card in to promiscuous mode.
Either by explicitly doing so, or by modifying the RX filter to accept
all frames regardless of BSSID. However, where this happens in
dhd_linux.c, there is a comment:
/* Mark below code due to current firmware doesn't support it.
* The error message may mislead other engineers
*/
So it seems as though the binary broadcom firmware does not allow the
card to be set in to promiscuous mode. I'd like to still muck with
the RX filter to see if I can basically set it in to promiscuous mode
without explicitly doing so. I'm going to muck around with this, but
if anyone else has experience with this to tell me to bark up another
tree, please let me know :)
It would be great though, if someone could better explain what the
interaction is between the BCM4329 and the host driver. Is it at all
possible to receive the raw 802.11 header? Any per-packet RSSI
information? It looks like the BCM4329 has an on-chip processor which
is doing all of this processing.
Also, it seems like the defacto Android thing to do is, have the
wireless interface be an Ethernet interface. All wireless frames are
translated in to Ethernet frames, and then pushed upwards. I noticed
this with the TI chipset in the Droid. This really limits the amount
of radio information which is, I suppose good for an embedded device,
but bad for hacking :\
Any feedback would be extremely appreciated :)
Thanks!
George
Hi Jason,
This was a *huge* help to get this response from you, thanks a bunch for that.
I'd love to poke GregKG's staging tree and the mac80211 driver for the
bcm4329. I did some searching for the staging tree, and the only
address I could find was:
git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging.git
But whenever I try to clone it, it just hangs up on me. "fatal: The
remote end hung up unexpectedly" ... is there another location that
I'm not finding?
I can definitely give cyanogenmod a shot, I had it running on my old
G1 at one point. Let me toss it on my Incredible and see where we can
go.
I actually tried to go the wl1271 on my Droid1 first with this code:
http://android.git.kernel.org/?p=platform/hardware/ti/wlan.git;a=tree
I am able to read the 802.11 header in the kernel module before it
gets translated to an Ethernet frame. That was a great step towards
what I wanted, I just needed to then kick it in to promiscuous mode.
The mode is disabled, but I figured I could reconfigure the RX filter.
I changed the RX filter to disable BSSID filtering, but I was still
only getting packets destined to my MAC.
But, then I found this comment which appears to state that the
firmware sets the local MAC address filter (plus broadcast traffic):
http://android.git.kernel.org/?p=platform/hardware/ti/wlan.git;a=blob;f=wl1271/TWD/Ctrl/CmdBldCmd.c#l147
So it seems like the firmware is preventing the driver from removing
the BSSID filter on the wl1271. But, as you mentioned the N900 was
able to kick it in to promiscuous mode which must be changing this
filter. Is it using a different firmware? But, I'm going to explore
the in-kernel driver for this as you mentioned. I will start poking
around that.
Thanks again, I really appreciate it.
- George
On Mon, Mar 7, 2011 at 9:01 AM, Jason <[email protected]> wrote:
> On Sun, Mar 06, 2011 at 11:11:48PM -0500, George Nychis wrote:
>> Hi all,
>>
>> I was really hoping to be able to access 802.11 headers of received
>> packets on a BCM4329 chip embedded on my HTC Incredible. ?However, the
>> further and further I dug in to the source code for the kernel and
>> BCM4329 driver, the more and more I became less hopeful. ?But, I'm
>> hoping someone with some more knowledge on this chipset might be able
>> to help (especially you, Howard!).
>>
>
> Most development work for Broadcom wifi is occurring in GregKH's staging
> tree, I've included the linuxdriverproject ml in the CC. ?It's in
> drivers/staging/brcm80211, it's a mac80211 driver that includes support
> for bcm4329. ?You may have more luck with it.
>
> If you're feeling really frisky, try cyanogenmod [1] as your base system,
> it's running 2.6.37 on my Nexus One right now. ?Here's how to build for
> the Incredible [2]. ?It shouldn't be too far of a leap to get brcm80211
> running on it.
>
> As a side note, the same holds for the TI wl1271 (right model?) found in
> the HTC G1 and Nokia N900. ?The in-kernel driver has much better support
> for mac80211. ?Android, by default uses the out-of-tree version, the
> N900 used the in-tree version. ?The N900 could go into monitor mode
> without modification once you had root access.
>
>> The HTC Incredible has the wireless driver loaded as a module, and
>> builds it straight from the kernel tree:
>> http://android.git.kernel.org/?p=kernel/msm.git;a=tree;f=drivers/net/wireless/bcm4329;h=01f09252ff9b80379e6db6dbb22af4fcba004982;hb=HEAD
>
> AFAICT, this driver will never make it into Linus' tree. ?All of Broadcom's
> efforts are on merging staging/brcm80211 into mainline.
>
> hth,
>
> Jason.
>
> [1] http://www.cyanogenmod.com
> [2]
> http://wiki.cyanogenmod.com/index.php?title=Compile_CyanogenMod_for_Incredible
>
On Sun, Mar 06, 2011 at 11:11:48PM -0500, George Nychis wrote:
> Hi all,
>
> I was really hoping to be able to access 802.11 headers of received
> packets on a BCM4329 chip embedded on my HTC Incredible. ?However, the
> further and further I dug in to the source code for the kernel and
> BCM4329 driver, the more and more I became less hopeful. ?But, I'm
> hoping someone with some more knowledge on this chipset might be able
> to help (especially you, Howard!).
>
Most development work for Broadcom wifi is occurring in GregKH's staging
tree, I've included the linuxdriverproject ml in the CC. It's in
drivers/staging/brcm80211, it's a mac80211 driver that includes support
for bcm4329. You may have more luck with it.
If you're feeling really frisky, try cyanogenmod [1] as your base system,
it's running 2.6.37 on my Nexus One right now. Here's how to build for
the Incredible [2]. It shouldn't be too far of a leap to get brcm80211
running on it.
As a side note, the same holds for the TI wl1271 (right model?) found in
the HTC G1 and Nokia N900. The in-kernel driver has much better support
for mac80211. Android, by default uses the out-of-tree version, the
N900 used the in-tree version. The N900 could go into monitor mode
without modification once you had root access.
> The HTC Incredible has the wireless driver loaded as a module, and
> builds it straight from the kernel tree:
> http://android.git.kernel.org/?p=kernel/msm.git;a=tree;f=drivers/net/wireless/bcm4329;h=01f09252ff9b80379e6db6dbb22af4fcba004982;hb=HEAD
AFAICT, this driver will never make it into Linus' tree. All of Broadcom's
efforts are on merging staging/brcm80211 into mainline.
hth,
Jason.
[1] http://www.cyanogenmod.com
[2]
http://wiki.cyanogenmod.com/index.php?title=Compile_CyanogenMod_for_Incredible
On Wed, Mar 09, 2011 at 12:59:33AM -0500, George Nychis wrote:
> This was a *huge* help to get this response from you, thanks a bunch for that.
>
No problem, I wish this particular idea could be higher on my project
list. ;-)
> I'd love to poke GregKG's staging tree and the mac80211 driver for the
s/GregKG/GregKH/
> bcm4329. I did some searching for the staging tree, and the only
> address I could find was:
> git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging.git
>
In my tree I did the following:
$ git remote add staging-2.6 \
git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging-2.6.git
$ git remote update staging-2.6
...successful output...
So, it looks like you're using the old url, try this:
$ git clone \
git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/staging-2.6.git
Then, you'll want the staging-next branch.
hth,
Jason.
I can answer the question about the per-packet RSSI.
Each frame consists of
HW header, SW header, BDC header, MAC header, and MSDU,
where HW is hareware and SW is software.
BDC header includes rssi as a member.
MAC header consists of DA, SA, and proto,
where DA is the destination address and SA is the source address.
When proto is IP (0x0800) or ARP (0x0806),
rssi in BDC header is greater than zero.
To obtain the correct value of rssi,
you must subtract 256 (=0x100) from it.
For some other protocols, rssi in BDC header is zero,
meaning we cannot get
correct rssi for them.
The following kernel messages are the examples that I produced.
----------------
<2>[ 477.763885] Jong: rssi=-54, SSID=Sender
<4>[ 477.892425] Jong: HW : 110 0 145 255
<4>[ 477.893188] Jong: SW : seq=185 chan=2 0 doff=14 0
txmax=154 0 0 0 0
<4>[ 477.893615] Jong: BDC : fl=16 pri=0 fl=0 rssi=202 --> -54 dBm
<4>[ 477.894287] Jong: MAC : DA=ff ff ff ff ff ff
SA=00 1f c6 d6 3 19 proto=0800 (IP)
<4>[ 477.894744] Jong: MSDU: 45 0 0 4e 1d a5 0 0 80 11
<4>[ 477.895782] Jong: HW : 78 0 177 255
<4>[ 477.896179] Jong: SW : seq=186 chan=2 0 doff=14 0
txmax=154 0 0 0 0
<4>[ 477.896606] Jong: BDC : fl=16 pri=0 fl=0 rssi=202 --> -54 dBm
<4>[ 477.897277] Jong: MAC : DA=ff ff ff ff ff ff
SA=00 04 96 1d 80 a0 proto=0806 (ARP)
<4>[ 477.897705] Jong: MSDU: 0 1 8 0 6 4 0 1 0 4
----------------
The code to produce the above kernel messages is as follows.
In dhdsdio_readframes() function,
add
struct sk_buff *TmpPkt;
uchar *HW_header_p;
and right before the comment
/* Fill in packet len and prio, deliver upward */
add
TmpPkt = (struct sk_buff *)pkt;
HW_header_p = (uchar *)TmpPkt->data;
and right before the comment
/* Unlock during rx call */
add
{
uchar *A = HW_header_p;
printk("Jong: HW : %d %d %d %d\n", A[0], A[1], A[2], A[3]);
printk("Jong: SW : seq=%d chan=%d %d doff=%d %d
txmax=%d %d %d %d %d\n",
A[4], A[5], A[6], A[7], A[8], A[9], A[10], A[11], A[12], A[13]);
printk("Jong: BDC : fl=%d pri=%d fl=%d rssi=%d\n",
A[14], A[15], A[16], A[17]);
printk("Jong: MAC : DA=%02x %02x %02x %02x %02x %02x
SA=%02x %02x %02x %02x %02x %02x proto=%02x%02x\n",
A[18], A[19], A[20], A[21], A[22], A[23],
A[24], A[25], A[26], A[27], A[28], A[29],
A[30], A[31]);
printk("Jong: MSDU : %02x %02x %02x %02x %02x %02x %02x
%02x %02x %02x\n",
A[32], A[33], A[34], A[35], A[36], A[37], A[38],
A[39], A[40], A[41]);
}
I have been tried to modify driver codes to get a monitor mode.
But it did not work since I guess that the firmware does not
support it. What I tried is follows.
In wl_iw_set_mode() function,
I addded
int monitor = htod32(1);
error = dev_wlc_ioctl(dev, WLC_SET_MONITOR,
&monitor, sizeof(monitor));
The result of error is -95 that means EOPNOTSUPP
(error operation not supported).
I hope that the developers of the firmware for bcm4329
release a new firmware providing monitor mode.
Hi George,
I am looking for a 1 GHz powered android phone which can support wifi-
promiscuous mode , can you please suggest one ?
I was going through your post and came to the impression that the BRCM4329
doesn't allow promiscuous mode even by modifying the kernel modules as the
firmware sets the local MAC address filter. Is that correct ?
Thanks in Advance
Sreejith