ImageVerifierCode 换一换
格式:DOCX , 页数:5 ,大小:18.16KB ,
资源ID:10478613      下载积分:15 金币
快捷下载
登录下载
邮箱/手机:
温馨提示:
快捷下载时,用户名和密码都是您填写的邮箱或者手机号,方便查询和重复下载(系统自动生成)。 如填写123,账号就是123,密码也是123。
特别说明:
请自助下载,系统不会自动发送文件的哦; 如果您已付费,想二次下载,请登录后访问:我的下载记录
支付方式: 支付宝    微信支付   
验证码:   换一换

加入VIP,免费下载
 

温馨提示:由于个人手机设置不同,如果发现不能下载,请复制以下地址【https://www.bdocx.com/down/10478613.html】到电脑端继续下载(重复下载不扣费)。

已注册用户请登录:
账号:
密码:
验证码:   换一换
  忘记密码?
三方登录: 微信登录   QQ登录  

下载须知

1: 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。
2: 试题试卷类文档,如果标题没有明确说明有答案则都视为没有答案,请知晓。
3: 文件的所有权益归上传用户所有。
4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
5. 本站仅提供交流平台,并不能对任何下载内容负责。
6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

版权提示 | 免责声明

本文(Android系统Recovery工作原理之使用updatezip升级过程分析七.docx)为本站会员(b****8)主动上传,冰豆网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。 若此文所含内容侵犯了您的版权或隐私,请立即通知冰豆网(发送邮件至service@bdocx.com或直接QQ联系客服),我们立即给予删除!

Android系统Recovery工作原理之使用updatezip升级过程分析七.docx

1、Android系统Recovery工作原理之使用updatezip升级过程分析七Android系统Recovery工作原理之使用update.zip升级过程分析(七) 置顶Android系统Recovery工作原理之使用update.zip升级过程分析(七)-Recovery服务的核心install_package函数分类:Andriod2012-04-16 13:554480人阅读评论(3)收藏举报android工作commandnullpathfile Android系统Recovery工作原理之使用update.zip升级过程分析(七)-Recovery服务的核心install_pack

2、age函数一、 Recovery服务的核心install_package(升级update.zip特有) 和Recovery服务中的wipe_data、wipe_cache不同,install_package()是升级update.zip特有的一部分,也是最核心的部分。在这一步才真正开始对我们的update.zip包进行处理。下面就开始分析这一部分。还是先看图例: 这一部分的源码文件位于:/gingerbread0919/bootable/recovery/install.c。这是一个没有main函数的源码文件,还是把源码先贴出来如下:cpp view plaincopy?/* * Copyr

3、ight (C) 2007 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the License); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http:/www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable

4、 law or agreed to in writing, software * distributed under the License is distributed on an AS IS BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #include <c

5、type.h> #include <errno.h> #include <fcntl.h> #include <limits.h> #include <sys/stat.h> #include <sys/wait.h> #include <unistd.h> #include common.h #include install.h #include mincrypt/rsa.h #include minui/minui.h #include minzip/SysUtil.h #include minzip/Zip.h

6、 #include mtdutils/mounts.h #include mtdutils/mtdutils.h #include roots.h #include verifier.h #define ASSUMED_UPDATE_BINARY_NAME META-INF/com/google/android/update-binary #define PUBLIC_KEYS_FILE /res/keys / If the package contains an update binary, extract it and run it. static int try_update_binar

7、y(const char *path, ZipArchive *zip) const ZipEntry* binary_entry = mzFindZipEntry(zip, ASSUMED_UPDATE_BINARY_NAME); if (binary_entry = NULL) mzCloseZipArchive(zip); return INSTALL_CORRUPT; char* binary = /tmp/update_binary; unlink(binary); int fd = creat(binary, 0755); if (fd < 0) mzCloseZipArch

8、ive(zip); LOGE(Cant make %sn, binary); return 1; bool ok = mzExtractZipEntryToFile(zip, binary_entry, fd); close(fd); mzCloseZipArchive(zip); if (!ok) LOGE(Cant copy %sn, ASSUMED_UPDATE_BINARY_NAME); return 1; int pipefd2; pipe(pipefd); / When executing the update binary contained in the package, th

9、e / arguments passed are: / / - the version number for this interface / / - an fd to which the program can write in order to update the / progress bar. The program can write single-line commands: / / progress <frac> <secs> / fill up the next <frac> part of of the progress bar / ove

10、r <secs> seconds. If <secs> is zero, use / set_progress commands to manually control the / progress of this segment of the bar / / set_progress <frac> / <frac> should be between 0.0 and 1.0; sets the / progress bar within the segment defined by the most / recent progress comm

11、and. / / firmware <hboot|radio> <filename> / arrange to install the contents of <filename> in the / given partition on reboot. / / (API v2: <filename> may start with PACKAGE: to / indicate taking a file from the OTA package.) / / (API v3: this command no longer exists.) / / u

12、i_print <string> / display <string> on the screen. / / - the name of the package zip file. / char* args = malloc(sizeof(char*) * 5); args0 = binary; args1 = EXPAND(RECOVERY_API_VERSION); / defined in Android.mk args2 = malloc(10); sprintf(args2, %d, pipefd1); args3 = (char*)path; args4 =

13、 NULL; pid_t pid = fork(); if (pid = 0) close(pipefd0); execv(binary, args); fprintf(stdout, E:Cant run %s (%s)n, binary, strerror(errno); _exit(-1); close(pipefd1); char buffer1024; FILE* from_child = fdopen(pipefd0, r); while (fgets(buffer, sizeof(buffer), from_child) != NULL) char* command = strt

14、ok(buffer, n); if (command = NULL) continue; else if (strcmp(command, progress) = 0) char* fraction_s = strtok(NULL, n); char* seconds_s = strtok(NULL, n); float fraction = strtof(fraction_s, NULL); int seconds = strtol(seconds_s, NULL, 10); ui_show_progress(fraction * (1-VERIFICATION_PROGRESS_FRACT

15、ION), seconds); else if (strcmp(command, set_progress) = 0) char* fraction_s = strtok(NULL, n); float fraction = strtof(fraction_s, NULL); ui_set_progress(fraction); else if (strcmp(command, ui_print) = 0) char* str = strtok(NULL, n); if (str) ui_print(%s, str); else ui_print(n); else LOGE(unknown c

16、ommand %sn, command); fclose(from_child); int status; waitpid(pid, &status, 0); if (!WIFEXITED(status) | WEXITSTATUS(status) != 0) LOGE(Error in %sn(Status %d)n, path, WEXITSTATUS(status); return INSTALL_ERROR; return INSTALL_SUCCESS; / Reads a file containing one or more public keys as produced

17、 by / DumpPublicKey: this is an RSAPublicKey struct as it would appear / as a C source literal, eg: / / 64,0xc926ad21,1795090719,.,-695002876,-857949815,.,1175080310 / / (Note that the braces and commas in this example are actual / characters the parser expects to find in the file; the ellipses / in

18、dicate more numbers omitted from this example.) / / The file may contain multiple keys in this format, separated by / commas. The last key must not be followed by a comma. / / Returns NULL if the file failed to parse, or if it contain zero keys. static RSAPublicKey* load_keys(const char* filename, i

19、nt* numKeys) RSAPublicKey* out = NULL; *numKeys = 0; FILE* f = fopen(filename, r); if (f = NULL) LOGE(opening %s: %sn, filename, strerror(errno); goto exit; int i; bool done = false; while (!done) +*numKeys; out = realloc(out, *numKeys * sizeof(RSAPublicKey); RSAPublicKey* key = out + (*numKeys - 1)

20、; if (fscanf(f, %i , 0x%x , %u, &(key->len), &(key->n0inv), &(key->n0) != 3) goto exit; if (key->len != RSANUMWORDS) LOGE(key length (%d) does not match expected sizen, key->len); goto exit; for (i = 1; i < key->len; +i) if (fscanf(f, , %u, &(key->ni) != 1) go

21、to exit; if (fscanf(f, , %u, &(key->rr0) != 1) goto exit; for (i = 1; i < key->len; +i) if (fscanf(f, , %u, &(key->rri) != 1) goto exit; fscanf(f, ); / if the line ends in a comma, this file has more keys. switch (fgetc(f) case ,: / more keys to come. break; case EOF: done = true

22、; break; default: LOGE(unexpected character between keysn); goto exit; fclose(f); return out; exit: if (f) fclose(f); free(out); *numKeys = 0; return NULL; int install_package(const char *path) ui_set_background(BACKGROUND_ICON_INSTALLING); ui_print(Finding update package.n); ui_show_indeterminate_p

23、rogress(); LOGI(Update location: %sn, path); if (ensure_path_mounted(path) != 0) LOGE(Cant mount %sn, path); return INSTALL_CORRUPT; ui_print(Opening update package.n); int numKeys; RSAPublicKey* loadedKeys = load_keys(PUBLIC_KEYS_FILE, &numKeys); if (loadedKeys = NULL) LOGE(Failed to load keysn

24、); return INSTALL_CORRUPT; LOGI(%d key(s) loaded from %sn, numKeys, PUBLIC_KEYS_FILE); / Give verification half the progress bar. ui_print(Verifying update package.n); ui_show_progress( VERIFICATION_PROGRESS_FRACTION, VERIFICATION_PROGRESS_TIME); int err; err = verify_file(path, loadedKeys, numKeys)

25、; free(loadedKeys); LOGI(verify_file returned %dn, err); if (err != VERIFY_SUCCESS) LOGE(signature verification failedn); return INSTALL_CORRUPT; /* Try to open the package. */ ZipArchive zip; err = mzOpenZipArchive(path, &zip); if (err != 0) LOGE(Cant open %sn(%s)n, path, err != -1 ? strerror(e

26、rr) : bad); return INSTALL_CORRUPT; /* Verify and install the contents of the package. */ ui_print(Installing update.n); return try_update_binary(path, &zip); 下面顺着上面的流程图和源码来分析这一流程: ensure_path_mount():先判断所传的update.zip包路径所在的分区是否已经挂载。如果没有则先挂载。 load_keys():加载公钥源文件,路径位于/res/keys。这个文件在Recovery镜像的根文件系

27、统中。 verify_file():对升级包update.zip包进行签名验证。 mzOpenZipArchive():打开升级包,并将相关的信息拷贝到一个临时的ZipArchinve变量中。这一步并未对我们的update.zip包解压。 try_update_binary():在这个函数中才是对我们的update.zip升级的地方。这个函数一开始先根据我们上一步获得的zip包信息,以及升级包的绝对路径将update_binary文件拷贝到内存文件系统的/tmp/update_binary中。以便后面使用。 pipe():创建管道,用于下面的子进程和父进程之间的通信。 fork():创建子进程

28、。其中的子进程主要负责执行binary(execv(binary,args),即执行我们的安装命令脚本),父进程负责接受子进程发送的命令去更新ui显示(显示当前的进度)。子父进程间通信依靠管道。 其中,在创建子进程后,父进程有两个作用。一是通过管道接受子进程发送的命令来更新UI显示。二是等待子进程退出并返回INSTALL SUCCESS。其中子进程在解析执行安装脚本的同时所发送的命令有以下几种: progress <frac> <secs>:根据第二个参数secs(秒)来设置进度条。 set_progress <frac>:直接设置进度条,frac取值在0.0到0.1之间。 firmware <”hboot”|”radio”><filename>:升级firmware时使用,在API V3中不再使用。 ui_print <string>:在屏幕上显示字符串,即打印更新过程。 execv(binary,args)的作用就是去执行binary程序,这个程序的实质就是去解析update.zip包中的updater-script脚本中的命令并执行。由此,Recovery服务就进入了实际安装update.zip包的过程。 下一篇继续分析使用update-binary解析并执行updater-script的过程。

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1