diff --git a/CMakeLists.txt b/CMakeLists.txt index fb54a14e0..1cab5f4f4 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -147,6 +147,10 @@ file(GLOB AWS_CRT_AUTH_HEADERS "include/aws/crt/auth/*.h" ) +file(GLOB AWS_CRT_CHECKSUM_HEADERS + "include/aws/crt/checksum/*.h" +) + file(GLOB AWS_CRT_CRYPTO_HEADERS "include/aws/crt/crypto/*.h" ) @@ -178,6 +182,7 @@ file(GLOB AWS_CRT_CBOR_HEADERS file(GLOB AWS_CRT_PUBLIC_HEADERS ${AWS_CRT_HEADERS} ${AWS_CRT_AUTH_HEADERS} + ${AWS_CRT_CHECKSUM_HEADERS} ${AWS_CRT_CRYPTO_HEADERS} ${AWS_CRT_IO_HEADERS} ${AWS_CRT_IOT_HEADERS} @@ -204,6 +209,10 @@ file(GLOB AWS_CRT_AUTH_SRC "source/auth/*.cpp" ) +file(GLOB AWS_CRT_CHECKSUM_SRC + "source/checksum/*.cpp" +) + file(GLOB AWS_CRT_CRYPTO_SRC "source/crypto/*.cpp" ) @@ -235,6 +244,7 @@ file(GLOB AWS_CRT_CBOR_SRC file(GLOB AWS_CRT_CPP_SRC ${AWS_CRT_SRC} ${AWS_CRT_AUTH_SRC} + ${AWS_CRT_CHECKSUM_SRC} ${AWS_CRT_CRYPTO_SRC} ${AWS_CRT_IO_SRC} ${AWS_CRT_IOT_SRC} @@ -248,6 +258,7 @@ if(WIN32) if(MSVC) source_group("Header Files\\aws\\crt" FILES ${AWS_CRT_HEADERS}) source_group("Header Files\\aws\\crt\\auth" FILES ${AWS_CRT_AUTH_HEADERS}) + source_group("Header Files\\aws\\crt\\checksum" FILES ${AWS_CRT_CHECKSUM_HEADERS}) source_group("Header Files\\aws\\crt\\crypto" FILES ${AWS_CRT_CRYPTO_HEADERS}) source_group("Header Files\\aws\\crt\\io" FILES ${AWS_CRT_IO_HEADERS}) source_group("Header Files\\aws\\iot" FILES ${AWS_CRT_IOT_HEADERS}) @@ -258,6 +269,7 @@ if(WIN32) source_group("Source Files" FILES ${AWS_CRT_SRC}) source_group("Source Files\\auth" FILES ${AWS_CRT_AUTH_SRC}) + source_group("Source Files\\checksum" FILES ${AWS_CRT_CHECKSUM_SRC}) source_group("Source Files\\crypto" FILES ${AWS_CRT_CRYPTO_SRC}) source_group("Source Files\\io" FILES ${AWS_CRT_IO_SRC}) source_group("Source Files\\iot" FILES ${AWS_CRT_IOT_SRC}) @@ -328,6 +340,7 @@ target_link_libraries(${PROJECT_NAME} PUBLIC ${DEP_AWS_LIBS}) install(FILES ${AWS_CRT_HEADERS} DESTINATION "include/aws/crt" COMPONENT Development) install(FILES ${AWS_CRT_AUTH_HEADERS} DESTINATION "include/aws/crt/auth" COMPONENT Development) +install(FILES ${AWS_CRT_CHECKSUM_HEADERS} DESTINATION "include/aws/crt/crypto" COMPONENT Development) install(FILES ${AWS_CRT_CRYPTO_HEADERS} DESTINATION "include/aws/crt/crypto" COMPONENT Development) install(FILES ${AWS_CRT_IO_HEADERS} DESTINATION "include/aws/crt/io" COMPONENT Development) install(FILES ${AWS_CRT_IOT_HEADERS} DESTINATION "include/aws/iot" COMPONENT Development) diff --git a/crt/aws-checksums b/crt/aws-checksums index aac442a2d..ce04ab00b 160000 --- a/crt/aws-checksums +++ b/crt/aws-checksums @@ -1 +1 @@ -Subproject commit aac442a2dbbb5e72d0a3eca8313cf65e7e1cac2f +Subproject commit ce04ab00b3ecc41912f478bfedca39f8e1919d6b diff --git a/include/aws/crt/checksum/CRC.h b/include/aws/crt/checksum/CRC.h new file mode 100644 index 000000000..023d1d21a --- /dev/null +++ b/include/aws/crt/checksum/CRC.h @@ -0,0 +1,39 @@ +#pragma once +/** + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0. + */ +#include +#include + +namespace Aws +{ + namespace Crt + { + namespace Checksum + { + /** + * The entry point function to perform a CRC32 (Ethernet, gzip) computation. + * Selects a suitable implementation based on hardware capabilities. + * Pass previousCRC32 if updating a running checksum. + */ + uint32_t AWS_CRT_CPP_API ComputeCRC32(ByteCursor input, uint32_t previousCRC32 = 0) noexcept; + + /** + * The entry point function to perform a Castagnoli CRC32c (iSCSI) computation. + * Selects a suitable implementation based on hardware capabilities. + * Pass previousCRC32C if updating a running checksum. + */ + uint32_t AWS_CRT_CPP_API ComputeCRC32C(ByteCursor input, uint32_t previousCRC32C = 0) noexcept; + + /** + * The entry point function to perform a CRC64-NVME (a.k.a. CRC64-Rocksoft) computation. + * Selects a suitable implementation based on hardware capabilities. + * Pass previousCRC64NVME if updating a running checksum. + * There are many variants of CRC64 algorithms. This CRC64 variant is bit-reflected (based on + * the non bit-reflected polynomial 0xad93d23594c93659) and inverts the CRC input and output bits. + */ + uint64_t AWS_CRT_CPP_API ComputeCRC64NVME(ByteCursor input, uint64_t previousCRC64NVME = 0) noexcept; + } // namespace Checksum + } // namespace Crt +} // namespace Aws diff --git a/include/aws/crt/crypto/Hash.h b/include/aws/crt/crypto/Hash.h index 98e3e3c93..af8a7c7d2 100644 --- a/include/aws/crt/crypto/Hash.h +++ b/include/aws/crt/crypto/Hash.h @@ -189,7 +189,7 @@ namespace Aws /** * Complete the hash computation and write the final digest to output. - * This cannote be called more than once. + * This cannot be called more than once. * If truncate_to is something other than 0, the output must be truncated to that number of bytes. * Raise an AWS error and return false to indicate failure. */ diff --git a/source/checksum/CRC.cpp b/source/checksum/CRC.cpp new file mode 100644 index 000000000..65ed70e28 --- /dev/null +++ b/source/checksum/CRC.cpp @@ -0,0 +1,32 @@ +/** + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0. + */ +#include + +#include + +namespace Aws +{ + namespace Crt + { + namespace Checksum + { + uint32_t ComputeCRC32(ByteCursor input, uint32_t previousCRC32) noexcept + { + return aws_checksums_crc32_ex(input.ptr, input.len, previousCRC32); + } + + uint32_t ComputeCRC32C(ByteCursor input, uint32_t previousCRC32C) noexcept + { + return aws_checksums_crc32c_ex(input.ptr, input.len, previousCRC32C); + } + + uint64_t ComputeCRC64NVME(ByteCursor input, uint64_t previousCRC64NVME) noexcept + { + return aws_checksums_crc64nvme_ex(input.ptr, input.len, previousCRC64NVME); + } + + } // namespace Checksum + } // namespace Crt +} // namespace Aws diff --git a/tests/CRCTest.cpp b/tests/CRCTest.cpp new file mode 100644 index 000000000..464fe4862 --- /dev/null +++ b/tests/CRCTest.cpp @@ -0,0 +1,46 @@ +/** + * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved. + * SPDX-License-Identifier: Apache-2.0. + */ +#include +#include +#include + +static int s_TestCRC32Piping(struct aws_allocator *allocator, void *) +{ + Aws::Crt::ApiHandle apiHandle(allocator); + uint8_t data[32] = {0}; + + Aws::Crt::ByteCursor dataCur = aws_byte_cursor_from_array(data, sizeof(data)); + + ASSERT_UINT_EQUALS(0x190A55AD, Aws::Crt::Checksum::ComputeCRC32(dataCur)); + + return AWS_OP_SUCCESS; +} +AWS_TEST_CASE(CRC32Piping, s_TestCRC32Piping) + +static int s_TestCRC32CPiping(struct aws_allocator *allocator, void *) +{ + Aws::Crt::ApiHandle apiHandle(allocator); + uint8_t data[32] = {0}; + + Aws::Crt::ByteCursor dataCur = aws_byte_cursor_from_array(data, sizeof(data)); + + ASSERT_UINT_EQUALS(0x8A9136AA, Aws::Crt::Checksum::ComputeCRC32C(dataCur)); + + return AWS_OP_SUCCESS; +} +AWS_TEST_CASE(CRC32CPiping, s_TestCRC32CPiping) + +static int s_TestCRC64NVMEPiping(struct aws_allocator *allocator, void *) +{ + Aws::Crt::ApiHandle apiHandle(allocator); + uint8_t data[32] = {0}; + + Aws::Crt::ByteCursor dataCur = aws_byte_cursor_from_array(data, sizeof(data)); + + ASSERT_UINT_EQUALS(0xCF3473434D4ECF3B, Aws::Crt::Checksum::ComputeCRC64NVME(dataCur)); + + return AWS_OP_SUCCESS; +} +AWS_TEST_CASE(CRC64NVMEPiping, s_TestCRC64NVMEPiping)