1 /*
2 * Copyright (c) 2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "fan_fault_detect.h"
17 #include "thermal_hisysevent.h"
18 #include "thermal_log.h"
19
20 namespace OHOS {
21 namespace PowerMgr {
22
23 const int32_t SENSOR_INVALID_VALUE = -1;
24 const std::string FAN = "fan";
25
OnFanSensorInfoChanged(const FanSensorInfo & report)26 void FanFaultDetect::OnFanSensorInfoChanged(const FanSensorInfo& report)
27 {
28 CheckFanFault(report);
29 }
30
CheckFanFault(const FanSensorInfo & report)31 void FanFaultDetect::CheckFanFault(const FanSensorInfo& report)
32 {
33 for (auto &faultInfo : fanFaultInfoMap_) {
34 if (faultInfo.first == FAN_FAULT_TOO_SLOW) {
35 CheckFanTooSlow(report, faultInfo.second);
36 } else if (faultInfo.first == FAN_FAULT_TOO_FAST) {
37 CheckFanTooFast(report, faultInfo.second);
38 }
39 }
40 }
41
CheckFanTooSlow(const FanSensorInfo & report,const FanSensorInfo & config)42 void FanFaultDetect::CheckFanTooSlow(const FanSensorInfo& report, const FanSensorInfo& config)
43 {
44 if (!CheckFanSensorInfo(report, config)) {
45 return;
46 }
47
48 bool tempHigh = false;
49 for (auto &sensorInfo : config) {
50 if (sensorInfo.first == "fan") {
51 continue;
52 }
53 if (report.at(sensorInfo.first) > sensorInfo.second) {
54 tempHigh = true;
55 break;
56 }
57 }
58 if (report.at(FAN) < config.at(FAN) && tempHigh) {
59 std::string reportInfo = FormatReportInfo(report, config);
60 THERMAL_HILOGE(COMP_SVC, "fan is slow, %{public}s", reportInfo.c_str());
61 WriteFanFaultEvent(FAN_FAULT_TOO_SLOW, reportInfo);
62 }
63 }
64
CheckFanTooFast(const FanSensorInfo & report,const FanSensorInfo & config)65 void FanFaultDetect::CheckFanTooFast(const FanSensorInfo& report, const FanSensorInfo& config)
66 {
67 if (!CheckFanSensorInfo(report, config)) {
68 return;
69 }
70
71 bool tempLow = true;
72 for (auto &sensorInfo : config) {
73 if (sensorInfo.first == "fan") {
74 continue;
75 }
76 if (report.at(sensorInfo.first) > sensorInfo.second) {
77 tempLow = false;
78 break;
79 }
80 }
81 if ((report.at(FAN) > config.at(FAN)) && tempLow) {
82 std::string reportInfo = FormatReportInfo(report, config);
83 THERMAL_HILOGE(COMP_SVC, "fan is fast, %{public}s", reportInfo.c_str());
84 WriteFanFaultEvent(FAN_FAULT_TOO_FAST, reportInfo);
85 }
86 }
87
CheckFanSensorInfo(const FanSensorInfo & report,const FanSensorInfo & config)88 bool FanFaultDetect::CheckFanSensorInfo(const FanSensorInfo& report, const FanSensorInfo& config)
89 {
90 // must config and report fan speed
91 if (GetSensorValue(report, "fan") < 0 || GetSensorValue(config, "fan") < 0) {
92 return false;
93 }
94
95 for (auto &sensorInfo : config) {
96 if (sensorInfo.second < 0) {
97 return false;
98 }
99 // config and report info must match
100 if (GetSensorValue(report, sensorInfo.first) < 0) {
101 return false;
102 }
103 }
104
105 return true;
106 }
107
GetSensorValue(const FanSensorInfo & map,const std::string & name)108 int32_t FanFaultDetect::GetSensorValue(const FanSensorInfo& map, const std::string& name)
109 {
110 auto iter = map.find(name);
111 if (iter == map.end()) {
112 return SENSOR_INVALID_VALUE;
113 }
114
115 return iter->second;
116 }
117
FormatReportInfo(const FanSensorInfo & report,const FanSensorInfo & config)118 std::string FanFaultDetect::FormatReportInfo(const FanSensorInfo& report, const FanSensorInfo& config)
119 {
120 std::string reportInfo = "Report";
121 for (auto &sensorInfo : config) {
122 reportInfo += " ";
123 reportInfo += sensorInfo.first;
124 reportInfo += ":";
125 reportInfo += std::to_string(report.at(sensorInfo.first));
126 }
127 return reportInfo;
128 }
129
HasFanConfig()130 bool FanFaultDetect::HasFanConfig()
131 {
132 return !fanFaultInfoMap_.empty();
133 }
134
SetFaultInfoMap(FanFaultInfoMap & map)135 void FanFaultDetect::SetFaultInfoMap(FanFaultInfoMap& map)
136 {
137 fanFaultInfoMap_ = map;
138 }
139 } // namespace PowerMgr
140 } // namespace OHOS
141