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 "speed_limit_configs_writer.h"
17 #include "wifi_common_util.h"
18 #include <fcntl.h>
19 #include <arpa/inet.h>
20 #include <unistd.h>
21 #include "wifi_logger.h"
22 
23 namespace OHOS {
24 namespace Wifi {
25 DEFINE_WIFILOG_LABEL("WifiSpeedLimitConfigsWriter");
26 
27 const int MAX_ARRAY_LENGTH = 256;
28 static const char * const AWARE_CTRL_FILENAME = "/proc/net/aware/aware_ctrl";
29 static const char * const FG_UID_PATH = "/proc/net/aware/fg_uids";
30 static const char * const BG_UID_PATH = "/proc/net/aware/bg_uids";
31 static const char * const BG_PID_PATH = "/proc/net/aware/bg_pids";
32 
SetBgLimitMode(int mode)33 ErrCode SetBgLimitMode(int mode)
34 {
35     int fd = open(AWARE_CTRL_FILENAME, O_RDWR);
36     if (fd < 0) {
37         WIFI_LOGE("open aware ctrl file failed, errno = %{public}d.", errno);
38         return WIFI_OPT_FAILED;
39     }
40 
41     char awareCtrlStr[MAX_ARRAY_LENGTH] = {0};
42     int ret = snprintf_s(awareCtrlStr, sizeof(awareCtrlStr), MAX_ARRAY_LENGTH - 1, "1:%d", mode);
43     if (ret == -1) {
44         WIFI_LOGE("SetBgLimitMode snprintf_s failed.");
45         close(fd);
46         return WIFI_OPT_FAILED;
47     }
48 
49     int len = strlen(awareCtrlStr);
50     if (write(fd, awareCtrlStr, len) != len) {
51         WIFI_LOGE("write awareCtrlStr failed, errno = %{public}d.", errno);
52         close(fd);
53         return WIFI_OPT_FAILED;
54     }
55     close(fd);
56     return WIFI_OPT_SUCCESS;
57 }
58 
SetBgLimitIdList(std::vector<int> idList,int type)59 void SetBgLimitIdList(std::vector<int> idList, int type)
60 {
61     switch (type) {
62         case SET_BG_UID:
63             SetUidPids(BG_UID_PATH, idList.data(), static_cast<int>(idList.size()));
64             break;
65         case SET_BG_PID:
66             SetUidPids(BG_PID_PATH, idList.data(), static_cast<int>(idList.size()));
67             break;
68         case SET_FG_UID:
69             SetUidPids(FG_UID_PATH, idList.data(), static_cast<int>(idList.size()));
70             break;
71         default:
72             WIFI_LOGD("Unknow type, not handle.");
73             break;
74     }
75 }
76 
SetUidPids(const char * filePath,const int * idArray,int size)77 void SetUidPids(const char *filePath, const int *idArray, int size)
78 {
79     int ret;
80     char tempStr[MAX_ARRAY_LENGTH];
81     char idStr[MAX_ARRAY_LENGTH];
82 
83     for (int i = 0; i < size; ++i) {
84         if (i == 0) {
85             ret = snprintf_s(tempStr, sizeof(tempStr), MAX_ARRAY_LENGTH - 1, "%d", idArray[i]);
86         } else {
87             ret = snprintf_s(tempStr, sizeof(tempStr), MAX_ARRAY_LENGTH - 1, "%s;%d", idStr, idArray[i]);
88         }
89         if (ret == -1) {
90             WIFI_LOGE("SetUidPids failed.");
91             break;
92         }
93 
94         if (strcpy_s(idStr, sizeof(idStr), tempStr) != 0) {
95             break;
96         }
97     }
98 
99     int len = strlen(idStr);
100     if (len <= 0) {
101         return;
102     }
103 
104     int fd = open(filePath, O_RDWR);
105     if (fd < 0) {
106         WIFI_LOGE("open file failed, errno = %{public}d.", errno);
107         return;
108     }
109 
110     if (write(fd, idStr, len) != len) {
111         WIFI_LOGE("write idStr failed, errno = %{public}d.", errno);
112     }
113     close(fd);
114     return;
115 }
116 } // namespace Wifi
117 } // namespace OHOS