Script 'mail_helper' called by obssrc
Hello community,

here is the log from the commit of package aws-crt-cpp for openSUSE:Factory 
checked in at 2024-04-16 20:05:11
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Comparing /work/SRC/openSUSE:Factory/aws-crt-cpp (Old)
 and      /work/SRC/openSUSE:Factory/.aws-crt-cpp.new.26366 (New)
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Package is "aws-crt-cpp"

Tue Apr 16 20:05:11 2024 rev:4 rq:1167979 version:0.26.8

Changes:
--------
--- /work/SRC/openSUSE:Factory/aws-crt-cpp/aws-crt-cpp.changes  2024-04-12 
17:37:20.085386438 +0200
+++ /work/SRC/openSUSE:Factory/.aws-crt-cpp.new.26366/aws-crt-cpp.changes       
2024-04-16 20:11:25.857181080 +0200
@@ -1,0 +2,10 @@
+Mon Apr 15 11:24:48 UTC 2024 - John Paul Adrian Glaubitz 
<[email protected]>
+
+- Update to version 0.26.8
+  * Bump s2n version to v1.4.11 to support ecdsa521p
+    with TLS1.3 by @alfred2g in (#614)
+- from version 0.26.7
+  * Updated crypto bindings to include SHA1 and AES for
+    use in C++ SDK by @JonathanHenson in (#470)
+
+-------------------------------------------------------------------

Old:
----
  v0.26.6.tar.gz

New:
----
  v0.26.8.tar.gz

++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++

Other differences:
------------------
++++++ aws-crt-cpp.spec ++++++
--- /var/tmp/diff_new_pack.Q7zTlT/_old  2024-04-16 20:11:26.977222240 +0200
+++ /var/tmp/diff_new_pack.Q7zTlT/_new  2024-04-16 20:11:26.981222387 +0200
@@ -19,7 +19,7 @@
 %define library_soversion 1
 
 Name:           aws-crt-cpp
-Version:        0.26.6
+Version:        0.26.8
 Release:        0
 Summary:        AWS C++ wrapper for AWS SDK C libraries
 License:        Apache-2.0

++++++ v0.26.6.tar.gz -> v0.26.8.tar.gz ++++++
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/VERSION 
new/aws-crt-cpp-0.26.8/VERSION
--- old/aws-crt-cpp-0.26.6/VERSION      2024-04-03 23:21:54.000000000 +0200
+++ new/aws-crt-cpp-0.26.8/VERSION      2024-04-12 22:46:53.000000000 +0200
@@ -1 +1 @@
-0.26.6
+0.26.8
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/include/aws/crt/Api.h 
new/aws-crt-cpp-0.26.8/include/aws/crt/Api.h
--- old/aws-crt-cpp-0.26.6/include/aws/crt/Api.h        2024-04-03 
23:21:54.000000000 +0200
+++ new/aws-crt-cpp-0.26.8/include/aws/crt/Api.h        2024-04-12 
22:46:53.000000000 +0200
@@ -94,6 +94,12 @@
             void SetBYOCryptoNewSHA256Callback(Crypto::CreateHashCallback 
&&callback);
 
             /**
+             * BYO_CRYPTO: set callback for creating SHA1 hashes.
+             * If using BYO_CRYPTO, you must call this.
+             */
+            void SetBYOCryptoNewSHA1Callback(Crypto::CreateHashCallback 
&&callback);
+
+            /**
              * BYO_CRYPTO: set callback for creating Streaming SHA256 HMAC 
objects.
              * If using BYO_CRYPTO, you must call this.
              */
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/include/aws/crt/Types.h 
new/aws-crt-cpp-0.26.8/include/aws/crt/Types.h
--- old/aws-crt-cpp-0.26.6/include/aws/crt/Types.h      2024-04-03 
23:21:54.000000000 +0200
+++ new/aws-crt-cpp-0.26.8/include/aws/crt/Types.h      2024-04-12 
22:46:53.000000000 +0200
@@ -65,8 +65,8 @@
         AWS_CRT_CPP_API ByteCursor ByteCursorFromByteBuf(const ByteBuf &) 
noexcept;
         AWS_CRT_CPP_API ByteCursor ByteCursorFromArray(const uint8_t *array, 
size_t len) noexcept;
 
-        AWS_CRT_CPP_API Vector<uint8_t> Base64Decode(const String &decode);
-        AWS_CRT_CPP_API String Base64Encode(const Vector<uint8_t> &encode);
+        AWS_CRT_CPP_API Vector<uint8_t> Base64Decode(const String &decode) 
noexcept;
+        AWS_CRT_CPP_API String Base64Encode(const Vector<uint8_t> &encode) 
noexcept;
 
         template <typename RawType, typename TargetType> using TypeConvertor = 
std::function<TargetType(RawType)>;
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/HMAC.h 
new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/HMAC.h
--- old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/HMAC.h        2024-04-03 
23:21:54.000000000 +0200
+++ new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/HMAC.h        2024-04-12 
22:46:53.000000000 +0200
@@ -88,6 +88,24 @@
                  */
                 bool Digest(ByteBuf &output, size_t truncateTo = 0) noexcept;
 
+                /**
+                 * Returns the size of the digest for this hmac algorithm. If 
this object is not valid, it will
+                 * return 0 instead.
+                 */
+                size_t DigestSize() const noexcept;
+
+                /**
+                 * Computes the running HMAC and finishes the running HMAC 
operation and writes the digest into output.
+                 * The available capacity of output must be large enough for 
the digest.
+                 * See: SHA256_DIGEST_SIZE and MD5_DIGEST_SIZE for size
+                 * hints. 'truncateTo' is for if you want truncated output 
(e.g. you only want the first 16 bytes of a
+                 * SHA256 HMAC digest. Returns true on success. Call 
LastError() for the reason this call failed.
+                 *
+                 * This is an API a user would use for smaller size inputs. 
For larger, streaming inputs, use
+                 * multiple calls to Update() for each buffer, followed by a 
single call to Digest().
+                 */
+                bool ComputeOneShot(const ByteCursor &input, ByteBuf &output, 
size_t truncateTo = 0) noexcept;
+
               private:
                 HMAC(aws_hmac *hmac) noexcept;
                 HMAC() = delete;
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/Hash.h 
new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/Hash.h
--- old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/Hash.h        2024-04-03 
23:21:54.000000000 +0200
+++ new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/Hash.h        2024-04-12 
22:46:53.000000000 +0200
@@ -15,8 +15,9 @@
     {
         namespace Crypto
         {
-            static const size_t SHA256_DIGEST_SIZE = 32;
-            static const size_t MD5_DIGEST_SIZE = 16;
+            static const size_t SHA1_DIGEST_SIZE = AWS_SHA1_LEN;
+            static const size_t SHA256_DIGEST_SIZE = AWS_SHA256_LEN;
+            static const size_t MD5_DIGEST_SIZE = AWS_MD5_LEN;
 
             /**
              * Computes a SHA256 Hash over input, and writes the digest to 
output. If truncateTo is non-zero, the digest
@@ -60,6 +61,26 @@
             bool AWS_CRT_CPP_API ComputeMD5(const ByteCursor &input, ByteBuf 
&output, size_t truncateTo = 0) noexcept;
 
             /**
+             * Computes a SHA1 Hash over input, and writes the digest to 
output. If truncateTo is non-zero, the digest
+             * will be truncated to the value of truncateTo. Returns true on 
success. If this function fails,
+             * Aws::Crt::LastError() will contain the error that occurred. 
Unless you're using 'truncateTo',
+             * output should have a minimum capacity of MD5_DIGEST_SIZE.
+             */
+            bool AWS_CRT_CPP_API ComputeSHA1(
+                Allocator *allocator,
+                const ByteCursor &input,
+                ByteBuf &output,
+                size_t truncateTo = 0) noexcept;
+
+            /**
+             * Computes a SHA1 Hash using the default allocator over input, 
and writes the digest to output. If
+             * truncateTo is non-zero, the digest will be truncated to the 
value of truncateTo. Returns true on success.
+             * If this function fails, Aws::Crt::LastError() will contain the 
error that occurred. Unless you're using
+             * 'truncateTo', output should have a minimum capacity of 
SHA1_DIGEST_SIZE.
+             */
+            bool AWS_CRT_CPP_API ComputeSHA1(const ByteCursor &input, ByteBuf 
&output, size_t truncateTo = 0) noexcept;
+
+            /**
              * Streaming Hash object. The typical use case is for computing 
the hash of an object that is too large to
              * load into memory. You can call Update() multiple times as you 
load chunks of data into memory. When
              * you're finished simply call Digest(). After Digest() is called, 
this object is no longer usable.
@@ -76,7 +97,7 @@
                 /**
                  * Returns true if the instance is in a valid state, false 
otherwise.
                  */
-                inline operator bool() const noexcept { return m_good; }
+                operator bool() const noexcept;
 
                 /**
                  * Returns the value of the last aws error encountered by 
operations on this instance.
@@ -89,6 +110,11 @@
                 static Hash CreateSHA256(Allocator *allocator = 
ApiAllocator()) noexcept;
 
                 /**
+                 * Creates an instance of a Stream SHA1 Hash.
+                 */
+                static Hash CreateSHA1(Allocator *allocator = ApiAllocator()) 
noexcept;
+
+                /**
                  * Creates an instance of a Streaming MD5 Hash.
                  */
                 static Hash CreateMD5(Allocator *allocator = ApiAllocator()) 
noexcept;
@@ -101,18 +127,36 @@
 
                 /**
                  * Finishes the running hash operation and writes the digest 
into output. The available capacity of
-                 * output must be large enough for the digest. See: 
SHA256_DIGEST_SIZE and MD5_DIGEST_SIZE for size
-                 * hints. 'truncateTo' is for if you want truncated output 
(e.g. you only want the first 16 bytes of a
-                 * SHA256 digest. Returns true on success. Call LastError() 
for the reason this call failed.
+                 * output must be large enough for the digest. See: 
SHA1_DIGEST_SIZE, SHA256_DIGEST_SIZE and
+                 * MD5_DIGEST_SIZE for size hints. 'truncateTo' is for if you 
want truncated output (e.g. you only want
+                 * the first 16 bytes of a SHA256 digest. Returns true on 
success. Call LastError() for the reason this
+                 * call failed.
                  */
                 bool Digest(ByteBuf &output, size_t truncateTo = 0) noexcept;
 
+                /**
+                 * Computes the hash of input and writes the digest into 
output. The available capacity of
+                 * output must be large enough for the digest. See: 
SHA1_DIGEST_SIZE, SHA256_DIGEST_SIZE and
+                 * MD5_DIGEST_SIZE for size hints. 'truncateTo' is for if you 
want truncated output (e.g. you only want
+                 * the first 16 bytes of a SHA256 digest. Returns true on 
success. Call LastError() for the reason this
+                 * call failed.
+                 *
+                 * This is an API a user would use for smaller size inputs. 
For larger, streaming inputs, use
+                 * multiple calls to Update() for each buffer, followed by a 
single call to Digest().
+                 */
+                bool ComputeOneShot(const ByteCursor &input, ByteBuf &output, 
size_t truncateTo = 0) noexcept;
+
+                /**
+                 * Returns the size of the digest for this hash algorithm. If 
this object is not valid, it will
+                 * return 0 instead.
+                 */
+                size_t DigestSize() const noexcept;
+
               private:
                 Hash(aws_hash *hash) noexcept;
                 Hash() = delete;
 
                 aws_hash *m_hash;
-                bool m_good;
                 int m_lastError;
             };
 
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/SecureRandom.h 
new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/SecureRandom.h
--- old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/SecureRandom.h        
1970-01-01 01:00:00.000000000 +0100
+++ new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/SecureRandom.h        
2024-04-12 22:46:53.000000000 +0200
@@ -0,0 +1,18 @@
+#pragma once
+/**
+ * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ * SPDX-License-Identifier: Apache-2.0.
+ */
+#include <aws/crt/Exports.h>
+#include <aws/crt/Types.h>
+
+namespace Aws
+{
+    namespace Crt
+    {
+        namespace Crypto
+        {
+            bool AWS_CRT_CPP_API GenerateRandomBytes(ByteBuf &output, size_t 
lengthToGenerate);
+        }
+    } // namespace Crt
+} // namespace Aws
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' 
old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/SymmetricCipher.h 
new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/SymmetricCipher.h
--- old/aws-crt-cpp-0.26.6/include/aws/crt/crypto/SymmetricCipher.h     
1970-01-01 01:00:00.000000000 +0100
+++ new/aws-crt-cpp-0.26.8/include/aws/crt/crypto/SymmetricCipher.h     
2024-04-12 22:46:53.000000000 +0200
@@ -0,0 +1,149 @@
+#pragma once
+/**
+ * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ * SPDX-License-Identifier: Apache-2.0.
+ */
+#include <aws/crt/Exports.h>
+#include <aws/crt/Types.h>
+
+struct aws_symmetric_cipher;
+
+namespace Aws
+{
+    namespace Crt
+    {
+        namespace Crypto
+        {
+            static const size_t AES_256_CIPHER_BLOCK_SIZE = 16u;
+            static const size_t AES_256_KEY_SIZE_BYTES = 32u;
+
+            class AWS_CRT_CPP_API SymmetricCipher final
+            {
+              public:
+                SymmetricCipher(const SymmetricCipher &) = delete;
+                SymmetricCipher &operator=(const SymmetricCipher &) = delete;
+                SymmetricCipher(SymmetricCipher &&) noexcept = default;
+                SymmetricCipher &operator=(SymmetricCipher &&) noexcept = 
default;
+
+                /**
+                 * Creates an AES 256 CBC mode cipher using a provided key and 
iv.
+                 * Key must be 32 bytes. If key or iv are not provided, they 
will be generated.
+                 */
+                static SymmetricCipher CreateAES_256_CBC_Cipher(
+                    const Optional<ByteCursor> &key = Optional<ByteCursor>(),
+                    const Optional<ByteCursor> &iv = Optional<ByteCursor>(),
+                    Allocator *allocator = ApiAllocator()) noexcept;
+
+                /**
+                 * Creates an AES 256 CTR mode cipher using a provided key and 
iv.
+                 * If key and iv are not provided, they will be generated.
+                 */
+                static SymmetricCipher CreateAES_256_CTR_Cipher(
+                    const Optional<ByteCursor> &key = Optional<ByteCursor>(),
+                    const Optional<ByteCursor> &iv = Optional<ByteCursor>(),
+                    Allocator *allocator = ApiAllocator()) noexcept;
+
+                /**
+                 * Creates an AES 256 GCM mode cipher using a provided key, 
iv, tag, and aad if provided.
+                 * Key and iv will be generated if not provided.
+                 * Tag and AAD values are not generated. Provide tag if you're 
trying to decrypt
+                 * a payload. The tag will be used to verify the payload has 
not been tampered with
+                 * upon decryption operations.
+                 * Provide AAD if you need to provide additional auth info.
+                 */
+                static SymmetricCipher CreateAES_256_GCM_Cipher(
+                    const Optional<ByteCursor> &key = Optional<ByteCursor>(),
+                    const Optional<ByteCursor> &iv = Optional<ByteCursor>(),
+                    const Optional<ByteCursor> &tag = Optional<ByteCursor>(),
+                    const Optional<ByteCursor> &aad = Optional<ByteCursor>(),
+                    Allocator *allocator = ApiAllocator()) noexcept;
+
+                /**
+                 * Creates an AES 256 Keywrap mode cipher using key if 
provided.
+                 * If a key is not provided, one will be generated.
+                 */
+                static SymmetricCipher CreateAES_256_KeyWrap_Cipher(
+                    const Optional<ByteCursor> &key = Optional<ByteCursor>(),
+                    Allocator *allocator = ApiAllocator()) noexcept;
+
+                /**
+                 * Returns true if the instance is in a valid state, false 
otherwise.
+                 */
+                operator bool() const noexcept;
+
+                /**
+                 * Returns the value of the last aws error encountered by 
operations on this instance.
+                 */
+                inline int LastError() const noexcept { return m_lastError; }
+
+                /**
+                 * Encrypts the value in toEncrypt and stores any immediate 
results in out. Out can be dynamically
+                 * re-sized if out is a dynamic byte buf. Otherwise, make sure 
the size of out is at least 2 blocks
+                 * larger than the input to allow for padding.
+                 *
+                 * Returns true on success. Call
+                 * LastError() for the reason this call failed.
+                 */
+                bool Encrypt(const ByteCursor &toEncrypt, ByteBuf &out) 
noexcept;
+
+                /**
+                 * Encrypts any remaining data on the cipher and stores the 
output in out. Out can be dynamically
+                 * re-sized if out is a dynamic byte buf. Otherwise, make sure 
the size of out is at least 2 blocks
+                 * for CBC, CTR, and GCM modes and 40 bytes for KeyWrap.
+                 *
+                 * Returns true on success. Call
+                 * LastError() for the reason this call failed.
+                 */
+                bool FinalizeEncryption(ByteBuf &out) noexcept;
+
+                /**
+                 * Decrypts the value in toEncrypt and stores any immediate 
results in out. Out can be dynamically
+                 * re-sized if out is a dynamic byte buf. Otherwise, make sure 
the size of out is at least 1 block
+                 * larger than the input to allow for padding. Returns true on 
success. Call LastError() for the reason
+                 * this call failed.
+                 */
+                bool Decrypt(const ByteCursor &toDecrypt, ByteBuf &out) 
noexcept;
+
+                /**
+                 * Decrypts any remaining data on the cipher and stores the 
output in out. Out can be dynamically
+                 * re-sized if out is a dynamic byte buf. Otherwise, make sure 
the size of out is at least 2 blocks
+                 * for CBC, CTR, GCM, and Keywrap modes.
+                 *
+                 * Returns true on success. Call
+                 * LastError() for the reason this call failed.
+                 */
+                bool FinalizeDecryption(ByteBuf &out) noexcept;
+
+                /**
+                 * Reset to cipher to new state.
+                 */
+                bool Reset() noexcept;
+
+                /**
+                 * Returns the key used for this cipher. This key is not 
copied from the cipher so do not mutate this
+                 * data. Copy if if you need to pass it around anywhere.
+                 */
+                ByteCursor GetKey() const noexcept;
+
+                /**
+                 * Returns the initialization vector used for this cipher.
+                 * This IV is not copied from the cipher so do not mutate this
+                 * data. Copy if if you need to pass it around anywhere.
+                 */
+                ByteCursor GetIV() const noexcept;
+
+                /**
+                 * Returns the encryption tag generated during encryption 
operations for this cipher in GCM mode.
+                 * This tag is not copied from the cipher so do not mutate this
+                 * data. Copy if if you need to pass it around anywhere.
+                 */
+                ByteCursor GetTag() const noexcept;
+
+              private:
+                SymmetricCipher(aws_symmetric_cipher *cipher) noexcept;
+                ScopedResource<struct aws_symmetric_cipher> m_cipher;
+                int m_lastError;
+            };
+        } // namespace Crypto
+    }     // namespace Crt
+} // namespace Aws
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/source/Api.cpp 
new/aws-crt-cpp-0.26.8/source/Api.cpp
--- old/aws-crt-cpp-0.26.6/source/Api.cpp       2024-04-03 23:21:54.000000000 
+0200
+++ new/aws-crt-cpp-0.26.8/source/Api.cpp       2024-04-12 22:46:53.000000000 
+0200
@@ -23,6 +23,7 @@
     {
         static Crypto::CreateHashCallback s_BYOCryptoNewMD5Callback;
         static Crypto::CreateHashCallback s_BYOCryptoNewSHA256Callback;
+        static Crypto::CreateHashCallback s_BYOCryptoNewSHA1Callback;
         static Crypto::CreateHMACCallback s_BYOCryptoNewSHA256HMACCallback;
         static Io::NewClientTlsHandlerCallback 
s_BYOCryptoNewClientTlsHandlerCallback;
         static Io::NewTlsContextImplCallback 
s_BYOCryptoNewTlsContextImplCallback;
@@ -182,6 +183,31 @@
             aws_set_sha256_new_fn(s_Sha256New);
         }
 
+        static struct aws_hash *s_Sha1New(struct aws_allocator *allocator)
+        {
+            if (!s_BYOCryptoNewSHA1Callback)
+            {
+                AWS_LOGF_ERROR(
+                    AWS_LS_IO_TLS,
+                    "Must call ApiHandle::SetBYOCryptoNewSHA1Callback() before 
SHA1 hash can be created");
+                aws_raise_error(AWS_ERROR_UNIMPLEMENTED);
+                return nullptr;
+            }
+
+            auto hash = s_BYOCryptoNewSHA1Callback(AWS_SHA1_LEN, allocator);
+            if (!hash)
+            {
+                return nullptr;
+            }
+            return hash->SeatForCInterop(hash);
+        }
+
+        void ApiHandle::SetBYOCryptoNewSHA1Callback(Crypto::CreateHashCallback 
&&callback)
+        {
+            s_BYOCryptoNewSHA1Callback = std::move(callback);
+            aws_set_sha1_new_fn(s_Sha1New);
+        }
+
         static struct aws_hmac *s_sha256HMACNew(struct aws_allocator 
*allocator, const struct aws_byte_cursor *secret)
         {
             if (!s_BYOCryptoNewSHA256HMACCallback)
@@ -276,6 +302,11 @@
                 AWS_LS_IO_TLS, "SetBYOCryptoNewSHA256Callback() has no effect 
unless compiled with BYO_CRYPTO");
         }
 
+        void ApiHandle::SetBYOCryptoNewSHA1Callback(Crypto::CreateHashCallback 
&&)
+        {
+            AWS_LOGF_WARN(AWS_LS_IO_TLS, "SetBYOCryptoNewSHA1Callback() has no 
effect unless compiled with BYO_CRYPTO");
+        }
+
         void 
ApiHandle::SetBYOCryptoNewSHA256HMACCallback(Crypto::CreateHMACCallback &&)
         {
             AWS_LOGF_WARN(
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/source/Types.cpp 
new/aws-crt-cpp-0.26.8/source/Types.cpp
--- old/aws-crt-cpp-0.26.6/source/Types.cpp     2024-04-03 23:21:54.000000000 
+0200
+++ new/aws-crt-cpp-0.26.8/source/Types.cpp     2024-04-12 22:46:53.000000000 
+0200
@@ -51,53 +51,53 @@
             return aws_byte_cursor_from_array(array, len);
         }
 
-        Vector<uint8_t> Base64Decode(const String &decode)
+        Vector<uint8_t> Base64Decode(const String &decode) noexcept
         {
             ByteCursor toDecode = ByteCursorFromString(decode);
 
-            size_t allocation_size = 0;
+            size_t allocationSize = 0;
 
-            if (aws_base64_compute_decoded_len(&toDecode, &allocation_size) == 
AWS_OP_SUCCESS)
+            if (AWS_OP_SUCCESS != aws_base64_compute_decoded_len(&toDecode, 
&allocationSize))
             {
-                Vector<uint8_t> output(allocation_size, 0x00);
-                ByteBuf tempBuf = aws_byte_buf_from_array(output.data(), 
output.size());
-                tempBuf.len = 0;
-
-                if (aws_base64_decode(&toDecode, &tempBuf) == AWS_OP_SUCCESS)
-                {
-                    return output;
-                }
+                return {};
             }
 
-            return {};
+            Vector<uint8_t> output(allocationSize, 0x00);
+            ByteBuf tempBuf = aws_byte_buf_from_empty_array(output.data(), 
output.size());
+
+            if (AWS_OP_SUCCESS != aws_base64_decode(&toDecode, &tempBuf))
+            {
+                return {};
+            }
+
+            return output;
         }
 
-        String Base64Encode(const Vector<uint8_t> &encode)
+        String Base64Encode(const Vector<uint8_t> &encode) noexcept
         {
-            ByteCursor toEncode = aws_byte_cursor_from_array((const void 
*)encode.data(), encode.size());
+            auto toEncode = aws_byte_cursor_from_array((const void 
*)encode.data(), encode.size());
+
+            size_t allocationSize = 0;
+            if (AWS_OP_SUCCESS != aws_base64_compute_encoded_len(toEncode.len, 
&allocationSize))
+            {
+                return {};
+            }
 
-            size_t allocation_size = 0;
+            String outputStr(allocationSize, 0x00);
+            auto tempBuf = aws_byte_buf_from_empty_array(outputStr.data(), 
outputStr.size());
 
-            if (aws_base64_compute_encoded_len(encode.size(), 
&allocation_size) == AWS_OP_SUCCESS)
+            if (AWS_OP_SUCCESS != aws_base64_encode(&toEncode, &tempBuf))
             {
-                String output(allocation_size, 0x00);
-                ByteBuf tempBuf = aws_byte_buf_from_array(output.data(), 
output.size());
-                tempBuf.len = 0;
-
-                if (aws_base64_encode(&toEncode, &tempBuf) == AWS_OP_SUCCESS)
-                {
-                    // encoding appends a null terminator, and accounts for it 
in the encoded length,
-                    // which makes the string 1 character too long
-                    if (output.back() == 0)
-                    {
-                        output.pop_back();
-                    }
-                    return output;
-                }
+                return {};
             }
 
-            return {};
+            // encoding appends a null terminator, and accounts for it in the 
encoded length,
+            // which makes the string 1 character too long
+            if (outputStr.back() == 0)
+            {
+                outputStr.pop_back();
+            }
+            return outputStr;
         }
-
     } // namespace Crt
 } // namespace Aws
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/source/crypto/HMAC.cpp 
new/aws-crt-cpp-0.26.8/source/crypto/HMAC.cpp
--- old/aws-crt-cpp-0.26.6/source/crypto/HMAC.cpp       2024-04-03 
23:21:54.000000000 +0200
+++ new/aws-crt-cpp-0.26.8/source/crypto/HMAC.cpp       2024-04-12 
22:46:53.000000000 +0200
@@ -19,7 +19,13 @@
                 ByteBuf &output,
                 size_t truncateTo) noexcept
             {
-                return aws_sha256_hmac_compute(allocator, &secret, &input, 
&output, truncateTo) == AWS_OP_SUCCESS;
+                auto hmac = HMAC::CreateSHA256HMAC(allocator, secret);
+                if (hmac)
+                {
+                    return hmac.ComputeOneShot(input, output, truncateTo);
+                }
+
+                return false;
             }
 
             bool ComputeSHA256HMAC(
@@ -28,7 +34,7 @@
                 ByteBuf &output,
                 size_t truncateTo) noexcept
             {
-                return aws_sha256_hmac_compute(ApiAllocator(), &secret, 
&input, &output, truncateTo) == AWS_OP_SUCCESS;
+                return ComputeSHA256HMAC(ApiAllocator(), secret, input, 
output, truncateTo);
             }
 
             HMAC::HMAC(aws_hmac *hmac) noexcept : m_hmac(hmac), m_good(false), 
m_lastError(0)
@@ -80,34 +86,54 @@
 
             bool HMAC::Update(const ByteCursor &toHMAC) noexcept
             {
-                if (*this)
+                if (!*this)
                 {
-                    if (aws_hmac_update(m_hmac, &toHMAC))
-                    {
-                        m_lastError = aws_last_error();
-                        m_good = false;
-                        return false;
-                    }
-                    return true;
+                    return false;
                 }
 
-                return false;
+                if (AWS_OP_SUCCESS != aws_hmac_update(m_hmac, &toHMAC))
+                {
+                    m_lastError = aws_last_error();
+                    m_good = false;
+                    return false;
+                }
+                return true;
             }
 
             bool HMAC::Digest(ByteBuf &output, size_t truncateTo) noexcept
             {
-                if (*this)
+                if (!*this)
                 {
-                    m_good = false;
-                    if (aws_hmac_finalize(m_hmac, &output, truncateTo))
-                    {
-                        m_lastError = aws_last_error();
-                        return false;
-                    }
-                    return true;
+                    return false;
                 }
 
-                return false;
+                m_good = false;
+                if (AWS_OP_SUCCESS != aws_hmac_finalize(m_hmac, &output, 
truncateTo))
+                {
+                    m_lastError = aws_last_error();
+                    return false;
+                }
+                return true;
+            }
+
+            bool HMAC::ComputeOneShot(const ByteCursor &input, ByteBuf 
&output, size_t truncateTo) noexcept
+            {
+                if (!*this || !Update(input))
+                {
+                    return false;
+                }
+
+                return Digest(output, truncateTo);
+            }
+
+            size_t HMAC::DigestSize() const noexcept
+            {
+                if (!*this)
+                {
+                    return 0;
+                }
+
+                return m_hmac->digest_size;
             }
 
             aws_hmac_vtable ByoHMAC::s_Vtable = {
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/source/crypto/Hash.cpp 
new/aws-crt-cpp-0.26.8/source/crypto/Hash.cpp
--- old/aws-crt-cpp-0.26.6/source/crypto/Hash.cpp       2024-04-03 
23:21:54.000000000 +0200
+++ new/aws-crt-cpp-0.26.8/source/crypto/Hash.cpp       2024-04-12 
22:46:53.000000000 +0200
@@ -18,31 +18,41 @@
                 ByteBuf &output,
                 size_t truncateTo) noexcept
             {
-                return aws_sha256_compute(allocator, &input, &output, 
truncateTo) == AWS_OP_SUCCESS;
+                auto hash = Hash::CreateSHA256(allocator);
+                return hash.ComputeOneShot(input, output, truncateTo);
             }
 
             bool ComputeSHA256(const ByteCursor &input, ByteBuf &output, 
size_t truncateTo) noexcept
             {
-                return aws_sha256_compute(ApiAllocator(), &input, &output, 
truncateTo) == AWS_OP_SUCCESS;
+                return ComputeSHA256(ApiAllocator(), input, output, 
truncateTo);
+            }
+
+            bool ComputeSHA1(Allocator *allocator, const ByteCursor &input, 
ByteBuf &output, size_t truncateTo) noexcept
+            {
+                auto hash = Hash::CreateSHA1(allocator);
+                return hash.ComputeOneShot(input, output, truncateTo);
+            }
+
+            bool ComputeSHA1(const ByteCursor &input, ByteBuf &output, size_t 
truncateTo) noexcept
+            {
+                return ComputeSHA1(ApiAllocator(), input, output, truncateTo);
             }
 
             bool ComputeMD5(Allocator *allocator, const ByteCursor &input, 
ByteBuf &output, size_t truncateTo) noexcept
             {
-                return aws_md5_compute(allocator, &input, &output, truncateTo) 
== AWS_OP_SUCCESS;
+                auto hash = Hash::CreateMD5(allocator);
+                return hash.ComputeOneShot(input, output, truncateTo);
             }
 
             bool ComputeMD5(const ByteCursor &input, ByteBuf &output, size_t 
truncateTo) noexcept
             {
-                return aws_md5_compute(ApiAllocator(), &input, &output, 
truncateTo) == AWS_OP_SUCCESS;
+                auto hash = Hash::CreateMD5(ApiAllocator());
+                return hash.ComputeOneShot(input, output, truncateTo);
             }
 
-            Hash::Hash(aws_hash *hash) noexcept : m_hash(hash), m_good(false), 
m_lastError(0)
+            Hash::Hash(aws_hash *hash) noexcept : m_hash(hash), m_lastError(0)
             {
-                if (hash)
-                {
-                    m_good = true;
-                }
-                else
+                if (!hash)
                 {
                     m_lastError = aws_last_error();
                 }
@@ -57,12 +67,13 @@
                 }
             }
 
-            Hash::Hash(Hash &&toMove) : m_hash(toMove.m_hash), 
m_good(toMove.m_good), m_lastError(toMove.m_lastError)
+            Hash::Hash(Hash &&toMove) : m_hash(toMove.m_hash), 
m_lastError(toMove.m_lastError)
             {
                 toMove.m_hash = nullptr;
-                toMove.m_good = false;
             }
 
+            Hash::operator bool() const noexcept { return m_hash != nullptr && 
m_hash->good; }
+
             Hash &Hash::operator=(Hash &&toMove)
             {
                 if (&toMove != this)
@@ -77,36 +88,56 @@
 
             Hash Hash::CreateMD5(Allocator *allocator) noexcept { return 
Hash(aws_md5_new(allocator)); }
 
+            Hash Hash::CreateSHA1(Allocator *allocator) noexcept { return 
Hash(aws_sha1_new(allocator)); }
+
             bool Hash::Update(const ByteCursor &toHash) noexcept
             {
-                if (*this)
+                if (!*this)
                 {
-                    if (aws_hash_update(m_hash, &toHash))
-                    {
-                        m_lastError = aws_last_error();
-                        m_good = false;
-                        return false;
-                    }
-                    return true;
+                    return false;
                 }
 
-                return false;
+                if (AWS_OP_SUCCESS != aws_hash_update(m_hash, &toHash))
+                {
+                    m_lastError = aws_last_error();
+                    return false;
+                }
+                return true;
             }
 
             bool Hash::Digest(ByteBuf &output, size_t truncateTo) noexcept
             {
-                if (*this)
+                if (!*this)
+                {
+                    return false;
+                }
+
+                if (aws_hash_finalize(m_hash, &output, truncateTo) != 
AWS_OP_SUCCESS)
+                {
+                    m_lastError = aws_last_error();
+                    return false;
+                }
+                return true;
+            }
+
+            bool Hash::ComputeOneShot(const ByteCursor &input, ByteBuf 
&output, size_t truncateTo) noexcept
+            {
+                if (!*this || !Update(input))
+                {
+                    return false;
+                }
+
+                return Digest(output, truncateTo);
+            }
+
+            size_t Hash::DigestSize() const noexcept
+            {
+                if (m_hash != nullptr)
                 {
-                    m_good = false;
-                    if (aws_hash_finalize(m_hash, &output, truncateTo))
-                    {
-                        m_lastError = aws_last_error();
-                        return false;
-                    }
-                    return true;
+                    return m_hash->digest_size;
                 }
 
-                return false;
+                return 0;
             }
 
             aws_hash_vtable ByoHash::s_Vtable = {
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/source/crypto/SecureRandom.cpp 
new/aws-crt-cpp-0.26.8/source/crypto/SecureRandom.cpp
--- old/aws-crt-cpp-0.26.6/source/crypto/SecureRandom.cpp       1970-01-01 
01:00:00.000000000 +0100
+++ new/aws-crt-cpp-0.26.8/source/crypto/SecureRandom.cpp       2024-04-12 
22:46:53.000000000 +0200
@@ -0,0 +1,21 @@
+/**
+ * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ * SPDX-License-Identifier: Apache-2.0.
+ */
+#include <aws/crt/crypto/SecureRandom.h>
+
+#include <aws/common/device_random.h>
+
+namespace Aws
+{
+    namespace Crt
+    {
+        namespace Crypto
+        {
+            bool GenerateRandomBytes(ByteBuf &output, size_t lengthToGenerate)
+            {
+                return aws_device_random_buffer_append(&output, 
lengthToGenerate) == AWS_OP_SUCCESS;
+            }
+        } // namespace Crypto
+    }     // namespace Crt
+} // namespace Aws
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/source/crypto/SymmetricCipher.cpp 
new/aws-crt-cpp-0.26.8/source/crypto/SymmetricCipher.cpp
--- old/aws-crt-cpp-0.26.6/source/crypto/SymmetricCipher.cpp    1970-01-01 
01:00:00.000000000 +0100
+++ new/aws-crt-cpp-0.26.8/source/crypto/SymmetricCipher.cpp    2024-04-12 
22:46:53.000000000 +0200
@@ -0,0 +1,167 @@
+/**
+ * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ * SPDX-License-Identifier: Apache-2.0.
+ */
+#include <aws/crt/Api.h>
+#include <aws/crt/crypto/SymmetricCipher.h>
+
+#include <aws/cal/symmetric_cipher.h>
+
+namespace Aws
+{
+    namespace Crt
+    {
+        namespace Crypto
+        {
+            SymmetricCipher::SymmetricCipher(aws_symmetric_cipher *cipher) 
noexcept
+                : m_cipher(cipher, aws_symmetric_cipher_destroy), 
m_lastError(0)
+            {
+                if (cipher == nullptr)
+                {
+                    m_lastError = Crt::LastError();
+                }
+            }
+
+            SymmetricCipher::operator bool() const noexcept
+            {
+                return m_cipher != nullptr ? 
aws_symmetric_cipher_is_good(m_cipher.get()) : false;
+            }
+
+            bool SymmetricCipher::Encrypt(const ByteCursor &toEncrypt, ByteBuf 
&out) noexcept
+            {
+                if (!*this)
+                {
+                    m_lastError = AWS_ERROR_INVALID_STATE;
+                    return false;
+                }
+
+                if (aws_symmetric_cipher_encrypt(m_cipher.get(), toEncrypt, 
&out) != AWS_OP_SUCCESS)
+                {
+                    m_lastError = Aws::Crt::LastError();
+                    return false;
+                }
+
+                return true;
+            }
+
+            bool SymmetricCipher::FinalizeEncryption(ByteBuf &out) noexcept
+            {
+                if (!*this)
+                {
+                    m_lastError = AWS_ERROR_INVALID_STATE;
+                    return false;
+                }
+
+                if (aws_symmetric_cipher_finalize_encryption(m_cipher.get(), 
&out) != AWS_OP_SUCCESS)
+                {
+                    m_lastError = Aws::Crt::LastError();
+                    return false;
+                }
+
+                return true;
+            }
+
+            bool SymmetricCipher::Decrypt(const ByteCursor &toDecrypt, ByteBuf 
&out) noexcept
+            {
+                if (!*this)
+                {
+                    m_lastError = AWS_ERROR_INVALID_STATE;
+                    return false;
+                }
+
+                if (aws_symmetric_cipher_decrypt(m_cipher.get(), toDecrypt, 
&out) != AWS_OP_SUCCESS)
+                {
+                    m_lastError = Aws::Crt::LastError();
+                    return false;
+                }
+
+                return true;
+            }
+
+            bool SymmetricCipher::FinalizeDecryption(ByteBuf &out) noexcept
+            {
+                if (!*this)
+                {
+                    m_lastError = AWS_ERROR_INVALID_STATE;
+                    return false;
+                }
+
+                if (aws_symmetric_cipher_finalize_decryption(m_cipher.get(), 
&out) != AWS_OP_SUCCESS)
+                {
+                    m_lastError = Aws::Crt::LastError();
+                    return false;
+                }
+
+                return true;
+            }
+
+            bool SymmetricCipher::Reset() noexcept
+            {
+                if (m_cipher.get() == nullptr)
+                {
+                    m_lastError = AWS_ERROR_INVALID_STATE;
+                    return false;
+                }
+
+                if (aws_symmetric_cipher_reset(m_cipher.get()) != 
AWS_OP_SUCCESS)
+                {
+                    m_lastError = Aws::Crt::LastError();
+                    return false;
+                }
+
+                m_lastError = 0;
+
+                return true;
+            }
+
+            ByteCursor SymmetricCipher::GetKey() const noexcept { return 
aws_symmetric_cipher_get_key(m_cipher.get()); }
+
+            ByteCursor SymmetricCipher::GetIV() const noexcept
+            {
+                return 
aws_symmetric_cipher_get_initialization_vector(m_cipher.get());
+            }
+
+            ByteCursor SymmetricCipher::GetTag() const noexcept { return 
aws_symmetric_cipher_get_tag(m_cipher.get()); }
+
+            SymmetricCipher SymmetricCipher::CreateAES_256_CBC_Cipher(
+                const Optional<ByteCursor> &key,
+                const Optional<ByteCursor> &iv,
+                Allocator *allocator) noexcept
+            {
+                return {aws_aes_cbc_256_new(
+                    allocator, key.has_value() ? &key.value() : nullptr, 
iv.has_value() ? &iv.value() : nullptr)};
+            }
+
+            SymmetricCipher SymmetricCipher::CreateAES_256_CTR_Cipher(
+                const Optional<ByteCursor> &key,
+                const Optional<ByteCursor> &iv,
+                Allocator *allocator) noexcept
+            {
+                return {aws_aes_ctr_256_new(
+                    allocator, key.has_value() ? &key.value() : nullptr, 
iv.has_value() ? &iv.value() : nullptr)};
+            }
+
+            SymmetricCipher SymmetricCipher::CreateAES_256_GCM_Cipher(
+                const Optional<ByteCursor> &key,
+                const Optional<ByteCursor> &iv,
+                const Optional<ByteCursor> &tag,
+                const Optional<ByteCursor> &aad,
+                Allocator *allocator) noexcept
+            {
+                return {aws_aes_gcm_256_new(
+                    allocator,
+                    key.has_value() ? &key.value() : nullptr,
+                    iv.has_value() ? &iv.value() : nullptr,
+                    tag.has_value() ? &tag.value() : nullptr,
+                    aad.has_value() ? &aad.value() : nullptr)};
+            }
+
+            SymmetricCipher SymmetricCipher::CreateAES_256_KeyWrap_Cipher(
+                const Optional<ByteCursor> &key,
+                Allocator *allocator) noexcept
+            {
+                return {aws_aes_keywrap_256_new(allocator, key.has_value() ? 
&key.value() : nullptr)};
+            }
+        } // namespace Crypto
+    }     // namespace Crt
+} // namespace Aws
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/tests/CMakeLists.txt 
new/aws-crt-cpp-0.26.8/tests/CMakeLists.txt
--- old/aws-crt-cpp-0.26.6/tests/CMakeLists.txt 2024-04-03 23:21:54.000000000 
+0200
+++ new/aws-crt-cpp-0.26.8/tests/CMakeLists.txt 2024-04-12 22:46:53.000000000 
+0200
@@ -64,8 +64,18 @@
 add_test_case(JsonMoveTest)
 add_test_case(SHA256ResourceSafety)
 add_test_case(MD5ResourceSafety)
+add_test_case(SHA1ResourceSafety)
 add_test_case(SHA256HMACResourceSafety)
 
+# TODO: disable aes byo tests for now. c-cal side is missing ability to 
override
+# aes constructors. those need to be implemented first before we can support 
it.
+if(NOT BYO_CRYPTO)
+    add_test_case(AES_256_CBC_Generated_Materials_ResourceSafety)
+    add_test_case(AES_256_CTR_Generated_Materials_ResourceSafety)
+    add_test_case(AES_256_GCM_Generated_Materials_ResourceSafety)
+    add_test_case(AES_256_Keywrap_Generated_Materials_ResourceSafety)
+endif()
+
 if(NOT BYO_CRYPTO)
     add_net_test_case(HttpDownloadNoBackPressureHTTP1_1)
     add_net_test_case(HttpDownloadNoBackPressureHTTP2)
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/tests/HMACTest.cpp 
new/aws-crt-cpp-0.26.8/tests/HMACTest.cpp
--- old/aws-crt-cpp-0.26.6/tests/HMACTest.cpp   2024-04-03 23:21:54.000000000 
+0200
+++ new/aws-crt-cpp-0.26.8/tests/HMACTest.cpp   2024-04-12 22:46:53.000000000 
+0200
@@ -32,6 +32,7 @@
         uint8_t output[Aws::Crt::Crypto::SHA256_HMAC_DIGEST_SIZE] = {0};
         Aws::Crt::ByteBuf outputBuf = Aws::Crt::ByteBufFromEmptyArray(output, 
sizeof(output));
 
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::SHA256_HMAC_DIGEST_SIZE, 
sha256Hmac.DigestSize());
         ASSERT_TRUE(sha256Hmac.Update(input));
         ASSERT_TRUE(sha256Hmac.Digest(outputBuf));
         ASSERT_FALSE(sha256Hmac);
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/tests/HashTest.cpp 
new/aws-crt-cpp-0.26.8/tests/HashTest.cpp
--- old/aws-crt-cpp-0.26.6/tests/HashTest.cpp   2024-04-03 23:21:54.000000000 
+0200
+++ new/aws-crt-cpp-0.26.8/tests/HashTest.cpp   2024-04-12 22:46:53.000000000 
+0200
@@ -28,6 +28,8 @@
 
         ASSERT_TRUE(sha256.Update(input));
         ASSERT_TRUE(sha256.Digest(outputBuf));
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::SHA256_DIGEST_SIZE, 
sha256.DigestSize());
+
         ASSERT_FALSE(sha256);
 
         ASSERT_BIN_ARRAYS_EQUALS(expectedBuf.buffer, expectedBuf.len, 
outputBuf.buffer, outputBuf.len);
@@ -71,6 +73,8 @@
 
         ASSERT_TRUE(md5.Update(input));
         ASSERT_TRUE(md5.Digest(outputBuf));
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::MD5_DIGEST_SIZE, 
md5.DigestSize());
+
         ASSERT_FALSE(md5);
 
         ASSERT_BIN_ARRAYS_EQUALS(expectedBuf.buffer, expectedBuf.len, 
outputBuf.buffer, outputBuf.len);
@@ -81,6 +85,36 @@
 
 AWS_TEST_CASE(MD5ResourceSafety, s_TestMD5ResourceSafety)
 
+static int s_TestSHA1ResourceSafety(struct aws_allocator *allocator, void *)
+{
+    {
+        Aws::Crt::ApiHandle apiHandle(allocator);
+        Aws::Crt::Crypto::Hash sha1 = 
Aws::Crt::Crypto::Hash::CreateSHA1(allocator);
+        ASSERT_TRUE(sha1);
+
+        Aws::Crt::ByteCursor input =
+            
aws_byte_cursor_from_c_str("abcdefghbcdefghicdefghijdefghijkefghijklfghijklmghijklmnhijklmnoijklmnop"
+                                       
"jklmnopqklmnopqrlmnopqrsmnopqrstnopqrstu");
+        uint8_t expected[] = {0xa4, 0x9b, 0x24, 0x46, 0xa0, 0x2c, 0x64, 0x5b, 
0xf4, 0x19,
+                              0xf9, 0x95, 0xb6, 0x70, 0x91, 0x25, 0x3a, 0x04, 
0xa2, 0x59};
+        Aws::Crt::ByteBuf expectedBuf = Aws::Crt::ByteBufFromArray(expected, 
sizeof(expected));
+
+        uint8_t output[Aws::Crt::Crypto::SHA1_DIGEST_SIZE] = {0};
+        Aws::Crt::ByteBuf outputBuf = Aws::Crt::ByteBufFromEmptyArray(output, 
sizeof(output));
+
+        ASSERT_TRUE(sha1.Update(input));
+        ASSERT_TRUE(sha1.Digest(outputBuf));
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::SHA1_DIGEST_SIZE, 
sha1.DigestSize());
+        ASSERT_FALSE(sha1);
+
+        ASSERT_BIN_ARRAYS_EQUALS(expectedBuf.buffer, expectedBuf.len, 
outputBuf.buffer, outputBuf.len);
+    }
+
+    return AWS_OP_SUCCESS;
+}
+
+AWS_TEST_CASE(SHA1ResourceSafety, s_TestSHA1ResourceSafety)
+
 #else
 
 class ByoCryptoHashInterceptor : public Aws::Crt::Crypto::ByoHash
@@ -146,6 +180,40 @@
 
 AWS_TEST_CASE(SHA256ResourceSafety, s_TestSHA256ResourceSafety)
 
+static int s_TestSHA1ResourceSafety(struct aws_allocator *allocator, void *)
+{
+    {
+        Aws::Crt::ApiHandle apiHandle(allocator);
+        uint8_t expected[] = {
+            0xba, 0x78, 0x16, 0xbf, 0x8f, 0x01, 0xcf, 0xea, 0x41, 0x41,
+            0x40, 0xde, 0x5d, 0xae, 0x22, 0x23, 0xb0, 0x03, 0x61, 0xa3,
+        };
+        Aws::Crt::String expectedStr = Aws::Crt::String(reinterpret_cast<const 
char *>(expected), sizeof(expected));
+
+        apiHandle.SetBYOCryptoNewSHA1Callback([&](size_t digestSize, 
Aws::Crt::Allocator *allocator) {
+            return Aws::Crt::MakeShared<ByoCryptoHashInterceptor>(allocator, 
digestSize, allocator, expectedStr);
+        });
+
+        Aws::Crt::Crypto::Hash sha1 = 
Aws::Crt::Crypto::Hash::CreateSHA1(allocator);
+        ASSERT_TRUE(sha1);
+
+        Aws::Crt::ByteCursor input = aws_byte_cursor_from_c_str("abc");
+
+        uint8_t output[Aws::Crt::Crypto::SHA1_DIGEST_SIZE] = {0};
+        Aws::Crt::ByteBuf outputBuf = Aws::Crt::ByteBufFromEmptyArray(output, 
sizeof(output));
+
+        ASSERT_TRUE(sha1.Update(input));
+        ASSERT_TRUE(sha1.Digest(outputBuf));
+        ASSERT_FALSE(sha1);
+
+        ASSERT_BIN_ARRAYS_EQUALS(expectedStr.c_str(), expectedStr.length(), 
outputBuf.buffer, outputBuf.len);
+    }
+
+    return AWS_OP_SUCCESS;
+}
+
+AWS_TEST_CASE(SHA1ResourceSafety, s_TestSHA1ResourceSafety)
+
 static int s_TestMD5ResourceSafety(struct aws_allocator *allocator, void *)
 {
     {
diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' 
'--exclude=.svnignore' old/aws-crt-cpp-0.26.6/tests/SymmetricCipherTest.cpp 
new/aws-crt-cpp-0.26.8/tests/SymmetricCipherTest.cpp
--- old/aws-crt-cpp-0.26.6/tests/SymmetricCipherTest.cpp        1970-01-01 
01:00:00.000000000 +0100
+++ new/aws-crt-cpp-0.26.8/tests/SymmetricCipherTest.cpp        2024-04-12 
22:46:53.000000000 +0200
@@ -0,0 +1,200 @@
+/**
+ * Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
+ * SPDX-License-Identifier: Apache-2.0.
+ */
+#include <aws/crt/Api.h>
+#include <aws/crt/crypto/SymmetricCipher.h>
+#include <aws/testing/aws_test_harness.h>
+
+#include <utility>
+
+static int s_TestAES_256_CBC_Generated_Materials_ResourceSafety(struct 
aws_allocator *allocator, void *)
+{
+    {
+        Aws::Crt::ApiHandle apiHandle(allocator);
+
+        auto cbcCipher = 
Aws::Crt::Crypto::SymmetricCipher::CreateAES_256_CBC_Cipher();
+
+        ASSERT_TRUE(cbcCipher);
+
+        auto input = aws_byte_cursor_from_c_str("abc");
+
+        uint8_t output[Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE * 2] = {0};
+        auto outputBuf = Aws::Crt::ByteBufFromEmptyArray(output, 
sizeof(output));
+
+        ASSERT_TRUE(cbcCipher.Encrypt(input, outputBuf));
+        ASSERT_TRUE(cbcCipher.FinalizeEncryption(outputBuf));
+
+        ASSERT_FALSE(cbcCipher);
+
+        ASSERT_TRUE(cbcCipher.Reset());
+
+        auto decryptInput = Aws::Crt::ByteCursorFromByteBuf(outputBuf);
+        outputBuf.len = 0;
+
+        ASSERT_TRUE(cbcCipher.Decrypt(decryptInput, outputBuf));
+        ASSERT_TRUE(cbcCipher.FinalizeDecryption(outputBuf));
+
+        ASSERT_BIN_ARRAYS_EQUALS(input.ptr, input.len, outputBuf.buffer, 
outputBuf.len);
+
+        ASSERT_FALSE(cbcCipher);
+
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_KEY_SIZE_BYTES, 
cbcCipher.GetKey().len);
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE, 
cbcCipher.GetIV().len);
+
+        ASSERT_FALSE(cbcCipher);
+
+        // check IV generates if a key is provided but iv is not
+        uint8_t key[Aws::Crt::Crypto::AES_256_KEY_SIZE_BYTES] = {0xDD};
+        auto keyCur = Aws::Crt::ByteCursorFromArray(key, sizeof(key));
+        cbcCipher = 
Aws::Crt::Crypto::SymmetricCipher::CreateAES_256_CBC_Cipher(keyCur);
+        ASSERT_TRUE(cbcCipher);
+        ASSERT_BIN_ARRAYS_EQUALS(keyCur.ptr, keyCur.len, 
cbcCipher.GetKey().ptr, cbcCipher.GetKey().len);
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE, 
cbcCipher.GetIV().len);
+    }
+
+    return AWS_OP_SUCCESS;
+}
+
+AWS_TEST_CASE(AES_256_CBC_Generated_Materials_ResourceSafety, 
s_TestAES_256_CBC_Generated_Materials_ResourceSafety)
+
+static int s_TestAES_256_CTR_Generated_Materials_ResourceSafety(struct 
aws_allocator *allocator, void *)
+{
+    {
+        Aws::Crt::ApiHandle apiHandle(allocator);
+        auto ctrCipher = 
Aws::Crt::Crypto::SymmetricCipher::CreateAES_256_CTR_Cipher();
+        ASSERT_TRUE(ctrCipher);
+
+        auto input = aws_byte_cursor_from_c_str("abc");
+
+        uint8_t output[Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE * 2] = {0};
+        auto outputBuf = Aws::Crt::ByteBufFromEmptyArray(output, 
sizeof(output));
+
+        ASSERT_TRUE(ctrCipher.Encrypt(input, outputBuf));
+        ASSERT_TRUE(ctrCipher.FinalizeEncryption(outputBuf));
+
+        ASSERT_FALSE(ctrCipher);
+
+        ASSERT_TRUE(ctrCipher.Reset());
+
+        auto decryptInput = Aws::Crt::ByteCursorFromByteBuf(outputBuf);
+        outputBuf.len = 0;
+
+        ASSERT_TRUE(ctrCipher.Decrypt(decryptInput, outputBuf));
+        ASSERT_TRUE(ctrCipher.FinalizeDecryption(outputBuf));
+
+        ASSERT_BIN_ARRAYS_EQUALS(input.ptr, input.len, outputBuf.buffer, 
outputBuf.len);
+
+        ASSERT_FALSE(ctrCipher);
+
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_KEY_SIZE_BYTES, 
ctrCipher.GetKey().len);
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE, 
ctrCipher.GetIV().len);
+
+        ASSERT_FALSE(ctrCipher);
+
+        // check IV generates if a key is provided but iv is not
+        uint8_t key[Aws::Crt::Crypto::AES_256_KEY_SIZE_BYTES] = {0xDD};
+        auto keyCur = Aws::Crt::ByteCursorFromArray(key, sizeof(key));
+        ctrCipher = 
Aws::Crt::Crypto::SymmetricCipher::CreateAES_256_CTR_Cipher(keyCur);
+        ASSERT_TRUE(ctrCipher);
+        ASSERT_BIN_ARRAYS_EQUALS(keyCur.ptr, keyCur.len, 
ctrCipher.GetKey().ptr, ctrCipher.GetKey().len);
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE, 
ctrCipher.GetIV().len);
+    }
+
+    return AWS_OP_SUCCESS;
+}
+
+AWS_TEST_CASE(AES_256_CTR_Generated_Materials_ResourceSafety, 
s_TestAES_256_CTR_Generated_Materials_ResourceSafety)
+
+static int s_TestAES_256_GCM_Generated_Materials_ResourceSafety(struct 
aws_allocator *allocator, void *)
+{
+    {
+        Aws::Crt::ApiHandle apiHandle(allocator);
+        auto gcmCipher = 
Aws::Crt::Crypto::SymmetricCipher::CreateAES_256_GCM_Cipher();
+        ASSERT_TRUE(gcmCipher);
+
+        auto input = aws_byte_cursor_from_c_str("abc");
+
+        uint8_t output[Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE * 2] = {0};
+        auto outputBuf = Aws::Crt::ByteBufFromEmptyArray(output, 
sizeof(output));
+
+        ASSERT_TRUE(gcmCipher.Encrypt(input, outputBuf));
+        ASSERT_TRUE(gcmCipher.FinalizeEncryption(outputBuf));
+
+        ASSERT_FALSE(gcmCipher);
+
+        ASSERT_TRUE(gcmCipher.Reset());
+
+        auto decryptInput = Aws::Crt::ByteCursorFromByteBuf(outputBuf);
+        outputBuf.len = 0;
+
+        ASSERT_TRUE(gcmCipher.Decrypt(decryptInput, outputBuf));
+        ASSERT_TRUE(gcmCipher.FinalizeDecryption(outputBuf));
+
+        ASSERT_BIN_ARRAYS_EQUALS(input.ptr, input.len, outputBuf.buffer, 
outputBuf.len);
+
+        ASSERT_FALSE(gcmCipher);
+
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_KEY_SIZE_BYTES, 
gcmCipher.GetKey().len);
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE - 4, 
gcmCipher.GetIV().len);
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE, 
gcmCipher.GetTag().len);
+
+        ASSERT_FALSE(gcmCipher);
+
+        // check IV generates if a key is provided but iv is not
+        uint8_t key[Aws::Crt::Crypto::AES_256_KEY_SIZE_BYTES] = {0xDD};
+        auto keyCur = Aws::Crt::ByteCursorFromArray(key, sizeof(key));
+        gcmCipher = 
Aws::Crt::Crypto::SymmetricCipher::CreateAES_256_GCM_Cipher(keyCur);
+        ASSERT_TRUE(gcmCipher);
+        ASSERT_BIN_ARRAYS_EQUALS(keyCur.ptr, keyCur.len, 
gcmCipher.GetKey().ptr, gcmCipher.GetKey().len);
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE - 4, 
gcmCipher.GetIV().len);
+    }
+
+    return AWS_OP_SUCCESS;
+}
+
+AWS_TEST_CASE(AES_256_GCM_Generated_Materials_ResourceSafety, 
s_TestAES_256_GCM_Generated_Materials_ResourceSafety)
+
+static int s_TestAES_256_Keywrap_Generated_Materials_ResourceSafety(struct 
aws_allocator *allocator, void *)
+{
+    {
+        Aws::Crt::ApiHandle apiHandle(allocator);
+        auto keywrapCipher = 
Aws::Crt::Crypto::SymmetricCipher::CreateAES_256_KeyWrap_Cipher();
+        ASSERT_TRUE(keywrapCipher);
+
+        auto input = 
aws_byte_cursor_from_c_str("abcdefghijklmnopqrstuvwxyz123456");
+
+        uint8_t output[Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE * 3] = {0};
+        auto outputBuf = Aws::Crt::ByteBufFromEmptyArray(output, 
sizeof(output));
+
+        ASSERT_TRUE(keywrapCipher.Encrypt(input, outputBuf));
+        ASSERT_TRUE(keywrapCipher.FinalizeEncryption(outputBuf));
+
+        ASSERT_FALSE(keywrapCipher);
+
+        ASSERT_TRUE(keywrapCipher.Reset());
+
+        uint8_t decryptOutput[Aws::Crt::Crypto::AES_256_CIPHER_BLOCK_SIZE * 3] 
= {0};
+        auto decryptOutputBuf = Aws::Crt::ByteBufFromEmptyArray(decryptOutput, 
sizeof(decryptOutput));
+
+        auto decryptInput = Aws::Crt::ByteCursorFromByteBuf(outputBuf);
+
+        ASSERT_TRUE(keywrapCipher.Decrypt(decryptInput, decryptOutputBuf));
+        ASSERT_TRUE(keywrapCipher.FinalizeDecryption(decryptOutputBuf));
+
+        ASSERT_BIN_ARRAYS_EQUALS(input.ptr, input.len, 
decryptOutputBuf.buffer, decryptOutputBuf.len);
+
+        ASSERT_FALSE(keywrapCipher);
+
+        ASSERT_UINT_EQUALS(Aws::Crt::Crypto::AES_256_KEY_SIZE_BYTES, 
keywrapCipher.GetKey().len);
+        ASSERT_UINT_EQUALS(0u, keywrapCipher.GetIV().len);
+
+        ASSERT_FALSE(keywrapCipher);
+    }
+
+    return AWS_OP_SUCCESS;
+}
+
+AWS_TEST_CASE(
+    AES_256_Keywrap_Generated_Materials_ResourceSafety,
+    s_TestAES_256_Keywrap_Generated_Materials_ResourceSafety)

Reply via email to