RSA Signature verification algorithm

First of all, I am using static buffer for memory allocation (I am using bare-metal) and before using any of the mbedtls algorithms, I have to call this API “mbedtls_memory_buffer_alloc_init” for reserving the static buffer needed to run the algorithm.

So please, Could you kindly tell me the maximum size of buf (used as an argument parameter in mbedtls_memory_buffer_alloc_init) needed for running RSA Signature verification algorithm successfully ?
If there is a general rule for computing buf size, Please mention it.

Hi @AhmedHamza
There isn’t a general rule for computing the buf size, as it varies from the components you are using.
An RSA certificate is large enough, and considering the server may send a certificate chain, it may be that you need several KB in your buffer.

Note that you can use ecdsa signed certificates with similar security strength, and smaller size, if RAM is an issue for you.
Mbed TLS Support

Thanks for your reply.

I just need to highlight the fact that we are using a specific component which is RSA with Key size 2048 and message hashing is done using SHA256.

I am having a specific buffer size, which was tested for different inputs with same bit size and eventually, all of these test cases passed successfully. But when I tried to verify signature with ZERO value and same bit size, the algorithm stuck in a while loop and this issue is solved by increasing the buffer size.

So, Is it possible that buffer size depends on the input value ?
If so, Could you justify how is it possible ?

Any feedback please ?

HI @AhmedHamza
I apologize for delay.

As you can see from the code, there are only two functions that mbedtls_calloc() is being called:
mbedtls_rsa_rsassa_pkcs1_v15_verify() and mbedtls_rsa_rsassa_pkcs1_v15_sign().
I am assuming you are using the MBEDTLS_RSA_PKCS_V15 padding scheme.

All the locations where the allocation are used are are dependent only on the key length, which is 2048 / 8 = 256 bytes long, so it should not be dependent on the input length.
Could you please elaborate what do you mean by a ZERO value signature? Is the length zero or is it 256 bytes of zero bytes?
Do you also sign the message or only verify it?
Do you call mbedtls_calloc() in your application for the input message?

Thanks for your attention.

Regarding the ZERO value signature, it is 256 bytes of zero value.

Regarding the signed message, No message is signed, Only verification for the mentioned signature is applied.

Considering mbedtls_calloc() and mbedtls_free(), We are not using these APIs because we are totally preventing dynamic memory allocation usage and use instead static buffer allocation by calling this API: mbedtls_memory_buffer_alloc_init().

The main problem lies within the buffer size which is passed as a paramter for mbedtls_memory_buffer_alloc_init() API. We need to know the code complexity regarding memory size so that, We can guarantee the length of the buffer used.

Thanks in advance for your great assistance.

Any updates for this? :slightly_smiling_face:
I need to know the same

Hi @TareqElgafy
If you are using the memory_buffer allocation, then every call to mbedtls_calloc and mbedtls_free will use memory chunks from the static memory. So, the maximum size for the buffer is the maximum size that is used in the mbedtls_calloc() function within the rsa functions. As mentioned in my previous comment, " All the locations where the allocation are used are are dependent only on the key length, which is 2048 / 8 = 256 bytes long, so it should not be dependent on the input length."
The code inside uses these functions.
Note that within, there are several other uses of mbedtls_calloc() ( when reading the signature into a bignum structure)
Could you elaborate where is the while loop that is being stuck?

My case is the same, I am using mbedtls_memory_buffer_alloc_init() not mbedtls_calloc() and mbedtls_free(),

It stuck in the following while loop
while (ret_cmp >= (sint32)0)
ret = mbedtls_mpi_sub_mpi(R, R, B);
if (ret != (sint32)0)
ret_cmp = mbedtls_mpi_cmp_mpi(R, B);

IN mbedtls_mpi_mod_mpi

Anyway What I want to know what was in developer mind when he implemented mbedtls_memory_buffer_alloc_init(uint8 *buf, uint32 len)?
Because as you can see it expected a buffer length to be passed. No any speak about mbedtls_calloc() and mbedtls_free() here.

As mentinoed in this article:

If you want mbed TLS to allocate everything inside a static buffer, you can enable the Buffer Allocator by defining MBEDTLS_MEMORY_BUFFER_ALLOC_C in config.h .

This implies that all internal memory allocations are actually done on the static memory buffer defined by mbedtls_memory_buffer_alloc_init().
In details, when you use the MBEDTLS_MEMORY_BUFFER_ALLOC_C , every call to mbedtls_calloc() and mbedtls_free() will actually allocate memory from the static buffer you set as the memory buffer, and not from the heap. This is why the size of the buffer you want to use should be the maximal accumulated size of memory that is used with mbedtls_calloc()(with additional size for informational data inside the memory context ).