Android 应用沙盒浅析

其实这是一个存在很久的概念,只是近几年Android开发者才开始适配。他如同Linux和ios那样,应用单独储存却又可以互相交互。下面就来说一下这其中有什么

1. 沙盒

首先看官方的解释

Android 平台利用基于用户的 Linux 保护机制识别和隔离应用资源,可将不同的应用分隔开来,并保护应用和系统免受恶意应用的攻击。为此,Android 会为每个 Android 应用分配一个独一无二的用户 ID (UID),并让应用在自己的进程中运行。

Android 会使用该 UID 设置一个内核级应用沙盒。内核会在进程级别利用标准的 Linux 机制(例如,分配给应用的用户 ID 和组 ID)实现应用和系统之间的安全防护。默认情况下,应用不能彼此交互,而且对操作系统的访问权限会受到限制。如果应用 A 尝试执行恶意操作(例如在没有权限的情况下读取应用 B 的数据或拨打电话),系统会阻止此类行为,因为应用 A 没有相应的默认用户权限。这一沙盒机制非常简单,可审核,并且基于已有数十年历史的 UNIX 风格的进程用户隔离和文件权限机制。

首先我们要来简单说一下SELinux的概念。SELinux就是Security-Enhanced Linux(安全增强型Linux),https://github.com/SELinuxProject/selinux 。Android 使用SELinux对包括root/su在内的所有进程进行控制强制访问权限(MAC,mandatory access control)。

下面来说一下,各个Android版本之间的应用间保护机制:

  • 5.0 Android只区分了系统APP(pre-app不包括在内)和第三方APP的区别,系统使用MAC将二者分离开来,但是两种APP在相同的SELinux环境中运行
  • 6.0 Android支持了跨用户边界隔离应用。并且对应用主目录上的默认 DAC 权限从 751 更改为 700,这里的权限请看(权限)[../权限]
  • 8.0 中,所有应用都设为使用 seccomp-bpf 过滤器运行,该过滤器可限制允许应用使用的系统调用,从而增强应用/内核边界的安全性
  • 9.0 中,targetSdkVersion >= 28 的所有非特权应用都必须在不同的 SELinux 沙盒中运行,并针对各个应用提供 MAC。这种保护机制可以提升应用隔离效果,防止替换安全默认设置,并且(最重要的是)防止应用的数据可让所有人访问。
  • 10.0 中,文件管理的权限甚至有限,不可以直接访问应用数据文件。APP不可以直接访问/sdcard/DCIM 文件夹,不过APP保留了访问媒体路径的方法。

2. 沙盒内容分享

数据文件/二进制文件 : content provider

不多赘述

物理媒体文件 :储存

Google推荐使用MediaStore 进行媒体文件储存,读取时使用MediaStore.Download 读取。 注意,这里的APP的intent必须使用ACTION_OPEN_DOCUMENT 属性。

Google 强调新APP需要使用分区储存,APP在自己data文件下储存内容即可,使用MediaStore进行媒体文件共享。如果你实在需要访问外部数据(之后的高版本系统可能被禁),那么你需要首先判断 Environment.getExternalStorageState() 的返回状态,当返回MEDIA_MOUNTED时,你可以在外部空间进行读写。返回MEDIA_MOUNTED_READ_ONLY时,你只可以进行读取。

共享集合空间的文件访问推荐使用MediaStore、MediaProvider进行适配。

其他

权限

r=读取属性  //值=4

w=写入属性  //值=2

x=执行属性  //值=1

7=4+2+1 ,5=4+1,3=2+1,6=4+2,0=没有权限

751 = 给file的属主分配读、写、执行(7)的权限,给file的所在组分配读、执行(5)的权限,给其他用户分配执行(1)的权限

700 依次类推