zig/src/link/StringTable.zig
Andrew Kelley 14c8e270bb link: fix false positive crtbegin/crtend detection
Embrace the Path abstraction, doing more operations based on directory
handles rather than absolute file paths. Most of the diff noise here
comes from this one.

Fix sorting of crtbegin/crtend atoms. Previously it would look at all
path components for those strings.

Make the C runtime path detection partially a pure function, and move
some logic to glibc.zig where it belongs.
2024-10-10 14:21:52 -07:00

50 lines
1.5 KiB
Zig

buffer: std.ArrayListUnmanaged(u8) = .empty,
table: std.HashMapUnmanaged(u32, void, StringIndexContext, std.hash_map.default_max_load_percentage) = .empty,
pub fn deinit(self: *Self, gpa: Allocator) void {
self.buffer.deinit(gpa);
self.table.deinit(gpa);
}
pub fn insert(self: *Self, gpa: Allocator, string: []const u8) !u32 {
const gop = try self.table.getOrPutContextAdapted(gpa, @as([]const u8, string), StringIndexAdapter{
.bytes = &self.buffer,
}, StringIndexContext{
.bytes = &self.buffer,
});
if (gop.found_existing) return gop.key_ptr.*;
try self.buffer.ensureUnusedCapacity(gpa, string.len + 1);
const new_off: u32 = @intCast(self.buffer.items.len);
self.buffer.appendSliceAssumeCapacity(string);
self.buffer.appendAssumeCapacity(0);
gop.key_ptr.* = new_off;
return new_off;
}
pub fn getOffset(self: *Self, string: []const u8) ?u32 {
return self.table.getKeyAdapted(string, StringIndexAdapter{
.bytes = &self.buffer,
});
}
pub fn get(self: Self, off: u32) ?[:0]const u8 {
if (off >= self.buffer.items.len) return null;
return mem.sliceTo(@as([*:0]const u8, @ptrCast(self.buffer.items.ptr + off)), 0);
}
pub fn getAssumeExists(self: Self, off: u32) [:0]const u8 {
return self.get(off) orelse unreachable;
}
const std = @import("std");
const mem = std.mem;
const Allocator = mem.Allocator;
const Self = @This();
const StringIndexAdapter = std.hash_map.StringIndexAdapter;
const StringIndexContext = std.hash_map.StringIndexContext;