mirror of
https://github.com/ghostty-org/ghostty.git
synced 2025-07-17 01:06:08 +03:00
windows: get +ssh-cache building on Windows (#7947)
There are still problems linking due to `gettext`. No idea if this actually _works_ on Windows. File locking had to be disabled on Windows because of a bug in the Zig std library. Adding all of the explicit error sets happened due to disabling file locking. Fixing permissions had to be disabled on Windows as the Windows file system does not support permissions in the way that POSIX systems like macOS and Linux do.
This commit is contained in:
@ -4,6 +4,7 @@
|
|||||||
const DiskCache = @This();
|
const DiskCache = @This();
|
||||||
|
|
||||||
const std = @import("std");
|
const std = @import("std");
|
||||||
|
const builtin = @import("builtin");
|
||||||
const assert = std.debug.assert;
|
const assert = std.debug.assert;
|
||||||
const Allocator = std.mem.Allocator;
|
const Allocator = std.mem.Allocator;
|
||||||
const xdg = @import("../../os/main.zig").xdg;
|
const xdg = @import("../../os/main.zig").xdg;
|
||||||
@ -56,6 +57,8 @@ pub fn clear(self: DiskCache) !void {
|
|||||||
|
|
||||||
pub const AddResult = enum { added, updated };
|
pub const AddResult = enum { added, updated };
|
||||||
|
|
||||||
|
pub const AddError = std.fs.Dir.MakeError || std.fs.File.OpenError || std.fs.File.LockError || std.fs.File.ReadError || std.fs.File.WriteError || std.posix.RealPathError || std.posix.RenameError || Allocator.Error || error{ HostnameIsInvalid, CacheIsLocked };
|
||||||
|
|
||||||
/// Add or update a hostname entry in the cache.
|
/// Add or update a hostname entry in the cache.
|
||||||
/// Returns AddResult.added for new entries or AddResult.updated for existing ones.
|
/// Returns AddResult.added for new entries or AddResult.updated for existing ones.
|
||||||
/// The cache file is created if it doesn't exist with secure permissions (0600).
|
/// The cache file is created if it doesn't exist with secure permissions (0600).
|
||||||
@ -63,7 +66,7 @@ pub fn add(
|
|||||||
self: DiskCache,
|
self: DiskCache,
|
||||||
alloc: Allocator,
|
alloc: Allocator,
|
||||||
hostname: []const u8,
|
hostname: []const u8,
|
||||||
) !AddResult {
|
) AddError!AddResult {
|
||||||
if (!isValidCacheKey(hostname)) return error.HostnameIsInvalid;
|
if (!isValidCacheKey(hostname)) return error.HostnameIsInvalid;
|
||||||
|
|
||||||
// Create cache directory if needed
|
// Create cache directory if needed
|
||||||
@ -94,8 +97,10 @@ pub fn add(
|
|||||||
defer file.close();
|
defer file.close();
|
||||||
|
|
||||||
// Lock
|
// Lock
|
||||||
_ = file.tryLock(.exclusive) catch return error.CacheIsLocked;
|
// Causes a compile failure in the Zig std library on Windows, see:
|
||||||
defer file.unlock();
|
// https://github.com/ziglang/zig/issues/18430
|
||||||
|
if (comptime builtin.os.tag != .windows) _ = file.tryLock(.exclusive) catch return error.CacheIsLocked;
|
||||||
|
defer if (comptime builtin.os.tag != .windows) file.unlock();
|
||||||
|
|
||||||
var entries = try readEntries(alloc, file);
|
var entries = try readEntries(alloc, file);
|
||||||
defer deinitEntries(alloc, &entries);
|
defer deinitEntries(alloc, &entries);
|
||||||
@ -125,13 +130,15 @@ pub fn add(
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub const RemoveError = std.fs.Dir.OpenError || std.fs.File.OpenError || std.fs.File.ReadError || std.fs.File.WriteError || std.posix.RealPathError || std.posix.RenameError || Allocator.Error || error{ HostnameIsInvalid, CacheIsLocked };
|
||||||
|
|
||||||
/// Remove a hostname entry from the cache.
|
/// Remove a hostname entry from the cache.
|
||||||
/// No error is returned if the hostname doesn't exist or the cache file is missing.
|
/// No error is returned if the hostname doesn't exist or the cache file is missing.
|
||||||
pub fn remove(
|
pub fn remove(
|
||||||
self: DiskCache,
|
self: DiskCache,
|
||||||
alloc: Allocator,
|
alloc: Allocator,
|
||||||
hostname: []const u8,
|
hostname: []const u8,
|
||||||
) !void {
|
) RemoveError!void {
|
||||||
if (!isValidCacheKey(hostname)) return error.HostnameIsInvalid;
|
if (!isValidCacheKey(hostname)) return error.HostnameIsInvalid;
|
||||||
|
|
||||||
// Open our file
|
// Open our file
|
||||||
@ -145,9 +152,11 @@ pub fn remove(
|
|||||||
defer file.close();
|
defer file.close();
|
||||||
try fixupPermissions(file);
|
try fixupPermissions(file);
|
||||||
|
|
||||||
// Acquire exclusive lock
|
// Lock
|
||||||
_ = file.tryLock(.exclusive) catch return error.CacheIsLocked;
|
// Causes a compile failure in the Zig std library on Windows, see:
|
||||||
defer file.unlock();
|
// https://github.com/ziglang/zig/issues/18430
|
||||||
|
if (comptime builtin.os.tag != .windows) _ = file.tryLock(.exclusive) catch return error.CacheIsLocked;
|
||||||
|
defer if (comptime builtin.os.tag != .windows) file.unlock();
|
||||||
|
|
||||||
// Read existing entries
|
// Read existing entries
|
||||||
var entries = try readEntries(alloc, file);
|
var entries = try readEntries(alloc, file);
|
||||||
@ -191,6 +200,9 @@ pub fn contains(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fn fixupPermissions(file: std.fs.File) !void {
|
fn fixupPermissions(file: std.fs.File) !void {
|
||||||
|
// Windows does not support chmod
|
||||||
|
if (comptime builtin.os.tag == .windows) return;
|
||||||
|
|
||||||
// Ensure file has correct permissions (readable/writable by
|
// Ensure file has correct permissions (readable/writable by
|
||||||
// owner only)
|
// owner only)
|
||||||
const stat = try file.stat();
|
const stat = try file.stat();
|
||||||
@ -199,12 +211,14 @@ fn fixupPermissions(file: std.fs.File) !void {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub const WriteCacheFileError = std.fs.Dir.OpenError || std.fs.File.OpenError || std.fs.File.WriteError || std.fs.Dir.RealPathAllocError || std.posix.RealPathError || std.posix.RenameError || error{FileTooBig};
|
||||||
|
|
||||||
fn writeCacheFile(
|
fn writeCacheFile(
|
||||||
self: DiskCache,
|
self: DiskCache,
|
||||||
alloc: Allocator,
|
alloc: Allocator,
|
||||||
entries: std.StringHashMap(Entry),
|
entries: std.StringHashMap(Entry),
|
||||||
expire_days: ?u32,
|
expire_days: ?u32,
|
||||||
) !void {
|
) WriteCacheFileError!void {
|
||||||
var td: TempDir = try .init();
|
var td: TempDir = try .init();
|
||||||
defer td.deinit();
|
defer td.deinit();
|
||||||
|
|
||||||
@ -264,7 +278,7 @@ pub fn deinitEntries(
|
|||||||
fn readEntries(
|
fn readEntries(
|
||||||
alloc: Allocator,
|
alloc: Allocator,
|
||||||
file: std.fs.File,
|
file: std.fs.File,
|
||||||
) !std.StringHashMap(Entry) {
|
) (std.fs.File.ReadError || Allocator.Error || error{FileTooBig})!std.StringHashMap(Entry) {
|
||||||
const content = try file.readToEndAlloc(alloc, MAX_CACHE_SIZE);
|
const content = try file.readToEndAlloc(alloc, MAX_CACHE_SIZE);
|
||||||
defer alloc.free(content);
|
defer alloc.free(content);
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user