Add workspace-level clippy config (#100)

Uses the same config from other repos (e.g. `traits`, `utils`)
This commit is contained in:
Tony Arcieri 2026-02-12 15:01:09 -07:00 committed by GitHub
parent c3a9ef249e
commit 0d9bf82ee5
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
15 changed files with 126 additions and 59 deletions

View File

@ -17,7 +17,7 @@ jobs:
- uses: RustCrypto/actions/cargo-cache@master
- uses: dtolnay/rust-toolchain@master
with:
toolchain: 1.85.0
toolchain: 1.93.0
components: clippy
- run: cargo clippy --all -- -D warnings

View File

@ -1,7 +1,46 @@
[workspace]
resolver = "2"
resolver = "3"
members = [
"ascon",
"bash-f",
"keccak",
]
[workspace.lints.clippy]
borrow_as_ptr = "warn"
cast_lossless = "warn"
cast_possible_truncation = "warn"
cast_possible_wrap = "warn"
cast_precision_loss = "warn"
cast_sign_loss = "warn"
checked_conversions = "warn"
from_iter_instead_of_collect = "warn"
implicit_saturating_sub = "warn"
manual_assert = "warn"
map_unwrap_or = "warn"
missing_errors_doc = "warn"
missing_panics_doc = "warn"
mod_module_files = "warn"
must_use_candidate = "warn"
needless_range_loop = "allow"
ptr_as_ptr = "warn"
redundant_closure_for_method_calls = "warn"
ref_as_ptr = "warn"
return_self_not_must_use = "warn"
semicolon_if_nothing_returned = "warn"
trivially_copy_pass_by_ref = "warn"
std_instead_of_alloc = "warn"
std_instead_of_core = "warn"
undocumented_unsafe_blocks = "warn"
unnecessary_safety_comment = "warn"
unwrap_in_result = "warn"
unwrap_used = "warn"
[workspace.lints.rust]
missing_copy_implementations = "warn"
missing_debug_implementations = "warn"
missing_docs = "warn"
trivial_casts = "warn"
trivial_numeric_casts = "warn"
unused_lifetimes = "warn"
unused_qualifications = "warn"

View File

@ -22,5 +22,8 @@ zeroize = { version = "1.6", default-features = false, optional = true }
[features]
no_unroll = [] # Do not unroll loops for binary size reduction
[lints]
workspace = true
[package.metadata.docs.rs]
rustdoc-args = ["--cfg", "docsrs"]

View File

@ -1,4 +1,4 @@
Copyright (c) 2016-2023 quininer kel, RustCrypto Developers
Copyright (c) 2016-2026 Sebastian Ramacher, RustCrypto Developers
Permission is hereby granted, free of charge, to any
person obtaining a copy of this software and associated

View File

@ -18,8 +18,8 @@ easy to implement.
Ascon is a family of lightweight algorithms built on a core permutation
algorithm. These algorithms include:
- [x] [`ascon-aead`]: Authenticated Encryption with Associated Data
- [x] [`ascon-hash`]: Hash functions and extendible-output functions (XOF)
- [x] [`ascon-aead128`]: Authenticated Encryption with Associated Data
- [x] [`ascon-hash256`]: Hash functions and extendible-output functions (XOF)
- [ ] Pseudo-random functions (PRF) and message authentication codes (MAC)
Ascon has been selected as [new standard for lightweight cryptography] in the
@ -64,8 +64,8 @@ dual licensed as above, without any additional terms or conditions.
[//]: # (links)
[`ascon-aead`]: https://github.com/RustCrypto/AEADs/tree/master/ascon-aead
[`ascon-hash`]: https://github.com/RustCrypto/hashes/tree/master/ascon-hash
[`ascon-aead128`]: https://docs.rs/ascon-aead128
[`ascon-hash256`]: https://docs.rs/ascon-hash256
[RustCrypto]: https://github.com/rustcrypto
[Ascon]: https://ascon.iaik.tugraz.at/
[New standard for lightweight cryptography]: https://www.nist.gov/news-events/news/2023/02/nist-selects-lightweight-cryptography-algorithms-protect-small-devices

View File

@ -1,22 +1,18 @@
// Copyright 2021-2022 Sebastian Ramacher
// SPDX-License-Identifier: Apache-2.0 OR MIT
#![no_std]
#![cfg_attr(docsrs, feature(doc_auto_cfg))]
#![cfg_attr(docsrs, feature(doc_cfg))]
#![doc = include_str!("../README.md")]
#![doc(
html_logo_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg",
html_favicon_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg"
)]
#![forbid(unsafe_code)]
#![warn(missing_docs)]
use core::mem::size_of;
#[cfg(feature = "zeroize")]
use zeroize::{Zeroize, ZeroizeOnDrop};
/// Produce mask for padding.
#[inline(always)]
#[must_use]
pub const fn pad(n: usize) -> u64 {
0x80_u64 << (56 - 8 * n)
}
@ -31,6 +27,7 @@ const fn round_constant(round: u64) -> u64 {
///
/// The permutation operates on a state of 320 bits represented as 5 64 bit words.
#[derive(Clone, Debug, Default)]
#[allow(missing_copy_implementations)]
pub struct State {
x: [u64; 5],
}
@ -68,6 +65,7 @@ const fn round(x: [u64; 5], c: u64) -> [u64; 5] {
impl State {
/// Instantiate new state from the given values.
#[must_use]
pub fn new(x0: u64, x1: u64, x2: u64, x3: u64, x4: u64) -> Self {
State {
x: [x0, x1, x2, x3, x4],
@ -181,6 +179,7 @@ impl State {
}
/// Convert state to bytes.
#[must_use]
pub fn as_bytes(&self) -> [u8; 40] {
let mut bytes = [0u8; size_of::<u64>() * 5];
for (dst, src) in bytes.chunks_exact_mut(size_of::<u64>()).zip(self.x) {
@ -227,15 +226,16 @@ impl TryFrom<&[u8]> for State {
type Error = ();
fn try_from(value: &[u8]) -> Result<Self, Self::Error> {
if value.len() != core::mem::size_of::<u64>() * 5 {
if value.len() != size_of::<u64>() * 5 {
return Err(());
}
let mut state = Self::default();
for (src, dst) in value
.chunks_exact(core::mem::size_of::<u64>())
.zip(state.x.iter_mut())
{
// TODO(tarcieri): use `[T]::as_chunks` when MSRV 1.88
#[allow(clippy::unwrap_in_result, reason = "MSRV")]
#[allow(clippy::unwrap_used, reason = "MSRV")]
for (src, dst) in value.chunks_exact(size_of::<u64>()).zip(state.x.iter_mut()) {
*dst = u64::from_be_bytes(src.try_into().unwrap());
}
Ok(state)
@ -245,10 +245,10 @@ impl TryFrom<&[u8]> for State {
impl From<&[u8; size_of::<u64>() * 5]> for State {
fn from(value: &[u8; size_of::<u64>() * 5]) -> Self {
let mut state = Self::default();
for (src, dst) in value
.chunks_exact(core::mem::size_of::<u64>())
.zip(state.x.iter_mut())
{
// TODO(tarcieri): use `[T]::as_chunks` when MSRV 1.88
#[allow(clippy::unwrap_used, reason = "MSRV")]
for (src, dst) in value.chunks_exact(size_of::<u64>()).zip(state.x.iter_mut()) {
*dst = u64::from_be_bytes(src.try_into().unwrap());
}
state

View File

@ -12,3 +12,6 @@ categories = ["cryptography", "no-std"]
readme = "README.md"
edition = "2024"
rust-version = "1.85"
[lints]
workspace = true

View File

@ -1,4 +1,4 @@
# RustCrypto: bash-f
# [RustCrypto]: bash-f
[![crate][crate-image]][crate-link]
[![Docs][docs-image]][docs-link]
@ -39,3 +39,7 @@ dual licensed as above, without any additional terms or conditions.
[rustc-image]: https://img.shields.io/badge/rustc-1.85+-blue.svg
[chat-image]: https://img.shields.io/badge/zulip-join_chat-blue.svg
[chat-link]: https://rustcrypto.zulipchat.com/#narrow/stream/369879-sponges
[//]: # (links)
[RustCrypto]: https://github.com/RustCrypto

View File

@ -1,3 +1,5 @@
//! bash-f benchmarks
#![feature(test)]
extern crate test;

View File

@ -1,3 +1,5 @@
//! bash-f tests
/// Test vector from Table A.2 of STB 34.101.77-2020.
#[test]
fn test_bash_f_table_a2() {
@ -58,8 +60,8 @@ fn test_bash_f_table_a2() {
0x7CED8E3F8B6E058E,
];
let mut state = input.map(|x| x.swap_bytes());
let expected = expected.map(|x| x.swap_bytes());
let mut state = input.map(u64::swap_bytes);
let expected = expected.map(u64::swap_bytes);
bash_f::bash_f(&mut state);

View File

@ -23,3 +23,6 @@ simd = [] # Use core::simd (nightly-only)
[target.'cfg(target_arch = "aarch64")'.dependencies]
cpufeatures = "0.3"
[lints]
workspace = true

View File

@ -1,4 +1,4 @@
# RustCrypto: Keccak Sponge Function
# [RustCrypto]: Keccak Sponge Function
[![crate][crate-image]][crate-link]
[![Docs][docs-image]][docs-link]
@ -7,7 +7,7 @@
![Rust Version][rustc-image]
[![Project Chat][chat-image]][chat-link]
Pure Rust implementation of the [Keccak Sponge Function][1] including the keccak-f
Pure Rust implementation of the [Keccak Sponge Function][keccak] including the keccak-f
and keccak-p variants.
[Documentation][docs-link]
@ -60,7 +60,8 @@ dual licensed as above, without any additional terms or conditions.
[chat-image]: https://img.shields.io/badge/zulip-join_chat-blue.svg
[chat-link]: https://rustcrypto.zulipchat.com/#narrow/stream/369879-sponges
[//]: # (general links)
[//]: # (links)
[1]: https://keccak.team/keccak.html
[RustCrypto]: https://github.com/RustCrypto
[keccak]: https://keccak.team/keccak.html
[`sha3`]: https://github.com/RustCrypto/hashes/tree/master/sha3

View File

@ -1,3 +1,5 @@
//! keccak benchmarks
#![feature(test)]
#![cfg_attr(feature = "simd", feature(portable_simd))]

View File

@ -1,10 +1,21 @@
/// Keccak-p1600 on ARMv8.4-A with FEAT_SHA3.
/// Keccak-p1600 on ARMv8.4-A with `FEAT_SHA3`.
///
/// See p. K12.2.2 p. 11,749 of the ARM Reference manual.
/// Adapted from the Keccak-f1600 implementation in the XKCP/K12.
/// see <https://github.com/XKCP/K12/blob/df6a21e6d1f34c1aa36e8d702540899c97dba5a0/lib/ARMv8Asha3/KeccakP-1600-ARMv8Asha3.S#L69>
#[target_feature(enable = "sha3")]
pub unsafe fn p1600_armv8_sha3_asm(state: &mut [u64; 25], round_count: usize) {
assert!(
matches!(round_count, 1..=24),
"invalid round count (must be 1-24): {}",
round_count
);
// SAFETY:
// - caller is responsible for ensuring that the target CPU is at least ARMv8.4-A with
// `FEAT_SHA3` using runtime CPU feature detection
// - `round_count` is ensured to be in the range `1..=24` above
// - `state` is valid, aligned, and mutably borrowed as a Rust reference above
unsafe {
core::arch::asm!("
// Read state
@ -123,6 +134,7 @@ pub unsafe fn p1600_armv8_sha3_asm(state: &mut [u64; 25], round_count: usize) {
}
#[cfg(all(test, target_feature = "sha3"))]
#[allow(clippy::undocumented_unsafe_blocks)]
mod tests {
use super::*;

View File

@ -1,10 +1,16 @@
//! Keccak [sponge function](https://en.wikipedia.org/wiki/Sponge_function).
#![no_std]
#![cfg_attr(docsrs, feature(doc_cfg))]
#![cfg_attr(feature = "simd", feature(portable_simd))]
#![doc = include_str!("../README.md")]
#![doc(
html_logo_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg",
html_favicon_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg"
)]
#![allow(non_upper_case_globals)]
//! ## Usage
//!
//! If you are looking for SHA-3 hash functions take a look at [`sha3`][1] and
//! [`tiny-keccak`][2] crates.
//!
//! To disable loop unrolling (e.g. for constraint targets) use `no_unroll`
//! feature.
//! To disable loop unrolling (e.g. for constrained targets) use `no_unroll` feature.
//!
//! ```
//! // Test vectors are from KeccakCodePackage
@ -36,23 +42,6 @@
//! [1]: https://docs.rs/sha3
//! [2]: https://docs.rs/tiny-keccak
#![no_std]
#![cfg_attr(docsrs, feature(doc_cfg))]
#![cfg_attr(feature = "simd", feature(portable_simd))]
#![doc(
html_logo_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg",
html_favicon_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg"
)]
#![allow(non_upper_case_globals)]
#![warn(
clippy::mod_module_files,
clippy::unwrap_used,
missing_docs,
rust_2018_idioms,
unused_lifetimes,
unused_qualifications
)]
use core::{
fmt::Debug,
mem::size_of,
@ -126,6 +115,7 @@ pub trait LaneSize:
fn truncate_rc(rc: u64) -> Self;
/// Rotate left function.
#[must_use]
fn rotate_left(self, n: u32) -> Self;
}
@ -179,20 +169,22 @@ impl_keccak!(p800, f800, u32);
#[cfg(not(all(target_arch = "aarch64", feature = "asm")))]
impl_keccak!(p1600, f1600, u64);
/// Keccak-p[1600, rc] permutation.
/// `Keccak-p[1600, rc]` permutation.
#[cfg(all(target_arch = "aarch64", feature = "asm"))]
pub fn p1600(state: &mut [u64; PLEN], round_count: usize) {
if armv8_sha3_intrinsics::get() {
// SAFETY: we just performed runtime CPU feature detection above
unsafe { armv8::p1600_armv8_sha3_asm(state, round_count) }
} else {
keccak_p(state, round_count);
}
}
/// Keccak-f[1600] permutation.
/// `Keccak-f[1600]` permutation.
#[cfg(all(target_arch = "aarch64", feature = "asm"))]
pub fn f1600(state: &mut [u64; PLEN]) {
if armv8_sha3_intrinsics::get() {
// SAFETY: we just performed runtime CPU feature detection above
unsafe { armv8::p1600_armv8_sha3_asm(state, 24) }
} else {
keccak_p(state, u64::KECCAK_F_ROUND_COUNT);
@ -230,12 +222,16 @@ pub mod simd {
impl_keccak!(p1600x8, f1600x8, u64x8);
}
/// Generic Keccak-p sponge function.
///
/// # Panics
/// If the round count is greater than `L::KECCAK_F_ROUND_COUNT`.
#[allow(unused_assignments)]
/// Generic Keccak-p sponge function
pub fn keccak_p<L: LaneSize>(state: &mut [L; PLEN], round_count: usize) {
if round_count > L::KECCAK_F_ROUND_COUNT {
panic!("A round_count greater than KECCAK_F_ROUND_COUNT is not supported!");
}
assert!(
round_count <= L::KECCAK_F_ROUND_COUNT,
"A round_count greater than KECCAK_F_ROUND_COUNT is not supported!"
);
// https://nvlpubs.nist.gov/nistpubs/FIPS/NIST.FIPS.202.pdf#page=25
// "the rounds of KECCAK-p[b, nr] match the last rounds of KECCAK-f[b]"