160 likes | 376 Views
Change and compile wifi driver on android. Get kernel. cd ~/Android git clone git://android.git.kernel.org/kernel/msm.git kernel- nexusOne # the last parameter, nexusOne is your choice. It is the destination directory. List branches and get the branch you want.
E N D
Get kernel • cd ~/Android • git clone git://android.git.kernel.org/kernel/msm.git kernel-nexusOne • # the last parameter, nexusOne is your choice. It is the destination directory
List branches and get the branch you want • #--- Listing all available branches • cd kernel-nexus • git branch -a • # find kernel that matches the phones.. • see setting -> about phone -> kernel version • #--- Selecting the desired branch. • # Assume that one of branch is "remotes/origin/android-msm-2.6.32-nexusonec" • #git checkout --track -b android-msm-2.6.29-nexusone origin/archive/android-msm-2.6.29-nexusone • git checkout --track -b android-msm-2.6.32 origin/archive/android-msm-2.6.32
Compile kernel • Make config file • adb pull /proc/config.gz • Move to kernel-nexusOne directory • gunzip config.gz • mvconfig .config • Make armmake • Open new file called armmake • Put the follow two lines • PATH=$PATH:/usr/Android/source/prebuilt/linux-x86/toolchain/arm-eabi-4.3.1/bin • make ARCH=arm CROSS_COMPILE=arm-eabi- $1 • Double check that the path is correct. • The arm compiler is part of the ndk • Make armmake executable • Compile kernel (and everything else) • ./armmake • This might take a long time, especially the first time you run it
Driver version • The wifi driver is • kernel-nexusOne/drivers/net/wireless/bcm4329.ko • The driver should be • /system/lib/modules/bcm4329.ko • Make a backup to current driver • ./adb pull /system/lib/modules/bcm4329.ko bcm4329.ko.old • Do not skip this step! • Move driver • Remount system parition • adb shell mount -o remount rw /system • ./adb push /usr/Android/source/kernel-nexusOne/drivers/net/wireless/bcm4329.ko /system/lib/modules/bcm4329.ko • Restart wifi • Doesn’t work!!!
Fixing driver version • The driver version must must match the kernel version • Check versions • Check old version of driver (if you didn’t it up, this step would be difficult) • at command prompt, type • strings bcm4329.ko.old | grep magic • The output is the kernel version • At the command prompts, type • Strings bcm4329.ko | grep magic • These two kernel versions do not match. • Fixes • Get the correct kernel version, or • Make the versions stored in the string the same • We follow this approach • Find and edit kernel-nexusOne/scripts/setlocalversion file • Step 1 • Make • echo "$atag" | awk -F- '{printf("-%05d-%s", $(NF-1),$(NF))}' • Into • echo "$atag" | awk -F- '{printf("-XXXX")}' • Where XXXX is the correct version • Step 2 • Make • printf '%s' –dirty • Into • printf '' –dirty • Save and recompile • When done, recheck if versions match • Move driver and check that wifi works
new driver • Let’s print information about received frames to kernel messages • Edit kernel-nexusOne/drivers/net/wireless/bcm4329/dhd_sdio.c • Search for function • dhdsdio_readframes • Add variables • structsk_buff *TmpPkt; • uchar *HW_header_p; • In the same function, search for • /* Fill in packet len and prio, deliver upward */ • Just above, add • TmpPkt = (structsk_buff *)pkt; • HW_header_p = (uchar *)TmpPkt->data;
Just before /* Unlock during rx call */, add • { • uchar *A = HW_header_p; • printk(“HW : %d %d %d %d\n", A[0], A[1], A[2], A[3]); • printk(“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(“BDC : fl=%d pri=%d fl=%d rssi=%d\n", A[14], A[15], A[16], A[17]-256); • printk(“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(“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]); • } • Save and recompile, move driver, restart wifi. Connect to access point. • In adb shell, cat /proc/kmsg • Observe info being printed out
Sk_buff • /** 261 * structsk_buff - socket buffer • 262 * @next: Next buffer in list • 263 * @prev: Previous buffer in list • 264 * @sk: Socket we are owned by • 265 * @tstamp: Time we arrived • 266 * @dev: Device we arrived on/are leaving by • 267 * @transport_header: Transport layer header • 268 * @network_header: Network layer header • 269 * @mac_header: Link layer header • 270 * @_skb_refdst: destination entry (with norefcount bit) • 271 * @sp: the security path, used for xfrm • 272 * @cb: Control buffer. Free for use by every layer. Put private vars here • 273 * @len: Length of actual data • 274 * @data_len: Data length • 275 * @mac_len: Length of link layer header • 276 * @hdr_len: writable header length of cloned skb • 277 * @csum: Checksum (must include start/offset pair) • 278 * @csum_start: Offset from skb->head where checksumming should start • 279 * @csum_offset: Offset from csum_start where checksum should be stored • 280 * @local_df: allow local fragmentation • 281 * @cloned: Head may be cloned (check refcnt to be sure) • 282 * @nohdr: Payload reference only, must not modify header • 283 * @pkt_type: Packet class • 284 * @fclone: skbuff clone status • 285 * @ip_summed: Driver fed us an IP checksum 2 • 86 * @priority: Packet queueing priority • 287 * @users: User count - see {datagram,tcp}.c • 288 * @protocol: Packet protocol from driver • 289 * @truesize: Buffer size • 290 * @head: Head of buffer • 291 * @data: Data head pointer • 292 * @tail: Tail pointer • 293 * @end: End pointer • 294 * @destructor: Destruct function • 295 * @mark: Generic packet mark • 296 * @nfct: Associated connection, if any • 297 * @ipvs_property: skbuff is owned by ipvs • 298 * @peeked: this packet has been seen already, so stats have been • 299 * done for it, don't do them again • 300 * @nf_trace: netfilter packet trace flag • 301 * @nfctinfo: Relationship of this skb to the connection • 302 * @nfct_reasm: netfilterconntrack re-assembly pointer • 303 * @nf_bridge: Saved data about a bridged frame - see br_netfilter.c • 304 * @skb_iif: ifindex of device we arrived on • 305 * @rxhash: the packet hash computed on receive • 306 * @queue_mapping: Queue mapping for multiqueue devices • 307 * @tc_index: Traffic control index • 308 * @tc_verd: traffic control verdict • 309 * @ndisc_nodetype: router type (from link layer) • 310 * @dma_cookie: a cookie to one of several possible DMA operations • 311 * done by skb DMA functions • 312 * @secmark: security marking • 313 * @vlan_tci: vlan tag control information
Socket buffer (skb) data structure len data tail end head
Functions skb_push(skb, s) len@ s data@,# tail end head data moves Tail is fixed @ : changed # : returned skb_pull(skb, s) len@ s data@,# tail end head
Functions skb_put(skb, s) len@ s data tail# tail@ end head @ : changed # : returned tail moves
Functions skb_headroom(skb) s# len data tail end head # : returned skb_tailroom(skb, s) s# len data tail end head
Functions skb_reserve(skb, s) len data tail end head len s data@ tail@ end head shifted
Functions skb_set_mac_header(skb, s) len s mac_header@ data tail end head skb_reset_mac_header(skb) mac_header@ len data tail end head Mac header points to the beginning of the data
Functions skb_mac_header(skb) mac_header# len data tail end head The pattern for network, transport layers is similar