tiny.quic.crypto.header
Defined in crypto.
API (8)
Actions
Public operations.
Types and contracts
Public types and contracts.
Values and defaults
Public values and defaults.
Source
Source: lib/quic/src/crypto/header.zig
zig
const std = @import("std");const quic = @import("../root.zig");const crypto = quic.crypto;const Aes128 = std.crypto.core.aes.Aes128;const ChaCha20 = std.crypto.stream.chacha.ChaCha20IETF;pub const sample_bytes: usize = 16;pub const mask_bytes: usize = 5;pub const ApplyError = error{ InvalidPacketNumberLength, InvalidPacketNumberOffset, TruncatedPacket,};pub const Inspected = struct { first_byte: u8, pn_len: u3,};pub fn mask(keys: *const crypto.Keys, sample: *const [sample_bytes]u8) [mask_bytes]u8 { return switch (keys.selectedSuite()) { .aes_128_gcm_sha256 => aesMask(keys, sample), .chacha20_poly1305_sha256 => chachaMask(keys, sample), };}fn aesMask(keys: *const crypto.Keys, sample: *const [sample_bytes]u8) [mask_bytes]u8 { const header_key = keys.headerKey(); const hp_key: [16]u8 = header_key[0..16].*; const cipher = Aes128.initEnc(hp_key); var block: [sample_bytes]u8 = undefined; cipher.encrypt(&block, sample); return block[0..mask_bytes].*;}fn chachaMask(keys: *const crypto.Keys, sample: *const [sample_bytes]u8) [mask_bytes]u8 { const counter = std.mem.readInt(u32, sample[0..4], .little); const nonce: [12]u8 = sample[4..16].*; var zeros: [mask_bytes]u8 = @splat(0); var result: [mask_bytes]u8 = undefined; ChaCha20.xor(&result, &zeros, counter, keys.headerKey(), nonce); return result;}fn protectedBits(first: u8) u8 { return if (first & 0x80 != 0) 0x0f else 0x1f;}fn validate(packet: []const u8, pn_offset: usize, pn_len: u3) ApplyError!void { if (packet.len == 0) return error.TruncatedPacket; if (pn_offset == 0) return error.InvalidPacketNumberOffset; if (pn_len == 0 or pn_len > 4) return error.InvalidPacketNumberLength; if (pn_offset > packet.len) return error.TruncatedPacket; if (pn_len > packet.len - pn_offset) return error.TruncatedPacket;}pub fn inspect( protection_mask: [mask_bytes]u8, packet: []const u8, pn_offset: usize,) ApplyError!Inspected { if (packet.len == 0) return error.TruncatedPacket; if (pn_offset == 0) return error.InvalidPacketNumberOffset; const first = packet[0] ^ (protection_mask[0] & protectedBits(packet[0])); const pn_len = quic.packet.packetNumberLength(first); try validate(packet, pn_offset, pn_len); return .{ .first_byte = first, .pn_len = pn_len };}pub fn protect( protection_mask: [mask_bytes]u8, packet: []u8, pn_offset: usize, pn_len: u3,) ApplyError!void { try validate(packet, pn_offset, pn_len); packet[0] ^= protection_mask[0] & protectedBits(packet[0]); for (0..4) |index| { if (index >= pn_len) break; packet[pn_offset + index] ^= protection_mask[index + 1]; }}pub fn unprotect( protection_mask: [mask_bytes]u8, packet: []u8, pn_offset: usize,) ApplyError!u3 { const inspected = try inspect(protection_mask, packet, pn_offset); packet[0] = inspected.first_byte; for (0..4) |index| { if (index >= inspected.pn_len) break; packet[pn_offset + index] ^= protection_mask[index + 1]; } return inspected.pn_len;}Source: lib/quic/src/crypto/root.zig:17
zig
pub const header = @import("header.zig");Audit
| Definitions | 9 |
|---|---|
| Public names | 9 |
| Members | 5 |
| Version | 26.7.0 |
| Revision | daab053ee433 |