当前位置: 首页 > news >正文

Android SELinux——添加策略实例(十五)

        通过前面的文章,我们基本了解在 Android 系统中 SELinux 策略配置和基本语法,这里我们就来看一些常见的问题及其解决方案。这里我们主要看通过 allow 添加策略的方案。

一、直接添加权限

       添加策略一般都是根据 Log 中的信息,使用 audit2allow 生成策略,谁缺少权限,就修改谁的 .te 文件。

示例

selinux: avc: denied { set } for property=vold.decrypt pid=7192 uid=2000 gid=2000 scontext=u:r:shell:s0
tcontext=u:object_r:exported_vold_prop:s0 tclass=property_service permissive=0

        从 Log 中可以看出来进程 u:r:shell:s0 缺少对 property_service 类型的对象 u:object_r:exported_vold_prop:s0 的 set 权限。 通过 audit2allow 生成策略也比较简单:

#============= shell ==============
allow shell exported_vold_prop:property_service { set };

        这样,我们找到或创建对应的 .te(即 shell.te)文件,添加上面的权限赋予语句即可解决。

二、添加domain或type

        为了细化 SELinux 的权限管理,我们可以通过定义自定义的 domain 和 type 来避免默认权限过大的问题。操作步骤如下:

  • 定义类型:根据进程或资源的类型, 在相应的 .te 中定义属性。
  • 绑定资源和安全上下文:在 xxx_contexts 文件中绑定进程或资源的安全上下文。
  • 定义策略:根据主体需要访问的文件,在主体 xxx.te 文件中添加策略。

1、自定义文件type

        这里我们以特定文件 /data/local/tmp/vsomeip-vehicle.log 定制 SELinux 安全策略。

定义新的文件类型

源码位置:/device/{厂商}/sepolicy/vendor/{设备名称}/file.te

# 在 file.te 文件中定义新的文件类型 vsomeip_data_file
type vsomeip_data_file, file_type, data_file_type, core_data_file_type, mlstrustedobject;

        这里在 file.te 文件中定义新的文件类型 vsomeip_data_file,该类型继承多个父类型:file_type, data_file_type, core_data_file_type, mlstrustedobject。 

设置文件的安全上下文

源码位置:/device/{厂商}/sepolicy/vendor/{设备名称}/file_contexts

# 在 file_contexts 文件中绑定文件的安全上下文
/data/local/tmp/vsomeip-vehicle.log u:object_r:vsomeip_data_file:s0

        在 file_contexts 文件中为 /data/local/tmp/vsomeip-vehicle.log 指定安全标签 u:object_r:vsomeip_data_file:s0。

添加策略 

源码位置:/device/{厂商}/sepolicy/vendor/{设备名称}/vsomeip-vehicle.te

 # 在 vsomeip-vehicle.te 文件中添加策略
allow vsomeip-vehicle vsomeip_data_file:file { append getattr open };

        在 vsomeip-vehicle.te 文件中添加策略,允许 vsomeip-vehicle 访问 vsomeip_data_file 类型的文件。 

2、自定义init服务type

        这里我们自定义一个 init 启动的服务 demo_service,对应的执行档是 /system/bin/demo。首先需要在 vendor 目录下中创建 demo.te 文件。

定义新的类型

源码位置:/device/{厂商}/sepolicy/vendor/demo.te 

# 定义新的类型
type demo, domain;
type demo_exec, exec_type, file_type;# 允许 demo 访问 demo_exec
allow demo demo_exec: file { execute read };

         这里修改 demo.te文件,定义demo 类型,init 启动 service 时类型转换。

设置文件的安全上下文

源码位置:/device/{厂商}/sepolicy/vendor/file_contexts

# 在 file_contexts 文件中绑定文件的安全上下文
/system/bin/demo u:object_r:demo_exec:s0

        到这里其实 SELinux 的策略其实已经修改完成了,但是还需要修改 init.rc 和 Android.mk 文件。在 init.rc 文件中定义 demo_service 并设置类型转换。

定义 init.rc 文件中的服务

service demo /system/bin/democlass mainuser rootgroup roottype demo

        在 Android.mk 文件中添加 BOARD_SEPOLICY_DIRS 目录,以确保 demo.te 文件被编译。

 修改 Android.mk 文件

LOCAL_PATH := $(call my-dir)include $(CLEAR_VARS)LOCAL_MODULE := sepolicyLOCAL_SRC_FILES := \$(wildcard $(LOCAL_PATH)/vendor/*.te)LOCAL_MODULE_CLASS := ETC
LOCAL_MODULE_PATH := $(TARGET_OUT_ETC)/selinux
LOCAL_MODULE_TAGS := optionalBOARD_SEPOLICY_DIRS += $(LOCAL_PATH)/vendorinclude $(BUILD_PREBUILT)
  • 确保一致性:确保 demo 和 demo_exec 的定义与系统中的其他策略一致。确认 /system/bin/demo 的路径正确无误。
  • 重新加载策略:修改完文件后,可能需要重新加载 SELinux 策略或重启设备以使更改生效。使用命令 semodule -i <模块文件> 重新加载模块。
  • 测试验证:修改后,进行测试以确保 demo_service 能够正确启动并访问 /system/bin/demo 文件。检查日志文件(如 /var/log/audit/audit.log)以获取详细信息。
  • 错误处理:如果遇到任何 SELinux 相关的错误,检查日志文件以获取详细信息,并根据错误提示进行调整。 

3、自定义属性type

        这里我们实现一个自定义的 native service demo 并设置一个自定义的系统属性 demo.setting.case1。首先同样需要在 vendor 目录下中创建 property.te 文件。

定义新的系统属性类型

源码位置:/device/{厂商}/sepolicy/vendor/property.te

# 定义 system property 类型
type demo_prop, property_type;

绑定系统属性的安全上下文 

源码位置:/device/{厂商}/sepolicy/vendor/property_contexts

# 绑定 demo.setting.case1 的安全上下文
demo.setting.case1 u:object_r:demo_prop:s0

添加权限并使用宏 

源码位置:/device/{厂商}/sepolicy/vendor/demo.te 

        这里我们使用上面的 demo.te 文件,在其中添加对应权限,可以使用 set_prop 宏。

# 允许 demo 访问 demo_prop
allow demo demo_prop: property { setprop };# 使用 set_prop 宏
set_prop(demo, demo_prop);# 允许其他 domain 获取 demo_prop
allow other_domain demo_prop: property getprop;

        在其他的 domain 里面需要读取,可以 get_prop 宏获取相关属性。

get_prop(xxxx, demo_prop);

4、自定义系统服务type

        这里我们实现一个 native service demo 并对外提供服务。同样需要在对应目录下创建 service.te 文件,然后在 service.te 中定义 service 类型。

定义新的服务类型

文件位置: /device/{厂商}/sepolicy/vendor/service.te

# 定义新的服务类型
type demo_service, service_manager_type;

绑定服务的安全上下文 

文件位置: /device/{厂商}/sepolicy/vendor/service_contexts

demo u:object_r:demo_service:s0

声明 Binder 权限 

文件位置: /device/{厂商}/sepolicy/vendor/demo.te

        这里我们同样在 demo.te 文件添加对应的 Binder 权限。

# 允许 demo 使用 Binder
binder_use(demo);# 允许 demo 调用其他域的 Binder 服务
binder_call(demo, binderservicedomain);# 允许 demo 提供 Binder 服务
binder_service(demo);# 允许 demo 进程添加 demo 服务
allow demo demo_service:service_manager add;

5、自定义系统设备节点type

        这里我们实现一个 native service 访问一个专属的字符设备 /dev/demo,同样在对应目录下创建 device.te 文件,然后在 device.te 中定义新的设备类型。

定义新的设备类型

文件位置: /device/{厂商}/sepolicy/vendor/device.te

# 定义新的设备类型
type demo_device, dev_type;

绑定设备的安全上下文 

文件位置: /device/{厂商}/sepolicy/vendor/file_contexts

/dev/demo u:object_r:demo_device:s0

添加权限

文件位置: /device/{厂商}/sepolicy/vendor/demo.te

        声明 demo 使用 demo_device 的权限,这里我们同样以 demo.te 为例:

# 允许 demo 访问 demo_device
allow demo demo_device:chr_file rw_file_perms;

6、自定义socket type

        这里我们实现一个 native service 通过 init 创建一个 socket 并绑定在 /dev/socket/demo,同时允许某些进程访问该 socket。

定义新的 socket 类型

文件位置: /device/{厂商}/sepolicy/vendor/file.te

# 定义新的 socket 类型
type demo_socket, file_type;

绑定 socket 的安全上下文

文件位置: /device/{厂商}/sepolicy/vendor/file_contexts

/dev/socket/demo u:object_r:demo_socket:s0

添加权限

文件位置: /device/{厂商}/sepolicy/vendor/demo.te

        添加 appdomain 访问 demo_socket 的权限:

# 允许 appdomain 连接和写入 demo_socket
allow appdomain demo_socket:unix_stream_socket { connectto write };

定义 demo 服务

文件位置: /device/{厂商}/sepolicy/vendor/init.rc

        在 init.rc 文件中定义 demo 服务并创建 socket。

service demo /system/bin/democlass mainuser rootgroup rootsocket demo /dev/socket/demo stream 0660 demo demo

绑定可执行文件的安全上下文

文件位置: /device/{厂商}/sepolicy/vendor/file_contexts 

/system/bin/demo u:object_r:demo_exec:s0

        对于添加权限的类型就先介绍这么多,以后在项目中遇到相关问题会继续更新的。


http://www.mrgr.cn/news/55125.html

相关文章:

  • 智能安全配电装置在老旧建筑防火中的应用
  • 从0开始深度学习(11)——多层感知机
  • Java比较两个Excel是否内容一致
  • C++智能指针及其应用
  • 【网安第三章】——XSS
  • 多IP连接
  • 组装电脑主板配置全解析:从入门到精通
  • SSDF攻击及防御PPT及讲稿
  • 【漏洞复现】华望云 会议管理平台 deptactionlist 后台SQL注入漏洞
  • 基于单片机的多功能鱼缸控制系统设计
  • Java数组的特性与实现、与其他语言的区别、多维数组的遍历、底层实现及其内存管理
  • YoloV9改进策略:归一化改进| ContraNormYoloV8中的创新应用(全网首发)
  • Java反射深入学习
  • c语言字符串函数strstr,strtok,strerror
  • AIGC实战——世界模型(World Model)
  • MiniConda 的安装与使用
  • 【学术会议投稿】Java Web开发实战:从零到一构建动态网站
  • 【学术会议投稿】机器学习框架终极指南:PyTorch vs TensorFlow vs Keras vs Scikit-learn
  • Anomalib 1.x 系列之二:自定义数据
  • 手动部署Java项目、nginx前端和mysql数据库到centos虚拟机
  • 简单的界面用于控制自动点击器
  • 二叉树算法之 Fenwick 树(Binary Indexed Tree, BIT)详细解读
  • 在Smarty模板中如何用自定义函数
  • C#/.NET/.NET Core技术前沿周刊 | 第 10 期(2024年10.14-10.20)
  • JS数组去重
  • 【算法】小红的ABC