Android 10.0 授权app获取cpu温度和电池温度功能实现

1.前言

在10.0的系统定制化开发中,在开发某些产品的老化应用的时候,需要app获取cpu温度和电池 温度等功能,有些产品带温度传感器,大部分的产品都不包含温度传感器,所以就需要读取 sys下的相关节点来获取相关温度值

2.授权app获取cpu温度和电池温度功能实现的核心类

device/mediatek/sepolicy/basic/neverallows/non_plat/neverallows.te
device/mediatek/sepolicy/basic/neverallows/plat_public/neverallows.te
device/mediatek/sepolicy/bsp/non_plat/untrusted_app_27.te
system/sepolicy/prebuilts/api/30.0/private/app_neverallows.te
system/sepolicy/prebuilts/api/30.0/private/coredomain.te
system/sepolicy/private/app_neverallows.te
system/sepolicy/private/coredomain.te

3.授权app获取cpu温度和电池温度功能实现的核心功能分析和实现

在Android系统中,获取CPU温度的方法并没有直接提供给我们开发者,我们可以通过两种方式来获取Cpu温度: 1、 通过读取手机传感器 sensor 的温度近似于手机CPU温度(当然这种方式只是一个近似的值,并不准确,同时还需要手机具备相应的传感器) 2、 通过读取CPU信息来获取(这种方式相较于前一种方式获取到的数据准确很多,但是还是有一定的局限性。) 通过研究发现,CPU的信息基本都是在/sys/class/thermal/目录下,通过adb shell、cat相关命令可以拿到一些手机的CPU信息,基本步骤如下: 1、打开终端命令窗口,如windows下的cmd程序。 2、输入adb shell,回车。 3、输入cat /sys/class/thermal/thermal_zone7/type,回车。其中7只是一个示例,不同的手机可能会有区别。此命令可以获取相关的硬件类别。 4、输入cat /sys/class/thermal/thermal_zone7/temp,回车。就可以获取对应的温度值。 首选看下第一种方式,通过温度传感器来获取cpu温度的功能实现

      SensorManager sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
        List<Sensor> sensorList = sensorManager.getSensorList(Sensor.TYPE_ALL);
        for (Sensor sensor : sensorList) {
            Log.e(TAG,"name:"+sensor.getName());
            if (sensor.getName().contains("thermal-zone")) {
                cpuTemperatureSensor = sensor;
                break;
            }
        }
        SensorEventListener cpuTemperatureListener = new SensorEventListener() {
            @Override
            public void onSensorChanged(SensorEvent event) {
                // 获取CPU温度
                float temperature = event.values[0];
                Log.e(TAG,"temperature:"+temperature);
                // 处理温度数据
                // ...
            }

            @Override
            public void onAccuracyChanged(Sensor sensor, int accuracy) {
                // 温度精度变化回调
            }
        };
        sensorManager.registerListener(cpuTemperatureListener, cpuTemperatureSensor, SensorManager.SENSOR_DELAY_NORMAL);

或者这样获取温度传感器:
    for (Sensor s : allSensors) {
        if (Build.VERSION.SDK_INT > Build.VERSION_CODES.KITKAT) {
            typeName = SensorTypeName.getSensorTypeName(s.getType()) + " " + s.getStringType();
            if (s.getStringType().toUpperCase().indexOf("TEMP") > 0) {
                // 可以看到,这里将包含有TEMP关键字的sensor付给了变量mTempSensor 
                // 而这个mTempSensor 就是我们需要的温度传感器
                mTempSensor = s;
            }
        } else {
            typeName = SensorTypeName.getSensorTypeName(s.getType()) + " " + s.getType();
        }
        sb.append(String.format("\t类型:%s\n", typeName));
        sb.append(String.format("\t设备名称:%s\n", s.getName()));
        sb.append(String.format("\t设备版本:%s\n", s.getVersion()));
        sb.append(String.format("\t供应商:%s\n", s.getVendor()));
        sb.append("\n");
    }
    // 这里我们将所有的传感器都放在一个subStr中,方便查看我们的结果
    tx1.setText(sb.toString());
    // 如果传感器不为空,那么我们就可添加一个监听,获取传感器的温度情况
    if (mTempSensor != null) {
        sm.registerListener(mSensorEventListener, mTempSensor
                , SensorManager.SENSOR_DELAY_GAME);
    }
    // 温度传感器的监听器
    private final SensorEventListener mSensorEventListener = new SensorEventListener() {
      @Override
      public void onSensorChanged(SensorEvent event) {
          if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.KITKAT_WATCH) {
              if (event.sensor.getStringType().toUpperCase().indexOf("TEMP") > 0) {
                  /*温度传感器返回当前的温度,单位是摄氏度(°C)。*/
                  float temperature = event.values[0];
                  Log.e("temperature: ", temperature);
                  sm.unregisterListener(mSensorEventListener, mTempSensor);
              }
          }
      }
 
      @Override
      public void onAccuracyChanged(Sensor sensor, int accuracy) {
      }
  };

通过发现好多手机设备不支持温度传感器,所以这样就获取不到当前的温度值,就需要读取 /sys/class/thermal/thermal_zone*/temp的值来判断当前的cpu温度的值,接下来看下 具体的代码实现

    public List<String> getThermalInfo() {
        List<String> result = new ArrayList<>();
        BufferedReader br = null;

        try {
            File dir = new File("/sys/class/thermal/");
            File[] files = dir.listFiles(new FileFilter() {
                @Override
                public boolean accept(File file) {
                    if (Pattern.matches("thermal_zone[0-9]+", file.getName())) {
                        return true;
                    }
                    return false;
                }
            });

            final int SIZE = files.length;
            String line = null;
            String type = null;
            String temp = null;
            for (int i = 0; i < SIZE; i++) {
                br = new BufferedReader(new FileReader("/sys/class/thermal/thermal_zone" + i + "/type"));
                line = br.readLine();
                if (line != null) {
                    type = line;
                }

                br = new BufferedReader(new FileReader("/sys/class/thermal/thermal_zone" + i + "/temp"));
                line = br.readLine();
                if (line != null) {
                    long temperature = Long.parseLong(line);
                    if (temperature < 0) {
                        temp = "Unknow";
                    } else {
                        temp = (float) (temperature / 1000.0) + "°C";
                    }
                }
                result.add(type + " : " + temp);
            }
            br.close();
        } catch (Exception e) {
            result.add(e.toString());
        } finally {
            if (br != null) {
                try {
                    br.close();
                } catch (Exception e) {
                    e.printStackTrace();
                }
            }
        }
        return result;
    }

在通过第二种方式来获取cpu温度和电池温度的时候,在app读取/sys/class/thermal/thermal_zone*/temp 的过程中,会出去读不到值,报selinux权限的问题,所以就需要根据报错信息来解决这个问题 首选可以通过adb命令禁用selinux来看是否能正常读取到cpu和电池温度,如果可以正常读取到 就证明需要根据log来授予selinux权限了,接下来看下具体的补丁

--- a/device/mediatek/sepolicy/basic/neverallows/non_plat/neverallows.te
+++ b/device/mediatek/sepolicy/basic/neverallows/non_plat/neverallows.te
@@ -40,6 +40,7 @@ full_treble_only(`
     ueventd
     vendor_init
     vold
+    untrusted_app_27
     } sysfs:file *;
--- a/device/mediatek/sepolicy/basic/neverallows/plat_public/neverallows.te
+++ b/device/mediatek/sepolicy/basic/neverallows/plat_public/neverallows.te
@@ -15,6 +15,7 @@ full_treble_only(`
     -init
     -ueventd
     -vold
+    -untrusted_app_27
     } sysfs:file *;
--- a/device/mediatek/sepolicy/bsp/non_plat/untrusted_app_27.te
+++ b/device/mediatek/sepolicy/bsp/non_plat/untrusted_app_27.te
@@ -12,3 +12,7 @@ get_prop(untrusted_app_27, vendor_mtk_atm_ipaddr_prop)
 # Operation : eMBMS Migration
 # Purpose :allow EXPWAY middleware to access the socket
 allow untrusted_app_27 radio:unix_stream_socket connectto;
+allow untrusted_app_27 sysfs_therm:dir { search read open };
+allow untrusted_app_27 sysfs:dir { search read open };
+allow untrusted_app_27 sysfs_therm:file { open read getattr };
+allow untrusted_app_27 sysfs:file { open read getattr };
--- a/system/sepolicy/prebuilts/api/30.0/private/app_neverallows.te
+++ b/system/sepolicy/prebuilts/api/30.0/private/app_neverallows.te
@@ -93,7 +93,7 @@ neverallow all_untrusted_apps sysfs_net:file no_rw_file_perms;
 neverallow all_untrusted_apps sysfs_type:file { no_w_file_perms no_x_file_perms };
 
 # Apps may never access the default sysfs label.
-neverallow all_untrusted_apps sysfs:file no_rw_file_perms;
+neverallow { all_untrusted_apps -untrusted_app_27 } sysfs:file no_rw_file_perms;
--- a/system/sepolicy/prebuilts/api/30.0/private/coredomain.te
+++ b/system/sepolicy/prebuilts/api/30.0/private/coredomain.te
@@ -108,6 +108,7 @@ full_treble_only(`
     -init
     -ueventd
     -vold
+    -untrusted_app_27
   } sysfs:file no_rw_file_perms;
--- a/system/sepolicy/private/app_neverallows.te
+++ b/system/sepolicy/private/app_neverallows.te
@@ -93,7 +93,7 @@ neverallow all_untrusted_apps sysfs_net:file no_rw_file_perms;
 neverallow all_untrusted_apps sysfs_type:file { no_w_file_perms no_x_file_perms };
 
 # Apps may never access the default sysfs label.
-neverallow all_untrusted_apps sysfs:file no_rw_file_perms;
+neverallow { all_untrusted_apps -untrusted_app_27 } sysfs:file no_rw_file_perms;
--- a/system/sepolicy/private/coredomain.te
+++ b/system/sepolicy/private/coredomain.te
@@ -108,6 +108,7 @@ full_treble_only(`
     -init
     -ueventd
     -vold
+    -untrusted_app_27
   } sysfs:file no_rw_file_perms;

通过上述的这些文件对selinux权限的授权,发现在读取/sys/class/thermal/thermal_zone*/temp 的节点的时候,就能够正常读取当前的cpu和电池的温度,得到的值除以1000就是摄氏度值, 在节点的type类型中,mtktsbattery代表是电池温度,mtktscpu代表是cpu温度,所以这样就 可以轮询获取温度值就可以了

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:/a/950566.html

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

IDEA 撤销 merge 操作(详解)

作为一个开发者&#xff0c;我们都知道Git是一个非常重要的版本控制工具&#xff0c;尤其是在协作开发的过程中。然而&#xff0c;在使用Git的过程中难免会踩一些坑&#xff0c;今天我来给大家分享一个我曾经遇到的问题&#xff1a;在使用IDEA中进行merge操作后如何撤销错误的合…

WD5105同步降压转换器:9.2V-95V宽电压输入,4.5A大电流输出,95%高效率,多重保护功能

概述 • WD5105同步降压转换器 • 封装形式&#xff1a;QFN-20封装 • 应用场景&#xff1a;适用于车载充电器、电动车仪表、电信基站电源、电源适配器等 性能特点 • 输入电压范围&#xff1a;9.2V至95V • 输出电流&#xff1a;可提供4.5A连续负载电流 • 效率&#xff1a;高…

【C++】B2108 图像模糊处理

博客主页&#xff1a; [小ᶻ☡꙳ᵃⁱᵍᶜ꙳] 本文专栏: C 文章目录 &#x1f4af;前言&#x1f4af;题目描述题目内容输入格式输出格式示例输入&#xff1a;输出&#xff1a; &#x1f4af;题目分析问题拆解 &#x1f4af;我的做法代码实现代码分析 &#x1f4af;老师的做法…

怎么把word试题转成excel?

在教育行业、学校管理以及在线学习平台中&#xff0c;试题库的高效管理是一项核心任务。许多教育工作者和系统开发人员常常面临将 Word 中的试题批量导入 Excel 的需求。本文将详细介绍如何快速将试题从 Word 转换为 Excel&#xff0c;帮助您轻松解决繁琐的数据整理问题&#x…

minibatch时,损失如何记录

目录 minibatch时&#xff0c;损失如何记录 报错&#xff1a;UnboundLocalError: local variable coef referenced before assignment是什么回事 未溢出则不会报错&#xff0c;可以完整滴运行完成 indent 缩进 炫酷技能&#xff1a;一遍运行&#xff0c;一遍画图 实例1 解释…

Linux : Linux环境开发工具vim / gcc / makefile / gdb / git的使用

Linux环境开发工具的使用 一、操作系统的生态二、程序下载安装&#xff08;一&#xff09;程序安装方式&#xff08;二&#xff09;包管理器 yum / apt 运行原理 三、文本编辑器 vim&#xff08;一&#xff09;认识vim 下的操作模式&#xff08;二&#xff09;命令模式常用的快…

国产游戏崛起,燕云十六移动端1.9上线,ToDesk云电脑先开玩

游戏爱好者的利好消息出新了&#xff01;网易大型武侠仙游《燕云十六声》正式官宣&#xff0c;移动端要在1月9日正式上线了&#xff01;你期待手游版的燕云吗&#xff1f;不妨评论区留言说说你的看法。小编分别花了几个小时在台式机电脑和手机上都试了下&#xff0c;欣赏画面还…

力扣刷题:数组OJ篇(下)

大家好&#xff0c;这里是小编的博客频道 小编的博客&#xff1a;就爱学编程 很高兴在CSDN这个大家庭与大家相识&#xff0c;希望能在这里与大家共同进步&#xff0c;共同收获更好的自己&#xff01;&#xff01;&#xff01; 目录 1.轮转数组&#xff08;1&#xff09;题目描述…

有序数据中插入不确定数据保证数据插入的位置顺序正确排序

解决有序数据中插入不确定数据保证数据插入的位置顺序正确排序 前言 java 数据库中存储自增id 有序的数据&#xff0c; 前端页面基于 id 5和 6 之间新增一条数据&#xff0c;在 id 6 和 7之间新增 2条&#xff0c;或者更复杂的场景&#xff0c;后台接口如何保存数据使得页面数…

python无需验证码免登录12306抢票 --selenium(2)

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 [TOC](python无需验证码免登录12306抢票 --selenium(2)) 前言 提示&#xff1a;这里可以添加本文要记录的大概内容&#xff1a; 就在刚刚我抢的票&#xff1a;2025年1月8日…

DNS协议漏洞利用实验_hust计算机网络安全实验

文章目录 计算机网络安全实验 DNS协议漏洞利用实验 docker使用 建立实验环境docker常用指令 一些注意事项设置本地 DNS 服务器 配置用户计算机设置本地DNS服务器在本地 DNS 服务器中建一个区域 修改主机文件&#xff08;可略&#xff09;netwox实施DNS的用户响应欺骗攻击netwo…

基于MP157AAA的I2C练习

练习要求&#xff1a; 通过I2C分别实现与芯片si7006(获取湿度、温度)和芯片ap3216(获取环境光照强度)的通讯&#xff1b; 1、运行效果 2、分析ap3216如何获取光照强度 2.1、需要操作的寄存器 通过分析手册&#xff0c;需要操作以下寄存器: 0x00&#xff1a;系统配置 0x0C&…

【Linux】深入理解文件系统(超详细)

目录 一.磁盘 1-1 磁盘、服务器、机柜、机房 &#x1f4cc;补充&#xff1a; &#x1f4cc;通常网络中用高低电平&#xff0c;磁盘中用磁化方向来表示。以下是具体说明&#xff1a; &#x1f4cc;如果有一块磁盘要进行销毁该怎么办&#xff1f; 1-2 磁盘存储结构 ​编辑…

网络安全图谱以及溯源算法

​ 本文提出了一种网络攻击溯源框架&#xff0c;以及一种网络安全知识图谱&#xff0c;该图由六个部分组成&#xff0c;G <H&#xff0c;V&#xff0c;A&#xff0c;E&#xff0c;L&#xff0c;S&#xff0c;R>。 1|11.知识图 ​ 网络知识图由六个部分组成&#xff0c…

《Spring Framework实战》7:4.1.2.容器概述

欢迎观看《Spring Framework实战》视频教程 容器概述 该接口表示 Spring IoC 容器&#xff0c;并负责实例化、配置和组装 bean。 容器在组件上获取其指令&#xff0c;以实例化、配置和 通过读取配置元数据进行汇编。可以表示配置元数据 作为带注释的组件类、具有工厂方法的配置…

学生公寓技术规格书如何编写?

学生公寓限电柜的技术规格书主要包括以下内容‌&#xff1a; ‌用电计量计费‌&#xff1a;限电柜可以通过计算机售电管理系统进行用电计量计费&#xff0c;学生需要预交电费&#xff0c;系统会自动将数据传给控电柜和配电箱&#xff0c;对宿舍的电量进行累减计量‌。 ‌时间控…

【HarmonyOS NEXT】鸿蒙应用点9图的处理(draw9patch)

【HarmonyOS NEXT】鸿蒙应用点9图的处理&#xff08;draw9patch&#xff09; 一、前言&#xff1a; 首先在鸿蒙中是不支持安卓 .9图的图片直接使用。只有类似拉伸的处理方案&#xff0c;鸿蒙提供的Image组件有与点九图相同功能的API设置。 可以通过设置resizable属性来设置R…

SpringBoot 使用 Cache 集成 Redis做缓存保姆教程

1. 项目背景 Spring Cache是Spring框架提供的一个缓存抽象层&#xff0c;它简化了缓存的使用和管理。Spring Cache默认使用服务器内存&#xff0c;并无法控制缓存时长&#xff0c;查找缓存中的数据比较麻烦。 因此Spring Cache支持将缓存数据集成到各种缓存中间件中。本文已常…

MySQL事件功能简介

MySQL 的事件调度器&#xff08;Event Scheduler&#xff09;提供了一种便捷的方法来定时执行 SQL 语句&#xff0c;从而实现数据维护、报告生成等自动化操作。本文将详细介绍 MySQL 的事件功能&#xff0c;并说明如何使用 Navicat 管理这些事件。 1. 什么是 MySQL 事件调度器…

高光谱相机的特点

光谱特性 高光谱分辨率&#xff1a;能将光谱范围分割成极窄的波段&#xff0c;光谱分辨率通常达到纳米级甚至亚纳米级&#xff0c;可精确捕捉到不同物质在细微光谱差异上的特征&#xff0c;比如可以区分不同种类的植被因叶绿素含量等差异而在光谱上的细微变化。 多波段探测&a…