mirror of
https://github.com/ziglang/zig.git
synced 2026-02-21 16:54:52 +00:00
Merge remote-tracking branch 'origin/master' into llvm11
This commit is contained in:
commit
f9bd049c89
@ -38,7 +38,7 @@ pub fn build(b: *Builder) !void {
|
||||
const test_step = b.step("test", "Run all the tests");
|
||||
|
||||
var test_stage2 = b.addTest("src-self-hosted/test.zig");
|
||||
test_stage2.setBuildMode(.Debug); // note this is only the mode of the test harness
|
||||
test_stage2.setBuildMode(mode);
|
||||
test_stage2.addPackagePath("stage2_tests", "test/stage2/test.zig");
|
||||
|
||||
const fmt_build_zig = b.addFmt(&[_][]const u8{"build.zig"});
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const debug = std.debug;
|
||||
const assert = debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const debug = std.debug;
|
||||
const mem = std.mem;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// Does NOT look at the locale the way C89's toupper(3), isspace() et cetera does.
|
||||
// I could have taken only a u7 to make this clear, but it would be slower
|
||||
// It is my opinion that encodings other than UTF-8 should not be supported.
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const Stack = @import("atomic/stack.zig").Stack;
|
||||
pub const Queue = @import("atomic/queue.zig").Queue;
|
||||
pub const Int = @import("atomic/int.zig").Int;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
/// Thread-safe, lock-free integer
|
||||
pub fn Int(comptime T: type) type {
|
||||
return struct {
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const assert = std.debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const assert = std.debug.assert;
|
||||
const builtin = @import("builtin");
|
||||
const expect = std.testing.expect;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const assert = std.debug.assert;
|
||||
const testing = std.testing;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const builtin = @import("builtin");
|
||||
const std = @import("std.zig");
|
||||
const math = std.math;
|
||||
@ -153,7 +158,7 @@ pub fn BloomFilter(
|
||||
}
|
||||
|
||||
fn hashFunc(out: []u8, Ki: usize, in: []const u8) void {
|
||||
var st = std.crypto.gimli.Hash.init();
|
||||
var st = std.crypto.hash.Gimli.init(.{});
|
||||
st.update(std.mem.asBytes(&Ki));
|
||||
st.update(in);
|
||||
st.final(out);
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const StringHashMap = std.StringHashMap;
|
||||
const mem = std.mem;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const StringHashMap = std.StringHashMap;
|
||||
const mem = @import("mem.zig");
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const builtin = std.builtin;
|
||||
const io = std.io;
|
||||
@ -449,7 +454,33 @@ pub const Builder = struct {
|
||||
return null;
|
||||
},
|
||||
},
|
||||
.Int => panic("TODO integer options to build script", .{}),
|
||||
.Int => switch (entry.value.value) {
|
||||
.Flag => {
|
||||
warn("Expected -D{} to be an integer, but received a boolean.\n", .{name});
|
||||
self.markInvalidUserInput();
|
||||
return null;
|
||||
},
|
||||
.Scalar => |s| {
|
||||
const n = std.fmt.parseInt(T, s, 10) catch |err| switch (err) {
|
||||
error.Overflow => {
|
||||
warn("-D{} value {} cannot fit into type {}.\n", .{ name, s, @typeName(T) });
|
||||
self.markInvalidUserInput();
|
||||
return null;
|
||||
},
|
||||
else => {
|
||||
warn("Expected -D{} to be an integer of type {}.\n", .{ name, @typeName(T) });
|
||||
self.markInvalidUserInput();
|
||||
return null;
|
||||
},
|
||||
};
|
||||
return n;
|
||||
},
|
||||
.List => {
|
||||
warn("Expected -D{} to be an integer, but received a list.\n", .{name});
|
||||
self.markInvalidUserInput();
|
||||
return null;
|
||||
},
|
||||
},
|
||||
.Float => panic("TODO float options to build script", .{}),
|
||||
.Enum => switch (entry.value.value) {
|
||||
.Flag => {
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const build = std.build;
|
||||
const Step = build.Step;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
|
||||
const Allocator = std.mem.Allocator;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const build = @import("../build.zig");
|
||||
const Step = build.Step;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = std.builtin;
|
||||
const build = std.build;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const build = std.build;
|
||||
const Step = build.Step;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const build = @import("../build.zig");
|
||||
const Step = build.Step;
|
||||
@ -53,7 +58,7 @@ pub const WriteFileStep = struct {
|
||||
// TODO port the cache system from stage1 to zig std lib. Until then we use blake2b
|
||||
// directly and construct the path, and no "cache hit" detection happens; the files
|
||||
// are always written.
|
||||
var hash = std.crypto.Blake2b384.init();
|
||||
var hash = std.crypto.hash.blake2.Blake2b384.init(.{});
|
||||
|
||||
// Random bytes to make WriteFileStep unique. Refresh this with
|
||||
// new random bytes when WriteFileStep implementation is modified
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub usingnamespace @import("builtin");
|
||||
|
||||
/// Deprecated: use `std.Target`.
|
||||
@ -254,7 +259,6 @@ pub const TypeInfo = union(enum) {
|
||||
/// therefore must be kept in sync with the compiler implementation.
|
||||
pub const StructField = struct {
|
||||
name: []const u8,
|
||||
offset: ?comptime_int,
|
||||
field_type: type,
|
||||
default_value: anytype,
|
||||
};
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const builtin = std.builtin;
|
||||
const page_size = std.mem.page_size;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const SegmentedList = std.SegmentedList;
|
||||
const Token = std.c.Token;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const assert = std.debug.assert;
|
||||
const builtin = @import("builtin");
|
||||
@ -41,10 +46,11 @@ const mach_hdr = if (@sizeOf(usize) == 8) mach_header_64 else mach_header;
|
||||
/// on this operating system. However when building object files or libraries,
|
||||
/// the system libc won't be linked until the final executable. So we
|
||||
/// export a weak symbol here, to be overridden by the real one.
|
||||
pub extern "c" var _mh_execute_header: mach_hdr = undefined;
|
||||
var dummy_execute_header: mach_hdr = undefined;
|
||||
pub extern var _mh_execute_header: mach_hdr;
|
||||
comptime {
|
||||
if (std.Target.current.isDarwin()) {
|
||||
@export(_mh_execute_header, .{ .name = "_mh_execute_header", .linkage = .Weak });
|
||||
@export(dummy_execute_header, .{ .name = "_mh_execute_header", .linkage = .Weak });
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
usingnamespace std.c;
|
||||
extern "c" threadlocal var errno: c_int;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const pthread_mutex_t = extern struct {
|
||||
size: [__SIZEOF_PTHREAD_MUTEX_T]u8 align(4) = [_]u8{0} ** __SIZEOF_PTHREAD_MUTEX_T,
|
||||
};
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
usingnamespace std.c;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const pthread_mutex_t = extern struct {
|
||||
size: [__SIZEOF_PTHREAD_MUTEX_T]u8 align(@alignOf(usize)) = [_]u8{0} ** __SIZEOF_PTHREAD_MUTEX_T,
|
||||
};
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const pthread_mutex_t = extern struct {
|
||||
flags: u32 = 0,
|
||||
lock: i32 = 0,
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const pthread_mutex_t = extern struct {
|
||||
inner: usize = ~@as(usize, 0),
|
||||
};
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const builtin = @import("builtin");
|
||||
const std = @import("../std.zig");
|
||||
const maxInt = std.math.maxInt;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const builtin = @import("builtin");
|
||||
pub const pthread_mutex_t = extern struct {
|
||||
size: [__SIZEOF_PTHREAD_MUTEX_T]u8 align(@alignOf(usize)) = [_]u8{0} ** __SIZEOF_PTHREAD_MUTEX_T,
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = std.builtin;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const pthread_mutex_t = extern struct {
|
||||
inner: ?*c_void = null,
|
||||
};
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const mem = std.mem;
|
||||
const assert = std.debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const pthread_mutex_t = extern struct {
|
||||
__pthread_mutex_flag1: u16 = 0,
|
||||
__pthread_mutex_flag2: u8 = 0,
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const mem = std.mem;
|
||||
|
||||
|
||||
@ -1 +1,6 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub extern "c" fn _errno() *c_int;
|
||||
|
||||
@ -1,5 +1,10 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const Blake3 = std.crypto.Blake3;
|
||||
const Blake3 = std.crypto.hash.Blake3;
|
||||
const fs = std.fs;
|
||||
const base64 = std.base64;
|
||||
const ArrayList = std.ArrayList;
|
||||
@ -51,7 +56,7 @@ pub const CacheHash = struct {
|
||||
pub fn init(allocator: *Allocator, dir: fs.Dir, manifest_dir_path: []const u8) !CacheHash {
|
||||
return CacheHash{
|
||||
.allocator = allocator,
|
||||
.blake3 = Blake3.init(),
|
||||
.blake3 = Blake3.init(.{}),
|
||||
.manifest_dir = try dir.makeOpenPath(manifest_dir_path, .{}),
|
||||
.manifest_file = null,
|
||||
.manifest_dirty = false,
|
||||
@ -132,7 +137,7 @@ pub const CacheHash = struct {
|
||||
|
||||
base64_encoder.encode(self.b64_digest[0..], &bin_digest);
|
||||
|
||||
self.blake3 = Blake3.init();
|
||||
self.blake3 = Blake3.init(.{});
|
||||
self.blake3.update(&bin_digest);
|
||||
|
||||
const manifest_file_path = try fmt.allocPrint(self.allocator, "{}.txt", .{self.b64_digest});
|
||||
@ -251,7 +256,7 @@ pub const CacheHash = struct {
|
||||
// cache miss
|
||||
// keep the manifest file open
|
||||
// reset the hash
|
||||
self.blake3 = Blake3.init();
|
||||
self.blake3 = Blake3.init(.{});
|
||||
self.blake3.update(&bin_digest);
|
||||
|
||||
// Remove files not in the initial hash
|
||||
@ -299,7 +304,7 @@ pub const CacheHash = struct {
|
||||
|
||||
// Hash while reading from disk, to keep the contents in the cpu cache while
|
||||
// doing hashing.
|
||||
var blake3 = Blake3.init();
|
||||
var blake3 = Blake3.init(.{});
|
||||
var off: usize = 0;
|
||||
while (true) {
|
||||
// give me everything you've got, captain
|
||||
@ -429,7 +434,7 @@ pub const CacheHash = struct {
|
||||
};
|
||||
|
||||
fn hashFile(file: fs.File, bin_digest: []u8) !void {
|
||||
var blake3 = Blake3.init();
|
||||
var blake3 = Blake3.init(.{});
|
||||
var buf: [1024]u8 = undefined;
|
||||
|
||||
while (true) {
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const cstr = std.cstr;
|
||||
const unicode = std.unicode;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const builtin = @import("builtin");
|
||||
const std = @import("std.zig");
|
||||
const io = std.io;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const mem = std.mem;
|
||||
|
||||
|
||||
@ -1,57 +1,70 @@
|
||||
pub const Md5 = @import("crypto/md5.zig").Md5;
|
||||
pub const Sha1 = @import("crypto/sha1.zig").Sha1;
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
|
||||
const sha2 = @import("crypto/sha2.zig");
|
||||
pub const Sha224 = sha2.Sha224;
|
||||
pub const Sha256 = sha2.Sha256;
|
||||
pub const Sha384 = sha2.Sha384;
|
||||
pub const Sha512 = sha2.Sha512;
|
||||
/// Hash functions.
|
||||
pub const hash = struct {
|
||||
pub const Md5 = @import("crypto/md5.zig").Md5;
|
||||
pub const Sha1 = @import("crypto/sha1.zig").Sha1;
|
||||
pub const sha2 = @import("crypto/sha2.zig");
|
||||
pub const sha3 = @import("crypto/sha3.zig");
|
||||
pub const blake2 = @import("crypto/blake2.zig");
|
||||
pub const Blake3 = @import("crypto/blake3.zig").Blake3;
|
||||
pub const Gimli = @import("crypto/gimli.zig").Hash;
|
||||
};
|
||||
|
||||
const sha3 = @import("crypto/sha3.zig");
|
||||
pub const Sha3_224 = sha3.Sha3_224;
|
||||
pub const Sha3_256 = sha3.Sha3_256;
|
||||
pub const Sha3_384 = sha3.Sha3_384;
|
||||
pub const Sha3_512 = sha3.Sha3_512;
|
||||
|
||||
pub const gimli = @import("crypto/gimli.zig");
|
||||
|
||||
const blake2 = @import("crypto/blake2.zig");
|
||||
pub const Blake2s224 = blake2.Blake2s224;
|
||||
pub const Blake2s256 = blake2.Blake2s256;
|
||||
pub const Blake2b384 = blake2.Blake2b384;
|
||||
pub const Blake2b512 = blake2.Blake2b512;
|
||||
|
||||
pub const Blake3 = @import("crypto/blake3.zig").Blake3;
|
||||
|
||||
const hmac = @import("crypto/hmac.zig");
|
||||
pub const HmacMd5 = hmac.HmacMd5;
|
||||
pub const HmacSha1 = hmac.HmacSha1;
|
||||
pub const HmacSha256 = hmac.HmacSha256;
|
||||
pub const HmacBlake2s256 = hmac.HmacBlake2s256;
|
||||
|
||||
pub const chacha20 = @import("crypto/chacha20.zig");
|
||||
pub const chaCha20IETF = chacha20.chaCha20IETF;
|
||||
pub const chaCha20With64BitNonce = chacha20.chaCha20With64BitNonce;
|
||||
pub const xChaCha20IETF = chacha20.xChaCha20IETF;
|
||||
|
||||
pub const Poly1305 = @import("crypto/poly1305.zig").Poly1305;
|
||||
|
||||
const import_aes = @import("crypto/aes.zig");
|
||||
pub const AES128 = import_aes.AES128;
|
||||
pub const AES256 = import_aes.AES256;
|
||||
|
||||
pub const Curve25519 = @import("crypto/25519/curve25519.zig").Curve25519;
|
||||
pub const Ed25519 = @import("crypto/25519/ed25519.zig").Ed25519;
|
||||
pub const Edwards25519 = @import("crypto/25519/edwards25519.zig").Edwards25519;
|
||||
pub const X25519 = @import("crypto/25519/x25519.zig").X25519;
|
||||
pub const Ristretto255 = @import("crypto/25519/ristretto255.zig").Ristretto255;
|
||||
/// Authentication (MAC) functions.
|
||||
pub const auth = struct {
|
||||
pub const hmac = @import("crypto/hmac.zig");
|
||||
};
|
||||
|
||||
/// Authenticated Encryption with Associated Data
|
||||
pub const aead = struct {
|
||||
pub const Gimli = gimli.Aead;
|
||||
const chacha20 = @import("crypto/chacha20.zig");
|
||||
|
||||
pub const Gimli = @import("crypto/gimli.zig").Aead;
|
||||
pub const ChaCha20Poly1305 = chacha20.Chacha20Poly1305;
|
||||
pub const XChaCha20Poly1305 = chacha20.XChacha20Poly1305;
|
||||
};
|
||||
|
||||
/// MAC functions requiring single-use secret keys.
|
||||
pub const onetimeauth = struct {
|
||||
pub const Poly1305 = @import("crypto/poly1305.zig").Poly1305;
|
||||
};
|
||||
|
||||
/// Core functions, that should rarely be used directly by applications.
|
||||
pub const core = struct {
|
||||
pub const aes = @import("crypto/aes.zig");
|
||||
pub const Gimli = @import("crypto/gimli.zig").State;
|
||||
};
|
||||
|
||||
/// Elliptic-curve arithmetic.
|
||||
pub const ecc = struct {
|
||||
pub const Curve25519 = @import("crypto/25519/curve25519.zig").Curve25519;
|
||||
pub const Edwards25519 = @import("crypto/25519/edwards25519.zig").Edwards25519;
|
||||
pub const Ristretto255 = @import("crypto/25519/ristretto255.zig").Ristretto255;
|
||||
};
|
||||
|
||||
/// Diffie-Hellman key exchange functions.
|
||||
pub const dh = struct {
|
||||
pub const X25519 = @import("crypto/25519/x25519.zig").X25519;
|
||||
};
|
||||
|
||||
/// Digital signature functions.
|
||||
pub const sign = struct {
|
||||
pub const Ed25519 = @import("crypto/25519/ed25519.zig").Ed25519;
|
||||
};
|
||||
|
||||
/// Stream ciphers. These do not provide any kind of authentication.
|
||||
/// Most applications should be using AEAD constructions instead of stream ciphers directly.
|
||||
pub const stream = struct {
|
||||
pub const ChaCha20IETF = @import("crypto/chacha20.zig").ChaCha20IETF;
|
||||
pub const XChaCha20IETF = @import("crypto/chacha20.zig").XChaCha20IETF;
|
||||
pub const ChaCha20With64BitNonce = @import("crypto/chacha20.zig").ChaCha20With64BitNonce;
|
||||
};
|
||||
|
||||
const std = @import("std.zig");
|
||||
pub const randomBytes = std.os.getrandom;
|
||||
|
||||
@ -78,27 +91,32 @@ test "crypto" {
|
||||
|
||||
test "issue #4532: no index out of bounds" {
|
||||
const types = [_]type{
|
||||
Md5,
|
||||
Sha1,
|
||||
Sha224,
|
||||
Sha256,
|
||||
Sha384,
|
||||
Sha512,
|
||||
Blake2s224,
|
||||
Blake2s256,
|
||||
Blake2b384,
|
||||
Blake2b512,
|
||||
hash.Md5,
|
||||
hash.Sha1,
|
||||
hash.sha2.Sha224,
|
||||
hash.sha2.Sha256,
|
||||
hash.sha2.Sha384,
|
||||
hash.sha2.Sha512,
|
||||
hash.sha3.Sha3_224,
|
||||
hash.sha3.Sha3_256,
|
||||
hash.sha3.Sha3_384,
|
||||
hash.sha3.Sha3_512,
|
||||
hash.blake2.Blake2s224,
|
||||
hash.blake2.Blake2s256,
|
||||
hash.blake2.Blake2b384,
|
||||
hash.blake2.Blake2b512,
|
||||
hash.Gimli,
|
||||
};
|
||||
|
||||
inline for (types) |Hasher| {
|
||||
var block = [_]u8{'#'} ** Hasher.block_length;
|
||||
var out1: [Hasher.digest_length]u8 = undefined;
|
||||
var out2: [Hasher.digest_length]u8 = undefined;
|
||||
|
||||
var h = Hasher.init();
|
||||
const h0 = Hasher.init(.{});
|
||||
var h = h0;
|
||||
h.update(block[0..]);
|
||||
h.final(out1[0..]);
|
||||
h.reset();
|
||||
h = h0;
|
||||
h.update(block[0..1]);
|
||||
h.update(block[1..]);
|
||||
h.final(out2[0..]);
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
|
||||
/// Group operations over Curve25519.
|
||||
|
||||
@ -1,7 +1,12 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const fmt = std.fmt;
|
||||
const mem = std.mem;
|
||||
const Sha512 = std.crypto.Sha512;
|
||||
const Sha512 = std.crypto.hash.sha2.Sha512;
|
||||
|
||||
/// Ed25519 (EdDSA) signatures.
|
||||
pub const Ed25519 = struct {
|
||||
@ -28,7 +33,7 @@ pub const Ed25519 = struct {
|
||||
/// from which the actual secret is derived.
|
||||
pub fn createKeyPair(seed: [seed_length]u8) ![keypair_length]u8 {
|
||||
var az: [Sha512.digest_length]u8 = undefined;
|
||||
var h = Sha512.init();
|
||||
var h = Sha512.init(.{});
|
||||
h.update(&seed);
|
||||
h.final(&az);
|
||||
const p = try Curve.basePoint.clampedMul(az[0..32].*);
|
||||
@ -51,11 +56,11 @@ pub const Ed25519 = struct {
|
||||
pub fn sign(msg: []const u8, key_pair: [keypair_length]u8, noise: ?[noise_length]u8) ![signature_length]u8 {
|
||||
const public_key = key_pair[32..];
|
||||
var az: [Sha512.digest_length]u8 = undefined;
|
||||
var h = Sha512.init();
|
||||
var h = Sha512.init(.{});
|
||||
h.update(key_pair[0..seed_length]);
|
||||
h.final(&az);
|
||||
|
||||
h = Sha512.init();
|
||||
h = Sha512.init(.{});
|
||||
if (noise) |*z| {
|
||||
h.update(z);
|
||||
}
|
||||
@ -69,7 +74,7 @@ pub const Ed25519 = struct {
|
||||
var sig: [signature_length]u8 = undefined;
|
||||
mem.copy(u8, sig[0..32], &r.toBytes());
|
||||
mem.copy(u8, sig[32..], public_key);
|
||||
h = Sha512.init();
|
||||
h = Sha512.init(.{});
|
||||
h.update(&sig);
|
||||
h.update(msg);
|
||||
var hram64: [Sha512.digest_length]u8 = undefined;
|
||||
@ -93,7 +98,7 @@ pub const Ed25519 = struct {
|
||||
const a = try Curve.fromBytes(public_key);
|
||||
try a.rejectIdentity();
|
||||
|
||||
var h = Sha512.init();
|
||||
var h = Sha512.init(.{});
|
||||
h.update(r);
|
||||
h.update(&public_key);
|
||||
h.update(msg);
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const fmt = std.fmt;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const readIntLittle = std.mem.readIntLittle;
|
||||
const writeIntLittle = std.mem.writeIntLittle;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const fmt = std.fmt;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const mem = std.mem;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const mem = std.mem;
|
||||
const fmt = std.fmt;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// Based on Go stdlib implementation
|
||||
|
||||
const std = @import("../std.zig");
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// zig run benchmark.zig --release-fast --override-lib-dir ..
|
||||
|
||||
const builtin = @import("builtin");
|
||||
@ -17,20 +22,20 @@ const Crypto = struct {
|
||||
};
|
||||
|
||||
const hashes = [_]Crypto{
|
||||
Crypto{ .ty = crypto.Md5, .name = "md5" },
|
||||
Crypto{ .ty = crypto.Sha1, .name = "sha1" },
|
||||
Crypto{ .ty = crypto.Sha256, .name = "sha256" },
|
||||
Crypto{ .ty = crypto.Sha512, .name = "sha512" },
|
||||
Crypto{ .ty = crypto.Sha3_256, .name = "sha3-256" },
|
||||
Crypto{ .ty = crypto.Sha3_512, .name = "sha3-512" },
|
||||
Crypto{ .ty = crypto.gimli.Hash, .name = "gimli-hash" },
|
||||
Crypto{ .ty = crypto.Blake2s256, .name = "blake2s" },
|
||||
Crypto{ .ty = crypto.Blake2b512, .name = "blake2b" },
|
||||
Crypto{ .ty = crypto.Blake3, .name = "blake3" },
|
||||
Crypto{ .ty = crypto.hash.Md5, .name = "md5" },
|
||||
Crypto{ .ty = crypto.hash.Sha1, .name = "sha1" },
|
||||
Crypto{ .ty = crypto.hash.sha2.Sha256, .name = "sha256" },
|
||||
Crypto{ .ty = crypto.hash.sha2.Sha512, .name = "sha512" },
|
||||
Crypto{ .ty = crypto.hash.sha3.Sha3_256, .name = "sha3-256" },
|
||||
Crypto{ .ty = crypto.hash.sha3.Sha3_512, .name = "sha3-512" },
|
||||
Crypto{ .ty = crypto.hash.Gimli, .name = "gimli-hash" },
|
||||
Crypto{ .ty = crypto.hash.blake2.Blake2s256, .name = "blake2s" },
|
||||
Crypto{ .ty = crypto.hash.blake2.Blake2b512, .name = "blake2b" },
|
||||
Crypto{ .ty = crypto.hash.Blake3, .name = "blake3" },
|
||||
};
|
||||
|
||||
pub fn benchmarkHash(comptime Hash: anytype, comptime bytes: comptime_int) !u64 {
|
||||
var h = Hash.init();
|
||||
var h = Hash.init(.{});
|
||||
|
||||
var block: [Hash.digest_length]u8 = undefined;
|
||||
prng.random.bytes(block[0..]);
|
||||
@ -50,19 +55,20 @@ pub fn benchmarkHash(comptime Hash: anytype, comptime bytes: comptime_int) !u64
|
||||
}
|
||||
|
||||
const macs = [_]Crypto{
|
||||
Crypto{ .ty = crypto.Poly1305, .name = "poly1305" },
|
||||
Crypto{ .ty = crypto.HmacMd5, .name = "hmac-md5" },
|
||||
Crypto{ .ty = crypto.HmacSha1, .name = "hmac-sha1" },
|
||||
Crypto{ .ty = crypto.HmacSha256, .name = "hmac-sha256" },
|
||||
Crypto{ .ty = crypto.onetimeauth.Poly1305, .name = "poly1305" },
|
||||
Crypto{ .ty = crypto.auth.hmac.HmacMd5, .name = "hmac-md5" },
|
||||
Crypto{ .ty = crypto.auth.hmac.HmacSha1, .name = "hmac-sha1" },
|
||||
Crypto{ .ty = crypto.auth.hmac.sha2.HmacSha256, .name = "hmac-sha256" },
|
||||
Crypto{ .ty = crypto.auth.hmac.sha2.HmacSha512, .name = "hmac-sha512" },
|
||||
};
|
||||
|
||||
pub fn benchmarkMac(comptime Mac: anytype, comptime bytes: comptime_int) !u64 {
|
||||
std.debug.assert(32 >= Mac.mac_length and 32 >= Mac.minimum_key_length);
|
||||
std.debug.assert(64 >= Mac.mac_length and 32 >= Mac.minimum_key_length);
|
||||
|
||||
var in: [1 * MiB]u8 = undefined;
|
||||
prng.random.bytes(in[0..]);
|
||||
|
||||
var key: [32]u8 = undefined;
|
||||
var key: [64]u8 = undefined;
|
||||
prng.random.bytes(key[0..]);
|
||||
|
||||
var offset: usize = 0;
|
||||
@ -79,7 +85,7 @@ pub fn benchmarkMac(comptime Mac: anytype, comptime bytes: comptime_int) !u64 {
|
||||
return throughput;
|
||||
}
|
||||
|
||||
const exchanges = [_]Crypto{Crypto{ .ty = crypto.X25519, .name = "x25519" }};
|
||||
const exchanges = [_]Crypto{Crypto{ .ty = crypto.dh.X25519, .name = "x25519" }};
|
||||
|
||||
pub fn benchmarkKeyExchange(comptime DhKeyExchange: anytype, comptime exchange_count: comptime_int) !u64 {
|
||||
std.debug.assert(DhKeyExchange.minimum_key_length >= DhKeyExchange.secret_length);
|
||||
@ -106,7 +112,7 @@ pub fn benchmarkKeyExchange(comptime DhKeyExchange: anytype, comptime exchange_c
|
||||
return throughput;
|
||||
}
|
||||
|
||||
const signatures = [_]Crypto{Crypto{ .ty = crypto.Ed25519, .name = "ed25519" }};
|
||||
const signatures = [_]Crypto{Crypto{ .ty = crypto.sign.Ed25519, .name = "ed25519" }};
|
||||
|
||||
pub fn benchmarkSignatures(comptime Signature: anytype, comptime signatures_count: comptime_int) !u64 {
|
||||
var seed: [Signature.seed_length]u8 = undefined;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const mem = @import("../mem.zig");
|
||||
const builtin = @import("builtin");
|
||||
const debug = @import("../debug.zig");
|
||||
@ -35,6 +40,7 @@ pub fn Blake2s(comptime out_len: usize) type {
|
||||
const Self = @This();
|
||||
pub const block_length = 64;
|
||||
pub const digest_length = out_len / 8;
|
||||
pub const Options = struct { key: ?[]const u8 = null, salt: ?[8]u8 = null, context: ?[8]u8 = null };
|
||||
|
||||
const iv = [8]u32{
|
||||
0x6A09E667,
|
||||
@ -66,42 +72,36 @@ pub fn Blake2s(comptime out_len: usize) type {
|
||||
buf: [64]u8,
|
||||
buf_len: u8,
|
||||
|
||||
key: []const u8,
|
||||
|
||||
pub fn init() Self {
|
||||
return init_keyed("");
|
||||
}
|
||||
|
||||
pub fn init_keyed(key: []const u8) Self {
|
||||
pub fn init(options: Options) Self {
|
||||
debug.assert(8 <= out_len and out_len <= 512);
|
||||
|
||||
var s: Self = undefined;
|
||||
s.key = key;
|
||||
s.reset();
|
||||
return s;
|
||||
}
|
||||
|
||||
pub fn reset(d: *Self) void {
|
||||
var d: Self = undefined;
|
||||
mem.copy(u32, d.h[0..], iv[0..]);
|
||||
|
||||
const key_len = if (options.key) |key| key.len else 0;
|
||||
// default parameters
|
||||
d.h[0] ^= 0x01010000 ^ @truncate(u32, d.key.len << 8) ^ @intCast(u32, out_len >> 3);
|
||||
d.h[0] ^= 0x01010000 ^ @truncate(u32, key_len << 8) ^ @intCast(u32, out_len >> 3);
|
||||
d.t = 0;
|
||||
d.buf_len = 0;
|
||||
|
||||
if (d.key.len > 0) {
|
||||
mem.set(u8, d.buf[d.key.len..], 0);
|
||||
d.update(d.key);
|
||||
if (options.salt) |salt| {
|
||||
d.h[4] ^= mem.readIntLittle(u32, salt[0..4]);
|
||||
d.h[5] ^= mem.readIntLittle(u32, salt[4..8]);
|
||||
}
|
||||
if (options.context) |context| {
|
||||
d.h[6] ^= mem.readIntLittle(u32, context[0..4]);
|
||||
d.h[7] ^= mem.readIntLittle(u32, context[4..8]);
|
||||
}
|
||||
if (key_len > 0) {
|
||||
mem.set(u8, d.buf[key_len..], 0);
|
||||
d.update(options.key.?);
|
||||
d.buf_len = 64;
|
||||
}
|
||||
return d;
|
||||
}
|
||||
|
||||
pub fn hash(b: []const u8, out: []u8) void {
|
||||
Self.hash_keyed("", b, out);
|
||||
}
|
||||
|
||||
pub fn hash_keyed(key: []const u8, b: []const u8, out: []u8) void {
|
||||
var d = Self.init_keyed(key);
|
||||
pub fn hash(b: []const u8, out: []u8, options: Options) void {
|
||||
var d = Self.init(options);
|
||||
d.update(b);
|
||||
d.final(out);
|
||||
}
|
||||
@ -210,7 +210,7 @@ test "blake2s224 single" {
|
||||
}
|
||||
|
||||
test "blake2s224 streaming" {
|
||||
var h = Blake2s224.init();
|
||||
var h = Blake2s224.init(.{});
|
||||
var out: [28]u8 = undefined;
|
||||
|
||||
const h1 = "1fa1291e65248b37b3433475b2a0dd63d54a11ecc4e3e034e7bc1ef4";
|
||||
@ -220,12 +220,12 @@ test "blake2s224 streaming" {
|
||||
|
||||
const h2 = "0b033fc226df7abde29f67a05d3dc62cf271ef3dfea4d387407fbd55";
|
||||
|
||||
h.reset();
|
||||
h = Blake2s224.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2s224.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -234,16 +234,29 @@ test "blake2s224 streaming" {
|
||||
|
||||
const h3 = "557381a78facd2b298640f4e32113e58967d61420af1aa939d0cfe01";
|
||||
|
||||
h.reset();
|
||||
h = Blake2s224.init(.{});
|
||||
h.update("a" ** 32);
|
||||
h.update("b" ** 32);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2s224.init(.{});
|
||||
h.update("a" ** 32 ++ "b" ** 32);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
|
||||
const h4 = "a4d6a9d253441b80e5dfd60a04db169ffab77aec56a2855c402828c3";
|
||||
|
||||
h = Blake2s224.init(.{ .context = [_]u8{0x69} ** 8, .salt = [_]u8{0x42} ** 8 });
|
||||
h.update("a" ** 32);
|
||||
h.update("b" ** 32);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h4, out[0..]);
|
||||
|
||||
h = Blake2s224.init(.{ .context = [_]u8{0x69} ** 8, .salt = [_]u8{0x42} ** 8 });
|
||||
h.update("a" ** 32 ++ "b" ** 32);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h4, out[0..]);
|
||||
}
|
||||
|
||||
test "comptime blake2s224" {
|
||||
@ -256,7 +269,7 @@ test "comptime blake2s224" {
|
||||
|
||||
htest.assertEqualHash(Blake2s224, h1, block[0..]);
|
||||
|
||||
var h = Blake2s224.init();
|
||||
var h = Blake2s224.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
|
||||
@ -279,7 +292,7 @@ test "blake2s256 single" {
|
||||
}
|
||||
|
||||
test "blake2s256 streaming" {
|
||||
var h = Blake2s256.init();
|
||||
var h = Blake2s256.init(.{});
|
||||
var out: [32]u8 = undefined;
|
||||
|
||||
const h1 = "69217a3079908094e11121d042354a7c1f55b6482ca1a51e1b250dfd1ed0eef9";
|
||||
@ -289,12 +302,12 @@ test "blake2s256 streaming" {
|
||||
|
||||
const h2 = "508c5e8c327c14e2e1a72ba34eeb452f37458b209ed63a294d999b4c86675982";
|
||||
|
||||
h.reset();
|
||||
h = Blake2s256.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2s256.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -303,13 +316,13 @@ test "blake2s256 streaming" {
|
||||
|
||||
const h3 = "8d8711dade07a6b92b9a3ea1f40bee9b2c53ff3edd2a273dec170b0163568977";
|
||||
|
||||
h.reset();
|
||||
h = Blake2s256.init(.{});
|
||||
h.update("a" ** 32);
|
||||
h.update("b" ** 32);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2s256.init(.{});
|
||||
h.update("a" ** 32 ++ "b" ** 32);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
@ -321,16 +334,16 @@ test "blake2s256 keyed" {
|
||||
const h1 = "10f918da4d74fab3302e48a5d67d03804b1ec95372a62a0f33b7c9fa28ba1ae6";
|
||||
const key = "secret_key";
|
||||
|
||||
Blake2s256.hash_keyed(key, "a" ** 64 ++ "b" ** 64, &out);
|
||||
Blake2s256.hash("a" ** 64 ++ "b" ** 64, &out, .{ .key = key });
|
||||
htest.assertEqual(h1, out[0..]);
|
||||
|
||||
var h = Blake2s256.init_keyed(key);
|
||||
var h = Blake2s256.init(.{ .key = key });
|
||||
h.update("a" ** 64 ++ "b" ** 64);
|
||||
h.final(out[0..]);
|
||||
|
||||
htest.assertEqual(h1, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2s256.init(.{ .key = key });
|
||||
h.update("a" ** 64);
|
||||
h.update("b" ** 64);
|
||||
h.final(out[0..]);
|
||||
@ -348,7 +361,7 @@ test "comptime blake2s256" {
|
||||
|
||||
htest.assertEqualHash(Blake2s256, h1, block[0..]);
|
||||
|
||||
var h = Blake2s256.init();
|
||||
var h = Blake2s256.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
|
||||
@ -359,6 +372,7 @@ test "comptime blake2s256" {
|
||||
/////////////////////
|
||||
// Blake2b
|
||||
|
||||
pub const Blake2b256 = Blake2b(256);
|
||||
pub const Blake2b384 = Blake2b(384);
|
||||
pub const Blake2b512 = Blake2b(512);
|
||||
|
||||
@ -367,6 +381,7 @@ pub fn Blake2b(comptime out_len: usize) type {
|
||||
const Self = @This();
|
||||
pub const block_length = 128;
|
||||
pub const digest_length = out_len / 8;
|
||||
pub const Options = struct { key: ?[]const u8 = null, salt: ?[16]u8 = null, context: ?[16]u8 = null };
|
||||
|
||||
const iv = [8]u64{
|
||||
0x6a09e667f3bcc908,
|
||||
@ -400,42 +415,36 @@ pub fn Blake2b(comptime out_len: usize) type {
|
||||
buf: [128]u8,
|
||||
buf_len: u8,
|
||||
|
||||
key: []const u8,
|
||||
|
||||
pub fn init() Self {
|
||||
return init_keyed("");
|
||||
}
|
||||
|
||||
pub fn init_keyed(key: []const u8) Self {
|
||||
pub fn init(options: Options) Self {
|
||||
debug.assert(8 <= out_len and out_len <= 512);
|
||||
|
||||
var s: Self = undefined;
|
||||
s.key = key;
|
||||
s.reset();
|
||||
return s;
|
||||
}
|
||||
|
||||
pub fn reset(d: *Self) void {
|
||||
var d: Self = undefined;
|
||||
mem.copy(u64, d.h[0..], iv[0..]);
|
||||
|
||||
const key_len = if (options.key) |key| key.len else 0;
|
||||
// default parameters
|
||||
d.h[0] ^= 0x01010000 ^ (d.key.len << 8) ^ (out_len >> 3);
|
||||
d.h[0] ^= 0x01010000 ^ (key_len << 8) ^ (out_len >> 3);
|
||||
d.t = 0;
|
||||
d.buf_len = 0;
|
||||
|
||||
if (d.key.len > 0) {
|
||||
mem.set(u8, d.buf[d.key.len..], 0);
|
||||
d.update(d.key);
|
||||
if (options.salt) |salt| {
|
||||
d.h[4] ^= mem.readIntLittle(u64, salt[0..8]);
|
||||
d.h[5] ^= mem.readIntLittle(u64, salt[8..16]);
|
||||
}
|
||||
if (options.context) |context| {
|
||||
d.h[6] ^= mem.readIntLittle(u64, context[0..8]);
|
||||
d.h[7] ^= mem.readIntLittle(u64, context[8..16]);
|
||||
}
|
||||
if (key_len > 0) {
|
||||
mem.set(u8, d.buf[key_len..], 0);
|
||||
d.update(options.key.?);
|
||||
d.buf_len = 128;
|
||||
}
|
||||
return d;
|
||||
}
|
||||
|
||||
pub fn hash(b: []const u8, out: []u8) void {
|
||||
Self.hash_keyed("", b, out);
|
||||
}
|
||||
|
||||
pub fn hash_keyed(key: []const u8, b: []const u8, out: []u8) void {
|
||||
var d = Self.init_keyed(key);
|
||||
pub fn hash(b: []const u8, out: []u8, options: Options) void {
|
||||
var d = Self.init(options);
|
||||
d.update(b);
|
||||
d.final(out);
|
||||
}
|
||||
@ -542,7 +551,7 @@ test "blake2b384 single" {
|
||||
}
|
||||
|
||||
test "blake2b384 streaming" {
|
||||
var h = Blake2b384.init();
|
||||
var h = Blake2b384.init(.{});
|
||||
var out: [48]u8 = undefined;
|
||||
|
||||
const h1 = "b32811423377f52d7862286ee1a72ee540524380fda1724a6f25d7978c6fd3244a6caf0498812673c5e05ef583825100";
|
||||
@ -552,12 +561,12 @@ test "blake2b384 streaming" {
|
||||
|
||||
const h2 = "6f56a82c8e7ef526dfe182eb5212f7db9df1317e57815dbda46083fc30f54ee6c66ba83be64b302d7cba6ce15bb556f4";
|
||||
|
||||
h.reset();
|
||||
h = Blake2b384.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2b384.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -566,16 +575,36 @@ test "blake2b384 streaming" {
|
||||
|
||||
const h3 = "b7283f0172fecbbd7eca32ce10d8a6c06b453cb3cf675b33eb4246f0da2bb94a6c0bdd6eec0b5fd71ec4fd51be80bf4c";
|
||||
|
||||
h.reset();
|
||||
h = Blake2b384.init(.{});
|
||||
h.update("a" ** 64 ++ "b" ** 64);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2b384.init(.{});
|
||||
h.update("a" ** 64);
|
||||
h.update("b" ** 64);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
|
||||
h = Blake2b384.init(.{});
|
||||
h.update("a" ** 64);
|
||||
h.update("b" ** 64);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
|
||||
const h4 = "934c48fcb197031c71f583d92f98703510805e72142e0b46f5752d1e971bc86c355d556035613ff7a4154b4de09dac5c";
|
||||
|
||||
h = Blake2b384.init(.{ .context = [_]u8{0x69} ** 16, .salt = [_]u8{0x42} ** 16 });
|
||||
h.update("a" ** 64);
|
||||
h.update("b" ** 64);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h4, out[0..]);
|
||||
|
||||
h = Blake2b384.init(.{ .context = [_]u8{0x69} ** 16, .salt = [_]u8{0x42} ** 16 });
|
||||
h.update("a" ** 64);
|
||||
h.update("b" ** 64);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h4, out[0..]);
|
||||
}
|
||||
|
||||
test "comptime blake2b384" {
|
||||
@ -588,7 +617,7 @@ test "comptime blake2b384" {
|
||||
|
||||
htest.assertEqualHash(Blake2b384, h1, block[0..]);
|
||||
|
||||
var h = Blake2b384.init();
|
||||
var h = Blake2b384.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
|
||||
@ -611,7 +640,7 @@ test "blake2b512 single" {
|
||||
}
|
||||
|
||||
test "blake2b512 streaming" {
|
||||
var h = Blake2b512.init();
|
||||
var h = Blake2b512.init(.{});
|
||||
var out: [64]u8 = undefined;
|
||||
|
||||
const h1 = "786a02f742015903c6c6fd852552d272912f4740e15847618a86e217f71f5419d25e1031afee585313896444934eb04b903a685b1448b755d56f701afe9be2ce";
|
||||
@ -621,12 +650,12 @@ test "blake2b512 streaming" {
|
||||
|
||||
const h2 = "ba80a53f981c4d0d6a2797b69f12f6e94c212f14685ac4b74b12bb6fdbffa2d17d87c5392aab792dc252d5de4533cc9518d38aa8dbf1925ab92386edd4009923";
|
||||
|
||||
h.reset();
|
||||
h = Blake2b512.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2b512.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -635,12 +664,12 @@ test "blake2b512 streaming" {
|
||||
|
||||
const h3 = "049980af04d6a2cf16b4b49793c3ed7e40732073788806f2c989ebe9547bda0541d63abe298ec8955d08af48ae731f2e8a0bd6d201655a5473b4aa79d211b920";
|
||||
|
||||
h.reset();
|
||||
h = Blake2b512.init(.{});
|
||||
h.update("a" ** 64 ++ "b" ** 64);
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h3, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2b512.init(.{});
|
||||
h.update("a" ** 64);
|
||||
h.update("b" ** 64);
|
||||
h.final(out[0..]);
|
||||
@ -653,16 +682,16 @@ test "blake2b512 keyed" {
|
||||
const h1 = "8a978060ccaf582f388f37454363071ac9a67e3a704585fd879fb8a419a447e389c7c6de790faa20a7a7dccf197de736bc5b40b98a930b36df5bee7555750c4d";
|
||||
const key = "secret_key";
|
||||
|
||||
Blake2b512.hash_keyed(key, "a" ** 64 ++ "b" ** 64, &out);
|
||||
Blake2b512.hash("a" ** 64 ++ "b" ** 64, &out, .{ .key = key });
|
||||
htest.assertEqual(h1, out[0..]);
|
||||
|
||||
var h = Blake2b512.init_keyed(key);
|
||||
var h = Blake2b512.init(.{ .key = key });
|
||||
h.update("a" ** 64 ++ "b" ** 64);
|
||||
h.final(out[0..]);
|
||||
|
||||
htest.assertEqual(h1, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Blake2b512.init(.{ .key = key });
|
||||
h.update("a" ** 64);
|
||||
h.update("b" ** 64);
|
||||
h.final(out[0..]);
|
||||
@ -680,7 +709,7 @@ test "comptime blake2b512" {
|
||||
|
||||
htest.assertEqualHash(Blake2b512, h1, block[0..]);
|
||||
|
||||
var h = Blake2b512.init();
|
||||
var h = Blake2b512.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// Translated from BLAKE3 reference implementation.
|
||||
// Source: https://github.com/BLAKE3-team/BLAKE3
|
||||
|
||||
@ -274,6 +279,9 @@ fn parent_cv(
|
||||
|
||||
/// An incremental hasher that can accept any number of writes.
|
||||
pub const Blake3 = struct {
|
||||
pub const Options = struct { key: ?[KEY_LEN]u8 = null };
|
||||
pub const KdfOptions = struct {};
|
||||
|
||||
chunk_state: ChunkState,
|
||||
key: [8]u32,
|
||||
cv_stack: [54][8]u32 = undefined, // Space for 54 subtree chaining values:
|
||||
@ -291,21 +299,20 @@ pub const Blake3 = struct {
|
||||
};
|
||||
}
|
||||
|
||||
/// Construct a new `Blake3` for the regular hash function.
|
||||
pub fn init() Blake3 {
|
||||
return Blake3.init_internal(IV, 0);
|
||||
}
|
||||
|
||||
/// Construct a new `Blake3` for the keyed hash function.
|
||||
pub fn init_keyed(key: [KEY_LEN]u8) Blake3 {
|
||||
var key_words: [8]u32 = undefined;
|
||||
words_from_little_endian_bytes(key_words[0..], key[0..]);
|
||||
return Blake3.init_internal(key_words, KEYED_HASH);
|
||||
/// Construct a new `Blake3` for the hash function, with an optional key
|
||||
pub fn init(options: Options) Blake3 {
|
||||
if (options.key) |key| {
|
||||
var key_words: [8]u32 = undefined;
|
||||
words_from_little_endian_bytes(key_words[0..], key[0..]);
|
||||
return Blake3.init_internal(key_words, KEYED_HASH);
|
||||
} else {
|
||||
return Blake3.init_internal(IV, 0);
|
||||
}
|
||||
}
|
||||
|
||||
/// Construct a new `Blake3` for the key derivation function. The context
|
||||
/// string should be hardcoded, globally unique, and application-specific.
|
||||
pub fn init_derive_key(context: []const u8) Blake3 {
|
||||
pub fn initKdf(context: []const u8, options: KdfOptions) Blake3 {
|
||||
var context_hasher = Blake3.init_internal(IV, DERIVE_KEY_CONTEXT);
|
||||
context_hasher.update(context);
|
||||
var context_key: [KEY_LEN]u8 = undefined;
|
||||
@ -315,18 +322,12 @@ pub const Blake3 = struct {
|
||||
return Blake3.init_internal(context_key_words, DERIVE_KEY_MATERIAL);
|
||||
}
|
||||
|
||||
pub fn hash(in: []const u8, out: []u8) void {
|
||||
var hasher = Blake3.init();
|
||||
pub fn hash(in: []const u8, out: []u8, options: Options) void {
|
||||
var hasher = Blake3.init(options);
|
||||
hasher.update(in);
|
||||
hasher.final(out);
|
||||
}
|
||||
|
||||
/// Reset the `Blake3` to its initial state.
|
||||
pub fn reset(self: *Blake3) void {
|
||||
self.chunk_state = ChunkState.init(self.key, 0, self.flags);
|
||||
self.cv_stack_len = 0;
|
||||
}
|
||||
|
||||
fn push_cv(self: *Blake3, cv: [8]u32) void {
|
||||
self.cv_stack[self.cv_stack_len] = cv;
|
||||
self.cv_stack_len += 1;
|
||||
@ -561,6 +562,9 @@ const reference_test = ReferenceTest{
|
||||
};
|
||||
|
||||
fn test_blake3(hasher: *Blake3, input_len: usize, expected_hex: [262]u8) void {
|
||||
// Save initial state
|
||||
const initial_state = hasher.*;
|
||||
|
||||
// Setup input pattern
|
||||
var input_pattern: [251]u8 = undefined;
|
||||
for (input_pattern) |*e, i| e.* = @truncate(u8, i);
|
||||
@ -576,18 +580,20 @@ fn test_blake3(hasher: *Blake3, input_len: usize, expected_hex: [262]u8) void {
|
||||
// Read final hash value
|
||||
var actual_bytes: [expected_hex.len / 2]u8 = undefined;
|
||||
hasher.final(actual_bytes[0..]);
|
||||
hasher.reset();
|
||||
|
||||
// Compare to expected value
|
||||
var expected_bytes: [expected_hex.len / 2]u8 = undefined;
|
||||
fmt.hexToBytes(expected_bytes[0..], expected_hex[0..]) catch unreachable;
|
||||
testing.expectEqual(actual_bytes, expected_bytes);
|
||||
|
||||
// Restore initial state
|
||||
hasher.* = initial_state;
|
||||
}
|
||||
|
||||
test "BLAKE3 reference test cases" {
|
||||
var hash = &Blake3.init();
|
||||
var keyed_hash = &Blake3.init_keyed(reference_test.key.*);
|
||||
var derive_key = &Blake3.init_derive_key(reference_test.context_string);
|
||||
var hash = &Blake3.init(.{});
|
||||
var keyed_hash = &Blake3.init(.{ .key = reference_test.key.* });
|
||||
var derive_key = &Blake3.initKdf(reference_test.context_string, .{});
|
||||
|
||||
for (reference_test.cases) |t| {
|
||||
test_blake3(hash, t.input_len, t.hash.*);
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// Based on public domain Supercop by Daniel J. Bernstein
|
||||
|
||||
const std = @import("../std.zig");
|
||||
@ -7,7 +12,7 @@ const assert = std.debug.assert;
|
||||
const testing = std.testing;
|
||||
const builtin = @import("builtin");
|
||||
const maxInt = std.math.maxInt;
|
||||
const Poly1305 = std.crypto.Poly1305;
|
||||
const Poly1305 = std.crypto.onetimeauth.Poly1305;
|
||||
|
||||
const QuarterRound = struct {
|
||||
a: usize,
|
||||
@ -132,56 +137,60 @@ fn keyToWords(key: [32]u8) [8]u32 {
|
||||
///
|
||||
/// ChaCha20 is self-reversing. To decrypt just run the cipher with the same
|
||||
/// counter, nonce, and key.
|
||||
pub fn chaCha20IETF(out: []u8, in: []const u8, counter: u32, key: [32]u8, nonce: [12]u8) void {
|
||||
assert(in.len >= out.len);
|
||||
assert((in.len >> 6) + counter <= maxInt(u32));
|
||||
pub const ChaCha20IETF = struct {
|
||||
pub fn xor(out: []u8, in: []const u8, counter: u32, key: [32]u8, nonce: [12]u8) void {
|
||||
assert(in.len >= out.len);
|
||||
assert((in.len >> 6) + counter <= maxInt(u32));
|
||||
|
||||
var c: [4]u32 = undefined;
|
||||
c[0] = counter;
|
||||
c[1] = mem.readIntLittle(u32, nonce[0..4]);
|
||||
c[2] = mem.readIntLittle(u32, nonce[4..8]);
|
||||
c[3] = mem.readIntLittle(u32, nonce[8..12]);
|
||||
chaCha20_internal(out, in, keyToWords(key), c);
|
||||
}
|
||||
var c: [4]u32 = undefined;
|
||||
c[0] = counter;
|
||||
c[1] = mem.readIntLittle(u32, nonce[0..4]);
|
||||
c[2] = mem.readIntLittle(u32, nonce[4..8]);
|
||||
c[3] = mem.readIntLittle(u32, nonce[8..12]);
|
||||
chaCha20_internal(out, in, keyToWords(key), c);
|
||||
}
|
||||
};
|
||||
|
||||
/// This is the original ChaCha20 before RFC 7539, which recommends using the
|
||||
/// orgininal version on applications such as disk or file encryption that might
|
||||
/// exceed the 256 GiB limit of the 96-bit nonce version.
|
||||
pub fn chaCha20With64BitNonce(out: []u8, in: []const u8, counter: u64, key: [32]u8, nonce: [8]u8) void {
|
||||
assert(in.len >= out.len);
|
||||
assert(counter +% (in.len >> 6) >= counter);
|
||||
pub const ChaCha20With64BitNonce = struct {
|
||||
pub fn xor(out: []u8, in: []const u8, counter: u64, key: [32]u8, nonce: [8]u8) void {
|
||||
assert(in.len >= out.len);
|
||||
assert(counter +% (in.len >> 6) >= counter);
|
||||
|
||||
var cursor: usize = 0;
|
||||
const k = keyToWords(key);
|
||||
var c: [4]u32 = undefined;
|
||||
c[0] = @truncate(u32, counter);
|
||||
c[1] = @truncate(u32, counter >> 32);
|
||||
c[2] = mem.readIntLittle(u32, nonce[0..4]);
|
||||
c[3] = mem.readIntLittle(u32, nonce[4..8]);
|
||||
var cursor: usize = 0;
|
||||
const k = keyToWords(key);
|
||||
var c: [4]u32 = undefined;
|
||||
c[0] = @truncate(u32, counter);
|
||||
c[1] = @truncate(u32, counter >> 32);
|
||||
c[2] = mem.readIntLittle(u32, nonce[0..4]);
|
||||
c[3] = mem.readIntLittle(u32, nonce[4..8]);
|
||||
|
||||
const block_size = (1 << 6);
|
||||
// The full block size is greater than the address space on a 32bit machine
|
||||
const big_block = if (@sizeOf(usize) > 4) (block_size << 32) else maxInt(usize);
|
||||
const block_size = (1 << 6);
|
||||
// The full block size is greater than the address space on a 32bit machine
|
||||
const big_block = if (@sizeOf(usize) > 4) (block_size << 32) else maxInt(usize);
|
||||
|
||||
// first partial big block
|
||||
if (((@intCast(u64, maxInt(u32) - @truncate(u32, counter)) + 1) << 6) < in.len) {
|
||||
chaCha20_internal(out[cursor..big_block], in[cursor..big_block], k, c);
|
||||
cursor = big_block - cursor;
|
||||
c[1] += 1;
|
||||
if (comptime @sizeOf(usize) > 4) {
|
||||
// A big block is giant: 256 GiB, but we can avoid this limitation
|
||||
var remaining_blocks: u32 = @intCast(u32, (in.len / big_block));
|
||||
var i: u32 = 0;
|
||||
while (remaining_blocks > 0) : (remaining_blocks -= 1) {
|
||||
chaCha20_internal(out[cursor .. cursor + big_block], in[cursor .. cursor + big_block], k, c);
|
||||
c[1] += 1; // upper 32-bit of counter, generic chaCha20_internal() doesn't know about this.
|
||||
cursor += big_block;
|
||||
// first partial big block
|
||||
if (((@intCast(u64, maxInt(u32) - @truncate(u32, counter)) + 1) << 6) < in.len) {
|
||||
chaCha20_internal(out[cursor..big_block], in[cursor..big_block], k, c);
|
||||
cursor = big_block - cursor;
|
||||
c[1] += 1;
|
||||
if (comptime @sizeOf(usize) > 4) {
|
||||
// A big block is giant: 256 GiB, but we can avoid this limitation
|
||||
var remaining_blocks: u32 = @intCast(u32, (in.len / big_block));
|
||||
var i: u32 = 0;
|
||||
while (remaining_blocks > 0) : (remaining_blocks -= 1) {
|
||||
chaCha20_internal(out[cursor .. cursor + big_block], in[cursor .. cursor + big_block], k, c);
|
||||
c[1] += 1; // upper 32-bit of counter, generic chaCha20_internal() doesn't know about this.
|
||||
cursor += big_block;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
chaCha20_internal(out[cursor..], in[cursor..], k, c);
|
||||
}
|
||||
chaCha20_internal(out[cursor..], in[cursor..], k, c);
|
||||
}
|
||||
};
|
||||
|
||||
// https://tools.ietf.org/html/rfc7539#section-2.4.2
|
||||
test "crypto.chacha20 test vector sunscreen" {
|
||||
@ -216,12 +225,12 @@ test "crypto.chacha20 test vector sunscreen" {
|
||||
0, 0, 0, 0,
|
||||
};
|
||||
|
||||
chaCha20IETF(result[0..], input[0..], 1, key, nonce);
|
||||
ChaCha20IETF.xor(result[0..], input[0..], 1, key, nonce);
|
||||
testing.expectEqualSlices(u8, &expected_result, &result);
|
||||
|
||||
// Chacha20 is self-reversing.
|
||||
var plaintext: [114]u8 = undefined;
|
||||
chaCha20IETF(plaintext[0..], result[0..], 1, key, nonce);
|
||||
ChaCha20IETF.xor(plaintext[0..], result[0..], 1, key, nonce);
|
||||
testing.expect(mem.order(u8, input, &plaintext) == .eq);
|
||||
}
|
||||
|
||||
@ -256,7 +265,7 @@ test "crypto.chacha20 test vector 1" {
|
||||
};
|
||||
const nonce = [_]u8{ 0, 0, 0, 0, 0, 0, 0, 0 };
|
||||
|
||||
chaCha20With64BitNonce(result[0..], input[0..], 0, key, nonce);
|
||||
ChaCha20With64BitNonce.xor(result[0..], input[0..], 0, key, nonce);
|
||||
testing.expectEqualSlices(u8, &expected_result, &result);
|
||||
}
|
||||
|
||||
@ -290,7 +299,7 @@ test "crypto.chacha20 test vector 2" {
|
||||
};
|
||||
const nonce = [_]u8{ 0, 0, 0, 0, 0, 0, 0, 0 };
|
||||
|
||||
chaCha20With64BitNonce(result[0..], input[0..], 0, key, nonce);
|
||||
ChaCha20With64BitNonce.xor(result[0..], input[0..], 0, key, nonce);
|
||||
testing.expectEqualSlices(u8, &expected_result, &result);
|
||||
}
|
||||
|
||||
@ -324,7 +333,7 @@ test "crypto.chacha20 test vector 3" {
|
||||
};
|
||||
const nonce = [_]u8{ 0, 0, 0, 0, 0, 0, 0, 1 };
|
||||
|
||||
chaCha20With64BitNonce(result[0..], input[0..], 0, key, nonce);
|
||||
ChaCha20With64BitNonce.xor(result[0..], input[0..], 0, key, nonce);
|
||||
testing.expectEqualSlices(u8, &expected_result, &result);
|
||||
}
|
||||
|
||||
@ -358,7 +367,7 @@ test "crypto.chacha20 test vector 4" {
|
||||
};
|
||||
const nonce = [_]u8{ 1, 0, 0, 0, 0, 0, 0, 0 };
|
||||
|
||||
chaCha20With64BitNonce(result[0..], input[0..], 0, key, nonce);
|
||||
ChaCha20With64BitNonce.xor(result[0..], input[0..], 0, key, nonce);
|
||||
testing.expectEqualSlices(u8, &expected_result, &result);
|
||||
}
|
||||
|
||||
@ -430,21 +439,21 @@ test "crypto.chacha20 test vector 5" {
|
||||
0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,
|
||||
};
|
||||
|
||||
chaCha20With64BitNonce(result[0..], input[0..], 0, key, nonce);
|
||||
ChaCha20With64BitNonce.xor(result[0..], input[0..], 0, key, nonce);
|
||||
testing.expectEqualSlices(u8, &expected_result, &result);
|
||||
}
|
||||
|
||||
pub const chacha20poly1305_tag_size = 16;
|
||||
|
||||
pub fn chacha20poly1305SealDetached(ciphertext: []u8, tag: *[chacha20poly1305_tag_size]u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [12]u8) void {
|
||||
fn chacha20poly1305SealDetached(ciphertext: []u8, tag: *[chacha20poly1305_tag_size]u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [12]u8) void {
|
||||
assert(ciphertext.len >= plaintext.len);
|
||||
|
||||
// derive poly1305 key
|
||||
var polyKey = [_]u8{0} ** 32;
|
||||
chaCha20IETF(polyKey[0..], polyKey[0..], 0, key, nonce);
|
||||
ChaCha20IETF.xor(polyKey[0..], polyKey[0..], 0, key, nonce);
|
||||
|
||||
// encrypt plaintext
|
||||
chaCha20IETF(ciphertext[0..plaintext.len], plaintext, 1, key, nonce);
|
||||
ChaCha20IETF.xor(ciphertext[0..plaintext.len], plaintext, 1, key, nonce);
|
||||
|
||||
// construct mac
|
||||
var mac = Poly1305.init(polyKey[0..]);
|
||||
@ -467,18 +476,18 @@ pub fn chacha20poly1305SealDetached(ciphertext: []u8, tag: *[chacha20poly1305_ta
|
||||
mac.final(tag);
|
||||
}
|
||||
|
||||
pub fn chacha20poly1305Seal(ciphertextAndTag: []u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [12]u8) void {
|
||||
fn chacha20poly1305Seal(ciphertextAndTag: []u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [12]u8) void {
|
||||
return chacha20poly1305SealDetached(ciphertextAndTag[0..plaintext.len], ciphertextAndTag[plaintext.len..][0..chacha20poly1305_tag_size], plaintext, data, key, nonce);
|
||||
}
|
||||
|
||||
/// Verifies and decrypts an authenticated message produced by chacha20poly1305SealDetached.
|
||||
pub fn chacha20poly1305OpenDetached(dst: []u8, ciphertext: []const u8, tag: *const [chacha20poly1305_tag_size]u8, data: []const u8, key: [32]u8, nonce: [12]u8) !void {
|
||||
fn chacha20poly1305OpenDetached(dst: []u8, ciphertext: []const u8, tag: *const [chacha20poly1305_tag_size]u8, data: []const u8, key: [32]u8, nonce: [12]u8) !void {
|
||||
// split ciphertext and tag
|
||||
assert(dst.len >= ciphertext.len);
|
||||
|
||||
// derive poly1305 key
|
||||
var polyKey = [_]u8{0} ** 32;
|
||||
chaCha20IETF(polyKey[0..], polyKey[0..], 0, key, nonce);
|
||||
ChaCha20IETF.xor(polyKey[0..], polyKey[0..], 0, key, nonce);
|
||||
|
||||
// construct mac
|
||||
var mac = Poly1305.init(polyKey[0..]);
|
||||
@ -514,11 +523,11 @@ pub fn chacha20poly1305OpenDetached(dst: []u8, ciphertext: []const u8, tag: *con
|
||||
}
|
||||
|
||||
// decrypt ciphertext
|
||||
chaCha20IETF(dst[0..ciphertext.len], ciphertext, 1, key, nonce);
|
||||
ChaCha20IETF.xor(dst[0..ciphertext.len], ciphertext, 1, key, nonce);
|
||||
}
|
||||
|
||||
/// Verifies and decrypts an authenticated message produced by chacha20poly1305Seal.
|
||||
pub fn chacha20poly1305Open(dst: []u8, ciphertextAndTag: []const u8, data: []const u8, key: [32]u8, nonce: [12]u8) !void {
|
||||
fn chacha20poly1305Open(dst: []u8, ciphertextAndTag: []const u8, data: []const u8, key: [32]u8, nonce: [12]u8) !void {
|
||||
if (ciphertextAndTag.len < chacha20poly1305_tag_size) {
|
||||
return error.InvalidMessage;
|
||||
}
|
||||
@ -557,31 +566,33 @@ fn extend(key: [32]u8, nonce: [24]u8) struct { key: [32]u8, nonce: [12]u8 } {
|
||||
};
|
||||
}
|
||||
|
||||
pub fn xChaCha20IETF(out: []u8, in: []const u8, counter: u32, key: [32]u8, nonce: [24]u8) void {
|
||||
const extended = extend(key, nonce);
|
||||
chaCha20IETF(out, in, counter, extended.key, extended.nonce);
|
||||
}
|
||||
pub const XChaCha20IETF = struct {
|
||||
pub fn xor(out: []u8, in: []const u8, counter: u32, key: [32]u8, nonce: [24]u8) void {
|
||||
const extended = extend(key, nonce);
|
||||
ChaCha20IETF.xor(out, in, counter, extended.key, extended.nonce);
|
||||
}
|
||||
};
|
||||
|
||||
pub const xchacha20poly1305_tag_size = 16;
|
||||
|
||||
pub fn xchacha20poly1305SealDetached(ciphertext: []u8, tag: *[chacha20poly1305_tag_size]u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [24]u8) void {
|
||||
fn xchacha20poly1305SealDetached(ciphertext: []u8, tag: *[chacha20poly1305_tag_size]u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [24]u8) void {
|
||||
const extended = extend(key, nonce);
|
||||
return chacha20poly1305SealDetached(ciphertext, tag, plaintext, data, extended.key, extended.nonce);
|
||||
}
|
||||
|
||||
pub fn xchacha20poly1305Seal(ciphertextAndTag: []u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [24]u8) void {
|
||||
fn xchacha20poly1305Seal(ciphertextAndTag: []u8, plaintext: []const u8, data: []const u8, key: [32]u8, nonce: [24]u8) void {
|
||||
const extended = extend(key, nonce);
|
||||
return chacha20poly1305Seal(ciphertextAndTag, plaintext, data, extended.key, extended.nonce);
|
||||
}
|
||||
|
||||
/// Verifies and decrypts an authenticated message produced by xchacha20poly1305SealDetached.
|
||||
pub fn xchacha20poly1305OpenDetached(plaintext: []u8, ciphertext: []const u8, tag: *const [chacha20poly1305_tag_size]u8, data: []const u8, key: [32]u8, nonce: [24]u8) !void {
|
||||
fn xchacha20poly1305OpenDetached(plaintext: []u8, ciphertext: []const u8, tag: *const [chacha20poly1305_tag_size]u8, data: []const u8, key: [32]u8, nonce: [24]u8) !void {
|
||||
const extended = extend(key, nonce);
|
||||
return try chacha20poly1305OpenDetached(plaintext, ciphertext, tag, data, extended.key, extended.nonce);
|
||||
}
|
||||
|
||||
/// Verifies and decrypts an authenticated message produced by xchacha20poly1305Seal.
|
||||
pub fn xchacha20poly1305Open(ciphertextAndTag: []u8, msgAndTag: []const u8, data: []const u8, key: [32]u8, nonce: [24]u8) !void {
|
||||
fn xchacha20poly1305Open(ciphertextAndTag: []u8, msgAndTag: []const u8, data: []const u8, key: [32]u8, nonce: [24]u8) !void {
|
||||
const extended = extend(key, nonce);
|
||||
return try chacha20poly1305Open(ciphertextAndTag, msgAndTag, data, extended.key, extended.nonce);
|
||||
}
|
||||
@ -709,7 +720,7 @@ test "crypto.xchacha20" {
|
||||
const input = "Ladies and Gentlemen of the class of '99: If I could offer you only one tip for the future, sunscreen would be it.";
|
||||
{
|
||||
var ciphertext: [input.len]u8 = undefined;
|
||||
xChaCha20IETF(ciphertext[0..], input[0..], 0, key, nonce);
|
||||
XChaCha20IETF.xor(ciphertext[0..], input[0..], 0, key, nonce);
|
||||
var buf: [2 * ciphertext.len]u8 = undefined;
|
||||
testing.expectEqualStrings(try std.fmt.bufPrint(&buf, "{X}", .{ciphertext}), "E0A1BCF939654AFDBDC1746EC49832647C19D891F0D1A81FC0C1703B4514BDEA584B512F6908C2C5E9DD18D5CBC1805DE5803FE3B9CA5F193FB8359E91FAB0C3BB40309A292EB1CF49685C65C4A3ADF4F11DB0CD2B6B67FBC174BC2E860E8F769FD3565BBFAD1C845E05A0FED9BE167C240D");
|
||||
}
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// Gimli is a 384-bit permutation designed to achieve high security with high
|
||||
// performance across a broad range of platforms, including 64-bit Intel/AMD
|
||||
// server CPUs, 64-bit and 32-bit ARM smartphone CPUs, 32-bit ARM
|
||||
@ -104,13 +109,14 @@ pub const Hash = struct {
|
||||
state: State,
|
||||
buf_off: usize,
|
||||
|
||||
pub const block_length = State.RATE;
|
||||
pub const Options = struct {};
|
||||
|
||||
const Self = @This();
|
||||
|
||||
pub fn init() Self {
|
||||
pub fn init(options: Options) Self {
|
||||
return Self{
|
||||
.state = State{
|
||||
.data = [_]u32{0} ** (State.BLOCKBYTES / 4),
|
||||
},
|
||||
.state = State{ .data = [_]u32{0} ** (State.BLOCKBYTES / 4) },
|
||||
.buf_off = 0,
|
||||
};
|
||||
}
|
||||
@ -155,8 +161,8 @@ pub const Hash = struct {
|
||||
}
|
||||
};
|
||||
|
||||
pub fn hash(out: []u8, in: []const u8) void {
|
||||
var st = Hash.init();
|
||||
pub fn hash(out: []u8, in: []const u8, options: Hash.Options) void {
|
||||
var st = Hash.init(options);
|
||||
st.update(in);
|
||||
st.final(out);
|
||||
}
|
||||
@ -169,7 +175,7 @@ test "hash" {
|
||||
var msg: [58 / 2]u8 = undefined;
|
||||
try std.fmt.hexToBytes(&msg, "000102030405060708090A0B0C0D0E0F101112131415161718191A1B1C");
|
||||
var md: [32]u8 = undefined;
|
||||
hash(&md, &msg);
|
||||
hash(&md, &msg, .{});
|
||||
htest.assertEqual("1C9A03DC6A5DDC5444CFC6F4B154CFF5CF081633B2CEA4D7D0AE7CCFED5AAA44", &md);
|
||||
}
|
||||
|
||||
|
||||
@ -1,12 +1,26 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const crypto = std.crypto;
|
||||
const debug = std.debug;
|
||||
const mem = std.mem;
|
||||
|
||||
pub const HmacMd5 = Hmac(crypto.Md5);
|
||||
pub const HmacSha1 = Hmac(crypto.Sha1);
|
||||
pub const HmacSha256 = Hmac(crypto.Sha256);
|
||||
pub const HmacBlake2s256 = Hmac(crypto.Blake2s256);
|
||||
pub const HmacMd5 = Hmac(crypto.hash.Md5);
|
||||
pub const HmacSha1 = Hmac(crypto.hash.Sha1);
|
||||
|
||||
pub const sha2 = struct {
|
||||
pub const HmacSha224 = Hmac(crypto.hash.sha2.Sha224);
|
||||
pub const HmacSha256 = Hmac(crypto.hash.sha2.Sha256);
|
||||
pub const HmacSha384 = Hmac(crypto.hash.sha2.Sha384);
|
||||
pub const HmacSha512 = Hmac(crypto.hash.sha2.Sha512);
|
||||
};
|
||||
|
||||
pub const blake2 = struct {
|
||||
pub const HmacBlake2s256 = Hmac(crypto.hash.blake2.Blake2s256);
|
||||
};
|
||||
|
||||
pub fn Hmac(comptime Hash: type) type {
|
||||
return struct {
|
||||
@ -31,7 +45,7 @@ pub fn Hmac(comptime Hash: type) type {
|
||||
|
||||
// Normalize key length to block size of hash
|
||||
if (key.len > Hash.block_length) {
|
||||
Hash.hash(key, ctx.scratch[0..mac_length]);
|
||||
Hash.hash(key, ctx.scratch[0..mac_length], .{});
|
||||
mem.set(u8, ctx.scratch[mac_length..Hash.block_length], 0);
|
||||
} else if (key.len < Hash.block_length) {
|
||||
mem.copy(u8, ctx.scratch[0..key.len], key);
|
||||
@ -48,7 +62,7 @@ pub fn Hmac(comptime Hash: type) type {
|
||||
b.* = ctx.scratch[i] ^ 0x36;
|
||||
}
|
||||
|
||||
ctx.hash = Hash.init();
|
||||
ctx.hash = Hash.init(.{});
|
||||
ctx.hash.update(ctx.i_key_pad[0..]);
|
||||
return ctx;
|
||||
}
|
||||
@ -61,10 +75,10 @@ pub fn Hmac(comptime Hash: type) type {
|
||||
debug.assert(Hash.block_length >= out.len and out.len >= mac_length);
|
||||
|
||||
ctx.hash.final(ctx.scratch[0..mac_length]);
|
||||
ctx.hash.reset();
|
||||
ctx.hash.update(ctx.o_key_pad[0..]);
|
||||
ctx.hash.update(ctx.scratch[0..mac_length]);
|
||||
ctx.hash.final(out[0..mac_length]);
|
||||
var ohash = Hash.init(.{});
|
||||
ohash.update(ctx.o_key_pad[0..]);
|
||||
ohash.update(ctx.scratch[0..mac_length]);
|
||||
ohash.final(out[0..mac_length]);
|
||||
}
|
||||
};
|
||||
}
|
||||
@ -90,10 +104,10 @@ test "hmac sha1" {
|
||||
}
|
||||
|
||||
test "hmac sha256" {
|
||||
var out: [HmacSha256.mac_length]u8 = undefined;
|
||||
HmacSha256.create(out[0..], "", "");
|
||||
var out: [sha2.HmacSha256.mac_length]u8 = undefined;
|
||||
sha2.HmacSha256.create(out[0..], "", "");
|
||||
htest.assertEqual("b613679a0814d9ec772f95d778c35fc5ff1697c493715653c6c712144292c5ad", out[0..]);
|
||||
|
||||
HmacSha256.create(out[0..], "The quick brown fox jumps over the lazy dog", "key");
|
||||
sha2.HmacSha256.create(out[0..], "The quick brown fox jumps over the lazy dog", "key");
|
||||
htest.assertEqual("f7bc83f430538424b13298e6aa6fb143ef4d59a14946175997479dbc2d1a3cd8", out[0..]);
|
||||
}
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const mem = @import("../mem.zig");
|
||||
const math = @import("../math.zig");
|
||||
const endian = @import("../endian.zig");
|
||||
@ -27,10 +32,14 @@ fn Rp(a: usize, b: usize, c: usize, d: usize, k: usize, s: u32, t: u32) RoundPar
|
||||
};
|
||||
}
|
||||
|
||||
/// The MD5 function is now considered cryptographically broken.
|
||||
/// Namely, it is trivial to find multiple inputs producing the same hash.
|
||||
/// For a fast-performing, cryptographically secure hash function, see SHA512/256, BLAKE2 or BLAKE3.
|
||||
pub const Md5 = struct {
|
||||
const Self = @This();
|
||||
pub const block_length = 64;
|
||||
pub const digest_length = 16;
|
||||
pub const Options = struct {};
|
||||
|
||||
s: [4]u32,
|
||||
// Streaming Cache
|
||||
@ -38,23 +47,22 @@ pub const Md5 = struct {
|
||||
buf_len: u8,
|
||||
total_len: u64,
|
||||
|
||||
pub fn init() Self {
|
||||
var d: Self = undefined;
|
||||
d.reset();
|
||||
return d;
|
||||
pub fn init(options: Options) Self {
|
||||
return Self{
|
||||
.s = [_]u32{
|
||||
0x67452301,
|
||||
0xEFCDAB89,
|
||||
0x98BADCFE,
|
||||
0x10325476,
|
||||
},
|
||||
.buf = undefined,
|
||||
.buf_len = 0,
|
||||
.total_len = 0,
|
||||
};
|
||||
}
|
||||
|
||||
pub fn reset(d: *Self) void {
|
||||
d.s[0] = 0x67452301;
|
||||
d.s[1] = 0xEFCDAB89;
|
||||
d.s[2] = 0x98BADCFE;
|
||||
d.s[3] = 0x10325476;
|
||||
d.buf_len = 0;
|
||||
d.total_len = 0;
|
||||
}
|
||||
|
||||
pub fn hash(b: []const u8, out: []u8) void {
|
||||
var d = Md5.init();
|
||||
pub fn hash(b: []const u8, out: []u8, options: Options) void {
|
||||
var d = Md5.init(options);
|
||||
d.update(b);
|
||||
d.final(out);
|
||||
}
|
||||
@ -250,18 +258,18 @@ test "md5 single" {
|
||||
}
|
||||
|
||||
test "md5 streaming" {
|
||||
var h = Md5.init();
|
||||
var h = Md5.init(.{});
|
||||
var out: [16]u8 = undefined;
|
||||
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("d41d8cd98f00b204e9800998ecf8427e", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Md5.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("900150983cd24fb0d6963f7d28e17f72", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Md5.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -274,7 +282,7 @@ test "md5 aligned final" {
|
||||
var block = [_]u8{0} ** Md5.block_length;
|
||||
var out: [Md5.digest_length]u8 = undefined;
|
||||
|
||||
var h = Md5.init();
|
||||
var h = Md5.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
}
|
||||
|
||||
@ -1,221 +1,199 @@
|
||||
// Translated from monocypher which is licensed under CC-0/BSD-3.
|
||||
//
|
||||
// https://monocypher.org/
|
||||
|
||||
const std = @import("../std.zig");
|
||||
const builtin = std.builtin;
|
||||
|
||||
const Endian = builtin.Endian;
|
||||
const readIntLittle = std.mem.readIntLittle;
|
||||
const writeIntLittle = std.mem.writeIntLittle;
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const mem = std.mem;
|
||||
|
||||
pub const Poly1305 = struct {
|
||||
const Self = @This();
|
||||
|
||||
pub const block_size: usize = 16;
|
||||
pub const mac_length = 16;
|
||||
pub const minimum_key_length = 32;
|
||||
|
||||
// constant multiplier (from the secret key)
|
||||
r: [4]u32,
|
||||
r: [3]u64,
|
||||
// accumulated hash
|
||||
h: [5]u32,
|
||||
// chunk of the message
|
||||
c: [5]u32,
|
||||
h: [3]u64 = [_]u64{ 0, 0, 0 },
|
||||
// random number added at the end (from the secret key)
|
||||
pad: [4]u32,
|
||||
// How many bytes are there in the chunk.
|
||||
c_idx: usize,
|
||||
pad: [2]u64,
|
||||
// how many bytes are waiting to be processed in a partial block
|
||||
leftover: usize = 0,
|
||||
// partial block buffer
|
||||
buf: [block_size]u8 align(16) = undefined,
|
||||
|
||||
fn secureZero(self: *Self) void {
|
||||
std.mem.secureZero(u8, @ptrCast([*]u8, self)[0..@sizeOf(Poly1305)]);
|
||||
pub fn init(key: []const u8) Poly1305 {
|
||||
std.debug.assert(key.len >= minimum_key_length);
|
||||
const t0 = mem.readIntLittle(u64, key[0..8]);
|
||||
const t1 = mem.readIntLittle(u64, key[8..16]);
|
||||
return Poly1305{
|
||||
.r = [_]u64{
|
||||
t0 & 0xffc0fffffff,
|
||||
((t0 >> 44) | (t1 << 20)) & 0xfffffc0ffff,
|
||||
((t1 >> 24)) & 0x00ffffffc0f,
|
||||
},
|
||||
.pad = [_]u64{
|
||||
mem.readIntLittle(u64, key[16..24]),
|
||||
mem.readIntLittle(u64, key[24..32]),
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
fn blocks(st: *Poly1305, m: []const u8, last: comptime bool) void {
|
||||
const hibit: u64 = if (last) 0 else 1 << 40;
|
||||
const r0 = st.r[0];
|
||||
const r1 = st.r[1];
|
||||
const r2 = st.r[2];
|
||||
var h0 = st.h[0];
|
||||
var h1 = st.h[1];
|
||||
var h2 = st.h[2];
|
||||
const s1 = r1 * (5 << 2);
|
||||
const s2 = r2 * (5 << 2);
|
||||
var i: usize = 0;
|
||||
while (i + block_size <= m.len) : (i += block_size) {
|
||||
// h += m[i]
|
||||
const t0 = mem.readIntLittle(u64, m[i..][0..8]);
|
||||
const t1 = mem.readIntLittle(u64, m[i + 8 ..][0..8]);
|
||||
h0 += @truncate(u44, t0);
|
||||
h1 += @truncate(u44, (t0 >> 44) | (t1 << 20));
|
||||
h2 += @truncate(u42, t1 >> 24) | hibit;
|
||||
|
||||
// h *= r
|
||||
const d0 = @as(u128, h0) * r0 + @as(u128, h1) * s2 + @as(u128, h2) * s1;
|
||||
var d1 = @as(u128, h0) * r1 + @as(u128, h1) * r0 + @as(u128, h2) * s2;
|
||||
var d2 = @as(u128, h0) * r2 + @as(u128, h1) * r1 + @as(u128, h2) * r0;
|
||||
|
||||
// partial reduction
|
||||
var carry = @intCast(u64, d0 >> 44);
|
||||
h0 = @truncate(u44, d0);
|
||||
d1 += carry;
|
||||
carry = @intCast(u64, d1 >> 44);
|
||||
h1 = @truncate(u44, d1);
|
||||
d2 += carry;
|
||||
carry = @intCast(u64, d2 >> 42);
|
||||
h2 = @truncate(u42, d2);
|
||||
h0 += @truncate(u64, carry) * 5;
|
||||
carry = h0 >> 44;
|
||||
h0 = @truncate(u44, h0);
|
||||
h1 += carry;
|
||||
}
|
||||
st.h = [_]u64{ h0, h1, h2 };
|
||||
}
|
||||
|
||||
pub fn update(st: *Poly1305, m: []const u8) void {
|
||||
var mb = m;
|
||||
|
||||
// handle leftover
|
||||
if (st.leftover > 0) {
|
||||
const want = std.math.min(block_size - st.leftover, mb.len);
|
||||
const mc = mb[0..want];
|
||||
for (mc) |x, i| {
|
||||
st.buf[st.leftover + i] = x;
|
||||
}
|
||||
mb = mb[want..];
|
||||
st.leftover += want;
|
||||
if (st.leftover > block_size) {
|
||||
return;
|
||||
}
|
||||
st.blocks(&st.buf, false);
|
||||
st.leftover = 0;
|
||||
}
|
||||
|
||||
// process full blocks
|
||||
if (mb.len >= block_size) {
|
||||
const want = mb.len & ~(block_size - 1);
|
||||
st.blocks(mb[0..want], false);
|
||||
mb = mb[want..];
|
||||
}
|
||||
|
||||
// store leftover
|
||||
if (mb.len > 0) {
|
||||
for (mb) |x, i| {
|
||||
st.buf[st.leftover + i] = x;
|
||||
}
|
||||
st.leftover += mb.len;
|
||||
}
|
||||
}
|
||||
|
||||
pub fn final(st: *Poly1305, out: []u8) void {
|
||||
std.debug.assert(out.len >= mac_length);
|
||||
if (st.leftover > 0) {
|
||||
var i = st.leftover;
|
||||
st.buf[i] = 1;
|
||||
i += 1;
|
||||
while (i < block_size) : (i += 1) {
|
||||
st.buf[i] = 0;
|
||||
}
|
||||
st.blocks(&st.buf, true);
|
||||
}
|
||||
// fully carry h
|
||||
var carry = st.h[1] >> 44;
|
||||
st.h[1] = @truncate(u44, st.h[1]);
|
||||
st.h[2] += carry;
|
||||
carry = st.h[2] >> 42;
|
||||
st.h[2] = @truncate(u42, st.h[2]);
|
||||
st.h[0] += carry * 5;
|
||||
carry = st.h[0] >> 44;
|
||||
st.h[0] = @truncate(u44, st.h[0]);
|
||||
st.h[1] += carry;
|
||||
carry = st.h[1] >> 44;
|
||||
st.h[1] = @truncate(u44, st.h[1]);
|
||||
st.h[2] += carry;
|
||||
carry = st.h[2] >> 42;
|
||||
st.h[2] = @truncate(u42, st.h[2]);
|
||||
st.h[0] += carry * 5;
|
||||
carry = st.h[0] >> 44;
|
||||
st.h[0] = @truncate(u44, st.h[0]);
|
||||
st.h[1] += carry;
|
||||
|
||||
// compute h + -p
|
||||
var g0 = st.h[0] + 5;
|
||||
carry = g0 >> 44;
|
||||
g0 = @truncate(u44, g0);
|
||||
var g1 = st.h[1] + carry;
|
||||
carry = g1 >> 44;
|
||||
g1 = @truncate(u44, g1);
|
||||
var g2 = st.h[2] + carry -% (1 << 42);
|
||||
|
||||
// (hopefully) constant-time select h if h < p, or h + -p if h >= p
|
||||
const mask = (g2 >> 63) -% 1;
|
||||
g0 &= mask;
|
||||
g1 &= mask;
|
||||
g2 &= mask;
|
||||
const nmask = ~mask;
|
||||
st.h[0] = (st.h[0] & nmask) | g0;
|
||||
st.h[1] = (st.h[1] & nmask) | g1;
|
||||
st.h[2] = (st.h[2] & nmask) | g2;
|
||||
|
||||
// h = (h + pad)
|
||||
const t0 = st.pad[0];
|
||||
const t1 = st.pad[1];
|
||||
st.h[0] += @truncate(u44, t0);
|
||||
carry = st.h[0] >> 44;
|
||||
st.h[0] = @truncate(u44, st.h[0]);
|
||||
st.h[1] += @truncate(u44, (t0 >> 44) | (t1 << 20)) + carry;
|
||||
carry = st.h[1] >> 44;
|
||||
st.h[1] = @truncate(u44, st.h[1]);
|
||||
st.h[2] += @truncate(u42, t1 >> 24) + carry;
|
||||
st.h[2] = @truncate(u42, st.h[2]);
|
||||
|
||||
// mac = h % (2^128)
|
||||
st.h[0] |= st.h[1] << 44;
|
||||
st.h[1] = (st.h[1] >> 20) | (st.h[2] << 24);
|
||||
|
||||
mem.writeIntLittle(u64, out[0..8], st.h[0]);
|
||||
mem.writeIntLittle(u64, out[8..16], st.h[1]);
|
||||
|
||||
std.mem.secureZero(u8, @ptrCast([*]u8, st)[0..@sizeOf(Poly1305)]);
|
||||
}
|
||||
|
||||
pub fn create(out: []u8, msg: []const u8, key: []const u8) void {
|
||||
std.debug.assert(out.len >= mac_length);
|
||||
std.debug.assert(key.len >= minimum_key_length);
|
||||
|
||||
var ctx = Poly1305.init(key);
|
||||
ctx.update(msg);
|
||||
ctx.final(out);
|
||||
}
|
||||
|
||||
// Initialize the MAC context.
|
||||
// - key.len is sufficient size.
|
||||
pub fn init(key: []const u8) Self {
|
||||
var ctx: Poly1305 = undefined;
|
||||
|
||||
// Initial hash is zero
|
||||
{
|
||||
var i: usize = 0;
|
||||
while (i < 5) : (i += 1) {
|
||||
ctx.h[i] = 0;
|
||||
}
|
||||
}
|
||||
// add 2^130 to every input block
|
||||
ctx.c[4] = 1;
|
||||
polyClearC(&ctx);
|
||||
|
||||
// load r and pad (r has some of its bits cleared)
|
||||
{
|
||||
var i: usize = 0;
|
||||
while (i < 1) : (i += 1) {
|
||||
ctx.r[0] = readIntLittle(u32, key[0..4]) & 0x0fffffff;
|
||||
}
|
||||
}
|
||||
{
|
||||
var i: usize = 1;
|
||||
while (i < 4) : (i += 1) {
|
||||
ctx.r[i] = readIntLittle(u32, key[i * 4 ..][0..4]) & 0x0ffffffc;
|
||||
}
|
||||
}
|
||||
{
|
||||
var i: usize = 0;
|
||||
while (i < 4) : (i += 1) {
|
||||
ctx.pad[i] = readIntLittle(u32, key[i * 4 + 16 ..][0..4]);
|
||||
}
|
||||
}
|
||||
|
||||
return ctx;
|
||||
}
|
||||
|
||||
// h = (h + c) * r
|
||||
// preconditions:
|
||||
// ctx->h <= 4_ffffffff_ffffffff_ffffffff_ffffffff
|
||||
// ctx->c <= 1_ffffffff_ffffffff_ffffffff_ffffffff
|
||||
// ctx->r <= 0ffffffc_0ffffffc_0ffffffc_0fffffff
|
||||
// Postcondition:
|
||||
// ctx->h <= 4_ffffffff_ffffffff_ffffffff_ffffffff
|
||||
fn polyBlock(ctx: *Self) void {
|
||||
// s = h + c, without carry propagation
|
||||
const s0 = @as(u64, ctx.h[0]) + ctx.c[0]; // s0 <= 1_fffffffe
|
||||
const s1 = @as(u64, ctx.h[1]) + ctx.c[1]; // s1 <= 1_fffffffe
|
||||
const s2 = @as(u64, ctx.h[2]) + ctx.c[2]; // s2 <= 1_fffffffe
|
||||
const s3 = @as(u64, ctx.h[3]) + ctx.c[3]; // s3 <= 1_fffffffe
|
||||
const s4 = @as(u64, ctx.h[4]) + ctx.c[4]; // s4 <= 5
|
||||
|
||||
// Local all the things!
|
||||
const r0 = ctx.r[0]; // r0 <= 0fffffff
|
||||
const r1 = ctx.r[1]; // r1 <= 0ffffffc
|
||||
const r2 = ctx.r[2]; // r2 <= 0ffffffc
|
||||
const r3 = ctx.r[3]; // r3 <= 0ffffffc
|
||||
const rr0 = (r0 >> 2) * 5; // rr0 <= 13fffffb // lose 2 bits...
|
||||
const rr1 = (r1 >> 2) + r1; // rr1 <= 13fffffb // rr1 == (r1 >> 2) * 5
|
||||
const rr2 = (r2 >> 2) + r2; // rr2 <= 13fffffb // rr1 == (r2 >> 2) * 5
|
||||
const rr3 = (r3 >> 2) + r3; // rr3 <= 13fffffb // rr1 == (r3 >> 2) * 5
|
||||
|
||||
// (h + c) * r, without carry propagation
|
||||
const x0 = s0 * r0 + s1 * rr3 + s2 * rr2 + s3 * rr1 + s4 * rr0; //<=97ffffe007fffff8
|
||||
const x1 = s0 * r1 + s1 * r0 + s2 * rr3 + s3 * rr2 + s4 * rr1; //<=8fffffe20ffffff6
|
||||
const x2 = s0 * r2 + s1 * r1 + s2 * r0 + s3 * rr3 + s4 * rr2; //<=87ffffe417fffff4
|
||||
const x3 = s0 * r3 + s1 * r2 + s2 * r1 + s3 * r0 + s4 * rr3; //<=7fffffe61ffffff2
|
||||
const x4 = s4 * (r0 & 3); // ...recover 2 bits //<= f
|
||||
|
||||
// partial reduction modulo 2^130 - 5
|
||||
const _u5 = @truncate(u32, x4 + (x3 >> 32)); // u5 <= 7ffffff5
|
||||
const _u0 = (_u5 >> 2) * 5 + (x0 & 0xffffffff);
|
||||
const _u1 = (_u0 >> 32) + (x1 & 0xffffffff) + (x0 >> 32);
|
||||
const _u2 = (_u1 >> 32) + (x2 & 0xffffffff) + (x1 >> 32);
|
||||
const _u3 = (_u2 >> 32) + (x3 & 0xffffffff) + (x2 >> 32);
|
||||
const _u4 = (_u3 >> 32) + (_u5 & 3);
|
||||
|
||||
// Update the hash
|
||||
ctx.h[0] = @truncate(u32, _u0); // u0 <= 1_9ffffff0
|
||||
ctx.h[1] = @truncate(u32, _u1); // u1 <= 1_97ffffe0
|
||||
ctx.h[2] = @truncate(u32, _u2); // u2 <= 1_8fffffe2
|
||||
ctx.h[3] = @truncate(u32, _u3); // u3 <= 1_87ffffe4
|
||||
ctx.h[4] = @truncate(u32, _u4); // u4 <= 4
|
||||
}
|
||||
|
||||
// (re-)initializes the input counter and input buffer
|
||||
fn polyClearC(ctx: *Self) void {
|
||||
ctx.c[0] = 0;
|
||||
ctx.c[1] = 0;
|
||||
ctx.c[2] = 0;
|
||||
ctx.c[3] = 0;
|
||||
ctx.c_idx = 0;
|
||||
}
|
||||
|
||||
fn polyTakeInput(ctx: *Self, input: u8) void {
|
||||
const word = ctx.c_idx >> 2;
|
||||
const byte = ctx.c_idx & 3;
|
||||
ctx.c[word] |= std.math.shl(u32, input, byte * 8);
|
||||
ctx.c_idx += 1;
|
||||
}
|
||||
|
||||
fn polyUpdate(ctx: *Self, msg: []const u8) void {
|
||||
for (msg) |b| {
|
||||
polyTakeInput(ctx, b);
|
||||
if (ctx.c_idx == 16) {
|
||||
polyBlock(ctx);
|
||||
polyClearC(ctx);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn alignTo(x: usize, block_size: usize) usize {
|
||||
return ((~x) +% 1) & (block_size - 1);
|
||||
}
|
||||
|
||||
// Feed data into the MAC context.
|
||||
pub fn update(ctx: *Self, msg: []const u8) void {
|
||||
// Align ourselves with block boundaries
|
||||
const alignm = std.math.min(alignTo(ctx.c_idx, 16), msg.len);
|
||||
polyUpdate(ctx, msg[0..alignm]);
|
||||
|
||||
var nmsg = msg[alignm..];
|
||||
|
||||
// Process the msg block by block
|
||||
const nb_blocks = nmsg.len >> 4;
|
||||
var i: usize = 0;
|
||||
while (i < nb_blocks) : (i += 1) {
|
||||
ctx.c[0] = readIntLittle(u32, nmsg[0..4]);
|
||||
ctx.c[1] = readIntLittle(u32, nmsg[4..8]);
|
||||
ctx.c[2] = readIntLittle(u32, nmsg[8..12]);
|
||||
ctx.c[3] = readIntLittle(u32, nmsg[12..16]);
|
||||
polyBlock(ctx);
|
||||
nmsg = nmsg[16..];
|
||||
}
|
||||
if (nb_blocks > 0) {
|
||||
polyClearC(ctx);
|
||||
}
|
||||
|
||||
// remaining bytes
|
||||
polyUpdate(ctx, nmsg[0..]);
|
||||
}
|
||||
|
||||
// Finalize the MAC and output into buffer provided by caller.
|
||||
pub fn final(ctx: *Self, out: []u8) void {
|
||||
// Process the last block (if any)
|
||||
if (ctx.c_idx != 0) {
|
||||
// move the final 1 according to remaining input length
|
||||
// (We may add less than 2^130 to the last input block)
|
||||
ctx.c[4] = 0;
|
||||
polyTakeInput(ctx, 1);
|
||||
// one last hash update
|
||||
polyBlock(ctx);
|
||||
}
|
||||
|
||||
// check if we should subtract 2^130-5 by performing the
|
||||
// corresponding carry propagation.
|
||||
const _u0 = @as(u64, 5) + ctx.h[0]; // <= 1_00000004
|
||||
const _u1 = (_u0 >> 32) + ctx.h[1]; // <= 1_00000000
|
||||
const _u2 = (_u1 >> 32) + ctx.h[2]; // <= 1_00000000
|
||||
const _u3 = (_u2 >> 32) + ctx.h[3]; // <= 1_00000000
|
||||
const _u4 = (_u3 >> 32) + ctx.h[4]; // <= 5
|
||||
// u4 indicates how many times we should subtract 2^130-5 (0 or 1)
|
||||
|
||||
// h + pad, minus 2^130-5 if u4 exceeds 3
|
||||
const uu0 = (_u4 >> 2) * 5 + ctx.h[0] + ctx.pad[0]; // <= 2_00000003
|
||||
const uu1 = (uu0 >> 32) + ctx.h[1] + ctx.pad[1]; // <= 2_00000000
|
||||
const uu2 = (uu1 >> 32) + ctx.h[2] + ctx.pad[2]; // <= 2_00000000
|
||||
const uu3 = (uu2 >> 32) + ctx.h[3] + ctx.pad[3]; // <= 2_00000000
|
||||
|
||||
writeIntLittle(u32, out[0..4], @truncate(u32, uu0));
|
||||
writeIntLittle(u32, out[4..8], @truncate(u32, uu1));
|
||||
writeIntLittle(u32, out[8..12], @truncate(u32, uu2));
|
||||
writeIntLittle(u32, out[12..16], @truncate(u32, uu3));
|
||||
|
||||
ctx.secureZero();
|
||||
var st = Poly1305.init(key);
|
||||
st.update(msg);
|
||||
st.final(out);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const mem = @import("../mem.zig");
|
||||
const math = @import("../math.zig");
|
||||
const endian = @import("../endian.zig");
|
||||
@ -24,35 +29,35 @@ fn Rp(a: usize, b: usize, c: usize, d: usize, e: usize, i: u32) RoundParam {
|
||||
};
|
||||
}
|
||||
|
||||
/// The SHA-1 function is now considered cryptographically broken.
|
||||
/// Namely, it is feasible to find multiple inputs producing the same hash.
|
||||
/// For a fast-performing, cryptographically secure hash function, see SHA512/256, BLAKE2 or BLAKE3.
|
||||
pub const Sha1 = struct {
|
||||
const Self = @This();
|
||||
pub const block_length = 64;
|
||||
pub const digest_length = 20;
|
||||
pub const Options = struct {};
|
||||
|
||||
s: [5]u32,
|
||||
// Streaming Cache
|
||||
buf: [64]u8,
|
||||
buf_len: u8,
|
||||
total_len: u64,
|
||||
buf: [64]u8 = undefined,
|
||||
buf_len: u8 = 0,
|
||||
total_len: u64 = 0,
|
||||
|
||||
pub fn init() Self {
|
||||
var d: Self = undefined;
|
||||
d.reset();
|
||||
return d;
|
||||
pub fn init(options: Options) Self {
|
||||
return Self{
|
||||
.s = [_]u32{
|
||||
0x67452301,
|
||||
0xEFCDAB89,
|
||||
0x98BADCFE,
|
||||
0x10325476,
|
||||
0xC3D2E1F0,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
pub fn reset(d: *Self) void {
|
||||
d.s[0] = 0x67452301;
|
||||
d.s[1] = 0xEFCDAB89;
|
||||
d.s[2] = 0x98BADCFE;
|
||||
d.s[3] = 0x10325476;
|
||||
d.s[4] = 0xC3D2E1F0;
|
||||
d.buf_len = 0;
|
||||
d.total_len = 0;
|
||||
}
|
||||
|
||||
pub fn hash(b: []const u8, out: []u8) void {
|
||||
var d = Sha1.init();
|
||||
pub fn hash(b: []const u8, out: []u8, options: Options) void {
|
||||
var d = Sha1.init(options);
|
||||
d.update(b);
|
||||
d.final(out);
|
||||
}
|
||||
@ -272,18 +277,18 @@ test "sha1 single" {
|
||||
}
|
||||
|
||||
test "sha1 streaming" {
|
||||
var h = Sha1.init();
|
||||
var h = Sha1.init(.{});
|
||||
var out: [20]u8 = undefined;
|
||||
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("da39a3ee5e6b4b0d3255bfef95601890afd80709", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha1.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("a9993e364706816aba3e25717850c26c9cd0d89d", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha1.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -295,7 +300,7 @@ test "sha1 aligned final" {
|
||||
var block = [_]u8{0} ** Sha1.block_length;
|
||||
var out: [Sha1.digest_length]u8 = undefined;
|
||||
|
||||
var h = Sha1.init();
|
||||
var h = Sha1.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
}
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const mem = @import("../mem.zig");
|
||||
const math = @import("../math.zig");
|
||||
const endian = @import("../endian.zig");
|
||||
@ -72,7 +77,10 @@ const Sha256Params = Sha2Params32{
|
||||
.out_len = 256,
|
||||
};
|
||||
|
||||
/// SHA-224
|
||||
pub const Sha224 = Sha2_32(Sha224Params);
|
||||
|
||||
/// SHA-256
|
||||
pub const Sha256 = Sha2_32(Sha256Params);
|
||||
|
||||
fn Sha2_32(comptime params: Sha2Params32) type {
|
||||
@ -80,34 +88,31 @@ fn Sha2_32(comptime params: Sha2Params32) type {
|
||||
const Self = @This();
|
||||
pub const block_length = 64;
|
||||
pub const digest_length = params.out_len / 8;
|
||||
pub const Options = struct {};
|
||||
|
||||
s: [8]u32,
|
||||
// Streaming Cache
|
||||
buf: [64]u8,
|
||||
buf_len: u8,
|
||||
total_len: u64,
|
||||
buf: [64]u8 = undefined,
|
||||
buf_len: u8 = 0,
|
||||
total_len: u64 = 0,
|
||||
|
||||
pub fn init() Self {
|
||||
var d: Self = undefined;
|
||||
d.reset();
|
||||
return d;
|
||||
pub fn init(options: Options) Self {
|
||||
return Self{
|
||||
.s = [_]u32{
|
||||
params.iv0,
|
||||
params.iv1,
|
||||
params.iv2,
|
||||
params.iv3,
|
||||
params.iv4,
|
||||
params.iv5,
|
||||
params.iv6,
|
||||
params.iv7,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
pub fn reset(d: *Self) void {
|
||||
d.s[0] = params.iv0;
|
||||
d.s[1] = params.iv1;
|
||||
d.s[2] = params.iv2;
|
||||
d.s[3] = params.iv3;
|
||||
d.s[4] = params.iv4;
|
||||
d.s[5] = params.iv5;
|
||||
d.s[6] = params.iv6;
|
||||
d.s[7] = params.iv7;
|
||||
d.buf_len = 0;
|
||||
d.total_len = 0;
|
||||
}
|
||||
|
||||
pub fn hash(b: []const u8, out: []u8) void {
|
||||
var d = Self.init();
|
||||
pub fn hash(b: []const u8, out: []u8, options: Options) void {
|
||||
var d = Self.init(options);
|
||||
d.update(b);
|
||||
d.final(out);
|
||||
}
|
||||
@ -292,18 +297,18 @@ test "sha224 single" {
|
||||
}
|
||||
|
||||
test "sha224 streaming" {
|
||||
var h = Sha224.init();
|
||||
var h = Sha224.init(.{});
|
||||
var out: [28]u8 = undefined;
|
||||
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("d14a028c2a3a2bc9476102bb288234c415a2b01f828ea62ac5b3e42f", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha224.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("23097d223405d8228642a477bda255b32aadbce4bda0b3f7e36c9da7", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha224.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -318,18 +323,18 @@ test "sha256 single" {
|
||||
}
|
||||
|
||||
test "sha256 streaming" {
|
||||
var h = Sha256.init();
|
||||
var h = Sha256.init(.{});
|
||||
var out: [32]u8 = undefined;
|
||||
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha256.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("ba7816bf8f01cfea414140de5dae2223b00361a396177a9cb410ff61f20015ad", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha256.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -341,7 +346,7 @@ test "sha256 aligned final" {
|
||||
var block = [_]u8{0} ** Sha256.block_length;
|
||||
var out: [Sha256.digest_length]u8 = undefined;
|
||||
|
||||
var h = Sha256.init();
|
||||
var h = Sha256.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
}
|
||||
@ -413,42 +418,72 @@ const Sha512Params = Sha2Params64{
|
||||
.out_len = 512,
|
||||
};
|
||||
|
||||
const Sha512256Params = Sha2Params64{
|
||||
.iv0 = 0x22312194FC2BF72C,
|
||||
.iv1 = 0x9F555FA3C84C64C2,
|
||||
.iv2 = 0x2393B86B6F53B151,
|
||||
.iv3 = 0x963877195940EABD,
|
||||
.iv4 = 0x96283EE2A88EFFE3,
|
||||
.iv5 = 0xBE5E1E2553863992,
|
||||
.iv6 = 0x2B0199FC2C85B8AA,
|
||||
.iv7 = 0x0EB72DDC81C52CA2,
|
||||
.out_len = 256,
|
||||
};
|
||||
|
||||
const Sha512T256Params = Sha2Params64{
|
||||
.iv0 = 0x6A09E667F3BCC908,
|
||||
.iv1 = 0xBB67AE8584CAA73B,
|
||||
.iv2 = 0x3C6EF372FE94F82B,
|
||||
.iv3 = 0xA54FF53A5F1D36F1,
|
||||
.iv4 = 0x510E527FADE682D1,
|
||||
.iv5 = 0x9B05688C2B3E6C1F,
|
||||
.iv6 = 0x1F83D9ABFB41BD6B,
|
||||
.iv7 = 0x5BE0CD19137E2179,
|
||||
.out_len = 256,
|
||||
};
|
||||
|
||||
/// SHA-384
|
||||
pub const Sha384 = Sha2_64(Sha384Params);
|
||||
|
||||
/// SHA-512
|
||||
pub const Sha512 = Sha2_64(Sha512Params);
|
||||
|
||||
/// SHA-512/256
|
||||
pub const Sha512256 = Sha2_64(Sha512256Params);
|
||||
|
||||
/// Truncated SHA-512
|
||||
pub const Sha512T256 = Sha2_64(Sha512T256Params);
|
||||
|
||||
fn Sha2_64(comptime params: Sha2Params64) type {
|
||||
return struct {
|
||||
const Self = @This();
|
||||
pub const block_length = 128;
|
||||
pub const digest_length = params.out_len / 8;
|
||||
pub const Options = struct {};
|
||||
|
||||
s: [8]u64,
|
||||
// Streaming Cache
|
||||
buf: [128]u8,
|
||||
buf_len: u8,
|
||||
total_len: u128,
|
||||
buf: [128]u8 = undefined,
|
||||
buf_len: u8 = 0,
|
||||
total_len: u128 = 0,
|
||||
|
||||
pub fn init() Self {
|
||||
var d: Self = undefined;
|
||||
d.reset();
|
||||
return d;
|
||||
pub fn init(options: Options) Self {
|
||||
return Self{
|
||||
.s = [_]u64{
|
||||
params.iv0,
|
||||
params.iv1,
|
||||
params.iv2,
|
||||
params.iv3,
|
||||
params.iv4,
|
||||
params.iv5,
|
||||
params.iv6,
|
||||
params.iv7,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
pub fn reset(d: *Self) void {
|
||||
d.s[0] = params.iv0;
|
||||
d.s[1] = params.iv1;
|
||||
d.s[2] = params.iv2;
|
||||
d.s[3] = params.iv3;
|
||||
d.s[4] = params.iv4;
|
||||
d.s[5] = params.iv5;
|
||||
d.s[6] = params.iv6;
|
||||
d.s[7] = params.iv7;
|
||||
d.buf_len = 0;
|
||||
d.total_len = 0;
|
||||
}
|
||||
|
||||
pub fn hash(b: []const u8, out: []u8) void {
|
||||
var d = Self.init();
|
||||
pub fn hash(b: []const u8, out: []u8, options: Options) void {
|
||||
var d = Self.init(options);
|
||||
d.update(b);
|
||||
d.final(out);
|
||||
}
|
||||
@ -660,7 +695,7 @@ test "sha384 single" {
|
||||
}
|
||||
|
||||
test "sha384 streaming" {
|
||||
var h = Sha384.init();
|
||||
var h = Sha384.init(.{});
|
||||
var out: [48]u8 = undefined;
|
||||
|
||||
const h1 = "38b060a751ac96384cd9327eb1b1e36a21fdb71114be07434c0cc7bf63f6e1da274edebfe76f65fbd51ad2f14898b95b";
|
||||
@ -669,12 +704,12 @@ test "sha384 streaming" {
|
||||
|
||||
const h2 = "cb00753f45a35e8bb5a03d699ac65007272c32ab0eded1631a8b605a43ff5bed8086072ba1e7cc2358baeca134c825a7";
|
||||
|
||||
h.reset();
|
||||
h = Sha384.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha384.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -694,7 +729,7 @@ test "sha512 single" {
|
||||
}
|
||||
|
||||
test "sha512 streaming" {
|
||||
var h = Sha512.init();
|
||||
var h = Sha512.init(.{});
|
||||
var out: [64]u8 = undefined;
|
||||
|
||||
const h1 = "cf83e1357eefb8bdf1542850d66d8007d620e4050b5715dc83f4a921d36ce9ce47d0d13c5d85f2b0ff8318d2877eec2f63b931bd47417a81a538327af927da3e";
|
||||
@ -703,12 +738,12 @@ test "sha512 streaming" {
|
||||
|
||||
const h2 = "ddaf35a193617abacc417349ae20413112e6fa4e89a97ea20a9eeee64b55d39a2192992a274fc1a836ba3c23a3feebbd454d4423643ce80e2a9ac94fa54ca49f";
|
||||
|
||||
h.reset();
|
||||
h = Sha512.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha512.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -720,7 +755,7 @@ test "sha512 aligned final" {
|
||||
var block = [_]u8{0} ** Sha512.block_length;
|
||||
var out: [Sha512.digest_length]u8 = undefined;
|
||||
|
||||
var h = Sha512.init();
|
||||
var h = Sha512.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
}
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const mem = @import("../mem.zig");
|
||||
const math = @import("../math.zig");
|
||||
const endian = @import("../endian.zig");
|
||||
@ -15,25 +20,18 @@ fn Keccak(comptime bits: usize, comptime delim: u8) type {
|
||||
const Self = @This();
|
||||
pub const block_length = 200;
|
||||
pub const digest_length = bits / 8;
|
||||
pub const Options = struct {};
|
||||
|
||||
s: [200]u8,
|
||||
offset: usize,
|
||||
rate: usize,
|
||||
|
||||
pub fn init() Self {
|
||||
var d: Self = undefined;
|
||||
d.reset();
|
||||
return d;
|
||||
pub fn init(options: Options) Self {
|
||||
return Self{ .s = [_]u8{0} ** 200, .offset = 0, .rate = 200 - (bits / 4) };
|
||||
}
|
||||
|
||||
pub fn reset(d: *Self) void {
|
||||
mem.set(u8, d.s[0..], 0);
|
||||
d.offset = 0;
|
||||
d.rate = 200 - (bits / 4);
|
||||
}
|
||||
|
||||
pub fn hash(b: []const u8, out: []u8) void {
|
||||
var d = Self.init();
|
||||
pub fn hash(b: []const u8, out: []u8, options: Options) void {
|
||||
var d = Self.init(options);
|
||||
d.update(b);
|
||||
d.final(out);
|
||||
}
|
||||
@ -178,18 +176,18 @@ test "sha3-224 single" {
|
||||
}
|
||||
|
||||
test "sha3-224 streaming" {
|
||||
var h = Sha3_224.init();
|
||||
var h = Sha3_224.init(.{});
|
||||
var out: [28]u8 = undefined;
|
||||
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("6b4e03423667dbb73b6e15454f0eb1abd4597f9a1b078e3f5b5a6bc7", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha3_224.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("e642824c3f8cf24ad09234ee7d3c766fc9a3a5168d0c94ad73b46fdf", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha3_224.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -204,18 +202,18 @@ test "sha3-256 single" {
|
||||
}
|
||||
|
||||
test "sha3-256 streaming" {
|
||||
var h = Sha3_256.init();
|
||||
var h = Sha3_256.init(.{});
|
||||
var out: [32]u8 = undefined;
|
||||
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("a7ffc6f8bf1ed76651c14756a061d662f580ff4de43b49fa82d80a4b80f8434a", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha3_256.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual("3a985da74fe225b2045c172d6bd390bd855f086e3e9d525b46bfe24511431532", out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha3_256.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -227,7 +225,7 @@ test "sha3-256 aligned final" {
|
||||
var block = [_]u8{0} ** Sha3_256.block_length;
|
||||
var out: [Sha3_256.digest_length]u8 = undefined;
|
||||
|
||||
var h = Sha3_256.init();
|
||||
var h = Sha3_256.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
}
|
||||
@ -242,7 +240,7 @@ test "sha3-384 single" {
|
||||
}
|
||||
|
||||
test "sha3-384 streaming" {
|
||||
var h = Sha3_384.init();
|
||||
var h = Sha3_384.init(.{});
|
||||
var out: [48]u8 = undefined;
|
||||
|
||||
const h1 = "0c63a75b845e4f7d01107d852e4c2485c51a50aaaa94fc61995e71bbee983a2ac3713831264adb47fb6bd1e058d5f004";
|
||||
@ -250,12 +248,12 @@ test "sha3-384 streaming" {
|
||||
htest.assertEqual(h1, out[0..]);
|
||||
|
||||
const h2 = "ec01498288516fc926459f58e2c6ad8df9b473cb0fc08c2596da7cf0e49be4b298d88cea927ac7f539f1edf228376d25";
|
||||
h.reset();
|
||||
h = Sha3_384.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha3_384.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -273,7 +271,7 @@ test "sha3-512 single" {
|
||||
}
|
||||
|
||||
test "sha3-512 streaming" {
|
||||
var h = Sha3_512.init();
|
||||
var h = Sha3_512.init(.{});
|
||||
var out: [64]u8 = undefined;
|
||||
|
||||
const h1 = "a69f73cca23a9ac5c8b567dc185a756e97c982164fe25859e0d1dcc1475c80a615b2123af1f5f94c11e3e9402c3ac558f500199d95b6d3e301758586281dcd26";
|
||||
@ -281,12 +279,12 @@ test "sha3-512 streaming" {
|
||||
htest.assertEqual(h1, out[0..]);
|
||||
|
||||
const h2 = "b751850b1a57168a5693cd924b6b096e08f621827444f70d884f5d0240d2712e10e116e9192af3c91a7ec57647e3934057340b4cf408d5a56592f8274eec53f0";
|
||||
h.reset();
|
||||
h = Sha3_512.init(.{});
|
||||
h.update("abc");
|
||||
h.final(out[0..]);
|
||||
htest.assertEqual(h2, out[0..]);
|
||||
|
||||
h.reset();
|
||||
h = Sha3_512.init(.{});
|
||||
h.update("a");
|
||||
h.update("b");
|
||||
h.update("c");
|
||||
@ -298,7 +296,7 @@ test "sha3-512 aligned final" {
|
||||
var block = [_]u8{0} ** Sha3_512.block_length;
|
||||
var out: [Sha3_512.digest_length]u8 = undefined;
|
||||
|
||||
var h = Sha3_512.init();
|
||||
var h = Sha3_512.init(.{});
|
||||
h.update(&block);
|
||||
h.final(out[0..]);
|
||||
}
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const testing = std.testing;
|
||||
const mem = std.mem;
|
||||
@ -6,7 +11,7 @@ const fmt = std.fmt;
|
||||
// Hash using the specified hasher `H` asserting `expected == H(input)`.
|
||||
pub fn assertEqualHash(comptime Hasher: anytype, comptime expected: []const u8, input: []const u8) void {
|
||||
var h: [expected.len / 2]u8 = undefined;
|
||||
Hasher.hash(input, h[0..]);
|
||||
Hasher.hash(input, h[0..], .{});
|
||||
|
||||
assertEqual(expected, &h);
|
||||
}
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const debug = std.debug;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const builtin = std.builtin;
|
||||
const math = std.math;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const testing = std.testing;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const debug = std.debug;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const TAG_padding = 0x00;
|
||||
pub const TAG_array_type = 0x01;
|
||||
pub const TAG_class_type = 0x02;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const builtin = @import("builtin");
|
||||
|
||||
const std = @import("std.zig");
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const builtin = std.builtin;
|
||||
const io = std.io;
|
||||
@ -558,6 +563,7 @@ fn preadNoEof(file: std.fs.File, buf: []u8, offset: u64) !void {
|
||||
error.InputOutput => return error.FileSystem,
|
||||
error.Unexpected => return error.Unexpected,
|
||||
error.WouldBlock => return error.Unexpected,
|
||||
error.NotOpenForReading => return error.Unexpected,
|
||||
error.AccessDenied => return error.Unexpected,
|
||||
};
|
||||
if (len == 0) return error.UnexpectedEndOfFile;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const Channel = @import("event/channel.zig").Channel;
|
||||
pub const Future = @import("event/future.zig").Future;
|
||||
pub const Group = @import("event/group.zig").Group;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const testing = std.testing;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const assert = std.debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const assert = std.debug.assert;
|
||||
const testing = std.testing;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const Lock = std.event.Lock;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const assert = std.debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const Lock = std.event.Lock;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const root = @import("root");
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const assert = std.debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const RwLock = std.event.RwLock;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// FIFO of fixed size items
|
||||
// Usually used for e.g. byte buffers
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std.zig");
|
||||
const math = std.math;
|
||||
const assert = std.debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const enum3 = @import("errol/enum3.zig").enum3;
|
||||
const enum3_data = @import("errol/enum3.zig").enum3_data;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const enum3 = [_]u64{
|
||||
0x4e2e2785c3a2a20b,
|
||||
0x240a28877a09a4e1,
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
pub const HP = struct {
|
||||
val: f64,
|
||||
off: f64,
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// Adapted from https://github.com/grzegorz-kraszewski/stringtofloat.
|
||||
|
||||
// MIT License
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const builtin = @import("builtin");
|
||||
const std = @import("std.zig");
|
||||
const os = std.os;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const os = std.os;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const unicode = std.unicode;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const builtin = @import("builtin");
|
||||
const std = @import("../std.zig");
|
||||
const debug = std.debug;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const testing = std.testing;
|
||||
const builtin = std.builtin;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const os = std.os;
|
||||
const mem = std.mem;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("../std.zig");
|
||||
const builtin = @import("builtin");
|
||||
const event = std.event;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const adler = @import("hash/adler.zig");
|
||||
pub const Adler32 = adler.Adler32;
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// Adler32 checksum.
|
||||
//
|
||||
// https://tools.ietf.org/html/rfc1950#section-9
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const builtin = @import("builtin");
|
||||
const assert = std.debug.assert;
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// zig run benchmark.zig --release-fast --override-lib-dir ..
|
||||
|
||||
const builtin = @import("builtin");
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const builtin = @import("builtin");
|
||||
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// There are two implementations of CRC32 implemented with the following key characteristics:
|
||||
//
|
||||
// - Crc32WithPoly uses 8Kb of tables but is ~10x faster than the small method.
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
// FNV1a - Fowler-Noll-Vo hash function
|
||||
//
|
||||
// FNV1a is a fast, non-cryptographic hash function with fairly good distribution properties.
|
||||
|
||||
@ -1,3 +1,8 @@
|
||||
// SPDX-License-Identifier: MIT
|
||||
// Copyright (c) 2015-2020 Zig Contributors
|
||||
// This file is part of [zig](https://ziglang.org/), which is MIT licensed.
|
||||
// The MIT license requires this copyright notice to be included in all copies
|
||||
// and substantial portions of the software.
|
||||
const std = @import("std");
|
||||
const builtin = @import("builtin");
|
||||
const testing = std.testing;
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Loading…
x
Reference in New Issue
Block a user