android关机充电流程、充电画面显示 |
您所在的位置:网站首页 › ipad充电关机充电图片真实 › android关机充电流程、充电画面显示 |
一、Android正常开机流程、关机充电流程 在写这篇文章之前我们先看两个流程:正常开机流程,关机充电系统启动流程 1、正常开机流程,按开机键。 可大致分成三部分 (1)、OS_level:UBOOT、kenrel、init这三步完成系统启动; (2)、Android_level:这部分完成android部的初始化; (3)、Home Screen:这部分就是我们看到的launcher部分。 2、关机充电系统启动流程 与前面相比,这个流程只走到init这一部分,就没有往后走了,这部分我们会在后面的代码中分析。 ![]() 二、关机充电逻辑硬件逻辑 1、插入DC,charger IC从硬件上唤醒系统,相当于长按开机键开机。 下面这部分是charger IC连接系统的控制部分。 三、软件逻辑。 DC插入,其实相当于关机状态下“按开机键”开机。第一步要走UBOOT、kernel 、android init这一流程。 1、UBOOT UBOOT启动代码我们不在这里详细分析,这里我们只要注意二个问题: a:如何判断是DC插入; b:设定setenv("bootargs", "androidboot.mode=charger"),androidboot.mode这个参数相当重要,这个参数决定系统是正常启动、还是关机充电状态。 Uboot/board/samsung/smdk4212/smkd4212.c [cpp] view plain copy int board_late_init (void) { int keystate = 0; printf("check start mode\n"); if ((*(int *)0x10020800==0x19721212) || (*(int *)0x10020804==0x19721212) || (*(int *)0x10020808==0x19721212)) //(1)、检查是否有DC插入; { setenv ("bootargs", "");//(2)、没有DC插入; } else {//DC插入 int tmp=*(int *)0x11000c08; *(int *)0x10020800=*(int *)0x10020804=0x19721212; *(int *)0x11000c08=(tmp&(~0xc000))|0xc000; udelay(10000); if ((*(int *)0x11000c04 & 0x80)!=0x80 && INF_REG4_REG != 0xf) { setenv ("bootargs", "androidboot.mode=charger");//(3)、设定bootargs为charger状态 printf("charger mode\n"); } else { setenv ("bootargs", ""); } *(int *)0x11000c08=tmp; } #ifdef CONFIG_CPU_EXYNOS4X12 int charge_status=CheckBatteryLow();//(4)、检查电池电量; keystate=board_key_check();//(5)、检查按键状态; // fuse bootloader if(second_boot_info != 0) { boot_symbol=1; INF_REG2_REG =0x8; run_command(CONFIG_BOOTCMD_FUSE_BOOTLOADER, NULL); } if((INF_REG4_REG == 0xd)) { // reboot default char buf[10]; sprintf(buf, "%d", CONFIG_BOOTDELAY); setenv ("bootdelay", buf); setenv ("reserved", NULL); saveenv(); } else if((INF_REG4_REG == 0xe) || keystate == (0x1 | 0x2)) {//(6)、按键进入fastboot模式; // reboot bootloader boot_symbol=1; INF_REG2_REG =0x8; printf("BOOTLOADER - FASTBOOT\n"); setenv ("reserved", "fastboot"); setenv ("bootdelay", "0"); } else if((INF_REG4_REG == 0xf) || keystate == (0x1 | 0x2 | 0x4)) {//(7)、按键进入recovery模式; // reboot recovery printf("BOOTLOADER - RECOVERY\n"); boot_symbol=1; INF_REG2_REG =0x8; setenv ("reserved", CONFIG_BOOTCMD_RECOVERY); setenv ("bootdelay", "0"); } else if(keystate == (0x1 | 0x4) || second_boot_info != 0 || partition_check()) {//(8)、按键进入卡升级模式; // 2nd boot printf("BOOTLOADER - 2ND BOOT DEVICE\n"); boot_symbol=1; INF_REG2_REG =0x8; setenv ("bootcmd", CONFIG_BOOTCOMMAND); setenv ("reserved", CONFIG_BOOTCMD_FUSE_RELEASE); setenv ("bootdelay", "0"); } else {//(9)、正常启动; // normal case char buf[10]; sprintf(buf, "%d", CONFIG_BOOTDELAY); setenv ("bootdelay", buf); } INF_REG4_REG = 0; return 0; }(1)、检查是否有DC插入; [cpp] view plain copy if ((*(int *)0x10020800==0x19721212) || (*(int *)0x10020804==0x19721212) (*(int *)0x10020808==0x19721212))这部分检查寄存器的值。 (2)、没有DC插入; (3)、设定bootargs为charger状态 [cpp] view plain copy if ((*(int *)0x11000c04 & 0x80)!=0x80 && INF_REG4_REG != 0xf) { setenv ("bootargs", "androidboot.mode=charger");这是这部分的重点,如果能过寄存器判断是DC插入,把androidboot.mode设定为charger状态。 以下这部分根据需要加入,通过判断不同的情况进入不同的功能,如fastboot\revovery…………,这部分不做详细解释。 (4)、检查电池电量; 这个在正常开机状态下,如果检测电量太低,则不开机,这部分代码就不做分析。 (5)、检查按键状态; 我们这个平台有几种模式:fastboot\recovery\卡升级等…… (6)、按键进入fastboot模式; (7)、按键进入recovery模式; (8)、按键进入卡升级模式 (9)、正常启动; 2、kernel 这部分和正常启动是一样的。 3、init 前面所有的描述其实只有一点和正常启动不太一样,那就是在UBOOT中把androidboot.mode设定为charger状态,内核正常流程启动,然后到init时要对charger这种状态处理。 system\core\init\init.c [cpp] view plain copy int main(int argc, char **argv) { ……………… action_for_each_trigger("early-init", action_add_queue_tail); queue_builtin_action(wait_for_coldboot_done_action, "wait_for_coldboot_done"); queue_builtin_action(property_init_action, "property_init"); queue_builtin_action(keychord_init_action, "keychord_init"); queue_builtin_action(console_init_action, "console_init"); //(1)、显示initlogo.rle,也就是android第二张图片; queue_builtin_action(set_init_properties_action, "set_init_properties"); /* execute all the boot actions to get us started */ action_for_each_trigger("init", action_add_queue_tail); /* skip mounting filesystems in charger mode */ if (strcmp(bootmode, "charger") != 0) {//(2)、这里就是UBOOT中设定的bootmode,如果是charger模式,跳过下面初始化; action_for_each_trigger("early-fs", action_add_queue_tail); action_for_each_trigger("fs", action_add_queue_tail); action_for_each_trigger("post-fs", action_add_queue_tail); action_for_each_trigger("post-fs-data", action_add_queue_tail); } queue_builtin_action(property_service_init_action, "property_service_init"); queue_builtin_action(signal_init_action, "signal_init"); queue_builtin_action(check_startup_action, "check_startup"); if (!strcmp(bootmode, "charger")) {//(3)、如果为charger,则调用charger.c。 action_for_each_trigger("charger", action_add_queue_tail); } else { action_for_each_trigger("early-boot", action_add_queue_tail); action_for_each_trigger("boot", action_add_queue_tail); } …………………… }(1)、显示initlogo.rle,也就是android第二张图片; queue_builtin_action(console_init_action,"console_init");调用console_init_action [cpp] view plain copy static int console_init_action(int nargs, char **args) { int fd; char tmp[PROP_VALUE_MAX]; if (console[0]) { snprintf(tmp, sizeof(tmp), "/dev/%s", console); console_name = strdup(tmp); } fd = open(console_name, O_RDWR); if (fd >= 0) have_console = 1; close(fd); if( load_565rle_image(INIT_IMAGE_FILE) ) {//这里定义rle文件的名称#define INIT_IMAGE_FILE "/initlogo.rle" fd = open("/dev/tty0", O_WRONLY); if (fd >= 0) {//如果没有这张图片,就显示android字样,在屏幕左上角; const char *msg; msg = "\n" "\n" "\n" // console is 40 cols x 30 lines "\n" "\n" "\n" "\n" "\n" "\n" "\n" " A N D R O I D "; write(fd, msg, strlen(msg)); close(fd); } } return 0; }(2)、这里就是UBOOT中设定的bootmode,如果是charger模式,跳过下面初始化; [cpp] view plain copy /* skip mounting filesystems in charger mode */ if (strcmp(bootmode, "charger") != 0) { action_for_each_trigger("early-fs", action_add_queue_tail); action_for_each_trigger("fs", action_add_queue_tail); action_for_each_trigger("post-fs", action_add_queue_tail); action_for_each_trigger("post-fs-data", action_add_queue_tail); }(3)、如果为charger,则调用charger.c [cpp] view plain copy action_for_each_trigger("charger", action_add_queue_tail);我们在后面细分charger这部分。 4、charger.c 这部分就是我们充电部分,充电画面显示的实现。 system\core\charger\charger.c [cpp] view plain copy int main(int argc, char **argv) { ……………… klog_set_level(CHARGER_KLOG_LEVEL); dump_last_kmsg(); LOGI("--------------- STARTING CHARGER MODE ---------------\n"); gr_init(); gr_font_size(&char_width, &char_height); //(1)、初始化graphics,包括buf大小; ev_init(input_callback, charger);//(2)初始化按键; fd = uevent_open_socket(64*1024, true); if (fd >= 0) { fcntl(fd, F_SETFL, O_NONBLOCK); ev_add_fd(fd, uevent_callback, charger); } charger->uevent_fd = fd; coldboot(charger, "/sys/class/power_supply", "add");//(3)、创建/sys/class/power_supply结点,把socket信息通知应用层; ret = res_create_surface("charger/battery_fail", &charger->surf_unknown); if (ret surf_unknown = NULL; } for (i = 0; i batt_anim->num_frames; i++) {//(4)、这里是显示charger logo,res_create_surface显示图片函数; struct frame *frame = &charger->batt_anim->frames[i]; ret = res_create_surface(frame->name, &frame->surface); if (ret name); /* TODO: free the already allocated surfaces... */ charger->batt_anim->num_frames = 0; charger->batt_anim->num_cycles = 1; break; } } ev_sync_key_state(set_key_callback, charger); gr_fb_blank(true); charger->next_screen_transition = now - 1; charger->next_key_check = -1; charger->next_pwr_check = -1; reset_animation(charger->batt_anim); kick_animation(charger->batt_anim); event_loop(charger);//(5)、event_loop循环,电池状态,检测按键是否按下; return 0; }(1)、初始化graphics,包括buf大小 android/bootable/recovery/minui/graphics.c gr_init():minui/graphics.c[settty0 to graphic mode, open fb0],设制tty0为图形模式,打开fb0; [cpp] view plain copy int gr_init(void) { gglInit(&gr_context); GGLContext *gl = gr_context; gr_init_font(); gr_vt_fd = open("/dev/tty0", O_RDWR | O_SYNC); if (gr_vt_fd |
CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3 |