authorgravatar for 124872+jedisct1@users.noreply.github.comFrank Denis <124872+jedisct1@users.noreply.github.com> 2023-03-07 12:19:38+01:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2023-03-07 17:45:31-05:00
log8da6b393fb6f34ba8cbe3efaf1dac4d459c05d5b
tree890bdcd3a300fa12fbe3a1be75faeb8b95db87e8
parent36d47dd1991f0ccd7a9673075624f09500cc415e

std.fmt: add bytesToHex() to encode bytes as hex digits

We already had `hexToBytes()`, but not the reverse operation (at least not without using formatters).

1 files changed, 22 insertions(+), 0 deletions(-)

lib/std/fmt.zig+22
...@@ -2555,6 +2555,21 @@ test "bytes.hex" {...@@ -2555,6 +2555,21 @@ test "bytes.hex" {
2555 try expectFmt("lowercase: 000ebabe\n", "lowercase: {x}\n", .{fmtSliceHexLower(bytes_with_zeros)});2555 try expectFmt("lowercase: 000ebabe\n", "lowercase: {x}\n", .{fmtSliceHexLower(bytes_with_zeros)});
2556}2556}
25572557
2558/// Encodes a sequence of bytes as hexadecimal digits.
2559/// Returns an array containing the encoded bytes.
2560pub fn bytesToHex(input: anytype, case: Case) [input.len * 2]u8 {
2561 if (input.len == 0) return [_]u8{};
2562 comptime assert(@TypeOf(input[0]) == u8); // elements to encode must be unsigned bytes
2563
2564 const charset = "0123456789" ++ if (case == .upper) "ABCDEF" else "abcdef";
2565 var result: [input.len * 2]u8 = undefined;
2566 for (input, 0..) |b, i| {
2567 result[i * 2 + 0] = charset[b >> 4];
2568 result[i * 2 + 1] = charset[b & 15];
2569 }
2570 return result;
2571}
2572
2558/// Decodes the sequence of bytes represented by the specified string of2573/// Decodes the sequence of bytes represented by the specified string of
2559/// hexadecimal characters.2574/// hexadecimal characters.
2560/// Returns a slice of the output buffer containing the decoded bytes.2575/// Returns a slice of the output buffer containing the decoded bytes.
...@@ -2575,6 +2590,13 @@ pub fn hexToBytes(out: []u8, input: []const u8) ![]u8 {...@@ -2575,6 +2590,13 @@ pub fn hexToBytes(out: []u8, input: []const u8) ![]u8 {
2575 return out[0 .. in_i / 2];2590 return out[0 .. in_i / 2];
2576}2591}
25772592
2593test "bytesToHex" {
2594 const input = "input slice";
2595 const encoded = bytesToHex(input, .lower);
2596 var decoded: [input.len]u8 = undefined;
2597 try std.testing.expectEqualSlices(u8, input, try hexToBytes(&decoded, &encoded));
2598}
2599
2578test "hexToBytes" {2600test "hexToBytes" {
2579 var buf: [32]u8 = undefined;2601 var buf: [32]u8 = undefined;
2580 try expectFmt("90" ** 32, "{s}", .{fmtSliceHexUpper(try hexToBytes(&buf, "90" ** 32))});2602 try expectFmt("90" ** 32, "{s}", .{fmtSliceHexUpper(try hexToBytes(&buf, "90" ** 32))});