authorgravatar for 124872+jedisct1@users.noreply.github.comFrank Denis <124872+jedisct1@users.noreply.github.com> 2023-03-22 17:58:24+01:00
committergravatar for noreply@github.comGitHub <noreply@github.com> 2023-03-22 17:58:24+01:00
logd61ac0db8c62f706ea65b70d2772cbb8c4efb416
treea91283de1e3db79d3c49f5ac5c512d271f328fd0
parent84b89d7cfe452f91fa22f2646ef53a3a7e990456
signaturebadge-question-mark Signed by PGP key 4AEE18F83AFDEB23

TLS: Favor ChaCha over AES-based ciphers on CPUs without AES support (#15034)

On CPUs without AES support, ChaCha is always faster and safer than software AES. Add `crypto.core.aes.has_hardware_support` to represent whether AES acceleration is available or not, and in `tls.Client`, favor AES-based ciphers only if hardware support is available. This matches what BoringSSL is doing.

2 files changed, 22 insertions(+), 7 deletions(-)

lib/std/crypto/aes.zig+6
...@@ -14,6 +14,12 @@ impl: {...@@ -14,6 +14,12 @@ impl: {
14 break :impl @import("aes/soft.zig");14 break :impl @import("aes/soft.zig");
15};15};
1616
17/// `true` if AES is backed by hardware (AES-NI on x86_64, ARM Crypto Extensions on AArch64).
18/// Software implementations are much slower, and should be avoided if possible.
19pub const has_hardware_support =
20 (builtin.cpu.arch == .x86_64 and has_aesni and has_avx) or
21 (builtin.cpu.arch == .aarch64 and has_armaes);
22
17pub const Block = impl.Block;23pub const Block = impl.Block;
18pub const AesEncryptCtx = impl.AesEncryptCtx;24pub const AesEncryptCtx = impl.AesEncryptCtx;
19pub const AesDecryptCtx = impl.AesDecryptCtx;25pub const AesDecryptCtx = impl.AesDecryptCtx;
lib/std/crypto/tls/Client.zig+16-7
...@@ -1363,13 +1363,22 @@ fn limitVecs(iovecs: []std.os.iovec, len: usize) []std.os.iovec {...@@ -1363,13 +1363,22 @@ fn limitVecs(iovecs: []std.os.iovec, len: usize) []std.os.iovec {
1363/// aegis-256: 461 MiB/s1363/// aegis-256: 461 MiB/s
1364/// aes128-gcm: 138 MiB/s1364/// aes128-gcm: 138 MiB/s
1365/// aes256-gcm: 120 MiB/s1365/// aes256-gcm: 120 MiB/s
1366const cipher_suites = enum_array(tls.CipherSuite, &.{1366const cipher_suites = if (crypto.core.aes.has_hardware_support)
1367 .AEGIS_128L_SHA256,1367 enum_array(tls.CipherSuite, &.{
1368 .AEGIS_256_SHA384,1368 .AEGIS_128L_SHA256,
1369 .AES_128_GCM_SHA256,1369 .AEGIS_256_SHA384,
1370 .AES_256_GCM_SHA384,1370 .AES_128_GCM_SHA256,
1371 .CHACHA20_POLY1305_SHA256,1371 .AES_256_GCM_SHA384,
1372});1372 .CHACHA20_POLY1305_SHA256,
1373 })
1374else
1375 enum_array(tls.CipherSuite, &.{
1376 .CHACHA20_POLY1305_SHA256,
1377 .AEGIS_128L_SHA256,
1378 .AEGIS_256_SHA384,
1379 .AES_128_GCM_SHA256,
1380 .AES_256_GCM_SHA384,
1381 });
13731382
1374test {1383test {
1375 _ = StreamInterface;1384 _ = StreamInterface;