技术实现
input注入
目前常用的input注入有两种,一种是以uinput为代表的创建/dev/input/xx节点,往节点里注入原始input数据;一种是以scrcpy为代表的利用adbd的高权限调用framework inputManager注入事件的接口。
投屏
以scrcpy为例,简述投屏的原理。scrcpy会通过adb在android内创建一个VirtualDisplay,并有一块surface与之关联,surface由mediacodec创建,surfaceFlinger在合成渲染完毕后会将结果传递给这个surface,mediacodec再编码后的结果通过socket传递给adb reverse传递的pc端映射端口,pc端解码后就拿到了该图像。
商业云手机在android端的图像采集技术与scrcpy类似,但是在各端的推拉流显示原理则各有差异,如webrtc/xdp等。
binder 驱动
redroid本质上是通过docker启动的android容器,与宿主共用一个内核,而各个容器都需要单独的binder驱动,因此一般会通过binderfs创建容器专属的binder节点,再在docker启动容器时映射进去。

渲染
redroid被设计用来跑在不同架构和GPU的平台,因此redroid预置了相当多的渲染相关的so,以便在运行时根据配置来决定是使用软渲染还是硬件渲染,使用哪个平台的渲染驱动等。
namespace和cgroup资源隔离
这是android容器能跑起来的最关键的机制,一般通过docker/podman/lxc实现。、
如何阅读 redroid
#####################
# fetch code
#####################
mkdir ~/redroid && cd ~/redroid
# check supported branch in https://github.com/remote-android/redroid-patches.git
repo init -u https://android.googlesource.com/platform/manifest --git-lfs --depth=1 -b android-11.0.0_r48
# add local manifests
git clone https://github.com/remote-android/local_manifests.git ~/redroid/.repo/local_manifests -b 11.0.0
# sync code
repo sync -c
# apply redroid patches
git clone https://github.com/remote-android/redroid-patches.git ~/redroid-patches
~/redroid-patches/apply-patch.sh ~/redroid
redroid代码主要分为patch仓库和redroid仓库两部分。
先看patch仓库部分

主要是屏蔽了selinux、vintf、seccomp等导致系统起不来的部分逻辑。
redroid仓库相对aosp的主要改动如下


可以看到都是为了应对不同平台和环境的一些渲染和编解码的库。