authorgravatar for ntamtam614@gmail.comNeel <ntamtam614@gmail.com> 2026-02-11 21:49:48-06:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2026-02-12 21:35:36-08:00
log5132d78e8385cbadc888275761258a1fca27b6f0
treed80ab86bf3bb54c55377ecb314ce66d6a2047406
parent4a3adaaa23faa1ae22fa72389850f04ece2570ca

libc: implement insque and remque in Zig

Implements insque() and remque() doubly-linked list functions in lib/c/search.zig and removes musl C implementation. Contributes to #30978

5 files changed, 68 insertions(+), 34 deletions(-)

lib/c.zig+1
...@@ -68,6 +68,7 @@ comptime {...@@ -68,6 +68,7 @@ comptime {
68 _ = @import("c/malloc.zig");68 _ = @import("c/malloc.zig");
69 }69 }
70 _ = @import("c/math.zig");70 _ = @import("c/math.zig");
71 _ = @import("c/search.zig");
71 _ = @import("c/stdlib.zig");72 _ = @import("c/stdlib.zig");
72 _ = @import("c/string.zig");73 _ = @import("c/string.zig");
73 _ = @import("c/strings.zig");74 _ = @import("c/strings.zig");
lib/c/search.zig created+67
...@@ -0,0 +1,67 @@
1const std = @import("std");
2const builtin = @import("builtin");
3const symbol = @import("../c.zig").symbol;
4
5comptime {
6 if (builtin.target.isMuslLibC() or builtin.target.isWasiLibC()) {
7 symbol(&insque, "insque");
8 symbol(&remque, "remque");
9 }
10}
11
12const Node = extern struct {
13 next: ?*Node,
14 prev: ?*Node,
15};
16
17fn insque(element: *anyopaque, pred: ?*anyopaque) callconv(.c) void {
18 const e: *Node = @ptrCast(@alignCast(element));
19
20 if (pred) |p_ptr| {
21 const p: *Node = @ptrCast(@alignCast(p_ptr));
22 e.next = p.next;
23 e.prev = p;
24 p.next = e;
25
26 if (e.next) |next| {
27 next.prev = e;
28 }
29 } else {
30 e.next = null;
31 e.prev = null;
32 }
33}
34
35fn remque(element: *anyopaque) callconv(.c) void {
36 const e: *Node = @ptrCast(@alignCast(element));
37
38 if (e.next) |next| next.prev = e.prev;
39 if (e.prev) |prev| prev.next = e.next;
40}
41
42test "insque and remque" {
43 var first = Node{ .next = null, .prev = null };
44 var second = Node{ .next = null, .prev = null };
45 var third = Node{ .next = null, .prev = null };
46
47 insque(&first, null);
48 try std.testing.expectEqual(@as(?*Node, null), first.next);
49 try std.testing.expectEqual(@as(?*Node, null), first.prev);
50
51 insque(&second, &first);
52 try std.testing.expectEqual(@as(?*Node, &second), first.next);
53 try std.testing.expectEqual(@as(?*Node, &first), second.prev);
54
55 insque(&third, &first);
56 try std.testing.expectEqual(@as(?*Node, &third), first.next);
57 try std.testing.expectEqual(@as(?*Node, &second), third.next);
58 try std.testing.expectEqual(@as(?*Node, &first), third.prev);
59 try std.testing.expectEqual(@as(?*Node, &third), second.prev);
60
61 remque(&third);
62 try std.testing.expectEqual(@as(?*Node, &second), first.next);
63 try std.testing.expectEqual(@as(?*Node, &first), second.prev);
64
65 remque(&second);
66 try std.testing.expectEqual(@as(?*Node, null), first.next);
67}
lib/libc/musl/src/search/insque.c deleted-32
...@@ -1,32 +0,0 @@
1#include <search.h>
2
3struct node {
4 struct node *next;
5 struct node *prev;
6};
7
8void insque(void *element, void *pred)
9{
10 struct node *e = element;
11 struct node *p = pred;
12
13 if (!p) {
14 e->next = e->prev = 0;
15 return;
16 }
17 e->next = p->next;
18 e->prev = p;
19 p->next = e;
20 if (e->next)
21 e->next->prev = e;
22}
23
24void remque(void *element)
25{
26 struct node *e = element;
27
28 if (e->next)
29 e->next->prev = e->prev;
30 if (e->prev)
31 e->prev->next = e->next;
32}
src/libs/musl.zig-1
...@@ -1296,7 +1296,6 @@ const src_files = [_][]const u8{...@@ -1296,7 +1296,6 @@ const src_files = [_][]const u8{
1296 "musl/src/sched/sched_setscheduler.c",1296 "musl/src/sched/sched_setscheduler.c",
1297 "musl/src/sched/sched_yield.c",1297 "musl/src/sched/sched_yield.c",
1298 "musl/src/search/hsearch.c",1298 "musl/src/search/hsearch.c",
1299 "musl/src/search/insque.c",
1300 "musl/src/search/lsearch.c",1299 "musl/src/search/lsearch.c",
1301 "musl/src/search/tdelete.c",1300 "musl/src/search/tdelete.c",
1302 "musl/src/search/tdestroy.c",1301 "musl/src/search/tdestroy.c",
src/libs/wasi_libc.zig-1
...@@ -848,7 +848,6 @@ const libc_top_half_src_files = [_][]const u8{...@@ -848,7 +848,6 @@ const libc_top_half_src_files = [_][]const u8{
848 "musl/src/regex/fnmatch.c",848 "musl/src/regex/fnmatch.c",
849 "musl/src/regex/regerror.c",849 "musl/src/regex/regerror.c",
850 "musl/src/search/hsearch.c",850 "musl/src/search/hsearch.c",
851 "musl/src/search/insque.c",
852 "musl/src/search/lsearch.c",851 "musl/src/search/lsearch.c",
853 "musl/src/search/tdelete.c",852 "musl/src/search/tdelete.c",
854 "musl/src/search/tdestroy.c",853 "musl/src/search/tdestroy.c",