1. 程式人生 > >android 手機中boot.img基址的計算方法(zz)

android 手機中boot.img基址的計算方法(zz)

boot.img基址 base的計算方法

如果您看這個帖子,沒有耐心的話,我只能對你說,出現任何問題都是你自己的錯,有點耐心繼續 看吧,雖然在文章最後有點邪惡,大家原諒一下!我在工具包中給了一個引數,對於我的GT540肯定沒有什麼問題,但是對於其他手機我不敢保證,所以可能還 需您自己計算,或者使用版區前輩得到的數值!如果您做完之後刷回到手機之後會卡在開機介面,螢幕一閃一閃啊黑屏啊之類的症狀層出不窮,普遍有兩種可能。
一、boot.img是加過密的。各位手機出產的公司,在做ROM的時候,以他們獨自的加密演算法,對整個檔案進行CRC驗算,然後將驗算值新增到 boot.img的最末尾。刷機的時候,手機的硬體BIOS就像一名盡職的士兵,對此進行驗算,對不上口令的,那麼對不起,請君離開,不離開我報警了~~ 呃,報不了警,那反正我不讓你進門~~
二、boot.img還有一個重要的引數,基址 base,用於告訴手機從哪個地址開始,是準備給記憶體盤的入口,哪個地址是給kernel的入口。如果你對不上號,對不起,不能非法入室的。
如果是第一種,那隻能望風而逃,罷手了。
各種查閱,終於發現在ROM的boardconfig.h中存在地址偏移的define。雖然本人手機的ROM中不存在這檔案,但各android系統這個偏移是通用的,一般沒吃錯藥不會去改。
偏移DEFINE如下:

  1. #define PHYSICAL_DRAM_BASE 0x00200000<!--IWMS_AD_BEGIN--> //基址,各不相同,我們的目的是為了獲得這個基址,但由於沒有ROM原始碼,這貌似是不可能的。<!--IWMS_AD_END-->#define KERNEL_ADDR (PHYSICAL_DRAM_BASE + 0x00008000)#define RAMDISK_ADDR (PHYSICAL_DRAM_BASE + 0x01000000)#define TAGS_ADDR (PHYSICAL_DRAM_BASE + 0x00000100)#define NEWTAGS_ADDR (PHYSICAL_DRAM_BASE + 0x00004000)

複製程式碼

還記得WIKI中有這句話吧?For Nexus One : Add --base 0x20000000 to mkbootimg command-line. 翻譯一下,如果是nexus one手機,那麼需要在mkbootimg命令中加入 --base 0x20000000。。現在是不是很熟了?原來基址寫在這裡,mkbootimg會自動為你加入偏移量,並寫入boot.img。。
好吧,我們現在需要知道,這些值是在哪個位置的。
為什麼需要呢?在第上面,我們已經知道了偏移量了,那麼如果我們再從官方ROM的boot.img中獲取 kernel_addr,再用kernel_addr -偏移量0x00008000,不就可以得出基址了嗎?
沒轍,需要知道bootimg工具把它們寫到哪了,只能檢視mkbootimg的原始碼(幸好bootimg作為一個典型的LINUX工具,是開源的。若換成WIN,哥就真悲情了)。
各種查詢,找到bootimg.c檔案,看吧。
header + padding + kernel + padding + ramdisk + padding + ...(padding是補全,還記得上面所說的,一個盒子裝10張卡片,11張卡片需要幾個盒子的事情吧?第二個盒子由於只放了一張卡片,所以需要9張空白卡片來填充位置,即padding)
4 * 2, magic,固定為"ANDROID!"
4 * 1, kernel長度,小端unsigned型別
4 * 1, kernel地址,應為base + 0x00008000
4 * 1, ramdisk長度,小端unsigned
4 * 1, ramdisk地址,應為base + 0x01000000
4 * 1, second stage長度,小端unsigned,為0
4 * 1, second stage地址,應為base + 0x00f00000
4 * 1, tags地址,應為base + 0x00000100
4 * 1, page大小,小端unsigned, 為2048或者4096
4 * 2, 未使用,固定為0x00
4 * 4, 板子名字,一般為空
4 * 128, 核心命令引數,一大串
4 * 8, id,不知道啥玩意,0x00
給親愛的16進位制帖張圖吧,看圖說話,下圖是N600+官方2.1ROM的16進製圖片,如下:



從圖中我們可以知道:
41 4E 44 52 4F 49 44 21 就是Magic Number ,內容是固定的ANDROID!。一一對應
kernel_size就是0x00237470。注意,小端讀法。是Byte內,順讀,整個型別中,逆讀。故70 74 23 00 的確切數字是0x 00 23 74 70
kernel_addr即0x 03008000。這時有人就問了,那用這個減去上面獲取的kernel偏移,0x00008000,那麼base是不是0x030000000?好了,我知道了,我就用--base 0x03000000來打包。那麼,恭喜你,在N600上,這樣寫依然是不能啟動的,為什麼,請繼續看。
ramdisk_size是:B9 66 03 00 -->0x 00 03 66 B9。
ramdisk_addr即00 00 A0 03 -->0x 03 A0 00 00。減去偏移0x01000000,base=0x02a00000
second_stage size:00000000
second_stage addr:00 00 90 03-->0x 03 90 00 00.減去偏移0x00f00000,base=0x02a00000
tags_addr:00 01 a0 02-->0x 02a00100.減去偏移0x00000100,base=0x02a00000
page_size:00 80 -->0x0800.這是頁長。記得我前面說過的頁長一般都為1K(1024)的整數倍吧?此處頁長是0x0800,轉為十進位制,則是2048

好吧,我們來看下base吧,嗯,kernel的base是0x03000000,ramdisk和second_stage及tags_addr的基址都一樣啊,是...是0x02a000000。。我了個去~~4個base竟然有不一樣的~是的,我當時就是這麼罵的。
我就想,還好本人閒著無事算了4個base,如果有隻算第1個,然後用0x03000000來打包的,基本就是悲劇的結果,可能還摸不著頭腦,以為這個boot.img是CRC校驗的,而非基址弄錯。
好吧,以少數服從多數的原則,我們在打包的時候,把基址填為0x02a00000。然後把第一個地址kernel_addr,手動修正。
那麼,正確的命令如下:

  1. bootimg ramdisk |gzip >ramdisk-new.gzmkbootimg --kernel boot.img-kernel --ramdisk ramdisk-new.gz --base 0x02a00000 -o boot.img

複製程式碼

然後用ghex2開啟boot.img,忽略前面的4*2Byte,41 4E 44 52 4F 49 44 21,這是magic number,固定不變的。
再跳過4*1Byte,在我這是70 74 23 00。這是kernel_size,程式生成,不需要手動改。
其後的4*1Byte才是kernel_addr,現在是00 80 A0 02,修改成 00 80 00 03。儲存之。
好了,將它放到刷機包目錄中,開啟刷機工具,刷之。快樂的啟動吧。

相關推薦

android 手機boot.img基址計算方法zz

boot.img基址 base的計算方法 如果您看這個帖子,沒有耐心的話,我只能對你說,出現任何問題都是你自己的錯,有點耐心繼續 看吧,雖然在文章最後有點邪惡,大家原諒一下!我在工具包中給了一個引數,對於我的GT540肯定沒有什麼問題,但是對於其他手機我不敢保證,所以可能還

eclipsejava程式碼格式化設定方法 zz

由於之前習慣了Java的程式碼格式化樣式,即如下圖1的第一種程式碼格式,而看第二種程式碼格式時感覺程式碼很亂,總找不到“{ }”對稱的感覺。eclipse自動格式化程式碼的快捷方式是Ctrl+Shift+F ,下面將通過設定eclipse來達到第一種程式碼樣式。

python關於操作時間的方法:使用datetime模塊

log time模塊 bsp lib .py nth mon target ear 使用datetime模塊來獲取當前的日期和時間 1 import datetime 2 i=datetime.datetime.now() 3 print ("當前的日期和時間是%

編寫Android.mk的LOCAL_SRC_FILES的終極技巧

jni 優雅 -1 窗口 name 截取 rds detail software 轉自:http://blog.csdn.net/fu_zk/article/details/12836431 問題的引入 在使用NDK編譯C/C++項目的過程中,免不了要編寫Android.m

java 專案使用 mongodb的基礎方法

一、準備工作 1、 首先,下載mongoDB對Java支援的驅動包 2、 下面建立一個JavaProject工程,匯入下載下來的驅動包。即可在Java中使用mongoDB,目錄如下: 二、Java操作MongoDB示例 在本示例之前你需要啟動mong

css新增螢幕自適應方法rem

css中新增螢幕自適應方法(rem) 只需要在公共css檔案中新增下面程式碼:設計稿以750px,基礎字型為20px為例,相容性高,使用過程中px轉化為rem即可 /*豎屏*/ @media screen and (max-aspect-ratio: 13/9){ html {font-si

Android開發——RecyclerView特性以及基本使用方法

0.  前言隨著Android的發展,雖然ListView依舊重要,但RecyclerView確實越來越多的被大家使用。但顯然並不能說RecyclerView就一定優於ListView,而是應該根據不同

Android Studio配置及使用OpenCV示例

Android Studio配置及使用OpenCV前言:最近在做專案移植,專案較大,在Eclipse中配置的Jni及OpenCV環境沒任何問題,但是遷移到Studio中就問題一大堆,網上也找了一些資料參考及學習,很感謝前人留下的總結及經驗。關於在AS中使用jni及配置Open

快速實現android手機端多人視訊會議直播免費

reechatsdk為所有基於網際網路的實時通訊需求使用者提供了完整的解決方案,包括實時音訊/視訊互動、原生sdk低延遲廣播,相容第三方rtmp和hls直播方案 解壓壓縮包,並把reechat.jar和其他*.so匯入目標android工程(Add as Library

android螢幕休眠和喚醒兩種方法newWakeLock

1.WakeLock主要程式碼如下: PowerManager pm = (PowerManager)getSystemService(Context.POWER_SERVICE); wakeLock = pm.newWakeLock(PowerManager.PARTIA

Android 開發一些不得不知的坑

如何正確的在ScrollView裡做巢狀 日常開發中,經常會遇到ScrollView巢狀ListView,GridView或者是ViewPager,更有甚者是ScrollView巢狀ScrollView,這樣一來必然會導致一系列的問題,比如ListView顯示

關於mysql新增新使用者名稱的方法許可權

mysql新增使用者方法 建立資料庫gamesp create database gamesp; 新增使用者 grant all on 資料庫名.* to 使用者名稱@localhost identified by '密碼'; grant all on gam

Android手機通過藍芽向目標裝置ble傳輸訊息

最近一直在研究兩個手機用過藍芽通訊,參考了部分網上程式碼,到最後也沒弄清楚。(樓主是學渣......)然後有一個專案要用手機通過藍芽控制三色燈,我就隨意寫了一下客戶端的應用程式,而且沒有測試,通過部落格記錄一下方便以後使用測試。閒話不多說。開始----參考部分網上程式碼:附上

定點陣圖像畫素座標的方法matlab

1. ginput [x,y] = ginput(n),n為你想選的點的個數,滑鼠點的那些點的橫座標和縱座標就會儲存到[x,y]中 或者直接輸入ginput,最後以回車結尾 2. impixelinfo(更為方便) 顯示影象後,直接在命令視窗輸入impixelinfo敲回車

Android開發Notification通知欄的基本用法總結

1、Notification的基本使用流程 狀態通知欄主要涉及到2個類:Notification 和NotificationManagerNotification:通知資訊類,它裡面對應了通知欄的各個屬性NotificationManager:是狀態列通知的管理類,負責發通知

[譯]Android防止記憶體洩漏的八種方法

原文網址:http://www.jianshu.com/p/c5ac51d804fa?hmsr=toutiao.io&utm_medium=toutiao.io&utm_source=toutiao.io 原文地址。 在上一篇Android記憶體洩漏的八

Android手機通過wifi進行數據傳輸

int apk nal com urn contacts views parent world 源文件5 main.xml <?xml version="1.0" encoding="utf-8"?> <LinearLayoutxmln

[日更-2019.5.24、25、26] Android系統的Binder通訊機制分析--servicemanager

宣告 其實對於Android系統Binder通訊的機制早就有分析的想法,記得去年6、7月份Mr.Deng離職期間約定一起對其進行

Android: Android Studio簽名打包的兩種方式zz

信息 rda pan 相同 prop .cn 一個 一次 ack 註:給我們自己開發的app簽名,就代表著我自己的版權,以後要進行升級,也必須要使用相同的簽名才行。簽名就代表著自己的身份(即keystore),多個app可以使用同一個簽名。如果不知道簽名是啥意思,請自行百度

PHP一種sign計算方法

get func return fun urn style 輸出 class pos 一言不合上代碼......... 1 <?php 2 function getsign($data,$key){ 3 $key=MD5("KEY_".$key."_K"); 4 $