mirror of
https://github.com/oven-sh/bun
synced 2026-02-14 04:49:06 +00:00
69
src/node_module_bundle.zig
Normal file
69
src/node_module_bundle.zig
Normal file
@@ -0,0 +1,69 @@
|
||||
const Api = @import("./api/schema.zig").Api;
|
||||
const std = @import("std");
|
||||
usingnamespace @import("global.zig");
|
||||
|
||||
pub const NodeModuleBundle = struct {
|
||||
container: *Api.JavascriptBundleContainer,
|
||||
bundle: *Api.JavascriptBundle,
|
||||
allocator: *std.mem.Allocator,
|
||||
fd: FileDescriptorType = 0,
|
||||
|
||||
pub const magic_bytes = "#!/usr/bin/env speedy\n\n";
|
||||
threadlocal var jsbundle_prefix: [magic_bytes.len + 5]u8 = undefined;
|
||||
|
||||
pub fn getCodeEndPosition(stream: anytype, comptime needs_seek: bool) !u32 {
|
||||
if (needs_seek) try stream.seekTo(0);
|
||||
|
||||
const read_bytes = try stream.read(&jsbundle_prefix);
|
||||
if (read_bytes != jsbundle_prefix.len) {
|
||||
return error.JSBundleBadHeaderTooShort;
|
||||
}
|
||||
|
||||
return std.mem.readIntNative(u32, jsbundle_prefix[magic_bytes.len .. magic_bytes.len + 4]);
|
||||
}
|
||||
|
||||
pub fn loadBundle(allocator: *std.mem.Allocator, stream: anytype) !NodeModuleBundle {
|
||||
const end = try getCodeEndPosition(stream);
|
||||
try stream.seekTo(end + 1);
|
||||
var reader = stream.reader();
|
||||
var container = try Api.JavascriptBundleContainer.decode(allocator, reader);
|
||||
return NodeModuleBundle{
|
||||
.allocator = allocator,
|
||||
.container = container,
|
||||
.bundle = container.bundle,
|
||||
.fd = if (std.meta.trait.hasField("handle")(stream)) stream.handle else 0,
|
||||
};
|
||||
}
|
||||
|
||||
pub fn printBundle(
|
||||
comptime StreamType: type,
|
||||
input: StreamType,
|
||||
comptime DestinationStreamType: type,
|
||||
output: DestinationStreamType,
|
||||
) !void {
|
||||
const BufferStreamContext = struct {
|
||||
pub fn run(in: StreamType, out: DestinationStreamType, end_at: u32) !void {
|
||||
var buf: [4096]u8 = undefined;
|
||||
var remain = @intCast(i64, end_at);
|
||||
var read_amount: i64 = @intCast(i64, in.read(&buf) catch 0);
|
||||
while (remain > 0 and read_amount > 0) {
|
||||
remain -= @intCast(i64, try out.write(buf[0..@intCast(usize, std.math.min(read_amount, remain))]));
|
||||
read_amount = @intCast(i64, in.read(&buf) catch 0);
|
||||
}
|
||||
|
||||
_ = try out.write(buf[0..@intCast(usize, remain + 1)]);
|
||||
}
|
||||
};
|
||||
if (isMac) {
|
||||
// darwin only allows reading ahead on/off, not specific amount
|
||||
_ = std.os.fcntl(input.handle, std.os.F_RDAHEAD, 1) catch 0;
|
||||
}
|
||||
const end = try getCodeEndPosition(input, false);
|
||||
|
||||
try BufferStreamContext.run(
|
||||
input,
|
||||
output,
|
||||
end,
|
||||
);
|
||||
}
|
||||
};
|
||||
Reference in New Issue
Block a user