Use bun.sys more instead of std.fs

This commit is contained in:
Jarred Sumner
2025-02-20 12:40:03 -08:00
parent 6e45e3bf1e
commit 70c08b23b4
3 changed files with 56 additions and 86 deletions

View File

@@ -129,10 +129,10 @@ pub const Fs = struct {
) !Entry {
var rfs = _fs.fs;
const file_handle: std.fs.File = if (_file_handle) |__file|
std.fs.File{ .handle = __file }
const file_handle: bun.sys.File = if (_file_handle) |__file|
bun.sys.File{ .handle = __file }
else
try std.fs.openFileAbsoluteZ(path, .{ .mode = .read_only });
try bun.sys.File.open(path, bun.sys.O.RDONLY, 0).unwrap();
defer {
if (rfs.needToCloseFiles() and _file_handle == null) {
@@ -183,11 +183,11 @@ pub const Fs = struct {
) !Entry {
var rfs = _fs.fs;
var file_handle: std.fs.File = if (_file_handle) |__file| __file.asFile() else undefined;
var file_handle: bun.sys.File = if (_file_handle) |__file| bun.sys.File{ .handle = __file } else undefined;
if (_file_handle == null) {
if (FeatureFlags.store_file_descriptors and dirname_fd != bun.invalid_fd and dirname_fd != .zero) {
file_handle = (bun.sys.openatA(dirname_fd, std.fs.path.basename(path), bun.O.RDONLY, 0).unwrap() catch |err| brk: {
file_handle = .{ .handle = (bun.sys.openatA(dirname_fd, std.fs.path.basename(path), bun.O.RDONLY, 0).unwrap() catch |err| brk: {
switch (err) {
error.ENOENT => {
const handle = try bun.openFile(path, .{ .mode = .read_only });
@@ -199,9 +199,9 @@ pub const Fs = struct {
},
else => return err,
}
}).asFile();
}) };
} else {
file_handle = try bun.openFile(path, .{ .mode = .read_only });
file_handle = .{ .handle = try bun.sys.openA(path, bun.sys.O.RDONLY, 0).unwrap() };
}
}
@@ -211,7 +211,6 @@ pub const Fs = struct {
const will_close = rfs.needToCloseFiles() and _file_handle == null;
defer {
if (will_close) {
debug("readFileWithAllocator close({d})", .{file_handle.handle});
file_handle.close();
}
}

View File

@@ -1135,7 +1135,7 @@ pub const FileSystem = struct {
fs: *RealFS,
path: string,
_size: ?usize,
file: std.fs.File,
file: bun.sys.File,
comptime use_shared_buffer: bool,
shared_buffer: *MutableString,
comptime stream: bool,
@@ -1157,19 +1157,18 @@ pub const FileSystem = struct {
allocator: std.mem.Allocator,
path: string,
_size: ?usize,
file: std.fs.File,
file: bun.sys.File,
comptime use_shared_buffer: bool,
shared_buffer: *MutableString,
comptime stream: bool,
) !PathContentsPair {
FileSystem.setMaxFd(file.handle);
if (comptime Environment.isPosix) {
FileSystem.setMaxFd(file.handle.int());
}
// Skip the extra file.stat() call when possible
var size = _size orelse (file.getEndPos() catch |err| {
fs.readFileError(path, err);
return err;
});
debug("stat({d}) = {d}", .{ file.handle, size });
var size = _size orelse try file.getEndPos().unwrap();
debug("stat({}) = {d}", .{ file.handle, size });
// Skip the pread call for empty files
// Otherwise will get out of bounds errors
@@ -1203,14 +1202,10 @@ pub const FileSystem = struct {
// We use pread to ensure if the file handle was open, it doesn't seek from the last position
const prev_file_pos = if (comptime Environment.isWindows) try file.getPos() else 0;
const read_count = file.preadAll(shared_buffer.list.items[offset..], offset) catch |err| {
fs.readFileError(path, err);
return err;
};
if (comptime Environment.isWindows) try file.seekTo(prev_file_pos);
shared_buffer.list.items = shared_buffer.list.items[0 .. read_count + offset];
const read_amount = try file.preadAll(shared_buffer.list.items[offset..], offset).unwrap();
if (comptime Environment.isWindows) try file.seekTo(@intCast(prev_file_pos));
shared_buffer.list.items = shared_buffer.list.items[0 .. read_amount + offset];
file_contents = shared_buffer.list.items;
debug("pread({d}, {d}) = {d}", .{ file.handle, size, read_count });
if (comptime stream) {
// check again that stat() didn't change the file size
@@ -1220,11 +1215,10 @@ pub const FileSystem = struct {
return err;
};
offset += read_count;
offset += read_amount;
// don't infinite loop is we're still not reading more
if (read_count == 0) break;
if (read_amount == 0) break;
if (offset < new_size) {
try shared_buffer.growBy(new_size - size);
shared_buffer.list.expandToCapacity();
@@ -1251,13 +1245,9 @@ pub const FileSystem = struct {
buf[size] = 0;
const prev_file_pos = if (comptime Environment.isWindows) try file.getPos() else 0;
const read_count = file.preadAll(buf, 0) catch |err| {
fs.readFileError(path, err);
return err;
};
const read_buf = try file.preadAll(buf, 0).unwrap();
if (comptime Environment.isWindows) try file.seekTo(prev_file_pos);
file_contents = buf[0..read_count];
debug("pread({d}, {d}) = {d}", .{ file.handle, size, read_count });
file_contents = buf[0..read_buf];
if (strings.BOM.detect(file_contents)) |bom| {
debug("Convert {s} BOM", .{@tagName(bom)});
@@ -1268,60 +1258,6 @@ pub const FileSystem = struct {
return PathContentsPair{ .path = Path.init(path), .contents = file_contents };
}
pub fn kindFromAbsolute(
fs: *RealFS,
absolute_path: [:0]const u8,
existing_fd: StoredFileDescriptorType,
store_fd: bool,
) !Entry.Cache {
var outpath: bun.PathBuffer = undefined;
const stat = try C.lstat_absolute(absolute_path);
const is_symlink = stat.kind == std.fs.File.Kind.SymLink;
var _kind = stat.kind;
var cache = Entry.Cache{
.kind = Entry.Kind.file,
.symlink = PathString.empty,
};
var symlink: []const u8 = "";
if (is_symlink) {
var file = try if (existing_fd != 0)
std.fs.File{ .handle = existing_fd }
else if (store_fd)
std.fs.openFileAbsoluteZ(absolute_path, .{ .mode = .read_only })
else
bun.openFileForPath(absolute_path);
setMaxFd(file.handle);
defer {
if ((!store_fd or fs.needToCloseFiles()) and existing_fd == 0) {
file.close();
} else if (comptime FeatureFlags.store_file_descriptors) {
cache.fd = file.handle;
}
}
const _stat = try file.stat();
symlink = try bun.getFdPath(file.handle, &outpath);
_kind = _stat.kind;
}
bun.assert(_kind != .SymLink);
if (_kind == .Directory) {
cache.kind = .dir;
} else {
cache.kind = .file;
}
if (symlink.len > 0) {
cache.symlink = PathString.init(try FilenameStore.instance.append([]const u8, symlink));
}
return cache;
}
pub fn kind(
fs: *RealFS,
_dir: string,

View File

@@ -4015,6 +4015,41 @@ pub const File = struct {
}
};
pub fn pread(this: File, buf: []u8, offset: usize) Maybe(usize) {
return bun.sys.pread(this.handle, buf, @intCast(offset));
}
pub fn seekTo(this: File, offset: i64) Maybe(void) {
if (comptime Environment.isWindows) {
const rc = std.os.windows.kernel32.SetFilePointerEx(this.handle.cast(), offset, null, std.os.windows.FILE_BEGIN);
if (Maybe(void).errnoSys(rc, .lseek)) |err| {
return err;
}
return .{ .result = {} };
}
return bun.sys.lseek(this.handle, offset, std.posix.SEEK.SET);
}
pub fn preadAll(this: File, buf: []u8, offset: usize) Maybe(usize) {
var total: usize = 0;
while (true) {
const read_amount = switch (this.pread(buf[total..], offset + total)) {
.err => |err| return .{ .err = err },
.result => |amt| amt,
};
if (read_amount == 0) {
break;
}
total += read_amount;
}
return .{ .result = total };
}
pub fn readFillBuf(this: File, buf: []u8) Maybe([]u8) {
var read_amount: usize = 0;
while (read_amount < buf.len) {