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 "common/napi_helper.cpp"
17 #include "napi/native_api.h"
18 #include <cstdio>
19 #include <cstring>
20 #include <fcntl.h>
21 #include <ifaddrs.h>
22 #include <js_native_api_types.h>
23 #include <linux/quota.h>
24 #include <net/if.h>
25 #include <string>
26 #include <sys/inotify.h>
27 #include <sys/stat.h>
28 #include <unistd.h>
29 #include <utmp.h>
30 #include <uv.h>
31 #include <hilog/log.h>
32
33 #define ONE 1
34 #define TWO 2
35 #define SIZE_2 2
36 #define PATH "/data/storage/el2/base/files"
37 #define PARAM_777 777
38 #define PARAM_0777 0777
39 #define PARAM_0 0
40 #define PARAM_1 1
41 #define PARAM_2 2
42 #define PARAM_UNNORMAL (-1)
43 #define ERRON_0 0
44 #define SUCCESS 1
45 #define SIZE_64 64
46 #define SEC_TIME 123840
47 #define TEST_MODE 0666
48 #define TEST_AT_FDCWD (-100)
49 #define TEST_ERROR_AT_FDCWD 100
50 #define NO_ERR 0
51 #define SUCCESS 1
52 #define FAIL (-1)
53 #define TEN 10
54 #define TEST_FIFO_MODE 0666
55 #define BUFSIZE 128
56 #define PARAM_3 3
57 #undef LOG_DOMAIN
58 #undef LOG_TAG
59 #define LOG_DOMAIN 0xFEFE
60 #define LOG_TAG "MUSL_STATNDK"
61
Stat(napi_env env,napi_callback_info info)62 static napi_value Stat(napi_env env, napi_callback_info info)
63 {
64 size_t argc = PARAM_1;
65 napi_value args[PARAM_1] = {nullptr};
66 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
67
68 int value;
69 napi_get_value_int32(env, args[PARAM_0], &value);
70 int intValue = PARAM_0;
71 struct stat sb = {PARAM_0};
72 if (value == ONE) {
73 intValue = stat(PATH, &sb);
74 } else if (value == TWO) {
75 intValue = stat(nullptr, &sb);
76 }
77 napi_value result = nullptr;
78 napi_create_int32(env, intValue, &result);
79 return result;
80 }
Stat64(napi_env env,napi_callback_info info)81 static napi_value Stat64(napi_env env, napi_callback_info info)
82 {
83 size_t argc = PARAM_1;
84 napi_value args[PARAM_1] = {nullptr};
85 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
86 int value;
87 napi_get_value_int32(env, args[PARAM_0], &value);
88 int intValue = PARAM_0;
89 struct stat64 sb = {PARAM_0};
90 if (value == ONE) {
91 intValue = stat64(PATH, &sb);
92 } else if (value == TWO) {
93 intValue = stat64(nullptr, &sb);
94 }
95 napi_value result = nullptr;
96 napi_create_int32(env, intValue, &result);
97 return result;
98 }
99
Umask(napi_env env,napi_callback_info info)100 static napi_value Umask(napi_env env, napi_callback_info info)
101 {
102 size_t argc = PARAM_1;
103 napi_value args[PARAM_1] = {nullptr};
104 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
105 int valueFirst;
106 napi_get_value_int32(env, args[PARAM_0], &valueFirst);
107 mode_t mode = PARAM_0;
108 if (valueFirst == PARAM_777) {
109 mode = S_IRWXU | S_IRWXG | S_IRWXO;
110 }
111 mode_t umaskValue = umask(mode);
112 umaskValue = umask(umaskValue);
113
114 int toJs = FAIL;
115 if (umaskValue == mode && valueFirst == PARAM_777) {
116 toJs = SUCCESS;
117 }
118 napi_value result = nullptr;
119 napi_create_int32(env, toJs, &result);
120 return result;
121 }
122
Utimensat(napi_env env,napi_callback_info info)123 static napi_value Utimensat(napi_env env, napi_callback_info info)
124 {
125 int toCppResult = FAIL;
126 char path[] = "/data/storage/el2/base/files/Utimensat.txt";
127 int fd = open(path, O_CREAT);
128
129 struct timespec times[] = {{.tv_nsec = UTIME_OMIT}, {.tv_nsec = UTIME_OMIT}};
130
131 int utimensatValue = utimensat(fd, path, times, PARAM_0);
132 if (utimensatValue == PARAM_0) {
133 toCppResult = SUCCESS;
134 }
135 close(fd);
136 remove(path);
137 napi_value result = nullptr;
138 napi_create_int32(env, toCppResult, &result);
139 return result;
140 }
141
FchModAt(napi_env env,napi_callback_info info)142 static napi_value FchModAt(napi_env env, napi_callback_info info)
143 {
144 char path[] = "/data/storage/el2/base/files/modAt.txt";
145 int df = open(path, O_CREAT, PARAM_0777);
146 int ret = fchmodat(df, path, S_IRUSR, PARAM_0);
147 close(df);
148 remove(path);
149 napi_value result = nullptr;
150 napi_create_int32(env, ret, &result);
151 return result;
152 }
153
FchMod(napi_env env,napi_callback_info info)154 static napi_value FchMod(napi_env env, napi_callback_info info)
155 {
156 char path[] = "/data/storage/el2/base/files/mod.txt";
157 int df = open(path, O_CREAT, PARAM_0777);
158 int ret = fchmod(df, S_IRUSR);
159 close(df);
160 remove(path);
161 napi_value result = nullptr;
162 napi_create_int32(env, ret, &result);
163 return result;
164 }
165
Creat(napi_env env,napi_callback_info info)166 static napi_value Creat(napi_env env, napi_callback_info info)
167 {
168 int backResult;
169 char path[] = "/data/storage/el2/base/files/Fzl.txt";
170 backResult = creat(path, O_CREAT);
171 napi_value result = nullptr;
172 if (backResult != FAIL) {
173 napi_create_int32(env, PARAM_0, &result);
174 } else {
175 napi_create_int32(env, PARAM_UNNORMAL, &result);
176 }
177 remove(path);
178 return result;
179 }
180
Creat64(napi_env env,napi_callback_info info)181 static napi_value Creat64(napi_env env, napi_callback_info info)
182 {
183 int backResult;
184 char path[] = "/data/storage/el2/base/files/Fzl.txt";
185 backResult = creat64(path, O_CREAT);
186 napi_value result = nullptr;
187 if (backResult != FAIL) {
188 napi_create_int32(env, PARAM_0, &result);
189 } else {
190 napi_create_int32(env, PARAM_UNNORMAL, &result);
191 }
192 remove(path);
193 return result;
194 }
195
Chmod(napi_env env,napi_callback_info info)196 static napi_value Chmod(napi_env env, napi_callback_info info)
197 {
198 int returnValue = chmod("/data/storage/el2/base/files", S_IRWXU | S_IRWXG | S_IRWXO);
199 napi_value result;
200 napi_create_int32(env, returnValue, &result);
201 return result;
202 }
203
Fstat(napi_env env,napi_callback_info info)204 static napi_value Fstat(napi_env env, napi_callback_info info)
205 {
206 size_t argc = PARAM_1;
207 napi_value args[PARAM_1] = {nullptr};
208 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
209 size_t length = SIZE_64;
210 size_t stresult = PARAM_0;
211 char path[SIZE_64] = {PARAM_0};
212 napi_get_value_string_utf8(env, args[PARAM_0], path, length, &stresult);
213 struct stat sb = {PARAM_0};
214 int fd = open(path, O_CREAT, PARAM_0777);
215 int value = fstat(fd, &sb);
216 napi_value result;
217 napi_create_int32(env, value, &result);
218 close(fd);
219 return result;
220 }
221
Fstat64(napi_env env,napi_callback_info info)222 static napi_value Fstat64(napi_env env, napi_callback_info info)
223 {
224 size_t argc = PARAM_1;
225 napi_value args[PARAM_1] = {nullptr};
226 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
227 size_t length = SIZE_64;
228 size_t stresult = PARAM_0;
229 char path[SIZE_64] = {PARAM_0};
230 napi_get_value_string_utf8(env, args[PARAM_0], path, length, &stresult);
231 struct stat sb = {PARAM_0};
232 int fd = open(path, O_CREAT, PARAM_0777);
233 int value = fstat64(fd, &sb);
234 napi_value result;
235 napi_create_int32(env, value, &result);
236 close(fd);
237 return result;
238 }
239
Fstatat(napi_env env,napi_callback_info info)240 static napi_value Fstatat(napi_env env, napi_callback_info info)
241 {
242 size_t argc = PARAM_1;
243 napi_value args[PARAM_1] = {nullptr};
244 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
245 size_t length = SIZE_64;
246 size_t stresult = PARAM_0;
247 char path[SIZE_64] = {PARAM_0};
248 napi_get_value_string_utf8(env, args[PARAM_0], path, length, &stresult);
249 struct stat st = {PARAM_0};
250 int fd = open(path, O_CREAT, PARAM_0777);
251 int ret = fstatat(AT_FDCWD, path, &st, PARAM_0);
252 napi_value result;
253 napi_create_int32(env, ret, &result);
254 close(fd);
255 return result;
256 }
257
Fstatat64(napi_env env,napi_callback_info info)258 static napi_value Fstatat64(napi_env env, napi_callback_info info)
259 {
260 size_t argc = PARAM_1;
261 napi_value args[PARAM_1] = {nullptr};
262 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
263 size_t length = SIZE_64;
264 size_t stresult = PARAM_0;
265 char path[SIZE_64] = {PARAM_0};
266 napi_get_value_string_utf8(env, args[PARAM_0], path, length, &stresult);
267 struct stat st = {PARAM_0};
268 int fd = open(path, O_CREAT, PARAM_0777);
269 int ret = fstatat64(AT_FDCWD, path, &st, PARAM_0);
270 napi_value result;
271 napi_create_int32(env, ret, &result);
272 close(fd);
273 return result;
274 }
275
Futimens(napi_env env,napi_callback_info info)276 static napi_value Futimens(napi_env env, napi_callback_info info)
277 {
278 int fd = open("/data/storage/el2/base/files/utime.txt", O_CREAT, PARAM_0777);
279 int ret = futimens(fd, ((struct timespec[PARAM_2]){{.tv_nsec = UTIME_OMIT}, {.tv_nsec = UTIME_OMIT}}));
280 napi_value result;
281 napi_create_int32(env, ret, &result);
282 close(fd);
283 remove("/data/storage/el2/base/files/utime.txt");
284 return result;
285 }
MkFifoAt(napi_env env,napi_callback_info info)286 static napi_value MkFifoAt(napi_env env, napi_callback_info info)
287 {
288 napi_value result = nullptr;
289 size_t argc = PARAM_2;
290 napi_value args[PARAM_2] = {nullptr};
291 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
292 int ret, name;
293 napi_get_value_int32(env, args[PARAM_0], &name);
294 size_t length = SIZE_64;
295 size_t strResult = PARAM_0;
296 char path[length];
297 napi_get_value_string_utf8(env, args[PARAM_1], path, length, &strResult);
298 errno = 0;
299 ret = mkfifoat(name, path, S_IFIFO | TEST_FIFO_MODE);
300 if (ret != 0) {
301 OH_LOG_INFO(LOG_APP, "MUSL mkfifoat ret %{public}d errno : %{public}d", ret, errno);
302 if (ret == -1 && errno == EACCES) {
303 ret = 0;
304 }
305 }
306 unlink(path);
307 remove(path);
308 napi_create_int32(env, ret, &result);
309 return result;
310 }
311
MkNodAt(napi_env env,napi_callback_info info)312 static napi_value MkNodAt(napi_env env, napi_callback_info info)
313 {
314 size_t argc = PARAM_3;
315 napi_value args[PARAM_3] = {nullptr};
316 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
317 int ret = 0;
318 int dirfd = 0;
319 int mode = 0;
320 napi_get_value_int32(env, args[PARAM_0], &dirfd);
321 size_t length = SIZE_64;
322 size_t strResult = PARAM_0;
323 char path[length];
324 napi_get_value_string_utf8(env, args[PARAM_1], path, length, &strResult);
325 napi_get_value_int32(env, args[PARAM_2], &mode);
326 dev_t st_dev = PARAM_0;
327 errno = 0;
328 ret = mknodat(dirfd, path, mode, st_dev);
329 if (ret != 0) {
330 OH_LOG_INFO(LOG_APP, "MUSL mknodat ret %{public}d errno : %{public}d", ret, errno);
331 if (ret == -1 && (errno == EACCES || errno == EPERM || errno == EEXIST)) {
332 ret = 0;
333 }
334 } else {
335 struct stat newFifo = {PARAM_0};
336 errno = 0;
337 ret = stat(path, &newFifo);
338 OH_LOG_INFO(LOG_APP, "MUSL stat ret %{public}d errno : %{public}d", ret, errno);
339 if (errno == EACCES) {
340 ret = 0;
341 }
342 }
343 napi_value result;
344 napi_create_int32(env, ret, &result);
345 unlink(path);
346 return result;
347 }
348
MkNod(napi_env env,napi_callback_info info)349 static napi_value MkNod(napi_env env, napi_callback_info info)
350 {
351 size_t argc = PARAM_2;
352 napi_value args[PARAM_2] = {nullptr};
353 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
354 size_t length = SIZE_64;
355 size_t strResult = PARAM_0;
356 char pathname[PATH_MAX];
357 napi_get_value_string_utf8(env, args[PARAM_0], pathname, length, &strResult);
358 int mode = PARAM_0;
359 napi_get_value_int32(env, args[PARAM_1], &mode);
360 int ret = PARAM_0;
361 napi_value result;
362 napi_create_int32(env, ret, &result);
363 return result;
364 }
365
MkDir(napi_env env,napi_callback_info info)366 static napi_value MkDir(napi_env env, napi_callback_info info)
367 {
368 int ret = PARAM_0;
369 char path[] = "/data/storage/el2/base/files/mkdir1";
370 if (access(path, F_OK) != PARAM_0) {
371 ret = mkdir(path, S_IRWXG);
372 remove(path);
373 } else {
374 remove(path);
375 ret = mkdir(path, S_IRWXG);
376 remove(path);
377 }
378 napi_value result = nullptr;
379 napi_create_int32(env, ret, &result);
380 return result;
381 }
382
MkDirAt(napi_env env,napi_callback_info info)383 static napi_value MkDirAt(napi_env env, napi_callback_info info)
384 {
385 int ret = PARAM_0;
386 char path[] = "/data/storage/el2/base/files/mkdirat1";
387 ret = mkdirat(PARAM_0, path, S_IRWXG);
388 napi_value result = nullptr;
389 napi_create_int32(env, ret, &result);
390 return result;
391 }
392
MkFiFo(napi_env env,napi_callback_info info)393 static napi_value MkFiFo(napi_env env, napi_callback_info info)
394 {
395 size_t argc = PARAM_1;
396 napi_value args[PARAM_1] = {nullptr};
397 napi_get_cb_info(env, info, &argc, args, nullptr, nullptr);
398 size_t lenA;
399 size_t lenV = BUFSIZE;
400 char path[BUFSIZE] = {PARAM_0};
401 napi_get_value_string_utf8(env, args[PARAM_0], path, lenV, &lenA);
402 int ret = PARAM_0;
403 unlink(path);
404 remove(path);
405 napi_value result = nullptr;
406 napi_create_int32(env, ret, &result);
407 return result;
408 }
409
Lstat(napi_env env,napi_callback_info info)410 static napi_value Lstat(napi_env env, napi_callback_info info)
411 {
412 struct stat statbuff;
413 int32_t ret = lstat("/etc/passwd", &statbuff);
414 napi_value result = nullptr;
415 if (ret == FAIL) {
416 napi_create_int32(env, PARAM_UNNORMAL, &result);
417 } else {
418 napi_create_int32(env, PARAM_0, &result);
419 }
420 return result;
421 }
422
Lstat64(napi_env env,napi_callback_info info)423 static napi_value Lstat64(napi_env env, napi_callback_info info)
424 {
425 struct stat statbuff;
426 int32_t ret = lstat64("/etc/passwd", &statbuff);
427 napi_value result = nullptr;
428 if (ret == FAIL) {
429 napi_create_int32(env, PARAM_UNNORMAL, &result);
430 } else {
431 napi_create_int32(env, PARAM_0, &result);
432 }
433 return result;
434 }
435
436 EXTERN_C_START
Init(napi_env env,napi_value exports)437 static napi_value Init(napi_env env, napi_value exports)
438 {
439 napi_property_descriptor desc[] = {
440 {"stat", nullptr, Stat, nullptr, nullptr, nullptr, napi_default, nullptr},
441 {"stat64", nullptr, Stat64, nullptr, nullptr, nullptr, napi_default, nullptr},
442 {"umask", nullptr, Umask, nullptr, nullptr, nullptr, napi_default, nullptr},
443 {"utimensat", nullptr, Utimensat, nullptr, nullptr, nullptr, napi_default, nullptr},
444 {"fchmodat", nullptr, FchModAt, nullptr, nullptr, nullptr, napi_default, nullptr},
445 {"fchmod", nullptr, FchMod, nullptr, nullptr, nullptr, napi_default, nullptr},
446 {"creat", nullptr, Creat, nullptr, nullptr, nullptr, napi_default, nullptr},
447 {"creat64", nullptr, Creat64, nullptr, nullptr, nullptr, napi_default, nullptr},
448 {"chmod", nullptr, Chmod, nullptr, nullptr, nullptr, napi_default, nullptr},
449 {"fstat", nullptr, Fstat, nullptr, nullptr, nullptr, napi_default, nullptr},
450 {"fstat64", nullptr, Fstat64, nullptr, nullptr, nullptr, napi_default, nullptr},
451 {"fstatat", nullptr, Fstatat, nullptr, nullptr, nullptr, napi_default, nullptr},
452 {"fstatat64", nullptr, Fstatat64, nullptr, nullptr, nullptr, napi_default, nullptr},
453 {"futimens", nullptr, Futimens, nullptr, nullptr, nullptr, napi_default, nullptr},
454 {"mkFifoAt", nullptr, MkFifoAt, nullptr, nullptr, nullptr, napi_default, nullptr},
455 {"mkNodAt", nullptr, MkNodAt, nullptr, nullptr, nullptr, napi_default, nullptr},
456 {"mkNod", nullptr, MkNod, nullptr, nullptr, nullptr, napi_default, nullptr},
457 {"mkDir", nullptr, MkDir, nullptr, nullptr, nullptr, napi_default, nullptr},
458 {"mkDirAt", nullptr, MkDirAt, nullptr, nullptr, nullptr, napi_default, nullptr},
459 {"lstat", nullptr, Lstat, nullptr, nullptr, nullptr, napi_default, nullptr},
460 {"lstat64", nullptr, Lstat64, nullptr, nullptr, nullptr, napi_default, nullptr},
461 {"mkFiFo", nullptr, MkFiFo, nullptr, nullptr, nullptr, napi_default, nullptr},
462
463 };
464 napi_define_properties(env, exports, sizeof(desc) / sizeof(desc[0]), desc);
465 return exports;
466 }
467 EXTERN_C_END
468
469 static napi_module demoModule = {
470 .nm_version = 1,
471 .nm_flags = 0,
472 .nm_filename = nullptr,
473 .nm_register_func = Init,
474 .nm_modname = "stat",
475 .nm_priv = ((void *)0),
476 .reserved = {0},
477 };
478
RegisterModule(void)479 extern "C" __attribute__((constructor)) void RegisterModule(void) { napi_module_register(&demoModule); }
480