From 57e73ecea01007441d308803bfbbb5542a06b5c6 Mon Sep 17 00:00:00 2001 From: "Jonathan M. Henson" Date: Tue, 15 Jun 2021 20:31:47 -0700 Subject: [PATCH 1/3] Try using a file instead? --- aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs | 1 + aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs | 1 + 2 files changed, 2 insertions(+) create mode 100644 aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs create mode 100644 aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs diff --git a/aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs b/aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs new file mode 100644 index 0000000..8b13789 --- /dev/null +++ b/aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs @@ -0,0 +1 @@ + diff --git a/aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs b/aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs new file mode 100644 index 0000000..8b13789 --- /dev/null +++ b/aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs @@ -0,0 +1 @@ + From 5f87b9527e08d565f89902c84024d146bdfaf356 Mon Sep 17 00:00:00 2001 From: "Jonathan M. Henson" Date: Mon, 21 Jun 2021 13:47:07 -0700 Subject: [PATCH 2/3] Working example of using common runtime across crate boundaries. --- .gitignore | 8 +++ aws_crt_checksums_ws/Cargo.toml | 6 ++ .../aws-crt-checksums-sys/Cargo.toml | 13 ++++ .../aws-crt-checksums-sys/build.rs | 66 +++++++++++++++++++ .../aws-crt-checksums/Cargo.toml | 11 ++++ 5 files changed, 104 insertions(+) create mode 100644 aws_crt_checksums_ws/Cargo.toml create mode 100644 aws_crt_checksums_ws/aws-crt-checksums-sys/Cargo.toml create mode 100644 aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs create mode 100644 aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml diff --git a/.gitignore b/.gitignore index 593c5e8..b2ef696 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,10 @@ build tags + +# Rust and Cargo +Cargo.lock +target/ + +#IDE +.idea + diff --git a/aws_crt_checksums_ws/Cargo.toml b/aws_crt_checksums_ws/Cargo.toml new file mode 100644 index 0000000..d441ff3 --- /dev/null +++ b/aws_crt_checksums_ws/Cargo.toml @@ -0,0 +1,6 @@ +[workspace] +members = [ + "aws-crt-checksums", + "aws-crt-checksums-sys", +] + diff --git a/aws_crt_checksums_ws/aws-crt-checksums-sys/Cargo.toml b/aws_crt_checksums_ws/aws-crt-checksums-sys/Cargo.toml new file mode 100644 index 0000000..9a8df6a --- /dev/null +++ b/aws_crt_checksums_ws/aws-crt-checksums-sys/Cargo.toml @@ -0,0 +1,13 @@ +[package] +name = "aws-crt-checksums-sys" +version = "0.1.0" +authors = ["AWS Common Runtime Team (aws-sdk-common-runtime-team@amazon.com)"] +edition = "2018" +links = "aws-checksums" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html +[build-dependencies] +aws-crt-c-flags = { git = "https://github.com/awslabs/aws-c-common", branch="move_to_rust_phase1" } + +[dependencies] +aws-crt-common-sys = { git = "https://github.com/awslabs/aws-c-common", branch="move_to_rust_phase1" } diff --git a/aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs b/aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs new file mode 100644 index 0000000..2594f1e --- /dev/null +++ b/aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs @@ -0,0 +1,66 @@ +use aws_crt_c_flags::{CRTModuleBuildInfo, HeaderType}; +use std::path::Path; + +fn main() { + let mut build_info = CRTModuleBuildInfo::new("aws-crt-checksums-sys"); + build_info.module_links_dependency("aws-c-common"); + + let include_path = Path::new("../../include/aws"); + build_info.include_dir(include_path, HeaderType::Public); + + build_info + .file(Path::new("../../source/crc.c")) + .file(Path::new("../../source/crc_sw.c")); + + let mut impl_found = false; + + #[cfg(any(target_arch = "x86", target_arch = "x86_64"))] + { + if build_info.follows_msvc_semantics() { + build_info.file(Path::new( + "../../source/intel/visualc/visualc_crc32c_sse42.c", + )); + } else { + build_info.file(Path::new("../../source/intel/asm/crc32c_sse42_asm.c")); + } + impl_found = true; + } + + #[cfg(target_arch = "aarch64")] + { + build_info.file(Path::new("../../source/arm/crc32c_arm.c")); + + if !build_info.follows_msvc_semantics() { + build_info.private_cflag("-march=armv8-a+crc"); + } + impl_found = true; + } + + #[cfg(all(target_arch = "arm"))] + { + if !build_info.follows_msvc_semantics() { + if build_info + .try_compile( + "#include + int main() { + int crc = __crc32d(0, 1); + return 0; + }", + ) + .is_ok() + { + build_info + .private_cflag("-march=armv8-a+crc") + .private_define("AWS_ARM32_CRC", "1"); + build_info.file(Path::new("../../source/arm/crc32c_arm.c")); + impl_found = true; + } + } + } + + if !impl_found { + build_info.file(Path::new("../../source/generic/crc32c_null.c")); + } + + build_info.build(); +} diff --git a/aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml b/aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml new file mode 100644 index 0000000..a99b22d --- /dev/null +++ b/aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml @@ -0,0 +1,11 @@ +[package] +name = "aws-crt-checksums" +version = "0.1.0" +authors = ["AWS Common Runtime Team (aws-sdk-common-runtime-team@amazon.com)"] +edition = "2018" + +# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html + +[dependencies] +aws-crt-checksums-sys = { path = "../aws-crt-checksums-sys" } + From d888fcd29b95645c572b1ae180bba143e5baf6a9 Mon Sep 17 00:00:00 2001 From: "Jonathan M. Henson" Date: Tue, 22 Jun 2021 11:38:11 -0700 Subject: [PATCH 3/3] Rust bits work and are ready. --- .gitignore | 2 + .../aws-crt-checksums-sys/build.rs | 9 ++- .../aws-crt-checksums-sys/src/lib.rs | 12 +++ .../aws-crt-checksums/Cargo.toml | 2 +- .../aws-crt-checksums/src/lib.rs | 75 +++++++++++++++++++ .../aws-crt-checksums/tests/lib.rs | 55 ++++++++++++++ 6 files changed, 153 insertions(+), 2 deletions(-) create mode 100644 aws_crt_checksums_ws/aws-crt-checksums/tests/lib.rs diff --git a/.gitignore b/.gitignore index b2ef696..55261a2 100644 --- a/.gitignore +++ b/.gitignore @@ -8,3 +8,5 @@ target/ #IDE .idea +# CMake +cmake-build-debug diff --git a/aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs b/aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs index 2594f1e..d8631a9 100644 --- a/aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs +++ b/aws_crt_checksums_ws/aws-crt-checksums-sys/build.rs @@ -1,8 +1,12 @@ +/** + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0. + */ use aws_crt_c_flags::{CRTModuleBuildInfo, HeaderType}; use std::path::Path; fn main() { - let mut build_info = CRTModuleBuildInfo::new("aws-crt-checksums-sys"); + let mut build_info = CRTModuleBuildInfo::new("aws-checksums"); build_info.module_links_dependency("aws-c-common"); let include_path = Path::new("../../include/aws"); @@ -12,6 +16,9 @@ fn main() { .file(Path::new("../../source/crc.c")) .file(Path::new("../../source/crc_sw.c")); + // rustc seems to be wrong on this one. + #[allow(unused_mut)] + #[allow(unused_assignments)] let mut impl_found = false; #[cfg(any(target_arch = "x86", target_arch = "x86_64"))] diff --git a/aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs b/aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs index 8b13789..a6ab5e6 100644 --- a/aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs +++ b/aws_crt_checksums_ws/aws-crt-checksums-sys/src/lib.rs @@ -1 +1,13 @@ +/** + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0. + */ +/// This module is a rust translation of the relevant declarations from the aws-c-common +/// header files. They are used from higher-level wrapper modules. + +#[allow(dead_code)] +extern "C" { + pub fn aws_checksums_crc32(input: *const u8, length: i32, previous_crc: u32) -> u32; + pub fn aws_checksums_crc32c(input: *const u8, length: i32, previous_crc: u32) -> u32; +} diff --git a/aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml b/aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml index a99b22d..443a895 100644 --- a/aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml +++ b/aws_crt_checksums_ws/aws-crt-checksums/Cargo.toml @@ -8,4 +8,4 @@ edition = "2018" [dependencies] aws-crt-checksums-sys = { path = "../aws-crt-checksums-sys" } - +aws-crt-common = { git = "https://github.com/awslabs/aws-c-common", branch="move_to_rust_phase1" } diff --git a/aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs b/aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs index 8b13789..dfd07b2 100644 --- a/aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs +++ b/aws_crt_checksums_ws/aws-crt-checksums/src/lib.rs @@ -1 +1,76 @@ +/** + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0. + */ +use aws_crt_checksums_sys::{aws_checksums_crc32, aws_checksums_crc32c}; +#[derive(Clone)] +pub struct Crc32C { + running_checksum: u32, +} + +#[derive(Clone)] +pub struct Crc32 { + running_checksum: u32, +} + +/// Trait for computing running checksums. +pub trait Checksum { + type Output; + /// update the checksum with the checksum value of input + /// # Arguments + /// * `input` the input data to be appended to the running checksum. + fn update(&mut self, input: &Vec); + /// Return the current value of the running checksum. + fn checksum(&self) -> Self::Output; +} + +impl Checksum for Crc32C { + type Output = u32; + + fn update(&mut self, input: &Vec) { + unsafe { + self.running_checksum = + aws_checksums_crc32c(input.as_ptr(), input.len() as i32, self.running_checksum); + } + } + + fn checksum(&self) -> u32 { + self.running_checksum + } +} + +impl Checksum for Crc32 { + type Output = u32; + + fn update(&mut self, input: &Vec) { + unsafe { + self.running_checksum = + aws_checksums_crc32(input.as_ptr(), input.len() as i32, self.running_checksum); + } + } + + fn checksum(&self) -> u32 { + self.running_checksum + } +} + +impl Crc32C { + /// Creates a new instance of the castagnoli CRC32c (iSCSI) checksum algorithm. Where supported + /// by the hardware, this implementation is hw accelerated. + pub fn new() -> Crc32C { + Crc32C { + running_checksum: 0, + } + } +} + +impl Crc32 { + /// Creates a new instance of the CRC32 (Ethernet, gzip) algorithm. Where supported + /// by the hardware, this implementation is hw accelerated. + pub fn new() -> Crc32 { + Crc32 { + running_checksum: 0, + } + } +} diff --git a/aws_crt_checksums_ws/aws-crt-checksums/tests/lib.rs b/aws_crt_checksums_ws/aws-crt-checksums/tests/lib.rs new file mode 100644 index 0000000..b7c7b44 --- /dev/null +++ b/aws_crt_checksums_ws/aws-crt-checksums/tests/lib.rs @@ -0,0 +1,55 @@ +/** + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0. + */ + +#[cfg(test)] +mod tests { + use aws_crt_checksums::{Checksum, Crc32, Crc32C}; + + #[test] + fn test_crc32_zeroes() { + let test_input: Vec = vec![0; 32]; + let expected_crc = 0x190A55AD; + + let mut crc_checksum = Crc32::new(); + crc_checksum.update(&test_input); + assert_eq!(expected_crc, crc_checksum.checksum()); + } + + #[test] + fn test_known_crc32() { + let test_input: Vec = vec![ + '1' as u8, '2' as u8, '3' as u8, '4' as u8, '5' as u8, '6' as u8, '7' as u8, '8' as u8, + '9' as u8, + ]; + let expected_crc = 0xCBF43926; + + let mut crc_checksum = Crc32::new(); + crc_checksum.update(&test_input); + assert_eq!(expected_crc, crc_checksum.checksum()); + } + + #[test] + fn test_crc32c_zeroes() { + let test_input: Vec = vec![0; 32]; + let expected_crc = 0x8A9136AA; + + let mut crc_checksum = Crc32C::new(); + crc_checksum.update(&test_input); + assert_eq!(expected_crc, crc_checksum.checksum()); + } + + #[test] + fn test_known_crc32c() { + let test_input: Vec = vec![ + '1' as u8, '2' as u8, '3' as u8, '4' as u8, '5' as u8, '6' as u8, '7' as u8, '8' as u8, + '9' as u8, + ]; + let expected_crc = 0xE3069283; + + let mut crc_checksum = Crc32C::new(); + crc_checksum.update(&test_input); + assert_eq!(expected_crc, crc_checksum.checksum()); + } +}