diff options
author | Rutger Broekhoff | 2021-05-25 15:33:45 +0200 |
---|---|---|
committer | Rutger Broekhoff | 2021-05-25 15:33:45 +0200 |
commit | 6ab0780b0240bcb47f78d35904f57694a52976f0 (patch) | |
tree | 5fc86d49db5fc04fd34e1ae0f27043364094b9b7 | |
parent | 60c08f0a418df148793870cdbde4b2a2cec73bd0 (diff) | |
download | zig-nkeys-6ab0780b0240bcb47f78d35904f57694a52976f0.tar.gz zig-nkeys-6ab0780b0240bcb47f78d35904f57694a52976f0.zip |
Reorder src/nkeys.zig
-rw-r--r-- | src/nkeys.zig | 94 |
1 files changed, 47 insertions, 47 deletions
diff --git a/src/nkeys.zig b/src/nkeys.zig index 42a781f..b7fd520 100644 --- a/src/nkeys.zig +++ b/src/nkeys.zig | |||
@@ -25,14 +25,14 @@ pub const KeyTypePrefixByte = enum(u8) { | |||
25 | seed = 18 << 3, // S | 25 | seed = 18 << 3, // S |
26 | private = 15 << 3, // P | 26 | private = 15 << 3, // P |
27 | 27 | ||
28 | fn char(self: Self) u8 { | 28 | pub fn char(self: Self) u8 { |
29 | return switch (self) { | 29 | return switch (self) { |
30 | .seed => 'S', | 30 | .seed => 'S', |
31 | .private => 'P', | 31 | .private => 'P', |
32 | }; | 32 | }; |
33 | } | 33 | } |
34 | 34 | ||
35 | fn fromChar(c: u8) InvalidPrefixByteError!Self { | 35 | pub fn fromChar(c: u8) InvalidPrefixByteError!Self { |
36 | return switch (c) { | 36 | return switch (c) { |
37 | 'S' => .seed, | 37 | 'S' => .seed, |
38 | 'P' => .private, | 38 | 'P' => .private, |
@@ -50,7 +50,7 @@ pub const PublicPrefixByte = enum(u8) { | |||
50 | server = 13 << 3, // N | 50 | server = 13 << 3, // N |
51 | user = 20 << 3, // U | 51 | user = 20 << 3, // U |
52 | 52 | ||
53 | fn fromU8(b: u8) InvalidPrefixByteError!PublicPrefixByte { | 53 | pub fn fromU8(b: u8) InvalidPrefixByteError!PublicPrefixByte { |
54 | return switch (b) { | 54 | return switch (b) { |
55 | @enumToInt(PublicPrefixByte.server) => .server, | 55 | @enumToInt(PublicPrefixByte.server) => .server, |
56 | @enumToInt(PublicPrefixByte.cluster) => .cluster, | 56 | @enumToInt(PublicPrefixByte.cluster) => .cluster, |
@@ -61,7 +61,7 @@ pub const PublicPrefixByte = enum(u8) { | |||
61 | }; | 61 | }; |
62 | } | 62 | } |
63 | 63 | ||
64 | fn char(self: Self) u8 { | 64 | pub fn char(self: Self) u8 { |
65 | return switch (self) { | 65 | return switch (self) { |
66 | .account => 'A', | 66 | .account => 'A', |
67 | .cluster => 'C', | 67 | .cluster => 'C', |
@@ -71,7 +71,7 @@ pub const PublicPrefixByte = enum(u8) { | |||
71 | }; | 71 | }; |
72 | } | 72 | } |
73 | 73 | ||
74 | fn fromChar(c: u8) InvalidPrefixByteError!Self { | 74 | pub fn fromChar(c: u8) InvalidPrefixByteError!Self { |
75 | return switch (c) { | 75 | return switch (c) { |
76 | 'A' => .account, | 76 | 'A' => .account, |
77 | 'C' => .cluster, | 77 | 'C' => .cluster, |
@@ -83,6 +83,21 @@ pub const PublicPrefixByte = enum(u8) { | |||
83 | } | 83 | } |
84 | }; | 84 | }; |
85 | 85 | ||
86 | // One prefix byte, two CRC bytes | ||
87 | const binary_private_size = 1 + Ed25519.secret_length + 2; | ||
88 | // One prefix byte, two CRC bytes | ||
89 | const binary_public_size = 1 + Ed25519.public_length + 2; | ||
90 | // Two prefix bytes, two CRC bytes | ||
91 | const binary_seed_size = 2 + Ed25519.seed_length + 2; | ||
92 | |||
93 | pub const text_private_len = base32.Encoder.calcSize(binary_private_size); | ||
94 | pub const text_public_len = base32.Encoder.calcSize(binary_public_size); | ||
95 | pub const text_seed_len = base32.Encoder.calcSize(binary_seed_size); | ||
96 | |||
97 | pub const text_private = [text_private_len]u8; | ||
98 | pub const text_public = [text_public_len]u8; | ||
99 | pub const text_seed = [text_seed_len]u8; | ||
100 | |||
86 | pub const SeedKeyPair = struct { | 101 | pub const SeedKeyPair = struct { |
87 | const Self = @This(); | 102 | const Self = @This(); |
88 | 103 | ||
@@ -168,15 +183,6 @@ pub const SeedKeyPair = struct { | |||
168 | } | 183 | } |
169 | }; | 184 | }; |
170 | 185 | ||
171 | fn wipeKeyPair(kp: *Ed25519.KeyPair) void { | ||
172 | wipeBytes(&kp.public_key); | ||
173 | wipeBytes(&kp.secret_key); | ||
174 | } | ||
175 | |||
176 | fn wipeBytes(bs: []u8) void { | ||
177 | for (bs) |*b| b.* = 0; | ||
178 | } | ||
179 | |||
180 | pub const PublicKey = struct { | 186 | pub const PublicKey = struct { |
181 | const Self = @This(); | 187 | const Self = @This(); |
182 | 188 | ||
@@ -272,21 +278,6 @@ pub const PrivateKey = struct { | |||
272 | } | 278 | } |
273 | }; | 279 | }; |
274 | 280 | ||
275 | // One prefix byte, two CRC bytes | ||
276 | const binary_private_size = 1 + Ed25519.secret_length + 2; | ||
277 | // One prefix byte, two CRC bytes | ||
278 | const binary_public_size = 1 + Ed25519.public_length + 2; | ||
279 | // Two prefix bytes, two CRC bytes | ||
280 | const binary_seed_size = 2 + Ed25519.seed_length + 2; | ||
281 | |||
282 | pub const text_private_len = base32.Encoder.calcSize(binary_private_size); | ||
283 | pub const text_public_len = base32.Encoder.calcSize(binary_public_size); | ||
284 | pub const text_seed_len = base32.Encoder.calcSize(binary_seed_size); | ||
285 | |||
286 | pub const text_private = [text_private_len]u8; | ||
287 | pub const text_public = [text_public_len]u8; | ||
288 | pub const text_seed = [text_seed_len]u8; | ||
289 | |||
290 | fn encoded_key(comptime prefix_len: usize, comptime data_len: usize) type { | 281 | fn encoded_key(comptime prefix_len: usize, comptime data_len: usize) type { |
291 | return [base32.Encoder.calcSize(prefix_len + data_len + 2)]u8; | 282 | return [base32.Encoder.calcSize(prefix_len + data_len + 2)]u8; |
292 | } | 283 | } |
@@ -429,7 +420,27 @@ pub fn parseDecoratedJwt(contents: []const u8) []const u8 { | |||
429 | return findKeySection(contents, &line_it) orelse return contents; | 420 | return findKeySection(contents, &line_it) orelse return contents; |
430 | } | 421 | } |
431 | 422 | ||
432 | fn validNkey(text: []const u8) bool { | 423 | pub fn parseDecoratedNkey(contents: []const u8) NoNkeySeedFoundError!SeedKeyPair { |
424 | var line_it = mem.split(contents, "\n"); | ||
425 | var current_off: usize = 0; | ||
426 | var seed: ?[]const u8 = null; | ||
427 | if (findKeySection(contents, &line_it) != null) | ||
428 | seed = findKeySection(contents, &line_it); | ||
429 | if (seed == null) | ||
430 | seed = findNkey(contents) orelse return error.NoNkeySeedFound; | ||
431 | if (!isValidCredsNkey(seed.?)) | ||
432 | return error.NoNkeySeedFound; | ||
433 | return SeedKeyPair.fromTextSeed(seed.?[0..text_seed_len]) catch return error.NoNkeySeedFound; | ||
434 | } | ||
435 | |||
436 | pub fn parseDecoratedUserNkey(contents: []const u8) (NoNkeySeedFoundError || NoNkeyUserSeedFoundError)!SeedKeyPair { | ||
437 | var key = try parseDecoratedNkey(contents); | ||
438 | if (!mem.startsWith(u8, &key.seedText(), "SU")) return error.NoNkeyUserSeedFound; | ||
439 | defer key.wipe(); | ||
440 | return key; | ||
441 | } | ||
442 | |||
443 | fn isValidCredsNkey(text: []const u8) bool { | ||
433 | const valid_prefix = | 444 | const valid_prefix = |
434 | mem.startsWith(u8, text, "SO") or | 445 | mem.startsWith(u8, text, "SO") or |
435 | mem.startsWith(u8, text, "SA") or | 446 | mem.startsWith(u8, text, "SA") or |
@@ -444,7 +455,7 @@ fn findNkey(text: []const u8) ?[]const u8 { | |||
444 | while (line_it.next()) |line| { | 455 | while (line_it.next()) |line| { |
445 | for (line) |c, i| { | 456 | for (line) |c, i| { |
446 | if (!ascii.isSpace(c)) { | 457 | if (!ascii.isSpace(c)) { |
447 | if (validNkey(line[i..])) return line[i..]; | 458 | if (isValidCredsNkey(line[i..])) return line[i..]; |
448 | break; | 459 | break; |
449 | } | 460 | } |
450 | } | 461 | } |
@@ -452,24 +463,13 @@ fn findNkey(text: []const u8) ?[]const u8 { | |||
452 | return null; | 463 | return null; |
453 | } | 464 | } |
454 | 465 | ||
455 | pub fn parseDecoratedNkey(contents: []const u8) NoNkeySeedFoundError!SeedKeyPair { | 466 | fn wipeKeyPair(kp: *Ed25519.KeyPair) void { |
456 | var line_it = mem.split(contents, "\n"); | 467 | wipeBytes(&kp.public_key); |
457 | var current_off: usize = 0; | 468 | wipeBytes(&kp.secret_key); |
458 | var seed: ?[]const u8 = null; | ||
459 | if (findKeySection(contents, &line_it) != null) | ||
460 | seed = findKeySection(contents, &line_it); | ||
461 | if (seed == null) | ||
462 | seed = findNkey(contents) orelse return error.NoNkeySeedFound; | ||
463 | if (!validNkey(seed.?)) | ||
464 | return error.NoNkeySeedFound; | ||
465 | return SeedKeyPair.fromTextSeed(seed.?[0..text_seed_len]) catch return error.NoNkeySeedFound; | ||
466 | } | 469 | } |
467 | 470 | ||
468 | pub fn parseDecoratedUserNkey(contents: []const u8) (NoNkeySeedFoundError || NoNkeyUserSeedFoundError)!SeedKeyPair { | 471 | fn wipeBytes(bs: []u8) void { |
469 | var key = try parseDecoratedNkey(contents); | 472 | for (bs) |*b| b.* = 0; |
470 | if (!mem.startsWith(u8, &key.seedText(), "SU")) return error.NoNkeyUserSeedFound; | ||
471 | defer key.wipe(); | ||
472 | return key; | ||
473 | } | 473 | } |
474 | 474 | ||
475 | test { | 475 | test { |