Giter VIP home page Giter VIP logo

symcrypt's Introduction

Introduction

SymCrypt is the core cryptographic function library currently used by Windows.

History

The library was started in late 2006 with the first sources committed in Feb 2007. Initially the goal was limited to implement symmetric cryptographic operations, hence the name. Starting with Windows 8, it has been the primary crypto library for symmetric algorithms.

In 2015 we started the work of adding asymmetric algorithms to SymCrypt. Since the 1703 release of Windows 10, SymCrypt has been the primary crypto library for all algorithms in Windows.

Goals

Like any engineering project, SymCrypt is a compromise between conflicting requirements:

  • Provide safe implementations of the cryptographic algorithms needed by Microsoft products.
  • Run on all CPU architectures supported by Windows.
  • Good performance.
  • Minimize maintenance cost.
  • Support FIPS 140-2 certification of products using SymCrypt.
  • Provide high assurance in the proper functionality of the library.

Cloning the Repo

In some of our Linux modules, SymCrypt uses Jitterentropy as a source of FIPS-certifiable entropy. To build these modules, you will need to ensure that the jitterentropy-library submodule is also cloned. You can do this by running git submodule update --init -- 3rdparty/jitterentropy-library after cloning.

The unittest/SymCryptDependencies submodule provides the RSA32 and msbignum implementations which are used as benchmarks in the unit tests when compiled on Windows. Due to licensing restrictions, we cannot release these libraries publicly, so this submodule will only be cloneable by Microsoft employees with access to our private Azure DevOps repository. If you are external to Microsoft, you can ignore this submodule. It is only used in the unit tests and does not change the behavior of the SymCrypt product code.

Building

The easiest way to get started building SymCrypt is to use the Python build script, scripts/build.py. You can run it with the --help argument to get help about which arguments are required and what each one does. For detailed build instructions, including alternative ways to build, see BUILD.md.

Testing

The SymCrypt unit test runs extensive functional tests on the SymCrypt library. On Windows it also compares results against on other implementations such as the Windows APIs CNG and CAPI, and the older crypto libraries rsa32 and msbignum, if they are available. It also provides detailed performance information.

After a successful build, you can use the scripts/test.py helper script to run the unit tests.

Versioning and Servicing

As of version 101.0.0, SymCrypt uses the version scheme defined by the Semantic Versioning 2.0.0 specification. This means:

  • Major version changes introduce ABI and/or API breaking changes (including behavior changes)
  • Minor version changes introduce backwards compatible additional functionality or improvements, and/or bug fixes
  • Patch version changes introduce backwards compatible bug fixes

The initial open source release started at version 100 for compatibility with our previous internal versioning scheme.

Regarding servicing, our strong recommendation is that distro vendors and application developers regularly update to the latest version of SymCrypt and SymCrypt engine for both security fixes and functionality/performance improvements. We take care to maintain a stable API and ABI for SymCrypt and have a suite of strong regression tests, and staying on the current version prevents the need for complex and potential riskier backports.

We will support long-term servicing of specific releases for security fixes. Details of this plan will be released publicly in the future.

Security Bugs

If you believe you have found a problem that affects the security of this code, please do NOT create an issue or pull request, but instead email your comments to [email protected]. See SECURITY.md for more info.

Contribute

We love to receive comments and suggestions. Unfortunately we cannot accept external code contributions except in specific circumstances from vetted partners with whom we have a pre-arranged agreement. Cryptographic code is considered highly sensitive by many of our large customers. We have some very big customers who put great value in the assurance of the crypto code used in their organization. By restricting the coding to a handful of employees we can greatly reduce the (perceived) risk of malicious contributions.

This project has adopted the Microsoft Open Source Code of Conduct. For more information see the Code of Conduct FAQ or contact [email protected] with any additional questions or comments.

symcrypt's People

Contributors

aaronsgiles avatar ccalik avatar mamckee avatar mcfi avatar mlindgren avatar msjuburke avatar nielsferguson avatar reynoldsbd avatar samuel-lee-msft avatar yourmsftacct avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

symcrypt's Issues

FIPS CMVP #

If you believe you have an issue that affects the security of applications that use SymCrypt,
please do NOT create a GitHub issue, but instead email your issue details to [email protected].
Your report may be eligible for a bug bounty, but ONLY if it is reported through email.

What is the FIPS CMVP Certificate # for this library?

Build break in GCC 8

Build error:

/__w/1/SymCrypt/lib/rdseed.c: In function 'SymCryptRdseedSizet':
/__w/1/SymCrypt/lib/rdseed.c:22:28: warning: implicit declaration of function '_rdseed64_step'; did you mean '_rdseedxx_step'? [-Wimplicit-function-declaration]
 #define _rdseedxx_step(_p) _rdseed64_step( (UINT64  *) (_p) )
                            ^~~~~~~~~~~~~~
/__w/1/SymCrypt/lib/rdseed.c:40:7: note: in expansion of macro '_rdseedxx_step'
   if( _rdseedxx_step( p ) != 0 )
       ^~~~~~~~~~~~~~


[ 98%] Built target symcryptunittest_lib
Scanning dependencies of target symcryptunittest
[ 99%] Building CXX object unittest/exe_linux/CMakeFiles/symcryptunittest.dir/main_exe.cpp.o
[ 99%] Linking CXX executable ../../exe/AMD64/LinuxUserMode/symcryptunittest
/usr/bin/ld: ../../lib/AMD64/LinuxUserMode/libsymcrypt_common.a(rdseed.c.o): in function `SymCryptRdseedSizet':
/__w/1/SymCrypt/lib/rdseed.c:40: undefined reference to `_rdseed64_step'
collect2: error: ld returned 1 exit status
make[2]: *** [unittest/exe_linux/CMakeFiles/symcryptunittest.dir/build.make:86: exe/AMD64/LinuxUserMode/symcryptunittest] Error 1
make[1]: *** [CMakeFiles/Makefile2:433: unittest/exe_linux/CMakeFiles/symcryptunittest.dir/all] Error 2
make: *** [Makefile:84: all] Error 2
##[error]Bash exited with code '2'.

See detail: https://dev.azure.com/mssonic/build/_build/results?buildId=22857&view=logs&j=12f1170f-54f2-53f3-20dd-22fc7dff55f9&t=59a85588-b0ba-5043-24c4-d9e29d89c6f6

To reproduce it, only need to build it in debian:buster docker image.

Analysis:

#include <immintrin.h>

/usr/lib/gcc/x86_64-linux-gnu/8/include/rdseedintrin.h:# error "Never use <rdseedintrin.h> directly; include <x86intrin.h> instead."

/usr/lib/gcc/x86_64-linux-gnu/9/include/rdseedintrin.h:# error "Never use <rdseedintrin.h> directly; include <immintrin.h> instead."

For GCC <=8, need to change to include <x86intrin.h>
See gcc-mirror/gcc@59a9514

Workaround:

cmake .. -DCMAKE_TOOLCHAIN_FILE=../cmake-toolchain/LinuxUserMode-AMD64.cmake -DCMAKE_C_FLAGS="-D_rdseed64_step=__builtin_ia32_rdseed_di_step"

Support request:

GCC 8 is used by debian:buster, which is the latest version of debian currently. Could you please help support it?

Reporting a security issue

I noticed a side channel and mailed a report to [email protected] but never received a response. I had assumed I would get at least an autoreply that my message had been received. Is there some better way to report security issues in this code?

LLVM Clang error: definition of builtin function '__cpuid'

Building on Ubuntu 22.10 with LLVM Clang 15 the following error occurs when attempting to compile linux/intrinsics.c:

SymCrypt/lib/linux/intrinsics.c:8:6: error: definition of builtin function '__cpuid'

Please consider adding a simple __has_builtin guard to linux/intrinsics.c in order to avoid redefining the cpuid intrinsics for compilers that support the cpuid intrinsics as builtins. Below is a patch:

diff --git lib/linux/intrinsics.c lib/linux/intrinsics.c
index 8670254..0935176 100644
--- lib/linux/intrinsics.c
+++ lib/linux/intrinsics.c
@@ -5,6 +5,12 @@
 // Copyright (c) Microsoft Corporation. Licensed under the MIT license.
 //

+#if !defined(__has_builtin)     // Optional of course.
+#define __has_builtin(x) 0      // Compatibility with non-clang compilers.
+#endif
+
+#if !__has_builtin(__cpuid)
+
 void __cpuid(int CPUInfo[4], int InfoType)
 {
     asm volatile ("cpuid"
@@ -12,9 +18,15 @@ void __cpuid(int CPUInfo[4], int InfoType)
         : "a" (InfoType));
 }

+#endif // !__has_builtin(__cpuid)
+
+#if !__has_builtin(__cpuidex)
+
 void __cpuidex(int CPUInfo[4], int InfoType, int ECXValue)
 {
     asm volatile ("cpuid"
         : "=a" (CPUInfo[0]), "=b" (CPUInfo[1]), "=c" (CPUInfo[2]), "=d" (CPUInfo[3])
         : "a" (InfoType), "c" (ECXValue));
 }
+
+#endif // !__has_builtin(__cpuidex)
\ No newline at end of file

Building on Fedora linux

Default build options need some changes when packaging for Fedora Linux.
For a release build, following test fails:

Starting performance measurements...
Perf min measurement clock time = 30000
Sanity check measurements:
512.0 cycles fixedTimeLoop, 6.0 cycles null, 39.0 cycles (for 32), 71.0 cycles (for 64), 135.0 cycles (for 128), 263.0 cycles (for 256), 519.0 cycles (for 512), 1030.9 cycles (for 1024), 2054.7 cycles (for 2048), 4103.1 cycles (for 4096), 8198.2 cycles (for 8192), 16391.6 cycles (for 16384)
*

***** FATAL ERROR /builddir/build/BUILD/SymCrypt-103.1.0/unittest/lib/perf.cpp(670): Measurement too fast
error: Bad exit status from /var/tmp/rpm-tmp.KJeasA (%check)

Build log

FIPS verification also seems to fail with a debug build:

Traceback (most recent call last):
  File "/builddir/build/BUILD/SymCrypt-103.1.0/scripts/process_fips_module.py", line 402, in <module>
    main()
  File "/builddir/build/BUILD/SymCrypt-103.1.0/scripts/process_fips_module.py", line 365, in main
    assert(fips_boundary_variable.value == PLACEHOLDER_VALUE)
           ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
AssertionError
make[2]: *** [modules_linux/generic/CMakeFiles/symcrypt_generic_linux.dir/build.make:149: module/generic/libsymcrypt.so.103.1.0] Error 1
make[2]: *** Deleting file 'module/generic/libsymcrypt.so.103.1.0'
make[1]: *** [CMakeFiles/Makefile2:328: modules_linux/generic/CMakeFiles/symcrypt_generic_linux.dir/all] Error 2
make: *** [Makefile:91: all] Error 2
error: Bad exit status from /var/tmp/rpm-tmp.2aryKX (%build)

Build log

Can investigate further if of interest to see how SymCrypt can be adapted to other platforms.

LLVM Clang error: function with no prototype cannot use the fastcall calling convention

Building on Windows with LLVM Clang 15 the following error occurs when targeting the i386 architecture:

SymCrypt\inc\symcrypt.h:493:1: error: function with no prototype cannot use the fastcall calling convention

Clang considers a function with no arguments unprototyped if the function is declared without a void type. See: llvm/llvm-project#28263

Please consider declaring functions without arguments with the void type in the prototype. Below is a patch:

diff --git inc/symcrypt.h inc/symcrypt.h
index 8ae5fb3..a4570ea 100644
--- inc/symcrypt.h
+++ inc/symcrypt.h
@@ -490,7 +490,7 @@ SymCryptUint64Bytesize( UINT64 value );

 VOID
 SYMCRYPT_CALL
-SymCryptInit();
+SymCryptInit( void );
 //
 // Initialize the static library.
 // This function MUST be called before any other function in the library.
@@ -893,7 +893,7 @@ SymCryptMd2StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptMd2Selftest();
+SymCryptMd2Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptMd2Algorithm;

@@ -956,7 +956,7 @@ SymCryptMd4StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptMd4Selftest();
+SymCryptMd4Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptMd4Algorithm;

@@ -1019,7 +1019,7 @@ SymCryptMd5StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptMd5Selftest();
+SymCryptMd5Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptMd5Algorithm;

@@ -1157,7 +1157,7 @@ SymCryptSha256StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptSha256Selftest();
+SymCryptSha256Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptSha256Algorithm;

@@ -1222,7 +1222,7 @@ SymCryptSha384StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptSha384Selftest();
+SymCryptSha384Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptSha384Algorithm;

@@ -1287,7 +1287,7 @@ SymCryptSha512StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptSha512Selftest();
+SymCryptSha512Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptSha512Algorithm;

@@ -1356,7 +1356,7 @@ SymCryptSha3_256StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptSha3_256Selftest();
+SymCryptSha3_256Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptSha3_256Algorithm;

@@ -1410,7 +1410,7 @@ SymCryptSha3_384StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptSha3_384Selftest();
+SymCryptSha3_384Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptSha3_384Algorithm;

@@ -1464,7 +1464,7 @@ SymCryptSha3_512StateImport(

 VOID
 SYMCRYPT_CALL
-SymCryptSha3_512Selftest();
+SymCryptSha3_512Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptSha3_512Algorithm;

@@ -1654,7 +1654,7 @@ SymCryptShake128StateCopy(_In_ PCSYMCRYPT_SHAKE128_STATE pSrc, _Out_ PSYMCRYPT_S

 VOID
 SYMCRYPT_CALL
-SymCryptShake128Selftest();
+SymCryptShake128Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptShake128HashAlgorithm;

@@ -1711,7 +1711,7 @@ SymCryptShake256StateCopy(_In_ PCSYMCRYPT_SHAKE256_STATE pSrc, _Out_ PSYMCRYPT_S

 VOID
 SYMCRYPT_CALL
-SymCryptShake256Selftest();
+SymCryptShake256Selftest( void );

 extern const PCSYMCRYPT_HASH SymCryptShake256HashAlgorithm;

@@ -1835,7 +1835,7 @@ SymCryptCShake128StateCopy(_In_ PCSYMCRYPT_CSHAKE128_STATE pSrc, _Out_ PSYMCRYPT

 VOID
 SYMCRYPT_CALL
-SymCryptCShake128Selftest();
+SymCryptCShake128Selftest( void );


 //
@@ -1892,7 +1892,7 @@ SymCryptCShake256StateCopy(_In_ PCSYMCRYPT_CSHAKE256_STATE pSrc, _Out_ PSYMCRYPT

 VOID
 SYMCRYPT_CALL
-SymCryptCShake256Selftest();
+SymCryptCShake256Selftest( void );



@@ -2064,15 +2064,15 @@ SymCryptParallelSha512Process(

 VOID
 SYMCRYPT_CALL
-SymCryptParallelSha256Selftest();
+SymCryptParallelSha256Selftest( void );

 VOID
 SYMCRYPT_CALL
-SymCryptParallelSha384Selftest();
+SymCryptParallelSha384Selftest( void );

 VOID
 SYMCRYPT_CALL
-SymCryptParallelSha512Selftest();
+SymCryptParallelSha512Selftest( void );



@@ -2326,7 +2326,7 @@ SymCryptHmacMd5Result(

 VOID
 SYMCRYPT_CALL
-SymCryptHmacMd5Selftest();
+SymCryptHmacMd5Selftest( void );

 extern const PCSYMCRYPT_MAC SymCryptHmacMd5Algorithm;

@@ -2391,7 +2391,7 @@ SymCryptHmacSha1Result(

 VOID
 SYMCRYPT_CALL
-SymCryptHmacSha1Selftest();
+SymCryptHmacSha1Selftest( void );

 extern const PCSYMCRYPT_MAC SymCryptHmacSha1Algorithm;

@@ -2455,7 +2455,7 @@ SymCryptHmacSha256Result(

 VOID
 SYMCRYPT_CALL
-SymCryptHmacSha256Selftest();
+SymCryptHmacSha256Selftest( void );

 extern const PCSYMCRYPT_MAC  SymCryptHmacSha256Algorithm;

@@ -2519,7 +2519,7 @@ SymCryptHmacSha384Result(

 VOID
 SYMCRYPT_CALL
-SymCryptHmacSha384Selftest();
+SymCryptHmacSha384Selftest( void );

 extern const PCSYMCRYPT_MAC  SymCryptHmacSha384Algorithm;

@@ -2583,7 +2583,7 @@ SymCryptHmacSha512Result(

 VOID
 SYMCRYPT_CALL
-SymCryptHmacSha512Selftest();
+SymCryptHmacSha512Selftest( void );

 extern const PCSYMCRYPT_MAC  SymCryptHmacSha512Algorithm;

@@ -2649,7 +2649,7 @@ SymCryptAesCmacResult(

 VOID
 SYMCRYPT_CALL
-SymCryptAesCmacSelftest();
+SymCryptAesCmacSelftest( void );

 extern const PCSYMCRYPT_MAC SymCryptAesCmacAlgorithm;

@@ -2908,7 +2908,7 @@ SymCryptKmac128StateCopy(_In_ const SYMCRYPT_KMAC128_STATE* pSrc, _Out_ SYMCRYPT

 VOID
 SYMCRYPT_CALL
-SymCryptKmac128Selftest();
+SymCryptKmac128Selftest( void );

 extern const PCSYMCRYPT_MAC SymCryptKmac128Algorithm;

@@ -2995,7 +2995,7 @@ SymCryptKmac256StateCopy(_In_ const SYMCRYPT_KMAC256_STATE* pSrc, _Out_ SYMCRYPT

 VOID
 SYMCRYPT_CALL
-SymCryptKmac256Selftest();
+SymCryptKmac256Selftest( void );

 extern const PCSYMCRYPT_MAC SymCryptKmac256Algorithm;

@@ -3047,7 +3047,7 @@ SymCryptPoly1305Result(

 VOID
 SYMCRYPT_CALL
-SymCryptPoly1305Selftest();
+SymCryptPoly1305Selftest( void );

 //
 // We do NOT define a SYMCRYPT_MAC structure SymCryptPoly1305Algorithm
@@ -3103,7 +3103,7 @@ SymCryptChaCha20Poly1305Decrypt(

 VOID
 SYMCRYPT_CALL
-SymCryptChaCha20Poly1305Selftest();
+SymCryptChaCha20Poly1305Selftest( void );

 ////////////////////////////////////////////////////////////////////////////
 //   MARVIN32
@@ -3205,7 +3205,7 @@ SymCryptMarvin32Result(

 VOID
 SYMCRYPT_CALL
-SymCryptMarvin32Selftest();
+SymCryptMarvin32Selftest( void );


 //==========================================================================
@@ -3571,7 +3571,7 @@ SymCryptDesSetOddParity(

 VOID
 SYMCRYPT_CALL
-SymCryptDesSelftest();
+SymCryptDesSelftest( void );

 extern const PCSYMCRYPT_BLOCKCIPHER SymCryptDesBlockCipher;

@@ -3634,7 +3634,7 @@ SymCrypt3DesCbcDecrypt(

 VOID
 SYMCRYPT_CALL
-SymCrypt3DesSelftest();
+SymCrypt3DesSelftest( void );

 extern const PCSYMCRYPT_BLOCKCIPHER SymCrypt3DesBlockCipher;

@@ -3672,7 +3672,7 @@ SymCryptDesxDecrypt(

 VOID
 SYMCRYPT_CALL
-SymCryptDesxSelftest();
+SymCryptDesxSelftest( void );

 extern const PCSYMCRYPT_BLOCKCIPHER SymCryptDesxBlockCipher;

@@ -3743,7 +3743,7 @@ SymCryptRc2Decrypt(

 VOID
 SYMCRYPT_CALL
-SymCryptRc2Selftest();
+SymCryptRc2Selftest( void );

 extern const PCSYMCRYPT_BLOCKCIPHER SymCryptRc2BlockCipher;

@@ -4201,7 +4201,7 @@ SymCryptCcmDecryptFinal(

 VOID
 SYMCRYPT_CALL
-SymCryptCcmSelftest();
+SymCryptCcmSelftest( void );
 //
 // Self test for CCM cipher mode
 //
@@ -4395,7 +4395,7 @@ SymCryptGcmDecryptFinal(

 VOID
 SYMCRYPT_CALL
-SymCryptGcmSelftest();
+SymCryptGcmSelftest( void );
 //
 // Self test for GCM cipher mode
 //
@@ -4591,7 +4591,7 @@ SymCryptRc4Crypt(

 VOID
 SYMCRYPT_CALL
-SymCryptRc4Selftest();
+SymCryptRc4Selftest( void );


 //
@@ -4667,7 +4667,7 @@ SymCryptChaCha20Crypt(

 VOID
 SYMCRYPT_CALL
-SymCryptChaCha20Selftest();
+SymCryptChaCha20Selftest( void );



@@ -4726,11 +4726,11 @@ SymCryptPbkdf2(

 VOID
 SYMCRYPT_CALL
-SymCryptPbkdf2_HmacSha1SelfTest();
+SymCryptPbkdf2_HmacSha1SelfTest( void );

 VOID
 SYMCRYPT_CALL
-SymCryptPbkdf2_HmacSha256SelfTest();
+SymCryptPbkdf2_HmacSha256SelfTest( void );

 ////////////////////////////////////////////////////////////////////////////
 // SP800-108 Counter mode
@@ -4777,19 +4777,19 @@ SymCryptSp800_108(

 VOID
 SYMCRYPT_CALL
-SymCryptSp800_108_HmacSha1SelfTest();
+SymCryptSp800_108_HmacSha1SelfTest( void );

 VOID
 SYMCRYPT_CALL
-SymCryptSp800_108_HmacSha256SelfTest();
+SymCryptSp800_108_HmacSha256SelfTest( void );

 VOID
 SYMCRYPT_CALL
-SymCryptSp800_108_HmacSha384SelfTest();
+SymCryptSp800_108_HmacSha384SelfTest( void );

 VOID
 SYMCRYPT_CALL
-SymCryptSp800_108_HmacSha512SelfTest();
+SymCryptSp800_108_HmacSha512SelfTest( void );

 ////////////////////////////////////////////////////////////////////////////
 // TLS Key Derivation PRFs
@@ -4840,7 +4840,7 @@ SymCryptTlsPrf1_1(

 VOID
 SYMCRYPT_CALL
-SymCryptTlsPrf1_1SelfTest();
+SymCryptTlsPrf1_1SelfTest( void );

 //
 //  Version 1.2
@@ -4879,7 +4879,7 @@ SymCryptTlsPrf1_2(

 VOID
 SYMCRYPT_CALL
-SymCryptTlsPrf1_2SelfTest();
+SymCryptTlsPrf1_2SelfTest( void );


 ////////////////////////////////////////////////////////////////////////////
@@ -4980,11 +4980,11 @@ SymCryptSshKdf(

 VOID
 SYMCRYPT_CALL
-SymCryptSshKdfSha256SelfTest();
+SymCryptSshKdfSha256SelfTest( void );

 VOID
 SYMCRYPT_CALL
-SymCryptSshKdfSha512SelfTest();
+SymCryptSshKdfSha512SelfTest( void );


 ////////////////////////////////////////////////////////////////////////////
@@ -5089,7 +5089,7 @@ SymCryptSrtpKdf(

 VOID
 SYMCRYPT_CALL
-SymCryptSrtpKdfSelfTest();
+SymCryptSrtpKdfSelfTest( void );


 ////////////////////////////////////////////////////////////////////////////
@@ -5170,7 +5170,7 @@ SymCryptHkdf(

 VOID
 SYMCRYPT_CALL
-SymCryptHkdfSelfTest();
+SymCryptHkdfSelfTest( void );

 //==========================================================================
 //   RNG ALGORITHMS
@@ -5274,7 +5274,7 @@ SymCryptRngAesUninstantiate(

 VOID
 SYMCRYPT_CALL
-SymCryptRngAesInstantiateSelftest();
+SymCryptRngAesInstantiateSelftest( void );
 //
 // For FIPS-certified modules, this function should be called before every instantiation.
 // If multiple DRBGs are instantiated 'in quick succession', a single self-test is sufficient
@@ -5284,14 +5284,14 @@ SymCryptRngAesInstantiateSelftest();

 VOID
 SYMCRYPT_CALL
-SymCryptRngAesReseedSelftest();
+SymCryptRngAesReseedSelftest( void );
 //
 // FIPS-certified modules should call this function before every call to the reseed function.
 //

 VOID
 SYMCRYPT_CALL
-SymCryptRngAesGenerateSelftest();
+SymCryptRngAesGenerateSelftest( void );
 //
 // FIPS-certified modules should call this function at least once on startup, and whenever
 // they want to re-test the generate function.
@@ -5388,7 +5388,7 @@ SymCryptProvideEntropy(

 SYMCRYPT_ERROR
 SYMCRYPT_CALL
-SymCryptRdrandStatus();
+SymCryptRdrandStatus( void );
 //
 // Returns SYMCRYPT_NO_ERROR if RdRand is available.
 // returns SYMCRYPT_NOT_IMPLEMENTED if RdRand is not available.
@@ -5442,7 +5442,7 @@ SymCryptRdrandGet(

 SYMCRYPT_ERROR
 SYMCRYPT_CALL
-SymCryptRdseedStatus();
+SymCryptRdseedStatus( void );
 //
 // Returns SYMCRYPT_NO_ERROR if RdSeed is available.
 // returns SYMCRYPT_NOT_IMPLEMENTED if RdSeed is not available.
@@ -5514,7 +5514,7 @@ SymCryptXtsAesDecrypt(

 VOID
 SYMCRYPT_CALL
-SymCryptXtsAesSelftest();
+SymCryptXtsAesSelftest( void );


 ////////////////////////////////////////////////////////////////////////////////////////////
@@ -5695,7 +5695,7 @@ SymCryptCallbackRandom(

 PVOID
 SYMCRYPT_CALL
-SymCryptCallbackAllocateMutexFastInproc();
+SymCryptCallbackAllocateMutexFastInproc( void );
 //
 // Allocate and initialize a mutex object; returns NULL on failure.
 //
@@ -7514,7 +7514,7 @@ SymCryptRsaPssVerify(

 VOID
 SYMCRYPT_CALL
-SymCryptRsaSelftest( );
+SymCryptRsaSelftest( void );
 //
 // FIPS self-test for RSA sign/verify. This function uses a hardcoded key to perform the self-test
 // without having to generate a key. If the self-test fails, SymCryptFatal will be called to
@@ -7571,7 +7571,7 @@ SymCryptDsaVerify(

 VOID
 SYMCRYPT_CALL
-SymCryptDsaSelftest( );
+SymCryptDsaSelftest( void );
 //
 // FIPS self-test for DSA sign/verify. This function uses a hardcoded key to perform the self-test
 // without having to generate a key. If the self-test fails, SymCryptFatal will be called to
@@ -7605,7 +7605,7 @@ SymCryptDhSecretAgreement(

 VOID
 SYMCRYPT_CALL
-SymCryptDhSecretAgreementSelftest();
+SymCryptDhSecretAgreementSelftest( void );
 //
 // FIPS self-test for DH secret agreement. This function uses two hardcoded keys and a precalculated
 // known answer to perform the self-test without having to generate a key. If the self-test fails,
@@ -7669,7 +7669,7 @@ SymCryptEcDsaVerify(

 VOID
 SYMCRYPT_CALL
-SymCryptEcDsaSelftest( );
+SymCryptEcDsaSelftest( void );
 //
 // FIPS self-test for ECDSA sign/verify. This function uses a hardcoded key to perform the self-test
 // without having to generate a key. If the self-test fails, SymCryptFatal will be called to
@@ -7702,7 +7702,7 @@ SymCryptEcDhSecretAgreement(

 VOID
 SYMCRYPT_CALL
-SymCryptEcDhSecretAgreementSelftest( );
+SymCryptEcDhSecretAgreementSelftest( void );
 //
 // FIPS self-test for ECDH secret agreement. This function uses two hardcoded keys and a
 // precalculated known answer to perform the self-test without having to generate a key. If the
diff --git inc/symcrypt_internal.h inc/symcrypt_internal.h
index 36b91d7..5f3912f 100644
--- inc/symcrypt_internal.h
+++ inc/symcrypt_internal.h
@@ -420,7 +420,7 @@ extern SYMCRYPT_CPU_FEATURES g_SymCryptCpuFeaturesNotPresent;

 SYMCRYPT_CPU_FEATURES
 SYMCRYPT_CALL
-SymCryptCpuFeaturesNeverPresent();
+SymCryptCpuFeaturesNeverPresent(void);

 #define SYMCRYPT_CPU_FEATURES_PRESENT( x )   ( ((x) & SymCryptCpuFeaturesNeverPresent()) == 0 && ( (x) & g_SymCryptCpuFeaturesNotPresent ) == 0 )

@@ -2671,14 +2671,14 @@ typedef struct _SYMCRYPT_EXTENDED_SAVE_DATA      SYMCRYPT_EXTENDED_SAVE_DATA, *P
 #define SYMCRYPT_ENVIRONMENT_DEFS( envName ) \
 SYMCRYPT_EXTERN_C \
     VOID SYMCRYPT_CALL SymCryptInitEnv##envName( UINT32 version ); \
-    VOID SYMCRYPT_CALL SymCryptInit() \
+    VOID SYMCRYPT_CALL SymCryptInit( void ) \
         { SymCryptInitEnv##envName( SYMCRYPT_API_VERSION ); } \
     \
     _Analysis_noreturn_ VOID SYMCRYPT_CALL SymCryptFatalEnv##envName( UINT32 fatalCode ); \
     _Analysis_noreturn_ VOID SYMCRYPT_CALL SymCryptFatal( UINT32 fatalCode ) \
         { SymCryptFatalEnv##envName( fatalCode ); } \
-    SYMCRYPT_CPU_FEATURES SYMCRYPT_CALL SymCryptCpuFeaturesNeverPresentEnv##envName(); \
-    SYMCRYPT_CPU_FEATURES SYMCRYPT_CALL SymCryptCpuFeaturesNeverPresent() \
+    SYMCRYPT_CPU_FEATURES SYMCRYPT_CALL SymCryptCpuFeaturesNeverPresentEnv##envName( void ); \
+    SYMCRYPT_CPU_FEATURES SYMCRYPT_CALL SymCryptCpuFeaturesNeverPresent( void ) \
         { return SymCryptCpuFeaturesNeverPresentEnv##envName(); } \
     \
     SYMCRYPT_ENVIRONMENT_DEFS_SAVEXMM( envName ) \
@@ -2886,7 +2886,7 @@ extern UINT32 g_SymCryptFipsSelftestsPerformed;

 UINT32
 SYMCRYPT_CALL
-SymCryptFipsGetSelftestsPerformed();
+SymCryptFipsGetSelftestsPerformed(void);
 // Returns current value of g_SymCryptFipsSelftestsPerformed so callers may inspect which FIPS
 // algorithm selftests have run

diff --git lib/sc_lib.h lib/sc_lib.h
index aa8c34f..b86673f 100644
--- lib/sc_lib.h
+++ lib/sc_lib.h
@@ -236,12 +236,12 @@ SymCryptRestoreYmm( _Inout_ PSYMCRYPT_EXTENDED_SAVE_DATA pSaveData );

 VOID
 SYMCRYPT_CALL
-SymCryptLibraryWasNotInitialized();
+SymCryptLibraryWasNotInitialized( void );

 FORCEINLINE
 VOID
 SYMCRYPT_CALL
-SymCryptCheckLibraryInitialized()
+SymCryptCheckLibraryInitialized( void )
 {
     if( !(g_SymCryptFlags & SYMCRYPT_FLAG_LIB_INITIALIZED)  )
     {
@@ -252,7 +252,7 @@ SymCryptCheckLibraryInitialized()
 FORCEINLINE
 VOID
 SYMCRYPT_CALL
-SymCryptCheckLibraryInitialized()
+SymCryptCheckLibraryInitialized( void )
 {
 }
 #endif
@@ -988,15 +988,15 @@ SymCryptDetectCpuFeaturesByCpuid( UINT32 flags );

 VOID
 SYMCRYPT_CALL
-SymCryptDetectCpuFeaturesFromRegisters();
+SymCryptDetectCpuFeaturesFromRegisters( void );

 VOID
 SYMCRYPT_CALL
-SymCryptDetectCpuFeaturesFromRegistersNoTry();
+SymCryptDetectCpuFeaturesFromRegistersNoTry( void );

 VOID
 SYMCRYPT_CALL
-SymCryptDetectCpuFeaturesFromIsProcessorFeaturePresent();
+SymCryptDetectCpuFeaturesFromIsProcessorFeaturePresent( void );

 VOID
 SYMCRYPT_CALL

MSVC 2022 17.8 compiler bug causes SymCryptAesGcmEncryptStitchedYmm_2048 to crash on Alder Lake CPUs

Visual Studio 2022 17.8 causes SymCryptAesGcmEncryptStitchedYmm_2048 to crash if run on an Alder Lake CPU. This is because the compiler incorrectly assumes that VAES and VPCLMULQDQ imply AVX-512 support, which is wrong. It then generates AVX-512 code and this crashes on Alder Lake, whose CPUID has VAES and VPCLMULQDQ but not AVX-512.

Reporting here for reference in case you want to work around it.
https://developercommunity.visualstudio.com/t/Compiler-incorrectly-assumes-VAES-and-VP/10578785

UB sanitizer reports NULL pointer access via SymCryptEcurveAllocate

#include <symcrypt.h>
#include <stdlib.h>

void SymCryptFatal(UINT32 fatalCode) {
    (void)fatalCode;

    abort();
}
void SymCryptInjectError( PBYTE pbData, SIZE_T cbData ) {
    (void)pbData;
    (void)cbData;
}

PVOID SymCryptCallbackAlloc( SIZE_T nBytes ) {
    return malloc(nBytes);
}

VOID SymCryptCallbackFree( VOID * pMem ) {
    free(pMem);
}

SYMCRYPT_ERROR SymCryptCallbackRandom(PBYTE   pbBuffer, SIZE_T  cbBuffer ) {
    abort();
}

SYMCRYPT_CPU_FEATURES
SymCryptCpuFeaturesNeverPresent(void) {
    return 0;
}

int main(void)
{
    SYMCRYPT_ECURVE* curve = SymCryptEcurveAllocate(SymCryptEcurveParamsNumsP512t1, 0);
    return 0;
}

If compiled with UndefinedBehaviorSanitizer (clang with -fsanitize=undefined, on Linux 64 bit), execution of this program will print:

/mnt/2tb/sym-crash/SymCrypt/lib/fdef_mod.c:53:12: runtime error: member access within null pointer of type 'SYMCRYPT_MODULUS' (aka 'struct _SYMCRYPT_MODULUS')
SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior /mnt/2tb/sym-crash/SymCrypt/lib/fdef_mod.c:53:12 in 
/mnt/2tb/sym-crash/SymCrypt/lib/fdef_general.c:819:12: runtime error: member access within null pointer of type 'SYMCRYPT_DIVISOR' (aka 'struct _SYMCRYPT_DIVISOR')
SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior /mnt/2tb/sym-crash/SymCrypt/lib/fdef_general.c:819:12 in 
/mnt/2tb/sym-crash/SymCrypt/lib/fdef_general.c:195:12: runtime error: member access within null pointer of type 'SYMCRYPT_INT' (aka 'struct _SYMCRYPT_INT')
SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior /mnt/2tb/sym-crash/SymCrypt/lib/fdef_general.c:195:12 in 
/mnt/2tb/sym-crash/SymCrypt/lib/fdef_mod.c:66:27: runtime error: member access within null pointer of type 'SYMCRYPT_MODULUS' (aka 'struct _SYMCRYPT_MODULUS')
SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior /mnt/2tb/sym-crash/SymCrypt/lib/fdef_mod.c:66:27 in 
/mnt/2tb/sym-crash/SymCrypt/lib/fdef_general.c:850:55: runtime error: member access within null pointer of type 'SYMCRYPT_DIVISOR' (aka 'struct _SYMCRYPT_DIVISOR')
SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior /mnt/2tb/sym-crash/SymCrypt/lib/fdef_general.c:850:55 in 

Invalid ECDSA signature and public key for private key that is curve order

#include <symcrypt.h>
#include <symcrypt_low_level.h>
#include <stdint.h>
#include <stdlib.h>
#include <stdio.h>

#define CF_CHECK_EQ(expr, res) if ( (expr) != (res) ) { goto end; }
#define CF_CHECK_NE(expr, res) if ( (expr) == (res) ) { goto end; }

void SymCryptFatal(UINT32 fatalCode) {
    (void)fatalCode;

    abort();
}
PVOID SymCryptCallbackAlloc( SIZE_T nBytes ) {
    return malloc(nBytes);
}

VOID SymCryptCallbackFree( VOID * pMem ) {
    free(pMem);
}
SYMCRYPT_CPU_FEATURES
SymCryptCpuFeaturesNeverPresent(void) {
    return 0;
}
SYMCRYPT_ERROR SymCryptCallbackRandom(PBYTE out, SIZE_T size) {
    for (size_t i = 0; i < size; i++) {
        out[i] = rand();
    }
    return SYMCRYPT_NO_ERROR;
}

int main(void)
{
    SYMCRYPT_ECURVE* curve = NULL;
    SYMCRYPT_ECKEY* key = NULL;
    SYMCRYPT_INT* nonce = NULL;

    CF_CHECK_NE(curve = SymCryptEcurveAllocate(SymCryptEcurveParamsNumsP256t1, 0), NULL);
    CF_CHECK_NE(key = SymCryptEckeyAllocate(curve), NULL);
    CF_CHECK_NE(nonce = SymCryptIntAllocate(SymCryptEcurveDigitsofScalarMultiplier(curve)), NULL);
    {
        const uint8_t nonce_bytes[] = {0x0C, 0x0B, 0xF3, 0xED, 0xBA, 31, 78, 0xE3, 0x8E};
        CF_CHECK_EQ(SymCryptIntSetValue(nonce_bytes, sizeof(nonce_bytes), SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, nonce), SYMCRYPT_NO_ERROR);
    }

    {
        const uint8_t priv_bytes[] = {
            0x3F, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF,
            0xFF, 0xFF, 0xFF, 0xFF, 0xBE, 0x6A, 0xA5, 0x5A, 0xD0, 0xA6, 0xBC, 0x64,
            0xE5, 0xB8, 0x4E, 0x6F, 0x11, 0x22, 0xB4, 0xAD};
        CF_CHECK_EQ(SymCryptEckeySetValue(
                priv_bytes, sizeof(priv_bytes),
                NULL, 0,
                SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, SYMCRYPT_ECPOINT_FORMAT_XY,
                0, key), SYMCRYPT_NO_ERROR);
    }

    {
        const size_t sigHalfSize = SymCryptEcurveSizeofScalarMultiplier(curve);
        const size_t sigSize = sigHalfSize * 2;
        uint8_t sig_bytes[sigSize];

        CF_CHECK_EQ(SymCryptEcDsaSignEx(
                    key,
                    NULL,
                    0,
                    nonce,
                    SYMCRYPT_NUMBER_FORMAT_MSB_FIRST,
                    0,
                    sig_bytes,
                    sigSize), SYMCRYPT_NO_ERROR);

        const size_t pubSize = SymCryptEckeySizeofPublicKey(key, SYMCRYPT_ECPOINT_FORMAT_XY);

        const size_t pubHalfSize = pubSize / 2;
        uint8_t pub_bytes[pubSize];

        CF_CHECK_EQ(SymCryptEckeyGetValue(
                    key,
                    NULL, 0,
                    pub_bytes, pubSize,
                    SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, SYMCRYPT_ECPOINT_FORMAT_XY,
                    0), SYMCRYPT_NO_ERROR);

        printf("Pub X:\n");
        for (size_t i = 0; i < pubHalfSize; i++) {
            printf("%02X ", pub_bytes[i]);
        }
        printf("\n");

        printf("Pub Y:\n");
        for (size_t i = 0; i < pubHalfSize; i++) {
            printf("%02X ", pub_bytes[pubHalfSize+i]);
        }
        printf("\n");

        printf("Sig R:\n");
        for (size_t i = 0; i < sigHalfSize; i++) {
            printf("%02X ", sig_bytes[i]);
        }
        printf("\n");

        printf("Sig S:\n");
        for (size_t i = 0; i < sigHalfSize; i++) {
            printf("%02X ", sig_bytes[sigHalfSize+i]);
        }
        printf("\n");
    }

end:
    if ( key ) {
        /* noret */ SymCryptEckeyFree(key);
    }
    if ( curve ) {
        /* noret */ SymCryptEcurveFree(curve);
    }
    if ( nonce ) {
        /* noret */ SymCryptIntFree(nonce);
    }

    return 0;
}

Pub X is 1, Pub Y is 0, Sig S is 0.

Found by Cryptofuzz running on OSS-Fuzz.

Bad security advice regarding RC4 in symcrypt.h

The following line regarding RC4: https://github.com/microsoft/SymCrypt/blob/main/inc/symcrypt.h#L4836

// Typically this is done by concatenating the key and a nonce or IV to generate the RC4 key.

is bad security advice. You really don't want to do that with RC4; you want to use a KDF to combine a key with an IV if you really have to use RC4 for some reason.

Ref: https://www.cs.cornell.edu/people/egs/615/rc4_ksaproc.pdf section 6

Tasks

No tasks being tracked yet.

Providing substitue for _aligned_malloc and _aligned_free

Is there a reason why in the test module and the new user module that the allocation functions are not settable by the library user?

For example, it's possible a user may want to use the stack for providing memory in super high performance scenarios.

Sorry this is more of a discussion but I didn't see the discussion tab open.

Signed overshift all across the library

I reported this to [email protected] (per your explicit request to report potential security bugs there, I personally don't care), but they don't understand what I'm talking about.

The problem is that you don't perform the necessary casting:

#define SYMCRYPT_INTERNAL_LOAD_MSBFIRST32( p ) ( (UINT32)(((PBYTE)p)[0] << 24 | ((PBYTE)p)[1] << 16 | ((PBYTE)p)[2] << 8 | ((PBYTE)p)[3] ) )

/mnt/2tb/cf-symcrypt/SymCrypt/lib/3des.c:207:10: runtime error: left shift of 241 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/3des.c:208:10: runtime error: left shift of 253 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/3des.c:366:9: runtime error: left shift of 225 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/3des.c:367:9: runtime error: left shift of 236 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/3des.c:486:9: runtime error: left shift of 187 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/3des.c:487:9: runtime error: left shift of 232 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:206:64: runtime error: left shift of 204 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:212:65: runtime error: left shift of 150 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:218:65: runtime error: left shift of 160 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:224:65: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:327:51: runtime error: left shift of 247 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:333:52: runtime error: left shift of 167 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:339:52: runtime error: left shift of 144 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-c.c:345:52: runtime error: left shift of 185 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:122:17: runtime error: left shift of 216 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:122:57: runtime error: left shift of 212 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:153:17: runtime error: left shift of 129 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:153:57: runtime error: left shift of 207 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:173:13: runtime error: left shift of 226 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:173:53: runtime error: left shift of 156 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:93:17: runtime error: left shift of 251 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aes-key.c:93:57: runtime error: left shift of 201 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/aescmac.c:193:47: runtime error: null pointer passed as argument 2, which is declared to never be null
/mnt/2tb/cf-symcrypt/SymCrypt/lib/blockciphermodes.c:296:9: runtime error: left shift of 163 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/blockciphermodes.c:296:9: runtime error: left shift of 250 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:220:9: runtime error: left shift of 192 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:221:9: runtime error: left shift of 167 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:222:9: runtime error: left shift of 141 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:223:9: runtime error: left shift of 164 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:224:9: runtime error: left shift of 166 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:225:9: runtime error: left shift of 143 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:226:9: runtime error: left shift of 191 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:227:9: runtime error: left shift of 135 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:228:9: runtime error: left shift of 232 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:229:9: runtime error: left shift of 189 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:230:9: runtime error: left shift of 217 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:231:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:232:9: runtime error: left shift of 237 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:233:9: runtime error: left shift of 201 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:234:9: runtime error: left shift of 145 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/chacha20.c:235:9: runtime error: left shift of 249 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/gcm.c:246:14: runtime error: left shift of 220 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/ghash.c:47:10: runtime error: left shift of 147 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/ghash.c:47:10: runtime error: left shift of 210 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/ghash.c:48:10: runtime error: left shift of 140 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/ghash.c:48:10: runtime error: left shift of 236 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/ghash.c:96:17: runtime error: left shift of 133 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/hkdf.c:114:12: runtime error: null pointer passed as argument 1, which is declared to never be null
/mnt/2tb/cf-symcrypt/SymCrypt/lib/hmac_pattern.c:63:25: runtime error: null pointer passed as argument 2, which is declared to never be null
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:255:9: runtime error: left shift of 234 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:256:9: runtime error: left shift of 155 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:257:9: runtime error: left shift of 170 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:258:9: runtime error: left shift of 145 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:259:9: runtime error: left shift of 234 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:260:9: runtime error: left shift of 163 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:261:9: runtime error: left shift of 147 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:262:9: runtime error: left shift of 134 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:263:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:264:9: runtime error: left shift of 154 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:265:9: runtime error: left shift of 246 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:266:9: runtime error: left shift of 154 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:267:9: runtime error: left shift of 215 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:268:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:269:9: runtime error: left shift of 223 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md4.c:270:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:316:9: runtime error: left shift of 251 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:317:9: runtime error: left shift of 214 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:318:9: runtime error: left shift of 186 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:319:9: runtime error: left shift of 142 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:320:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:321:9: runtime error: left shift of 133 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:322:9: runtime error: left shift of 225 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:323:9: runtime error: left shift of 254 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:324:9: runtime error: left shift of 212 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:325:9: runtime error: left shift of 229 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:326:9: runtime error: left shift of 251 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:327:9: runtime error: left shift of 254 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:328:9: runtime error: left shift of 203 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:329:9: runtime error: left shift of 229 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:330:9: runtime error: left shift of 237 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/md5.c:331:9: runtime error: left shift of 186 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sc_lib.h:424:21: runtime error: left shift of 194 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:252:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:253:9: runtime error: left shift of 180 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:254:9: runtime error: left shift of 236 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:255:9: runtime error: left shift of 142 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:256:9: runtime error: left shift of 154 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:257:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:258:9: runtime error: left shift of 200 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:259:9: runtime error: left shift of 189 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:260:9: runtime error: left shift of 253 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:261:9: runtime error: left shift of 226 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:262:9: runtime error: left shift of 132 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:263:9: runtime error: left shift of 200 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:264:9: runtime error: left shift of 227 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:265:9: runtime error: left shift of 253 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:266:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha1.c:267:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:596:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:597:9: runtime error: left shift of 237 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:598:9: runtime error: left shift of 168 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:599:9: runtime error: left shift of 242 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:600:9: runtime error: left shift of 176 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:601:9: runtime error: left shift of 165 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:602:9: runtime error: left shift of 240 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:603:9: runtime error: left shift of 240 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:604:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:605:9: runtime error: left shift of 134 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:606:9: runtime error: left shift of 178 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:607:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:608:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:609:9: runtime error: left shift of 148 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:610:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha256.c:611:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:657:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:657:9: runtime error: left shift of 201 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:658:9: runtime error: left shift of 213 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:658:9: runtime error: left shift of 226 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:659:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:659:9: runtime error: left shift of 189 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:660:9: runtime error: left shift of 141 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:660:9: runtime error: left shift of 232 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:661:9: runtime error: left shift of 151 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:661:9: runtime error: left shift of 252 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:662:9: runtime error: left shift of 158 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:662:9: runtime error: left shift of 171 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:663:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:663:9: runtime error: left shift of 200 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:664:9: runtime error: left shift of 180 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:664:9: runtime error: left shift of 254 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:665:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:666:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:666:9: runtime error: left shift of 212 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:667:9: runtime error: left shift of 253 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:667:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:668:9: runtime error: left shift of 212 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:669:9: runtime error: left shift of 154 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:669:9: runtime error: left shift of 255 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:670:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:670:9: runtime error: left shift of 159 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:671:9: runtime error: left shift of 128 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:671:9: runtime error: left shift of 133 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:672:9: runtime error: left shift of 147 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/sha512.c:672:9: runtime error: left shift of 236 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/tlsprf.c:334:19: runtime error: null pointer passed as argument 2, which is declared to never be null
/mnt/2tb/cf-symcrypt/SymCrypt/lib/tlsprf.c:336:19: runtime error: null pointer passed as argument 2, which is declared to never be null
/mnt/2tb/cf-symcrypt/SymCrypt/lib/xtsaes.c:784:17: runtime error: left shift of 224 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/xtsaes.c:784:17: runtime error: left shift of 244 by 24 places cannot be represented in type 'int'
/mnt/2tb/cf-symcrypt/SymCrypt/lib/xtsaes.c:785:17: runtime error: left shift of 225 by 24 places cannot be represented in type 'int'

Publics cache

Hi,

After setting up a Windows 10 Razzle environment, and building this on a regular machine, I can see that the build reaches the "Do not know how to populate publics cache" error when building using this repository.

Is that usual?
image

Note that this didn't prevent symcrypt.lib from being built, althrough the tests cannot run in this case, because of missing rsa32 and bignum libraries, which are supposed to be located there.

Thanks,

Elliptic curve private-to-public incorrect result on Linux 32 bit

Reproducer:

#include <cstdint>
#include <iostream>
#include <sstream>
#include <string>
#include <vector>
#include <boost/multiprecision/cpp_int.hpp>
#include <symcrypt.h>

#define CF_CHECK_EQ(expr, res) if ( (expr) != (res) ) { goto end; }
#define CF_CHECK_NE(expr, res) if ( (expr) == (res) ) { goto end; }

extern "C" {
    void SymCryptFatal(UINT32 fatalCode) {
        (void)fatalCode;

        abort();
    }
    void SymCryptInjectError( PBYTE pbData, SIZE_T cbData ) {
        (void)pbData;
        (void)cbData;
    }

    PVOID SymCryptCallbackAlloc( SIZE_T nBytes ) {
        return malloc(nBytes);
    }

    VOID SymCryptCallbackFree( VOID * pMem ) {
        free(pMem);
    }

    SYMCRYPT_ERROR SymCryptCallbackRandom(PBYTE   pbBuffer, SIZE_T  cbBuffer ) {
        abort();
    }

    SYMCRYPT_CPU_FEATURES
    SymCryptCpuFeaturesNeverPresent(void) {
        return 0;
    }
}

namespace SymCrypt_detail {
    static bool EncodeBignum(const std::string s, uint8_t* out, const size_t outSize) {
        std::vector<uint8_t> v;
        boost::multiprecision::cpp_int c(s);
        boost::multiprecision::export_bits(c, std::back_inserter(v), 8);
        if ( v.size() > outSize ) {
            return false;
        }
        const auto diff = outSize - v.size();

        memset(out, 0, outSize);
        memcpy(out + diff, v.data(), v.size());

        return true;
    }

    static std::string toString(const boost::multiprecision::cpp_int& i) {
        std::stringstream ss;
        ss << i;

        if ( ss.str().empty() ) {
            return "0";
        } else {
            return ss.str();
        }
    }
}

int main(void)
{
    SYMCRYPT_ECURVE* curve = nullptr;
    SYMCRYPT_ECKEY* key = nullptr;
    const SYMCRYPT_ECURVE_PARAMS* curveParams = SymCryptEcurveParamsNistP384;

    CF_CHECK_NE(curve = SymCryptEcurveAllocate(curveParams, 0), nullptr);
    CF_CHECK_NE(key = SymCryptEckeyAllocate(curve), nullptr);

    {
        const auto priv_size = SymCryptEckeySizeofPrivateKey(key);
        std::vector<uint8_t> priv_bytes(priv_size);

        CF_CHECK_EQ(SymCrypt_detail::EncodeBignum(
                    "15",
                    priv_bytes.data(),
                    priv_size), true);

        CF_CHECK_EQ(SymCryptEckeySetValue(
                priv_bytes.data(), priv_size,
                NULL, 0,
                SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, SYMCRYPT_ECPOINT_FORMAT_XY,
                0, key), SYMCRYPT_NO_ERROR);
    }

    {
        const auto pub_size = SymCryptEckeySizeofPublicKey(key, SYMCRYPT_ECPOINT_FORMAT_XY);
        if ( (pub_size % 2) != 0 ) {
            abort();
        }
        std::vector<uint8_t> pub_bytes(pub_size);

        CF_CHECK_EQ(SymCryptEckeyGetValue(
                    key,
                    NULL, 0,
                    pub_bytes.data(), pub_size,
                    SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, SYMCRYPT_ECPOINT_FORMAT_XY,
                    0), SYMCRYPT_NO_ERROR);

        {
            boost::multiprecision::cpp_int x, y;

            boost::multiprecision::import_bits(x, pub_bytes.begin(), pub_bytes.begin() + (pub_size/2));
            boost::multiprecision::import_bits(y, pub_bytes.begin() + (pub_size/2), pub_bytes.end());

            std::cout << SymCrypt_detail::toString(x) << std::endl;
            std::cout << SymCrypt_detail::toString(y) << std::endl;
        }
    }

end:
    if ( key ) {
        /* noret */ SymCryptEckeyFree(key);
    }
    if ( curve ) {
        /* noret */ SymCryptEcurveFree(curve);
    }

    return 0;
}

First, compile SymCrypt like this:

export CC=clang
export CXX=clang++
export CFLAGS="-m32"
export CXXFLAGS="-m32"

git clone --depth 1 https://github.com/microsoft/SymCrypt.git
cd SymCrypt/
# Unittests don't build with clang and are not needed anyway
sed -i "s/^add_subdirectory(unittest)$//g" CMakeLists.txt
mkdir b/
cd b/
setarch i386 cmake ../
make -j$(nproc)

Then compile and run the reproducer:

$ $CXX $CXXFLAGS -DSYMCRYPT_IGNORE_PLATFORM -I SymCrypt/inc/ p.cpp SymCrypt/b/lib/i686/Generic/libsymcrypt_common.a
$ ./a.out
3371410058567038036102658371067750911905410377350295952202630426945666718973957844373613366326295398452393
6490343607037185220769843464241451023660093550735871349269711288852702861970840804993910898129495774144414

But it should print:

27676427741886189792545170648212433086611990497738896912065553637549098719435212229527415490501936487430563654174219
3256906964515830166357393887851908050144111374947447699655351073133031632026642053647058697111201931251927081270626

OSS-Fuzz #33189: ECDSA signing produces invalid signature

https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=33189

Curve: secp384r1
Nonce = 1
Msg = Curve base point X
Private key = Curve order - 1

#include <stdlib.h>
#include <symcrypt.h>
#include <symcrypt_low_level.h>
#include <stdint.h>
#include <stdio.h>

#define CF_CHECK_EQ(expr, res) if ( (expr) != (res) ) { goto end; }
#define CF_CHECK_NE(expr, res) if ( (expr) == (res) ) { goto end; }

void SymCryptFatal(UINT32 fatalCode) {
    (void)fatalCode;

    abort();
}
PVOID SymCryptCallbackAlloc( SIZE_T nBytes ) {
    return malloc(nBytes);
}

VOID SymCryptCallbackFree( VOID * pMem ) {
    free(pMem);
}
SYMCRYPT_CPU_FEATURES
SymCryptCpuFeaturesNeverPresent(void) {
    return 0;
}
SYMCRYPT_ERROR SymCryptCallbackRandom(PBYTE out, SIZE_T size) {
    for (size_t i = 0; i < size; i++) {
        out[i] = rand();
    }
    return SYMCRYPT_NO_ERROR;
}

int main(void)
{
    const uint8_t msg[] = {0xaa, 0x87, 0xca, 0x22, 0xbe, 0x8b, 0x05, 0x37, 0x8e, 0xb1, 0xc7, 0x1e, 0xf3, 0x20, 0xad, 0x74,
 0x6e, 0x1d, 0x3b, 0x62, 0x8b, 0xa7, 0x9b, 0x98, 0x59, 0xf7, 0x41, 0xe0, 0x82, 0x54, 0x2a, 0x38,
 0x55, 0x02, 0xf2, 0x5d, 0xbf, 0x55, 0x29, 0x6c, 0x3a, 0x54, 0x5e, 0x38, 0x72, 0x76, 0x0a, 0xb7};

    SYMCRYPT_ECURVE* curve = NULL;
    SYMCRYPT_ECKEY* key = NULL;
    SYMCRYPT_INT* nonce = NULL;

    CF_CHECK_NE(curve = SymCryptEcurveAllocate(SymCryptEcurveParamsNistP384, 0), NULL);
    CF_CHECK_NE(key = SymCryptEckeyAllocate(curve), NULL);
    CF_CHECK_NE(nonce = SymCryptIntAllocate(SymCryptEcurveDigitsofScalarMultiplier(curve)), NULL);
    {
        const uint8_t nonce_bytes[] = {0x01};
        CF_CHECK_EQ(SymCryptIntSetValue(nonce_bytes, sizeof(nonce_bytes), SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, nonce), SYMCRYPT_NO_ERROR);
    }

    {
        const uint8_t priv_bytes[] = {
            0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xc7, 0x63, 0x4d, 0x81, 0xf4, 0x37, 0x2d, 0xdf, 0x58, 0x1a, 0x0d, 0xb2, 0x48, 0xb0, 0xa7, 0x7a, 0xec, 0xec, 0x19, 0x6a, 0xcc, 0xc5, 0x29, 0x72};
        CF_CHECK_EQ(SymCryptEckeySetValue(
                priv_bytes, sizeof(priv_bytes),
                NULL, 0,
                SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, SYMCRYPT_ECPOINT_FORMAT_XY,
                0, key), SYMCRYPT_NO_ERROR);
    }

    {
        const size_t sigHalfSize = SymCryptEcurveSizeofScalarMultiplier(curve);
        const size_t sigSize = sigHalfSize * 2;
        uint8_t sig_bytes[sigSize];

        CF_CHECK_EQ(SymCryptEcDsaSignEx(
                    key,
                    msg,
                    sizeof(msg),
                    nonce,
                    SYMCRYPT_NUMBER_FORMAT_MSB_FIRST,
                    0,
                    sig_bytes,
                    sigSize), SYMCRYPT_NO_ERROR);

        const size_t pubSize = SymCryptEckeySizeofPublicKey(key, SYMCRYPT_ECPOINT_FORMAT_XY);

        const size_t pubHalfSize = pubSize / 2;
        uint8_t pub_bytes[pubSize];

        CF_CHECK_EQ(SymCryptEckeyGetValue(
                    key,
                    NULL, 0,
                    pub_bytes, pubSize,
                    SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, SYMCRYPT_ECPOINT_FORMAT_XY,
                    0), SYMCRYPT_NO_ERROR);

        printf("Pub X:\n");
        for (size_t i = 0; i < pubHalfSize; i++) {
            printf("%02X ", pub_bytes[i]);
        }
        printf("\n");

        printf("Pub Y:\n");
        for (size_t i = 0; i < pubHalfSize; i++) {
            printf("%02X ", pub_bytes[pubHalfSize+i]);
        }
        printf("\n");

        printf("Sig R:\n");
        for (size_t i = 0; i < sigHalfSize; i++) {
            printf("%02X ", sig_bytes[i]);
        }
        printf("\n");

        printf("Sig S:\n");
        for (size_t i = 0; i < sigHalfSize; i++) {
            printf("%02X ", sig_bytes[sigHalfSize+i]);
        }
        printf("\n");
    }

end:
    if ( key ) {
        /* noret */ SymCryptEckeyFree(key);
    }
    if ( curve ) {
        /* noret */ SymCryptEcurveFree(curve);
    }
    if ( nonce ) {
        /* noret */ SymCryptIntFree(nonce);
    }

    return 0;
}

Output:

Pub X:
AA 87 CA 22 BE 8B 05 37 8E B1 C7 1E F3 20 AD 74 6E 1D 3B 62 8B A7 9B 98 59 F7 41 E0 82 54 2A 38 55 02 F2 5D BF 55 29 6C 3A 54 5E 38 72 76 0A B7 
Pub Y:
C9 E8 21 B5 69 D9 D3 90 A2 61 67 40 6D 6D 23 D6 07 0B E2 42 D7 65 EB 83 16 25 CE EC 4A 0F 47 3E F5 9F 4E 30 E2 81 7E 62 85 BC E2 84 6F 15 F1 A0 
Sig R:
AA 87 CA 22 BE 8B 05 37 8E B1 C7 1E F3 20 AD 74 6E 1D 3B 62 8B A7 9B 98 59 F7 41 E0 82 54 2A 38 55 02 F2 5D BF 55 29 6C 3A 54 5E 38 72 76 0A B7 
Sig S:
00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 

S = 0, which makes the signature invalid. SymCryptEcDsaSignEx should fail instead.

Ask some project infomations

What is the difference between the algorithm in this project and the algorithm in bcrypt.dll (usermode) and ksecdd.sys (kernelmode) (I guess it has better performance and more algorithms?)

OSS-Fuzz #31514: ECDSA signing branches on uninitialized memory

Reproducer:

#include <stdlib.h>
#include <string.h>
#include <symcrypt.h>
#include <symcrypt_low_level.h>

#define CF_CHECK_EQ(expr, res) if ( (expr) != (res) ) { goto end; }
#define CF_CHECK_NE(expr, res) if ( (expr) == (res) ) { goto end; }

void SymCryptFatal(UINT32 fatalCode) {
    (void)fatalCode;

    abort();
}
void SymCryptInjectError( PBYTE pbData, SIZE_T cbData ) {
    (void)pbData;
    (void)cbData;
}

PVOID SymCryptCallbackAlloc( SIZE_T nBytes ) {
    return malloc(nBytes);
}

VOID SymCryptCallbackFree( VOID * pMem ) {
    free(pMem);
}

SYMCRYPT_ERROR SymCryptCallbackRandom(PBYTE   pbBuffer, SIZE_T  cbBuffer ) {
    memset(pbBuffer, 0xAA, cbBuffer);
    return SYMCRYPT_NO_ERROR;
}

SYMCRYPT_CPU_FEATURES
SymCryptCpuFeaturesNeverPresent(void) {
    return 0;
}

int main(void)
{
    const unsigned char priv_bytes[] = {0xD3, 0x03, 0x3A, 0xD6, 0xF6, 0x04, 0x6D, 0x78, 0x44, 0x23, 0x42, 0x5C, 0xCA, 0x9A, 0xEE, 0x1A, 0x07, 0x69, 0x93, 0x58, 0xE3, 0x8E, 0x38, 0xE3, 0x8E, 0x38, 0xE3, 0x8E};
    const unsigned char nonce_bytes[] = {0x31, 0xCB, 0x27, 0xF1, 0xD1, 0x42, 0x28, 0xEE, 0x5F, 0x42, 0xD1, 0xA8, 0x9A, 0xBD, 0x42, 0x4F, 0x65, 0xD1, 0xA1, 0x79, 0x02, 0xBC, 0x39, 0x58, 0xE3, 0x8E, 0x38, 0xE3, 0x8E, 0x38, 0xE3, 0x91};
    const unsigned char hash_bytes[] = {0x20, 0x20, 0x20, 0xff, 0xff, 0xff, 0x20, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
        0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
        0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
        0x20, 0x20, 0x20, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff,
        0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0x20,
        0x20, 0x20, 0x20, 0x20, 0x20, 0x20, 0xff, 0xff, 0xff, 0x20, 0x20, 0xff, 0x20, 0x20, 0x20, 0x20,
        0x20, 0x20, 0x20, 0x20};

    SYMCRYPT_ECURVE* curve = SymCryptEcurveAllocate(SymCryptEcurveParamsNistP224, 0);
    SYMCRYPT_ECKEY* key = NULL;
    SYMCRYPT_INT* nonce = NULL;

    CF_CHECK_NE(key = SymCryptEckeyAllocate(curve), NULL);

    CF_CHECK_NE(nonce = SymCryptIntAllocate(SymCryptEcurveDigitsofScalarMultiplier(curve)), NULL);
    CF_CHECK_EQ(SymCryptIntSetValue(nonce_bytes, sizeof(nonce_bytes), SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, nonce), SYMCRYPT_NO_ERROR);

    CF_CHECK_EQ(SymCryptEckeySetValue(
                priv_bytes, sizeof(priv_bytes),
                NULL, 0,
                SYMCRYPT_NUMBER_FORMAT_MSB_FIRST, SYMCRYPT_ECPOINT_FORMAT_XY,
                0, key), SYMCRYPT_NO_ERROR);

    {
        const size_t sigHalfSize = SymCryptEcurveSizeofScalarMultiplier(curve);
        const size_t sigSize = sigHalfSize * 2;
        unsigned char* sig_bytes = malloc(sigSize);

        CF_CHECK_EQ(SymCryptEcDsaSignEx(
                    key,
                    hash_bytes,
                    sizeof(hash_bytes),
                    nonce,
                    SYMCRYPT_NUMBER_FORMAT_MSB_FIRST,
                    0,
                    sig_bytes,
                    sigSize), SYMCRYPT_NO_ERROR);
    }

end:
    return 0;
}

Stack trace copy/paste from https://bugs.chromium.org/p/oss-fuzz/issues/detail?id=31514:

==9311==WARNING: MemorySanitizer: use-of-uninitialized-value
--
  | #0 0x107160f in SymCryptFdefModInvGeneric SymCrypt/lib/fdef_mod.c:996:9
  | #1 0x1072897 in SymCryptFdefModInvMontgomery SymCrypt/lib/fdef_mod.c:1375:15
  | #2 0x103f66b in SymCryptModInv SymCrypt/lib/a_dispatch.c:940:12
  | #3 0x105764a in SymCryptEcpointTransform SymCrypt/lib/ecpoint.c:420:23
  | #4 0x105a019 in SymCryptEcpointGetValue SymCrypt/lib/ecpoint.c:723:15
  | #5 0x104edea in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:299:19
  | #6 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #7 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #8 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #9 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #10 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #11 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #12 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #13 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #14 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #15 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  | #16 0x4804c8 in _start
  |  
  | Uninitialized value was stored to memory at
  | #0 0x105f0b0 in SymCryptFdefMaskedCopyC SymCrypt/lib/fdef_general.c:66:19
  | #1 0x105f191 in SymCryptFdefMaskedCopy SymCrypt/lib/fdef_general.c:83:5
  | #2 0x1056827 in SymCryptEcpointMaskedCopy SymCrypt/lib/ecpoint.c:181:5
  | #3 0x10c8b82 in SymCryptEcpointScalarMulFixedWindow SymCrypt/lib/ec_mul.c:252:9
  | #4 0x10c4c27 in SymCryptEcpointScalarMul SymCrypt/lib/ec_dispatch.c:231:12
  | #5 0x104e999 in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:280:13
  | #6 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #7 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #8 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #9 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #10 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #11 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #12 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #13 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #14 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #15 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  |  
  | Uninitialized value was stored to memory at
  | #0 0x105f0b0 in SymCryptFdefMaskedCopyC SymCrypt/lib/fdef_general.c:66:19
  | #1 0x105f191 in SymCryptFdefMaskedCopy SymCrypt/lib/fdef_general.c:83:5
  | #2 0x1056827 in SymCryptEcpointMaskedCopy SymCrypt/lib/ecpoint.c:181:5
  | #3 0x10c8b82 in SymCryptEcpointScalarMulFixedWindow SymCrypt/lib/ec_mul.c:252:9
  | #4 0x10c4c27 in SymCryptEcpointScalarMul SymCrypt/lib/ec_dispatch.c:231:12
  | #5 0x104e999 in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:280:13
  | #6 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #7 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #8 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #9 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #10 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #11 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #12 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #13 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #14 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #15 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  |  
  | Uninitialized value was stored to memory at
  | #0 0x105f0b0 in SymCryptFdefMaskedCopyC SymCrypt/lib/fdef_general.c:66:19
  | #1 0x105f191 in SymCryptFdefMaskedCopy SymCrypt/lib/fdef_general.c:83:5
  | #2 0x1056827 in SymCryptEcpointMaskedCopy SymCrypt/lib/ecpoint.c:181:5
  | #3 0x10c8b82 in SymCryptEcpointScalarMulFixedWindow SymCrypt/lib/ec_mul.c:252:9
  | #4 0x10c4c27 in SymCryptEcpointScalarMul SymCrypt/lib/ec_dispatch.c:231:12
  | #5 0x104e999 in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:280:13
  | #6 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #7 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #8 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #9 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #10 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #11 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #12 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #13 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #14 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #15 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  |  
  | Uninitialized value was stored to memory at
  | #0 0x105f0b0 in SymCryptFdefMaskedCopyC SymCrypt/lib/fdef_general.c:66:19
  | #1 0x105f191 in SymCryptFdefMaskedCopy SymCrypt/lib/fdef_general.c:83:5
  | #2 0x1056827 in SymCryptEcpointMaskedCopy SymCrypt/lib/ecpoint.c:181:5
  | #3 0x10c8b82 in SymCryptEcpointScalarMulFixedWindow SymCrypt/lib/ec_mul.c:252:9
  | #4 0x10c4c27 in SymCryptEcpointScalarMul SymCrypt/lib/ec_dispatch.c:231:12
  | #5 0x104e999 in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:280:13
  | #6 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #7 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #8 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #9 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #10 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #11 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #12 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #13 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #14 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #15 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  |  
  | Uninitialized value was stored to memory at
  | #0 0x105f0b0 in SymCryptFdefMaskedCopyC SymCrypt/lib/fdef_general.c:66:19
  | #1 0x105f191 in SymCryptFdefMaskedCopy SymCrypt/lib/fdef_general.c:83:5
  | #2 0x1056827 in SymCryptEcpointMaskedCopy SymCrypt/lib/ecpoint.c:181:5
  | #3 0x10c8b82 in SymCryptEcpointScalarMulFixedWindow SymCrypt/lib/ec_mul.c:252:9
  | #4 0x10c4c27 in SymCryptEcpointScalarMul SymCrypt/lib/ec_dispatch.c:231:12
  | #5 0x104e999 in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:280:13
  | #6 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #7 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #8 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #9 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #10 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #11 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #12 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #13 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #14 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #15 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  |  
  | Uninitialized value was stored to memory at
  | #0 0x105f0b0 in SymCryptFdefMaskedCopyC SymCrypt/lib/fdef_general.c:66:19
  | #1 0x105f191 in SymCryptFdefMaskedCopy SymCrypt/lib/fdef_general.c:83:5
  | #2 0x1056827 in SymCryptEcpointMaskedCopy SymCrypt/lib/ecpoint.c:181:5
  | #3 0x10c8b82 in SymCryptEcpointScalarMulFixedWindow SymCrypt/lib/ec_mul.c:252:9
  | #4 0x10c4c27 in SymCryptEcpointScalarMul SymCrypt/lib/ec_dispatch.c:231:12
  | #5 0x104e999 in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:280:13
  | #6 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #7 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #8 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #9 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #10 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #11 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #12 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #13 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #14 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #15 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  |  
  | Uninitialized value was created by a heap allocation
  | #0 0x5371bd in malloc /src/llvm-project/compiler-rt/lib/msan/msan_interceptors.cpp:901:3
  | #1 0x1022ccf in SymCryptCallbackAlloc cryptofuzz/modules/symcrypt/module.cpp:25:16
  | #2 0x104e0f8 in SymCryptEcDsaSignEx SymCrypt/lib/ec_dsa.c:220:17
  | #3 0x1034a90 in cryptofuzz::module::SymCrypt::OpECDSA_Sign(cryptofuzz::operation::ECDSA_Sign&) cryptofuzz/modules/symcrypt/module.cpp:1256:9
  | #4 0x64e8af in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::callModule(std::__1::shared_ptr<cryptofuzz::Module>, cryptofuzz::operation::ECDSA_Sign&) const cryptofuzz/executor.cpp:799:20
  | #5 0x64bf80 in cryptofuzz::ExecutorBase<cryptofuzz::component::ECDSA_Signature, cryptofuzz::operation::ECDSA_Sign>::Run(fuzzing::datasource::Datasource&, unsigned char const*, unsigned long) const cryptofuzz/executor.cpp:1486:47
  | #6 0x58a172 in cryptofuzz::Driver::Run(unsigned char const*, unsigned long) const cryptofuzz/driver.cpp:136:36
  | #7 0x7f809d in LLVMFuzzerTestOneInput cryptofuzz/entry.cpp:388:13
  | #8 0x4bbe41 in fuzzer::Fuzzer::ExecuteCallback(unsigned char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerLoop.cpp:599:15
  | #9 0x4a5b02 in fuzzer::RunOneTest(fuzzer::Fuzzer*, char const*, unsigned long) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:323:6
  | #10 0x4abe56 in fuzzer::FuzzerDriver(int*, char***, int (*)(unsigned char const*, unsigned long)) /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerDriver.cpp:856:9
  | #11 0x4d5e42 in main /src/llvm-project/compiler-rt/lib/fuzzer/FuzzerMain.cpp:20:10
  | #12 0x7f4b1349e83f in __libc_start_main /build/glibc-e6zv40/glibc-2.23/csu/libc-start.c:291
  |  
  | SUMMARY: MemorySanitizer: use-of-uninitialized-value (/mnt/scratch0/clusterfuzz/bot/builds/clusterfuzz-builds_cryptofuzz_94ef8836220c0eccbf1cd983651c4b1f64b4d368/revisions/cryptofuzz-boringssl-noasm+0x107160f)
  |  

Update README for jitterentropy submodule

Consider updating README from
git submodule update --init -- jitterentropy-library
to
git submodule update --init -- 3rdparty/jitterentropy-library
or change linked location.

OSS-Fuzz integration

I've integrated SymCrypt into my cryptography fuzzing project Cryptofuzz (SymCrypt module is not yet pushed to the repository).

I would now like to activate the SymCrypt module for Cryptofuzz on Google OSS-Fuzz.

Would you like to receive e-mail notifications when a bug is found? For this I need one or more e-mail addresses linked to a Google account.

If I include you in the e-mail list, you will also receive notifications of bugs that do not pertain to SymCrypt. If this is not desired, you may also choose to instead be informed by me personally once a bug is found.

Modify the unit tests to not depend on internal-only code

Currently, the unit tests depend on code that is not publicly available. Judging by the name “msbignum”, it should be possible to replace this with an alternative bignum implementation, such as GMP, OpenSSL, or libtommath.

Test suite failures in RSA when using Cng

image

According to the documentation, "The key size must be greater than or equal to 512 bits, less than or equal to 16384 bits, and must be a multiple of 64" from https://docs.microsoft.com/en-us/windows/desktop/api/bcrypt/nf-bcrypt-bcryptgeneratekeypair. In this case it isn't, and it makes Cng stop early.

Using
g_BitSizeEntries[iSize].nBitsOfModulus = g_BitSizeEntries[iSize].nBitsOfModulus & ~63; makes the test suite fail much later than that point.

Any reason why?

LLVM Clang and GCC Error: request for member 'm128i_u64' in something not a structure or union

Building on Windows or Ubuntu 22.10 with LLVM Clang 15 or GCC 12.2.0, the following error occurs when attempting to compile lib/sha512.c:

F:/Projects/Bootlie/contrib/SymCrypt/lib/sha512.c:1036:33: error: request for member 'm128i_u64' in something not a structure or union

This error occurs because Clang and GCC define the 128-bit XMM data types as typedef'd vectors rather than as a struct/union like defined in the UCRT. I.e. Clang defines these types as such:
typedef long long __m128i __attribute__((__vector_size__(16), __aligned__(16)));

A quick fix for little endian systems is to simply pointer-cast a given 128-bit XMM data type variable to an unsigned 64-bit integer.

Please consider adding a simple compiler check to pointer-cast to an unsigned __int64 type for Clang and GCC toolchains. Below is a patch:

diff --git lib/sha512.c lib/sha512.c
index 745ef24..f4abe4a 100644
--- lib/sha512.c
+++ lib/sha512.c
@@ -1030,7 +1030,11 @@ SymCryptSha512AppendBlocks_ull3(
 #define XMMROR( _a, _n ) _mm_xor_si128( _mm_slli_epi64( (_a), 64-(_n)), _mm_srli_epi64( (_a), (_n)) )
 #define XMMSHR( _a, _n ) _mm_srli_epi64((_a), (_n))
 #define XMMXOR( _a, _b ) _mm_xor_si128((_a), (_b))
+#if defined(__clang__) || defined(__GNUC__)
+#define XMMTO_UINT64( _a ) *(unsigned __int64 *)(&(_a))
+#else
 #define XMMTO_UINT64( _a ) ((_a).m128i_u64[0])
+#endif

 #define XMMMAJ( x, y, z )  XMMOR( XMMAND( XMMOR( (z), (y)), (x)), XMMAND( (z), (y) ) )
 #define XMMCH(  x, y, z )  XMMXOR( XMMAND( XMMXOR( (z), (y) ), (x)), (z))

Unit test build fails when setting C++ standard to C++20

Building SymCrypt fails with GCC11 or newer. It causes errors such as:

error: template-id not allowed for destructor
2683 | TlsCbcHmacImp<ImpXxx, AlgTlsCbcHmacSha384>::~TlsCbcHmacImp<ImpXxx, AlgTlsCbcHmacSha384>()

We'll track this internally, but I'm creating a public issue so that it's known that we're aware of it.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.