安卓开机过程
- 格式:docx
- 大小:28.79 KB
- 文档页数:7
安卓开机过程描述开机过程对任何电子类产品终端来说是很重要的,安卓终端也是如此。
基于安卓4.x系统,描述开机过程中被调用的文件,重点描述:1. 开机动画是如何控制的2. 是否能实现开机音效,如是,指明音效文件的位置3. 开机视频能否实现,如是,指明视频的格式要求及存放位置安卓开机过程描述一,描述开机过程中被调用的文件1.系统引导bootloader1) 源码:bootable/bootloader/*2) 说明:加电后,CPU将先执行bootloader程序,此处有三种选择a) 开机按Camera+Power启动到fastboot,即命令或SD卡烧写模式,不加载内核及文件系统,此处可以进行工厂模式的烧写b) 开机按Home+Power启动到recovery模式,加载recovery.img,recovery.img包含内核,基本的文件系统,用于工程模式的烧写c) 开机按Power,正常启动系统,加载boot.img,boot.img包含内核,基本文件系统,用于正常启动手机(以下只分析正常启动的情况)2. 内核kernel1) 源码:kernel/*2) 说明:kernel由bootloader加载3. 文件系统及应用init1) 源码:system/core/init/*2) 配置文件:system/rootdir/init.rc,3) 说明:init是一个由内核启动的用户级进程,它按照init.rc中的设置执行:启动服务(这里的服务指linux底层服务,如adbd提供adb支持,vold提供SD卡挂载等),执行命令和按其中的配置语句执行相应功能4. 重要的后台程序zygote1) 源码:frameworks/base/cmds/app_main.cpp等2) 说明:zygote是一个在init.rc中被指定启动的服务,该服务对应的命令是/system/bin/app_processa) 建立Java Runtime,建立虚拟机b) 建立Socket接收ActivityManangerService的请求,用于Fork应用程序 c) 启动System Server5. 系统服务system server1) 源码:frameworks/base/services/java/com/android/server/SystemServer.java 2) 说明:被zygote启动,通过System Manager管理android的服务(这里的服务指frameworks/base/services下的服务,如卫星定位服务,剪切板服务等)6. 桌面launcher1) 源码:ActivityManagerService.java为入口,packages/apps/launcher*实现2) 说明:系统启动成功后SystemServer使用xxx.systemReady()通知各个服务,系统已经就绪,桌面程序Home就是在ActivityManagerService.systemReady()通知的过程中建立的,最终调用startHomeActivityLocked()启launcher7. 解锁1) 源码:frameworks/policies/base/phone/com/android/internal/policy/impl/*lock*2) 说明:系统启动成功后SystemServer调用wm.systemReady()通知WindowManagerService,进而调用PhoneWindowManager,最终通过LockPatternKeyguardView 显示解锁界面,跟踪代码可以看到解锁界面并不是一个Activity,这是只是向特定层上绘图,其代码了存放在特殊的位置8. 开机自启动的第三方应用程序1) 源码:frameworks/base/services/java/com/android/server/am/ActivityManagerService.java 2) 说明:系统启动成功后SystemServer调用ActivityManagerNative.getDefault().systemReady()通知ActivityManager启动成功,ActivityManager会通过置变量mBooting,通知它的另一线程,该线程会发送广播android.intent.action.BOOT_COMPLETED以告知已注册的第三方程序在开机时自动启动。
9. 总结综上所述,系统层次关于启动最核心的部分是zygote(即app_process)和system server,zygote 它负责最基本的虚拟机的建立,以支持各个应用程序的启动,而system server用于管理android后台服务,启动步骤及顺序二. 开机动画是如何控制的Android 开机会出现3个画面:1. Linux 系统启动,出现Linux小企鹅画面(reboot)(Android 1.5及以上版本已经取消加载图片);2. Android平台启动初始化,出现"A N D R I O D"文字字样画面;3. Android平台图形系统启动,出现含闪动的ANDROID字样的动画图片(start)。
1、开机图片(Linux小企鹅) (Android 1.5及以上版本已经取消加载图片);Linux Kernel引导启动后,加载该图片。
logo.c中定义nologo,在fb_find_logo(int depth)函数中根据nologo的值判断是否需要加载相应图片2、开机文字("A N D R I O D")Android 系统启动后,init.c中main()调用load_565rle_image()函数读取/initlogo.rle(一张565 rle压缩的位图),如果读取成功,则在/dev/graphics/fb0显示Logo图片;如果读取失败,则将/dev/tty0设为TEXT模式,并打开/dev/tty0,输出文本“A N D R I O D”字样。
3、开机动画(闪动的ANDROID字样的动画图片)Android 1.5版本:Android的系统登录动画类似于Windows系统的滚动条,是由前景和背景两张PNG图片组成,这两张图片存在于手机或模拟器/system/framework /framework-res.apk文件当中,对应原文件位于/frameworks/base/core/res/assets/images/。
前景图片(android-logo-mask.png)上的Android文字部分镂空,背景图片(android-logo-shine.png)则是简单的纹理。
系统登录时,前景图片在最上层显示,程序代码(BootAnimation.android())控制背景图片连续滚动,透过前景图片文字镂空部分滚动显示背景纹理,从而实现动画效果。
三. 是否能实现开机音效,如是,指明音效文件的位置Android开机音效:由于动画是在BootAnimation播放的,所以我们的声音肯定也在这个类中做!其源码目录在framworks/base/data/sounds,可以对源码进行编辑,修改等途径实现自定义音效!四. 开机视频能否实现,如是,指明视频的格式要求及存放位置Android自定义开机视频是可以实现的主要以.MP4格式和.3gp格式为主。
路径可以在视频播放类 VideoPlayer.java中配置修改具体代码如下:1 首先配置AndroidManifest.xml 注册一个开机服务广播主要代码如下:<receiver android:name=".BootBroadCastReceiver"><intent-filter><action android:name="android.intent.action.BOOT_COMPLETED" /><category android:name="UNCHER" /> </intent-filter></receiver>权限:<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>2广播接受类:public class BootBroadCastReceiver extends BroadcastReceiver {public static final String ACTION = "android.intent.action.BOOT_COMPLETED";@Overridepublic void onReceive(Context context, Intent intent) {if (intent.getAction().equals(ACTION)) {Log.i("Videoplayer", "onReceive");Intent myintent = new Intent(context, Videoplayer.class);myintent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);//这个一定要加否则无法启动activitycontext.startActivity(myintent);}}}3 就是视频播放类了 Videoplayer.javapackage .sy;import java.io.File;import java.io.FilenameFilter;import java.util.List;import android.app.Activity;import android.media.AudioManager;import android.media.MediaPlayer;import android.media.MediaPlayer.OnCompletionListener;import android.media.MediaPlayer.OnPreparedListener;import android.os.Bundle;import android.os.Environment;import android.util.Log;import android.view.SurfaceHolder;import android.view.SurfaceView;import android.view.View;import android.view.Window;import android.view.WindowManager;import android.view.SurfaceHolder.Callback;import android.widget.EditText;import android.widget.Toast;public class Videoplayer extends Activity implements OnCompletionListener { public static final String TAG = "Videoplayer";private String path;private MediaPlayermediaPlayer;private SurfaceViewsurfaceView;private File[] mVideoFiles;private int index = 0;@Overridepublic void onCreate(Bundle savedInstanceState) {super.onCreate(savedInstanceState);// 全屏显示requestWindowFeature(Window.FEATURE_NO_TITLE);getWindow().setFlags(youtParams.FLAG_FULLSCREEN, youtParams.FLAG_FULLSCREEN);setContentView(yout.main);// 播放器mediaPlayer = new MediaPlayer();// 每次播完后监听事件mediaPlayer.setOnCompletionListener(this);// 遍历SD卡下的视频文件/** String url = Environment.getExternalStorageDirectory()* .getAbsolutePath() + File.separatorChar + "目录名";*/String url = Environment.getExternalStorageDirectory().getAbsolutePath();Log.i(TAG, url);getFiles(url);surfaceView = (SurfaceView) this.findViewById(R.id.surfaceView);// 把输送给surfaceView的视频画面,直接显示到屏幕上,不要维持它自身的缓冲区 surfaceView.getHolder().setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);// 屏幕尺寸surfaceView.getHolder().setFixedSize(176, 144);// 保持屏幕唤醒状态surfaceView.getHolder().setKeepScreenOn(true);// 回调SurfaceViewCallback对象surfaceView.getHolder().addCallback(new SurfaceCallback());}private final class SurfaceCallback implements Callback {public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {}public void surfaceCreated(SurfaceHolder holder) {play();}public void surfaceDestroyed(SurfaceHolder holder) {onStop();}}@Overrideprotected void onStop() {if (mediaPlayer != null) {if (mediaPlayer.isPlaying())mediaPlayer.stop();}releaseMediaPlayer();super.onStop();}@Overrideprotected void onDestroy() {releaseMediaPlayer();super.onDestroy();}// 释放播放器资源private void releaseMediaPlayer() {if (mediaPlayer != null) {Log.i(TAG, "Release MediaPlayer");mediaPlayer.release();mediaPlayer = null;}}// 封装播放方法private void play() {if (mVideoFiles == null || mVideoFiles.length == 0) {Toast.makeText(this.getApplicationContext(), "No video files", Toast.LENGTH_LONG).show();return;}try {path = mVideoFiles[index].getAbsolutePath();Log.i(TAG, "onplaying==" + path);index++;if (index == mVideoFiles.length)index = 0;// 播放器重置mediaPlayer.reset();// 文件路径mediaPlayer.setDataSource(path);// 设置Video影片以SurfaceHolder播放mediaPlayer.setDisplay(surfaceView.getHolder());// 设置播放器播放数据流类型mediaPlayer.setAudioStreamType(AudioManager.STREAM_MUSIC);// 缓冲mediaPlayer.prepare();mediaPlayer.start();} catch (Exception e) {e.printStackTrace();}}@Overridepublic void onCompletion(MediaPlayermp) {Log.i(TAG, "onCompletion");play();}// 遍历指定目录下的视频文件private void getFiles(String url) {try {File file = new File(url);mVideoFiles = file.listFiles(new FilenameFilter() {@Overridepublic boolean accept(File dir, String name) {return name.endsWith(".mp4") || name.endsWith(".3gp");}});Log.i("Videoplayer", "files.length==" + mVideoFiles.length);} catch (Exception e) {Log.i("Videoplayer", "not find file !");}}}。