Commit Graph

694 Commits

Author SHA1 Message Date
andrewkraevskii de489031d8 Remove usages of deprecatedWriter 2025-09-18 22:39:33 -07:00
Andrew Kelley b782cdb9b3 Merge pull request #25249 from jedisct1/siv
std.crypto: add AES-SIV and AES-GCM-SIV
2025-09-17 20:05:23 -07:00
Frank Denis 4406127cca std.crypto: add Ascon-AEAD, Ascon-Hash, Ascon-CHash (#25239)
Ascon is the family of cryptographic constructions standardized by NIST
for lightweight cryptography.

The Zig standard library already included the Ascon permutation itself,
but higher-level constructions built on top of it were intentionally
postponed until NIST released the final specification.

That specification has now been published as NIST SP 800-232:
https://csrc.nist.gov/pubs/sp/800/232/final

With this publication, we can now confidently include these constructions
in the standard library.
2025-09-17 19:59:55 -07:00
Frank Denis 8e8a143d62 Avoid logic where we return success in case of an error (#25251)
In ed25519.zig, we checked if a test succeeds, in which case we
returned an error. This was confusing, and Andrew pointed out that
Zig weights branches against errors by default.
2025-09-17 12:09:35 +02:00
Frank Denis b1b2cd7ef8 Parallelize deriveKeys 2025-09-16 23:13:58 +02:00
Frank Denis 5eb7610112 Import crypto/aes_gcm_siv.zig 2025-09-16 23:01:16 +02:00
Frank Denis dd46e07fb9 std.crypto: add AES-SIV and AES-GCM-SIV
The Zig standard library lacked schemes that resist nonce reuse.

AES-SIV and AES-GCM-SIV are the standard options for this.

AES-GCM-SIV can be very useful when Zig is used to target embedded
systems, and AES-SIV is especially useful for key wrapping.

Also take it as an opportunity to add a bunch of test vectors to
modes.ctr and make sure it works with block ciphers whose size is
not 16.
2025-09-16 12:45:08 +02:00
Frank Denis 1872c85ac2 std.crypto.ed25519: support cofactorless verification
Add verifyStrict() functions for cofactorless verification.

Also:

- Support messages < 64 characters in the test vectors
- Allow mulDoubleBasePublic to return the identity as a regular
value. There are valid use cases for this.
2025-09-08 14:25:57 -07:00
Igor Anić c41b9d7508 ECDSA signature der encoding should produce smallest number of octets (#25177)
I noticed this by stress testing my tls server implementation. From time to time curl (and other tools: ab, vegeta) will report invalid signature. I trace the problem to the way how std lib is encoding raw signature into der format. Using raw signature I got in some cases different encoding using std and openssl. Std is not producing minimal der when signature `r` or `s` integers has leading zero(es).

Here is an example to illustrate difference. Notice leading 00 in `s`
integer which is removed in openssl encoding but not in std encoding.

```Zig
const std = @import("std");

test "ecdsa signature to der" {
    // raw signature r and s bytes
    const raw = hexToBytes(
        \\ 49  63  0c  94  95  2e  ff  4b  02  bf  35  c4  97  9e  a7  24
        \\ 20  dc  94  de  aa  1b  17  ff  e1  49  25  3e  34  ef  e8  d0
        \\ c4  43  aa  7b  a9  f3  9c  b9  f8  72  7d  d7  0c  9a  13  1e
        \\
        \\ 00  56  85  43  d3  d4  05  62  a1  1d  d8  a1  45  44  b5  dd
        \\ 62  9f  d1  e0  ab  f1  cd  4a  85  d0  1f  5d  11  d9  f8  89
        \\ 89  d4  59  0c  b0  6e  ea  3c  19  6a  f7  0b  1a  4a  ce  f1
    );
    // encoded by openssl
    const expected = hexToBytes(
        \\ 30  63  02  30
        \\ 49  63  0c  94  95  2e  ff  4b  02  bf  35  c4  97  9e  a7  24
        \\ 20  dc  94  de  aa  1b  17  ff  e1  49  25  3e  34  ef  e8  d0
        \\ c4  43  aa  7b  a9  f3  9c  b9  f8  72  7d  d7  0c  9a  13  1e
        \\
        \\ 02  2f
        \\ 56  85  43  d3  d4  05  62  a1  1d  d8  a1  45  44  b5  dd
        \\ 62  9f  d1  e0  ab  f1  cd  4a  85  d0  1f  5d  11  d9  f8  89
        \\ 89  d4  59  0c  b0  6e  ea  3c  19  6a  f7  0b  1a  4a  ce  f1
    );
    // encoded by std
    const actual = hexToBytes(
        \\ 30  64  02  30
        \\ 49  63  0c  94  95  2e  ff  4b  02  bf  35  c4  97  9e  a7  24
        \\ 20  dc  94  de  aa  1b  17  ff  e1  49  25  3e  34  ef  e8  d0
        \\ c4  43  aa  7b  a9  f3  9c  b9  f8  72  7d  d7  0c  9a  13  1e
        \\
        \\ 02  30
        \\ 00  56  85  43  d3  d4  05  62  a1  1d  d8  a1  45  44  b5  dd
        \\ 62  9f  d1  e0  ab  f1  cd  4a  85  d0  1f  5d  11  d9  f8  89
        \\ 89  d4  59  0c  b0  6e  ea  3c  19  6a  f7  0b  1a  4a  ce  f1
    );
    _ = actual;

    const Ecdsa = std.crypto.sign.ecdsa.EcdsaP384Sha384;
    const sig = Ecdsa.Signature.fromBytes(raw);
    var buf: [Ecdsa.Signature.der_encoded_length_max]u8 = undefined;
    const encoded = sig.toDer(&buf);

    try std.testing.expectEqualSlices(u8, &expected, encoded);
}

pub fn hexToBytes(comptime hex: []const u8) [removeNonHex(hex).len / 2]u8 {
    @setEvalBranchQuota(1000 * 100);
    const hex2 = comptime removeNonHex(hex);
    comptime var res: [hex2.len / 2]u8 = undefined;
    _ = comptime std.fmt.hexToBytes(&res, hex2) catch unreachable;
    return res;
}
fn removeNonHex(comptime hex: []const u8) []const u8 {
    @setEvalBranchQuota(1000 * 100);
    var res: [hex.len]u8 = undefined;
    var i: usize = 0;
    for (hex) |c| {
        if (std.ascii.isHex(c)) {
            res[i] = c;
            i += 1;
        }
    }
    return res[0..i];
}
```

Trimming leading zeroes from signature integers fixes encoding.
2025-09-08 22:53:03 +02:00
Andrew Kelley b7104231af Merge pull request #25077 from ziglang/GenericReader
std.Io: delete GenericReader, AnyReader, FixedBufferStream; and related API breakage
2025-08-30 12:43:52 -07:00
Alex Rønne Petersen 66b43234bb std: disable sha3-512 single test on RISC-V with V support
https://github.com/ziglang/zig/issues/25083
2025-08-30 13:27:25 +02:00
Andrew Kelley 07da9567e6 compiler: fix macos build 2025-08-30 00:48:50 -07:00
Andrew Kelley 79f267f6b9 std.Io: delete GenericReader
and delete deprecated alias std.io
2025-08-29 17:14:26 -07:00
Andrew Kelley 888f00e856 std.crypto.ml_kem: update to not use GenericWriter 2025-08-28 18:30:57 -07:00
Andrew Kelley 9860dd475a std: delete most remaining uses of GenericWriter 2025-08-28 18:30:57 -07:00
Andrew Kelley 57dbc9e74a std.Io: delete GenericWriter 2025-08-28 18:30:57 -07:00
Frank Denis 12a58087a4 Fix TLS 1.2 client key exchange to use negotiated named group (#25007)
The TLS 1.2 implementation was incorrectly hardcoded to always send the
secp256r1 public key in the client key exchange message, regardless of
which elliptic curve the server actually negotiated.

This caused TLS handshake failures with servers that preferred other curves
like X25519.

This fix:

- Tracks the negotiated named group from the server key exchange message
- Dynamically selects the correct public key (X25519, secp256r1, or
  secp384r1) based on what the server negotiated
- Properly constructs the client key exchange message with the
  appropriate key size for each curve type

Fixes TLS 1.2 connections to servers like ziglang.freetls.fastly.net
that prefer X25519 over secp256r1.
2025-08-27 11:18:40 +02:00
Erik Schlyter 37f4bee92a Fix #24999: copy left-overs before we XOR into c. (#25001)
It is important we copy the left-overs in the message *before* we XOR
it into the ciphertext, because if we're encrypting in-place (i.e., m ==
c), we will manipulate the message that will be used for tag generation.
This will generate faulty tags when message length doesn't conform with
16 byte blocks.
2025-08-25 15:59:42 +00:00
Andrew Kelley a0f9a5e78d std: more reliable HTTP and TLS networking
* std.Io.Reader: fix confused semantics of rebase. Before it was
  ambiguous whether it was supposed to be based on end or seek. Now it
  is clearly based on seek, with an added assertion for clarity.

* std.crypto.tls.Client: fix panic due to not enough buffer size
  available. Also, avoid unnecessary rebasing.

* std.http.Reader: introduce max_head_len to limit HTTP header length.
  This prevents crash in underlying reader which may require a minimum
  buffer length.

* std.http.Client: choose better buffer sizes for streams and TLS
  client. Crucially, the buffer shared by HTTP reader and TLS client
  needs to be big enough for all http headers *and* the max TLS record
  size. Bump HTTP header size default from 4K to 8K.

fixes #24872

I have noticed however that there are still fetch problems
2025-08-16 00:16:15 -07:00
Frank Denis c1eff72c4a crypto/aes_ocb.zig: actually check against test vectors (#24835)
And use the correct bit endianness for padding
2025-08-15 13:09:06 +00:00
Frank Denis 96e4825fbb Validate wildcard TLS certificates correctly (#24829)
Validate wildcard certificates as specified in RFC 6125.

In particular, `*.example.com` should match `foo.example.com` but
NOT `bar.foo.example.com` as it previously did.
2025-08-14 13:57:00 +00:00
Erik Schlyter 7abd62800c std.crypto.aegis: Absorb ad instead of encrypting it.
`Aegis256XGeneric` behaves differently than `Aegis128XGeneric` in that
it currently encrypts associated data instead of just absorbing it. Even
though the end result is the same, there's no point in encrypting and
copying the ad into a buffer that gets overwritten anyway. This fix
makes `Aegis256XGeneric` behave the same as `Aegis128XGeneric`.
2025-08-13 09:00:57 +02:00
Andrew Kelley 749f10af49 std.ArrayList: make unmanaged the default 2025-08-11 15:52:49 -07:00
Andrew Kelley 1ba6838bc3 Merge pull request #24740 from ziglang/http-plus-fixes
fetch, tls, and http fixes
2025-08-08 12:33:53 -07:00
Andrew Kelley 94dd28b7f7 std.Io: delete CountingWriter 2025-08-07 22:26:42 -07:00
Andrew Kelley 8721efece4 std.crypto.tls.Client: always write to buffer
simplifies the logic & makes it respect limit
2025-08-07 19:55:40 -07:00
Andrew Kelley 46b34949c3 TLS, HTTP, and package fetching fixes
* TLS: add missing assert for output buffer length requirement
* TLS: add missing flushes
* TLS: add flush implementation
* TLS: finish drain implementation
* HTTP: correct buffer sizes for TLS
* HTTP: expose a getReadError method on Connection
* HTTP: add missing flush on sendBodyComplete
* Fetch: remove unwanted deinit
* Fetch: improve error reporting
2025-08-07 10:04:52 -07:00
Andrew Kelley 3837862e52 fix 32-bit builds 2025-08-07 10:04:52 -07:00
Andrew Kelley e2d81bf6c0 http fixes 2025-08-07 10:04:29 -07:00
Andrew Kelley 28190cc404 std.crypto.tls: rework for new std.Io API 2025-08-07 10:04:29 -07:00
Matthew Lugg fd9cfc39f5 Merge pull request #24199 from Justus2308/24106-fmt-casts
zig fmt: canonicalize nested cast builtin order
2025-08-07 10:55:03 +01:00
David Rubin def25b9189 crypto: fix typo in ecdsa comment 2025-08-05 07:51:39 +01:00
Justus Klausecker 7c35070b90 zig fmt: apply new cast builtin order 2025-08-03 14:59:56 +02:00
Andrew Kelley 1dcea220a4 std.tar: update to new I/O API 2025-07-22 09:41:44 -07:00
Andrew Kelley 76d04c1662 zig fmt 2025-07-16 10:27:39 -07:00
Andrew Kelley 96a4e9b866 std.crypto: fix Sha1 namespace 2025-07-14 00:14:21 -07:00
Andrew Kelley e7b18a7ce6 std.crypto: remove inline from most functions
To quote the language reference,

It is generally better to let the compiler decide when to inline a
function, except for these scenarios:

* To change how many stack frames are in the call stack, for debugging
  purposes.
* To force comptime-ness of the arguments to propagate to the return
  value of the function, as in the above example.
* Real world performance measurements demand it. Don't guess!

Note that inline actually restricts what the compiler is allowed to do.
This can harm binary size, compilation speed, and even runtime
performance.

`zig run lib/std/crypto/benchmark.zig -OReleaseFast`
[-before-] vs {+after+}

              md5:        [-990-]        {+998+} MiB/s
             sha1:       [-1144-]       {+1140+} MiB/s
           sha256:       [-2267-]       {+2275+} MiB/s
           sha512:        [-762-]        {+767+} MiB/s
         sha3-256:        [-680-]        {+683+} MiB/s
         sha3-512:        [-362-]        {+363+} MiB/s
        shake-128:        [-835-]        {+839+} MiB/s
        shake-256:        [-680-]        {+681+} MiB/s
   turboshake-128:       [-1567-]       {+1570+} MiB/s
   turboshake-256:       [-1276-]       {+1282+} MiB/s
          blake2s:        [-778-]        {+789+} MiB/s
          blake2b:       [-1071-]       {+1086+} MiB/s
           blake3:       [-1148-]       {+1137+} MiB/s
            ghash:      [-10044-]      {+10033+} MiB/s
          polyval:       [-9726-]      {+10033+} MiB/s
         poly1305:       [-2486-]       {+2703+} MiB/s
         hmac-md5:        [-991-]        {+998+} MiB/s
        hmac-sha1:       [-1134-]       {+1137+} MiB/s
      hmac-sha256:       [-2265-]       {+2288+} MiB/s
      hmac-sha512:        [-765-]        {+764+} MiB/s
      siphash-2-4:       [-4410-]       {+4438+} MiB/s
      siphash-1-3:       [-7144-]       {+7225+} MiB/s
   siphash128-2-4:       [-4397-]       {+4449+} MiB/s
   siphash128-1-3:       [-7281-]       {+7374+} MiB/s
  aegis-128x4 mac:      [-73385-]      {+74523+} MiB/s
  aegis-256x4 mac:      [-30160-]      {+30539+} MiB/s
  aegis-128x2 mac:      [-66662-]      {+67267+} MiB/s
  aegis-256x2 mac:      [-16812-]      {+16806+} MiB/s
   aegis-128l mac:      [-33876-]      {+34055+} MiB/s
    aegis-256 mac:       [-8993-]       {+9087+} MiB/s
         aes-cmac:       2036 MiB/s
           x25519:      [-20670-]      {+16844+} exchanges/s
          ed25519:      [-29763-]      {+29576+} signatures/s
       ecdsa-p256:       [-4762-]       {+4900+} signatures/s
       ecdsa-p384:       [-1465-]       {+1500+} signatures/s
  ecdsa-secp256k1:       [-5643-]       {+5769+} signatures/s
          ed25519:      [-21926-]      {+21721+} verifications/s
          ed25519:      [-51200-]      {+50880+} verifications/s (batch)
 chacha20Poly1305:       [-1189-]       {+1109+} MiB/s
xchacha20Poly1305:       [-1196-]       {+1107+} MiB/s
 xchacha8Poly1305:       [-1466-]       {+1555+} MiB/s
 xsalsa20Poly1305:        [-660-]        {+620+} MiB/s
      aegis-128x4:      [-76389-]      {+78181+} MiB/s
      aegis-128x2:      [-53946-]      {+53495+} MiB/s
       aegis-128l:      [-27219-]      {+25621+} MiB/s
      aegis-256x4:      [-49351-]      {+49542+} MiB/s
      aegis-256x2:      [-32390-]      {+32366+} MiB/s
        aegis-256:       [-8881-]       {+8944+} MiB/s
       aes128-gcm:       [-6095-]       {+6205+} MiB/s
       aes256-gcm:       [-5306-]       {+5427+} MiB/s
       aes128-ocb:       [-8529-]      {+13974+} MiB/s
       aes256-ocb:       [-7241-]       {+9442+} MiB/s
        isapa128a:        [-204-]        {+214+} MiB/s
    aes128-single:  [-133857882-]  {+134170944+} ops/s
    aes256-single:   [-96306962-]   {+96408639+} ops/s
         aes128-8: [-1083210101-] {+1073727253+} ops/s
         aes256-8:  [-762042466-]  {+767091778+} ops/s
           bcrypt:      0.009 s/ops
           scrypt:      [-0.018-]      {+0.017+} s/ops
           argon2:      [-0.037-]      {+0.060+} s/ops
      kyber512d00:     [-206057-]     {+205779+} encaps/s
      kyber768d00:     [-156074-]     {+150711+} encaps/s
     kyber1024d00:     [-116626-]     {+115469+} encaps/s
      kyber512d00:     [-181149-]     {+182046+} decaps/s
      kyber768d00:     [-136965-]     {+135676+} decaps/s
     kyber1024d00:     [-101307-]     {+100643+} decaps/s
      kyber512d00:     [-123624-]     {+123375+} keygen/s
      kyber768d00:      [-69465-]      {+70828+} keygen/s
     kyber1024d00:      [-43117-]      {+43208+} keygen/s
2025-07-13 18:26:13 +02:00
Marcos Gutiérrez Alonso f97baca6f6 Add documentation to std.crypto.aes_gcm.AesGcm.encrypt (#24427) 2025-07-13 07:33:08 +00:00
Linus Groh eb37552536 Remove numerous things deprecated during the 0.14 release cycle
Basically everything that has a direct replacement or no uses left.

Notable omissions:

- std.ArrayHashMap: Too much fallout, needs a separate cleanup.
- std.debug.runtime_safety: Too much fallout.
- std.heap.GeneralPurposeAllocator: Lots of references to it remain, not
  a simple find and replace as "debug allocator" is not equivalent to
  "general purpose allocator".
- std.io.Reader: Is being reworked at the moment.
- std.unicode.utf8Decode(): No replacement, needs a new API first.
- Manifest backwards compat options: Removal would break test data used
  by TestFetchBuilder.
- panic handler needs to be a namespace: Many tests still rely on it
  being a function, needs a separate cleanup.
2025-07-11 08:17:43 +02:00
Andrew Kelley 93ac76594a std: fmt.format to io.Writer.print
allows reverting format -> deprecatedFormat, plus I think this is a
nicer place for the function.
2025-07-09 15:31:02 -07:00
Andrew Kelley 0e37ff0d59 std.fmt: breaking API changes
added adapter to AnyWriter and GenericWriter to help bridge the gap
between old and new API

make std.testing.expectFmt work at compile-time

std.fmt no longer has a dependency on std.unicode. Formatted printing
was never properly unicode-aware. Now it no longer pretends to be.

Breakage/deprecations:
* std.fs.File.reader -> std.fs.File.deprecatedReader
* std.fs.File.writer -> std.fs.File.deprecatedWriter
* std.io.GenericReader -> std.io.Reader
* std.io.GenericWriter -> std.io.Writer
* std.io.AnyReader -> std.io.Reader
* std.io.AnyWriter -> std.io.Writer
* std.fmt.format -> std.fmt.deprecatedFormat
* std.fmt.fmtSliceEscapeLower -> std.ascii.hexEscape
* std.fmt.fmtSliceEscapeUpper -> std.ascii.hexEscape
* std.fmt.fmtSliceHexLower -> {x}
* std.fmt.fmtSliceHexUpper -> {X}
* std.fmt.fmtIntSizeDec -> {B}
* std.fmt.fmtIntSizeBin -> {Bi}
* std.fmt.fmtDuration -> {D}
* std.fmt.fmtDurationSigned -> {D}
* {} -> {f} when there is a format method
* format method signature
  - anytype -> *std.io.Writer
  - inferred error set -> error{WriteFailed}
  - options -> (deleted)
* std.fmt.Formatted
  - now takes context type explicitly
  - no fmt string
2025-07-07 22:43:51 -07:00
Andrew Kelley 0b3f0124dc std.io: move getStdIn, getStdOut, getStdErr functions to fs.File
preparing to rearrange std.io namespace into an interface

how to upgrade:

std.io.getStdIn() -> std.fs.File.stdin()
std.io.getStdOut() -> std.fs.File.stdout()
std.io.getStdErr() -> std.fs.File.stderr()
2025-07-07 22:43:51 -07:00
Andrew Kelley 9f27d770a1 std.io: deprecated Reader/Writer; introduce new API 2025-07-07 22:43:51 -07:00
Alex Rønne Petersen 8e511e031f std.crypto.salsa20: Disable some tests on RISC-V with vector support
https://github.com/ziglang/zig/issues/24299
2025-07-01 23:03:15 +02:00
Elaine Gibson ed48e2eb75 std.crypto.Certificate.Bundle: haiku support 2025-06-05 13:45:52 +01:00
Alex Rønne Petersen 9d534790eb std.Target: Introduce Cpu convenience functions for feature tests.
Before:

* std.Target.arm.featureSetHas(target.cpu.features, .has_v7)
* std.Target.x86.featureSetHasAny(target.cpu.features, .{ .sse, .avx, .cmov })
* std.Target.wasm.featureSetHasAll(target.cpu.features, .{ .atomics, .bulk_memory })

After:

* target.cpu.has(.arm, .has_v7)
* target.cpu.hasAny(.x86, &.{ .sse, .avx, .cmov })
* target.cpu.hasAll(.wasm, &.{ .atomics, .bulk_memory })
2025-06-05 06:12:00 +02:00
Jacob Young ec579aa0f3 Legalize: implement scalarization of @shuffle 2025-06-01 08:24:01 +01:00
Jacob Young 1f6f8b0ffe x86_64: implement integer @reduce(.Add) 2025-05-28 15:10:22 -04:00
Jacob Young d69f4c48fc x86_64: rewrite bitwise @reduce 2025-05-28 15:10:22 -04:00
HydroH cc1475c91d std: remove std.crypto.Certificate.Parsed.pubKeySigAlgo method (#23811) 2025-05-16 00:21:25 +02:00