这就是进程名

android 如何通过代码启动分身app android 分身原理_android

Android系统的底层是Linux内核,Linux操作系统就是进程隔离的,每一个程序有一个单独的进程(一个app就是一个进程),如果没有进程隔离,那app之间就会出现安全性问题。

流氓软件读取到app数据采用的策略就是“数据共享”,利用进程之间通信原理。

线程是跑在进程里面的,一个进程含有有无数个线程。

进程四要素

  1. 有一段程序供其执行
  2. 拥有专用的系统堆栈空间
  3. 在内核存在对应进程控制块
  4. 拥有独立的用户存储空间
adb shell dumpsys meminfo   //打印当前手机进程的所有信息

参考 https://www.jianshu.com/p/3a5baa670ed8

 

进程间数据共享

1、广播

广播的类型

  1. 普通广播(Normal Broadcast)
  2. 系统广播(System Broadcast)
  3. 有序广播(Ordered Broadcast)
  4. App应用内广播(Local Broadcast)

2、内容提供者

 

com.bbk.lancher2 桌面应用进程

surfaceflinger 系统渲染进程

zygote  受精卵进程(基本上所有的进程同时通过它复制出来的,因为创建一个进程是需要销毁一定内存的,复制手段可减少启动时间)

点击桌面图标,app被提起,运行(手指触摸屏幕,经过手机的硬件检测会生成一个touch event“触摸事件”,相当于一个手势),点击之后它就会向系统发出一个消息,所有的应用的子进程都是通过zygote (中文名“受精卵”),通过它复制出一个进程供应用去使用

/init  初始化进程

安卓手机刚启动时,第一个启动的进程,它会初始化硬件的一些信息

activities 代表有界面的程序

安卓含有进程群,com.news.today.todayinformation,即app Module这个就是主进程,如果在AndroidManifest里面配置这个进程就属于进程集。

跳转不同进程的Activity,在AndroidManifest里面配置上海的子进程

<activity
            android:process=":shanghai.detatil"
            android:name=".main.shanghai.view.ShanghaiDetailActivity" />

 而BeijingFragment是在主进程里面,仍然可以从子进程跳到主进程,但是动画没有了,那跨进程的意义在哪?

android 如何通过代码启动分身app android 分身原理_API_02

android 如何通过代码启动分身app android 分身原理_#include_03

注意!添加“:”,这样主进程也可以加载进来

android 如何通过代码启动分身app android 分身原理_android_04

多进程app需要注意哪些问题

android 如何通过代码启动分身app android 分身原理_API_05

直接进入 https://developer.android.google.cn/ndk/guides

android 如何通过代码启动分身app android 分身原理_android_06

android 如何通过代码启动分身app android 分身原理_#include_07

android 如何通过代码启动分身app android 分身原理_#include_08

我之前安装过NDK(做音视频流媒体开发的时候),但是之前出现过jar不合适的原因,也有可能是Kotlin什么的内部jar包不合适,我把NDK删了,也有可能Android studio4.0升级会不会影响NDK的版本

OpenGL:用于2D,3D渲染

原生应用API:获取手机时间,配置,还可以做原生的Activity

AAudio API:专门做音频,C++音频库

硬件缓存区 API:

共享内存 API以及JNI API:

神经网络 API:

surfaceTexture API:

创建NDK的开发项目

android 如何通过代码启动分身app android 分身原理_android_09

默认C++

android 如何通过代码启动分身app android 分身原理_API_10

android 如何通过代码启动分身app android 分身原理_android_11

JNI就是连接java和C++之间的桥梁

android 如何通过代码启动分身app android 分身原理_#include_12

android 如何通过代码启动分身app android 分身原理_API_13

android 如何通过代码启动分身app android 分身原理_#include_14

.cpp就代表C和C++的源码

android 如何通过代码启动分身app android 分身原理_android_15

打包成.so文件(动态链接库)

android 如何通过代码启动分身app android 分身原理_android_16

android 如何通过代码启动分身app android 分身原理_android_17

然后可以把这个动态链接库(.so文件)拷贝到在原生安卓应用项目里。

在原生安卓应用里去使用这个动态链接库

如果64位找不到,就向下兼容去找(一般情况下有一种.so文件,很多安卓手机都能适配了)

// Used to load the 'native-lib' library on application startup.
//    static { //加载C/C++的动态链接库的java语法
//        System.loadLibrary("native-lib");
//    }
/**
     * A native method that is implemented by the 'native-lib' native library,
     * which is packaged with this application.
     */
    public native String stringFromJNI();

把动态链接库和引用库文件源码的JNI桥梁代码一起拷贝到原生应用的项目中

android 如何通过代码启动分身app android 分身原理_#include_18

android 如何通过代码启动分身app android 分身原理_android_19

注意!

android 如何通过代码启动分身app android 分身原理_#include_20

android 如何通过代码启动分身app android 分身原理_android_21

实际上我们不用每次使用.so库文件的都去创建stringFromJNI()方法对应的类,而是采用配套的anr或jar包,因为java做桥接部分类名一定要跟C++ 通过jns约定好的,如果直接复制一个stringFromJNI()方法放到任意一个原生应用里面去调用是使用不了的

运行效果

android 如何通过代码启动分身app android 分身原理_android_22

混合技术编程

先做一个opengl NDK的demo,生成.so动态链接库和jar包

C++: Android JNI NDK开发

1.效率高-直接跟CPU进行操作(像操作系统底层就是C++写的,它是位于硬件和软件之间的,采用C++开发可以直接跟硬件交互,而java需要通过C来驱动“像JVM虚拟机”去跟设备打交道,而C++可以直接跟设备打交道)

2.保密性好,打包出来是so的动态链接库,不易破解

3.引入优良的C++库(FFmpeg,V8,OpenCV,OpenVino,OpenGl ES)

参考 

FFmpeg:音视频(解码)开发

V8:google出的,JS引擎,安卓中的WebView(JS渲染引擎)就是v8,在ios当中就是Pluto(JSCore

OpenCV:处理视觉图像的库,像抖音就是使用这个进行技术合成,图像处理的底层开源库

OpenGL ES: 做图形图像渲染库的,在安卓里面分两大渲染引擎,一个是SKia,还有一个就是OpenGL 用的C++对外暴露java接口,在混合开发中起到至关重要的作用,比如微信小程序渲染区别

微信小程序Canvas渲染上下文:https://developers.weixin.qq.com/miniprogram/dev/api/canvas/RenderingContext.html

像常用的SQLite安卓底层数据库也是C++写的,像Cocos2d-x游戏引擎,Panda3D,JSON,著名的机器学习Caffe神经网络框架,脚本Lua和V8

<android.opengl.GLSurfaceView
        android:layout_gravity="center"
        android:id="@+id/gl_surface_view"
        android:layout_width="match_parent"
        android:layout_height="match_parent" />

创建C++文件与java关联上,模仿Android studio给我自动生成的cpp目录

android 如何通过代码启动分身app android 分身原理_android_23

android 如何通过代码启动分身app android 分身原理_android_24

android 如何通过代码启动分身app android 分身原理_API_25

 里面的stringFromJNI 

android 如何通过代码启动分身app android 分身原理_#include_26

更改成

android 如何通过代码启动分身app android 分身原理_android_27

opengl这个Module的build.gradle也需要这部分,拷贝过去

android 如何通过代码启动分身app android 分身原理_android_28

JNI 及 c ++ 基本语法

宏定义:#define  ,宏定义一个参数,相当于全局变量,可以定义宏方法(函数)

头文件jni.h:定义了一些接口,interface,cpp可以把这些头文件引用进来实现相应的方法

extern :外部拓展,表示可以用其他语言编写

android 如何通过代码启动分身app android 分身原理_android_29

点击JNIEXPORT进入:

android 如何通过代码启动分身app android 分身原理_android_30

JNIEXPORT,JNICALL :表示对外提供接口,可以被外部调用,相当于“入口”

JNIEnv :JNI 环境,可以理解 Android中的Context

“##”:表示字符串拼接

android 如何通过代码启动分身app android 分身原理_#include_31

C++ 和 Java通信 (通过JNIEnv 去访问java

1、java 通讯到C++,通过Native方法 调用JNI

2、c++ 通讯到 Java,通过JNI反射到Java(需要个对象jobject,这是个java的对象,可以代表静态,也可非静态)

android 如何通过代码启动分身app android 分身原理_android_32

调用OpenGLManager这个类时,它的对象就默认传到opengl-lib的这个jobject里

导包:#include

#include<GLES2/gl2.h>

#include<GLES2/gl2ext.h>

#include <jni.h>
#include <string>
#include<GLES2/gl2.h>
#include<GLES2/gl2ext.h>
//宏定义函数,用于字符串拼接
#define OPENGLFUN(arg) Java_com_panda_opengl_OpenGIManager##arg
/**
 * onSurfaceCreated()方法
 */
extern "C" JNIEXPORT void JNICALL
        OPENGLFUN(onSurfaceCreated)(
        JNIEnv* env,
        jobject /* this */) {
        glClearColor(0.0f, 0.0f, 1.0f, 1.0f);
}
extern "C" JNIEXPORT void JNICALL
        OPENGLFUN(onSurfaceChanged)(
        JNIEnv* env,
        jobject /* this */,
        jint width,
        jint height) {
        glViewport(0, 0, width, height);
}
extern "C" JNIEXPORT void JNICALL
        OPENGLFUN(onDrawFrame)(
        JNIEnv* env,
        jobject /* this */) {
        //设置色彩
        glClear(GL_COLOR_BUFFER_BIT);
}

运行

android 如何通过代码启动分身app android 分身原理_#include_33

少了指示libopengl-lib.so生成路径

android 如何通过代码启动分身app android 分身原理_#include_34

android 如何通过代码启动分身app android 分身原理_API_35