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 "updater_utils_fuzzer.h"
17
18 #include <fcntl.h>
19 #include <fstream>
20 #include <iostream>
21 #include <sys/stat.h>
22 #include <unistd.h>
23 #include <vector>
24 #include "cJSON.h"
25 #include "json_node.h"
26 #include "log/log.h"
27 #include "utils.h"
28
29 using namespace std::literals;
30 using namespace std;
31 using namespace Updater;
32 using namespace Utils;
33
34 namespace {
CloseStdout(void)35 void CloseStdout(void)
36 {
37 int fd = open("/dev/null", O_RDWR | O_CLOEXEC);
38 if (fd < 0) {
39 return;
40 }
41 dup2(fd, 1);
42 close(fd);
43 }
44
TestTrim(const uint8_t * data,size_t size)45 void TestTrim(const uint8_t* data, size_t size)
46 {
47 Utils::Trim("");
48 Utils::Trim(" ");
49 Utils::Trim("aa ");
50 Utils::Trim(std::string(reinterpret_cast<const char*>(data), size));
51 }
52
TestConvertSha256Hex(void)53 void TestConvertSha256Hex(void)
54 {
55 uint8_t a[1] = {0};
56 a[0] = 1;
57 Utils::ConvertSha256Hex(a, 1);
58 }
59
TestSplitString(void)60 void TestSplitString(void)
61 {
62 Utils::SplitString("aaa\nbbb", "\n");
63 }
64
TestMkdirRecursive(void)65 void TestMkdirRecursive(void)
66 {
67 Utils::MkdirRecursive("/data/xx?xx", S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH);
68 }
69
TestString2Int(void)70 void TestString2Int(void)
71 {
72 Utils::String2Int<int>("", 10); // 10 : size
73 Utils::String2Int<int>("0x01", 10); // 10 : size
74 }
75
TestGetFilesFromDirectory(void)76 void TestGetFilesFromDirectory(void)
77 {
78 std::vector<std::string> files;
79 Utils::SaveLogs();
80 Utils::CompressLogs("/data/updater/log/updater_log_test");
81 Utils::GetFilesFromDirectory("/data/updater/log", files, true);
82 }
83
TestRemoveDir(void)84 void TestRemoveDir(void)
85 {
86 string path = "";
87 Utils::RemoveDir(path);
88 path = "/data/updater/utils/nonExistDir";
89 Utils::RemoveDir(path);
90 path = "/data/updater/rmDir";
91 int ret = mkdir(path.c_str(), S_IRWXU | S_IRGRP | S_IXGRP | S_IROTH | S_IXOTH);
92 if (ret == 0) {
93 ofstream tmpFile;
94 string filePath = path + "/tmpFile";
95 tmpFile.open(filePath.c_str());
96 if (tmpFile.is_open()) {
97 tmpFile.close();
98 Utils::RemoveDir(path);
99 }
100 }
101 }
102
TestIsUpdaterMode(void)103 void TestIsUpdaterMode(void)
104 {
105 Utils::IsUpdaterMode();
106 }
107
TestIsFileExist(void)108 void TestIsFileExist(void)
109 {
110 Utils::IsFileExist("/bin/test_updater");
111 Utils::IsFileExist("/bin/updater_binary");
112 }
113
TestIsDirExist(void)114 void TestIsDirExist(void)
115 {
116 Utils::IsDirExist("/bin/test_updater");
117 Utils::IsDirExist("/bin");
118 Utils::IsDirExist("/bin/");
119 }
120
TestCopyUpdaterLogs(void)121 void TestCopyUpdaterLogs(void)
122 {
123 const std::string sLog = "/data/updater/main_data/updater.tab";
124 const std::string dLog = "/data/updater/main_data/ut_dLog.txt";
125 Utils::CopyUpdaterLogs(sLog, dLog);
126 unlink(dLog.c_str());
127 }
128
TestGetDirSizeForFile(void)129 void TestGetDirSizeForFile(void)
130 {
131 Utils::GetDirSizeForFile("xxx");
132 Utils::GetDirSizeForFile("xxx/xxx");
133 Utils::GetDirSizeForFile("/data/updater/updater/etc/fstab.ut.updater");
134 }
135
TestJsonNodeValueKey(void)136 void TestJsonNodeValueKey(void)
137 {
138 {
139 std::string str = R"({"key": "value1"})";
140 JsonNode node(str);
141 node.Key();
142 node["key"].Key();
143 }
144 {
145 std::string str = R"({"key"})";
146 JsonNode node(str);
147 node.Key();
148 }
149 }
150
TestJsonNodeKey(void)151 void TestJsonNodeKey(void)
152 {
153 std::string str = R"({"key": "value1"})";
154 JsonNode node(str);
155 node["key"];
156 }
157
TestJsonNodeValueTypeStr(void)158 void TestJsonNodeValueTypeStr(void)
159 {
160 std::string str = R"({"key": "value1"})";
161 JsonNode node(str);
162 node["key"].Type();
163 node["key"];
164 }
165
TestJsonNodeValueTypeInt(void)166 void TestJsonNodeValueTypeInt(void)
167 {
168 std::string str = R"({"key": 1})";
169 JsonNode node(str);
170 node["key"].Type();
171 node["key"];
172 }
173
TestJsonNodeValueTypeBool(void)174 void TestJsonNodeValueTypeBool(void)
175 {
176 std::string str = R"({"key": true})";
177 JsonNode node(str);
178 node["key"].Type();
179 node["key"];
180 }
181
TestJsonNodeValueTypeArray(void)182 void TestJsonNodeValueTypeArray(void)
183 {
184 std::string str = R"({"key": [1, true, "value"]})";
185 JsonNode node(str);
186 node["key"].Type();
187 node["key"][0];
188 node["key"][1];
189 node["key"][2]; // 2 : value index
190 }
191
192
TestJsonNodeValueTypeObject(void)193 void TestJsonNodeValueTypeObject(void)
194 {
195 std::string str = R"({"key": {"key" : "value"}}})";
196 JsonNode node(str);
197 node["key"].Type();
198 node["key"]["key"];
199 }
200
TestJsonNodeValueTypeNull(void)201 void TestJsonNodeValueTypeNull(void)
202 {
203 std::string str = R"({"key1": null})";
204 JsonNode node(str);
205 node["key1"].Type();
206 }
207
TestJsonNodeValueTypeUnknow(void)208 void TestJsonNodeValueTypeUnknow(void)
209 {
210 std::string str = R"({"key":})";
211 JsonNode node(str);
212 node.Type();
213 }
214
TestJsonNodeValueTypeJsonNode(void)215 void TestJsonNodeValueTypeJsonNode(void)
216 {
217 std::string str = R"(
218 {
219 "A": "B",
220 "C": {
221 "D": "E",
222 "F": {
223 "G": {
224 "H": "I",
225 "J": 8879,
226 "K": {
227 "L": "M",
228 "N": ["O", "P"]
229 },
230 "L": true
231 }
232 }
233 }
234 })";
235 JsonNode node(str);
236 const JsonNode &nodeC = node["C"];
237 const JsonNode &nodeG = nodeC["F"]["G"];
238 node.Type();
239 node["A"];
240 nodeC["D"];
241 nodeG["H"];
242 nodeG["J"];
243 nodeG["K"]["L"];
244 nodeG["K"]["N"][0];
245 nodeG["K"]["N"][1];
246 nodeG["L"];
247 }
248
TestJsonNodeKey1Type(void)249 void TestJsonNodeKey1Type(void)
250 {
251 std::string str = R"({"key": "value1"})";
252 JsonNode node(str);
253 node["key1"].Type();
254 }
255
TestJsonNodeValueTypeString(void)256 void TestJsonNodeValueTypeString(void)
257 {
258 {
259 std::string str = R"({"key": "value1"})";
260 JsonNode node(str);
261 node["key"].Type();
262 node["key1"].Type();
263 node["key"].Type();
264 }
265 {
266 std::string str = R"({"key": [1]})";
267 JsonNode node(str);
268 node["key"].Type();
269 node["key"][0].Type();
270 node["key"][1].Type();
271 }
272 }
273
TestJsonNodeTypeUnknow(void)274 void TestJsonNodeTypeUnknow(void)
275 {
276 JsonNode node(Fs::path {R"(\invalid)"});
277 node.Type();
278 }
279
TestJsonNodeTypeUnknow1(void)280 void TestJsonNodeTypeUnknow1(void)
281 {
282 JsonNode node(Fs::path {"/data/noexist"});
283 node.Type();
284 }
285
TestJsonNodeFileType(void)286 void TestJsonNodeFileType(void)
287 {
288 constexpr auto invalidContent = R"({ "key" : "value")";
289 constexpr auto invalidJsonPath = "/tmp/tmp.json";
290 {
291 std::ofstream ofs(Fs::path {invalidJsonPath});
292 ofs << invalidContent;
293 ofs.flush();
294 }
295 JsonNode node(Fs::path {invalidJsonPath});
296 node.Type();
297 DeleteFile(invalidJsonPath);
298 }
299
TestJsonNodeOperation(void)300 void TestJsonNodeOperation(void)
301 {
302 std::string str = R"({"key":[1, true, "value"]})";
303 JsonNode node {str};
304 constexpr int intVal = 2;
305 constexpr bool boolVal = false;
306 const char *strVal = "newValue";
307 int idx = 0;
308 node["key"][idx++] = intVal;
309 node["key"][idx++] = boolVal;
310 node["key"][idx++] = strVal;
311 node["key"][--idx];
312 node["key"][--idx];
313 node["key"][--idx];
314 }
315
TestJsonNodeValueIntChange(void)316 void TestJsonNodeValueIntChange(void)
317 {
318 std::string str = R"({"key":1})";
319 JsonNode node {str};
320 constexpr int intVal = 2;
321 node["key"] = intVal;
322 node["key"];
323 }
324
TestJsonNodeValueBoolChange(void)325 void TestJsonNodeValueBoolChange(void)
326 {
327 std::string str = R"({"key":true})";
328 JsonNode node {str};
329 constexpr bool boolVal = false;
330 node["key"] = boolVal;
331 node["key"];
332 }
333
TestJsonNodeValueStrChange(void)334 void TestJsonNodeValueStrChange(void)
335 {
336 std::string str = R"({"key":"value"})";
337 JsonNode node {str};
338 const char *strVal = "newValue";
339 node["key"] = strVal;
340 node["key"];
341 }
342
TestJsonNodeValueArrayChange(void)343 void TestJsonNodeValueArrayChange(void)
344 {
345 std::string str = R"({"key1":{
346 "key2":1,
347 "key3":"value"
348 }})";
349 JsonNode node {str};
350 constexpr int newValue = 2;
351 node["key1"]["key2"] = newValue;
352 node["key1"]["key3"] = "value2";
353 node["key1"]["key2"];
354 node["key1"]["key3"];
355 }
356
TestJsonNodeValueChange(void)357 void TestJsonNodeValueChange(void)
358 {
359 std::string str = R"({"key" : 1})";
360 JsonNode node {str};
361 node["key"] = false;
362 node["key"];
363 node["key"] = "newValue";
364 node["key"];
365 }
366 }
367
368 namespace OHOS {
FuzzUtils(const uint8_t * data,size_t size)369 void FuzzUtils(const uint8_t* data, size_t size)
370 {
371 CloseStdout();
372 TestTrim(data, size);
373 TestConvertSha256Hex();
374 TestSplitString();
375 TestMkdirRecursive();
376 TestString2Int();
377 TestGetFilesFromDirectory();
378 TestRemoveDir();
379 TestIsUpdaterMode();
380 TestIsFileExist();
381 TestIsDirExist();
382 TestCopyUpdaterLogs();
383 TestGetDirSizeForFile();
384 TestJsonNodeValueKey();
385 TestJsonNodeKey();
386 TestJsonNodeValueTypeStr();
387 TestJsonNodeValueTypeInt();
388 TestJsonNodeValueTypeBool();
389 TestJsonNodeValueTypeArray();
390 TestJsonNodeValueTypeObject();
391 TestJsonNodeValueTypeNull();
392 TestJsonNodeValueTypeUnknow();
393 TestJsonNodeValueTypeJsonNode();
394 TestJsonNodeKey1Type();
395 TestJsonNodeValueTypeString();
396 TestJsonNodeTypeUnknow();
397 TestJsonNodeTypeUnknow1();
398 TestJsonNodeFileType();
399 TestJsonNodeOperation();
400 TestJsonNodeValueIntChange();
401 TestJsonNodeValueBoolChange();
402 TestJsonNodeValueStrChange();
403 TestJsonNodeValueArrayChange();
404 TestJsonNodeValueChange();
405 }
406 }
407
408 /* Fuzzer entry point */
LLVMFuzzerTestOneInput(const uint8_t * data,size_t size)409 extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size)
410 {
411 /* Run your code on data */
412 OHOS::FuzzUtils(data, size);
413 return 0;
414 }
415