Skip to content

Commit 029982c

Browse files
committed
Add AES support for RISC-V: RV64 scalar
1 parent 1f7c695 commit 029982c

File tree

8 files changed

+1037
-0
lines changed

8 files changed

+1037
-0
lines changed

.github/workflows/aes.yml

Lines changed: 27 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -310,6 +310,33 @@ jobs:
310310
- run: cross test --package aes --target ${{ matrix.target }} --features hazmat
311311
- run: cross test --package aes --target ${{ matrix.target }} --all-features
312312

313+
riscv:
314+
strategy:
315+
matrix:
316+
include:
317+
- target: riscv64gc-unknown-linux-gnu
318+
rustflags: ''
319+
rust: nightly
320+
- target: riscv64gc-unknown-linux-gnu
321+
rustflags: '-Ctarget-feature=+zkne,+zknd'
322+
rust: nightly
323+
runs-on: ubuntu-latest
324+
defaults:
325+
run:
326+
working-directory: .
327+
steps:
328+
- uses: actions/checkout@v4
329+
- uses: RustCrypto/actions/cargo-cache@master
330+
- uses: dtolnay/rust-toolchain@master
331+
with:
332+
toolchain: ${{ matrix.rust }}
333+
- run: cargo install cross --git https://github.com/cross-rs/cross
334+
env:
335+
RUSTFLAGS: "${{ env.RUSTFLAGS }} -Astatic-mut-refs"
336+
- run: cross test --package aes --target ${{ matrix.target }}
337+
env:
338+
RUSTFLAGS: "-Dwarning ${{ matrix.rustflags }}"
339+
313340
clippy:
314341
env:
315342
RUSTFLAGS: "-Dwarnings --cfg aes_compact"

aes/benches/mod.rs

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,19 @@ block_decryptor_bench!(
1313
aes128_decrypt_block,
1414
aes128_decrypt_blocks,
1515
);
16+
#[cfg(any(
17+
not(target_arch = "riscv64"),
18+
all(target_feature = "zknd", target_feature = "zkne")
19+
))]
1620
block_encryptor_bench!(
1721
Key: aes::Aes192,
1822
aes192_encrypt_block,
1923
aes192_encrypt_blocks,
2024
);
25+
#[cfg(any(
26+
not(target_arch = "riscv64"),
27+
all(target_feature = "zknd", target_feature = "zkne")
28+
))]
2129
block_decryptor_bench!(
2230
Key: aes::Aes192,
2331
aes192_decrypt_block,
@@ -43,6 +51,10 @@ fn aes128_new(bh: &mut test::Bencher) {
4351
});
4452
}
4553

54+
#[cfg(any(
55+
not(target_arch = "riscv64"),
56+
all(target_feature = "zknd", target_feature = "zkne")
57+
))]
4658
#[bench]
4759
fn aes192_new(bh: &mut test::Bencher) {
4860
bh.iter(|| {

aes/src/lib.rs

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,13 @@
3535
//! runtime. On other platforms the `aes` target feature must be enabled via
3636
//! RUSTFLAGS.
3737
//!
38+
//! ## RISC-V rv64 (scalar) {Zkne, ZKnd} extensions
39+
//!
40+
//! Support is available for the RISC-V rv64 scalar crypto extensions for AES. This
41+
//! is not currently autodetected at runtime. In order to enable, you need to
42+
//! enable the appropriate target features at compile time. For example:
43+
//! `RUSTFLAGS=-C target-feature=+zkne,+zknd`.
44+
//!
3845
//! ## `x86`/`x86_64` intrinsics (AES-NI and VAES)
3946
//! By default this crate uses runtime detection on `i686`/`x86_64` targets
4047
//! in order to determine if AES-NI and VAES are available, and if they are
@@ -123,12 +130,26 @@
123130
)]
124131
#![cfg_attr(docsrs, feature(doc_auto_cfg))]
125132
#![warn(missing_docs, rust_2018_idioms)]
133+
#![cfg_attr(
134+
all(
135+
any(target_arch = "riscv32", target_arch = "riscv64"),
136+
target_feature = "zknd",
137+
target_feature = "zkne"
138+
),
139+
feature(riscv_ext_intrinsics)
140+
)]
126141

127142
#[cfg(feature = "hazmat")]
128143
pub mod hazmat;
129144

130145
#[macro_use]
131146
mod macros;
147+
#[cfg_attr(any(target_arch = "riscv32", target_arch = "riscv64"),
148+
// The `soft` AES-192 is used for RISC-V when RVV crypto (Zvkned) is supported
149+
// but Scalar crypto (Zkn{ed}) is not supported. Most of the rest of the `soft`
150+
// is unused which generates warnings about unused definitions. We just disable
151+
// the warnings here rather than cluttering `soft` with RISC-V conditionals.
152+
allow(unused))]
132153
mod soft;
133154

134155
use cfg_if::cfg_if;
@@ -138,6 +159,9 @@ cfg_if! {
138159
mod armv8;
139160
mod autodetect;
140161
pub use autodetect::*;
162+
} else if #[cfg(all(target_arch = "riscv64", target_feature = "zkne", target_feature = "zknd"))] {
163+
mod riscv;
164+
pub use riscv::rv64::*;
141165
} else if #[cfg(all(
142166
any(target_arch = "x86", target_arch = "x86_64"),
143167
not(aes_force_soft)

aes/src/riscv.rs

Lines changed: 149 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,149 @@
1+
//! AES block cipher implementations for RISC-V using the Cryptography
2+
//! Extensions
3+
//!
4+
//! Supported targets: rv64 (scalar)
5+
//!
6+
//! NOTE: rv32 (scalar) is not currently implemented, primarily due to the
7+
//! difficulty in obtaining a suitable development environment (lack of distro
8+
//! support and lack of precompiled toolchains), the effort required for
9+
//! maintaining a test environment as 32-bit becomes less supported, and the
10+
//! overall scarcity of relevant hardware. If someone has a specific need for
11+
//! such an implementation, please open an issue.
12+
//!
13+
//! NOTE: These implementations are currently not enabled through
14+
//! auto-detection. In order to use this implementation, you must enable the
15+
//! appropriate target-features.
16+
//!
17+
//! Examining the module structure for this implementation should give you an
18+
//! idea of how to specify these features in your own code.
19+
//!
20+
//! NOTE: AES-128, AES-192, and AES-256 are supported.
21+
22+
#[cfg(all(
23+
target_arch = "riscv64",
24+
target_feature = "zknd",
25+
target_feature = "zkne"
26+
))]
27+
pub(crate) mod rv64;
28+
29+
use crate::Block;
30+
31+
#[cfg(test)]
32+
mod test {
33+
use hex_literal::hex;
34+
35+
#[cfg(all(
36+
any(target_arch = "riscv32", target_arch = "riscv64"),
37+
target_feature = "zknd",
38+
target_feature = "zkne"
39+
))]
40+
mod inner {
41+
use super::*;
42+
43+
pub(crate) const AES128_EXP_INVKEYS: [[u8; 16]; 11] = [
44+
AES128_KEY,
45+
hex!("2b3708a7f262d405bc3ebdbf4b617d62"),
46+
hex!("cc7505eb3e17d1ee82296c51c9481133"),
47+
hex!("7c1f13f74208c219c021ae480969bf7b"),
48+
hex!("90884413d280860a12a128421bc89739"),
49+
hex!("6ea30afcbc238cf6ae82a4b4b54a338d"),
50+
hex!("6efcd876d2df54807c5df034c917c3b9"),
51+
hex!("12c07647c01f22c7bc42d2f37555114a"),
52+
hex!("df7d925a1f62b09da320626ed6757324"),
53+
hex!("0c7b5a631319eafeb0398890664cfbb4"),
54+
hex!("d014f9a8c9ee2589e13f0cc8b6630ca6"),
55+
];
56+
57+
pub(crate) const AES192_KEY: [u8; 24] =
58+
hex!("8e73b0f7da0e6452c810f32b809079e562f8ead2522c6b7b");
59+
pub(crate) const AES192_EXP_KEYS: [[u8; 16]; 13] = [
60+
hex!("8e73b0f7da0e6452c810f32b809079e5"),
61+
hex!("62f8ead2522c6b7bfe0c91f72402f5a5"),
62+
hex!("ec12068e6c827f6b0e7a95b95c56fec2"),
63+
hex!("4db7b4bd69b5411885a74796e92538fd"),
64+
hex!("e75fad44bb095386485af05721efb14f"),
65+
hex!("a448f6d94d6dce24aa326360113b30e6"),
66+
hex!("a25e7ed583b1cf9a27f939436a94f767"),
67+
hex!("c0a69407d19da4e1ec1786eb6fa64971"),
68+
hex!("485f703222cb8755e26d135233f0b7b3"),
69+
hex!("40beeb282f18a2596747d26b458c553e"),
70+
hex!("a7e1466c9411f1df821f750aad07d753"),
71+
hex!("ca4005388fcc5006282d166abc3ce7b5"),
72+
hex!("e98ba06f448c773c8ecc720401002202"),
73+
];
74+
pub(crate) const AES192_EXP_INVKEYS: [[u8; 16]; 13] = [
75+
hex!("8e73b0f7da0e6452c810f32b809079e5"),
76+
hex!("9eb149c479d69c5dfeb4a27ceab6d7fd"),
77+
hex!("659763e78c817087123039436be6a51e"),
78+
hex!("41b34544ab0592b9ce92f15e421381d9"),
79+
hex!("5023b89a3bc51d84d04b19377b4e8b8e"),
80+
hex!("b5dc7ad0f7cffb09a7ec43939c295e17"),
81+
hex!("c5ddb7f8be933c760b4f46a6fc80bdaf"),
82+
hex!("5b6cfe3cc745a02bf8b9a572462a9904"),
83+
hex!("4d65dfa2b1e5620dea899c312dcc3c1a"),
84+
hex!("f3b42258b59ebb5cf8fb64fe491e06f3"),
85+
hex!("a3979ac28e5ba6d8e12cc9e654b272ba"),
86+
hex!("ac491644e55710b746c08a75c89b2cad"),
87+
hex!("e98ba06f448c773c8ecc720401002202"),
88+
];
89+
90+
pub(crate) const AES256_EXP_INVKEYS: [[u8; 16]; 15] = [
91+
hex!("603deb1015ca71be2b73aef0857d7781"),
92+
hex!("8ec6bff6829ca03b9e49af7edba96125"),
93+
hex!("42107758e9ec98f066329ea193f8858b"),
94+
hex!("4a7459f9c8e8f9c256a156bc8d083799"),
95+
hex!("6c3d632985d1fbd9e3e36578701be0f3"),
96+
hex!("54fb808b9c137949cab22ff547ba186c"),
97+
hex!("25ba3c22a06bc7fb4388a28333934270"),
98+
hex!("d669a7334a7ade7a80c8f18fc772e9e3"),
99+
hex!("c440b289642b757227a3d7f114309581"),
100+
hex!("32526c367828b24cf8e043c33f92aa20"),
101+
hex!("34ad1e4450866b367725bcc763152946"),
102+
hex!("b668b621ce40046d36a047ae0932ed8e"),
103+
hex!("57c96cf6074f07c0706abb07137f9241"),
104+
hex!("ada23f4963e23b2455427c8a5c709104"),
105+
hex!("fe4890d1e6188d0b046df344706c631e"),
106+
];
107+
}
108+
#[cfg(all(
109+
any(target_arch = "riscv32", target_arch = "riscv64"),
110+
target_feature = "zknd",
111+
target_feature = "zkne"
112+
))]
113+
pub(crate) use self::inner::*;
114+
115+
pub(crate) const AES128_KEY: [u8; 16] = hex!("2b7e151628aed2a6abf7158809cf4f3c");
116+
pub(crate) const AES128_EXP_KEYS: [[u8; 16]; 11] = [
117+
AES128_KEY,
118+
hex!("a0fafe1788542cb123a339392a6c7605"),
119+
hex!("f2c295f27a96b9435935807a7359f67f"),
120+
hex!("3d80477d4716fe3e1e237e446d7a883b"),
121+
hex!("ef44a541a8525b7fb671253bdb0bad00"),
122+
hex!("d4d1c6f87c839d87caf2b8bc11f915bc"),
123+
hex!("6d88a37a110b3efddbf98641ca0093fd"),
124+
hex!("4e54f70e5f5fc9f384a64fb24ea6dc4f"),
125+
hex!("ead27321b58dbad2312bf5607f8d292f"),
126+
hex!("ac7766f319fadc2128d12941575c006e"),
127+
hex!("d014f9a8c9ee2589e13f0cc8b6630ca6"),
128+
];
129+
130+
pub(crate) const AES256_KEY: [u8; 32] =
131+
hex!("603deb1015ca71be2b73aef0857d77811f352c073b6108d72d9810a30914dff4");
132+
pub(crate) const AES256_EXP_KEYS: [[u8; 16]; 15] = [
133+
hex!("603deb1015ca71be2b73aef0857d7781"),
134+
hex!("1f352c073b6108d72d9810a30914dff4"),
135+
hex!("9ba354118e6925afa51a8b5f2067fcde"),
136+
hex!("a8b09c1a93d194cdbe49846eb75d5b9a"),
137+
hex!("d59aecb85bf3c917fee94248de8ebe96"),
138+
hex!("b5a9328a2678a647983122292f6c79b3"),
139+
hex!("812c81addadf48ba24360af2fab8b464"),
140+
hex!("98c5bfc9bebd198e268c3ba709e04214"),
141+
hex!("68007bacb2df331696e939e46c518d80"),
142+
hex!("c814e20476a9fb8a5025c02d59c58239"),
143+
hex!("de1369676ccc5a71fa2563959674ee15"),
144+
hex!("5886ca5d2e2f31d77e0af1fa27cf73c3"),
145+
hex!("749c47ab18501ddae2757e4f7401905a"),
146+
hex!("cafaaae3e4d59b349adf6acebd10190d"),
147+
hex!("fe4890d1e6188d0b046df344706c631e"),
148+
];
149+
}

0 commit comments

Comments
 (0)