本文為個人原創(chuàng)峡继,歡迎轉(zhuǎn)載暗挑,但請務必在明顯位置注明出處更舞!
http://www.reibang.com/p/8686931d31f0
1掠剑、前言
從Android 4.4宣布支持64位系統(tǒng)以來竟痰,各終端方案廠商逐步推出了各自的64位soc解決方案尚胞。Google為了兼容之前32位系統(tǒng)的應用硬霍,在64位系統(tǒng)上也實現(xiàn)了對32位應用的支持。那么問題就來了笼裳,在一個64位系統(tǒng)的Android手機上如何檢測應用是運行在32位還是64位環(huán)境唯卖?本博文將為大家解答這個問題。
本文會分別對Android系統(tǒng)中的App躬柬、Native進程以及動態(tài)鏈接庫的32/64位檢測方法進行介紹拜轨。
2、檢測App
任何一個Android手機用戶對APK文件肯定不會陌生允青,它是一個Android應用資源的封裝文件橄碾。當你下載安裝一個App之后,從Launcher啟動該應用颠锉,系統(tǒng)會由Zygote分叉出一個子進程來提供App運行的虛擬機和Runtime環(huán)境法牲。與32位系統(tǒng)不同的是,在64系統(tǒng)中會同時存在兩個Zygote進程——zygote和zygote64琼掠,分別對應32位和64位應用拒垃。所以,要進行App的32/64位檢測眉枕,只需要看它的父進程是哪個Zygote即可恶复。
下面的例子通過App的PPID信息——2759怜森,檢測出了終端系統(tǒng)中所有的64位應用速挑,且該方式無需root權(quán)限。
$ adb shell ps |grep zygote
root 2759 1 2131692 87052 0 0000000000 S zygote64
root 2760 1 1574048 53740 0 0000000000 S zygote
$ adb shell ps|grep 2759
root 2759 1 2131692 87052 0 0000000000 S zygote64
system 3257 2759 2339956 158936 0 0000000000 S system_server
radio 3393 2759 1601272 96220 0 0000000000 S com.android.phone
u0_a85 3407 2759 1564856 88740 0 0000000000 S com.android.inputmethod.latin
u0_a20 3422 2759 1970228 167288 0 0000000000 S com.android.systemui
u0_a7 3769 2759 1548288 63384 0 0000000000 S android.ext.services
u0_a13 3958 2759 1896704 131832 0 0000000000 S com.android.launcher3
u0_a6 3989 2759 1562416 94060 0 0000000000 S android.process.acore
u0_a17 4046 2759 1563300 88504 0 0000000000 S android.process.media
u0_a28 4112 2759 1555640 82004 0 0000000000 S com.android.quicksearchbox
u0_a64 4157 2759 1554484 72944 0 0000000000 S com.android.calendar
u0_a57 4215 2759 1572160 83532 0 0000000000 S com.android.email
u0_a77 4231 2759 1554408 67192 0 0000000000 S com.android.exchange
u0_a5 4279 2759 1549136 66072 0 0000000000 S com.android.onetimeinitializer
u0_a10 4299 2759 1552472 74088 0 0000000000 S com.android.providers.calendar
u0_a94 4325 2759 1869948 112984 0 0000000000 S com.android.soundrecorder
system 4345 2759 1561180 73680 0 0000000000 S com.sprd.engineermode
u0_a15 4887 2759 1874612 106196 0 0000000000 S com.android.packageinstaller
u0_a73 5133 2759 2425904 205912 0 0000000000 S com.android.browser
3副硅、檢測Native進程
Andorid手機開機啟動之后姥宝,init進程會啟動一些后臺守護進程。通常恐疲,這些進程會對整個Android系統(tǒng)起到重要作用腊满,例如Zygote、MediaServer和ServiceManager等培己。因為這些Native進程并不是通過安裝APK獲得碳蛋,所以上一章節(jié)的方法在這里并不適用。我們知道Andorid Framework層以下都是繼承自Linux省咨,因此可以采用Linux系統(tǒng)的一些工具和方法來對Native進程進行32/64位系統(tǒng)的檢測肃弟。
方法一,通過readelf工具來分析Native進程對應的bin文件,下面以mediaserver為例
$readelf -h mediaserver
ELF Header:
Magic: 7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00
Class: ELF32
Data: 2's complement, little endian
Version: 1 (current)
OS/ABI: UNIX - System V
ABI Version: 0
Type: DYN (Shared object file)
Machine: ARM
Version: 0x1
Entry point address: 0x1e24
Start of program headers: 52 (bytes into file)
Start of section headers: 20980 (bytes into file)
Flags: 0x5000000, Version5 EABI
Size of this header: 52 (bytes)
Size of program headers: 32 (bytes)
Number of program headers: 9
Size of section headers: 40 (bytes)
Number of section headers: 29
Section header string table index: 28
從上面的信息中我們看到mediaserver文件的Class字段為ELF32笤受,Machine字段為ARM穷缤。由此可知,在Android 64位系統(tǒng)中箩兽,mediaserver運行在32位環(huán)境中津肛。
方法二,在運行時通過打印Native進程的內(nèi)存映射列表(maps)來檢測32/64位汗贫,這個方法同樣也適用于App的32/64位檢測身坐。這里以com.android.email為例,從上一章節(jié)的進程列表打印可以看到落包,com.android.email的PID為4215掀亥。
u0_a57 4215 2759 1572160 83532 0 0000000000 S com.android.email
然后,通過proc文件系統(tǒng)便可查詢到PID=4215的內(nèi)存映射列表 (截取片段)
$adb root
$adb shell cat /proc/4215/maps
......
71ebcb1000-71ebcb3000 r-xp 00000000 103:15 1453 /system/lib64/libOpenSLES.so
71ebcb3000-71ebcb4000 r--p 00001000 103:15 1453 /system/lib64/libOpenSLES.so
71ebcb4000-71ebcb5000 rw-p 00002000 103:15 1453 /system/lib64/libOpenSLES.so
71ebcb5000-71ebcd5000 r--s 00000000 00:12 282 /dev/__properties__/u:object_r:logd_prop:s0
71ebcd5000-71ebcf5000 r--s 00000000 00:12 287 /dev/__properties__/u:object_r:log_tag_prop:s0
71ebcf5000-71ebcf6000 r--p 00000000 00:00 0 [anon:linker_alloc]
71ebcf6000-71ebcf7000 rw-p 00000000 00:00 0 [anon:linker_alloc_vector]
71ebcf7000-71ebcf8000 r--p 00000000 00:00 0 [anon:linker_alloc]
71ebcf8000-71ebcf9000 rw-p 00000000 00:00 0 [anon:linker_alloc]
71ebcf9000-71ebcfb000 r-xp 00000000 103:15 1452 /system/lib64/libOpenMAXAL.so
71ebcfb000-71ebcfc000 r--p 00001000 103:15 1452 /system/lib64/libOpenMAXAL.so
71ebcfc000-71ebcfd000 rw-p 00002000 103:15 1452 /system/lib64/libOpenMAXAL.so
71ebcfd000-71ebcff000 rw-p 00000000 00:01 22281 /dev/ashmem/dalvik-indirect ref table (deleted)
71ebcff000-71ebd00000 r-xp 00000000 103:15 1565 /system/lib64/libjnigraphics.so
71ebd00000-71ebd01000 r--p 00000000 103:15 1565 /system/lib64/libjnigraphics.so
71ebd01000-71ebd02000 rw-p 00001000 103:15 1565 /system/lib64/libjnigraphics.so
71ebd02000-71ebd04000 rw-p 00000000 00:01 22280 /dev/ashmem/dalvik-indirect ref table (deleted)
71ebd04000-71ebd05000 r-xp 00000000 103:15 1644 /system/lib64/libsigchain.so
71ebd05000-71ebd06000 r--p 00000000 103:15 1644 /system/lib64/libsigchain.so
71ebd06000-71ebd07000 rw-p 00001000 103:15 1644 /system/lib64/libsigchain.so
......
從上面的打印中可以看出妥色,com.android.email加載的動態(tài)鏈接庫均位于/system/lib64搪花。由此便可判斷com.android.email運行于64位環(huán)境。需要注意的是這個方法要root權(quán)限才能檢測嘹害。
4撮竿、檢測動態(tài)鏈接庫(*.so文件)
如果想要對一個.so文件的進行32/64位檢測,那么采用上一章節(jié)中的方法一就可以做到笔呀。但是幢踏,有native開發(fā)經(jīng)驗的讀者應該知道,64位系統(tǒng)中動態(tài)鏈接庫通常會同時存在32位和64位兩個版本许师,它們分別位于/system/lib和/system/lib64路徑中房蝉。所以,孤立地對某一個.so文件進行32位/64位檢測并沒有現(xiàn)實意義微渠,應該將其與加載該.so文件的App或Native進程作為一個整體來分析搭幻。
5、后語
本文分別對Android系統(tǒng)中App逞盆、Native進程和動態(tài)鏈接庫進行32/64位檢測的方法進行了介紹檀蹋,希望對大家的學習開發(fā)工作有所幫助。