]> glassweightruler.freedombox.rocks Git - Ventoy.git/blob - Plugson/src/Web/ventoy_http.c
Add theme plugin duplicate file check. (#2078)
[Ventoy.git] / Plugson / src / Web / ventoy_http.c
1 /******************************************************************************
2 * ventoy_http.c ---- ventoy http
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
27 #if defined(_MSC_VER) || defined(WIN32)
28 #else
29 #include <unistd.h>
30 #include <fcntl.h>
31 #include <sys/types.h>
32 #include <sys/ioctl.h>
33 #include <sys/stat.h>
34 #include <sys/types.h>
35 #include <sys/mount.h>
36 #include <linux/fs.h>
37 #include <linux/limits.h>
38 #include <dirent.h>
39 #include <pthread.h>
40 #endif
41
42 #include <ventoy_define.h>
43 #include <ventoy_json.h>
44 #include <ventoy_util.h>
45 #include <ventoy_disk.h>
46 #include <ventoy_http.h>
47 #include "fat_filelib.h"
48
49 static const char *g_json_title_postfix[bios_max + 1] =
50 {
51 "", "_legacy", "_uefi", "_ia32", "_aa64", "_mips", ""
52 };
53
54 static const char *g_ventoy_kbd_layout[] =
55 {
56 "QWERTY_USA", "AZERTY", "CZECH_QWERTY", "CZECH_QWERTZ", "DANISH",
57 "DVORAK_USA", "FRENCH", "GERMAN", "ITALIANO", "JAPAN_106", "LATIN_USA",
58 "PORTU_BRAZIL", "QWERTY_UK", "QWERTZ", "QWERTZ_HUN", "QWERTZ_SLOV_CROAT",
59 "SPANISH", "SWEDISH", "TURKISH_Q", "VIETNAMESE",
60 NULL
61 };
62
63 #define VTOY_DEL_ALL_PATH "4119ae33-98ea-448e-b9c0-569aafcf1fb4"
64
65 static int g_json_exist[plugin_type_max][bios_max];
66 static const char *g_plugin_name[plugin_type_max] =
67 {
68 "control", "theme", "menu_alias", "menu_tip",
69 "menu_class", "auto_install", "persistence", "injection",
70 "conf_replace", "password", "image_list",
71 "auto_memdisk", "dud"
72 };
73
74 static char g_ventoy_menu_lang[MAX_LANGUAGE][8];
75
76 static char g_pub_path[2 * MAX_PATH];
77 static data_control g_data_control[bios_max + 1];
78 static data_theme g_data_theme[bios_max + 1];
79 static data_alias g_data_menu_alias[bios_max + 1];
80 static data_tip g_data_menu_tip[bios_max + 1];
81 static data_class g_data_menu_class[bios_max + 1];
82 static data_image_list g_data_image_list[bios_max + 1];
83 static data_image_list *g_data_image_blacklist = g_data_image_list;
84 static data_auto_memdisk g_data_auto_memdisk[bios_max + 1];
85 static data_password g_data_password[bios_max + 1];
86 static data_conf_replace g_data_conf_replace[bios_max + 1];
87 static data_injection g_data_injection[bios_max + 1];
88 static data_auto_install g_data_auto_install[bios_max + 1];
89 static data_persistence g_data_persistence[bios_max + 1];
90 static data_dud g_data_dud[bios_max + 1];
91
92 static char *g_pub_json_buffer = NULL;
93 static char *g_pub_save_buffer = NULL;
94 #define JSON_BUFFER g_pub_json_buffer
95 #define JSON_SAVE_BUFFER g_pub_save_buffer
96
97 static pthread_mutex_t g_api_mutex;
98 static struct mg_context *g_ventoy_http_ctx = NULL;
99
100 static int ventoy_is_kbd_valid(const char *key)
101 {
102 int i = 0;
103
104 for (i = 0; g_ventoy_kbd_layout[i]; i++)
105 {
106 if (strcmp(g_ventoy_kbd_layout[i], key) == 0)
107 {
108 return 1;
109 }
110 }
111
112 return 0;
113 }
114
115 static const char * ventoy_real_path(const char *org)
116 {
117 int count = 0;
118
119 if (g_sysinfo.pathcase)
120 {
121 scnprintf(g_pub_path, MAX_PATH, "%s", org);
122 count = ventoy_path_case(g_pub_path + 1, 1);
123 if (count > 0)
124 {
125 return g_pub_path;
126 }
127 return org;
128 }
129 else
130 {
131 return org;
132 }
133 }
134
135
136 static int ventoy_json_result(struct mg_connection *conn, const char *err)
137 {
138 mg_printf(conn,
139 "HTTP/1.1 200 OK \r\n"
140 "Content-Type: application/json\r\n"
141 "Content-Length: %d\r\n"
142 "\r\n%s",
143 (int)strlen(err), err);
144
145 return 0;
146 }
147
148 static int ventoy_json_buffer(struct mg_connection *conn, const char *json_buf, int json_len)
149 {
150 mg_printf(conn,
151 "HTTP/1.1 200 OK \r\n"
152 "Content-Type: application/json\r\n"
153 "Content-Length: %d\r\n"
154 "\r\n%s",
155 json_len, json_buf);
156
157 return 0;
158 }
159
160 static void ventoy_free_path_node_list(path_node *list)
161 {
162 path_node *next = NULL;
163 path_node *node = list;
164
165 while (node)
166 {
167 next = node->next;
168 free(node);
169 node = next;
170 }
171 }
172
173 static path_node * ventoy_path_node_add_array(VTOY_JSON *array)
174 {
175 path_node *head = NULL;
176 path_node *node = NULL;
177 path_node *cur = NULL;
178 VTOY_JSON *item = NULL;
179
180 for (item = array->pstChild; item; item = item->pstNext)
181 {
182 node = zalloc(sizeof(path_node));
183 if (node)
184 {
185 scnprintf(node->path, sizeof(node->path), "%s", item->unData.pcStrVal);
186 vtoy_list_add(head, cur, node);
187 }
188 }
189
190 return head;
191 }
192
193 static int ventoy_check_fuzzy_path(char *path, int prefix)
194 {
195 int rc;
196 char c;
197 char *cur = NULL;
198 char *pos = NULL;
199
200 if (!path)
201 {
202 return 0;
203 }
204
205 pos = strchr(path, '*');
206 if (pos)
207 {
208 for (cur = pos; *cur; cur++)
209 {
210 if (*cur == '/')
211 {
212 return 0;
213 }
214 }
215
216 while (pos != path)
217 {
218 if (*pos == '/')
219 {
220 break;
221 }
222 pos--;
223 }
224
225 if (*pos == '/')
226 {
227 if (pos != path)
228 {
229 c = *pos;
230 *pos = 0;
231 if (prefix)
232 {
233 rc = ventoy_is_directory_exist("%s%s", g_cur_dir, path);
234 }
235 else
236 {
237 rc = ventoy_is_directory_exist("%s", path);
238 }
239 *pos = c;
240
241 if (rc == 0)
242 {
243 return 0;
244 }
245 }
246
247 return -1;
248 }
249 else
250 {
251 return 0;
252 }
253 }
254 else
255 {
256 if (prefix)
257 {
258 return ventoy_is_file_exist("%s%s", g_cur_dir, path);
259 }
260 else
261 {
262 return ventoy_is_file_exist("%s", path);
263 }
264 }
265 }
266
267 static int ventoy_path_list_cmp(path_node *list1, path_node *list2)
268 {
269 if (NULL == list1 && NULL == list2)
270 {
271 return 0;
272 }
273 else if (list1 && list2)
274 {
275 while (list1 && list2)
276 {
277 if (strcmp(list1->path, list2->path))
278 {
279 return 1;
280 }
281
282 list1 = list1->next;
283 list2 = list2->next;
284 }
285
286 if (list1 == NULL && list2 == NULL)
287 {
288 return 0;
289 }
290 return 1;
291 }
292 else
293 {
294 return 1;
295 }
296 }
297
298
299 static int ventoy_api_device_info(struct mg_connection *conn, VTOY_JSON *json)
300 {
301 int pos = 0;
302
303 (void)json;
304
305 VTOY_JSON_FMT_BEGIN(pos, JSON_BUFFER, JSON_BUF_MAX);
306 VTOY_JSON_FMT_OBJ_BEGIN();
307
308 VTOY_JSON_FMT_STRN("dev_name", g_sysinfo.cur_model);
309 VTOY_JSON_FMT_STRN("dev_capacity", g_sysinfo.cur_capacity);
310 VTOY_JSON_FMT_STRN("dev_fs", g_sysinfo.cur_fsname);
311 VTOY_JSON_FMT_STRN("ventoy_ver", g_sysinfo.cur_ventoy_ver);
312 VTOY_JSON_FMT_SINT("part_style", g_sysinfo.cur_part_style);
313 VTOY_JSON_FMT_SINT("secure_boot", g_sysinfo.cur_secureboot);
314
315 VTOY_JSON_FMT_OBJ_END();
316 VTOY_JSON_FMT_END(pos);
317
318 ventoy_json_buffer(conn, JSON_BUFFER, pos);
319 return 0;
320 }
321
322 static int ventoy_api_sysinfo(struct mg_connection *conn, VTOY_JSON *json)
323 {
324 int pos = 0;
325
326 (void)json;
327
328 VTOY_JSON_FMT_BEGIN(pos, JSON_BUFFER, JSON_BUF_MAX);
329 VTOY_JSON_FMT_OBJ_BEGIN();
330 VTOY_JSON_FMT_STRN("language", ventoy_get_os_language());
331 VTOY_JSON_FMT_STRN("curdir", g_cur_dir);
332
333 //read clear
334 VTOY_JSON_FMT_SINT("syntax_error", g_sysinfo.syntax_error);
335 g_sysinfo.syntax_error = 0;
336
337 VTOY_JSON_FMT_SINT("invalid_config", g_sysinfo.invalid_config);
338 g_sysinfo.invalid_config = 0;
339
340 #if defined(_MSC_VER) || defined(WIN32)
341 VTOY_JSON_FMT_STRN("os", "windows");
342 #else
343 VTOY_JSON_FMT_STRN("os", "linux");
344 #endif
345
346 VTOY_JSON_FMT_OBJ_END();
347 VTOY_JSON_FMT_END(pos);
348
349 ventoy_json_buffer(conn, JSON_BUFFER, pos);
350 return 0;
351 }
352
353 static int ventoy_api_handshake(struct mg_connection *conn, VTOY_JSON *json)
354 {
355 int i = 0;
356 int j = 0;
357 int pos = 0;
358 char key[128];
359
360 (void)json;
361
362 VTOY_JSON_FMT_BEGIN(pos, JSON_BUFFER, JSON_BUF_MAX);
363 VTOY_JSON_FMT_OBJ_BEGIN();
364 VTOY_JSON_FMT_SINT("status", 0);
365 VTOY_JSON_FMT_SINT("save_error", g_sysinfo.config_save_error);
366 g_sysinfo.config_save_error = 0;
367
368 for (i = 0; i < plugin_type_max; i++)
369 {
370 scnprintf(key, sizeof(key), "exist_%s", g_plugin_name[i]);
371 VTOY_JSON_FMT_KEY(key);
372 VTOY_JSON_FMT_ARY_BEGIN();
373 for (j = 0; j < bios_max; j++)
374 {
375 VTOY_JSON_FMT_ITEM_INT(g_json_exist[i][j]);
376 }
377 VTOY_JSON_FMT_ARY_ENDEX();
378 }
379
380 VTOY_JSON_FMT_OBJ_END();
381 VTOY_JSON_FMT_END(pos);
382
383 ventoy_json_buffer(conn, JSON_BUFFER, pos);
384 return 0;
385 }
386
387 static int ventoy_api_check_exist(struct mg_connection *conn, VTOY_JSON *json)
388 {
389 int dir = 0;
390 int pos = 0;
391 int exist = 0;
392 const char *path = NULL;
393
394 path = vtoy_json_get_string_ex(json, "path");
395 vtoy_json_get_int(json, "dir", &dir);
396
397 if (path)
398 {
399 if (dir)
400 {
401 exist = ventoy_is_directory_exist("%s", path);
402 }
403 else
404 {
405 exist = ventoy_is_file_exist("%s", path);
406 }
407 }
408
409 VTOY_JSON_FMT_BEGIN(pos, JSON_BUFFER, JSON_BUF_MAX);
410 VTOY_JSON_FMT_OBJ_BEGIN();
411 VTOY_JSON_FMT_SINT("exist", exist);
412 VTOY_JSON_FMT_OBJ_END();
413 VTOY_JSON_FMT_END(pos);
414
415 ventoy_json_buffer(conn, JSON_BUFFER, pos);
416 return 0;
417 }
418
419 static int ventoy_api_check_exist2(struct mg_connection *conn, VTOY_JSON *json)
420 {
421 int dir1 = 0;
422 int dir2 = 0;
423 int fuzzy1 = 0;
424 int fuzzy2 = 0;
425 int pos = 0;
426 int exist1 = 0;
427 int exist2 = 0;
428 const char *path1 = NULL;
429 const char *path2 = NULL;
430
431 path1 = vtoy_json_get_string_ex(json, "path1");
432 path2 = vtoy_json_get_string_ex(json, "path2");
433 vtoy_json_get_int(json, "dir1", &dir1);
434 vtoy_json_get_int(json, "dir2", &dir2);
435 vtoy_json_get_int(json, "fuzzy1", &fuzzy1);
436 vtoy_json_get_int(json, "fuzzy2", &fuzzy2);
437
438 if (path1)
439 {
440 if (dir1)
441 {
442 exist1 = ventoy_is_directory_exist("%s", path1);
443 }
444 else
445 {
446 if (fuzzy1)
447 {
448 exist1 = ventoy_check_fuzzy_path((char *)path1, 0);
449 }
450 else
451 {
452 exist1 = ventoy_is_file_exist("%s", path1);
453 }
454 }
455 }
456
457 if (path2)
458 {
459 if (dir2)
460 {
461 exist2 = ventoy_is_directory_exist("%s", path2);
462 }
463 else
464 {
465 if (fuzzy2)
466 {
467 exist2 = ventoy_check_fuzzy_path((char *)path2, 0);
468 }
469 else
470 {
471 exist2 = ventoy_is_file_exist("%s", path2);
472 }
473 }
474 }
475
476 VTOY_JSON_FMT_BEGIN(pos, JSON_BUFFER, JSON_BUF_MAX);
477 VTOY_JSON_FMT_OBJ_BEGIN();
478 VTOY_JSON_FMT_SINT("exist1", exist1);
479 VTOY_JSON_FMT_SINT("exist2", exist2);
480 VTOY_JSON_FMT_OBJ_END();
481 VTOY_JSON_FMT_END(pos);
482
483 ventoy_json_buffer(conn, JSON_BUFFER, pos);
484 return 0;
485 }
486
487 static int ventoy_api_check_fuzzy(struct mg_connection *conn, VTOY_JSON *json)
488 {
489 int pos = 0;
490 int exist = 0;
491 const char *path = NULL;
492
493 path = vtoy_json_get_string_ex(json, "path");
494 if (path)
495 {
496 exist = ventoy_check_fuzzy_path((char *)path, 0);
497 }
498
499 VTOY_JSON_FMT_BEGIN(pos, JSON_BUFFER, JSON_BUF_MAX);
500 VTOY_JSON_FMT_OBJ_BEGIN();
501 VTOY_JSON_FMT_SINT("exist", exist);
502 VTOY_JSON_FMT_OBJ_END();
503 VTOY_JSON_FMT_END(pos);
504
505 ventoy_json_buffer(conn, JSON_BUFFER, pos);
506 return 0;
507 }
508
509
510 #if 0
511 #endif
512 void ventoy_data_default_control(data_control *data)
513 {
514 memset(data, 0, sizeof(data_control));
515
516 data->password_asterisk = 1;
517 data->secondary_menu = 1;
518 data->filter_dot_underscore = 1;
519 data->max_search_level = -1;
520 data->menu_timeout = 0;
521 data->secondary_menu_timeout = 0;
522
523 strlcpy(data->default_kbd_layout, "QWERTY_USA");
524 strlcpy(data->menu_language, "en_US");
525 }
526
527 int ventoy_data_cmp_control(data_control *data1, data_control *data2)
528 {
529 if (data1->default_menu_mode != data2->default_menu_mode ||
530 data1->treeview_style != data2->treeview_style ||
531 data1->filter_dot_underscore != data2->filter_dot_underscore ||
532 data1->sort_casesensitive != data2->sort_casesensitive ||
533 data1->max_search_level != data2->max_search_level ||
534 data1->vhd_no_warning != data2->vhd_no_warning ||
535 data1->filter_iso != data2->filter_iso ||
536 data1->filter_wim != data2->filter_wim ||
537 data1->filter_efi != data2->filter_efi ||
538 data1->filter_img != data2->filter_img ||
539 data1->filter_vhd != data2->filter_vhd ||
540 data1->filter_vtoy != data2->filter_vtoy ||
541 data1->win11_bypass_check != data2->win11_bypass_check ||
542 data1->linux_remount != data2->linux_remount ||
543 data1->password_asterisk != data2->password_asterisk ||
544 data1->secondary_menu != data2->secondary_menu ||
545 data1->menu_timeout != data2->menu_timeout ||
546 data1->secondary_menu_timeout != data2->secondary_menu_timeout)
547 {
548 return 1;
549 }
550
551 if (strcmp(data1->default_search_root, data2->default_search_root) ||
552 strcmp(data1->default_image, data2->default_image) ||
553 strcmp(data1->default_kbd_layout, data2->default_kbd_layout) ||
554 strcmp(data1->menu_language, data2->menu_language))
555 {
556 return 1;
557 }
558
559 return 0;
560 }
561
562 int ventoy_data_save_control(data_control *data, const char *title, char *buf, int buflen)
563 {
564 int pos = 0;
565 data_control *def = g_data_control + bios_max;
566
567 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
568
569 VTOY_JSON_FMT_KEY_L(L1, title);
570 VTOY_JSON_FMT_ARY_BEGIN_N();
571
572 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_DEFAULT_MENU_MODE", default_menu_mode);
573 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_TREE_VIEW_MENU_STYLE", treeview_style);
574 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_FILT_DOT_UNDERSCORE_FILE", filter_dot_underscore);
575 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_SORT_CASE_SENSITIVE", sort_casesensitive);
576
577 if (data->max_search_level >= 0)
578 {
579 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_MAX_SEARCH_LEVEL", max_search_level);
580 }
581
582 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_VHD_NO_WARNING", vhd_no_warning);
583 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_FILE_FLT_ISO", filter_iso);
584 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_FILE_FLT_WIM", filter_wim);
585 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_FILE_FLT_EFI", filter_efi);
586 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_FILE_FLT_IMG", filter_img);
587 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_FILE_FLT_VHD", filter_vhd);
588 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_FILE_FLT_VTOY", filter_vtoy);
589 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_WIN11_BYPASS_CHECK", win11_bypass_check);
590 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_LINUX_REMOUNT", linux_remount);
591 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_SECONDARY_BOOT_MENU", secondary_menu);
592 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_SHOW_PASSWORD_ASTERISK", password_asterisk);
593 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_MENU_TIMEOUT", menu_timeout);
594 VTOY_JSON_FMT_CTRL_INT(L2, "VTOY_SECONDARY_TIMEOUT", secondary_menu_timeout);
595
596 VTOY_JSON_FMT_CTRL_STRN(L2, "VTOY_DEFAULT_KBD_LAYOUT", default_kbd_layout);
597 VTOY_JSON_FMT_CTRL_STRN(L2, "VTOY_MENU_LANGUAGE", menu_language);
598
599 if (strcmp(def->default_search_root, data->default_search_root))
600 {
601 VTOY_JSON_FMT_CTRL_STRN_STR(L2, "VTOY_DEFAULT_SEARCH_ROOT", ventoy_real_path(data->default_search_root));
602 }
603
604 if (strcmp(def->default_image, data->default_image))
605 {
606 VTOY_JSON_FMT_CTRL_STRN_STR(L2, "VTOY_DEFAULT_IMAGE", ventoy_real_path(data->default_image));
607 }
608
609 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
610 VTOY_JSON_FMT_END(pos);
611
612 return pos;
613 }
614
615 int ventoy_data_json_control(data_control *ctrl, char *buf, int buflen)
616 {
617 int i = 0;
618 int pos = 0;
619 int valid = 0;
620
621 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
622 VTOY_JSON_FMT_OBJ_BEGIN();
623
624 VTOY_JSON_FMT_SINT("default_menu_mode", ctrl->default_menu_mode);
625 VTOY_JSON_FMT_SINT("treeview_style", ctrl->treeview_style);
626 VTOY_JSON_FMT_SINT("filter_dot_underscore", ctrl->filter_dot_underscore);
627 VTOY_JSON_FMT_SINT("sort_casesensitive", ctrl->sort_casesensitive);
628 VTOY_JSON_FMT_SINT("max_search_level", ctrl->max_search_level);
629 VTOY_JSON_FMT_SINT("vhd_no_warning", ctrl->vhd_no_warning);
630
631 VTOY_JSON_FMT_SINT("filter_iso", ctrl->filter_iso);
632 VTOY_JSON_FMT_SINT("filter_wim", ctrl->filter_wim);
633 VTOY_JSON_FMT_SINT("filter_efi", ctrl->filter_efi);
634 VTOY_JSON_FMT_SINT("filter_img", ctrl->filter_img);
635 VTOY_JSON_FMT_SINT("filter_vhd", ctrl->filter_vhd);
636 VTOY_JSON_FMT_SINT("filter_vtoy", ctrl->filter_vtoy);
637 VTOY_JSON_FMT_SINT("win11_bypass_check", ctrl->win11_bypass_check);
638 VTOY_JSON_FMT_SINT("linux_remount", ctrl->linux_remount);
639 VTOY_JSON_FMT_SINT("secondary_menu", ctrl->secondary_menu);
640 VTOY_JSON_FMT_SINT("password_asterisk", ctrl->password_asterisk);
641 VTOY_JSON_FMT_SINT("menu_timeout", ctrl->menu_timeout);
642 VTOY_JSON_FMT_SINT("secondary_menu_timeout", ctrl->secondary_menu_timeout);
643 VTOY_JSON_FMT_STRN("default_kbd_layout", ctrl->default_kbd_layout);
644 VTOY_JSON_FMT_STRN("menu_language", ctrl->menu_language);
645
646 valid = 0;
647 if (ctrl->default_search_root[0] && ventoy_is_directory_exist("%s%s", g_cur_dir, ctrl->default_search_root))
648 {
649 valid = 1;
650 }
651 VTOY_JSON_FMT_STRN("default_search_root", ctrl->default_search_root);
652 VTOY_JSON_FMT_SINT("default_search_root_valid", valid);
653
654
655 valid = 0;
656 if (ctrl->default_image[0] && ventoy_is_file_exist("%s%s", g_cur_dir, ctrl->default_image))
657 {
658 valid = 1;
659 }
660 VTOY_JSON_FMT_STRN("default_image", ctrl->default_image);
661 VTOY_JSON_FMT_SINT("default_image_valid", valid);
662
663 VTOY_JSON_FMT_KEY("menu_list");
664 VTOY_JSON_FMT_ARY_BEGIN();
665
666 for (i = 0; g_ventoy_menu_lang[i][0]; i++)
667 {
668 VTOY_JSON_FMT_ITEM(g_ventoy_menu_lang[i]);
669 }
670 VTOY_JSON_FMT_ARY_ENDEX();
671
672 VTOY_JSON_FMT_OBJ_END();
673 VTOY_JSON_FMT_END(pos);
674
675 return pos;
676 }
677
678 static int ventoy_api_get_control(struct mg_connection *conn, VTOY_JSON *json)
679 {
680 api_get_func(conn, json, control);
681 return 0;
682 }
683
684 static int ventoy_api_save_control(struct mg_connection *conn, VTOY_JSON *json)
685 {
686 int ret;
687 int index = 0;
688 data_control *ctrl = NULL;
689
690 vtoy_json_get_int(json, "index", &index);
691 ctrl = g_data_control + index;
692
693 VTOY_JSON_INT("default_menu_mode", ctrl->default_menu_mode);
694 VTOY_JSON_INT("treeview_style", ctrl->treeview_style);
695 VTOY_JSON_INT("filter_dot_underscore", ctrl->filter_dot_underscore);
696 VTOY_JSON_INT("sort_casesensitive", ctrl->sort_casesensitive);
697 VTOY_JSON_INT("max_search_level", ctrl->max_search_level);
698 VTOY_JSON_INT("vhd_no_warning", ctrl->vhd_no_warning);
699 VTOY_JSON_INT("filter_iso", ctrl->filter_iso);
700 VTOY_JSON_INT("filter_wim", ctrl->filter_wim);
701 VTOY_JSON_INT("filter_efi", ctrl->filter_efi);
702 VTOY_JSON_INT("filter_img", ctrl->filter_img);
703 VTOY_JSON_INT("filter_vhd", ctrl->filter_vhd);
704 VTOY_JSON_INT("filter_vtoy", ctrl->filter_vtoy);
705 VTOY_JSON_INT("win11_bypass_check", ctrl->win11_bypass_check);
706 VTOY_JSON_INT("linux_remount", ctrl->linux_remount);
707 VTOY_JSON_INT("secondary_menu", ctrl->secondary_menu);
708 VTOY_JSON_INT("password_asterisk", ctrl->password_asterisk);
709 VTOY_JSON_INT("menu_timeout", ctrl->menu_timeout);
710 VTOY_JSON_INT("secondary_menu_timeout", ctrl->secondary_menu_timeout);
711
712 VTOY_JSON_STR("default_image", ctrl->default_image);
713 VTOY_JSON_STR("default_search_root", ctrl->default_search_root);
714 VTOY_JSON_STR("menu_language", ctrl->menu_language);
715 VTOY_JSON_STR("default_kbd_layout", ctrl->default_kbd_layout);
716
717 ret = ventoy_data_save_all();
718
719 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
720 return 0;
721 }
722
723
724 #if 0
725 #endif
726
727 void ventoy_data_default_theme(data_theme *data)
728 {
729 memset(data, 0, sizeof(data_theme));
730 strlcpy(data->gfxmode, "1024x768");
731 scnprintf(data->ventoy_left, sizeof(data->ventoy_left), "5%%");
732 scnprintf(data->ventoy_top, sizeof(data->ventoy_top), "95%%");
733 scnprintf(data->ventoy_color, sizeof(data->ventoy_color), "%s", "#0000ff");
734 }
735
736 int ventoy_data_cmp_theme(data_theme *data1, data_theme *data2)
737 {
738 if (data1->display_mode != data2->display_mode ||
739 strcmp(data1->ventoy_left, data2->ventoy_left) ||
740 strcmp(data1->ventoy_top, data2->ventoy_top) ||
741 strcmp(data1->gfxmode, data2->gfxmode) ||
742 strcmp(data1->ventoy_color, data2->ventoy_color)
743 )
744 {
745 return 1;
746 }
747
748 if (ventoy_path_list_cmp(data1->filelist, data2->filelist))
749 {
750 return 1;
751 }
752
753 if (ventoy_path_list_cmp(data1->fontslist, data2->fontslist))
754 {
755 return 1;
756 }
757
758 return 0;
759 }
760
761
762 int ventoy_data_save_theme(data_theme *data, const char *title, char *buf, int buflen)
763 {
764 int pos = 0;
765 path_node *node = NULL;
766 data_theme *def = g_data_theme + bios_max;
767
768 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
769
770 VTOY_JSON_FMT_KEY_L(L1, title);
771 VTOY_JSON_FMT_OBJ_BEGIN_N();
772
773 if (data->filelist)
774 {
775 if (data->filelist->next)
776 {
777 VTOY_JSON_FMT_KEY_L(L2, "file");
778 VTOY_JSON_FMT_ARY_BEGIN_N();
779
780 for (node = data->filelist; node; node = node->next)
781 {
782 VTOY_JSON_FMT_ITEM_PATH_LN(L3, node->path);
783 }
784
785 VTOY_JSON_FMT_ARY_ENDEX_LN(L2);
786
787 if (def->default_file != data->default_file)
788 {
789 VTOY_JSON_FMT_SINT_LN(L2, "default_file", data->default_file);
790 }
791 }
792 else
793 {
794 VTOY_JSON_FMT_STRN_PATH_LN(L2, "file", data->filelist->path);
795 }
796 }
797
798 if (data->display_mode != def->display_mode)
799 {
800 if (display_mode_cli == data->display_mode)
801 {
802 VTOY_JSON_FMT_STRN_LN(L2, "display_mode", "CLI");
803 }
804 else if (display_mode_serial == data->display_mode)
805 {
806 VTOY_JSON_FMT_STRN_LN(L2, "display_mode", "serial");
807 }
808 else if (display_mode_ser_console == data->display_mode)
809 {
810 VTOY_JSON_FMT_STRN_LN(L2, "display_mode", "serial_console");
811 }
812 else
813 {
814 VTOY_JSON_FMT_STRN_LN(L2, "display_mode", "GUI");
815 }
816 }
817
818 VTOY_JSON_FMT_DIFF_STRN(L2, "gfxmode", gfxmode);
819
820 VTOY_JSON_FMT_DIFF_STRN(L2, "ventoy_left", ventoy_left);
821 VTOY_JSON_FMT_DIFF_STRN(L2, "ventoy_top", ventoy_top);
822 VTOY_JSON_FMT_DIFF_STRN(L2, "ventoy_color", ventoy_color);
823
824 if (data->fontslist)
825 {
826 VTOY_JSON_FMT_KEY_L(L2, "fonts");
827 VTOY_JSON_FMT_ARY_BEGIN_N();
828
829 for (node = data->fontslist; node; node = node->next)
830 {
831 VTOY_JSON_FMT_ITEM_PATH_LN(L3, node->path);
832 }
833
834 VTOY_JSON_FMT_ARY_ENDEX_LN(L2);
835 }
836
837 VTOY_JSON_FMT_OBJ_ENDEX_LN(L1);
838 VTOY_JSON_FMT_END(pos);
839
840 return pos;
841 }
842
843
844 int ventoy_data_json_theme(data_theme *data, char *buf, int buflen)
845 {
846 int pos = 0;
847 path_node *node = NULL;
848
849 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
850 VTOY_JSON_FMT_OBJ_BEGIN();
851
852 VTOY_JSON_FMT_SINT("default_file", data->default_file);
853 VTOY_JSON_FMT_SINT("display_mode", data->display_mode);
854 VTOY_JSON_FMT_STRN("gfxmode", data->gfxmode);
855
856 VTOY_JSON_FMT_STRN("ventoy_color", data->ventoy_color);
857 VTOY_JSON_FMT_STRN("ventoy_left", data->ventoy_left);
858 VTOY_JSON_FMT_STRN("ventoy_top", data->ventoy_top);
859
860 VTOY_JSON_FMT_KEY("filelist");
861 VTOY_JSON_FMT_ARY_BEGIN();
862 for (node = data->filelist; node; node = node->next)
863 {
864 VTOY_JSON_FMT_OBJ_BEGIN();
865 VTOY_JSON_FMT_STRN("path", node->path);
866 VTOY_JSON_FMT_SINT("valid", ventoy_is_file_exist("%s%s", g_cur_dir, node->path));
867 VTOY_JSON_FMT_OBJ_ENDEX();
868 }
869 VTOY_JSON_FMT_ARY_ENDEX();
870
871 VTOY_JSON_FMT_KEY("fontslist");
872 VTOY_JSON_FMT_ARY_BEGIN();
873 for (node = data->fontslist; node; node = node->next)
874 {
875 VTOY_JSON_FMT_OBJ_BEGIN();
876 VTOY_JSON_FMT_STRN("path", node->path);
877 VTOY_JSON_FMT_SINT("valid", ventoy_is_file_exist("%s%s", g_cur_dir, node->path));
878 VTOY_JSON_FMT_OBJ_ENDEX();
879 }
880 VTOY_JSON_FMT_ARY_ENDEX();
881
882 VTOY_JSON_FMT_OBJ_END();
883 VTOY_JSON_FMT_END(pos);
884
885 return pos;
886 }
887
888 static int ventoy_api_get_theme(struct mg_connection *conn, VTOY_JSON *json)
889 {
890 api_get_func(conn, json, theme);
891 return 0;
892 }
893
894 static int ventoy_api_save_theme(struct mg_connection *conn, VTOY_JSON *json)
895 {
896 int ret;
897 int index = 0;
898 data_theme *data = NULL;
899
900 vtoy_json_get_int(json, "index", &index);
901 data = g_data_theme + index;
902
903 VTOY_JSON_INT("default_file", data->default_file);
904 VTOY_JSON_INT("display_mode", data->display_mode);
905 VTOY_JSON_STR("gfxmode", data->gfxmode);
906 VTOY_JSON_STR("ventoy_left", data->ventoy_left);
907 VTOY_JSON_STR("ventoy_top", data->ventoy_top);
908 VTOY_JSON_STR("ventoy_color", data->ventoy_color);
909
910 ret = ventoy_data_save_all();
911
912 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
913 return 0;
914 }
915
916 static int ventoy_api_theme_add_file(struct mg_connection *conn, VTOY_JSON *json)
917 {
918 int ret;
919 int index = 0;
920 const char *path = NULL;
921 const char *realpath = NULL;
922 path_node *node = NULL;
923 path_node *cur = NULL;
924 data_theme *data = NULL;
925 char pathbuf[MAX_PATH];
926
927 vtoy_json_get_int(json, "index", &index);
928 data = g_data_theme + index;
929
930 path = VTOY_JSON_STR_EX("path");
931 if (path)
932 {
933 realpath = ventoy_real_path(path);
934 scnprintf(pathbuf, sizeof(pathbuf), "%s", realpath);
935
936 for (node = data->filelist; node; node = node->next)
937 {
938 realpath = ventoy_real_path(node->path);
939 if (strcmp(pathbuf, realpath) == 0)
940 {
941 ventoy_json_result(conn, VTOY_JSON_DUPLICATE);
942 return 0;
943 }
944 }
945
946 node = zalloc(sizeof(path_node));
947 if (node)
948 {
949 scnprintf(node->path, sizeof(node->path), "%s", path);
950
951 vtoy_list_add(data->filelist, cur, node);
952 }
953 }
954
955 ret = ventoy_data_save_all();
956
957 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
958 return 0;
959 }
960
961 static int ventoy_api_theme_del_file(struct mg_connection *conn, VTOY_JSON *json)
962 {
963 int ret;
964 int index = 0;
965 const char *path = NULL;
966 path_node *node = NULL;
967 path_node *last = NULL;
968 data_theme *data = NULL;
969
970 vtoy_json_get_int(json, "index", &index);
971 data = g_data_theme + index;
972
973 path = VTOY_JSON_STR_EX("path");
974 if (path)
975 {
976 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
977 {
978 vtoy_list_free(path_node, data->filelist);
979 }
980 else
981 {
982 vtoy_list_del(last, node, data->filelist, path);
983 }
984 }
985
986 ret = ventoy_data_save_all();
987
988 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
989 return 0;
990 }
991
992
993 static int ventoy_api_theme_add_font(struct mg_connection *conn, VTOY_JSON *json)
994 {
995 int ret;
996 int index = 0;
997 const char *path = NULL;
998 const char *realpath = NULL;
999 path_node *node = NULL;
1000 path_node *cur = NULL;
1001 data_theme *data = NULL;
1002 char pathbuf[MAX_PATH];
1003
1004 vtoy_json_get_int(json, "index", &index);
1005 data = g_data_theme + index;
1006
1007 path = VTOY_JSON_STR_EX("path");
1008 if (path)
1009 {
1010 realpath = ventoy_real_path(path);
1011 scnprintf(pathbuf, sizeof(pathbuf), "%s", realpath);
1012
1013 for (node = data->fontslist; node; node = node->next)
1014 {
1015 realpath = ventoy_real_path(node->path);
1016 if (strcmp(pathbuf, realpath) == 0)
1017 {
1018 ventoy_json_result(conn, VTOY_JSON_DUPLICATE);
1019 return 0;
1020 }
1021 }
1022
1023 node = zalloc(sizeof(path_node));
1024 if (node)
1025 {
1026 scnprintf(node->path, sizeof(node->path), "%s", path);
1027 vtoy_list_add(data->fontslist, cur, node);
1028 }
1029 }
1030
1031 ret = ventoy_data_save_all();
1032
1033 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1034 return 0;
1035 }
1036
1037
1038 static int ventoy_api_theme_del_font(struct mg_connection *conn, VTOY_JSON *json)
1039 {
1040 int ret;
1041 int index = 0;
1042 const char *path = NULL;
1043 path_node *node = NULL;
1044 path_node *last = NULL;
1045 data_theme *data = NULL;
1046
1047 vtoy_json_get_int(json, "index", &index);
1048 data = g_data_theme + index;
1049
1050 path = VTOY_JSON_STR_EX("path");
1051 if (path)
1052 {
1053 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
1054 {
1055 vtoy_list_free(path_node, data->fontslist);
1056 }
1057 else
1058 {
1059 vtoy_list_del(last, node, data->fontslist, path);
1060 }
1061 }
1062
1063 ret = ventoy_data_save_all();
1064
1065 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1066 return 0;
1067 }
1068
1069 #if 0
1070 #endif
1071
1072 void ventoy_data_default_menu_alias(data_alias *data)
1073 {
1074 memset(data, 0, sizeof(data_alias));
1075 }
1076
1077 int ventoy_data_cmp_menu_alias(data_alias *data1, data_alias *data2)
1078 {
1079 data_alias_node *list1 = NULL;
1080 data_alias_node *list2 = NULL;
1081
1082 if (NULL == data1->list && NULL == data2->list)
1083 {
1084 return 0;
1085 }
1086 else if (data1->list && data2->list)
1087 {
1088 list1 = data1->list;
1089 list2 = data2->list;
1090
1091 while (list1 && list2)
1092 {
1093 if ((list1->type != list2->type) ||
1094 strcmp(list1->path, list2->path) ||
1095 strcmp(list1->alias, list2->alias))
1096 {
1097 return 1;
1098 }
1099
1100 list1 = list1->next;
1101 list2 = list2->next;
1102 }
1103
1104 if (list1 == NULL && list2 == NULL)
1105 {
1106 return 0;
1107 }
1108 return 1;
1109 }
1110 else
1111 {
1112 return 1;
1113 }
1114
1115 return 0;
1116 }
1117
1118
1119 int ventoy_data_save_menu_alias(data_alias *data, const char *title, char *buf, int buflen)
1120 {
1121 int pos = 0;
1122 data_alias_node *node = NULL;
1123
1124 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1125
1126 VTOY_JSON_FMT_KEY_L(L1, title);
1127 VTOY_JSON_FMT_ARY_BEGIN_N();
1128
1129 for (node = data->list; node; node = node->next)
1130 {
1131 VTOY_JSON_FMT_OBJ_BEGIN_LN(L2);
1132
1133 if (node->type == path_type_file)
1134 {
1135 VTOY_JSON_FMT_STRN_PATH_LN(L3, "image", node->path);
1136 }
1137 else
1138 {
1139 VTOY_JSON_FMT_STRN_PATH_LN(L3, "dir", node->path);
1140 }
1141
1142 VTOY_JSON_FMT_STRN_EX_LN(L3, "alias", node->alias);
1143
1144 VTOY_JSON_FMT_OBJ_ENDEX_LN(L2);
1145 }
1146
1147 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
1148 VTOY_JSON_FMT_END(pos);
1149
1150 return pos;
1151 }
1152
1153
1154 int ventoy_data_json_menu_alias(data_alias *data, char *buf, int buflen)
1155 {
1156 int pos = 0;
1157 int valid = 0;
1158 data_alias_node *node = NULL;
1159
1160 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1161 VTOY_JSON_FMT_ARY_BEGIN();
1162
1163 for (node = data->list; node; node = node->next)
1164 {
1165 VTOY_JSON_FMT_OBJ_BEGIN();
1166
1167 VTOY_JSON_FMT_UINT("type", node->type);
1168 VTOY_JSON_FMT_STRN("path", node->path);
1169 if (node->type == path_type_file)
1170 {
1171 valid = ventoy_check_fuzzy_path(node->path, 1);
1172 }
1173 else
1174 {
1175 valid = ventoy_is_directory_exist("%s%s", g_cur_dir, node->path);
1176 }
1177
1178 VTOY_JSON_FMT_SINT("valid", valid);
1179 VTOY_JSON_FMT_STRN("alias", node->alias);
1180
1181 VTOY_JSON_FMT_OBJ_ENDEX();
1182 }
1183
1184 VTOY_JSON_FMT_ARY_END();
1185 VTOY_JSON_FMT_END(pos);
1186
1187 return pos;
1188 }
1189
1190 static int ventoy_api_get_alias(struct mg_connection *conn, VTOY_JSON *json)
1191 {
1192 api_get_func(conn, json, menu_alias);
1193 return 0;
1194 }
1195
1196 static int ventoy_api_save_alias(struct mg_connection *conn, VTOY_JSON *json)
1197 {
1198 int ret;
1199 ret = ventoy_data_save_all();
1200
1201 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1202 return 0;
1203 }
1204
1205 static int ventoy_api_alias_add(struct mg_connection *conn, VTOY_JSON *json)
1206 {
1207 int ret;
1208 int index = 0;
1209 int type = path_type_file;
1210 const char *path = NULL;
1211 const char *alias = NULL;
1212 data_alias_node *node = NULL;
1213 data_alias_node *cur = NULL;
1214 data_alias *data = NULL;
1215
1216 vtoy_json_get_int(json, "index", &index);
1217 data = g_data_menu_alias + index;
1218
1219 vtoy_json_get_int(json, "type", &type);
1220
1221 path = VTOY_JSON_STR_EX("path");
1222 alias = VTOY_JSON_STR_EX("alias");
1223 if (path && alias)
1224 {
1225 node = zalloc(sizeof(data_alias_node));
1226 if (node)
1227 {
1228 node->type = type;
1229 scnprintf(node->path, sizeof(node->path), "%s", path);
1230 scnprintf(node->alias, sizeof(node->alias), "%s", alias);
1231
1232 vtoy_list_add(data->list, cur, node);
1233 }
1234 }
1235
1236 ret = ventoy_data_save_all();
1237
1238 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1239 return 0;
1240 }
1241
1242 static int ventoy_api_alias_del(struct mg_connection *conn, VTOY_JSON *json)
1243 {
1244 int ret;
1245 int index = 0;
1246 const char *path = NULL;
1247 data_alias_node *last = NULL;
1248 data_alias_node *node = NULL;
1249 data_alias *data = NULL;
1250
1251 vtoy_json_get_int(json, "index", &index);
1252 data = g_data_menu_alias + index;
1253
1254 path = VTOY_JSON_STR_EX("path");
1255 if (path)
1256 {
1257 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
1258 {
1259 vtoy_list_free(data_alias_node, data->list);
1260 }
1261 else
1262 {
1263 vtoy_list_del(last, node, data->list, path);
1264 }
1265 }
1266
1267 ret = ventoy_data_save_all();
1268
1269 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1270 return 0;
1271 }
1272
1273 #if 0
1274 #endif
1275
1276 void ventoy_data_default_menu_tip(data_tip *data)
1277 {
1278 memset(data, 0, sizeof(data_tip));
1279
1280 scnprintf(data->left, sizeof(data->left), "10%%");
1281 scnprintf(data->top, sizeof(data->top), "81%%");
1282 scnprintf(data->color, sizeof(data->color), "%s", "blue");
1283 }
1284
1285 int ventoy_data_cmp_menu_tip(data_tip *data1, data_tip *data2)
1286 {
1287 data_tip_node *list1 = NULL;
1288 data_tip_node *list2 = NULL;
1289
1290 if (strcmp(data1->left, data2->left) || strcmp(data1->top, data2->top) || strcmp(data1->color, data2->color))
1291 {
1292 return 1;
1293 }
1294
1295 if (NULL == data1->list && NULL == data2->list)
1296 {
1297 return 0;
1298 }
1299 else if (data1->list && data2->list)
1300 {
1301 list1 = data1->list;
1302 list2 = data2->list;
1303
1304 while (list1 && list2)
1305 {
1306 if ((list1->type != list2->type) ||
1307 strcmp(list1->path, list2->path) ||
1308 strcmp(list1->tip, list2->tip))
1309 {
1310 return 1;
1311 }
1312
1313 list1 = list1->next;
1314 list2 = list2->next;
1315 }
1316
1317 if (list1 == NULL && list2 == NULL)
1318 {
1319 return 0;
1320 }
1321 return 1;
1322 }
1323 else
1324 {
1325 return 1;
1326 }
1327
1328 return 0;
1329 }
1330
1331
1332 int ventoy_data_save_menu_tip(data_tip *data, const char *title, char *buf, int buflen)
1333 {
1334 int pos = 0;
1335 data_tip_node *node = NULL;
1336 data_tip *def = g_data_menu_tip + bios_max;
1337
1338 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1339 VTOY_JSON_FMT_KEY_L(L1, title);
1340 VTOY_JSON_FMT_OBJ_BEGIN_N();
1341
1342 VTOY_JSON_FMT_DIFF_STRN(L2, "left", left);
1343 VTOY_JSON_FMT_DIFF_STRN(L2, "top", top);
1344 VTOY_JSON_FMT_DIFF_STRN(L2, "color", color);
1345
1346 if (data->list)
1347 {
1348 VTOY_JSON_FMT_KEY_L(L2, "tips");
1349 VTOY_JSON_FMT_ARY_BEGIN_N();
1350
1351 for (node = data->list; node; node = node->next)
1352 {
1353 VTOY_JSON_FMT_OBJ_BEGIN_LN(L3);
1354
1355 if (node->type == path_type_file)
1356 {
1357 VTOY_JSON_FMT_STRN_PATH_LN(L4, "image", node->path);
1358 }
1359 else
1360 {
1361 VTOY_JSON_FMT_STRN_PATH_LN(L4, "dir", node->path);
1362 }
1363 VTOY_JSON_FMT_STRN_EX_LN(L4, "tip", node->tip);
1364
1365 VTOY_JSON_FMT_OBJ_ENDEX_LN(L3);
1366 }
1367
1368 VTOY_JSON_FMT_ARY_ENDEX_LN(L2);
1369 }
1370
1371 VTOY_JSON_FMT_OBJ_ENDEX_LN(L1);
1372
1373 VTOY_JSON_FMT_END(pos);
1374
1375 return pos;
1376 }
1377
1378
1379 int ventoy_data_json_menu_tip(data_tip *data, char *buf, int buflen)
1380 {
1381 int pos = 0;
1382 int valid = 0;
1383 data_tip_node *node = NULL;
1384
1385 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1386
1387 VTOY_JSON_FMT_OBJ_BEGIN();
1388
1389 VTOY_JSON_FMT_STRN("left", data->left);
1390 VTOY_JSON_FMT_STRN("top", data->top);
1391 VTOY_JSON_FMT_STRN("color", data->color);
1392
1393 VTOY_JSON_FMT_KEY("tips");
1394 VTOY_JSON_FMT_ARY_BEGIN();
1395
1396 for (node = data->list; node; node = node->next)
1397 {
1398 VTOY_JSON_FMT_OBJ_BEGIN();
1399
1400 VTOY_JSON_FMT_UINT("type", node->type);
1401 VTOY_JSON_FMT_STRN("path", node->path);
1402 if (node->type == path_type_file)
1403 {
1404 valid = ventoy_check_fuzzy_path(node->path, 1);
1405 }
1406 else
1407 {
1408 valid = ventoy_is_directory_exist("%s%s", g_cur_dir, node->path);
1409 }
1410
1411 VTOY_JSON_FMT_SINT("valid", valid);
1412 VTOY_JSON_FMT_STRN("tip", node->tip);
1413
1414 VTOY_JSON_FMT_OBJ_ENDEX();
1415 }
1416
1417 VTOY_JSON_FMT_ARY_ENDEX();
1418
1419 VTOY_JSON_FMT_OBJ_END();
1420 VTOY_JSON_FMT_END(pos);
1421
1422 return pos;
1423 }
1424
1425 static int ventoy_api_get_tip(struct mg_connection *conn, VTOY_JSON *json)
1426 {
1427 api_get_func(conn, json, menu_tip);
1428 return 0;
1429 }
1430
1431 static int ventoy_api_save_tip(struct mg_connection *conn, VTOY_JSON *json)
1432 {
1433 int ret;
1434 int index = 0;
1435 data_tip *data = NULL;
1436
1437 vtoy_json_get_int(json, "index", &index);
1438 data = g_data_menu_tip + index;
1439
1440 VTOY_JSON_STR("left", data->left);
1441 VTOY_JSON_STR("top", data->top);
1442 VTOY_JSON_STR("color", data->color);
1443
1444 ret = ventoy_data_save_all();
1445
1446 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1447 return 0;
1448 }
1449
1450 static int ventoy_api_tip_add(struct mg_connection *conn, VTOY_JSON *json)
1451 {
1452 int ret;
1453 int index = 0;
1454 int type = path_type_file;
1455 const char *path = NULL;
1456 const char *tip = NULL;
1457 data_tip_node *node = NULL;
1458 data_tip_node *cur = NULL;
1459 data_tip *data = NULL;
1460
1461 vtoy_json_get_int(json, "index", &index);
1462 data = g_data_menu_tip + index;
1463
1464 vtoy_json_get_int(json, "type", &type);
1465
1466 path = VTOY_JSON_STR_EX("path");
1467 tip = VTOY_JSON_STR_EX("tip");
1468 if (path && tip)
1469 {
1470 node = zalloc(sizeof(data_tip_node));
1471 if (node)
1472 {
1473 node->type = type;
1474 scnprintf(node->path, sizeof(node->path), "%s", path);
1475 scnprintf(node->tip, sizeof(node->tip), "%s", tip);
1476
1477 vtoy_list_add(data->list, cur, node);
1478 }
1479 }
1480
1481 ret = ventoy_data_save_all();
1482
1483 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1484 return 0;
1485 }
1486
1487 static int ventoy_api_tip_del(struct mg_connection *conn, VTOY_JSON *json)
1488 {
1489 int ret;
1490 int index = 0;
1491 const char *path = NULL;
1492 data_tip_node *last = NULL;
1493 data_tip_node *node = NULL;
1494 data_tip *data = NULL;
1495
1496 vtoy_json_get_int(json, "index", &index);
1497 data = g_data_menu_tip + index;
1498
1499 path = VTOY_JSON_STR_EX("path");
1500 if (path)
1501 {
1502 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
1503 {
1504 vtoy_list_free(data_tip_node, data->list);
1505 }
1506 else
1507 {
1508 vtoy_list_del(last, node, data->list, path);
1509 }
1510 }
1511
1512 ret = ventoy_data_save_all();
1513
1514 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1515 return 0;
1516 }
1517
1518 #if 0
1519 #endif
1520
1521 void ventoy_data_default_menu_class(data_class *data)
1522 {
1523 memset(data, 0, sizeof(data_class));
1524 }
1525
1526 int ventoy_data_cmp_menu_class(data_class *data1, data_class *data2)
1527 {
1528 data_class_node *list1 = NULL;
1529 data_class_node *list2 = NULL;
1530
1531 if (NULL == data1->list && NULL == data2->list)
1532 {
1533 return 0;
1534 }
1535 else if (data1->list && data2->list)
1536 {
1537 list1 = data1->list;
1538 list2 = data2->list;
1539
1540 while (list1 && list2)
1541 {
1542 if ((list1->type != list2->type) ||
1543 strcmp(list1->path, list2->path) ||
1544 strcmp(list1->class, list2->class))
1545 {
1546 return 1;
1547 }
1548
1549 list1 = list1->next;
1550 list2 = list2->next;
1551 }
1552
1553 if (list1 == NULL && list2 == NULL)
1554 {
1555 return 0;
1556 }
1557 return 1;
1558 }
1559 else
1560 {
1561 return 1;
1562 }
1563
1564 return 0;
1565 }
1566
1567
1568 int ventoy_data_save_menu_class(data_class *data, const char *title, char *buf, int buflen)
1569 {
1570 int pos = 0;
1571 data_class_node *node = NULL;
1572
1573 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1574
1575 VTOY_JSON_FMT_KEY_L(L1, title);
1576 VTOY_JSON_FMT_ARY_BEGIN_N();
1577
1578 for (node = data->list; node; node = node->next)
1579 {
1580 VTOY_JSON_FMT_OBJ_BEGIN_LN(L2);
1581
1582 if (node->type == class_type_key)
1583 {
1584 VTOY_JSON_FMT_STRN_LN(L3, "key", node->path);
1585 }
1586 else if (node->type == class_type_dir)
1587 {
1588 VTOY_JSON_FMT_STRN_PATH_LN(L3, "dir", node->path);
1589 }
1590 else
1591 {
1592 VTOY_JSON_FMT_STRN_PATH_LN(L3, "parent", node->path);
1593 }
1594 VTOY_JSON_FMT_STRN_LN(L3, "class", node->class);
1595
1596 VTOY_JSON_FMT_OBJ_ENDEX_LN(L2);
1597 }
1598
1599 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
1600 VTOY_JSON_FMT_END(pos);
1601
1602 return pos;
1603 }
1604
1605
1606 int ventoy_data_json_menu_class(data_class *data, char *buf, int buflen)
1607 {
1608 int pos = 0;
1609 int valid = 0;
1610 data_class_node *node = NULL;
1611
1612 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1613 VTOY_JSON_FMT_ARY_BEGIN();
1614
1615 for (node = data->list; node; node = node->next)
1616 {
1617 VTOY_JSON_FMT_OBJ_BEGIN();
1618
1619 VTOY_JSON_FMT_UINT("type", node->type);
1620 VTOY_JSON_FMT_STRN("path", node->path);
1621
1622 if (node->type == class_type_key)
1623 {
1624 valid = 1;
1625 }
1626 else
1627 {
1628 valid = ventoy_is_directory_exist("%s%s", g_cur_dir, node->path);
1629 }
1630 VTOY_JSON_FMT_SINT("valid", valid);
1631
1632 VTOY_JSON_FMT_STRN("class", node->class);
1633
1634 VTOY_JSON_FMT_OBJ_ENDEX();
1635 }
1636
1637 VTOY_JSON_FMT_ARY_END();
1638 VTOY_JSON_FMT_END(pos);
1639
1640 return pos;
1641 }
1642
1643
1644 static int ventoy_api_get_class(struct mg_connection *conn, VTOY_JSON *json)
1645 {
1646 api_get_func(conn, json, menu_class);
1647 return 0;
1648 }
1649
1650 static int ventoy_api_save_class(struct mg_connection *conn, VTOY_JSON *json)
1651 {
1652 int ret;
1653 ret = ventoy_data_save_all();
1654
1655 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1656 return 0;
1657 }
1658
1659 static int ventoy_api_class_add(struct mg_connection *conn, VTOY_JSON *json)
1660 {
1661 int ret;
1662 int index = 0;
1663 int type = class_type_key;
1664 const char *path = NULL;
1665 const char *class = NULL;
1666 data_class_node *node = NULL;
1667 data_class_node *cur = NULL;
1668 data_class *data = NULL;
1669
1670 vtoy_json_get_int(json, "index", &index);
1671 data = g_data_menu_class + index;
1672
1673 vtoy_json_get_int(json, "type", &type);
1674
1675 path = VTOY_JSON_STR_EX("path");
1676 class = VTOY_JSON_STR_EX("class");
1677 if (path && class)
1678 {
1679 node = zalloc(sizeof(data_class_node));
1680 if (node)
1681 {
1682 node->type = type;
1683
1684 scnprintf(node->path, sizeof(node->path), "%s", path);
1685 scnprintf(node->class, sizeof(node->class), "%s", class);
1686
1687 vtoy_list_add(data->list, cur, node);
1688 }
1689 }
1690
1691 ret = ventoy_data_save_all();
1692
1693 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1694 return 0;
1695 }
1696
1697 static int ventoy_api_class_del(struct mg_connection *conn, VTOY_JSON *json)
1698 {
1699 int ret;
1700 int index = 0;
1701 const char *path = NULL;
1702 data_class_node *last = NULL;
1703 data_class_node *node = NULL;
1704 data_class *data = NULL;
1705
1706 vtoy_json_get_int(json, "index", &index);
1707 data = g_data_menu_class + index;
1708
1709 path = VTOY_JSON_STR_EX("path");
1710 if (path)
1711 {
1712 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
1713 {
1714 vtoy_list_free(data_class_node, data->list);
1715 }
1716 else
1717 {
1718 vtoy_list_del(last, node, data->list, path);
1719 }
1720 }
1721
1722 ret = ventoy_data_save_all();
1723
1724 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1725 return 0;
1726 }
1727
1728 #if 0
1729 #endif
1730
1731 void ventoy_data_default_auto_memdisk(data_auto_memdisk *data)
1732 {
1733 memset(data, 0, sizeof(data_auto_memdisk));
1734 }
1735
1736 int ventoy_data_cmp_auto_memdisk(data_auto_memdisk *data1, data_auto_memdisk *data2)
1737 {
1738 return ventoy_path_list_cmp(data1->list, data2->list);
1739 }
1740
1741 int ventoy_data_save_auto_memdisk(data_auto_memdisk *data, const char *title, char *buf, int buflen)
1742 {
1743 int pos = 0;
1744 path_node *node = NULL;
1745
1746 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1747
1748 VTOY_JSON_FMT_KEY_L(L1, title);
1749 VTOY_JSON_FMT_ARY_BEGIN_N();
1750
1751 for (node = data->list; node; node = node->next)
1752 {
1753 VTOY_JSON_FMT_ITEM_PATH_LN(L2, node->path);
1754 }
1755
1756 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
1757 VTOY_JSON_FMT_END(pos);
1758
1759 return pos;
1760 }
1761
1762 int ventoy_data_json_auto_memdisk(data_auto_memdisk *data, char *buf, int buflen)
1763 {
1764 int pos = 0;
1765 int valid = 0;
1766 path_node *node = NULL;
1767
1768 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1769 VTOY_JSON_FMT_ARY_BEGIN();
1770
1771 for (node = data->list; node; node = node->next)
1772 {
1773 VTOY_JSON_FMT_OBJ_BEGIN();
1774
1775 VTOY_JSON_FMT_STRN("path", node->path);
1776 valid = ventoy_check_fuzzy_path(node->path, 1);
1777 VTOY_JSON_FMT_SINT("valid", valid);
1778
1779 VTOY_JSON_FMT_OBJ_ENDEX();
1780 }
1781
1782 VTOY_JSON_FMT_ARY_END();
1783 VTOY_JSON_FMT_END(pos);
1784
1785 return pos;
1786 }
1787
1788 static int ventoy_api_get_auto_memdisk(struct mg_connection *conn, VTOY_JSON *json)
1789 {
1790 api_get_func(conn, json, auto_memdisk);
1791 return 0;
1792 }
1793
1794 static int ventoy_api_save_auto_memdisk(struct mg_connection *conn, VTOY_JSON *json)
1795 {
1796 int ret;
1797
1798 ret = ventoy_data_save_all();
1799
1800 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1801 return 0;
1802 }
1803
1804 static int ventoy_api_auto_memdisk_add(struct mg_connection *conn, VTOY_JSON *json)
1805 {
1806 int ret;
1807 int index = 0;
1808 const char *path = NULL;
1809 path_node *node = NULL;
1810 path_node *cur = NULL;
1811 data_auto_memdisk *data = NULL;
1812
1813 vtoy_json_get_int(json, "index", &index);
1814 data = g_data_auto_memdisk + index;
1815
1816 path = VTOY_JSON_STR_EX("path");
1817 if (path)
1818 {
1819 node = zalloc(sizeof(path_node));
1820 if (node)
1821 {
1822 scnprintf(node->path, sizeof(node->path), "%s", path);
1823 vtoy_list_add(data->list, cur, node);
1824 }
1825 }
1826
1827 ret = ventoy_data_save_all();
1828
1829 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1830 return 0;
1831 }
1832
1833 static int ventoy_api_auto_memdisk_del(struct mg_connection *conn, VTOY_JSON *json)
1834 {
1835 int ret;
1836 int index = 0;
1837 const char *path = NULL;
1838 path_node *last = NULL;
1839 path_node *node = NULL;
1840 data_auto_memdisk *data = NULL;
1841
1842 vtoy_json_get_int(json, "index", &index);
1843 data = g_data_auto_memdisk + index;
1844
1845 path = VTOY_JSON_STR_EX("path");
1846 if (path)
1847 {
1848 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
1849 {
1850 vtoy_list_free(path_node, data->list);
1851 }
1852 else
1853 {
1854 vtoy_list_del(last, node, data->list, path);
1855 }
1856 }
1857
1858 ret = ventoy_data_save_all();
1859
1860 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1861 return 0;
1862 }
1863
1864 #if 0
1865 #endif
1866
1867 void ventoy_data_default_image_list(data_image_list *data)
1868 {
1869 memset(data, 0, sizeof(data_image_list));
1870 }
1871
1872 int ventoy_data_cmp_image_list(data_image_list *data1, data_image_list *data2)
1873 {
1874 if (data1->type != data2->type)
1875 {
1876 if (data1->list || data2->list)
1877 {
1878 return 1;
1879 }
1880 else
1881 {
1882 return 0;
1883 }
1884 }
1885
1886 return ventoy_path_list_cmp(data1->list, data2->list);
1887 }
1888
1889 int ventoy_data_save_image_list(data_image_list *data, const char *title, char *buf, int buflen)
1890 {
1891 int pos = 0;
1892 int prelen;
1893 path_node *node = NULL;
1894 char newtitle[64];
1895
1896 (void)title;
1897
1898 if (!(data->list))
1899 {
1900 return 0;
1901 }
1902
1903 prelen = (int)strlen("image_list");
1904
1905 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1906
1907 if (data->type == 0)
1908 {
1909 scnprintf(newtitle, sizeof(newtitle), "image_list%s", title + prelen);
1910 }
1911 else
1912 {
1913 scnprintf(newtitle, sizeof(newtitle), "image_blacklist%s", title + prelen);
1914 }
1915 VTOY_JSON_FMT_KEY_L(L1, newtitle);
1916
1917 VTOY_JSON_FMT_ARY_BEGIN_N();
1918
1919 for (node = data->list; node; node = node->next)
1920 {
1921 VTOY_JSON_FMT_ITEM_PATH_LN(L2, node->path);
1922 }
1923
1924 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
1925 VTOY_JSON_FMT_END(pos);
1926
1927 return pos;
1928 }
1929
1930 int ventoy_data_json_image_list(data_image_list *data, char *buf, int buflen)
1931 {
1932 int pos = 0;
1933 int valid = 0;
1934 path_node *node = NULL;
1935
1936 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
1937
1938 VTOY_JSON_FMT_OBJ_BEGIN();
1939 VTOY_JSON_FMT_SINT("type", data->type);
1940
1941 VTOY_JSON_FMT_KEY("list");
1942 VTOY_JSON_FMT_ARY_BEGIN();
1943
1944 for (node = data->list; node; node = node->next)
1945 {
1946 VTOY_JSON_FMT_OBJ_BEGIN();
1947
1948 VTOY_JSON_FMT_STRN("path", node->path);
1949 valid = ventoy_check_fuzzy_path(node->path, 1);
1950 VTOY_JSON_FMT_SINT("valid", valid);
1951
1952 VTOY_JSON_FMT_OBJ_ENDEX();
1953 }
1954
1955 VTOY_JSON_FMT_ARY_ENDEX();
1956 VTOY_JSON_FMT_OBJ_END();
1957
1958 VTOY_JSON_FMT_END(pos);
1959
1960 return pos;
1961 }
1962
1963 static int ventoy_api_get_image_list(struct mg_connection *conn, VTOY_JSON *json)
1964 {
1965 api_get_func(conn, json, image_list);
1966 return 0;
1967 }
1968
1969 static int ventoy_api_save_image_list(struct mg_connection *conn, VTOY_JSON *json)
1970 {
1971 int ret;
1972 int index = 0;
1973 data_image_list *data = NULL;
1974
1975 vtoy_json_get_int(json, "index", &index);
1976 data = g_data_image_list + index;
1977
1978 VTOY_JSON_INT("type", data->type);
1979
1980 ret = ventoy_data_save_all();
1981
1982 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
1983 return 0;
1984 }
1985
1986 static int ventoy_api_image_list_add(struct mg_connection *conn, VTOY_JSON *json)
1987 {
1988 int ret;
1989 int index = 0;
1990 const char *path = NULL;
1991 path_node *node = NULL;
1992 path_node *cur = NULL;
1993 data_image_list *data = NULL;
1994
1995 vtoy_json_get_int(json, "index", &index);
1996 data = g_data_image_list + index;
1997
1998 path = VTOY_JSON_STR_EX("path");
1999 if (path)
2000 {
2001 node = zalloc(sizeof(path_node));
2002 if (node)
2003 {
2004 scnprintf(node->path, sizeof(node->path), "%s", path);
2005 vtoy_list_add(data->list, cur, node);
2006 }
2007 }
2008
2009 ret = ventoy_data_save_all();
2010
2011 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2012 return 0;
2013 }
2014
2015 static int ventoy_api_image_list_del(struct mg_connection *conn, VTOY_JSON *json)
2016 {
2017 int ret;
2018 int index = 0;
2019 const char *path = NULL;
2020 path_node *last = NULL;
2021 path_node *node = NULL;
2022 data_image_list *data = NULL;
2023
2024 vtoy_json_get_int(json, "index", &index);
2025 data = g_data_image_list + index;
2026
2027 path = VTOY_JSON_STR_EX("path");
2028 if (path)
2029 {
2030 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
2031 {
2032 vtoy_list_free(path_node, data->list);
2033 }
2034 else
2035 {
2036 vtoy_list_del(last, node, data->list, path);
2037 }
2038 }
2039
2040 ret = ventoy_data_save_all();
2041
2042 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2043 return 0;
2044 }
2045
2046 #if 0
2047 #endif
2048
2049 void ventoy_data_default_password(data_password *data)
2050 {
2051 memset(data, 0, sizeof(data_password));
2052 }
2053
2054 int ventoy_data_cmp_password(data_password *data1, data_password *data2)
2055 {
2056 menu_password *list1 = NULL;
2057 menu_password *list2 = NULL;
2058
2059 if (strcmp(data1->bootpwd, data2->bootpwd) ||
2060 strcmp(data1->isopwd, data2->isopwd) ||
2061 strcmp(data1->wimpwd, data2->wimpwd) ||
2062 strcmp(data1->vhdpwd, data2->vhdpwd) ||
2063 strcmp(data1->imgpwd, data2->imgpwd) ||
2064 strcmp(data1->efipwd, data2->efipwd) ||
2065 strcmp(data1->vtoypwd, data2->vtoypwd)
2066 )
2067 {
2068 return 1;
2069 }
2070
2071 if (NULL == data1->list && NULL == data2->list)
2072 {
2073 return 0;
2074 }
2075 else if (data1->list && data2->list)
2076 {
2077 list1 = data1->list;
2078 list2 = data2->list;
2079
2080 while (list1 && list2)
2081 {
2082 if ((list1->type != list2->type) || strcmp(list1->path, list2->path))
2083 {
2084 return 1;
2085 }
2086
2087 list1 = list1->next;
2088 list2 = list2->next;
2089 }
2090
2091 if (list1 == NULL && list2 == NULL)
2092 {
2093 return 0;
2094 }
2095 return 1;
2096 }
2097 else
2098 {
2099 return 1;
2100 }
2101
2102 return 0;
2103 }
2104
2105
2106 int ventoy_data_save_password(data_password *data, const char *title, char *buf, int buflen)
2107 {
2108 int pos = 0;
2109 menu_password *node = NULL;
2110 data_password *def = g_data_password + bios_max;
2111
2112 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2113 VTOY_JSON_FMT_KEY_L(L1, title);
2114 VTOY_JSON_FMT_OBJ_BEGIN_N();
2115
2116 VTOY_JSON_FMT_DIFF_STRN(L2, "bootpwd", bootpwd);
2117 VTOY_JSON_FMT_DIFF_STRN(L2, "isopwd", isopwd);
2118 VTOY_JSON_FMT_DIFF_STRN(L2, "wimpwd", wimpwd);
2119 VTOY_JSON_FMT_DIFF_STRN(L2, "vhdpwd", vhdpwd);
2120 VTOY_JSON_FMT_DIFF_STRN(L2, "imgpwd", imgpwd);
2121 VTOY_JSON_FMT_DIFF_STRN(L2, "efipwd", efipwd);
2122 VTOY_JSON_FMT_DIFF_STRN(L2, "vtoypwd", vtoypwd);
2123
2124 if (data->list)
2125 {
2126 VTOY_JSON_FMT_KEY_L(L2, "menupwd");
2127 VTOY_JSON_FMT_ARY_BEGIN_N();
2128
2129 for (node = data->list; node; node = node->next)
2130 {
2131 VTOY_JSON_FMT_OBJ_BEGIN_LN(L3);
2132
2133 if (node->type == 0)
2134 {
2135 VTOY_JSON_FMT_STRN_PATH_LN(L4, "file", node->path);
2136 }
2137 else
2138 {
2139 VTOY_JSON_FMT_STRN_PATH_LN(L4, "parent", node->path);
2140 }
2141 VTOY_JSON_FMT_STRN_LN(L4, "pwd", node->pwd);
2142
2143 VTOY_JSON_FMT_OBJ_ENDEX_LN(L3);
2144 }
2145
2146 VTOY_JSON_FMT_ARY_ENDEX_LN(L2);
2147 }
2148
2149 VTOY_JSON_FMT_OBJ_ENDEX_LN(L1);
2150
2151 VTOY_JSON_FMT_END(pos);
2152
2153 return pos;
2154 }
2155
2156
2157 int ventoy_data_json_password(data_password *data, char *buf, int buflen)
2158 {
2159 int pos = 0;
2160 int valid = 0;
2161 menu_password *node = NULL;
2162
2163 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2164
2165 VTOY_JSON_FMT_OBJ_BEGIN();
2166
2167 VTOY_JSON_FMT_STRN("bootpwd", data->bootpwd);
2168 VTOY_JSON_FMT_STRN("isopwd", data->isopwd);
2169 VTOY_JSON_FMT_STRN("wimpwd", data->wimpwd);
2170 VTOY_JSON_FMT_STRN("vhdpwd", data->vhdpwd);
2171 VTOY_JSON_FMT_STRN("imgpwd", data->imgpwd);
2172 VTOY_JSON_FMT_STRN("efipwd", data->efipwd);
2173 VTOY_JSON_FMT_STRN("vtoypwd", data->vtoypwd);
2174
2175 VTOY_JSON_FMT_KEY("list");
2176 VTOY_JSON_FMT_ARY_BEGIN();
2177
2178 for (node = data->list; node; node = node->next)
2179 {
2180 VTOY_JSON_FMT_OBJ_BEGIN();
2181
2182 VTOY_JSON_FMT_SINT("type", node->type);
2183 VTOY_JSON_FMT_STRN("path", node->path);
2184 if (node->type == path_type_file)
2185 {
2186 valid = ventoy_check_fuzzy_path(node->path, 1);
2187 }
2188 else
2189 {
2190 valid = ventoy_is_directory_exist("%s%s", g_cur_dir, node->path);
2191 }
2192
2193 VTOY_JSON_FMT_SINT("valid", valid);
2194 VTOY_JSON_FMT_STRN("pwd", node->pwd);
2195
2196 VTOY_JSON_FMT_OBJ_ENDEX();
2197 }
2198
2199 VTOY_JSON_FMT_ARY_ENDEX();
2200
2201 VTOY_JSON_FMT_OBJ_END();
2202 VTOY_JSON_FMT_END(pos);
2203
2204 return pos;
2205 }
2206
2207 static int ventoy_api_get_password(struct mg_connection *conn, VTOY_JSON *json)
2208 {
2209 api_get_func(conn, json, password);
2210 return 0;
2211 }
2212
2213 static int ventoy_api_save_password(struct mg_connection *conn, VTOY_JSON *json)
2214 {
2215 int ret;
2216 int index = 0;
2217 data_password *data = NULL;
2218
2219 vtoy_json_get_int(json, "index", &index);
2220 data = g_data_password + index;
2221
2222 VTOY_JSON_STR("bootpwd", data->bootpwd);
2223 VTOY_JSON_STR("isopwd", data->isopwd);
2224 VTOY_JSON_STR("wimpwd", data->wimpwd);
2225 VTOY_JSON_STR("vhdpwd", data->vhdpwd);
2226 VTOY_JSON_STR("imgpwd", data->imgpwd);
2227 VTOY_JSON_STR("efipwd", data->efipwd);
2228 VTOY_JSON_STR("vtoypwd", data->vtoypwd);
2229
2230 ret = ventoy_data_save_all();
2231
2232 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2233 return 0;
2234 }
2235
2236 static int ventoy_api_password_add(struct mg_connection *conn, VTOY_JSON *json)
2237 {
2238 int ret;
2239 int index = 0;
2240 int type = 0;
2241 const char *path = NULL;
2242 const char *pwd = NULL;
2243 menu_password *node = NULL;
2244 menu_password *cur = NULL;
2245 data_password *data = NULL;
2246
2247 vtoy_json_get_int(json, "index", &index);
2248 data = g_data_password + index;
2249
2250 vtoy_json_get_int(json, "type", &type);
2251
2252 path = VTOY_JSON_STR_EX("path");
2253 pwd = VTOY_JSON_STR_EX("pwd");
2254 if (path && pwd)
2255 {
2256 node = zalloc(sizeof(menu_password));
2257 if (node)
2258 {
2259 node->type = type;
2260 scnprintf(node->path, sizeof(node->path), "%s", path);
2261 scnprintf(node->pwd, sizeof(node->pwd), "%s", pwd);
2262
2263 vtoy_list_add(data->list, cur, node);
2264 }
2265 }
2266
2267 ret = ventoy_data_save_all();
2268
2269 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2270 return 0;
2271 }
2272
2273 static int ventoy_api_password_del(struct mg_connection *conn, VTOY_JSON *json)
2274 {
2275 int ret;
2276 int index = 0;
2277 const char *path = NULL;
2278 menu_password *last = NULL;
2279 menu_password *node = NULL;
2280 data_password *data = NULL;
2281
2282 vtoy_json_get_int(json, "index", &index);
2283 data = g_data_password + index;
2284
2285 path = VTOY_JSON_STR_EX("path");
2286 if (path)
2287 {
2288 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
2289 {
2290 vtoy_list_free(menu_password, data->list);
2291 }
2292 else
2293 {
2294 vtoy_list_del(last, node, data->list, path);
2295 }
2296 }
2297
2298 ret = ventoy_data_save_all();
2299
2300 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2301 return 0;
2302 }
2303
2304 #if 0
2305 #endif
2306
2307 void ventoy_data_default_conf_replace(data_conf_replace *data)
2308 {
2309 memset(data, 0, sizeof(data_conf_replace));
2310 }
2311
2312 int ventoy_data_cmp_conf_replace(data_conf_replace *data1, data_conf_replace *data2)
2313 {
2314 conf_replace_node *list1 = NULL;
2315 conf_replace_node *list2 = NULL;
2316
2317 if (NULL == data1->list && NULL == data2->list)
2318 {
2319 return 0;
2320 }
2321 else if (data1->list && data2->list)
2322 {
2323 list1 = data1->list;
2324 list2 = data2->list;
2325
2326 while (list1 && list2)
2327 {
2328 if (list1->image != list2->image ||
2329 strcmp(list1->path, list2->path) ||
2330 strcmp(list1->org, list2->org) ||
2331 strcmp(list1->new, list2->new)
2332 )
2333 {
2334 return 1;
2335 }
2336
2337 list1 = list1->next;
2338 list2 = list2->next;
2339 }
2340
2341 if (list1 == NULL && list2 == NULL)
2342 {
2343 return 0;
2344 }
2345 return 1;
2346 }
2347 else
2348 {
2349 return 1;
2350 }
2351
2352 return 0;
2353 }
2354
2355
2356 int ventoy_data_save_conf_replace(data_conf_replace *data, const char *title, char *buf, int buflen)
2357 {
2358 int pos = 0;
2359 conf_replace_node *node = NULL;
2360
2361 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2362
2363 VTOY_JSON_FMT_KEY_L(L1, title);
2364 VTOY_JSON_FMT_ARY_BEGIN_N();
2365
2366 for (node = data->list; node; node = node->next)
2367 {
2368 VTOY_JSON_FMT_OBJ_BEGIN_LN(L2);
2369
2370 VTOY_JSON_FMT_STRN_PATH_LN(L3, "iso", node->path);
2371 VTOY_JSON_FMT_STRN_LN(L3, "org", node->org);
2372 VTOY_JSON_FMT_STRN_PATH_LN(L3, "new", node->new);
2373 if (node->image)
2374 {
2375 VTOY_JSON_FMT_SINT_LN(L3, "img", node->image);
2376 }
2377
2378 VTOY_JSON_FMT_OBJ_ENDEX_LN(L2);
2379 }
2380
2381 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
2382 VTOY_JSON_FMT_END(pos);
2383
2384 return pos;
2385 }
2386
2387
2388 int ventoy_data_json_conf_replace(data_conf_replace *data, char *buf, int buflen)
2389 {
2390 int pos = 0;
2391 conf_replace_node *node = NULL;
2392
2393 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2394 VTOY_JSON_FMT_ARY_BEGIN();
2395
2396 for (node = data->list; node; node = node->next)
2397 {
2398 VTOY_JSON_FMT_OBJ_BEGIN();
2399
2400 VTOY_JSON_FMT_STRN("path", node->path);
2401 VTOY_JSON_FMT_SINT("valid", ventoy_check_fuzzy_path(node->path, 1));
2402 VTOY_JSON_FMT_STRN("org", node->org);
2403 VTOY_JSON_FMT_STRN("new", node->new);
2404 VTOY_JSON_FMT_SINT("new_valid", ventoy_is_file_exist("%s%s", g_cur_dir, node->new));
2405 VTOY_JSON_FMT_SINT("img", node->image);
2406
2407 VTOY_JSON_FMT_OBJ_ENDEX();
2408 }
2409
2410 VTOY_JSON_FMT_ARY_END();
2411 VTOY_JSON_FMT_END(pos);
2412
2413 return pos;
2414 }
2415
2416 static int ventoy_api_get_conf_replace(struct mg_connection *conn, VTOY_JSON *json)
2417 {
2418 api_get_func(conn, json, conf_replace);
2419 return 0;
2420 }
2421
2422 static int ventoy_api_save_conf_replace(struct mg_connection *conn, VTOY_JSON *json)
2423 {
2424 int ret;
2425 ret = ventoy_data_save_all();
2426
2427 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2428 return 0;
2429 }
2430
2431 static int ventoy_api_conf_replace_add(struct mg_connection *conn, VTOY_JSON *json)
2432 {
2433 int ret;
2434 int image = 0;
2435 int index = 0;
2436 const char *path = NULL;
2437 const char *org = NULL;
2438 const char *new = NULL;
2439 conf_replace_node *node = NULL;
2440 conf_replace_node *cur = NULL;
2441 data_conf_replace *data = NULL;
2442
2443 vtoy_json_get_int(json, "img", &image);
2444
2445 vtoy_json_get_int(json, "index", &index);
2446 data = g_data_conf_replace + index;
2447
2448 path = VTOY_JSON_STR_EX("path");
2449 org = VTOY_JSON_STR_EX("org");
2450 new = VTOY_JSON_STR_EX("new");
2451 if (path && org && new)
2452 {
2453 node = zalloc(sizeof(conf_replace_node));
2454 if (node)
2455 {
2456 node->image = image;
2457 scnprintf(node->path, sizeof(node->path), "%s", path);
2458 scnprintf(node->org, sizeof(node->org), "%s", org);
2459 scnprintf(node->new, sizeof(node->new), "%s", new);
2460
2461 vtoy_list_add(data->list, cur, node);
2462 }
2463 }
2464
2465 ret = ventoy_data_save_all();
2466
2467 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2468 return 0;
2469 }
2470
2471 static int ventoy_api_conf_replace_del(struct mg_connection *conn, VTOY_JSON *json)
2472 {
2473 int ret;
2474 int index = 0;
2475 const char *path = NULL;
2476 conf_replace_node *last = NULL;
2477 conf_replace_node *node = NULL;
2478 data_conf_replace *data = NULL;
2479
2480 vtoy_json_get_int(json, "index", &index);
2481 data = g_data_conf_replace + index;
2482
2483 path = VTOY_JSON_STR_EX("path");
2484 if (path)
2485 {
2486 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
2487 {
2488 vtoy_list_free(conf_replace_node, data->list);
2489 }
2490 else
2491 {
2492 vtoy_list_del(last, node, data->list, path);
2493 }
2494 }
2495
2496 ret = ventoy_data_save_all();
2497
2498 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2499 return 0;
2500 }
2501
2502
2503 #if 0
2504 #endif
2505
2506 void ventoy_data_default_dud(data_dud *data)
2507 {
2508 memset(data, 0, sizeof(data_dud));
2509 }
2510
2511 int ventoy_data_cmp_dud(data_dud *data1, data_dud *data2)
2512 {
2513 dud_node *list1 = NULL;
2514 dud_node *list2 = NULL;
2515
2516 if (NULL == data1->list && NULL == data2->list)
2517 {
2518 return 0;
2519 }
2520 else if (data1->list && data2->list)
2521 {
2522 list1 = data1->list;
2523 list2 = data2->list;
2524
2525 while (list1 && list2)
2526 {
2527 if (strcmp(list1->path, list2->path))
2528 {
2529 return 1;
2530 }
2531
2532 /* no need to compare dud list with default */
2533 list1 = list1->next;
2534 list2 = list2->next;
2535 }
2536
2537 if (list1 == NULL && list2 == NULL)
2538 {
2539 return 0;
2540 }
2541 return 1;
2542 }
2543 else
2544 {
2545 return 1;
2546 }
2547
2548 return 0;
2549 }
2550
2551
2552 int ventoy_data_save_dud(data_dud *data, const char *title, char *buf, int buflen)
2553 {
2554 int pos = 0;
2555 dud_node *node = NULL;
2556 path_node *pathnode = NULL;
2557
2558 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2559
2560 VTOY_JSON_FMT_KEY_L(L1, title);
2561 VTOY_JSON_FMT_ARY_BEGIN_N();
2562
2563 for (node = data->list; node; node = node->next)
2564 {
2565 VTOY_JSON_FMT_OBJ_BEGIN_LN(L2);
2566 VTOY_JSON_FMT_STRN_PATH_LN(L3, "image", node->path);
2567
2568 VTOY_JSON_FMT_KEY_L(L3, "dud");
2569 VTOY_JSON_FMT_ARY_BEGIN_N();
2570 for (pathnode = node->list; pathnode; pathnode = pathnode->next)
2571 {
2572 VTOY_JSON_FMT_ITEM_PATH_LN(L4, pathnode->path);
2573 }
2574 VTOY_JSON_FMT_ARY_ENDEX_LN(L3);
2575
2576 VTOY_JSON_FMT_OBJ_ENDEX_LN(L2);
2577 }
2578
2579 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
2580 VTOY_JSON_FMT_END(pos);
2581
2582 return pos;
2583 }
2584
2585
2586 int ventoy_data_json_dud(data_dud *data, char *buf, int buflen)
2587 {
2588 int pos = 0;
2589 int valid = 0;
2590 dud_node *node = NULL;
2591 path_node *pathnode = NULL;
2592
2593 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2594 VTOY_JSON_FMT_ARY_BEGIN();
2595
2596 for (node = data->list; node; node = node->next)
2597 {
2598 VTOY_JSON_FMT_OBJ_BEGIN();
2599
2600 VTOY_JSON_FMT_STRN("path", node->path);
2601 valid = ventoy_check_fuzzy_path(node->path, 1);
2602 VTOY_JSON_FMT_SINT("valid", valid);
2603
2604
2605 VTOY_JSON_FMT_KEY("list");
2606 VTOY_JSON_FMT_ARY_BEGIN();
2607 for (pathnode = node->list; pathnode; pathnode = pathnode->next)
2608 {
2609 VTOY_JSON_FMT_OBJ_BEGIN();
2610 VTOY_JSON_FMT_STRN("path", pathnode->path);
2611
2612 valid = ventoy_is_file_exist("%s%s", g_cur_dir, pathnode->path);
2613 VTOY_JSON_FMT_SINT("valid", valid);
2614 VTOY_JSON_FMT_OBJ_ENDEX();
2615 }
2616 VTOY_JSON_FMT_ARY_ENDEX();
2617
2618
2619 VTOY_JSON_FMT_OBJ_ENDEX();
2620 }
2621
2622 VTOY_JSON_FMT_ARY_END();
2623 VTOY_JSON_FMT_END(pos);
2624
2625 return pos;
2626 }
2627
2628 static int ventoy_api_get_dud(struct mg_connection *conn, VTOY_JSON *json)
2629 {
2630 api_get_func(conn, json, dud);
2631 return 0;
2632 }
2633
2634 static int ventoy_api_save_dud(struct mg_connection *conn, VTOY_JSON *json)
2635 {
2636 int ret;
2637 ret = ventoy_data_save_all();
2638
2639 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2640 return 0;
2641 }
2642
2643
2644 static int ventoy_api_dud_add(struct mg_connection *conn, VTOY_JSON *json)
2645 {
2646 int ret;
2647 int index = 0;
2648 const char *path = NULL;
2649 dud_node *node = NULL;
2650 dud_node *cur = NULL;
2651 data_dud *data = NULL;
2652 VTOY_JSON *array = NULL;
2653
2654 vtoy_json_get_int(json, "index", &index);
2655 data = g_data_dud + index;
2656
2657 array = vtoy_json_find_item(json, JSON_TYPE_ARRAY, "dud");
2658 path = VTOY_JSON_STR_EX("path");
2659 if (path && array)
2660 {
2661 node = zalloc(sizeof(dud_node));
2662 if (node)
2663 {
2664 scnprintf(node->path, sizeof(node->path), "%s", path);
2665 node->list = ventoy_path_node_add_array(array);
2666
2667 vtoy_list_add(data->list, cur, node);
2668 }
2669 }
2670
2671 ret = ventoy_data_save_all();
2672
2673 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2674 return 0;
2675 }
2676
2677 static int ventoy_api_dud_del(struct mg_connection *conn, VTOY_JSON *json)
2678 {
2679 int ret;
2680 int index = 0;
2681 const char *path = NULL;
2682 dud_node *next = NULL;
2683 dud_node *last = NULL;
2684 dud_node *node = NULL;
2685 data_dud *data = NULL;
2686
2687 vtoy_json_get_int(json, "index", &index);
2688 data = g_data_dud + index;
2689
2690 path = VTOY_JSON_STR_EX("path");
2691 if (path)
2692 {
2693 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
2694 {
2695 for (node = data->list; node; node = next)
2696 {
2697 next = node->next;
2698 ventoy_free_path_node_list(node->list);
2699 free(node);
2700 }
2701 data->list = NULL;
2702 }
2703 else
2704 {
2705 vtoy_list_del_ex(last, node, data->list, path, ventoy_free_path_node_list);
2706 }
2707 }
2708
2709 ret = ventoy_data_save_all();
2710
2711 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2712 return 0;
2713 }
2714
2715
2716 static int ventoy_api_dud_add_inner(struct mg_connection *conn, VTOY_JSON *json)
2717 {
2718 int ret;
2719 int index = 0;
2720 const char *path = NULL;
2721 const char *outpath = NULL;
2722 path_node *pcur = NULL;
2723 path_node *pnode = NULL;
2724 dud_node *node = NULL;
2725 data_dud *data = NULL;
2726
2727 vtoy_json_get_int(json, "index", &index);
2728 data = g_data_dud + index;
2729
2730 path = VTOY_JSON_STR_EX("path");
2731 outpath = VTOY_JSON_STR_EX("outpath");
2732 if (path && outpath)
2733 {
2734 for (node = data->list; node; node = node->next)
2735 {
2736 if (strcmp(outpath, node->path) == 0)
2737 {
2738 pnode = zalloc(sizeof(path_node));
2739 if (pnode)
2740 {
2741 scnprintf(pnode->path, sizeof(pnode->path), "%s", path);
2742 vtoy_list_add(node->list, pcur, pnode);
2743 }
2744
2745 break;
2746 }
2747 }
2748 }
2749
2750 ret = ventoy_data_save_all();
2751
2752 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2753 return 0;
2754 }
2755
2756 static int ventoy_api_dud_del_inner(struct mg_connection *conn, VTOY_JSON *json)
2757 {
2758 int ret;
2759 int index = 0;
2760 const char *path = NULL;
2761 const char *outpath = NULL;
2762 path_node *plast = NULL;
2763 path_node *pnode = NULL;
2764 dud_node *node = NULL;
2765 data_dud *data = NULL;
2766
2767 vtoy_json_get_int(json, "index", &index);
2768 data = g_data_dud + index;
2769
2770 path = VTOY_JSON_STR_EX("path");
2771 outpath = VTOY_JSON_STR_EX("outpath");
2772 if (path && outpath)
2773 {
2774 for (node = data->list; node; node = node->next)
2775 {
2776 if (strcmp(outpath, node->path) == 0)
2777 {
2778 vtoy_list_del(plast, pnode, node->list, path);
2779 break;
2780 }
2781 }
2782 }
2783
2784 ret = ventoy_data_save_all();
2785
2786 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2787 return 0;
2788 }
2789
2790
2791 #if 0
2792 #endif
2793
2794 void ventoy_data_default_auto_install(data_auto_install *data)
2795 {
2796 memset(data, 0, sizeof(data_auto_install));
2797 }
2798
2799 int ventoy_data_cmp_auto_install(data_auto_install *data1, data_auto_install *data2)
2800 {
2801 auto_install_node *list1 = NULL;
2802 auto_install_node *list2 = NULL;
2803
2804 if (NULL == data1->list && NULL == data2->list)
2805 {
2806 return 0;
2807 }
2808 else if (data1->list && data2->list)
2809 {
2810 list1 = data1->list;
2811 list2 = data2->list;
2812
2813 while (list1 && list2)
2814 {
2815 if (list1->timeout != list2->timeout ||
2816 list1->autosel != list2->autosel ||
2817 strcmp(list1->path, list2->path))
2818 {
2819 return 1;
2820 }
2821
2822 /* no need to compare auto install list with default */
2823 list1 = list1->next;
2824 list2 = list2->next;
2825 }
2826
2827 if (list1 == NULL && list2 == NULL)
2828 {
2829 return 0;
2830 }
2831 return 1;
2832 }
2833 else
2834 {
2835 return 1;
2836 }
2837
2838 return 0;
2839 }
2840
2841
2842 int ventoy_data_save_auto_install(data_auto_install *data, const char *title, char *buf, int buflen)
2843 {
2844 int pos = 0;
2845 auto_install_node *node = NULL;
2846 path_node *pathnode = NULL;
2847
2848 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2849
2850 VTOY_JSON_FMT_KEY_L(L1, title);
2851 VTOY_JSON_FMT_ARY_BEGIN_N();
2852
2853 for (node = data->list; node; node = node->next)
2854 {
2855 VTOY_JSON_FMT_OBJ_BEGIN_LN(L2);
2856 if (node->type == 0)
2857 {
2858 VTOY_JSON_FMT_STRN_PATH_LN(L3, "image", node->path);
2859 }
2860 else
2861 {
2862 VTOY_JSON_FMT_STRN_PATH_LN(L3, "parent", node->path);
2863 }
2864
2865
2866 VTOY_JSON_FMT_KEY_L(L3, "template");
2867 VTOY_JSON_FMT_ARY_BEGIN_N();
2868 for (pathnode = node->list; pathnode; pathnode = pathnode->next)
2869 {
2870 VTOY_JSON_FMT_ITEM_PATH_LN(L4, pathnode->path);
2871 }
2872 VTOY_JSON_FMT_ARY_ENDEX_LN(L3);
2873
2874 if (node->timeouten)
2875 {
2876 VTOY_JSON_FMT_SINT_LN(L3, "timeout", node->timeout);
2877 }
2878
2879 if (node->autoselen)
2880 {
2881 VTOY_JSON_FMT_SINT_LN(L3, "autosel", node->autosel);
2882 }
2883
2884 VTOY_JSON_FMT_OBJ_ENDEX_LN(L2);
2885 }
2886
2887 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
2888 VTOY_JSON_FMT_END(pos);
2889
2890 return pos;
2891 }
2892
2893
2894 int ventoy_data_json_auto_install(data_auto_install *data, char *buf, int buflen)
2895 {
2896 int pos = 0;
2897 int valid = 0;
2898 auto_install_node *node = NULL;
2899 path_node *pathnode = NULL;
2900
2901 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
2902 VTOY_JSON_FMT_ARY_BEGIN();
2903
2904 for (node = data->list; node; node = node->next)
2905 {
2906 VTOY_JSON_FMT_OBJ_BEGIN();
2907
2908 VTOY_JSON_FMT_STRN("path", node->path);
2909
2910 if (node->type == 0)
2911 {
2912 valid = ventoy_check_fuzzy_path(node->path, 1);
2913 }
2914 else
2915 {
2916 valid = ventoy_is_directory_exist("%s%s", g_cur_dir, node->path);
2917 }
2918 VTOY_JSON_FMT_SINT("valid", valid);
2919 VTOY_JSON_FMT_SINT("type", node->type);
2920
2921 VTOY_JSON_FMT_BOOL("timeouten", node->timeouten);
2922 VTOY_JSON_FMT_BOOL("autoselen", node->autoselen);
2923
2924 VTOY_JSON_FMT_SINT("autosel", node->autosel);
2925 VTOY_JSON_FMT_SINT("timeout", node->timeout);
2926
2927 VTOY_JSON_FMT_KEY("list");
2928 VTOY_JSON_FMT_ARY_BEGIN();
2929 for (pathnode = node->list; pathnode; pathnode = pathnode->next)
2930 {
2931 VTOY_JSON_FMT_OBJ_BEGIN();
2932 VTOY_JSON_FMT_STRN("path", pathnode->path);
2933
2934 valid = ventoy_is_file_exist("%s%s", g_cur_dir, pathnode->path);
2935 VTOY_JSON_FMT_SINT("valid", valid);
2936 VTOY_JSON_FMT_OBJ_ENDEX();
2937 }
2938 VTOY_JSON_FMT_ARY_ENDEX();
2939
2940
2941 VTOY_JSON_FMT_OBJ_ENDEX();
2942 }
2943
2944 VTOY_JSON_FMT_ARY_END();
2945 VTOY_JSON_FMT_END(pos);
2946
2947 return pos;
2948 }
2949
2950 static int ventoy_api_get_auto_install(struct mg_connection *conn, VTOY_JSON *json)
2951 {
2952 api_get_func(conn, json, auto_install);
2953 return 0;
2954 }
2955
2956 static int ventoy_api_save_auto_install(struct mg_connection *conn, VTOY_JSON *json)
2957 {
2958 int ret;
2959 int id = -1;
2960 int cnt = 0;
2961 int index = 0;
2962 uint8_t timeouten = 0;
2963 uint8_t autoselen = 0;
2964 auto_install_node *node = NULL;
2965 data_auto_install *data = NULL;
2966
2967 vtoy_json_get_int(json, "index", &index);
2968 vtoy_json_get_int(json, "id", &id);
2969
2970 vtoy_json_get_bool(json, "timeouten", &timeouten);
2971 vtoy_json_get_bool(json, "autoselen", &autoselen);
2972
2973 data = g_data_auto_install + index;
2974
2975 if (id >= 0)
2976 {
2977 for (node = data->list; node; node = node->next)
2978 {
2979 if (cnt == id)
2980 {
2981 node->timeouten = (int)timeouten;
2982 node->autoselen = (int)autoselen;
2983 VTOY_JSON_INT("timeout", node->timeout);
2984 VTOY_JSON_INT("autosel", node->autosel);
2985 break;
2986 }
2987 }
2988 }
2989
2990 ret = ventoy_data_save_all();
2991
2992 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
2993 return 0;
2994 }
2995
2996
2997 static int ventoy_api_auto_install_add(struct mg_connection *conn, VTOY_JSON *json)
2998 {
2999 int ret;
3000 int index = 0;
3001 int type = 0;
3002 const char *path = NULL;
3003 auto_install_node *node = NULL;
3004 auto_install_node *cur = NULL;
3005 data_auto_install *data = NULL;
3006 VTOY_JSON *array = NULL;
3007
3008 vtoy_json_get_int(json, "type", &type);
3009 vtoy_json_get_int(json, "index", &index);
3010 data = g_data_auto_install + index;
3011
3012 array = vtoy_json_find_item(json, JSON_TYPE_ARRAY, "template");
3013 path = VTOY_JSON_STR_EX("path");
3014 if (path && array)
3015 {
3016 node = zalloc(sizeof(auto_install_node));
3017 if (node)
3018 {
3019 node->type = type;
3020 node->timeouten = 0;
3021 node->autoselen = 0;
3022 node->autosel = 1;
3023 node->timeout = 0;
3024 scnprintf(node->path, sizeof(node->path), "%s", path);
3025 node->list = ventoy_path_node_add_array(array);
3026
3027 vtoy_list_add(data->list, cur, node);
3028 }
3029 }
3030
3031 ret = ventoy_data_save_all();
3032
3033 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3034 return 0;
3035 }
3036
3037 static int ventoy_api_auto_install_del(struct mg_connection *conn, VTOY_JSON *json)
3038 {
3039 int ret;
3040 int index = 0;
3041 const char *path = NULL;
3042 auto_install_node *last = NULL;
3043 auto_install_node *next = NULL;
3044 auto_install_node *node = NULL;
3045 data_auto_install *data = NULL;
3046
3047 vtoy_json_get_int(json, "index", &index);
3048 data = g_data_auto_install + index;
3049
3050 path = VTOY_JSON_STR_EX("path");
3051 if (path)
3052 {
3053 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
3054 {
3055 for (node = data->list; node; node = next)
3056 {
3057 next = node->next;
3058 ventoy_free_path_node_list(node->list);
3059 free(node);
3060 }
3061 data->list = NULL;
3062 }
3063 else
3064 {
3065 vtoy_list_del_ex(last, node, data->list, path, ventoy_free_path_node_list);
3066 }
3067 }
3068
3069 ret = ventoy_data_save_all();
3070
3071 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3072 return 0;
3073 }
3074
3075 static int ventoy_api_auto_install_add_inner(struct mg_connection *conn, VTOY_JSON *json)
3076 {
3077 int ret;
3078 int index = 0;
3079 const char *path = NULL;
3080 const char *outpath = NULL;
3081 path_node *pcur = NULL;
3082 path_node *pnode = NULL;
3083 auto_install_node *node = NULL;
3084 data_auto_install *data = NULL;
3085
3086 vtoy_json_get_int(json, "index", &index);
3087 data = g_data_auto_install + index;
3088
3089 path = VTOY_JSON_STR_EX("path");
3090 outpath = VTOY_JSON_STR_EX("outpath");
3091 if (path && outpath)
3092 {
3093 for (node = data->list; node; node = node->next)
3094 {
3095 if (strcmp(outpath, node->path) == 0)
3096 {
3097 pnode = zalloc(sizeof(path_node));
3098 if (pnode)
3099 {
3100 scnprintf(pnode->path, sizeof(pnode->path), "%s", path);
3101 vtoy_list_add(node->list, pcur, pnode);
3102 }
3103
3104 break;
3105 }
3106 }
3107 }
3108
3109 ret = ventoy_data_save_all();
3110
3111 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3112 return 0;
3113 }
3114
3115 static int ventoy_api_auto_install_del_inner(struct mg_connection *conn, VTOY_JSON *json)
3116 {
3117 int ret;
3118 int index = 0;
3119 const char *path = NULL;
3120 const char *outpath = NULL;
3121 path_node *plast = NULL;
3122 path_node *pnode = NULL;
3123 auto_install_node *node = NULL;
3124 data_auto_install *data = NULL;
3125
3126 vtoy_json_get_int(json, "index", &index);
3127 data = g_data_auto_install + index;
3128
3129 path = VTOY_JSON_STR_EX("path");
3130 outpath = VTOY_JSON_STR_EX("outpath");
3131 if (path && outpath)
3132 {
3133 for (node = data->list; node; node = node->next)
3134 {
3135 if (strcmp(outpath, node->path) == 0)
3136 {
3137 vtoy_list_del(plast, pnode, node->list, path);
3138 break;
3139 }
3140 }
3141 }
3142
3143 ret = ventoy_data_save_all();
3144
3145 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3146 return 0;
3147 }
3148
3149
3150 #if 0
3151 #endif
3152
3153
3154 void ventoy_data_default_persistence(data_persistence *data)
3155 {
3156 memset(data, 0, sizeof(data_persistence));
3157 }
3158
3159 int ventoy_data_cmp_persistence(data_persistence *data1, data_persistence *data2)
3160 {
3161 persistence_node *list1 = NULL;
3162 persistence_node *list2 = NULL;
3163
3164 if (NULL == data1->list && NULL == data2->list)
3165 {
3166 return 0;
3167 }
3168 else if (data1->list && data2->list)
3169 {
3170 list1 = data1->list;
3171 list2 = data2->list;
3172
3173 while (list1 && list2)
3174 {
3175 if (list1->timeout != list2->timeout ||
3176 list1->autosel != list2->autosel ||
3177 strcmp(list1->path, list2->path))
3178 {
3179 return 1;
3180 }
3181
3182 /* no need to compare auto install list with default */
3183 list1 = list1->next;
3184 list2 = list2->next;
3185 }
3186
3187 if (list1 == NULL && list2 == NULL)
3188 {
3189 return 0;
3190 }
3191 return 1;
3192 }
3193 else
3194 {
3195 return 1;
3196 }
3197
3198 return 0;
3199 }
3200
3201
3202 int ventoy_data_save_persistence(data_persistence *data, const char *title, char *buf, int buflen)
3203 {
3204 int pos = 0;
3205 persistence_node *node = NULL;
3206 path_node *pathnode = NULL;
3207
3208 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
3209
3210 VTOY_JSON_FMT_KEY_L(L1, title);
3211 VTOY_JSON_FMT_ARY_BEGIN_N();
3212
3213 for (node = data->list; node; node = node->next)
3214 {
3215 VTOY_JSON_FMT_OBJ_BEGIN_LN(L2);
3216 VTOY_JSON_FMT_STRN_PATH_LN(L3, "image", node->path);
3217 VTOY_JSON_FMT_KEY_L(L3, "backend");
3218 VTOY_JSON_FMT_ARY_BEGIN_N();
3219 for (pathnode = node->list; pathnode; pathnode = pathnode->next)
3220 {
3221 VTOY_JSON_FMT_ITEM_PATH_LN(L4, pathnode->path);
3222 }
3223 VTOY_JSON_FMT_ARY_ENDEX_LN(L3);
3224
3225 if (node->timeouten)
3226 {
3227 VTOY_JSON_FMT_SINT_LN(L3, "timeout", node->timeout);
3228 }
3229
3230 if (node->autoselen)
3231 {
3232 VTOY_JSON_FMT_SINT_LN(L3, "autosel", node->autosel);
3233 }
3234
3235 VTOY_JSON_FMT_OBJ_ENDEX_LN(L2);
3236 }
3237
3238 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
3239 VTOY_JSON_FMT_END(pos);
3240
3241 return pos;
3242 }
3243
3244
3245 int ventoy_data_json_persistence(data_persistence *data, char *buf, int buflen)
3246 {
3247 int pos = 0;
3248 int valid = 0;
3249 persistence_node *node = NULL;
3250 path_node *pathnode = NULL;
3251
3252 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
3253 VTOY_JSON_FMT_ARY_BEGIN();
3254
3255 for (node = data->list; node; node = node->next)
3256 {
3257 VTOY_JSON_FMT_OBJ_BEGIN();
3258
3259 VTOY_JSON_FMT_STRN("path", node->path);
3260
3261 valid = ventoy_check_fuzzy_path(node->path, 1);
3262 VTOY_JSON_FMT_SINT("valid", valid);
3263 VTOY_JSON_FMT_SINT("type", node->type);
3264
3265 VTOY_JSON_FMT_BOOL("timeouten", node->timeouten);
3266 VTOY_JSON_FMT_BOOL("autoselen", node->autoselen);
3267
3268 VTOY_JSON_FMT_SINT("autosel", node->autosel);
3269 VTOY_JSON_FMT_SINT("timeout", node->timeout);
3270
3271 VTOY_JSON_FMT_KEY("list");
3272 VTOY_JSON_FMT_ARY_BEGIN();
3273 for (pathnode = node->list; pathnode; pathnode = pathnode->next)
3274 {
3275 VTOY_JSON_FMT_OBJ_BEGIN();
3276 VTOY_JSON_FMT_STRN("path", pathnode->path);
3277
3278 valid = ventoy_is_file_exist("%s%s", g_cur_dir, pathnode->path);
3279 VTOY_JSON_FMT_SINT("valid", valid);
3280 VTOY_JSON_FMT_OBJ_ENDEX();
3281 }
3282 VTOY_JSON_FMT_ARY_ENDEX();
3283
3284
3285 VTOY_JSON_FMT_OBJ_ENDEX();
3286 }
3287
3288 VTOY_JSON_FMT_ARY_END();
3289 VTOY_JSON_FMT_END(pos);
3290
3291 return pos;
3292 }
3293
3294 static int ventoy_api_get_persistence(struct mg_connection *conn, VTOY_JSON *json)
3295 {
3296 api_get_func(conn, json, persistence);
3297 return 0;
3298 }
3299
3300 static int ventoy_api_save_persistence(struct mg_connection *conn, VTOY_JSON *json)
3301 {
3302 int ret;
3303 int id = -1;
3304 int cnt = 0;
3305 int index = 0;
3306 uint8_t timeouten = 0;
3307 uint8_t autoselen = 0;
3308 persistence_node *node = NULL;
3309 data_persistence *data = NULL;
3310
3311 vtoy_json_get_int(json, "index", &index);
3312 vtoy_json_get_int(json, "id", &id);
3313
3314 vtoy_json_get_bool(json, "timeouten", &timeouten);
3315 vtoy_json_get_bool(json, "autoselen", &autoselen);
3316
3317 data = g_data_persistence + index;
3318
3319 if (id >= 0)
3320 {
3321 for (node = data->list; node; node = node->next)
3322 {
3323 if (cnt == id)
3324 {
3325 node->timeouten = (int)timeouten;
3326 node->autoselen = (int)autoselen;
3327 VTOY_JSON_INT("timeout", node->timeout);
3328 VTOY_JSON_INT("autosel", node->autosel);
3329 break;
3330 }
3331 }
3332 }
3333
3334 ret = ventoy_data_save_all();
3335
3336 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3337 return 0;
3338 }
3339
3340
3341 static int ventoy_api_persistence_add(struct mg_connection *conn, VTOY_JSON *json)
3342 {
3343 int ret;
3344 int index = 0;
3345 const char *path = NULL;
3346 persistence_node *node = NULL;
3347 persistence_node *cur = NULL;
3348 data_persistence *data = NULL;
3349 VTOY_JSON *array = NULL;
3350
3351 vtoy_json_get_int(json, "index", &index);
3352 data = g_data_persistence + index;
3353
3354 array = vtoy_json_find_item(json, JSON_TYPE_ARRAY, "backend");
3355 path = VTOY_JSON_STR_EX("path");
3356 if (path && array)
3357 {
3358 node = zalloc(sizeof(persistence_node));
3359 if (node)
3360 {
3361 node->timeouten = 0;
3362 node->autoselen = 0;
3363 node->autosel = 1;
3364 node->timeout = 0;
3365 scnprintf(node->path, sizeof(node->path), "%s", path);
3366 node->list = ventoy_path_node_add_array(array);
3367
3368 vtoy_list_add(data->list, cur, node);
3369 }
3370 }
3371
3372 ret = ventoy_data_save_all();
3373
3374 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3375 return 0;
3376 }
3377
3378 static int ventoy_api_persistence_del(struct mg_connection *conn, VTOY_JSON *json)
3379 {
3380 int ret;
3381 int index = 0;
3382 const char *path = NULL;
3383 persistence_node *last = NULL;
3384 persistence_node *next = NULL;
3385 persistence_node *node = NULL;
3386 data_persistence *data = NULL;
3387
3388 vtoy_json_get_int(json, "index", &index);
3389 data = g_data_persistence + index;
3390
3391 path = VTOY_JSON_STR_EX("path");
3392 if (path)
3393 {
3394 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
3395 {
3396 for (node = data->list; node; node = next)
3397 {
3398 next = node->next;
3399 ventoy_free_path_node_list(node->list);
3400 free(node);
3401 }
3402 data->list = NULL;
3403 }
3404 else
3405 {
3406 vtoy_list_del_ex(last, node, data->list, path, ventoy_free_path_node_list);
3407 }
3408 }
3409
3410 ret = ventoy_data_save_all();
3411
3412 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3413 return 0;
3414 }
3415
3416 static int ventoy_api_persistence_add_inner(struct mg_connection *conn, VTOY_JSON *json)
3417 {
3418 int ret;
3419 int index = 0;
3420 const char *path = NULL;
3421 const char *outpath = NULL;
3422 path_node *pcur = NULL;
3423 path_node *pnode = NULL;
3424 persistence_node *node = NULL;
3425 data_persistence *data = NULL;
3426
3427 vtoy_json_get_int(json, "index", &index);
3428 data = g_data_persistence + index;
3429
3430 path = VTOY_JSON_STR_EX("path");
3431 outpath = VTOY_JSON_STR_EX("outpath");
3432 if (path && outpath)
3433 {
3434 for (node = data->list; node; node = node->next)
3435 {
3436 if (strcmp(outpath, node->path) == 0)
3437 {
3438 pnode = zalloc(sizeof(path_node));
3439 if (pnode)
3440 {
3441 scnprintf(pnode->path, sizeof(pnode->path), "%s", path);
3442 vtoy_list_add(node->list, pcur, pnode);
3443 }
3444
3445 break;
3446 }
3447 }
3448 }
3449
3450 ret = ventoy_data_save_all();
3451
3452 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3453 return 0;
3454 }
3455
3456 static int ventoy_api_persistence_del_inner(struct mg_connection *conn, VTOY_JSON *json)
3457 {
3458 int ret;
3459 int index = 0;
3460 const char *path = NULL;
3461 const char *outpath = NULL;
3462 path_node *plast = NULL;
3463 path_node *pnode = NULL;
3464 persistence_node *node = NULL;
3465 data_persistence *data = NULL;
3466
3467 vtoy_json_get_int(json, "index", &index);
3468 data = g_data_persistence + index;
3469
3470 path = VTOY_JSON_STR_EX("path");
3471 outpath = VTOY_JSON_STR_EX("outpath");
3472 if (path && outpath)
3473 {
3474 for (node = data->list; node; node = node->next)
3475 {
3476 if (strcmp(outpath, node->path) == 0)
3477 {
3478 vtoy_list_del(plast, pnode, node->list, path);
3479 break;
3480 }
3481 }
3482 }
3483
3484 ret = ventoy_data_save_all();
3485
3486 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3487 return 0;
3488 }
3489
3490
3491 #if 0
3492 #endif
3493
3494 void ventoy_data_default_injection(data_injection *data)
3495 {
3496 memset(data, 0, sizeof(data_injection));
3497 }
3498
3499 int ventoy_data_cmp_injection(data_injection *data1, data_injection *data2)
3500 {
3501 injection_node *list1 = NULL;
3502 injection_node *list2 = NULL;
3503
3504 if (NULL == data1->list && NULL == data2->list)
3505 {
3506 return 0;
3507 }
3508 else if (data1->list && data2->list)
3509 {
3510 list1 = data1->list;
3511 list2 = data2->list;
3512
3513 while (list1 && list2)
3514 {
3515 if ((list1->type != list2->type) ||
3516 strcmp(list1->path, list2->path) ||
3517 strcmp(list1->archive, list2->archive))
3518 {
3519 return 1;
3520 }
3521
3522 list1 = list1->next;
3523 list2 = list2->next;
3524 }
3525
3526 if (list1 == NULL && list2 == NULL)
3527 {
3528 return 0;
3529 }
3530 return 1;
3531 }
3532 else
3533 {
3534 return 1;
3535 }
3536
3537 return 0;
3538 }
3539
3540
3541 int ventoy_data_save_injection(data_injection *data, const char *title, char *buf, int buflen)
3542 {
3543 int pos = 0;
3544 injection_node *node = NULL;
3545
3546 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
3547
3548 VTOY_JSON_FMT_KEY_L(L1, title);
3549 VTOY_JSON_FMT_ARY_BEGIN_N();
3550
3551 for (node = data->list; node; node = node->next)
3552 {
3553 VTOY_JSON_FMT_OBJ_BEGIN_LN(L2);
3554
3555 if (node->type == 0)
3556 {
3557 VTOY_JSON_FMT_STRN_PATH_LN(L3, "image", node->path);
3558 }
3559 else
3560 {
3561 VTOY_JSON_FMT_STRN_PATH_LN(L3, "parent", node->path);
3562 }
3563 VTOY_JSON_FMT_STRN_PATH_LN(L3, "archive", node->archive);
3564
3565 VTOY_JSON_FMT_OBJ_ENDEX_LN(L2);
3566 }
3567
3568 VTOY_JSON_FMT_ARY_ENDEX_LN(L1);
3569 VTOY_JSON_FMT_END(pos);
3570
3571 return pos;
3572 }
3573
3574
3575 int ventoy_data_json_injection(data_injection *data, char *buf, int buflen)
3576 {
3577 int pos = 0;
3578 int valid = 0;
3579 injection_node *node = NULL;
3580
3581 VTOY_JSON_FMT_BEGIN(pos, buf, buflen);
3582 VTOY_JSON_FMT_ARY_BEGIN();
3583
3584 for (node = data->list; node; node = node->next)
3585 {
3586 VTOY_JSON_FMT_OBJ_BEGIN();
3587
3588 VTOY_JSON_FMT_UINT("type", node->type);
3589 VTOY_JSON_FMT_STRN("path", node->path);
3590
3591 if (node->type == 0)
3592 {
3593 valid = ventoy_check_fuzzy_path(node->path, 1);
3594 }
3595 else
3596 {
3597 valid = ventoy_is_directory_exist("%s%s", g_cur_dir, node->path);
3598 }
3599 VTOY_JSON_FMT_SINT("valid", valid);
3600
3601 VTOY_JSON_FMT_STRN("archive", node->archive);
3602
3603 valid = ventoy_is_file_exist("%s%s", g_cur_dir, node->archive);
3604 VTOY_JSON_FMT_SINT("archive_valid", valid);
3605
3606 VTOY_JSON_FMT_OBJ_ENDEX();
3607 }
3608
3609 VTOY_JSON_FMT_ARY_END();
3610 VTOY_JSON_FMT_END(pos);
3611
3612 return pos;
3613 }
3614
3615
3616 static int ventoy_api_get_injection(struct mg_connection *conn, VTOY_JSON *json)
3617 {
3618 api_get_func(conn, json, injection);
3619 return 0;
3620 }
3621
3622 static int ventoy_api_save_injection(struct mg_connection *conn, VTOY_JSON *json)
3623 {
3624 int ret;
3625 ret = ventoy_data_save_all();
3626
3627 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3628 return 0;
3629 }
3630
3631 static int ventoy_api_injection_add(struct mg_connection *conn, VTOY_JSON *json)
3632 {
3633 int ret;
3634 int index = 0;
3635 int type = 0;
3636 const char *path = NULL;
3637 const char *archive = NULL;
3638 injection_node *node = NULL;
3639 injection_node *cur = NULL;
3640 data_injection *data = NULL;
3641
3642 vtoy_json_get_int(json, "index", &index);
3643 data = g_data_injection + index;
3644
3645 vtoy_json_get_int(json, "type", &type);
3646
3647 path = VTOY_JSON_STR_EX("path");
3648 archive = VTOY_JSON_STR_EX("archive");
3649 if (path && archive)
3650 {
3651 node = zalloc(sizeof(injection_node));
3652 if (node)
3653 {
3654 node->type = type;
3655
3656 scnprintf(node->path, sizeof(node->path), "%s", path);
3657 scnprintf(node->archive, sizeof(node->archive), "%s", archive);
3658
3659 vtoy_list_add(data->list, cur, node);
3660 }
3661 }
3662
3663 ret = ventoy_data_save_all();
3664
3665 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3666 return 0;
3667 }
3668
3669 static int ventoy_api_injection_del(struct mg_connection *conn, VTOY_JSON *json)
3670 {
3671 int ret;
3672 int index = 0;
3673 const char *path = NULL;
3674 injection_node *last = NULL;
3675 injection_node *node = NULL;
3676 data_injection *data = NULL;
3677
3678 vtoy_json_get_int(json, "index", &index);
3679 data = g_data_injection + index;
3680
3681 path = VTOY_JSON_STR_EX("path");
3682 if (path)
3683 {
3684 if (strcmp(path, VTOY_DEL_ALL_PATH) == 0)
3685 {
3686 vtoy_list_free(injection_node, data->list);
3687 }
3688 else
3689 {
3690 vtoy_list_del(last, node, data->list, path);
3691 }
3692 }
3693
3694 ret = ventoy_data_save_all();
3695
3696 ventoy_json_result(conn, ret == 0 ? VTOY_JSON_SUCCESS_RET : VTOY_JSON_FAILED_RET);
3697 return 0;
3698 }
3699
3700 #if 0
3701 #endif
3702
3703 static int ventoy_api_preview_json(struct mg_connection *conn, VTOY_JSON *json)
3704 {
3705 int i = 0;
3706 int pos = 0;
3707 int len = 0;
3708 int utf16enclen = 0;
3709 char *encodebuf = NULL;
3710 unsigned short *utf16buf = NULL;
3711
3712 (void)json;
3713
3714 /* We can not use json directly, because it will be formated in the JS. */
3715
3716 len = ventoy_data_real_save_all(0);
3717
3718 utf16buf = (unsigned short *)malloc(2 * len + 16);
3719 if (!utf16buf)
3720 {
3721 goto json;
3722 }
3723
3724 utf16enclen = (int)utf8_to_utf16((unsigned char *)JSON_SAVE_BUFFER, len, utf16buf, len + 2);
3725
3726 encodebuf = (char *)malloc(utf16enclen * 4 + 16);
3727 if (!encodebuf)
3728 {
3729 goto json;
3730 }
3731
3732 for (i = 0; i < utf16enclen; i++)
3733 {
3734 scnprintf(encodebuf + i * 4, 5, "%04X", utf16buf[i]);
3735 }
3736
3737 json:
3738 VTOY_JSON_FMT_BEGIN(pos, JSON_BUFFER, JSON_BUF_MAX);
3739 VTOY_JSON_FMT_OBJ_BEGIN();
3740 VTOY_JSON_FMT_STRN("json", (encodebuf ? encodebuf : ""));
3741 VTOY_JSON_FMT_OBJ_END();
3742 VTOY_JSON_FMT_END(pos);
3743
3744 CHECK_FREE(encodebuf);
3745 CHECK_FREE(utf16buf);
3746
3747 ventoy_json_buffer(conn, JSON_BUFFER, pos);
3748 return 0;
3749 }
3750
3751
3752 #if 0
3753 #endif
3754
3755 int ventoy_data_save_all(void)
3756 {
3757 ventoy_set_writeback_event();
3758 return 0;
3759 }
3760
3761 int ventoy_data_real_save_all(int apilock)
3762 {
3763 int i = 0;
3764 int pos = 0;
3765 char title[64];
3766
3767 if (apilock)
3768 {
3769 pthread_mutex_lock(&g_api_mutex);
3770 }
3771
3772 ssprintf(pos, JSON_SAVE_BUFFER, JSON_BUF_MAX, "{\n");
3773
3774 ventoy_save_plug(control);
3775 ventoy_save_plug(theme);
3776 ventoy_save_plug(menu_alias);
3777 ventoy_save_plug(menu_tip);
3778 ventoy_save_plug(menu_class);
3779 ventoy_save_plug(auto_install);
3780 ventoy_save_plug(persistence);
3781 ventoy_save_plug(injection);
3782 ventoy_save_plug(conf_replace);
3783 ventoy_save_plug(password);
3784 ventoy_save_plug(image_list);
3785 ventoy_save_plug(auto_memdisk);
3786 ventoy_save_plug(dud);
3787
3788 if (JSON_SAVE_BUFFER[pos - 1] == '\n' && JSON_SAVE_BUFFER[pos - 2] == ',')
3789 {
3790 JSON_SAVE_BUFFER[pos - 2] = '\n';
3791 pos--;
3792 }
3793 ssprintf(pos, JSON_SAVE_BUFFER, JSON_BUF_MAX, "}\n");
3794
3795 if (apilock)
3796 {
3797 pthread_mutex_unlock(&g_api_mutex);
3798 }
3799
3800 return pos;
3801 }
3802
3803 int ventoy_http_writeback(void)
3804 {
3805 int ret;
3806 int pos;
3807 char filename[128];
3808
3809 ventoy_get_json_path(filename, NULL);
3810
3811 pos = ventoy_data_real_save_all(1);
3812
3813 #ifdef VENTOY_SIM
3814 printf("%s", JSON_SAVE_BUFFER);
3815 #endif
3816
3817 ret = ventoy_write_buf_to_file(filename, JSON_SAVE_BUFFER, pos);
3818 if (ret)
3819 {
3820 vlog("Failed to write ventoy.json file.\n");
3821 g_sysinfo.config_save_error = 1;
3822 }
3823
3824 return 0;
3825 }
3826
3827
3828 static JSON_CB g_ventoy_json_cb[] =
3829 {
3830 { "sysinfo", ventoy_api_sysinfo },
3831 { "handshake", ventoy_api_handshake },
3832 { "check_path", ventoy_api_check_exist },
3833 { "check_path2", ventoy_api_check_exist2 },
3834 { "check_fuzzy", ventoy_api_check_fuzzy },
3835
3836 { "device_info", ventoy_api_device_info },
3837
3838 { "get_control", ventoy_api_get_control },
3839 { "save_control", ventoy_api_save_control },
3840
3841 { "get_theme", ventoy_api_get_theme },
3842 { "save_theme", ventoy_api_save_theme },
3843 { "theme_add_file", ventoy_api_theme_add_file },
3844 { "theme_del_file", ventoy_api_theme_del_file },
3845 { "theme_add_font", ventoy_api_theme_add_font },
3846 { "theme_del_font", ventoy_api_theme_del_font },
3847
3848 { "get_alias", ventoy_api_get_alias },
3849 { "save_alias", ventoy_api_save_alias },
3850 { "alias_add", ventoy_api_alias_add },
3851 { "alias_del", ventoy_api_alias_del },
3852
3853 { "get_tip", ventoy_api_get_tip },
3854 { "save_tip", ventoy_api_save_tip },
3855 { "tip_add", ventoy_api_tip_add },
3856 { "tip_del", ventoy_api_tip_del },
3857
3858 { "get_class", ventoy_api_get_class },
3859 { "save_class", ventoy_api_save_class },
3860 { "class_add", ventoy_api_class_add },
3861 { "class_del", ventoy_api_class_del },
3862
3863 { "get_auto_memdisk", ventoy_api_get_auto_memdisk },
3864 { "save_auto_memdisk", ventoy_api_save_auto_memdisk },
3865 { "auto_memdisk_add", ventoy_api_auto_memdisk_add },
3866 { "auto_memdisk_del", ventoy_api_auto_memdisk_del },
3867
3868 { "get_image_list", ventoy_api_get_image_list },
3869 { "save_image_list", ventoy_api_save_image_list },
3870 { "image_list_add", ventoy_api_image_list_add },
3871 { "image_list_del", ventoy_api_image_list_del },
3872
3873 { "get_conf_replace", ventoy_api_get_conf_replace },
3874 { "save_conf_replace", ventoy_api_save_conf_replace },
3875 { "conf_replace_add", ventoy_api_conf_replace_add },
3876 { "conf_replace_del", ventoy_api_conf_replace_del },
3877
3878 { "get_dud", ventoy_api_get_dud },
3879 { "save_dud", ventoy_api_save_dud },
3880 { "dud_add", ventoy_api_dud_add },
3881 { "dud_del", ventoy_api_dud_del },
3882 { "dud_add_inner", ventoy_api_dud_add_inner },
3883 { "dud_del_inner", ventoy_api_dud_del_inner },
3884
3885 { "get_auto_install", ventoy_api_get_auto_install },
3886 { "save_auto_install", ventoy_api_save_auto_install },
3887 { "auto_install_add", ventoy_api_auto_install_add },
3888 { "auto_install_del", ventoy_api_auto_install_del },
3889 { "auto_install_add_inner", ventoy_api_auto_install_add_inner },
3890 { "auto_install_del_inner", ventoy_api_auto_install_del_inner },
3891
3892 { "get_persistence", ventoy_api_get_persistence },
3893 { "save_persistence", ventoy_api_save_persistence },
3894 { "persistence_add", ventoy_api_persistence_add },
3895 { "persistence_del", ventoy_api_persistence_del },
3896 { "persistence_add_inner", ventoy_api_persistence_add_inner },
3897 { "persistence_del_inner", ventoy_api_persistence_del_inner },
3898
3899 { "get_password", ventoy_api_get_password },
3900 { "save_password", ventoy_api_save_password },
3901 { "password_add", ventoy_api_password_add },
3902 { "password_del", ventoy_api_password_del },
3903
3904 { "get_injection", ventoy_api_get_injection },
3905 { "save_injection", ventoy_api_save_injection },
3906 { "injection_add", ventoy_api_injection_add },
3907 { "injection_del", ventoy_api_injection_del },
3908 { "preview_json", ventoy_api_preview_json },
3909
3910 };
3911
3912 static int ventoy_json_handler(struct mg_connection *conn, VTOY_JSON *json, char *jsonstr)
3913 {
3914 int i;
3915 const char *method = NULL;
3916
3917 method = vtoy_json_get_string_ex(json, "method");
3918 if (!method)
3919 {
3920 ventoy_json_result(conn, VTOY_JSON_SUCCESS_RET);
3921 return 0;
3922 }
3923
3924 if (strcmp(method, "handshake") == 0)
3925 {
3926 ventoy_api_handshake(conn, json);
3927 return 0;
3928 }
3929
3930 for (i = 0; i < (int)(sizeof(g_ventoy_json_cb) / sizeof(g_ventoy_json_cb[0])); i++)
3931 {
3932 if (strcmp(method, g_ventoy_json_cb[i].method) == 0)
3933 {
3934 g_ventoy_json_cb[i].callback(conn, json);
3935 break;
3936 }
3937 }
3938
3939 return 0;
3940 }
3941
3942 static int ventoy_request_handler(struct mg_connection *conn)
3943 {
3944 int post_data_len;
3945 int post_buf_len;
3946 VTOY_JSON *json = NULL;
3947 char *post_data_buf = NULL;
3948 const struct mg_request_info *ri = NULL;
3949 char stack_buf[512];
3950
3951 ri = mg_get_request_info(conn);
3952
3953 if (strcmp(ri->uri, "/vtoy/json") == 0)
3954 {
3955 if (ri->content_length > 500)
3956 {
3957 post_data_buf = malloc((int)(ri->content_length + 4));
3958 post_buf_len = (int)(ri->content_length + 1);
3959 }
3960 else
3961 {
3962 post_data_buf = stack_buf;
3963 post_buf_len = sizeof(stack_buf);
3964 }
3965
3966 post_data_len = mg_read(conn, post_data_buf, post_buf_len);
3967 post_data_buf[post_data_len] = 0;
3968
3969 json = vtoy_json_create();
3970 if (JSON_SUCCESS == vtoy_json_parse(json, post_data_buf))
3971 {
3972 pthread_mutex_lock(&g_api_mutex);
3973 ventoy_json_handler(conn, json->pstChild, post_data_buf);
3974 pthread_mutex_unlock(&g_api_mutex);
3975 }
3976 else
3977 {
3978 ventoy_json_result(conn, VTOY_JSON_INVALID_RET);
3979 }
3980
3981 vtoy_json_destroy(json);
3982
3983 if (post_data_buf != stack_buf)
3984 {
3985 free(post_data_buf);
3986 }
3987 return 1;
3988 }
3989 else
3990 {
3991 return 0;
3992 }
3993 }
3994
3995 const char *ventoy_web_openfile(const struct mg_connection *conn, const char *path, size_t *data_len)
3996 {
3997 ventoy_file *node = NULL;
3998
3999 (void)conn;
4000
4001 if (!path)
4002 {
4003 return NULL;
4004 }
4005
4006 node = ventoy_tar_find_file(path);
4007 if (node)
4008 {
4009 *data_len = node->size;
4010 return node->addr;
4011 }
4012 else
4013 {
4014 return NULL;
4015 }
4016 }
4017
4018 #if 0
4019 #endif
4020
4021 static int ventoy_parse_control(VTOY_JSON *json, void *p)
4022 {
4023 int i;
4024 VTOY_JSON *node = NULL;
4025 VTOY_JSON *child = NULL;
4026 data_control *data = (data_control *)p;
4027
4028 if (json->enDataType != JSON_TYPE_ARRAY)
4029 {
4030 return 0;
4031 }
4032
4033 for (node = json->pstChild; node; node = node->pstNext)
4034 {
4035 if (node->enDataType == JSON_TYPE_OBJECT)
4036 {
4037 child = node->pstChild;
4038
4039 if (child->enDataType != JSON_TYPE_STRING)
4040 {
4041 continue;
4042 }
4043
4044 if (strcmp(child->pcName, "VTOY_DEFAULT_MENU_MODE") == 0)
4045 {
4046 CONTROL_PARSE_INT_DEF_0(child, data->default_menu_mode);
4047 }
4048 else if (strcmp(child->pcName, "VTOY_WIN11_BYPASS_CHECK") == 0)
4049 {
4050 CONTROL_PARSE_INT_DEF_0(child, data->win11_bypass_check);
4051 }
4052 else if (strcmp(child->pcName, "VTOY_LINUX_REMOUNT") == 0)
4053 {
4054 CONTROL_PARSE_INT_DEF_0(child, data->linux_remount);
4055 }
4056 else if (strcmp(child->pcName, "VTOY_SECONDARY_BOOT_MENU") == 0)
4057 {
4058 CONTROL_PARSE_INT_DEF_1(child, data->secondary_menu);
4059 }
4060 else if (strcmp(child->pcName, "VTOY_SHOW_PASSWORD_ASTERISK") == 0)
4061 {
4062 CONTROL_PARSE_INT_DEF_1(child, data->password_asterisk);
4063 }
4064 else if (strcmp(child->pcName, "VTOY_TREE_VIEW_MENU_STYLE") == 0)
4065 {
4066 CONTROL_PARSE_INT_DEF_0(child, data->treeview_style);
4067 }
4068 else if (strcmp(child->pcName, "VTOY_FILT_DOT_UNDERSCORE_FILE") == 0)
4069 {
4070 CONTROL_PARSE_INT_DEF_1(child, data->filter_dot_underscore);
4071 }
4072 else if (strcmp(child->pcName, "VTOY_SORT_CASE_SENSITIVE") == 0)
4073 {
4074 CONTROL_PARSE_INT_DEF_0(child, data->sort_casesensitive);
4075 }
4076 else if (strcmp(child->pcName, "VTOY_MAX_SEARCH_LEVEL") == 0)
4077 {
4078 if (strcmp(child->unData.pcStrVal, "max") == 0)
4079 {
4080 data->max_search_level = -1;
4081 }
4082 else
4083 {
4084 data->max_search_level = (int)strtol(child->unData.pcStrVal, NULL, 10);
4085 }
4086 }
4087 else if (strcmp(child->pcName, "VTOY_DEFAULT_SEARCH_ROOT") == 0)
4088 {
4089 strlcpy(data->default_search_root, child->unData.pcStrVal);
4090 }
4091 else if (strcmp(child->pcName, "VTOY_DEFAULT_IMAGE") == 0)
4092 {
4093 strlcpy(data->default_image, child->unData.pcStrVal);
4094 }
4095 else if (strcmp(child->pcName, "VTOY_DEFAULT_KBD_LAYOUT") == 0)
4096 {
4097 for (i = 0; g_ventoy_kbd_layout[i]; i++)
4098 {
4099 if (strcmp(child->unData.pcStrVal, g_ventoy_kbd_layout[i]) == 0)
4100 {
4101 strlcpy(data->default_kbd_layout, child->unData.pcStrVal);
4102 break;
4103 }
4104 }
4105 }
4106 else if (strcmp(child->pcName, "VTOY_MENU_LANGUAGE") == 0)
4107 {
4108 for (i = 0; g_ventoy_menu_lang[i][0]; i++)
4109 {
4110 if (strcmp(child->unData.pcStrVal, g_ventoy_menu_lang[i]) == 0)
4111 {
4112 strlcpy(data->menu_language, child->unData.pcStrVal);
4113 break;
4114 }
4115 }
4116 }
4117 else if (strcmp(child->pcName, "VTOY_MENU_TIMEOUT") == 0)
4118 {
4119 data->menu_timeout = (int)strtol(child->unData.pcStrVal, NULL, 10);
4120 }
4121 else if (strcmp(child->pcName, "VTOY_SECONDARY_TIMEOUT") == 0)
4122 {
4123 data->secondary_menu_timeout = (int)strtol(child->unData.pcStrVal, NULL, 10);
4124 }
4125 else if (strcmp(child->pcName, "VTOY_VHD_NO_WARNING") == 0)
4126 {
4127 CONTROL_PARSE_INT_DEF_0(child, data->vhd_no_warning);
4128 }
4129 else if (strcmp(child->pcName, "VTOY_FILE_FLT_ISO") == 0)
4130 {
4131 CONTROL_PARSE_INT_DEF_0(child, data->filter_iso);
4132 }
4133 else if (strcmp(child->pcName, "VTOY_FILE_FLT_IMG") == 0)
4134 {
4135 CONTROL_PARSE_INT_DEF_0(child, data->filter_img);
4136 }
4137 else if (strcmp(child->pcName, "VTOY_FILE_FLT_EFI") == 0)
4138 {
4139 CONTROL_PARSE_INT_DEF_0(child, data->filter_efi);
4140 }
4141 else if (strcmp(child->pcName, "VTOY_FILE_FLT_WIM") == 0)
4142 {
4143 CONTROL_PARSE_INT_DEF_0(child, data->filter_wim);
4144 }
4145 else if (strcmp(child->pcName, "VTOY_FILE_FLT_VHD") == 0)
4146 {
4147 CONTROL_PARSE_INT_DEF_0(child, data->filter_vhd);
4148 }
4149 else if (strcmp(child->pcName, "VTOY_FILE_FLT_VTOY") == 0)
4150 {
4151 CONTROL_PARSE_INT_DEF_0(child, data->filter_vtoy);
4152 }
4153
4154 }
4155 }
4156
4157 return 0;
4158 }
4159 static int ventoy_parse_theme(VTOY_JSON *json, void *p)
4160 {
4161 const char *dismode = NULL;
4162 VTOY_JSON *child = NULL;
4163 VTOY_JSON *node = NULL;
4164 path_node *tail = NULL;
4165 path_node *pnode = NULL;
4166 data_theme *data = (data_theme *)p;
4167
4168 if (json->enDataType != JSON_TYPE_OBJECT)
4169 {
4170 return 0;
4171 }
4172
4173 child = json->pstChild;
4174
4175 dismode = vtoy_json_get_string_ex(child, "display_mode");
4176 vtoy_json_get_string(child, "ventoy_left", sizeof(data->ventoy_left), data->ventoy_left);
4177 vtoy_json_get_string(child, "ventoy_top", sizeof(data->ventoy_top), data->ventoy_top);
4178 vtoy_json_get_string(child, "ventoy_color", sizeof(data->ventoy_color), data->ventoy_color);
4179
4180 vtoy_json_get_int(child, "default_file", &(data->default_file));
4181 vtoy_json_get_string(child, "gfxmode", sizeof(data->gfxmode), data->gfxmode);
4182 vtoy_json_get_string(child, "serial_param", sizeof(data->serial_param), data->serial_param);
4183
4184 if (dismode)
4185 {
4186 if (strcmp(dismode, "CLI") == 0)
4187 {
4188 data->display_mode = display_mode_cli;
4189 }
4190 else if (strcmp(dismode, "serial") == 0)
4191 {
4192 data->display_mode = display_mode_serial;
4193 }
4194 else if (strcmp(dismode, "serial_console") == 0)
4195 {
4196 data->display_mode = display_mode_ser_console;
4197 }
4198 else
4199 {
4200 data->display_mode = display_mode_gui;
4201 }
4202 }
4203
4204 node = vtoy_json_find_item(child, JSON_TYPE_STRING, "file");
4205 if (node)
4206 {
4207 data->default_file = 0;
4208
4209 pnode = zalloc(sizeof(path_node));
4210 if (pnode)
4211 {
4212 strlcpy(pnode->path, node->unData.pcStrVal);
4213 data->filelist = pnode;
4214 }
4215 }
4216 else
4217 {
4218 node = vtoy_json_find_item(child, JSON_TYPE_ARRAY, "file");
4219 if (node)
4220 {
4221 for (node = node->pstChild; node; node = node->pstNext)
4222 {
4223 if (node->enDataType == JSON_TYPE_STRING)
4224 {
4225 pnode = zalloc(sizeof(path_node));
4226 if (pnode)
4227 {
4228 strlcpy(pnode->path, node->unData.pcStrVal);
4229 if (data->filelist)
4230 {
4231 tail->next = pnode;
4232 tail = pnode;
4233 }
4234 else
4235 {
4236 data->filelist = tail = pnode;
4237 }
4238 }
4239 }
4240 }
4241 }
4242 }
4243
4244
4245 node = vtoy_json_find_item(child, JSON_TYPE_ARRAY, "fonts");
4246 if (node)
4247 {
4248 for (node = node->pstChild; node; node = node->pstNext)
4249 {
4250 if (node->enDataType == JSON_TYPE_STRING)
4251 {
4252 pnode = zalloc(sizeof(path_node));
4253 if (pnode)
4254 {
4255 strlcpy(pnode->path, node->unData.pcStrVal);
4256 if (data->fontslist)
4257 {
4258 tail->next = pnode;
4259 tail = pnode;
4260 }
4261 else
4262 {
4263 data->fontslist = tail = pnode;
4264 }
4265 }
4266 }
4267 }
4268 }
4269
4270 return 0;
4271 }
4272 static int ventoy_parse_menu_alias(VTOY_JSON *json, void *p)
4273 {
4274 int type;
4275 const char *path = NULL;
4276 const char *alias = NULL;
4277 data_alias *data = (data_alias *)p;
4278 data_alias_node *tail = NULL;
4279 data_alias_node *pnode = NULL;
4280 VTOY_JSON *node = NULL;
4281
4282 if (json->enDataType != JSON_TYPE_ARRAY)
4283 {
4284 return 0;
4285 }
4286
4287 for (node = json->pstChild; node; node = node->pstNext)
4288 {
4289 if (node->enDataType != JSON_TYPE_OBJECT)
4290 {
4291 continue;
4292 }
4293
4294 type = path_type_file;
4295 path = vtoy_json_get_string_ex(node->pstChild, "image");
4296 if (!path)
4297 {
4298 path = vtoy_json_get_string_ex(node->pstChild, "dir");
4299 type = path_type_dir;
4300 }
4301 alias = vtoy_json_get_string_ex(node->pstChild, "alias");
4302
4303 if (path && alias)
4304 {
4305 pnode = zalloc(sizeof(data_alias_node));
4306 if (pnode)
4307 {
4308 pnode->type = type;
4309 strlcpy(pnode->path, path);
4310 strlcpy(pnode->alias, alias);
4311
4312 if (data->list)
4313 {
4314 tail->next = pnode;
4315 tail = pnode;
4316 }
4317 else
4318 {
4319 data->list = tail = pnode;
4320 }
4321 }
4322 }
4323 }
4324
4325 return 0;
4326 }
4327
4328 static int ventoy_parse_menu_tip(VTOY_JSON *json, void *p)
4329 {
4330 int type;
4331 const char *path = NULL;
4332 const char *tip = NULL;
4333 data_tip *data = (data_tip *)p;
4334 data_tip_node *tail = NULL;
4335 data_tip_node *pnode = NULL;
4336 VTOY_JSON *node = NULL;
4337 VTOY_JSON *tips = NULL;
4338
4339 if (json->enDataType != JSON_TYPE_OBJECT)
4340 {
4341 return 0;
4342 }
4343
4344 vtoy_json_get_string(json->pstChild, "left", sizeof(data->left), data->left);
4345 vtoy_json_get_string(json->pstChild, "top", sizeof(data->top), data->top);
4346 vtoy_json_get_string(json->pstChild, "color", sizeof(data->color), data->color);
4347
4348 tips = vtoy_json_find_item(json->pstChild, JSON_TYPE_ARRAY, "tips");
4349 if (!tips)
4350 {
4351 return 0;
4352 }
4353
4354 for (node = tips->pstChild; node; node = node->pstNext)
4355 {
4356 if (node->enDataType != JSON_TYPE_OBJECT)
4357 {
4358 continue;
4359 }
4360
4361 type = path_type_file;
4362 path = vtoy_json_get_string_ex(node->pstChild, "image");
4363 if (!path)
4364 {
4365 path = vtoy_json_get_string_ex(node->pstChild, "dir");
4366 type = path_type_dir;
4367 }
4368 tip = vtoy_json_get_string_ex(node->pstChild, "tip");
4369
4370 if (path && tip)
4371 {
4372 pnode = zalloc(sizeof(data_tip_node));
4373 if (pnode)
4374 {
4375 pnode->type = type;
4376 strlcpy(pnode->path, path);
4377 strlcpy(pnode->tip, tip);
4378
4379 if (data->list)
4380 {
4381 tail->next = pnode;
4382 tail = pnode;
4383 }
4384 else
4385 {
4386 data->list = tail = pnode;
4387 }
4388 }
4389 }
4390 }
4391
4392 return 0;
4393 }
4394 static int ventoy_parse_menu_class(VTOY_JSON *json, void *p)
4395 {
4396 int type;
4397 const char *path = NULL;
4398 const char *class = NULL;
4399 data_class *data = (data_class *)p;
4400 data_class_node *tail = NULL;
4401 data_class_node *pnode = NULL;
4402 VTOY_JSON *node = NULL;
4403
4404 if (json->enDataType != JSON_TYPE_ARRAY)
4405 {
4406 return 0;
4407 }
4408
4409 for (node = json->pstChild; node; node = node->pstNext)
4410 {
4411 if (node->enDataType != JSON_TYPE_OBJECT)
4412 {
4413 continue;
4414 }
4415
4416 type = class_type_key;
4417 path = vtoy_json_get_string_ex(node->pstChild, "key");
4418 if (!path)
4419 {
4420 type = class_type_dir;
4421 path = vtoy_json_get_string_ex(node->pstChild, "dir");
4422 if (!path)
4423 {
4424 type = class_type_parent;
4425 path = vtoy_json_get_string_ex(node->pstChild, "parent");
4426 }
4427 }
4428 class = vtoy_json_get_string_ex(node->pstChild, "class");
4429
4430 if (path && class)
4431 {
4432 pnode = zalloc(sizeof(data_class_node));
4433 if (pnode)
4434 {
4435 pnode->type = type;
4436 strlcpy(pnode->path, path);
4437 strlcpy(pnode->class, class);
4438
4439 if (data->list)
4440 {
4441 tail->next = pnode;
4442 tail = pnode;
4443 }
4444 else
4445 {
4446 data->list = tail = pnode;
4447 }
4448 }
4449 }
4450 }
4451
4452 return 0;
4453 }
4454 static int ventoy_parse_auto_install(VTOY_JSON *json, void *p)
4455 {
4456 int type;
4457 int count;
4458 int timeout;
4459 int timeouten;
4460 int autosel;
4461 int autoselen;
4462 const char *path = NULL;
4463 const char *file = NULL;
4464 data_auto_install *data = (data_auto_install *)p;
4465 auto_install_node *tail = NULL;
4466 auto_install_node *pnode = NULL;
4467 path_node *pathnode = NULL;
4468 path_node *pathtail = NULL;
4469 VTOY_JSON *node = NULL;
4470 VTOY_JSON *filelist = NULL;
4471 VTOY_JSON *filenode = NULL;
4472
4473 if (json->enDataType != JSON_TYPE_ARRAY)
4474 {
4475 return 0;
4476 }
4477
4478 for (node = json->pstChild; node; node = node->pstNext)
4479 {
4480 if (node->enDataType != JSON_TYPE_OBJECT)
4481 {
4482 continue;
4483 }
4484
4485 type = 0;
4486 path = vtoy_json_get_string_ex(node->pstChild, "image");
4487 if (!path)
4488 {
4489 path = vtoy_json_get_string_ex(node->pstChild, "parent");
4490 type = 1;
4491 }
4492 if (!path)
4493 {
4494 continue;
4495 }
4496
4497 file = vtoy_json_get_string_ex(node->pstChild, "template");
4498 if (file)
4499 {
4500 pnode = zalloc(sizeof(auto_install_node));
4501 if (pnode)
4502 {
4503 pnode->type = type;
4504 pnode->autosel = 1;
4505 strlcpy(pnode->path, path);
4506
4507 pathnode = zalloc(sizeof(path_node));
4508 if (pathnode)
4509 {
4510 strlcpy(pathnode->path, file);
4511 pnode->list = pathnode;
4512 }
4513 else
4514 {
4515 free(pnode);
4516 }
4517
4518 if (data->list)
4519 {
4520 tail->next = pnode;
4521 tail = pnode;
4522 }
4523 else
4524 {
4525 data->list = tail = pnode;
4526 }
4527 }
4528
4529 continue;
4530 }
4531
4532
4533 timeouten = autoselen = 0;
4534 if (JSON_SUCCESS == vtoy_json_get_int(node->pstChild, "timeout", &timeout))
4535 {
4536 timeouten = 1;
4537 }
4538 if (JSON_SUCCESS == vtoy_json_get_int(node->pstChild, "autosel", &autosel))
4539 {
4540 autoselen = 1;
4541 }
4542
4543 filelist = vtoy_json_find_item(node->pstChild, JSON_TYPE_ARRAY, "template");
4544 if (!filelist)
4545 {
4546 continue;
4547 }
4548
4549 pnode = zalloc(sizeof(auto_install_node));
4550 if (!pnode)
4551 {
4552 continue;
4553 }
4554
4555 pnode->type = type;
4556 pnode->autoselen = autoselen;
4557 pnode->timeouten = timeouten;
4558 pnode->timeout = timeout;
4559 pnode->autosel = autosel;
4560 strlcpy(pnode->path, path);
4561
4562 count = 0;
4563 for (filenode = filelist->pstChild; filenode; filenode = filenode->pstNext)
4564 {
4565 if (filenode->enDataType != JSON_TYPE_STRING)
4566 {
4567 continue;
4568 }
4569
4570 pathnode = zalloc(sizeof(path_node));
4571 if (pathnode)
4572 {
4573 count++;
4574 strlcpy(pathnode->path, filenode->unData.pcStrVal);
4575
4576 if (pnode->list)
4577 {
4578 pathtail->next = pathnode;
4579 pathtail = pathnode;
4580 }
4581 else
4582 {
4583 pnode->list = pathtail = pathnode;
4584 }
4585 }
4586 }
4587
4588 if (count == 0)
4589 {
4590 free(pnode);
4591 }
4592 else
4593 {
4594 if (pnode->autoselen && pnode->autosel > count)
4595 {
4596 pnode->autosel = 1;
4597 }
4598
4599 if (data->list)
4600 {
4601 tail->next = pnode;
4602 tail = pnode;
4603 }
4604 else
4605 {
4606 data->list = tail = pnode;
4607 }
4608 }
4609 }
4610
4611 return 0;
4612 }
4613 static int ventoy_parse_persistence(VTOY_JSON *json, void *p)
4614 {
4615 int count;
4616 int timeout;
4617 int timeouten;
4618 int autosel;
4619 int autoselen;
4620 const char *path = NULL;
4621 const char *file = NULL;
4622 data_persistence *data = (data_persistence *)p;
4623 persistence_node *tail = NULL;
4624 persistence_node *pnode = NULL;
4625 path_node *pathnode = NULL;
4626 path_node *pathtail = NULL;
4627 VTOY_JSON *node = NULL;
4628 VTOY_JSON *filelist = NULL;
4629 VTOY_JSON *filenode = NULL;
4630
4631 if (json->enDataType != JSON_TYPE_ARRAY)
4632 {
4633 return 0;
4634 }
4635
4636 for (node = json->pstChild; node; node = node->pstNext)
4637 {
4638 if (node->enDataType != JSON_TYPE_OBJECT)
4639 {
4640 continue;
4641 }
4642
4643 path = vtoy_json_get_string_ex(node->pstChild, "image");
4644 if (!path)
4645 {
4646 continue;
4647 }
4648
4649 file = vtoy_json_get_string_ex(node->pstChild, "backend");
4650 if (file)
4651 {
4652 pnode = zalloc(sizeof(persistence_node));
4653 if (pnode)
4654 {
4655 pnode->type = 0;
4656 pnode->autosel = 1;
4657 strlcpy(pnode->path, path);
4658
4659 pathnode = zalloc(sizeof(path_node));
4660 if (pathnode)
4661 {
4662 strlcpy(pathnode->path, file);
4663 pnode->list = pathnode;
4664 }
4665 else
4666 {
4667 free(pnode);
4668 }
4669
4670 if (data->list)
4671 {
4672 tail->next = pnode;
4673 tail = pnode;
4674 }
4675 else
4676 {
4677 data->list = tail = pnode;
4678 }
4679 }
4680
4681 continue;
4682 }
4683
4684
4685 timeouten = autoselen = 0;
4686 if (JSON_SUCCESS == vtoy_json_get_int(node->pstChild, "timeout", &timeout))
4687 {
4688 timeouten = 1;
4689 }
4690 if (JSON_SUCCESS == vtoy_json_get_int(node->pstChild, "autosel", &autosel))
4691 {
4692 autoselen = 1;
4693 }
4694
4695 filelist = vtoy_json_find_item(node->pstChild, JSON_TYPE_ARRAY, "backend");
4696 if (!filelist)
4697 {
4698 continue;
4699 }
4700
4701 pnode = zalloc(sizeof(persistence_node));
4702 if (!pnode)
4703 {
4704 continue;
4705 }
4706
4707 pnode->type = 0;
4708 pnode->autoselen = autoselen;
4709 pnode->timeouten = timeouten;
4710 pnode->timeout = timeout;
4711 pnode->autosel = autosel;
4712 strlcpy(pnode->path, path);
4713
4714 count = 0;
4715 for (filenode = filelist->pstChild; filenode; filenode = filenode->pstNext)
4716 {
4717 if (filenode->enDataType != JSON_TYPE_STRING)
4718 {
4719 continue;
4720 }
4721
4722 pathnode = zalloc(sizeof(path_node));
4723 if (pathnode)
4724 {
4725 count++;
4726 strlcpy(pathnode->path, filenode->unData.pcStrVal);
4727
4728 if (pnode->list)
4729 {
4730 pathtail->next = pathnode;
4731 pathtail = pathnode;
4732 }
4733 else
4734 {
4735 pnode->list = pathtail = pathnode;
4736 }
4737 }
4738 }
4739
4740 if (count == 0)
4741 {
4742 free(pnode);
4743 }
4744 else
4745 {
4746 if (pnode->autoselen && pnode->autosel > count)
4747 {
4748 pnode->autosel = 1;
4749 }
4750
4751 if (data->list)
4752 {
4753 tail->next = pnode;
4754 tail = pnode;
4755 }
4756 else
4757 {
4758 data->list = tail = pnode;
4759 }
4760 }
4761 }
4762
4763 return 0;
4764 }
4765 static int ventoy_parse_injection(VTOY_JSON *json, void *p)
4766 {
4767 int type;
4768 const char *path = NULL;
4769 const char *archive = NULL;
4770 data_injection *data = (data_injection *)p;
4771 injection_node *tail = NULL;
4772 injection_node *pnode = NULL;
4773 VTOY_JSON *node = NULL;
4774
4775 if (json->enDataType != JSON_TYPE_ARRAY)
4776 {
4777 return 0;
4778 }
4779
4780 for (node = json->pstChild; node; node = node->pstNext)
4781 {
4782 if (node->enDataType != JSON_TYPE_OBJECT)
4783 {
4784 continue;
4785 }
4786
4787 type = 0;
4788 path = vtoy_json_get_string_ex(node->pstChild, "image");
4789 if (!path)
4790 {
4791 path = vtoy_json_get_string_ex(node->pstChild, "parent");
4792 type = 1;
4793 }
4794 archive = vtoy_json_get_string_ex(node->pstChild, "archive");
4795
4796 if (path && archive)
4797 {
4798 pnode = zalloc(sizeof(injection_node));
4799 if (pnode)
4800 {
4801 pnode->type = type;
4802 strlcpy(pnode->path, path);
4803 strlcpy(pnode->archive, archive);
4804
4805 if (data->list)
4806 {
4807 tail->next = pnode;
4808 tail = pnode;
4809 }
4810 else
4811 {
4812 data->list = tail = pnode;
4813 }
4814 }
4815 }
4816 }
4817
4818 return 0;
4819 }
4820 static int ventoy_parse_conf_replace(VTOY_JSON *json, void *p)
4821 {
4822 int img = 0;
4823 const char *path = NULL;
4824 const char *org = NULL;
4825 const char *new = NULL;
4826 data_conf_replace *data = (data_conf_replace *)p;
4827 conf_replace_node *tail = NULL;
4828 conf_replace_node *pnode = NULL;
4829 VTOY_JSON *node = NULL;
4830
4831 if (json->enDataType != JSON_TYPE_ARRAY)
4832 {
4833 return 0;
4834 }
4835
4836 for (node = json->pstChild; node; node = node->pstNext)
4837 {
4838 if (node->enDataType != JSON_TYPE_OBJECT)
4839 {
4840 continue;
4841 }
4842
4843 path = vtoy_json_get_string_ex(node->pstChild, "iso");
4844 org = vtoy_json_get_string_ex(node->pstChild, "org");
4845 new = vtoy_json_get_string_ex(node->pstChild, "new");
4846
4847 img = 0;
4848 vtoy_json_get_int(node->pstChild, "img", &img);
4849
4850 if (path && org && new)
4851 {
4852 pnode = zalloc(sizeof(conf_replace_node));
4853 if (pnode)
4854 {
4855 strlcpy(pnode->path, path);
4856 strlcpy(pnode->org, org);
4857 strlcpy(pnode->new, new);
4858 if (img == 1)
4859 {
4860 pnode->image = img;
4861 }
4862
4863 if (data->list)
4864 {
4865 tail->next = pnode;
4866 tail = pnode;
4867 }
4868 else
4869 {
4870 data->list = tail = pnode;
4871 }
4872 }
4873 }
4874 }
4875
4876 return 0;
4877 }
4878 static int ventoy_parse_password(VTOY_JSON *json, void *p)
4879 {
4880 int type;
4881 const char *bootpwd = NULL;
4882 const char *isopwd= NULL;
4883 const char *wimpwd= NULL;
4884 const char *imgpwd= NULL;
4885 const char *efipwd= NULL;
4886 const char *vhdpwd= NULL;
4887 const char *vtoypwd= NULL;
4888 const char *path = NULL;
4889 const char *pwd = NULL;
4890 data_password *data = (data_password *)p;
4891 menu_password *tail = NULL;
4892 menu_password *pnode = NULL;
4893 VTOY_JSON *node = NULL;
4894 VTOY_JSON *menupwd = NULL;
4895
4896 if (json->enDataType != JSON_TYPE_OBJECT)
4897 {
4898 return 0;
4899 }
4900
4901 bootpwd = vtoy_json_get_string_ex(json->pstChild, "bootpwd");
4902 isopwd = vtoy_json_get_string_ex(json->pstChild, "isopwd");
4903 wimpwd = vtoy_json_get_string_ex(json->pstChild, "wimpwd");
4904 imgpwd = vtoy_json_get_string_ex(json->pstChild, "imgpwd");
4905 efipwd = vtoy_json_get_string_ex(json->pstChild, "efipwd");
4906 vhdpwd = vtoy_json_get_string_ex(json->pstChild, "vhdpwd");
4907 vtoypwd = vtoy_json_get_string_ex(json->pstChild, "vtoypwd");
4908
4909
4910 if (bootpwd) strlcpy(data->bootpwd, bootpwd);
4911 if (isopwd) strlcpy(data->isopwd, isopwd);
4912 if (wimpwd) strlcpy(data->wimpwd, wimpwd);
4913 if (imgpwd) strlcpy(data->imgpwd, imgpwd);
4914 if (efipwd) strlcpy(data->efipwd, efipwd);
4915 if (vhdpwd) strlcpy(data->vhdpwd, vhdpwd);
4916 if (vtoypwd) strlcpy(data->vtoypwd, vtoypwd);
4917
4918
4919 menupwd = vtoy_json_find_item(json->pstChild, JSON_TYPE_ARRAY, "menupwd");
4920 if (!menupwd)
4921 {
4922 return 0;
4923 }
4924
4925 for (node = menupwd->pstChild; node; node = node->pstNext)
4926 {
4927 if (node->enDataType != JSON_TYPE_OBJECT)
4928 {
4929 continue;
4930 }
4931
4932 type = 0;
4933 path = vtoy_json_get_string_ex(node->pstChild, "file");
4934 if (!path)
4935 {
4936 path = vtoy_json_get_string_ex(node->pstChild, "parent");
4937 type = 1;
4938 }
4939 pwd = vtoy_json_get_string_ex(node->pstChild, "pwd");
4940
4941 if (path && pwd)
4942 {
4943 pnode = zalloc(sizeof(menu_password));
4944 if (pnode)
4945 {
4946 pnode->type = type;
4947 strlcpy(pnode->path, path);
4948 strlcpy(pnode->pwd, pwd);
4949
4950 if (data->list)
4951 {
4952 tail->next = pnode;
4953 tail = pnode;
4954 }
4955 else
4956 {
4957 data->list = tail = pnode;
4958 }
4959 }
4960 }
4961 }
4962
4963 return 0;
4964 }
4965
4966 static int ventoy_parse_image_list_real(VTOY_JSON *json, int type, void *p)
4967 {
4968 VTOY_JSON *node = NULL;
4969 data_image_list *data = (data_image_list *)p;
4970 path_node *tail = NULL;
4971 path_node *pnode = NULL;
4972
4973 if (json->enDataType != JSON_TYPE_ARRAY)
4974 {
4975 return 0;
4976 }
4977
4978 data->type = type;
4979
4980 for (node = json->pstChild; node; node = node->pstNext)
4981 {
4982 if (node->enDataType == JSON_TYPE_STRING)
4983 {
4984 pnode = zalloc(sizeof(path_node));
4985 if (pnode)
4986 {
4987 strlcpy(pnode->path, node->unData.pcStrVal);
4988 if (data->list)
4989 {
4990 tail->next = pnode;
4991 tail = pnode;
4992 }
4993 else
4994 {
4995 data->list = tail = pnode;
4996 }
4997 }
4998 }
4999 }
5000
5001 return 0;
5002 }
5003 static int ventoy_parse_image_blacklist(VTOY_JSON *json, void *p)
5004 {
5005 return ventoy_parse_image_list_real(json, 1, p);
5006 }
5007 static int ventoy_parse_image_list(VTOY_JSON *json, void *p)
5008 {
5009 return ventoy_parse_image_list_real(json, 0, p);
5010 }
5011
5012 static int ventoy_parse_auto_memdisk(VTOY_JSON *json, void *p)
5013 {
5014 VTOY_JSON *node = NULL;
5015 data_auto_memdisk *data = (data_auto_memdisk *)p;
5016 path_node *tail = NULL;
5017 path_node *pnode = NULL;
5018
5019 if (json->enDataType != JSON_TYPE_ARRAY)
5020 {
5021 return 0;
5022 }
5023
5024 for (node = json->pstChild; node; node = node->pstNext)
5025 {
5026 if (node->enDataType == JSON_TYPE_STRING)
5027 {
5028 pnode = zalloc(sizeof(path_node));
5029 if (pnode)
5030 {
5031 strlcpy(pnode->path, node->unData.pcStrVal);
5032 if (data->list)
5033 {
5034 tail->next = pnode;
5035 tail = pnode;
5036 }
5037 else
5038 {
5039 data->list = tail = pnode;
5040 }
5041 }
5042 }
5043 }
5044
5045 return 0;
5046 }
5047 static int ventoy_parse_dud(VTOY_JSON *json, void *p)
5048 {
5049 int count = 0;
5050 const char *path = NULL;
5051 const char *file = NULL;
5052 data_dud *data = (data_dud *)p;
5053 dud_node *tail = NULL;
5054 dud_node *pnode = NULL;
5055 path_node *pathnode = NULL;
5056 path_node *pathtail = NULL;
5057 VTOY_JSON *node = NULL;
5058 VTOY_JSON *filelist = NULL;
5059 VTOY_JSON *filenode = NULL;
5060
5061 if (json->enDataType != JSON_TYPE_ARRAY)
5062 {
5063 return 0;
5064 }
5065
5066 for (node = json->pstChild; node; node = node->pstNext)
5067 {
5068 if (node->enDataType != JSON_TYPE_OBJECT)
5069 {
5070 continue;
5071 }
5072
5073 path = vtoy_json_get_string_ex(node->pstChild, "image");
5074 if (!path)
5075 {
5076 continue;
5077 }
5078
5079 file = vtoy_json_get_string_ex(node->pstChild, "dud");
5080 if (file)
5081 {
5082 pnode = zalloc(sizeof(dud_node));
5083 if (pnode)
5084 {
5085 strlcpy(pnode->path, path);
5086
5087 pathnode = zalloc(sizeof(path_node));
5088 if (pathnode)
5089 {
5090 strlcpy(pathnode->path, file);
5091 pnode->list = pathnode;
5092 }
5093 else
5094 {
5095 free(pnode);
5096 }
5097
5098 if (data->list)
5099 {
5100 tail->next = pnode;
5101 tail = pnode;
5102 }
5103 else
5104 {
5105 data->list = tail = pnode;
5106 }
5107 }
5108
5109 continue;
5110 }
5111
5112 filelist = vtoy_json_find_item(node->pstChild, JSON_TYPE_ARRAY, "dud");
5113 if (!filelist)
5114 {
5115 continue;
5116 }
5117
5118 pnode = zalloc(sizeof(dud_node));
5119 if (!pnode)
5120 {
5121 continue;
5122 }
5123
5124 strlcpy(pnode->path, path);
5125
5126 for (filenode = filelist->pstChild; filenode; filenode = filenode->pstNext)
5127 {
5128 if (filenode->enDataType != JSON_TYPE_STRING)
5129 {
5130 continue;
5131 }
5132
5133 pathnode = zalloc(sizeof(path_node));
5134 if (pathnode)
5135 {
5136 strlcpy(pathnode->path, filenode->unData.pcStrVal);
5137 count++;
5138
5139 if (pnode->list)
5140 {
5141 pathtail->next = pathnode;
5142 pathtail = pathnode;
5143 }
5144 else
5145 {
5146 pnode->list = pathtail = pathnode;
5147 }
5148 }
5149 }
5150
5151 if (count == 0)
5152 {
5153 free(pnode);
5154 }
5155 else
5156 {
5157 if (data->list)
5158 {
5159 tail->next = pnode;
5160 tail = pnode;
5161 }
5162 else
5163 {
5164 data->list = tail = pnode;
5165 }
5166 }
5167 }
5168
5169 return 0;
5170 }
5171
5172
5173
5174 #if 0
5175 #endif
5176
5177
5178 static int ventoy_load_old_json(const char *filename)
5179 {
5180 int ret = 0;
5181 int offset = 0;
5182 int buflen = 0;
5183 char *buffer = NULL;
5184 unsigned char *start = NULL;
5185 VTOY_JSON *json = NULL;
5186 VTOY_JSON *node = NULL;
5187 VTOY_JSON *next = NULL;
5188
5189 ret = ventoy_read_file_to_buf(filename, 4, (void **)&buffer, &buflen);
5190 if (ret)
5191 {
5192 vlog("Failed to read old ventoy.json file.\n");
5193 return 1;
5194 }
5195 buffer[buflen] = 0;
5196
5197 start = (unsigned char *)buffer;
5198
5199 if (start[0] == 0xef && start[1] == 0xbb && start[2] == 0xbf)
5200 {
5201 offset = 3;
5202 }
5203 else if ((start[0] == 0xff && start[1] == 0xfe) || (start[0] == 0xfe && start[1] == 0xff))
5204 {
5205 vlog("ventoy.json is in UCS-2 encoding, ignore it.\n");
5206 free(buffer);
5207 return 1;
5208 }
5209
5210 json = vtoy_json_create();
5211 if (!json)
5212 {
5213 free(buffer);
5214 return 1;
5215 }
5216
5217 if (vtoy_json_parse_ex(json, buffer + offset, buflen - offset) == JSON_SUCCESS)
5218 {
5219 vlog("parse ventoy.json success\n");
5220
5221 for (node = json->pstChild; node; node = node->pstNext)
5222 for (next = node->pstNext; next; next = next->pstNext)
5223 {
5224 if (node->pcName && next->pcName && strcmp(node->pcName, next->pcName) == 0)
5225 {
5226 vlog("ventoy.json contains duplicate key <%s>.\n", node->pcName);
5227 g_sysinfo.invalid_config = 1;
5228 ret = 1;
5229 goto end;
5230 }
5231 }
5232
5233 for (node = json->pstChild; node; node = node->pstNext)
5234 {
5235 ventoy_parse_json(control);
5236 ventoy_parse_json(theme);
5237 ventoy_parse_json(menu_alias);
5238 ventoy_parse_json(menu_tip);
5239 ventoy_parse_json(menu_class);
5240 ventoy_parse_json(auto_install);
5241 ventoy_parse_json(persistence);
5242 ventoy_parse_json(injection);
5243 ventoy_parse_json(conf_replace);
5244 ventoy_parse_json(password);
5245 ventoy_parse_json(image_list);
5246 ventoy_parse_json(image_blacklist);
5247 ventoy_parse_json(auto_memdisk);
5248 ventoy_parse_json(dud);
5249 }
5250 }
5251 else
5252 {
5253 vlog("ventoy.json has syntax error.\n");
5254 g_sysinfo.syntax_error = 1;
5255 ret = 1;
5256 }
5257
5258 end:
5259 vtoy_json_destroy(json);
5260
5261 free(buffer);
5262 return ret;
5263 }
5264
5265
5266 int ventoy_http_start(const char *ip, const char *port)
5267 {
5268 int i = 0;
5269 int ret = 0;
5270 char addr[128];
5271 char filename[128];
5272 char backupname[128];
5273 struct mg_callbacks callbacks;
5274 const char *options[] =
5275 {
5276 "listening_ports", "24681",
5277 "document_root", "www",
5278 "index_files", "index.html",
5279 "num_threads", "16",
5280 "error_log_file", LOG_FILE,
5281 "request_timeout_ms", "10000",
5282 NULL
5283 };
5284
5285 for (i = 0; i <= bios_max; i++)
5286 {
5287 ventoy_data_default_control(g_data_control + i);
5288 ventoy_data_default_theme(g_data_theme + i);
5289 ventoy_data_default_menu_alias(g_data_menu_alias + i);
5290 ventoy_data_default_menu_class(g_data_menu_class + i);
5291 ventoy_data_default_menu_tip(g_data_menu_tip + i);
5292 ventoy_data_default_auto_install(g_data_auto_install + i);
5293 ventoy_data_default_persistence(g_data_persistence + i);
5294 ventoy_data_default_injection(g_data_injection + i);
5295 ventoy_data_default_conf_replace(g_data_conf_replace + i);
5296 ventoy_data_default_password(g_data_password + i);
5297 ventoy_data_default_image_list(g_data_image_list + i);
5298 ventoy_data_default_auto_memdisk(g_data_auto_memdisk + i);
5299 ventoy_data_default_dud(g_data_dud + i);
5300 }
5301
5302 ventoy_get_json_path(filename, backupname);
5303 if (ventoy_is_file_exist("%s", filename))
5304 {
5305 ventoy_copy_file(filename, backupname);
5306 ret = ventoy_load_old_json(filename);
5307 if (ret == 0)
5308 {
5309 ventoy_data_real_save_all(0);
5310 }
5311 }
5312
5313 /* option */
5314 scnprintf(addr, sizeof(addr), "%s:%s", ip, port);
5315 options[1] = addr;
5316
5317 memset(&callbacks, 0, sizeof(callbacks));
5318 callbacks.begin_request = ventoy_request_handler;
5319 #ifndef VENTOY_SIM
5320 callbacks.open_file = ventoy_web_openfile;
5321 #endif
5322 g_ventoy_http_ctx = mg_start(&callbacks, NULL, options);
5323
5324 ventoy_start_writeback_thread(ventoy_http_writeback);
5325
5326 return g_ventoy_http_ctx ? 0 : 1;
5327 }
5328
5329 int ventoy_http_stop(void)
5330 {
5331 if (g_ventoy_http_ctx)
5332 {
5333 mg_stop(g_ventoy_http_ctx);
5334 }
5335
5336 ventoy_stop_writeback_thread();
5337 return 0;
5338 }
5339
5340 int ventoy_http_init(void)
5341 {
5342 int i = 0;
5343
5344 #ifdef VENTOY_SIM
5345 char *Buffer = NULL;
5346 int BufLen = 0;
5347
5348 ventoy_read_file_to_buf("www/menulist", 4, (void **)&Buffer, &BufLen);
5349 if (Buffer)
5350 {
5351 for (i = 0; i < BufLen / 5; i++)
5352 {
5353 memcpy(g_ventoy_menu_lang[i], Buffer + i * 5, 5);
5354 g_ventoy_menu_lang[i][5] = 0;
5355 }
5356 free(Buffer);
5357 }
5358 #else
5359 ventoy_file *file;
5360
5361 file = ventoy_tar_find_file("www/menulist");
5362 if (file)
5363 {
5364 for (i = 0; i < file->size / 5; i++)
5365 {
5366 memcpy(g_ventoy_menu_lang[i], (char *)(file->addr) + i * 5, 5);
5367 g_ventoy_menu_lang[i][5] = 0;
5368 }
5369 }
5370 #endif
5371
5372 if (!g_pub_json_buffer)
5373 {
5374 g_pub_json_buffer = malloc(JSON_BUF_MAX * 2);
5375 g_pub_save_buffer = g_pub_json_buffer + JSON_BUF_MAX;
5376 }
5377
5378
5379 pthread_mutex_init(&g_api_mutex, NULL);
5380 return 0;
5381 }
5382
5383 void ventoy_http_exit(void)
5384 {
5385 check_free(g_pub_json_buffer);
5386 g_pub_json_buffer = NULL;
5387 g_pub_save_buffer = NULL;
5388
5389 pthread_mutex_destroy(&g_api_mutex);
5390 }
5391
5392