cj-tauri 2.0.0 → 2.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +113 -99
- package/bin/cj-tauri.js +287 -287
- package/cjpm.toml +63 -52
- package/cli/cjpm.toml +22 -22
- package/cli/src/doctor.cj +308 -306
- package/cli/src/main.cj +129 -129
- package/cli/src/manifest.cj +632 -558
- package/cli/src/manifest_test.cj +87 -0
- package/cli/src/project.cj +770 -770
- package/cli/src/resolve.cj +348 -348
- package/cli/src/scaffold.cj +369 -369
- package/cli/src/sync.cj +526 -526
- package/cli/src/util.cj +168 -168
- package/cli/templates/app/README.md +51 -48
- package/cli/templates/app/assets/capabilities/default.json +7 -7
- package/cli/templates/app/assets/ui/index.html +120 -118
- package/cli/templates/app/cj-tauri.toml +32 -22
- package/cli/templates/app/cjpm.toml +34 -34
- package/cli/templates/app/src/main.cj +101 -90
- package/cli/templates/app-react/README.md +56 -56
- package/cli/templates/app-react/assets/capabilities/default.json +7 -7
- package/cli/templates/app-react/assets/ui/index.html +25 -25
- package/cli/templates/app-react/assets/ui/package.json +19 -19
- package/cli/templates/app-react/assets/ui/src/App.css +67 -67
- package/cli/templates/app-react/assets/ui/src/App.jsx +124 -124
- package/cli/templates/app-react/assets/ui/src/main.jsx +6 -6
- package/cli/templates/app-react/assets/ui/vite.config.js +24 -24
- package/cli/templates/app-react/cj-tauri.toml +33 -23
- package/cli/templates/app-react/cjpm.toml +34 -34
- package/cli/templates/app-react/src/main.cj +91 -91
- package/cli/templates/app-vue/README.md +56 -56
- package/cli/templates/app-vue/assets/capabilities/default.json +7 -7
- package/cli/templates/app-vue/assets/ui/index.html +25 -25
- package/cli/templates/app-vue/assets/ui/package.json +18 -18
- package/cli/templates/app-vue/assets/ui/src/App.vue +176 -176
- package/cli/templates/app-vue/assets/ui/src/main.js +4 -4
- package/cli/templates/app-vue/assets/ui/vite.config.js +24 -24
- package/cli/templates/app-vue/cj-tauri.toml +33 -23
- package/cli/templates/app-vue/cjpm.toml +34 -34
- package/cli/templates/app-vue/src/main.cj +91 -91
- package/cli/templates/ohos-skeleton/AppScope/app.json5 +13 -13
- package/cli/templates/ohos-skeleton/AppScope/resources/base/element/string.json +8 -8
- package/cli/templates/ohos-skeleton/AppScope/resources/base/media/layered_image.json +6 -6
- package/cli/templates/ohos-skeleton/README.md +84 -79
- package/cli/templates/ohos-skeleton/build-hap.sh +15 -0
- package/cli/templates/ohos-skeleton/build-profile.json5 +46 -46
- package/cli/templates/ohos-skeleton/entry/build-profile.json5 +26 -26
- package/cli/templates/ohos-skeleton/entry/cjpm.toml +51 -43
- package/cli/templates/ohos-skeleton/entry/hvigorfile.ts +6 -6
- package/cli/templates/ohos-skeleton/entry/oh-package.json5 +9 -9
- package/cli/templates/ohos-skeleton/entry/src/main/cangjie/ability_stage.cj +17 -17
- package/cli/templates/ohos-skeleton/entry/src/main/cangjie/app_host.cj +94 -94
- package/cli/templates/ohos-skeleton/entry/src/main/cangjie/dialog_host.cj +217 -0
- package/cli/templates/ohos-skeleton/entry/src/main/cangjie/index.cj +527 -167
- package/cli/templates/ohos-skeleton/entry/src/main/cangjie/main_ability.cj +139 -139
- package/cli/templates/ohos-skeleton/entry/src/main/module.json5 +57 -49
- package/cli/templates/ohos-skeleton/entry/src/main/resources/base/element/color.json +8 -8
- package/cli/templates/ohos-skeleton/entry/src/main/resources/base/element/string.json +16 -16
- package/cli/templates/ohos-skeleton/entry/src/main/resources/base/media/layered_image.json +6 -6
- package/cli/templates/ohos-skeleton/entry/src/main/resources/base/profile/main_pages.json +2 -2
- package/cli/templates/ohos-skeleton/entry/src/main/resources/rawfile/capabilities.json +6 -6
- package/cli/templates/ohos-skeleton/entry/src/main/resources/rawfile/index.html +92 -92
- package/cli/templates/ohos-skeleton/hvigor/hvigor-config.json5 +5 -5
- package/cli/templates/ohos-skeleton/hvigorfile.ts +6 -6
- package/cli/templates/ohos-skeleton/oh-package.json5 +10 -10
- package/native/build_win.bat +62 -62
- package/native/core/bridge_core.c +1681 -1626
- package/native/core/bridge_core.h +675 -618
- package/native/core/bridge_js.h +108 -108
- package/native/platforms/harmonyos/README.md +115 -6
- package/native/platforms/linux/bridge_linux.c +2787 -2485
- package/native/platforms/windows/bridge_win.c +3740 -3248
- package/native/tests/gtk_threading_probe.c +143 -143
- package/native/tests/test_bridge_core.c +1339 -1228
- package/package.json +53 -53
- package/prebuilt/linux-x64/cj-tauri +0 -0
- package/src/api_system.cj +67 -67
- package/src/app.cj +325 -969
- package/src/app_events.cj +166 -0
- package/src/app_host_ops.cj +287 -0
- package/src/app_run.cj +283 -0
- package/src/app_spec.cj +76 -76
- package/src/arkweb_menu.cj +216 -0
- package/src/arkweb_script.cj +142 -142
- package/src/capability.cj +409 -409
- package/src/clipboard_bridge.cj +178 -0
- package/src/dialog_spec.cj +79 -0
- package/src/dragdrop.cj +26 -26
- package/src/embedded_assets.cj +98 -98
- package/src/host.cj +752 -607
- package/src/host_arkweb.cj +924 -778
- package/src/host_webkit.cj +663 -570
- package/src/host_webview2.cj +663 -570
- package/src/hotkey.cj +66 -66
- package/src/ipc_hub.cj +337 -337
- package/src/ipc_message.cj +286 -286
- package/src/launch.cj +62 -62
- package/src/logging.cj +127 -127
- package/src/menu.cj +197 -197
- package/src/platform/platform_app_context.cj +77 -77
- package/src/platform/platform_assets.cj +33 -33
- package/src/platform/platform_discover.cj +176 -176
- package/src/platform/platform_env.cj +29 -29
- package/src/platform/platform_feature.cj +31 -31
- package/src/platform/platform_page_source.cj +87 -87
- package/src/platform/platform_target_info.cj +32 -32
- package/src/platform_host_provider.cj +87 -87
- package/src/plugin.cj +333 -333
- package/src/plugins/clipboard/plugin_clipboard.cj +152 -152
- package/src/plugins/dialog/plugin_dialog.cj +209 -209
- package/src/plugins/fs/plugin_fs.cj +105 -1
- package/src/plugins/http/http_backend.cj +131 -0
- package/src/plugins/http/http_desktop.cj +195 -0
- package/src/plugins/http/http_ohos.cj +204 -0
- package/src/plugins/http/plugin_http.cj +310 -459
- package/src/plugins/log/plugin_log.cj +105 -105
- package/src/plugins/menu/plugin_menu.cj +158 -158
- package/src/plugins/notification/plugin_notification.cj +154 -154
- package/src/plugins/serial/plugin_serial.cj +458 -454
- package/src/plugins/serial/serial_bridge.cj +194 -194
- package/src/plugins/serial/serial_manager_ohos.cj +92 -0
- package/src/plugins/serial/serial_ohos.cj +529 -0
- package/src/plugins/shell/plugin_shell.cj +258 -258
- package/src/plugins/sqlite/plugin_sqlite.cj +705 -710
- package/src/plugins/sqlite/sqlite_ffi.cj +206 -211
- package/src/plugins/ws/plugin_ws.cj +488 -470
- package/src/process_hidden.cj +174 -174
- package/src/scope.cj +391 -391
- package/src/shell_event.cj +69 -69
- package/src/tests/app_spec_test.cj +126 -127
- package/src/tests/capability_test.cj +243 -243
- package/src/tests/dialog_spec_test.cj +73 -0
- package/src/tests/fake_host.cj +201 -201
- package/src/tests/ipc_hub_test.cj +487 -487
- package/src/tests/logging_test.cj +62 -62
- package/src/tests/platform_contract_test.cj +251 -251
- package/src/tests/plugin_clipboard_test.cj +222 -222
- package/src/tests/plugin_dialog_test.cj +237 -237
- package/src/tests/plugin_fs_test.cj +207 -0
- package/src/tests/plugin_http_test.cj +124 -124
- package/src/tests/plugin_notification_test.cj +205 -205
- package/src/tests/plugin_serial_test.cj +48 -0
- package/src/tests/plugin_test.cj +605 -585
- package/src/tests/plugin_ws_test.cj +40 -40
- package/src/tests/process_hidden_test.cj +129 -129
- package/src/tests/scope_test.cj +350 -350
- package/src/tests/system_host_test.cj +99 -81
- package/src/tests/urlutil_test.cj +53 -53
- package/src/tests/version_test.cj +75 -75
- package/src/tests/window_registry_test.cj +123 -123
- package/src/tray.cj +90 -90
- package/src/urlutil.cj +159 -159
- package/src/version.cj +44 -44
- package/src/window.cj +51 -51
- package/src/window_registry.cj +116 -116
- package/prebuilt/win32-x64/cj-tauri.exe +0 -0
- package/src/plugins/serial/serial_ohos_stub.cj +0 -61
- package/src/plugins/sqlite/sqlite_ohos_stub.cj +0 -91
|
@@ -1,143 +1,143 @@
|
|
|
1
|
-
/*
|
|
2
|
-
* 多窗口可行性最小对照(纯 GTK / GTK+WebKit;无仓颉、无 cj-tauri 代码)
|
|
3
|
-
*
|
|
4
|
-
* 用途:把 docs/架构演进-多平台与多窗口.md §8 的结论做成可复跑的复现器。
|
|
5
|
-
*
|
|
6
|
-
* 用法: gtk_threading_probe <N> [--webkit] [--stagger-ms N]
|
|
7
|
-
* N=1 → exit=0(基线)
|
|
8
|
-
* N=2(纯 GTK) → exit=0:GTK 本身不反对两条各自的 gtk_main
|
|
9
|
-
* N=2 --webkit → **不可用**:实测 8/8 致命失败(多数 exit=139 SIGSEGV +
|
|
10
|
-
* Gtk-CRITICAL;早先 /tmp 变体是 exit=134 abort;也可能表现为
|
|
11
|
-
* 线程卡在 gtk_init 里 → main 超时给 exit=3)
|
|
12
|
-
*
|
|
13
|
-
* 退出码:0 = N 个窗口都起来且无迟到崩溃;3 = 超时(有窗口没起来);134/139 = 被信号打死。
|
|
14
|
-
*
|
|
15
|
-
* 线程一律**串行起**(默认纯 GTK 300ms、带 WebKit 1500ms):串行也逃不掉(8/8),
|
|
16
|
-
* 所以既不是单纯的「初始化撞车」,也不是靠时序能回避的竞态——一个进程里两个
|
|
17
|
-
* WebKitWebView 分处两条线程就是不被支持的用法。
|
|
18
|
-
*
|
|
19
|
-
* 编译 / 跑法见 scripts/test-gtk-threading.sh(本文件不会被 cjpm 编译,纯 C 小程序)。
|
|
20
|
-
*/
|
|
21
|
-
#include <gtk/gtk.h>
|
|
22
|
-
|
|
23
|
-
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
24
|
-
#include <webkit2/webkit2.h>
|
|
25
|
-
#endif
|
|
26
|
-
|
|
27
|
-
#include <pthread.h>
|
|
28
|
-
#include <stdint.h>
|
|
29
|
-
#include <stdio.h>
|
|
30
|
-
#include <stdlib.h>
|
|
31
|
-
#include <string.h>
|
|
32
|
-
#include <unistd.h>
|
|
33
|
-
|
|
34
|
-
typedef struct worker_arg {
|
|
35
|
-
int idx;
|
|
36
|
-
int use_webkit;
|
|
37
|
-
} worker_arg;
|
|
38
|
-
|
|
39
|
-
/* 已经「窗口建好、进了 gtk_main」的线程数。主线程靠它判成败——不能只 sleep 完就 return:
|
|
40
|
-
线程卡在 gtk_init 里没出来时,主线程照样返回 0,那会把「卡死」误报成干净退出(本探针首版
|
|
41
|
-
就踩过这个坑:日志里没有 window up 行,退出码却是 0)。 */
|
|
42
|
-
static volatile int g_windows_up = 0;
|
|
43
|
-
|
|
44
|
-
static gboolean tick(gpointer d) {
|
|
45
|
-
fprintf(stderr, "[gtkprobe] window %ld alive\n", (long)(intptr_t)d);
|
|
46
|
-
return G_SOURCE_CONTINUE;
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
50
|
-
static void on_load(WebKitWebView *view, WebKitLoadEvent ev, gpointer d) {
|
|
51
|
-
(void)view;
|
|
52
|
-
fprintf(stderr, "[gtkprobe] window %ld load event=%d\n", (long)(intptr_t)d, (int)ev);
|
|
53
|
-
}
|
|
54
|
-
#endif
|
|
55
|
-
|
|
56
|
-
static void *worker(void *arg) {
|
|
57
|
-
worker_arg *wa = (worker_arg *)arg;
|
|
58
|
-
GtkWidget *w;
|
|
59
|
-
GtkWidget *view = NULL;
|
|
60
|
-
char tmp[160];
|
|
61
|
-
|
|
62
|
-
fprintf(stderr, "[gtkprobe] thread %d: gtk_init\n", wa->idx);
|
|
63
|
-
gtk_init(NULL, NULL); /* 每条线程各初始化一次 GDK,与本项目的桥同构 */
|
|
64
|
-
|
|
65
|
-
w = gtk_window_new(GTK_WINDOW_TOPLEVEL);
|
|
66
|
-
snprintf(tmp, sizeof(tmp), "gtkprobe %d", wa->idx);
|
|
67
|
-
gtk_window_set_title(GTK_WINDOW(w), tmp);
|
|
68
|
-
gtk_window_set_default_size(GTK_WINDOW(w), 400, 300);
|
|
69
|
-
|
|
70
|
-
if (wa->use_webkit) {
|
|
71
|
-
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
72
|
-
view = webkit_web_view_new(); /* 默认 WebKitWebContext */
|
|
73
|
-
gtk_container_add(GTK_CONTAINER(w), view);
|
|
74
|
-
g_signal_connect(view, "load-changed", G_CALLBACK(on_load), (gpointer)(intptr_t)wa->idx);
|
|
75
|
-
#else
|
|
76
|
-
fprintf(stderr, "[gtkprobe] 本二进制未编入 WebKit(--webkit 无效)\n");
|
|
77
|
-
return NULL;
|
|
78
|
-
#endif
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
g_signal_connect(w, "destroy", G_CALLBACK(gtk_main_quit), NULL);
|
|
82
|
-
gtk_widget_show_all(w);
|
|
83
|
-
|
|
84
|
-
if (wa->use_webkit && view) {
|
|
85
|
-
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
86
|
-
snprintf(tmp, sizeof(tmp), "data:text/html,<h1>win %d</h1>", wa->idx);
|
|
87
|
-
webkit_web_view_load_uri(WEBKIT_WEB_VIEW(view), tmp);
|
|
88
|
-
#endif
|
|
89
|
-
}
|
|
90
|
-
fprintf(stderr, "[gtkprobe] thread %d: window up, entering gtk_main\n", wa->idx);
|
|
91
|
-
__sync_fetch_and_add(&g_windows_up, 1);
|
|
92
|
-
g_timeout_add(500, tick, (gpointer)(intptr_t)wa->idx);
|
|
93
|
-
gtk_main();
|
|
94
|
-
fprintf(stderr, "[gtkprobe] thread %d: gtk_main returned\n", wa->idx);
|
|
95
|
-
return NULL;
|
|
96
|
-
}
|
|
97
|
-
|
|
98
|
-
int main(int argc, char **argv) {
|
|
99
|
-
int n = 1;
|
|
100
|
-
int use_webkit = 0;
|
|
101
|
-
int stagger_ms = 300;
|
|
102
|
-
int i;
|
|
103
|
-
pthread_t t[8];
|
|
104
|
-
worker_arg args[8];
|
|
105
|
-
|
|
106
|
-
for (i = 1; i < argc; i++) {
|
|
107
|
-
if (strcmp(argv[i], "--webkit") == 0) {
|
|
108
|
-
use_webkit = 1;
|
|
109
|
-
} else if (strcmp(argv[i], "--stagger-ms") == 0 && i + 1 < argc) {
|
|
110
|
-
stagger_ms = atoi(argv[++i]);
|
|
111
|
-
} else {
|
|
112
|
-
n = atoi(argv[i]);
|
|
113
|
-
}
|
|
114
|
-
}
|
|
115
|
-
if (n < 1) n = 1;
|
|
116
|
-
if (n > 8) n = 8;
|
|
117
|
-
if (use_webkit && stagger_ms == 300) stagger_ms = 1500; /* WebKit 起视图更慢,给它更多余量 */
|
|
118
|
-
|
|
119
|
-
fprintf(stderr, "[gtkprobe] creating %d thread(s) use_webkit=%d stagger=%dms\n",
|
|
120
|
-
n, use_webkit, stagger_ms);
|
|
121
|
-
for (i = 0; i < n; i++) {
|
|
122
|
-
args[i].idx = i;
|
|
123
|
-
args[i].use_webkit = use_webkit;
|
|
124
|
-
pthread_create(&t[i], NULL, worker, &args[i]);
|
|
125
|
-
usleep(stagger_ms * 1000);
|
|
126
|
-
}
|
|
127
|
-
{
|
|
128
|
-
int waited = 0;
|
|
129
|
-
while (g_windows_up < n && waited < 8000) {
|
|
130
|
-
usleep(100000);
|
|
131
|
-
waited += 100;
|
|
132
|
-
}
|
|
133
|
-
if (g_windows_up < n) {
|
|
134
|
-
fprintf(stderr, "[gtkprobe] 超时:只有 %d/%d 个窗口起来了(线程卡在初始化里)\n",
|
|
135
|
-
g_windows_up, n);
|
|
136
|
-
return 3; /* 独立退出码,别和 SIGSEGV/abort 混为一谈 */
|
|
137
|
-
}
|
|
138
|
-
fprintf(stderr, "[gtkprobe] %d 个窗口都起来了,再观察 3s(抓迟到的崩溃)\n", n);
|
|
139
|
-
sleep(3);
|
|
140
|
-
}
|
|
141
|
-
fprintf(stderr, "[gtkprobe] main: 正常退出\n");
|
|
142
|
-
return 0;
|
|
143
|
-
}
|
|
1
|
+
/*
|
|
2
|
+
* 多窗口可行性最小对照(纯 GTK / GTK+WebKit;无仓颉、无 cj-tauri 代码)
|
|
3
|
+
*
|
|
4
|
+
* 用途:把 docs/架构演进-多平台与多窗口.md §8 的结论做成可复跑的复现器。
|
|
5
|
+
*
|
|
6
|
+
* 用法: gtk_threading_probe <N> [--webkit] [--stagger-ms N]
|
|
7
|
+
* N=1 → exit=0(基线)
|
|
8
|
+
* N=2(纯 GTK) → exit=0:GTK 本身不反对两条各自的 gtk_main
|
|
9
|
+
* N=2 --webkit → **不可用**:实测 8/8 致命失败(多数 exit=139 SIGSEGV +
|
|
10
|
+
* Gtk-CRITICAL;早先 /tmp 变体是 exit=134 abort;也可能表现为
|
|
11
|
+
* 线程卡在 gtk_init 里 → main 超时给 exit=3)
|
|
12
|
+
*
|
|
13
|
+
* 退出码:0 = N 个窗口都起来且无迟到崩溃;3 = 超时(有窗口没起来);134/139 = 被信号打死。
|
|
14
|
+
*
|
|
15
|
+
* 线程一律**串行起**(默认纯 GTK 300ms、带 WebKit 1500ms):串行也逃不掉(8/8),
|
|
16
|
+
* 所以既不是单纯的「初始化撞车」,也不是靠时序能回避的竞态——一个进程里两个
|
|
17
|
+
* WebKitWebView 分处两条线程就是不被支持的用法。
|
|
18
|
+
*
|
|
19
|
+
* 编译 / 跑法见 scripts/test-gtk-threading.sh(本文件不会被 cjpm 编译,纯 C 小程序)。
|
|
20
|
+
*/
|
|
21
|
+
#include <gtk/gtk.h>
|
|
22
|
+
|
|
23
|
+
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
24
|
+
#include <webkit2/webkit2.h>
|
|
25
|
+
#endif
|
|
26
|
+
|
|
27
|
+
#include <pthread.h>
|
|
28
|
+
#include <stdint.h>
|
|
29
|
+
#include <stdio.h>
|
|
30
|
+
#include <stdlib.h>
|
|
31
|
+
#include <string.h>
|
|
32
|
+
#include <unistd.h>
|
|
33
|
+
|
|
34
|
+
typedef struct worker_arg {
|
|
35
|
+
int idx;
|
|
36
|
+
int use_webkit;
|
|
37
|
+
} worker_arg;
|
|
38
|
+
|
|
39
|
+
/* 已经「窗口建好、进了 gtk_main」的线程数。主线程靠它判成败——不能只 sleep 完就 return:
|
|
40
|
+
线程卡在 gtk_init 里没出来时,主线程照样返回 0,那会把「卡死」误报成干净退出(本探针首版
|
|
41
|
+
就踩过这个坑:日志里没有 window up 行,退出码却是 0)。 */
|
|
42
|
+
static volatile int g_windows_up = 0;
|
|
43
|
+
|
|
44
|
+
static gboolean tick(gpointer d) {
|
|
45
|
+
fprintf(stderr, "[gtkprobe] window %ld alive\n", (long)(intptr_t)d);
|
|
46
|
+
return G_SOURCE_CONTINUE;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
50
|
+
static void on_load(WebKitWebView *view, WebKitLoadEvent ev, gpointer d) {
|
|
51
|
+
(void)view;
|
|
52
|
+
fprintf(stderr, "[gtkprobe] window %ld load event=%d\n", (long)(intptr_t)d, (int)ev);
|
|
53
|
+
}
|
|
54
|
+
#endif
|
|
55
|
+
|
|
56
|
+
static void *worker(void *arg) {
|
|
57
|
+
worker_arg *wa = (worker_arg *)arg;
|
|
58
|
+
GtkWidget *w;
|
|
59
|
+
GtkWidget *view = NULL;
|
|
60
|
+
char tmp[160];
|
|
61
|
+
|
|
62
|
+
fprintf(stderr, "[gtkprobe] thread %d: gtk_init\n", wa->idx);
|
|
63
|
+
gtk_init(NULL, NULL); /* 每条线程各初始化一次 GDK,与本项目的桥同构 */
|
|
64
|
+
|
|
65
|
+
w = gtk_window_new(GTK_WINDOW_TOPLEVEL);
|
|
66
|
+
snprintf(tmp, sizeof(tmp), "gtkprobe %d", wa->idx);
|
|
67
|
+
gtk_window_set_title(GTK_WINDOW(w), tmp);
|
|
68
|
+
gtk_window_set_default_size(GTK_WINDOW(w), 400, 300);
|
|
69
|
+
|
|
70
|
+
if (wa->use_webkit) {
|
|
71
|
+
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
72
|
+
view = webkit_web_view_new(); /* 默认 WebKitWebContext */
|
|
73
|
+
gtk_container_add(GTK_CONTAINER(w), view);
|
|
74
|
+
g_signal_connect(view, "load-changed", G_CALLBACK(on_load), (gpointer)(intptr_t)wa->idx);
|
|
75
|
+
#else
|
|
76
|
+
fprintf(stderr, "[gtkprobe] 本二进制未编入 WebKit(--webkit 无效)\n");
|
|
77
|
+
return NULL;
|
|
78
|
+
#endif
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
g_signal_connect(w, "destroy", G_CALLBACK(gtk_main_quit), NULL);
|
|
82
|
+
gtk_widget_show_all(w);
|
|
83
|
+
|
|
84
|
+
if (wa->use_webkit && view) {
|
|
85
|
+
#ifdef CJ_GTK_PROBE_WITH_WEBKIT
|
|
86
|
+
snprintf(tmp, sizeof(tmp), "data:text/html,<h1>win %d</h1>", wa->idx);
|
|
87
|
+
webkit_web_view_load_uri(WEBKIT_WEB_VIEW(view), tmp);
|
|
88
|
+
#endif
|
|
89
|
+
}
|
|
90
|
+
fprintf(stderr, "[gtkprobe] thread %d: window up, entering gtk_main\n", wa->idx);
|
|
91
|
+
__sync_fetch_and_add(&g_windows_up, 1);
|
|
92
|
+
g_timeout_add(500, tick, (gpointer)(intptr_t)wa->idx);
|
|
93
|
+
gtk_main();
|
|
94
|
+
fprintf(stderr, "[gtkprobe] thread %d: gtk_main returned\n", wa->idx);
|
|
95
|
+
return NULL;
|
|
96
|
+
}
|
|
97
|
+
|
|
98
|
+
int main(int argc, char **argv) {
|
|
99
|
+
int n = 1;
|
|
100
|
+
int use_webkit = 0;
|
|
101
|
+
int stagger_ms = 300;
|
|
102
|
+
int i;
|
|
103
|
+
pthread_t t[8];
|
|
104
|
+
worker_arg args[8];
|
|
105
|
+
|
|
106
|
+
for (i = 1; i < argc; i++) {
|
|
107
|
+
if (strcmp(argv[i], "--webkit") == 0) {
|
|
108
|
+
use_webkit = 1;
|
|
109
|
+
} else if (strcmp(argv[i], "--stagger-ms") == 0 && i + 1 < argc) {
|
|
110
|
+
stagger_ms = atoi(argv[++i]);
|
|
111
|
+
} else {
|
|
112
|
+
n = atoi(argv[i]);
|
|
113
|
+
}
|
|
114
|
+
}
|
|
115
|
+
if (n < 1) n = 1;
|
|
116
|
+
if (n > 8) n = 8;
|
|
117
|
+
if (use_webkit && stagger_ms == 300) stagger_ms = 1500; /* WebKit 起视图更慢,给它更多余量 */
|
|
118
|
+
|
|
119
|
+
fprintf(stderr, "[gtkprobe] creating %d thread(s) use_webkit=%d stagger=%dms\n",
|
|
120
|
+
n, use_webkit, stagger_ms);
|
|
121
|
+
for (i = 0; i < n; i++) {
|
|
122
|
+
args[i].idx = i;
|
|
123
|
+
args[i].use_webkit = use_webkit;
|
|
124
|
+
pthread_create(&t[i], NULL, worker, &args[i]);
|
|
125
|
+
usleep(stagger_ms * 1000);
|
|
126
|
+
}
|
|
127
|
+
{
|
|
128
|
+
int waited = 0;
|
|
129
|
+
while (g_windows_up < n && waited < 8000) {
|
|
130
|
+
usleep(100000);
|
|
131
|
+
waited += 100;
|
|
132
|
+
}
|
|
133
|
+
if (g_windows_up < n) {
|
|
134
|
+
fprintf(stderr, "[gtkprobe] 超时:只有 %d/%d 个窗口起来了(线程卡在初始化里)\n",
|
|
135
|
+
g_windows_up, n);
|
|
136
|
+
return 3; /* 独立退出码,别和 SIGSEGV/abort 混为一谈 */
|
|
137
|
+
}
|
|
138
|
+
fprintf(stderr, "[gtkprobe] %d 个窗口都起来了,再观察 3s(抓迟到的崩溃)\n", n);
|
|
139
|
+
sleep(3);
|
|
140
|
+
}
|
|
141
|
+
fprintf(stderr, "[gtkprobe] main: 正常退出\n");
|
|
142
|
+
return 0;
|
|
143
|
+
}
|