1 /*
2 * Copyright (c) 2021-2022 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 "battery_backlight.h"
17
18 #include <iostream>
19 #include <fstream>
20 #include <vector>
21 #include <unistd.h>
22 #include <cstring>
23 #include <dirent.h>
24 #include <fcntl.h>
25 #include <sys/stat.h>
26 #include <sys/types.h>
27 #include "errors.h"
28 #include "battery_log.h"
29
30 namespace OHOS {
31 namespace HDI {
32 namespace Battery {
33 namespace V1_1 {
34 namespace {
35 constexpr uint32_t BACKLIGHT_ON = 128;
36 constexpr uint32_t BACKLIGHT_OFF = 0;
37 std::vector<std::string> g_backlightNodeNames;
38 const std::string BACKLIGHT_BASE_PATH = "/sys/class/leds";
39 const std::string MOCK_BACKLIGHT_PATH = "/data/service/el0/display/brightness";
40 std::string g_backlightNode = "backlight";
41 }
42
BatteryBacklight()43 BatteryBacklight::BatteryBacklight()
44 {
45 InitDefaultSysfs();
46 }
47
TraversalBacklightNode()48 void BatteryBacklight::TraversalBacklightNode()
49 {
50 std::string::size_type idx;
51
52 for (auto iter = g_backlightNodeNames.begin(); iter != g_backlightNodeNames.end(); ++iter) {
53 idx = iter->find(g_backlightNode);
54 if (idx == std::string::npos) {
55 BATTERY_HILOGW(FEATURE_CHARGING, "not found backlight node, use default");
56 } else {
57 g_backlightNode = *iter;
58 BATTERY_HILOGD(FEATURE_CHARGING, "backlight node is %{public}s", iter->c_str());
59 }
60 }
61 }
62
InitBacklightSysfs()63 int32_t BatteryBacklight::InitBacklightSysfs()
64 {
65 BATTERY_HILOGD(FEATURE_CHARGING, "start init backlight sysfs");
66 DIR* dir = nullptr;
67 struct dirent* entry = nullptr;
68 int32_t index = 0;
69 const int32_t MAX_SIZE = 64;
70
71 dir = opendir(BACKLIGHT_BASE_PATH.c_str());
72 if (dir == nullptr) {
73 BATTERY_HILOGW(FEATURE_CHARGING, "backlight base path is not exist");
74 return ERR_INVALID_VALUE;
75 }
76
77 while (true) {
78 entry = readdir(dir);
79 if (entry == nullptr) {
80 break;
81 }
82
83 if (strcmp(entry->d_name, ".") == 0 || strcmp(entry->d_name, "..") == 0) {
84 continue;
85 }
86
87 if (entry->d_type == DT_DIR || entry->d_type == DT_LNK) {
88 BATTERY_HILOGI(FEATURE_CHARGING, "init backlight info of %{public}s", entry->d_name);
89 if (index >= MAX_SIZE) {
90 BATTERY_HILOGE(FEATURE_CHARGING, "too many backlight types");
91 break;
92 }
93 g_backlightNodeNames.emplace_back(entry->d_name);
94 index++;
95 }
96 }
97
98 TraversalBacklightNode();
99 BATTERY_HILOGD(FEATURE_CHARGING, "backlight index is %{public}d", index);
100 closedir(dir);
101 BATTERY_HILOGD(FEATURE_CHARGING, "finish init backlight sysfs");
102 return ERR_OK;
103 }
104
TurnOnScreen()105 void BatteryBacklight::TurnOnScreen()
106 {
107 BATTERY_HILOGD(FEATURE_CHARGING, "start turn on screen");
108 HandleBacklight(BACKLIGHT_ON);
109 screenOn_ = true;
110 }
111
TurnOffScreen()112 void BatteryBacklight::TurnOffScreen()
113 {
114 BATTERY_HILOGI(FEATURE_CHARGING, "start turn off screen");
115 HandleBacklight(BACKLIGHT_OFF);
116 screenOn_ = false;
117 }
118
GetScreenState() const119 bool BatteryBacklight::GetScreenState() const
120 {
121 BATTERY_HILOGI(FEATURE_CHARGING, "screen state: %{public}d", screenOn_);
122 return screenOn_;
123 }
124
CreateFile(const std::string & path,const std::string & content)125 void BatteryBacklight::CreateFile(const std::string& path, const std::string& content)
126 {
127 std::ofstream stream(path.c_str());
128 if (!stream.is_open()) {
129 BATTERY_HILOGD(FEATURE_CHARGING, "Cannot create file");
130 return;
131 }
132 stream << content << std::endl;
133 stream.close();
134 }
135
InitDefaultSysfs()136 void BatteryBacklight::InitDefaultSysfs()
137 {
138 BATTERY_HILOGI(FEATURE_CHARGING, "create default brightness path");
139 CreateFile(MOCK_BACKLIGHT_PATH, "127");
140 }
141
InitDevicePah(std::string & path)142 void BatteryBacklight::InitDevicePah(std::string& path)
143 {
144 if (access(path.c_str(), F_OK) == 0) {
145 BATTERY_HILOGI(FEATURE_CHARGING, "system backlight path exist");
146 return;
147 } else {
148 BATTERY_HILOGI(FEATURE_CHARGING, "create mock backlight path");
149 path = MOCK_BACKLIGHT_PATH;
150 return;
151 }
152
153 BATTERY_HILOGI(FEATURE_CHARGING, "exit");
154 }
155
HandleBacklight(uint32_t backlight)156 int32_t BatteryBacklight::HandleBacklight(uint32_t backlight)
157 {
158 FILE* fp = nullptr;
159 int32_t ret = -1;
160 std::string devicePath = BACKLIGHT_BASE_PATH + "/" + g_backlightNode + "/" + "brightness";
161 InitDevicePah(devicePath);
162
163 BATTERY_HILOGD(FEATURE_CHARGING, "backlight value is %{public}d", backlight);
164 fp = fopen(devicePath.c_str(), "w");
165 if (fp != nullptr) {
166 ret = fprintf(fp, "%u\n", backlight);
167 fclose(fp);
168 }
169 if (ret <= 0) {
170 BATTERY_HILOGW(FEATURE_CHARGING, "failed to set backlight");
171 }
172 return ret;
173 }
174 } // namespace V1_1
175 } // namespace Battery
176 } // namespace HDI
177 } // namespace OHOS
178