Android 如何从应用深入到Framework (一)
今天,明哥想跟大家聊聊,如何从应用开发,转向Framework开发。
系统应用开发,现在来说,已经开始脱离系统,单独拿出来开发,系统定制接口,已提供给应用调用,用来增强功能。
原生的桌面,拨号,设置,已经没法做出差异化优势,因此都费尽心机,来进行应用深度开发。
对于之前维护系统应用模块的人来讲,修修补补,真的没有什么成长。每天的工作来说,没有很深的技术壁垒,很容易被别人攻陷。
比如设置,比如联系人,在小的改动,修改故障的时候,没有非常高的要求,做过应用开发的,都可以过来参合一脚,改改问题。而让一个应用开发得去修改系统接口,估计改的心累,并且犹豫不决。
技术壁垒,也便是自己的竞争优势。只有顽强的技术能力,并持之以恒的学习,扩充自己的深度,广度,那么你的位置则牢不可破,不会轻易被替代。
这节,明哥从自身的角度,讲讲系统应用开发,该如何向Framework进军,进行学习,掌握更加核心的技术。
这里有人会说,我做应用风生水起,也游刃有余,不比你们做系统Framework的差,何必把系统应用开发的贬的一文不值。这里要说一下,文中没有这个意思,你的应用做的有声有色,赚的盆满钵满,这里肯定有其因素。比如它的性能,它的界面绚丽,百变主题。或者它有智能识别,等等。这些都叫做差异化产品,有其亮点,特色,才能杀出重围。
而系统应用开发,我这里偏向于手机整机开发中的OEM厂商,主要做出系统,能够保证功能正常,不会花费大量人力精力去做应用深度开发,系统重构的。这里主要会以追求速度,同时满足客户的硬件要求,比如多个霍尔器件,多个温度传感器,多个皮套功能,等等,但很少去大量改动应用架构,以免影响最终量产。
以上,就是特指的这个应用开发人员。随后,我来讲讲,Framework需要掌握哪些知识呢?
①操作系统。
熟悉我的人都知道,我特喜欢把这个放在第一位,原因很简单,它确实支撑了我随后的所有知识根基,让我能够从容不迫的,将一个个系统拆解出来。
我们就拿安卓来讲,启动过程
跟linux如出一辙,所以很容易迁移过来,同时,差异化的init进程,完成初始任务,创建安卓世界的孵化器,既然这里要进入安卓世界,而安卓世界的基础语言是java,那么就需要一个Java虚拟机,于是孵化器就要构造一个虚拟机,用来解析执行Java编译出来的字节流。而孵化器本身是由c cpp语言实现,于是Java虚拟机就是由c cpp语言写出来的,linux操作系统也是c(还有一些汇编)写出来的,于是Java虚拟机运行的Java语言,就需要跟c cpp打交道,于是就有了JNI。
孵化器做了几件事情:
1完成Java虚拟机的构造
2完成JNI对接Java与c的桥梁
3加载公共的共享库
4等待别人给它发消息,创建新进程
在这期间,孵化器要做一件事情,便是创建system_server ,这个进程要做什么呢?我们创建了一个可以运行Java的虚拟机,这时我们就要提供一堆系统接口,用来协助应用开发,比如请求网络啦,比如创建界面啦,比如定位啦,获取存储卡啦,等等支持,方便用户开发功能。一个平台的好坏,往往取决于它的功能是否强大,是否有丰富的技术文档,以及开发调试工具。
所以就有了一堆线程,比如AMS,WMS,PMS,BT,WIFI,这些都可以在/proc/{ system_server_pid}/ tast找到记录。
有了这些线程,那么我们就可以轻松的去实现很多功能啦。这时我们就要配套的开发工具,比如AS编辑器,可以编辑,编译出来APK,安装到手机运行。
关于操作系统,需要掌握的知识点为:
1进程,线程概念
2互斥,死锁机制与原理,如何避免死锁
3内存管理机制,虚拟内存
4静态库与动态库的区别
5进程之间的内存屏障,如何通信(IPC)
6binder的通信优势
这里先想到这些,注意不是要完成懂所有机制,要的是整体理解即可。如下问题,请思考下,看是否能够答上来。
1 如果我写了一个应用,名字叫做,com.codegg.home 在主activity里面,加载一个布局,layout_main. xml,布局里面写入了一个TextView,那么我想调试这个TextView,要在com.codegg.home这个进程下断点,还是在system_server进程下断点呢?如果是想调试ActivityThread. java的话?应该在哪个进程下断点呢?
以上答案,都是com.codegg.home下断点,原因是这两个当前的运行进程,都是在com.codegg.home里,所以要调试的话,要在com.codegg.home进程下断点。
那么我们再来思考下,我现在要去追应用的启动过程,start Activity的流程,要在哪个地方下断点呢?
我们知道这个流程,最终核心的都在Activity manager server里面,而它是在system server进程里面,以一个线程的状态存在,于是我们要调试,就要在system server上面下断点了。
如果你对这几个问题,没有疑惑,恭喜你,进程和线程,你已经有了概念了。
------------未完待续----------