static AzureIoTResult_t prvJWS_RS256Verify()

in ports/mbedTLS/azure_iot_jws_mbedtls.c [187:278]


static AzureIoTResult_t prvJWS_RS256Verify( uint8_t * pucInput,
                                            uint32_t ulInputLength,
                                            uint8_t * pucSignature,
                                            uint32_t ulSignatureLength,
                                            uint8_t * pucN,
                                            uint32_t ulNLength,
                                            uint8_t * pucE,
                                            uint32_t ulELength,
                                            uint8_t * pucBuffer,
                                            uint32_t ulBufferLength )
{
    AzureIoTResult_t xResult;
    int32_t lMbedTLSResult;
    mbedtls_rsa_context ctx;

    if( ulBufferLength < azureiotjwsSHA_CALCULATION_SCRATCH_SIZE )
    {
        AZLogError( ( "[JWS] Buffer Not Large Enough" ) );
        return eAzureIoTErrorOutOfMemory;
    }

    /* The signature is encrypted using the input key. We need to decrypt the */
    /* signature which gives us the SHA256 inside a PKCS7 structure. We then compare */
    /* that to the SHA256 of the input. */
    #if MBEDTLS_VERSION_NUMBER >= 0x03000000
        mbedtls_rsa_init( &ctx );
    #else
        mbedtls_rsa_init( &ctx, MBEDTLS_RSA_PKCS_V15, 0 );
    #endif

    lMbedTLSResult = mbedtls_rsa_import_raw( &ctx,
                                             pucN, ulNLength,
                                             NULL, 0,
                                             NULL, 0,
                                             NULL, 0,
                                             pucE, ulELength );

    if( lMbedTLSResult != 0 )
    {
        AZLogError( ( "[JWS] mbedtls_rsa_import_raw res: %08x", ( uint16_t ) lMbedTLSResult ) );
        mbedtls_rsa_free( &ctx );
        return eAzureIoTErrorFailed;
    }

    lMbedTLSResult = mbedtls_rsa_complete( &ctx );

    if( lMbedTLSResult != 0 )
    {
        AZLogError( ( "[JWS] mbedtls_rsa_complete res: %08x", ( uint16_t ) lMbedTLSResult ) );
        mbedtls_rsa_free( &ctx );
        return eAzureIoTErrorFailed;
    }

    lMbedTLSResult = mbedtls_rsa_check_pubkey( &ctx );

    if( lMbedTLSResult != 0 )
    {
        AZLogError( ( "[JWS] mbedtls_rsa_check_pubkey res: %08x", ( uint16_t ) lMbedTLSResult ) );
        mbedtls_rsa_free( &ctx );
        return eAzureIoTErrorFailed;
    }

    /* RSA */
    xResult = prvJWS_SHA256Calculate( pucInput, ulInputLength,
                                      pucBuffer );

    if( xResult != eAzureIoTSuccess )
    {
        AZLogError( ( "[JWS] prvJWS_SHA256Calculate failed" ) );
        return xResult;
    }

    #if MBEDTLS_VERSION_NUMBER >= 0x03000000
        lMbedTLSResult = mbedtls_rsa_pkcs1_verify( &ctx, MBEDTLS_MD_SHA256, azureiotjwsSHA256_SIZE, pucBuffer, pucSignature );
    #else
        lMbedTLSResult = mbedtls_rsa_pkcs1_verify( &ctx, NULL, NULL, MBEDTLS_RSA_PUBLIC, MBEDTLS_MD_SHA256, azureiotjwsSHA256_SIZE, pucBuffer, pucSignature );
    #endif

    if( lMbedTLSResult != 0 )
    {
        AZLogError( ( "[JWS] SHA of JWK does NOT match (%08x)", ( uint16_t ) lMbedTLSResult ) );
        xResult = eAzureIoTErrorFailed;
    }
    else
    {
        xResult = eAzureIoTSuccess;
    }

    mbedtls_rsa_free( &ctx );

    return xResult;
}