]> glassweightruler.freedombox.rocks Git - Ventoy.git/blob - Plugson/src/Core/ventoy_util_linux.c
Update README.md
[Ventoy.git] / Plugson / src / Core / ventoy_util_linux.c
1 /******************************************************************************
2 * ventoy_util_linux.c ---- ventoy util
3 * Copyright (c) 2021, longpanda <admin@ventoy.net>
4 *
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License as
7 * published by the Free Software Foundation; either version 3 of the
8 * License, or (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful, but
11 * WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, see <http://www.gnu.org/licenses/>.
17 *
18 */
19 #include <stdio.h>
20 #include <stdlib.h>
21 #include <stdint.h>
22 #include <string.h>
23 #include <stdarg.h>
24 #include <errno.h>
25 #include <time.h>
26 #include <unistd.h>
27 #include <fcntl.h>
28 #include <sys/types.h>
29 #include <sys/ioctl.h>
30 #include <sys/stat.h>
31 #include <sys/types.h>
32 #include <sys/mount.h>
33 #include <linux/fs.h>
34 #include <dirent.h>
35 #include <time.h>
36 #include <semaphore.h>
37 #include <ventoy_define.h>
38 #include <ventoy_util.h>
39
40 void ventoy_gen_preudo_uuid(void *uuid)
41 {
42 int i;
43 int fd;
44
45 fd = open("/dev/urandom", O_RDONLY | O_BINARY);
46 if (fd < 0)
47 {
48 srand(time(NULL));
49 for (i = 0; i < 8; i++)
50 {
51 *((uint16_t *)uuid + i) = (uint16_t)(rand() & 0xFFFF);
52 }
53 }
54 else
55 {
56 read(fd, uuid, 16);
57 close(fd);
58 }
59 }
60
61 int ventoy_get_sys_file_line(char *buffer, int buflen, const char *fmt, ...)
62 {
63 int len;
64 char c;
65 char path[256];
66 va_list arg;
67
68 va_start(arg, fmt);
69 vsnprintf(path, 256, fmt, arg);
70 va_end(arg);
71
72 if (access(path, F_OK) >= 0)
73 {
74 FILE *fp = fopen(path, "r");
75 memset(buffer, 0, buflen);
76 len = (int)fread(buffer, 1, buflen - 1, fp);
77 fclose(fp);
78
79 while (len > 0)
80 {
81 c = buffer[len - 1];
82 if (c == '\r' || c == '\n' || c == ' ' || c == '\t')
83 {
84 buffer[len - 1] = 0;
85 len--;
86 }
87 else
88 {
89 break;
90 }
91 }
92
93 return 0;
94 }
95 else
96 {
97 vdebug("%s not exist \n", path);
98 return 1;
99 }
100 }
101
102 int ventoy_is_disk_mounted(const char *devpath)
103 {
104 int len;
105 int mount = 0;
106 char line[512];
107 FILE *fp = NULL;
108
109 fp = fopen("/proc/mounts", "r");
110 if (!fp)
111 {
112 return 0;
113 }
114
115 len = (int)strlen(devpath);
116 while (fgets(line, sizeof(line), fp))
117 {
118 if (strncmp(line, devpath, len) == 0)
119 {
120 mount = 1;
121 vdebug("%s mounted <%s>\n", devpath, line);
122 goto end;
123 }
124 }
125
126 end:
127 fclose(fp);
128 return mount;
129 }
130
131 const char * ventoy_get_os_language(void)
132 {
133 const char *env = getenv("LANG");
134
135 if (env && strncasecmp(env, "zh_CN", 5) == 0)
136 {
137 return "cn";
138 }
139 else
140 {
141 return "en";
142 }
143 }
144
145 int ventoy_is_file_exist(const char *fmt, ...)
146 {
147 va_list ap;
148 struct stat sb;
149 char fullpath[MAX_PATH];
150
151 va_start (ap, fmt);
152 vsnprintf(fullpath, MAX_PATH, fmt, ap);
153 va_end (ap);
154
155 if (stat(fullpath, &sb))
156 {
157 return 0;
158 }
159
160 if (S_ISREG(sb.st_mode))
161 {
162 return 1;
163 }
164
165 return 0;
166 }
167
168 int ventoy_is_directory_exist(const char *fmt, ...)
169 {
170 va_list ap;
171 struct stat sb;
172 char fullpath[MAX_PATH];
173
174 va_start (ap, fmt);
175 vsnprintf(fullpath, MAX_PATH, fmt, ap);
176 va_end (ap);
177
178 if (stat(fullpath, &sb))
179 {
180 return 0;
181 }
182
183 if (S_ISDIR(sb.st_mode))
184 {
185 return 1;
186 }
187
188 return 0;
189 }
190
191 int ventoy_get_file_size(const char *file)
192 {
193 int Size = -1;
194 struct stat stStat;
195
196 if (stat(file, &stStat) >= 0)
197 {
198 Size = (int)(stStat.st_size);
199 }
200
201 return Size;
202 }
203
204
205 int ventoy_write_buf_to_file(const char *FileName, void *Bufer, int BufLen)
206 {
207 int fd;
208 int rc;
209 ssize_t size;
210
211 fd = open(FileName, O_CREAT | O_RDWR | O_TRUNC, 0755);
212 if (fd < 0)
213 {
214 vlog("Failed to open file %s %d\n", FileName, errno);
215 return 1;
216 }
217
218 rc = fchmod(fd, 0755);
219 if (rc)
220 {
221 vlog("Failed to chmod <%s> %d\n", FileName, errno);
222 }
223
224 size = write(fd, Bufer, BufLen);
225 if ((int)size != BufLen)
226 {
227 close(fd);
228 vlog("write file %s failed %d err:%d\n", FileName, (int)size, errno);
229 return 1;
230 }
231
232 fsync(fd);
233 close(fd);
234
235 return 0;
236 }
237
238 static sem_t g_writeback_sem;
239 static volatile int g_thread_stop = 0;
240 static pthread_t g_writeback_thread;
241
242 static void * ventoy_local_thread_run(void* data)
243 {
244 ventoy_http_writeback_pf callback = (ventoy_http_writeback_pf)data;
245
246 while (0 == g_thread_stop)
247 {
248 sem_wait(&g_writeback_sem);
249 callback();
250 }
251
252 return NULL;
253 }
254
255 void ventoy_set_writeback_event(void)
256 {
257 sem_post(&g_writeback_sem);
258 }
259
260 int ventoy_start_writeback_thread(ventoy_http_writeback_pf callback)
261 {
262 g_thread_stop = 0;
263
264 sem_init(&g_writeback_sem, 0, 0);
265 pthread_create(&g_writeback_thread, NULL, ventoy_local_thread_run, callback);
266
267 return 0;
268 }
269
270 void ventoy_stop_writeback_thread(void)
271 {
272 g_thread_stop = 1;
273
274 sem_post(&g_writeback_sem);
275 pthread_join(g_writeback_thread, NULL);
276 sem_destroy(&g_writeback_sem);
277 }
278
279
280
281 int ventoy_read_file_to_buf(const char *FileName, int ExtLen, void **Bufer, int *BufLen)
282 {
283 int FileSize;
284 FILE *fp = NULL;
285 void *Data = NULL;
286
287 fp = fopen(FileName, "rb");
288 if (fp == NULL)
289 {
290 vlog("Failed to open file %s", FileName);
291 return 1;
292 }
293
294 fseek(fp, 0, SEEK_END);
295 FileSize = (int)ftell(fp);
296
297 Data = malloc(FileSize + ExtLen);
298 if (!Data)
299 {
300 fclose(fp);
301 return 1;
302 }
303
304 fseek(fp, 0, SEEK_SET);
305 fread(Data, 1, FileSize, fp);
306
307 fclose(fp);
308
309 *Bufer = Data;
310 *BufLen = FileSize;
311
312 return 0;
313 }
314
315 int ventoy_copy_file(const char *a, const char *b)
316 {
317 int len = 0;
318 char *buf = NULL;
319
320 if (0 == ventoy_read_file_to_buf(a, 0, (void **)&buf, &len))
321 {
322 ventoy_write_buf_to_file(b, buf, len);
323 free(buf);
324 }
325
326 return 0;
327 }
328