authorgravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2023-01-16 14:59:41-07:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2023-01-17 00:08:42-07:00
log09560bc69a87f0540bd7a5a5c5e9e2a44db3a0cc
treec81259b74a244d45c346e111a48ede31658043aa
parent1f9fa822350ddf73fb7b3b9eb8f493ab64c935c8

clean up windows cert scanning

* keep helper functions out of the DLL bindings APIs * unify the logic for linux and windows certificate scanning with regards to error handling

2 files changed, 20 insertions(+), 39 deletions(-)

lib/std/crypto/Certificate/Bundle.zig+20-17
...@@ -111,25 +111,29 @@ pub fn rescanWindows(cb: *Bundle, gpa: Allocator) !void {...@@ -111,25 +111,29 @@ pub fn rescanWindows(cb: *Bundle, gpa: Allocator) !void {
111 cb.bytes.clearRetainingCapacity();111 cb.bytes.clearRetainingCapacity();
112 cb.map.clearRetainingCapacity();112 cb.map.clearRetainingCapacity();
113113
114 const store = try os.windows.crypt32.certOpenSystemStoreW(null, &[4:0]u16{ 'R', 'O', 'O', 'T' });114 const w = std.os.windows;
115 defer os.windows.crypt32.certCloseStore(store, 0) catch unreachable;115 const GetLastError = w.kernel32.GetLastError;
116116 const root = [4:0]u16{ 'R', 'O', 'O', 'T' };
117 var ctx = os.windows.crypt32.CertEnumCertificatesInStore(store, null);117 const store = w.crypt32.CertOpenSystemStoreW(null, &root) orelse switch (GetLastError()) {
118 while (ctx) |context| : (ctx = os.windows.crypt32.CertEnumCertificatesInStore(store, ctx)) {118 .FILE_NOT_FOUND => return error.FileNotFound,
119 var start = @intCast(u32, cb.bytes.items.len);119 else => |err| return w.unexpectedError(err),
120 try cb.bytes.appendSlice(gpa, context.pbCertEncoded[0..context.cbCertEncoded]);120 };
121 var parsed = Certificate.parse(.{121 defer _ = w.crypt32.CertCloseStore(store, 0);
122
123 var ctx = w.crypt32.CertEnumCertificatesInStore(store, null);
124 while (ctx) |context| : (ctx = w.crypt32.CertEnumCertificatesInStore(store, ctx)) {
125 const decoded_start = @intCast(u32, cb.bytes.items.len);
126 const encoded_cert = context.pbCertEncoded[0..context.cbCertEncoded];
127 try cb.bytes.appendSlice(gpa, encoded_cert);
128 const parsed_cert = try Certificate.parse(.{
122 .buffer = cb.bytes.items,129 .buffer = cb.bytes.items,
123 .index = start,130 .index = decoded_start,
124 }) catch {131 });
125 cb.bytes.items.len = start;132 const gop = try cb.map.getOrPutContext(gpa, parsed_cert.subject_slice, .{ .cb = cb });
126 continue;
127 };
128 const gop = try cb.map.getOrPutContext(gpa, parsed.subject_slice, .{ .cb = cb });
129 if (gop.found_existing) {133 if (gop.found_existing) {
130 cb.bytes.items.len = start;134 cb.bytes.items.len = decoded_start;
131 } else {135 } else {
132 gop.value_ptr.* = start;136 gop.value_ptr.* = decoded_start;
133 }137 }
134 }138 }
135 cb.bytes.shrinkAndFree(gpa, cb.bytes.items.len);139 cb.bytes.shrinkAndFree(gpa, cb.bytes.items.len);
...@@ -250,7 +254,6 @@ pub fn parseCert(cb: *Bundle, gpa: Allocator, decoded_start: u32, now_sec: i64)...@@ -250,7 +254,6 @@ pub fn parseCert(cb: *Bundle, gpa: Allocator, decoded_start: u32, now_sec: i64)
250const builtin = @import("builtin");254const builtin = @import("builtin");
251const std = @import("../../std.zig");255const std = @import("../../std.zig");
252const assert = std.debug.assert;256const assert = std.debug.assert;
253const os = std.os;
254const fs = std.fs;257const fs = std.fs;
255const mem = std.mem;258const mem = std.mem;
256const crypto = std.crypto;259const crypto = std.crypto;
lib/std/os/windows/crypt32.zig-22
...@@ -5,7 +5,6 @@ const DWORD = windows.DWORD;...@@ -5,7 +5,6 @@ const DWORD = windows.DWORD;
5const BYTE = windows.BYTE;5const BYTE = windows.BYTE;
6const LPCWSTR = windows.LPCWSTR;6const LPCWSTR = windows.LPCWSTR;
7const WINAPI = windows.WINAPI;7const WINAPI = windows.WINAPI;
8const GetLastError = windows.kernel32.GetLastError;
98
10pub const CERT_INFO = *opaque {};9pub const CERT_INFO = *opaque {};
11pub const HCERTSTORE = *opaque {};10pub const HCERTSTORE = *opaque {};
...@@ -21,32 +20,11 @@ pub extern "crypt32" fn CertOpenSystemStoreW(...@@ -21,32 +20,11 @@ pub extern "crypt32" fn CertOpenSystemStoreW(
21 _: ?*const anyopaque,20 _: ?*const anyopaque,
22 szSubsystemProtocol: LPCWSTR,21 szSubsystemProtocol: LPCWSTR,
23) callconv(WINAPI) ?HCERTSTORE;22) callconv(WINAPI) ?HCERTSTORE;
24pub fn certOpenSystemStoreW(
25 hProv: ?*const anyopaque,
26 szSubsystemProtocol: LPCWSTR,
27) !HCERTSTORE {
28 const value = CertOpenSystemStoreW(hProv, szSubsystemProtocol);
29 return if (value) |store|
30 store
31 else switch (GetLastError()) {
32 .FILE_NOT_FOUND => error.FileNotFound,
33 else => |err| windows.unexpectedError(err),
34 };
35}
3623
37pub extern "crypt32" fn CertCloseStore(24pub extern "crypt32" fn CertCloseStore(
38 hCertStore: HCERTSTORE,25 hCertStore: HCERTSTORE,
39 dwFlags: DWORD,26 dwFlags: DWORD,
40) callconv(WINAPI) BOOL;27) callconv(WINAPI) BOOL;
41pub fn certCloseStore(
42 hCertStore: HCERTSTORE,
43 dwFlags: DWORD,
44) !void {
45 const value = CertCloseStore(hCertStore, dwFlags);
46 if (value == 0) {
47 return windows.unexpectedError(GetLastError());
48 }
49}
5028
51pub extern "crypt32" fn CertEnumCertificatesInStore(29pub extern "crypt32" fn CertEnumCertificatesInStore(
52 hCertStore: HCERTSTORE,30 hCertStore: HCERTSTORE,