lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  linux-hardening  PHC 
Open Source and information security mailing list archives
Hash Suite for Android: free password hash cracker in your pocket
[<prev] [next>] [<thread-prev] [day] [month] [year] [list]
Date:   Thu, 09 Nov 2017 14:55:41 +0000
From:   Vaneet Narang <>
To:     Ayush Mittal <>
CC:     "" <>,
        "" <>,
        "" <>,
        "" <>,
        AMIT SAHRAWAT <>,
        PANKAJ MISHRA <>
Subject: RE: Re: [PATCH 1/1] mpi: check for shift exponent greater than 31.


>> This patch check for shift exponent greater than 31,

Yes, This should be "check for shift exponent greater than BITS_PER_LONG"

>Firstly, isn't it 63 on 64-bit machines?

Description of patch is specific to 32bit machine but patch is made considering 64bit in mind also. 
and this is the precisly the reason we have been comparing with BITS_PER_MPI_LIMB 

>Secondly, this is the wrong way to do things.  The banner comment on
>mpihelp_lshift(), for example, says that the function has the following
>argument constraints:


>so sh1 and sh2 must both be in the range 1-31 or 1-63, assuming cnt is
>within its constraints.

You are right, there is already a comment for the range but in our case caller was mpi_powm() itself
so to fix UBSAN warning we prefferd handling in mpihelp_lshift/mpihelp_rshift.

Call Sequence:
[0-1.1677] [<c03ba190>] (ubsan_epilogue) from [<c03ba754>] (__ubsan_handle_shift_out_of_bounds+0xf4/0x13c)
[0-1.1677] [<c03ba660>] (__ubsan_handle_shift_out_of_bounds) from [<c03b5a44>] (mpihelp_lshift+0xf0/0x160)
[0-1.1677] [<c03b5954>] (mpihelp_lshift) from [<c03b8920>] (mpi_powm+0x308/0xc7c)

Scenario: MPI mod passed to mpi_powm has 0 last valid limb. 

count_leading_zeros() returns 32/64 when last valid limb of mod is 0.

* If @x is 0 then the result is COUNT_LEADING_ZEROS_0.
static inline int count_leading_zeros(unsigned long x)

int mpi_powm(MPI res, MPI base, MPI exp, MPI mod)
        mod_shift_cnt = count_leading_zeros(mod->d[msize - 1]);  --> count_leading_zeros can return 32/64
        if (mod_shift_cnt)
                mpihelp_lshift(mp, mod->d, msize, mod_shift_cnt); --> 32/64 can be passed to mpihelp_lshift
                /* Remove any leading zero words from the result.  */
                if (mod_shift_cnt)
                        mpihelp_rshift(rp, rp, rsize, mod_shift_cnt); --> Similarly 32/64 can be passed to mpihelp_rshift

>Therefore if it needs a checking, you only need to check cnt on entry to the
>function, rather than checking sh1 and sh2 inside the loop.  Further, you
>should use pr_err() so that we know that this has gone wrong and return an
>error to the caller (there are security implications).

Since we were not sure about checking cnt and returning some error value. we thought it may break mpi_powm().
We preferred doing a clean handling of invalid input without changing any behaviour of mpihelp_lshift/rshift . 
Please suggest how overflow can handled without breaking mpi_powm().

>Further, have you checked the caller to see if they do ever violate the

From caller side, only issue which i can think is passing 0 in as last valid limb of mod. Is this any
constraint ?

Vaneet Narang

Powered by blists - more mailing lists