commit d07e885
pnthr
·
2026-07-17 16:40:12 +0000 UTC
parent c30e59b
Added double buffer and removed gnu plus some unused things
3 files changed,
+63,
-45
+5,
-0
1@@ -9,6 +9,11 @@
2 /*-test
3 /screenshot-*.bmp
4
5+src/wlr-layer-shell-client-protocol.c
6+src/wlr-layer-shell-client-protocol.h
7+src/xdg-shell-client-protocol.h
8+src/xdg-shell-protocol.c
9+
10 *snarf
11 *theme
12
M
makefile
+4,
-3
1@@ -3,11 +3,12 @@ DEBUG_flags=-std=c99 -D_POSIX_C_SOURCE=199309L -DDEBUG -Wall -Wno-unknown-pragma
2 PREFIX=${HOME}/.local
3
4 WAYLAND_SCANNER=wayland-scanner
5-XDG_XML=$(shell pkg-config --variable=pkgdatadir wayland-protocols)/stable/xdg-shell/xdg-shell.xml
6+XDG_XML=`pkg-config --variable=pkgdatadir wayland-protocols`/stable/xdg-shell/xdg-shell.xml
7 WLR_XML=src/wlr-layer-shell-unstable-v1.xml
8
9 PROTO_C=src/xdg-shell-protocol.c src/wlr-layer-shell-client-protocol.c
10 PROTO_H=src/xdg-shell-client-protocol.h src/wlr-layer-shell-client-protocol.h
11+LIBS=`pkg-config --cflags --libs wayland-client xkbcommon`
12
13 run: bin/uxn12 bin/m_pc.rom bin/perifs.rom
14 bin/uxn12 bin/m_pc.rom bin/perifs.rom run
15@@ -50,10 +51,10 @@ archive:
16
17 bin/uxn12: src/uxn12.c $(PROTO_C) $(PROTO_H)
18 mkdir -p bin
19- cc ${RELEASE_flags} ${CFLAGS} -s src/uxn12.c $(PROTO_C) -lwayland-client -lxkbcommon -o bin/uxn12
20+ cc ${RELEASE_flags} ${CFLAGS} -s src/uxn12.c $(PROTO_C) $(LIBS) -o bin/uxn12
21 bin/uxn12-debug: src/uxn12.c $(PROTO_C) $(PROTO_H)
22 mkdir -p bin
23- cc ${DEBUG_flags} ${CFLAGS} -s src/uxn12.c $(PROTO_C) -lwayland-client -lxkbcommon -o bin/uxn12-debug
24+ cc ${DEBUG_flags} ${CFLAGS} -s src/uxn12.c $(PROTO_C) $(LIBS) -o bin/uxn12-debug
25
26 # Tools
27
+54,
-42
1@@ -1,10 +1,8 @@
2-#define _GNU_SOURCE
3 #include <stdio.h>
4 #include <stdlib.h>
5 #include <unistd.h>
6 #include <string.h>
7 #include <sys/mman.h>
8-#include <sys/timerfd.h>
9 #include <poll.h>
10 #include <wayland-client.h>
11 #include <xkbcommon/xkbcommon.h>
12@@ -54,7 +52,7 @@ static inline void poke2(Uint8 *d, Uint16 v) { d[0] = v >> 8, d[1] = v; }
13 @|System ------------------------------------------------------------ */
14
15 static char *system_boot_path;
16-static void emu_screenshot();
17+static void emu_screenshot(void);
18
19 static void
20 system_print(char *name, int r)
21@@ -159,11 +157,7 @@ console_input(int c, unsigned int type)
22 uxn_eval(console_vector);
23 }
24
25-#undef _POSIX_C_SOURCE
26-#define _POSIX_C_SOURCE 200112L
27-
28 #include <signal.h>
29-#include <sys/select.h>
30 #include <sys/wait.h>
31
32 #ifdef __linux
33@@ -355,6 +349,8 @@ static int screen_width, screen_height, screen_wmar2, screen_hmar2;
34 static int *screen_pixels, screen_palette[16];
35 static Uint8 *screen_layers;
36
37+void emu_redraw(void), emu_resize(void);
38+
39 static const Uint8 blend_lut[16][2][4] = {
40 {{0, 0, 1, 2}, {0, 0, 4, 8}},
41 {{0, 1, 2, 3}, {0, 4, 8, 12}},
42@@ -373,7 +369,6 @@ static const Uint8 blend_lut[16][2][4] = {
43 {{3, 2, 3, 1}, {12, 8, 12, 4}},
44 {{3, 3, 1, 2}, {12, 12, 4, 8}}};
45
46-void emu_redraw(void), emu_resize(void);
47
48 static void
49 system_deo_colorize(void)
50@@ -435,7 +430,6 @@ screen_redraw(void)
51 }
52 }
53 }
54- emu_redraw();
55 screen_reqdraw = 0;
56 }
57
58@@ -1104,17 +1098,17 @@ static struct xdg_wm_base *emu_wm;
59 static struct wl_surface *emu_surf;
60 static struct xdg_surface *emu_xdgsurf;
61 static struct xdg_toplevel *emu_top;
62-static struct wl_buffer *emu_buf;
63+static struct wl_buffer *emu_bufs[2];
64 static struct zwlr_layer_shell_v1 *emu_layer_shell;
65 static struct zwlr_layer_surface_v1 *emu_layer_surf;
66 static int use_layer_shell = 0;
67 static int layer_shell_x = 0;
68 static int layer_shell_y = 0;
69-static int emu_timer;
70 static int emu_configured;
71+static int active_buf;
72
73 static void *shm_data;
74-static int shm_size, shm_width, shm_height;
75+static int shm_size, shm_bufsize, shm_width, shm_height;
76
77 static struct xkb_context *xkb_ctx;
78 static struct xkb_keymap *xkb_map;
79@@ -1134,30 +1128,56 @@ emu_resize(void)
80 int fd;
81 if(shm_data)
82 munmap(shm_data, shm_size);
83- if(emu_buf)
84- wl_buffer_destroy(emu_buf);
85- fd = memfd_create("uxn-wl", MFD_CLOEXEC);
86- ftruncate(fd, size);
87- shm_data = mmap(NULL, size, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
88- pool = wl_shm_create_pool(emu_shm, fd, size);
89- emu_buf = wl_shm_pool_create_buffer(pool, 0, width, height, stride, WL_SHM_FORMAT_XRGB8888);
90+ if(emu_bufs[0])
91+ wl_buffer_destroy(emu_bufs[0]);
92+ if(emu_bufs[1])
93+ wl_buffer_destroy(emu_bufs[1]);
94+ char tmpl[] = "/tmp/uxn-wl-XXXXXX";
95+ fd = mkstemp(tmpl);
96+ unlink(tmpl);
97+ ftruncate(fd, size * 2);
98+ shm_data = mmap(NULL, size * 2, PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0);
99+ pool = wl_shm_create_pool(emu_shm, fd, size * 2);
100+ emu_bufs[0] = wl_shm_pool_create_buffer(pool, 0, width, height, stride, WL_SHM_FORMAT_XRGB8888);
101+ emu_bufs[1] = wl_shm_pool_create_buffer(pool, size, width, height, stride, WL_SHM_FORMAT_XRGB8888);
102 wl_shm_pool_destroy(pool);
103 close(fd);
104- shm_size = size, shm_width = width, shm_height = height;
105+ shm_size = size * 2, shm_bufsize = size, shm_width = width, shm_height = height;
106 }
107- screen_pixels = (int *)shm_data;
108+ screen_pixels = (int *)((Uint8 *)shm_data + active_buf * shm_bufsize);
109+ active_buf = 0;
110 }
111
112+static void frame_callback(void *, struct wl_callback *, uint32_t);
113+
114+static const struct wl_callback_listener frame_listener = {
115+ .done = frame_callback,
116+};
117+
118 void
119 emu_redraw(void)
120 {
121 if(!emu_configured)
122 return;
123- wl_surface_attach(emu_surf, emu_buf, 0, 0);
124+ wl_callback_add_listener(wl_surface_frame(emu_surf), &frame_listener, NULL);
125+ wl_surface_attach(emu_surf, emu_bufs[active_buf], 0, 0);
126 wl_surface_damage_buffer(emu_surf, 0, 0, screen_width * screen_zoom, screen_height * screen_zoom);
127 wl_surface_commit(emu_surf);
128 }
129
130+static void
131+frame_callback(void *data, struct wl_callback *cb, uint32_t time)
132+{
133+ wl_callback_destroy(cb);
134+ int old = active_buf;
135+ active_buf ^= 1;
136+ memcpy((Uint8 *)shm_data + active_buf * shm_bufsize,
137+ (Uint8 *)shm_data + old * shm_bufsize, shm_bufsize);
138+ screen_pixels = (int *)((Uint8 *)shm_data + active_buf * shm_bufsize);
139+ screen_update();
140+ emu_redraw();
141+}
142+
143 static void
144 emu_restart(unsigned int soft)
145 {
146@@ -1403,10 +1423,10 @@ static const struct wl_registry_listener reg_listener = {
147 .global = reg_global,
148 };
149
150+
151 static int
152 emu_init(void)
153 {
154- static const struct itimerspec screen_tspec = {{0, 16666666}, {0, 16666666}};
155 xkb_ctx = xkb_context_new(XKB_CONTEXT_NO_FLAGS);
156 emu_dpy = wl_display_connect(NULL);
157 if(!emu_dpy)
158@@ -1440,10 +1460,6 @@ emu_init(void)
159 wl_surface_commit(emu_surf);
160 }
161 wl_display_roundtrip(emu_dpy);
162- emu_timer = timerfd_create(CLOCK_MONOTONIC, TFD_CLOEXEC);
163- if(emu_timer < 0)
164- return !fprintf(stderr, "timerfd_create: failed\n");
165- timerfd_settime(emu_timer, 0, &screen_tspec, NULL);
166 return 1;
167 }
168
169@@ -1451,25 +1467,20 @@ static void
170 emu_run(void)
171 {
172 int has_input, stdin_active = 1;
173- char expirations[8], coninp[CONINBUFSIZE];
174- struct pollfd fds[3];
175+ char coninp[CONINBUFSIZE];
176+ struct pollfd fds[2];
177 fds[0].fd = wl_display_get_fd(emu_dpy), fds[0].events = POLLIN;
178- fds[1].fd = emu_timer, fds[1].events = POLLIN;
179- fds[2].fd = STDIN_FILENO, fds[2].events = POLLIN | POLLHUP;
180+ fds[1].fd = STDIN_FILENO, fds[1].events = POLLIN | POLLHUP;
181 while(!dev[0x0f]) {
182 wl_display_dispatch_pending(emu_dpy);
183 wl_display_flush(emu_dpy);
184 /* only poll stdin while it's still active */
185- if(poll(fds, stdin_active ? 3 : 2, -1) <= 0)
186+ if(poll(fds, stdin_active ? 2 : 1, -1) <= 0)
187 continue;
188 if(fds[0].revents & POLLIN)
189 wl_display_dispatch(emu_dpy);
190- if(fds[1].revents & POLLIN) {
191- read(emu_timer, expirations, sizeof expirations);
192- screen_update();
193- }
194- has_input = stdin_active && (fds[2].revents & POLLIN);
195- if(has_input || (stdin_active && (fds[2].revents & POLLHUP))) {
196+ has_input = stdin_active && (fds[1].revents & POLLIN);
197+ if(has_input || (stdin_active && (fds[1].revents & POLLHUP))) {
198 int i, n = read(STDIN_FILENO, coninp, CONINBUFSIZE - 1);
199 if(n > 0) {
200 for(i = 0; i < n; i++)
201@@ -1481,10 +1492,10 @@ emu_run(void)
202 }
203 datetime_busy = 0;
204 }
205- if(emu_timer >= 0)
206- close(emu_timer);
207- if(emu_buf)
208- wl_buffer_destroy(emu_buf);
209+ if(emu_bufs[0])
210+ wl_buffer_destroy(emu_bufs[0]);
211+ if(emu_bufs[1])
212+ wl_buffer_destroy(emu_bufs[1]);
213 if(emu_top)
214 xdg_toplevel_destroy(emu_top);
215 if(emu_xdgsurf)
216@@ -1535,6 +1546,7 @@ main(int argc, char **argv)
217 if(!emu_init())
218 return !fprintf(stdout, "Could not initialize %s.\n", argv[0]);
219 screen_update();
220+ emu_redraw();
221 emu_run();
222 }
223 return dev[0x0f] & 0x7f;