xref: /aosp_15_r20/hardware/interfaces/thermal/1.0/default/Thermal.cpp (revision 4d7e907c777eeecc4c5bd7cf640a754fac206ff7)
1*4d7e907cSAndroid Build Coastguard Worker /*
2*4d7e907cSAndroid Build Coastguard Worker  * Copyright (C) 2016 The Android Open Source Project
3*4d7e907cSAndroid Build Coastguard Worker  *
4*4d7e907cSAndroid Build Coastguard Worker  * Licensed under the Apache License, Version 2.0 (the "License");
5*4d7e907cSAndroid Build Coastguard Worker  * you may not use this file except in compliance with the License.
6*4d7e907cSAndroid Build Coastguard Worker  * You may obtain a copy of the License at
7*4d7e907cSAndroid Build Coastguard Worker  *
8*4d7e907cSAndroid Build Coastguard Worker  *      http://www.apache.org/licenses/LICENSE-2.0
9*4d7e907cSAndroid Build Coastguard Worker  *
10*4d7e907cSAndroid Build Coastguard Worker  * Unless required by applicable law or agreed to in writing, software
11*4d7e907cSAndroid Build Coastguard Worker  * distributed under the License is distributed on an "AS IS" BASIS,
12*4d7e907cSAndroid Build Coastguard Worker  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13*4d7e907cSAndroid Build Coastguard Worker  * See the License for the specific language governing permissions and
14*4d7e907cSAndroid Build Coastguard Worker  * limitations under the License.
15*4d7e907cSAndroid Build Coastguard Worker  */
16*4d7e907cSAndroid Build Coastguard Worker 
17*4d7e907cSAndroid Build Coastguard Worker #define LOG_TAG "[email protected]"
18*4d7e907cSAndroid Build Coastguard Worker 
19*4d7e907cSAndroid Build Coastguard Worker #include <errno.h>
20*4d7e907cSAndroid Build Coastguard Worker #include <math.h>
21*4d7e907cSAndroid Build Coastguard Worker 
22*4d7e907cSAndroid Build Coastguard Worker #include <vector>
23*4d7e907cSAndroid Build Coastguard Worker 
24*4d7e907cSAndroid Build Coastguard Worker #include <log/log.h>
25*4d7e907cSAndroid Build Coastguard Worker 
26*4d7e907cSAndroid Build Coastguard Worker #include <hardware/hardware.h>
27*4d7e907cSAndroid Build Coastguard Worker #include <hardware/thermal.h>
28*4d7e907cSAndroid Build Coastguard Worker 
29*4d7e907cSAndroid Build Coastguard Worker #include "Thermal.h"
30*4d7e907cSAndroid Build Coastguard Worker 
31*4d7e907cSAndroid Build Coastguard Worker namespace android {
32*4d7e907cSAndroid Build Coastguard Worker namespace hardware {
33*4d7e907cSAndroid Build Coastguard Worker namespace thermal {
34*4d7e907cSAndroid Build Coastguard Worker namespace V1_0 {
35*4d7e907cSAndroid Build Coastguard Worker namespace implementation {
36*4d7e907cSAndroid Build Coastguard Worker 
37*4d7e907cSAndroid Build Coastguard Worker namespace {
38*4d7e907cSAndroid Build Coastguard Worker 
finalizeTemperature(float temperature)39*4d7e907cSAndroid Build Coastguard Worker float finalizeTemperature(float temperature) {
40*4d7e907cSAndroid Build Coastguard Worker     return temperature == UNKNOWN_TEMPERATURE ? NAN : temperature;
41*4d7e907cSAndroid Build Coastguard Worker }
42*4d7e907cSAndroid Build Coastguard Worker 
43*4d7e907cSAndroid Build Coastguard Worker }
44*4d7e907cSAndroid Build Coastguard Worker 
Thermal(thermal_module_t * module)45*4d7e907cSAndroid Build Coastguard Worker Thermal::Thermal(thermal_module_t* module) : mModule(module) {}
46*4d7e907cSAndroid Build Coastguard Worker 
47*4d7e907cSAndroid Build Coastguard Worker // Methods from ::android::hardware::thermal::V1_0::IThermal follow.
getTemperatures(getTemperatures_cb _hidl_cb)48*4d7e907cSAndroid Build Coastguard Worker Return<void> Thermal::getTemperatures(getTemperatures_cb _hidl_cb) {
49*4d7e907cSAndroid Build Coastguard Worker   ThermalStatus status;
50*4d7e907cSAndroid Build Coastguard Worker   status.code = ThermalStatusCode::SUCCESS;
51*4d7e907cSAndroid Build Coastguard Worker   hidl_vec<Temperature> temperatures;
52*4d7e907cSAndroid Build Coastguard Worker 
53*4d7e907cSAndroid Build Coastguard Worker   if (!mModule || !mModule->getTemperatures) {
54*4d7e907cSAndroid Build Coastguard Worker     ALOGI("getTemperatures is not implemented in Thermal HAL.");
55*4d7e907cSAndroid Build Coastguard Worker     _hidl_cb(status, temperatures);
56*4d7e907cSAndroid Build Coastguard Worker     return Void();
57*4d7e907cSAndroid Build Coastguard Worker   }
58*4d7e907cSAndroid Build Coastguard Worker 
59*4d7e907cSAndroid Build Coastguard Worker   ssize_t size = mModule->getTemperatures(mModule, nullptr, 0);
60*4d7e907cSAndroid Build Coastguard Worker   if (size >= 0) {
61*4d7e907cSAndroid Build Coastguard Worker     std::vector<temperature_t> list;
62*4d7e907cSAndroid Build Coastguard Worker     list.resize(size);
63*4d7e907cSAndroid Build Coastguard Worker     size = mModule->getTemperatures(mModule, list.data(), list.size());
64*4d7e907cSAndroid Build Coastguard Worker     if (size >= 0) {
65*4d7e907cSAndroid Build Coastguard Worker       temperatures.resize(list.size());
66*4d7e907cSAndroid Build Coastguard Worker       for (size_t i = 0; i < list.size(); ++i) {
67*4d7e907cSAndroid Build Coastguard Worker         switch (list[i].type) {
68*4d7e907cSAndroid Build Coastguard Worker           case DEVICE_TEMPERATURE_UNKNOWN:
69*4d7e907cSAndroid Build Coastguard Worker             temperatures[i].type = TemperatureType::UNKNOWN;
70*4d7e907cSAndroid Build Coastguard Worker             break;
71*4d7e907cSAndroid Build Coastguard Worker           case DEVICE_TEMPERATURE_CPU:
72*4d7e907cSAndroid Build Coastguard Worker             temperatures[i].type = TemperatureType::CPU;
73*4d7e907cSAndroid Build Coastguard Worker             break;
74*4d7e907cSAndroid Build Coastguard Worker           case DEVICE_TEMPERATURE_GPU:
75*4d7e907cSAndroid Build Coastguard Worker             temperatures[i].type = TemperatureType::GPU;
76*4d7e907cSAndroid Build Coastguard Worker             break;
77*4d7e907cSAndroid Build Coastguard Worker           case DEVICE_TEMPERATURE_BATTERY:
78*4d7e907cSAndroid Build Coastguard Worker             temperatures[i].type = TemperatureType::BATTERY;
79*4d7e907cSAndroid Build Coastguard Worker             break;
80*4d7e907cSAndroid Build Coastguard Worker           case DEVICE_TEMPERATURE_SKIN:
81*4d7e907cSAndroid Build Coastguard Worker             temperatures[i].type = TemperatureType::SKIN;
82*4d7e907cSAndroid Build Coastguard Worker             break;
83*4d7e907cSAndroid Build Coastguard Worker           default:
84*4d7e907cSAndroid Build Coastguard Worker             ALOGE("Unknown temperature %s type", list[i].name);
85*4d7e907cSAndroid Build Coastguard Worker             ;
86*4d7e907cSAndroid Build Coastguard Worker         }
87*4d7e907cSAndroid Build Coastguard Worker         temperatures[i].name = list[i].name;
88*4d7e907cSAndroid Build Coastguard Worker         temperatures[i].currentValue = finalizeTemperature(list[i].current_value);
89*4d7e907cSAndroid Build Coastguard Worker         temperatures[i].throttlingThreshold = finalizeTemperature(list[i].throttling_threshold);
90*4d7e907cSAndroid Build Coastguard Worker         temperatures[i].shutdownThreshold = finalizeTemperature(list[i].shutdown_threshold);
91*4d7e907cSAndroid Build Coastguard Worker         temperatures[i].vrThrottlingThreshold =
92*4d7e907cSAndroid Build Coastguard Worker                 finalizeTemperature(list[i].vr_throttling_threshold);
93*4d7e907cSAndroid Build Coastguard Worker       }
94*4d7e907cSAndroid Build Coastguard Worker     }
95*4d7e907cSAndroid Build Coastguard Worker   }
96*4d7e907cSAndroid Build Coastguard Worker   if (size < 0) {
97*4d7e907cSAndroid Build Coastguard Worker     status.code = ThermalStatusCode::FAILURE;
98*4d7e907cSAndroid Build Coastguard Worker     status.debugMessage = strerror(-size);
99*4d7e907cSAndroid Build Coastguard Worker   }
100*4d7e907cSAndroid Build Coastguard Worker   _hidl_cb(status, temperatures);
101*4d7e907cSAndroid Build Coastguard Worker   return Void();
102*4d7e907cSAndroid Build Coastguard Worker }
103*4d7e907cSAndroid Build Coastguard Worker 
getCpuUsages(getCpuUsages_cb _hidl_cb)104*4d7e907cSAndroid Build Coastguard Worker Return<void> Thermal::getCpuUsages(getCpuUsages_cb _hidl_cb) {
105*4d7e907cSAndroid Build Coastguard Worker   ThermalStatus status;
106*4d7e907cSAndroid Build Coastguard Worker   hidl_vec<CpuUsage> cpuUsages;
107*4d7e907cSAndroid Build Coastguard Worker   status.code = ThermalStatusCode::SUCCESS;
108*4d7e907cSAndroid Build Coastguard Worker 
109*4d7e907cSAndroid Build Coastguard Worker   if (!mModule || !mModule->getCpuUsages) {
110*4d7e907cSAndroid Build Coastguard Worker     ALOGI("getCpuUsages is not implemented in Thermal HAL");
111*4d7e907cSAndroid Build Coastguard Worker     _hidl_cb(status, cpuUsages);
112*4d7e907cSAndroid Build Coastguard Worker     return Void();
113*4d7e907cSAndroid Build Coastguard Worker   }
114*4d7e907cSAndroid Build Coastguard Worker 
115*4d7e907cSAndroid Build Coastguard Worker   ssize_t size = mModule->getCpuUsages(mModule, nullptr);
116*4d7e907cSAndroid Build Coastguard Worker   if (size >= 0) {
117*4d7e907cSAndroid Build Coastguard Worker     std::vector<cpu_usage_t> list;
118*4d7e907cSAndroid Build Coastguard Worker     list.resize(size);
119*4d7e907cSAndroid Build Coastguard Worker     size = mModule->getCpuUsages(mModule, list.data());
120*4d7e907cSAndroid Build Coastguard Worker     if (size >= 0) {
121*4d7e907cSAndroid Build Coastguard Worker       list.resize(size);
122*4d7e907cSAndroid Build Coastguard Worker       cpuUsages.resize(size);
123*4d7e907cSAndroid Build Coastguard Worker       for (size_t i = 0; i < list.size(); ++i) {
124*4d7e907cSAndroid Build Coastguard Worker         cpuUsages[i].name = list[i].name;
125*4d7e907cSAndroid Build Coastguard Worker         cpuUsages[i].active = list[i].active;
126*4d7e907cSAndroid Build Coastguard Worker         cpuUsages[i].total = list[i].total;
127*4d7e907cSAndroid Build Coastguard Worker         cpuUsages[i].isOnline = list[i].is_online;
128*4d7e907cSAndroid Build Coastguard Worker       }
129*4d7e907cSAndroid Build Coastguard Worker     } else {
130*4d7e907cSAndroid Build Coastguard Worker       status.code = ThermalStatusCode::FAILURE;
131*4d7e907cSAndroid Build Coastguard Worker       status.debugMessage = strerror(-size);
132*4d7e907cSAndroid Build Coastguard Worker     }
133*4d7e907cSAndroid Build Coastguard Worker   }
134*4d7e907cSAndroid Build Coastguard Worker   if (size < 0) {
135*4d7e907cSAndroid Build Coastguard Worker     status.code = ThermalStatusCode::FAILURE;
136*4d7e907cSAndroid Build Coastguard Worker     status.debugMessage = strerror(-size);
137*4d7e907cSAndroid Build Coastguard Worker   }
138*4d7e907cSAndroid Build Coastguard Worker   _hidl_cb(status, cpuUsages);
139*4d7e907cSAndroid Build Coastguard Worker   return Void();
140*4d7e907cSAndroid Build Coastguard Worker }
141*4d7e907cSAndroid Build Coastguard Worker 
getCoolingDevices(getCoolingDevices_cb _hidl_cb)142*4d7e907cSAndroid Build Coastguard Worker Return<void> Thermal::getCoolingDevices(getCoolingDevices_cb _hidl_cb) {
143*4d7e907cSAndroid Build Coastguard Worker   ThermalStatus status;
144*4d7e907cSAndroid Build Coastguard Worker   status.code = ThermalStatusCode::SUCCESS;
145*4d7e907cSAndroid Build Coastguard Worker   hidl_vec<CoolingDevice> coolingDevices;
146*4d7e907cSAndroid Build Coastguard Worker 
147*4d7e907cSAndroid Build Coastguard Worker   if (!mModule || !mModule->getCoolingDevices) {
148*4d7e907cSAndroid Build Coastguard Worker     ALOGI("getCoolingDevices is not implemented in Thermal HAL.");
149*4d7e907cSAndroid Build Coastguard Worker     _hidl_cb(status, coolingDevices);
150*4d7e907cSAndroid Build Coastguard Worker     return Void();
151*4d7e907cSAndroid Build Coastguard Worker   }
152*4d7e907cSAndroid Build Coastguard Worker 
153*4d7e907cSAndroid Build Coastguard Worker   ssize_t size = mModule->getCoolingDevices(mModule, nullptr, 0);
154*4d7e907cSAndroid Build Coastguard Worker   if (size >= 0) {
155*4d7e907cSAndroid Build Coastguard Worker     std::vector<cooling_device_t> list;
156*4d7e907cSAndroid Build Coastguard Worker     list.resize(size);
157*4d7e907cSAndroid Build Coastguard Worker     size = mModule->getCoolingDevices(mModule, list.data(), list.size());
158*4d7e907cSAndroid Build Coastguard Worker     if (size >= 0) {
159*4d7e907cSAndroid Build Coastguard Worker       list.resize(size);
160*4d7e907cSAndroid Build Coastguard Worker       coolingDevices.resize(list.size());
161*4d7e907cSAndroid Build Coastguard Worker       for (size_t i = 0; i < list.size(); ++i) {
162*4d7e907cSAndroid Build Coastguard Worker         switch (list[i].type) {
163*4d7e907cSAndroid Build Coastguard Worker           case FAN_RPM:
164*4d7e907cSAndroid Build Coastguard Worker             coolingDevices[i].type = CoolingType::FAN_RPM;
165*4d7e907cSAndroid Build Coastguard Worker             break;
166*4d7e907cSAndroid Build Coastguard Worker           default:
167*4d7e907cSAndroid Build Coastguard Worker             ALOGE("Unknown cooling device %s type", list[i].name);
168*4d7e907cSAndroid Build Coastguard Worker         }
169*4d7e907cSAndroid Build Coastguard Worker         coolingDevices[i].name = list[i].name;
170*4d7e907cSAndroid Build Coastguard Worker         coolingDevices[i].currentValue = list[i].current_value;
171*4d7e907cSAndroid Build Coastguard Worker       }
172*4d7e907cSAndroid Build Coastguard Worker     }
173*4d7e907cSAndroid Build Coastguard Worker   }
174*4d7e907cSAndroid Build Coastguard Worker   if (size < 0) {
175*4d7e907cSAndroid Build Coastguard Worker     status.code = ThermalStatusCode::FAILURE;
176*4d7e907cSAndroid Build Coastguard Worker     status.debugMessage = strerror(-size);
177*4d7e907cSAndroid Build Coastguard Worker   }
178*4d7e907cSAndroid Build Coastguard Worker   _hidl_cb(status, coolingDevices);
179*4d7e907cSAndroid Build Coastguard Worker   return Void();
180*4d7e907cSAndroid Build Coastguard Worker }
181*4d7e907cSAndroid Build Coastguard Worker 
HIDL_FETCH_IThermal(const char *)182*4d7e907cSAndroid Build Coastguard Worker IThermal* HIDL_FETCH_IThermal(const char* /* name */) {
183*4d7e907cSAndroid Build Coastguard Worker   thermal_module_t* module;
184*4d7e907cSAndroid Build Coastguard Worker   status_t err = hw_get_module(THERMAL_HARDWARE_MODULE_ID,
185*4d7e907cSAndroid Build Coastguard Worker                                const_cast<hw_module_t const**>(
186*4d7e907cSAndroid Build Coastguard Worker                                    reinterpret_cast<hw_module_t**>(&module)));
187*4d7e907cSAndroid Build Coastguard Worker   if (err || !module) {
188*4d7e907cSAndroid Build Coastguard Worker     ALOGE("Couldn't load %s module (%s)", THERMAL_HARDWARE_MODULE_ID,
189*4d7e907cSAndroid Build Coastguard Worker           strerror(-err));
190*4d7e907cSAndroid Build Coastguard Worker   }
191*4d7e907cSAndroid Build Coastguard Worker 
192*4d7e907cSAndroid Build Coastguard Worker   if (err == 0 && module->common.methods->open) {
193*4d7e907cSAndroid Build Coastguard Worker     struct hw_device_t* device;
194*4d7e907cSAndroid Build Coastguard Worker     err = module->common.methods->open(&module->common,
195*4d7e907cSAndroid Build Coastguard Worker                                        THERMAL_HARDWARE_MODULE_ID, &device);
196*4d7e907cSAndroid Build Coastguard Worker     if (err) {
197*4d7e907cSAndroid Build Coastguard Worker       ALOGE("Couldn't open %s module (%s)", THERMAL_HARDWARE_MODULE_ID,
198*4d7e907cSAndroid Build Coastguard Worker             strerror(-err));
199*4d7e907cSAndroid Build Coastguard Worker     } else {
200*4d7e907cSAndroid Build Coastguard Worker       return new Thermal(reinterpret_cast<thermal_module_t*>(device));
201*4d7e907cSAndroid Build Coastguard Worker     }
202*4d7e907cSAndroid Build Coastguard Worker   }
203*4d7e907cSAndroid Build Coastguard Worker   return new Thermal(module);
204*4d7e907cSAndroid Build Coastguard Worker }
205*4d7e907cSAndroid Build Coastguard Worker 
206*4d7e907cSAndroid Build Coastguard Worker }  // namespace implementation
207*4d7e907cSAndroid Build Coastguard Worker }  // namespace V1_0
208*4d7e907cSAndroid Build Coastguard Worker }  // namespace thermal
209*4d7e907cSAndroid Build Coastguard Worker }  // namespace hardware
210*4d7e907cSAndroid Build Coastguard Worker }  // namespace android
211