Android SELinux 小结

本文详细介绍了Android系统的SELinux(安全增强型Linux)的运行模式、调试方法、标签规则以及如何在Android设备上进行权限管理。主要内容包括宽容与强制模式的切换,标签与规则的定义,以及如何处理SELinux拒绝事件。此外,还阐述了在Android 8.0及以上版本中政策文件的位置、关键文件和如何新增或修改权限。最后,提供了调试SELinux问题的步骤和常见问题分析。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

Android SELinux 知识点

运行模式

SELinux 按照默认拒绝的原则运行:任何未经明确允许的行为都会被拒绝。SELinux 可按两种全局模式运行:

  • 宽容模式:权限拒绝事件会被记录下来,但不会被强制执行。
  • 强制模式:权限拒绝事件会被记录下来并强制执行。
调试中修改运行模式

获取运行模式

getenforce
//Enforcing: seLinux已经打开;        
//Permissive:seLinux已经关闭;

修改运行模式

//关闭selinux
setenforce 0 

//打开selinux
setenforce 1
编译选择运行模式
  • 在内核中启用 SELinux
// kernel/configs/android-5.4/android-base.config
CONFIG_SECURITY_SELINUX=y
  • 更改 kernel_cmdline参数
//device/qcom/msmnile_gvmq/BoardConfig.mk
BOARD_KERNEL_CMDLINE += androidboot.selinux=permissive

这仅适用于初始制定设备政策的情况。在拥有初始引导程序政策后,请移除此参数,以便将设备恢复强制模式,否则设备将无法通过 CTS 验证。

标签、规则和域

SELinux 依靠标签来匹配操作和政策。标签用于决定允许的事项。套接字、文件和进程在 SELinux 中都有标签。SELinux 在做决定时需参照两点:一是为这些对象分配的标签,二是定义这些对象如何交互的政策。

在 SELinux 中,标签采用以下形式:user:role:type:mls_level(如u:r:init:s0),其中 type 是访问决定的主要组成部分,可通过构成标签的其他组成部分进行修改。对象会映射到类,对每个类的不同访问类型由权限表示。(type是关键中的关键。)

政策规则采用以下形式:allow domains types:classes permissions;

#表示init进程可以对chr_file类型的 ipa_dev具有open权限
# Domain -> init
# Type -> ipa_dev
# Class -> chr_file
#Permission -> open
allow  init  ipa_dev : chr_file { open }; 

其中:

  • Domain - 一个进程或一组进程的标签。也称为域类型,因为它只是指进程的类型。
  • Type - 一个对象(例如,文件、套接字)或一组对象的标签。
  • Class - 要访问的对象(例如,文件、套接字)的类型。
  • Permission - 要执行的操作(例如,读取、写入)。
相关文件

在 Android 8.0 及更高版本中,政策位于 AOSP 中的以下位置:

  • system/sepolicy/public。其中包括所导出的用于供应商特定政策的政策。所有内容都会纳入 Android 8.0 兼容性基础架构。公共政策会保留在不同版本上,因此您可以在自定义政策的 /public 中添加任何内容。正因如此,可存放在 /public 中的政策类型的限制性更强。将此目录视为相应平台的已导出政策 API:处理 /system 与 /vendor 之间的接口的所有内容都位于这里。
  • system/sepolicy/private。包括系统映像正常运行所必需(但供应商映像政策应该不知道)的政策。
  • system/sepolicy/vendor。包括位于 /vendor 但存在于核心平台树(非设备特定目录)中的组件的相关政策。这是构建系统区分设备和全局组件的软件工件;从概念上讲,这是下述设备专用政策的一部分。
  • device/manufacturer/device-name/sepolicy。包含设备专用政策,以及对政策进行的设备自定义(在 Android 8.0 及更高版本中,该政策对应于供应商映像组件的相关政策)。
位置包含
system/sepolicy/public平台的 sepolicy API
system/sepolicy/private平台实现详情(供应商可以忽略)
system/sepolicy/vendor供应商可以使用的政策和上下文文件(供应商可以根据情况忽略)
BOARD_SEPOLICY_DIRS供应商 sepolicy
关键文件
  • BoardConfig.mk
    定义 vendor sepolicy
TARGET_SEPOLICY_DIR := ***
  • file_contexts
    需要在此处添加进程声明 (PS : 如果是增量添加,一定要在末尾空一行。否则编译会报错。)
/(vendor|system/vendor)/bin/hw/android\.hardware\.vibrator@1\.0-service       u:object_r:hal_vibrator_default_exec:s0
/(vendor|system/vendor)/bin/hw/android\.hardware\.vr@1\.0-service             u:object_r:hal_vr_default_exec:s0
/(vendor|system/vendor)/bin/hw/android\.hardware\.wifi\.offload@1\.0-service  u:object_r:hal_wifi_offload_default_exec:s0
/(vendor|system/vendor)/bin/hw/android\.hardware\.wifi@1\.0-service           u:object_r:hal_wifi_default_exec:s0
  • hal_vibrator.te
    相关进程需要申请的权限,需要在此处添加。
# HwBinder IPC from client to server
binder_call(hal_vibrator_client, hal_vibrator_server)

add_hwservice(hal_vibrator_server, hal_vibrator_hwservice)
allow hal_vibrator_client hal_vibrator_hwservice:hwservice_manager find;

# vibrator sysfs rw access
allow hal_vibrator sysfs_vibrator:file rw_file_perms;
allow hal_vibrator sysfs_vibrator:dir search;

  • hwservice.te
    声明hidl serivce 类型,需要配合hwservice_contexts一起使用。
//生命 hal_vibrator_hwservice 归为 hwservice_manager_type 一类。
type hal_vibrator_hwservice, hwservice_manager_type;
type hal_vr_hwservice, hwservice_manager_type;
type hal_weaver_hwservice, hwservice_manager_type;
type hal_wifi_hwservice, hwservice_manager_type;

  • hwservice_contexts
    用于声明HIDL service 安全上下文。
//格式   
//包名::接口      属性
//包名:android.hardware.vibrator   接口:IVibrator.hal   Type:
android.hardware.vibrator::IVibrator                u:object_r:hal_vibrator_hwservice:s0
android.hardware.vr::IVr                            u:object_r:hal_vr_hwservice:s0
android.hardware.weaver::IWeaver                    u:object_r:hal_weaver_hwservice:s0
android.hardware.wifi::IWifi                        u:object_r:hal_wifi_hwservice:s0

如何新增

辅助参考
  • /system/sepolicy/public/domain.te
  • /system/sepolicy/public/te_macros
重要类型/属性

在这里插入图片描述
在这里插入图片描述

步骤
  • 1 添加启动rc
service hal_vendorlight /vendor/bin/hw/vendorlight@1.0-service
class core
  • 2 在file_contexts 添加type
/vendor/bin/hw/vendorlight@1.0-service u:object_r:hal_vendorlight_exec:s0
  • 3 添加相关.te
# vendorlight service
type hal_vendorlight, domain;
type hal_vendorlight_exec, exec_type, file_type;

init_daemon_domain(foo)

调试相关

neverallow
  • 1 添加权限
    在mediaserver.te中添加
allow mediaserver device:chr_file { read write open};
  • 2 编译报错
libsepol.check_assertion_helper: neverallow on line 258 ofexternal/sepolicy/domain.te (or line 5252 of policy.conf) violated byallow mediaserver device:chr_file { read write open};

违反了domain.te 258:

neverallow {domain –unconfineddomain –ueventd } device:chr_file { open read write}

此句表示 所有domain(声明为domain 的域 type *, domain) 除了unconfineddomain 和 ueventd 的type之外(–unconfineddomain –ueventd, -表示移除) 都不允许对device的chr_file进行 open read write 操作。

  • 3 运行Log:
avc: denied { read write } for pid=303 comm="mediaserver"name="tfa9890" dev="tmpfs" ino=3880 scontext=u:r:mediaserver:s0 tcontext=u:object_r:device:s0tclass=chr_file permissive=0
  • 4 修改步骤:
  1. 目标名称是: tfa9890, 其在系统中的路径是: /dev/tfa9890, 是audio相关的设备文件
  2. 源类型是mediaserver, 在mediaserver.te 文件中发现其具有 audio_device 目标类型的权限
  3. 所以在file_contexts 中添加 /dev/tfa9890 u:object_r:audio_device:s0可以解决问题

通过增加 typeattribute来解决

  • 1 查看声明的属性 hal_attribute 这个宏在 te_macros 展开
# system/sepolicy/public/attribute
hal_attribute(health_storage);
hal_attribute(input_classifier);
hal_attribute(ir);
hal_attribute(keymaster);
hal_attribute(light);
hal_attribute(lowpan);
hal_attribute(memtrack);
hal_attribute(neuralnetworks);
  • 2 hal_attribute 展开后 划等号的 语法
# system/sepolicy/public/te_macros
#####################################
# hal_attribute(hal_name)
# Add an attribute for hal implementations along with necessary
# restrictions.
define(`hal_attribute', `
attribute hal_$1;
expandattribute hal_$1 true;
attribute hal_$1_client;
expandattribute hal_$1_client true;
attribute hal_$1_server;
expandattribute hal_$1_server false;
``
- 3 hal_attribute_hwservice 也是个宏定义,需要在te_macros 中展开
```clike
# system/sepolicy/public/hal_light.te
# HwBinder IPC from client to server, and callbacks
binder_call(hal_light_client, hal_light_server)
binder_call(hal_light_server, hal_light_client)

hal_attribute_hwservice(hal_light, hal_light_hwservice)

allow hal_light sysfs_leds:lnk_file read;
allow hal_light sysfs_leds:file rw_file_perms;
allow hal_light sysfs_leds:dir r_dir_perms;
  • 4 hal_attribute_hwservice 展开
# system/sepolicy/public/te_macros
###########################################
# hal_attribute_hwservice(attribute, service)
# Ability for domain to get a service to hwservice_manager
# and find it. It also creates a neverallow preventing
# others from adding it.
#
# Used to pair hal_foo_client with hal_foo_hwservice
define(`hal_attribute_hwservice', `
  allow $1_client $2:hwservice_manager find;
  add_hwservice($1_server, $2)

  build_test_only(`
    neverallow { domain -$1_client -$1_server } $2:hwservice_manager find;
  ')
')
增加权限
过滤

常规

dmesg | grep 'avc: '

or

// hal_vendorlight 是根据 type hal_vendorlight, domain;
logcat -b all | grep hal_vendorlight

以宽容模式启动系统,看看在启动时会遇到哪些拒绝事件:
在 Ubuntu 14.04 或更高版本中:

adb shell su -c dmesg | grep denied | audit2allow -p out/target/product/BOARD/root/sepolicy

在 Ubuntu 12.04 中:

adb shell su -c dmesg | grep denied | audit2allow
根据avc提示添加
auditd  : avc:  denied  { add } for interface=android.hidl.base::IBase pid=438 scontext=u:r:hal_vendorlight:s0 tcontext=u:object_r:hidl_base_hwservice:s0 tclass=hwservice_manager permissive=1

以下是此拒绝事件的关键元素:

  • 操作 - 试图进行的操作使用括号突出显示:add 。
  • 操作方 - scontext(来源环境)条目表示操作方;hal_vendorlight
  • 对象 - tcontext(目标环境)条目表示正在对哪个对象执行操作;hidl_base_hwservice
  • 结果 - tclass(目标类别)条目表示当前操作对象的类型;hwservice_manager
常见问题
auditd  : avc:  denied  { find } for interface=vendor.leo.light::ILightVendor pid=438 scontext=u:r:hal_vendorlight:s0 tcontext=u:object_r:default_android_hwservice:s0 tclass=hwservice_manager permissive=1
auditd  : avc:  denied  { add } for interface=vendor.leo.light::ILightVendor pid=438 scontext=u:r:hal_vendorlight:s0 tcontext=u:object_r:default_android_hwservice:s0 tclass=hwservice_manager permissive=1

注意此处的提示 对default_android_hwservice的hwservice_manager 缺少 add find 权限,切记不可直接allow hal_vendorlight default_android_hwservice:hwservice_manager { add find },。
正确的做法是

  • 1 在hwservice_contexts 声明
vendor.leo.light::ILightVendor                                u:object_r:hal_light_leo_hwservice:s0
  • 2 在hwservice.te 声明为 hwservice_manager_type 的类型
type hal_light_leo_hwservice , hwservice_manager_type;
  • 3 再向 hal_light_leo_hwservice 加权限
allow hal_vendorlight hal_leo_yft_hwservice:hwservice_manager { add find };

参考

Android 中的安全增强型 Linux
Android P添加一个可以让system_server进程访问的hal service需要改动的sepolicy文件
Android O selinux违反Neverallow解决办法
Android : SELinux 简析&修改
Android sepolicy简要记

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值