Add a feature flag to omit ASM dependencies
Compiling the ASM dependencies has turned out to be a major pain point.
This commit adds a feature flag to optionally disable support for all
algorithms that require ASM.
diff --git a/Cargo.toml b/Cargo.toml
index 2123253..b401776 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -14,7 +14,9 @@
name = "crypto"
[features]
+default = ["with-asm"]
with-bench = []
+with-asm = []
[build-dependencies]
gcc = "^0.3"
diff --git a/build.rs b/build.rs
index 92dd2b6..a77ba27 100644
--- a/build.rs
+++ b/build.rs
@@ -10,32 +10,33 @@
use std::path::Path;
fn main() {
- let target = env::var("TARGET").unwrap();
- let host = env::var("HOST").unwrap();
- if target.contains("msvc") && host.contains("windows") {
- let mut config = gcc::Config::new();
- config.file("src/util_helpers.asm");
- config.file("src/aesni_helpers.asm");
- if target.contains("x86_64") {
- config.define("X64", None);
- }
- config.compile("lib_rust_crypto_helpers.a");
- }
- else {
- let mut cfg = gcc::Config::new();
- cfg.file("src/util_helpers.c");
- cfg.file("src/aesni_helpers.c");
- if env::var_os("CC").is_none() {
- if host.contains("openbsd") {
- // Use clang on openbsd since there have been reports that
- // GCC doesn't like some of the assembly that we use on that
- // platform.
- cfg.compiler(Path::new("clang"));
- } else if target == host {
- cfg.compiler(Path::new("cc"));
+ if env::var("CARGO_FEATURE_WITH_ASM").is_ok() {
+ let target = env::var("TARGET").unwrap();
+ let host = env::var("HOST").unwrap();
+ if target.contains("msvc") && host.contains("windows") {
+ let mut config = gcc::Config::new();
+ config.file("src/util_helpers.asm");
+ config.file("src/aesni_helpers.asm");
+ if target.contains("x86_64") {
+ config.define("X64", None);
}
+ config.compile("lib_rust_crypto_helpers.a");
}
- cfg.compile("lib_rust_crypto_helpers.a");
+ else {
+ let mut cfg = gcc::Config::new();
+ cfg.file("src/util_helpers.c");
+ cfg.file("src/aesni_helpers.c");
+ if env::var_os("CC").is_none() {
+ if host.contains("openbsd") {
+ // Use clang on openbsd since there have been reports that
+ // GCC doesn't like some of the assembly that we use on that
+ // platform.
+ cfg.compiler(Path::new("clang"));
+ } else if target == host {
+ cfg.compiler(Path::new("cc"));
+ }
+ }
+ cfg.compile("lib_rust_crypto_helpers.a");
+ }
}
}
-
diff --git a/src/aes.rs b/src/aes.rs
index 1de8c56..f10867a 100644
--- a/src/aes.rs
+++ b/src/aes.rs
@@ -4,13 +4,17 @@
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
use aesni;
use aessafe;
-use blockmodes::{PaddingProcessor, EcbEncryptor, EcbDecryptor, CbcEncryptor, CbcDecryptor, CtrMode,
+use blockmodes::{PaddingProcessor, EcbEncryptor, EcbDecryptor, CbcEncryptor, CbcDecryptor,
CtrModeX8};
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
+use blockmodes::CtrMode;
use symmetriccipher::{Encryptor, Decryptor, SynchronousStreamCipher};
+
+#[cfg(feature = "with-asm")]
use util;
/// AES key size
@@ -22,7 +26,7 @@
}
/// Get the best implementation of an EcbEncryptor
-#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
pub fn ecb_encryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -53,7 +57,7 @@
}
/// Get the best implementation of an EcbEncryptor
-#[cfg(all(not(target_arch = "x86"), not(target_arch = "x86_64")))]
+#[cfg(any(not(feature = "with-asm"), all(not(target_arch = "x86"), not(target_arch = "x86_64"))))]
pub fn ecb_encryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -78,7 +82,7 @@
}
/// Get the best implementation of an EcbDecryptor
-#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
pub fn ecb_decryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -109,7 +113,7 @@
}
/// Get the best implementation of an EcbDecryptor
-#[cfg(all(not(target_arch = "x86"), not(target_arch = "x86_64")))]
+#[cfg(any(not(feature = "with-asm"), all(not(target_arch = "x86"), not(target_arch = "x86_64"))))]
pub fn ecb_decryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -134,7 +138,7 @@
}
/// Get the best implementation of a CbcEncryptor
-#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
pub fn cbc_encryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -166,7 +170,7 @@
}
/// Get the best implementation of a CbcEncryptor
-#[cfg(all(not(target_arch = "x86"), not(target_arch = "x86_64")))]
+#[cfg(any(not(feature = "with-asm"), all(not(target_arch = "x86"), not(target_arch = "x86_64"))))]
pub fn cbc_encryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -192,7 +196,7 @@
}
/// Get the best implementation of a CbcDecryptor
-#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
pub fn cbc_decryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -224,7 +228,7 @@
}
/// Get the best implementation of a CbcDecryptor
-#[cfg(all(not(target_arch = "x86"), not(target_arch = "x86_64")))]
+#[cfg(any(not(feature = "with-asm"), all(not(target_arch = "x86"), not(target_arch = "x86_64"))))]
pub fn cbc_decryptor<X: PaddingProcessor + Send + 'static>(
key_size: KeySize,
key: &[u8],
@@ -250,7 +254,7 @@
}
/// Get the best implementation of a Ctr
-#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
pub fn ctr(
key_size: KeySize,
key: &[u8],
@@ -281,7 +285,7 @@
}
/// Get the best implementation of a Ctr
-#[cfg(all(not(target_arch = "x86"), not(target_arch = "x86_64")))]
+#[cfg(any(not(feature = "with-asm"), all(not(target_arch = "x86"), not(target_arch = "x86_64"))))]
pub fn ctr(
key_size: KeySize,
key: &[u8],
@@ -309,14 +313,16 @@
mod test {
use std::iter::repeat;
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
use aesni;
use aessafe;
use symmetriccipher::{BlockEncryptor, BlockDecryptor, BlockEncryptorX8, BlockDecryptorX8,
SynchronousStreamCipher};
+ #[cfg(feature = "with-asm")]
use util;
use aes;
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
use aes::KeySize::{KeySize128, KeySize192, KeySize256};
// Test vectors from:
@@ -472,7 +478,7 @@
}
}
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
#[test]
fn test_aesni_128() {
if util::supports_aesni() {
@@ -485,7 +491,7 @@
}
}
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
#[test]
fn test_aesni_192() {
if util::supports_aesni() {
@@ -498,7 +504,7 @@
}
}
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
#[test]
fn test_aesni_256() {
if util::supports_aesni() {
@@ -709,7 +715,7 @@
mod bench {
use test::Bencher;
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
use aesni;
use aessafe;
@@ -717,25 +723,25 @@
use util;
use aes::KeySize::{self, KeySize128, KeySize192, KeySize256};
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
#[bench]
pub fn aesni_128_bench(bh: &mut Bencher) {
aesni_bench(bh, KeySize128);
}
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
#[bench]
pub fn aesni_192_bench(bh: &mut Bencher) {
aesni_bench(bh, KeySize192);
}
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
#[bench]
pub fn aesni_256_bench(bh: &mut Bencher) {
aesni_bench(bh, KeySize256);
}
- #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+ #[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
fn aesni_bench(bh: &mut Bencher, key_size: KeySize) {
if util::supports_aesni() {
let key: [u8; 16] = [1u8; 16];
diff --git a/src/cryptoutil.rs b/src/cryptoutil.rs
index f6744e0..0c1acaa 100644
--- a/src/cryptoutil.rs
+++ b/src/cryptoutil.rs
@@ -165,6 +165,7 @@
}
/// Read the value of a vector of bytes as a u32 value in big-endian format.
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
pub fn read_u32_be(input: &[u8]) -> u32 {
assert!(input.len() == 4);
unsafe {
diff --git a/src/lib.rs b/src/lib.rs
index 59ad3af..e82cfbc 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -16,33 +16,46 @@
pub mod aead;
pub mod aes;
+#[cfg(feature = "with-asm")]
pub mod aes_gcm;
pub mod aessafe;
pub mod bcrypt;
pub mod bcrypt_pbkdf;
+#[cfg(feature = "with-asm")]
pub mod blake2b;
+#[cfg(feature = "with-asm")]
pub mod blake2s;
pub mod blockmodes;
pub mod blowfish;
pub mod buffer;
pub mod chacha20;
+#[cfg(feature = "with-asm")]
pub mod chacha20poly1305;
mod cryptoutil;
+#[cfg(feature = "with-asm")]
pub mod curve25519;
pub mod digest;
+#[cfg(feature = "with-asm")]
pub mod ed25519;
pub mod fortuna;
+#[cfg(feature = "with-asm")]
pub mod ghash;
pub mod hc128;
+#[cfg(feature = "with-asm")]
pub mod hmac;
+#[cfg(feature = "with-asm")]
pub mod hkdf;
+#[cfg(feature = "with-asm")]
pub mod mac;
pub mod md5;
+#[cfg(feature = "with-asm")]
pub mod pbkdf2;
+#[cfg(feature = "with-asm")]
pub mod poly1305;
pub mod rc4;
pub mod ripemd160;
pub mod salsa20;
+#[cfg(feature = "with-asm")]
pub mod scrypt;
pub mod sha1;
pub mod sha2;
@@ -51,8 +64,9 @@
pub mod sosemanuk;
mod step_by;
pub mod symmetriccipher;
+#[cfg(feature = "with-asm")]
pub mod util;
pub mod whirlpool;
-#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
+#[cfg(all(feature = "with-asm", any(target_arch = "x86", target_arch = "x86_64")))]
pub mod aesni;