bug in gcrypt's bit manipulation routines

bpgcrypt at itaparica.org bpgcrypt at itaparica.org
Mon Jul 31 18:33:14 CEST 2006


it seems to me that I found some bugs in the bit manipulation routines of

1. The function gcry_mpi_set_bit ommits the (re-)allocation of enough 
   memory to store an MPI of the needed size. The following code snippet 
   demonstrates this:

#include <stdio.h>
#include <gcrypt.h>

int main()
  gcry_mpi_t a;
  int i;
  a = gcry_mpi_new(0);
  gcry_mpi_randomize(a, 50, GCRY_WEAK_RANDOM);   // get 50 random bits
  gcry_mpi_set_ui(a, 0);                         // "reset" them to 0

  for(i = 50; i >= 0; i--)                       // display a string of 0s
    printf("%d", gcry_mpi_test_bit(a, i));

  gcry_mpi_set_bit(a, 49);                       // set bit 49

  for(i = 50; i >= 0; i--)                       // this string has unexpected
    printf("%d", gcry_mpi_test_bit(a, i));       // random bit content!

  Of course one would expect that all but one of the bits in the second
  output line should be cleared, but they aren't. An example output follows


  The problem can be tracked down to libgcrypt-1.2.2/mpi/mpi-bit.c :

gcry_mpi_set_bit( gcry_mpi_t a, unsigned int n )
    unsigned int limbno, bitno;

    limbno = n / BITS_PER_MPI_LIMB;
    bitno  = n % BITS_PER_MPI_LIMB;

    if( limbno >= a->nlimbs ) { /* resize */
        if( a->alloced >= limbno )              /* XXXXXXXXXXXX */
            mpi_resize(a, limbno+1 );
        a->nlimbs = limbno+1;
    a->d[limbno] |= (A_LIMB_1<<bitno);

  To me it seems that the line I marked with XXXXX should contain a "<="
  instead of the ">=". The same is true for the function
  gcry_mpi_set_highbit in the same file.

  BTW: The code
     a = gcry_mpi_new(0); gcry_mpi_set_bit(a, 10000);
  immediately leads to a segmentation violation on my machine.

2. The routine gcry_mpi_rshift always interpretes the "shift value" N 
   as (N % 32). This behaviour is commented (a little bit) in

* Argument constraints:

   But this is NOT documented in the gcrypt manual:

-- Function: void gcry_mpi_rshift (gcry_mpi_t X, gcry_mpi_t A,
         unsigned int N)
    Shift the value of A by N bits to the right and store the result
    in X.

  I cannot decide ultimately weather the error here is in the code or 
  in the documentation. I personally would absolutely prefer an rshift
  implementation that can handly arbitrary large Ns.

3. HMAC-SHA256 calculation via

gcry_md_open(&mh, GCRY_MD_SHA256, GCRY_MD_FLAG_HMAC);

   aborts with some "no secure memory allocated" message. This can be
   fixed by explicitely doing a 

gcry_control(GCRYCTL_INIT_SECMEM, 1);

   but as the gcry_control function isn't documented properly, this
   necessity cannot be deduced from the docs. It took me hours of
   source reading to get the HMAC-256 to work. Again it is not me to
   decide weather this is a bug in the lib or a misdocumentation.

Thank you for libgcrypt!

More information about the Gcrypt-devel mailing list