Android App Selinux seapp权限详解

目录

一、 系统原理详解

二、代码流程分析

 三、其他


一、 系统原理详解

      经常修改和增加一般是内核态的进程,设备节点,但对Android App加权限的介绍并

不多见,同时在原理方面介绍的比较少。 Android 在App上首先通过签名划分第一大类,

platform,system,media,share等等,然后是在同一类key下,建立不同的uid,gid来

进一步区分。                              签名key   ---------------    顶层根

                                               /        |         \

                                           /            |           \

                               Platform       System      media    share  ....    device/mediatek/common/security

                             /        |      \         media.pk8   platform.pk8   shared.pk8

                           /         |          \

              user=system  bluetooth  nfc   radio  shell   _app _isolated 

          system_app -> external\sepolicy\system_app.te
          untrusted_app -> external\sepolicy\untrusted_app.te
          platform_app -> external\sepolicy\platform_app.te          

二、代码流程分析

1.   system\sepolicy\private  keys.conf

           [@TESTSEC]
           ALL : $DEFAULT_SYSTEM_DEV_CERTIFICATE/testsec.x509.pem

           device/mediatek/common/security/testsec.x509.pem

       The keys.conf file is used for controlling the mapping of "tags" found in
        the mac_permissions.xml signature stanzas with actual public keys found in
        pem files. 

       增加一对RSA公私秘钥对,证书,给apk签名使用

2.  添加mac_permissions.xml

 <!-- testsec key in AOSP -->
    <signer signature="@TESTSEC" >
      <seinfo value="testsec" />
    </signer>

3.  Android.mk

$(HOST_OUT_EXECUTABLES)/insertkeys.py -t $(TARGET_BUILD_VARIANT) -c $(TOP) $< -o $@ $(PRIVATE_MAC_PERMS_FILES)

4.  system/sepolicy/public/te_macros

#####################################
# app_domain(domain)
# Allow a base set of permissions required for all apps.
define(`app_domain', `
typeattribute $1 appdomain;
# Label ashmem objects with our own unique type.
tmpfs_domain($1)
# Map with PROT_EXEC.
allow $1 $1_tmpfs:file execute;
neverallow { $1 -shell } { domain -$1 }:file no_rw_file_perms;
neverallow { appdomain -shell -$1 } $1:file no_rw_file_perms;
')

#####################################
# untrusted_app_domain(domain)
# Allow a base set of permissions required for all untrusted apps.
define(`untrusted_app_domain', `
typeattribute $1 untrusted_app_all;
')

#####################################
# net_domain(domain)
# Allow a base set of permissions required for network access.
define(`net_domain', `
typeattribute $1 netdomain;
')
 

5.   system/sepolicy/private/seapp_contexts  注意下顺序,这是脚本文件,添加一个新seinfo时,

要优先放前面。

user=_isolated domain=isolated_app levelFrom=all
user=_app seinfo=media domain=mediaprovider name=android.process.media type=app_data_file levelFrom=user
user=_app seinfo=platform domain=platform_app type=app_data_file levelFrom=user
user=_app isV2App=true isEphemeralApp=true domain=ephemeral_app type=app_data_file levelFrom=all
user=_app isPrivApp=true domain=priv_app type=app_data_file levelFrom=user

6.  selinux/libselinux/src/android/android.c seapp_context_cmp()

7.   packages\apps  自定义uid,配置一组apk权限; UID 通过和AID建立对应联系

      include/private/android_filesystem_config.h

      android:sharedUserId="android.uid.testuid"

#define AID_RADIO 1001           /* telephony subsystem, RIL */
#define AID_BLUETOOTH 1002       /* bluetooth subsystem */
#define AID_GRAPHICS 1003        /* graphics devices */
#define AID_INPUT 1004           /* input devices */
#define AID_AUDIO 1005           /* audio devices */
#define AID_CAMERA 1006          /* camera devices */
#define AID_LOG 1007             /* log devices */
#define AID_COMPASS 1008         /* compass device */
#define AID_MOUNT 1009           /* mountd socket */
#define AID_WIFI 1010            /* wifi subsystem */

static const struct android_id_info android_ids[] = {
    { "root",          AID_ROOT, },
    { "system",        AID_SYSTEM, },
    { "radio",         AID_RADIO, },
    { "bluetooth",     AID_BLUETOOTH, },
    { "graphics",      AID_GRAPHICS, },
    { "input",         AID_INPUT, },
    { "audio",         AID_AUDIO, },
    { "camera",        AID_CAMERA, },
    { "log",           AID_LOG, },
    { "compass",       AID_COMPASS, },
    { "mount",         AID_MOUNT, },
    { "wifi",          AID_WIFI, },
    { "adb",           AID_ADB, },


/*
 * android_ids has moved to pwd/grp functionality.
 * If you need to add one, the structure is now
 * auto-generated based on the AID_ constraints
 * documented at the top of this header file.
 * Also see build/tools/fs_config for more details.
 */  ----------最新版本说明

build/make/tools/fs_config/fs_config_generator.py

@generator('aidarray')
class AIDArrayGen(BaseGenerator):
    """Generates the android_id static array."""

 _OPEN_ID_ARRAY = 'static const struct android_id_info android_ids[] = {

测试了下脚本:

python  build/tools/fs_config/fs_config_generator.py aidarray  system/core/libcutils/include/private/android_filesystem_config.h   

8. MLS(Multi-Level Security)  什么是MLS,为何要引入MLS

MLS称为多级别安全是另一种强制访问控制方法,特别适合于政府机密数据的访问控制,早期对计算机安全的研究大多数都是以在操作系统内实现MLS访问控制为驱动的。所有MLS的使用都是建立在TE安全的基础之上。在SELinux中MLS是一个可选访问控制方式,而在SEAndroid中则是被作为安全访问方式的其中之一。

本质问题: MLS在安全策略上有一个形象的描述叫no write down和no read up

    1  低级别的东西只能往高级别的东西里边写数据

    2  低级别的东西不能从高级别的东西那边读数据

  -----这个经典的解释就是:

      员工必须向领导汇报问题,讲报告写在领导给你分配的目录下。

      领导可以查看员工所有的一切信息,无需去写员工的数据,只需要结果就好,然后分析,判断

在SEAndroid中sensitivity只有一个级别即s0,category共有1024个,因此最低安全级别就是s0,最高安全级别就是s0:c0.c1023。

sensitivity和category组合一起声明了当前的安全级别(security level),“-”号左右分别标识了安全级别的最低和最高,这一列的参数将在MLS约束检查时用到,“15”、“1023”表示了sensitivity和category的最大值,这一参数可在Android.mk中定义。

 type testmetad, domain, mlstrustedsubject;  忽略这个c512, c600问题

 typeattribute teei_client_device mlstrustedobject;

 type usb_device, dev_type, mlstrustedobject;

 type devpts, fs_type, mlstrustedobject;

9.  添加默认权限system/core/libcutils/fs_config.cpp 

static const struct fs_path_config android_dirs[] = {
    // clang-format off
    { 00770, AID_SYSTEM,       AID_CACHE,        0, "cache" },
    { 00555, AID_ROOT,         AID_ROOT,         0, "config" },
    { 00771, AID_SYSTEM,       AID_SYSTEM,       0, "data/app" },

10.所有的Android App或用户程序,Server都只是是Selinux的使用者,上层所有的.te等文件

仅仅只是规则的编写而已,所以只要遵循规则便可定制,无需修改代码。

11.  neverallow { appdomain -nfc } nfc_device:chr_file

     neverallow { domain -system_server -vdc -vold } vold_service:service_manager find;

     -表示排除对应的进程,不在范围内。

12 编译错误

         SELinux: The following types were found added to the policy without an entry into the compatibility mapping file(s) found in private/compat/26.0/26.0[.ignore].cil/nlid_service

         需要在prebuilts目录下的sepolicy中添加相同的内容

         参考Android 源代码:  注意其中的细微差别

               device\mediatek\common\BoardConfig.mk

              关键宏   BOARD_SEPOLICY_DIRS    BOARD_PLAT_PUBLIC_SEPOLICY_DIR    BOARD_PLAT_PRIVATE_SEPOLICY_DIR

    BOARD_PREBUILTS_FULL_PUBLIC_PLAT_DIRS    BOARD_PREBUILTS_FULL_PRIVATE_PLAT_DIRS   

    BOARD_COMPAT_MAPPING_CIL_DIRS     BOARD_COMPAT_MAPPING_IGNORE_CIL_DIRS   

    BOARD_26.0_NONPLAT_FILE            BOARD_PLAT_PUBLIC_SEPOLICY_DIR   BOARD_PLAT_PRIVATE_SEPOLICY_DIR

13.  Log:

system/sepolicy/Android.mk:410: warning: "PLAT_PUBLIC_POLICY is " system/sepolicy/public device/mediatek/sepolicy/basic/plat_public device/mediatek/sepolicy/bsp/plat_public
system/sepolicy/Android.mk:411: warning: "sepolicy build files" security_classes initial_sids access_vectors global_macros neverallow_macros mls_macros mls_decl mls policy_capabilities te_macros attributes ioctl_defines ioctl_macros *.te roles_decl roles users initial_sid_contexts fs_use genfs_contexts port_contexts

 三、其他

type hal_camera_default, domain;
hal_server_domain(hal_camera_default, hal_camera)

### add for 
vndbinder_use(hal_camera_default)
hwbinder_use(hal_camera_default)

#allow hal_camera_default vndbinder_device:chr_file { open read write ioctl};
#allow hal_camera_default binder_device:chr_file { open read write ioctl};

full_treble_only(`
  neverallow {
    domain
    -coredomain
    -appdomain
    -hal_camera
    -binder_in_vendor_violators # TODO(b/35870313): Remove once all violations are gone
  } binder_device:chr_file rw_file_perms;
')

输入命令ps -Z -A能够查询当前所有进程的安全属性

进程SContext的type字段代表该进程所属的Domain(域名),个人理解domain就跟tcp协议栈里面的域名一样,它对应于一类进程,

后文将要讲解的安全策略就会应用于该类的所有进程,即相同type的进程具有相同的访问权限。

在Android系统根目录执行ls -l  -Z命令,能够查看根目录文件的SContext。大多数资源的SContext的user值为u代表SEAndroid用户;

role值为object_r代表文件;range值为s0。

SEAndroid世界将所有事物都打上了标签(每个事物都有自己的SContext),那么SEAndroid就能根据这些SContext来进行统一管理。

SEAndroid就是通过一系列的te文件来管理所有进程和资源的权限,每个te文件里面都有无数条te语句,每条te语句对应一条安全策略。

  • 主体:主体和客体只是一个逻辑上的概念,就跟主谓宾语句:小红在吃米饭,其中主语是小红(活的),宾语是米饭(死的)。同理在Linux世界中,
  • 活的东西只有进程,死的东西是资源。即资源是被使用的东西,进程是使用者,这里的主体就是指使用者。SEAndroid中的主体就是指的进程,
  • 当然可能是单一的进程,也可以是一组具有相同权限的进程,但是它们都对应一个type。
  • 客体:同上客体就是这个被使用者。SEAndroid中的客体就是指的资源(包括普通文件/特殊文件/套接字),当然可能是单一的资源,也可以是一组
  • 相同类型的资源,但是他们都对应一个type。
  • 客体类别:客体与客体类别的概念就类似于Java语言中的object和class,其中class表示一个类,object表示一个实例对象。同样客体和客体类别也是这样
  • 的关系,例如小红在吃米饭,小红在吃鱼肉,米饭和鱼肉都是具体的事物(客体),但是他们却是不一样的类别(客体类别)。SEAndroid中已经为资源
  • 定义了一些客体类别,我们也可以自定义。例如/etc/password是一个普通文件,/atv/socket_0是一个套接字。
  • 访问许可:这个比较好理解,代表对客体的访问权限,例如读写权限,查询发送等权限。这个也是可以自定义的。
  • AV规则:既然已经有了主体和客体,那么就有对应访问规则,又叫AV规则。属于SElinux策略语言的控制部分,即te文件中每一条AV规则语句都需要能够
  • 描述清楚:主体 对 客体 是否具有 访问许可。其实就是te文件里面的allow、neverallow、dontaudit、auditallow等语句。

参考Android安全策略SELinux_诸神黄昏EX的博客-CSDN博客_android selinux配置

注意:在任何情况下,都不应该直接允许域(domain)访问以下通用标签;而应为一个或多个对象创建一个更具体的类型;

  1. socket_device
  2. device
  3. block_device
  4. default_service
  5. system_data_file
  6. tmpfs
  • 3
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
### 回答1: Android SELinuxAndroid操作系统中的一种安全机制,它可以限制应用程序的访问权限,保护用户数据的安全性。SELinux是一种强制访问控制(MAC)机制,它通过强制规则来限制应用程序的访问权限,即使应用程序本身存在漏洞,也可以保护系统的安全性。Android SELinux的实现基于Linux内核的SELinux模块,它通过定义安全策略来控制应用程序的访问权限,包括文件系统、网络、进程等方面。Android SELinux的实现需要在系统级别进行配置,因此需要一定的技术知识和经验。 ### 回答2: 安卓的SELinux是一项安全功能,做到了不同级别权限间的隔离。它与Linux的SELinux相似,都是基于Mandatary Access Control(MAC)的实现。MAC使用了定义好的安全策略来决定进程访问对象的许可。每个对象有一个或多个安全标签,决定了可访问这些对象的访问者。SELinux实现了一个高度定制化的MAC实现,以达到保护系统免受攻击的效果。 SELinux可以将任何应用程序、库或系统进程在安全上互相隔离。每个进程可以分配一个不同的安全上下文,用于决定该进程可以执行的操作。SELinux允许管理员定义一个策略集,以确保只有那些拥有特定权限的应用程序可以执行特定的操作。SELinux包括以下4个组件。 * Security-enhanced kernel:该内核支持SELinux,并且为应用程序和系统提供安全保护。通常,操作系统上的SELinux是直接编译到内核配置中的。 * SELinux policy:这是一组规则,它定义了哪些进程可以访问哪些资源,以及何时可以访问它们。这是SELinux的“脑”。SELinux策略通过使用安全标签来标识资源和进程,并使用规则来决定它们之间的安全关系。 * SELinux utilities:这些社区提供的工具用于安装、更新和管理SELinux策略。通常情况下,管理员会安装每个Linux发行版自带的安全工具。 * SELinux-aware applications:这是应用程序和守护进程,它们能够在SELinux的约束下运行。这些应用程序还懂得如何处理SELinux策略,以确保它们对系统的安全有积极贡献。 总的来说,SELinux是一项强大而高度定制化的MAC实现,能够确保安卓系统和应用程序免受攻击。它通过一组规则定义了可用资源和进程之间的安全关系,从而在操作系统和应用层上实现了分离和隔离。作为一项优秀的安全保护功能,它能够在各种安卓设备上为用户提供强大的保护措施,从而发挥关键的作用。 ### 回答3: Android操作系统是目前全球手机、平板等终端设备最常用的操作系统之一。Android系统架构中有一个非常重要的安全机制,即SE_LINUX(Security-Enhanced Linux)。SE_LINUX是由美国国家安全局(NSA)和Redhat合作研发的一种新型操作系统,它基于强制性访问控制(Mandatory Access Control)机制,是一种可扩展的安全模型,功能十分强大。 Android系统使用SE_LINUX来保障应用程序的安全。在Android的SE_LINUX中,安全策略旨在为每个进程提供最佳的资源保护。当应用程序尝试访问受限制的资源时,安全策略会检查该应用程序的标记是否具有访问受限制资源的许可权,以确保安全性。如果没有访问权限,访问请求就会被拒绝,在应用程序层面上保证了Android系统的安全。 其中,SE_LINUX的工作原理是在内核上增加了一个“SELinux子系统”,具体实现过程如下:(1)在内核源代码中添加SELinux子系统;(2)在Linux 内核上开发安全模块;(3)编写用户空间程序和共享代码,实现SELinux规则和策略以及管理SELinux权限的机制。Android系统的SE_LINUX是基于SMLS架构,即安全、多层、标签、安全。 同时,SE_LINUX还为Android系统中的进程、文件系统、系统服务进行了标记化管理。每个进程都有一个唯一的SELinux安全上下文标签进行标识,涉及到的对象都会增加一个SELinux标签,当某个进程尝试访问某个对象时,它的SELinux上下文标签需要满足该对象的SELinux上下文标签的安全策略,否则该进程就会被降级或者拒绝访问该对象。 总之,Android SE_LINUX是Android操作系统架构中的重要安全机制,它通过强制性访问控制(Mandatory Access Control)机制来保护应用程序的安全,在访问受限制的资源时会进行检查、获取许可证以保证安全。SE_LINUX的工作原理是标记化管理,确保每个进程、文件系统、系统服务都对应一个唯一的安全标签,实现了权限的有效、高效管理。
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值