LCOV - code coverage report
Current view: top level - mpi - mpi-inline.h (source / functions) Hit Total Coverage
Test: coverage.info Lines: 51 52 98.1 %
Date: 2016-09-12 12:56:58 Functions: 5 5 100.0 %

          Line data    Source code
       1             : /* mpi-inline.h  -  Internal to the Multi Precision Integers
       2             :  * Copyright (C) 1994, 1996, 1998, 1999,
       3             :  *               2001, 2002 Free Software Foundation, Inc.
       4             :  *
       5             :  * This file is part of Libgcrypt.
       6             :  *
       7             :  * Libgcrypt is free software; you can redistribute it and/or modify
       8             :  * it under the terms of the GNU Lesser General Public License as
       9             :  * published by the Free Software Foundation; either version 2.1 of
      10             :  * the License, or (at your option) any later version.
      11             :  *
      12             :  * Libgcrypt is distributed in the hope that it will be useful,
      13             :  * but WITHOUT ANY WARRANTY; without even the implied warranty of
      14             :  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      15             :  * GNU Lesser General Public License for more details.
      16             :  *
      17             :  * You should have received a copy of the GNU Lesser General Public
      18             :  * License along with this program; if not, write to the Free Software
      19             :  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA
      20             :  *
      21             :  * Note: This code is heavily based on the GNU MP Library.
      22             :  *       Actually it's the same code with only minor changes in the
      23             :  *       way the data is stored; this is to support the abstraction
      24             :  *       of an optional secure memory allocation which may be used
      25             :  *       to avoid revealing of sensitive data due to paging etc.
      26             :  */
      27             : 
      28             : #ifndef G10_MPI_INLINE_H
      29             : #define G10_MPI_INLINE_H
      30             : 
      31             : /* Starting with gcc 4.3 "extern inline" conforms in c99 mode to the
      32             :    c99 semantics.  To keep the useful old semantics we use an
      33             :    attribute.  */
      34             : #ifndef G10_MPI_INLINE_DECL
      35             : # ifdef __GNUC_STDC_INLINE__
      36             : #  define G10_MPI_INLINE_DECL  extern inline __attribute__ ((__gnu_inline__))
      37             : # else
      38             : #  define G10_MPI_INLINE_DECL  extern __inline__
      39             : # endif
      40             : #endif
      41             : 
      42             : G10_MPI_INLINE_DECL  mpi_limb_t
      43    11933230 : _gcry_mpih_add_1( mpi_ptr_t res_ptr, mpi_ptr_t s1_ptr,
      44             :                mpi_size_t s1_size, mpi_limb_t s2_limb)
      45             : {
      46             :     mpi_limb_t x;
      47             : 
      48    11933230 :     x = *s1_ptr++;
      49    11933230 :     s2_limb += x;
      50    11933230 :     *res_ptr++ = s2_limb;
      51    11933230 :     if( s2_limb < x ) { /* sum is less than the left operand: handle carry */
      52         987 :         while( --s1_size ) {
      53         828 :             x = *s1_ptr++ + 1;  /* add carry */
      54         828 :             *res_ptr++ = x;     /* and store */
      55         828 :             if( x )             /* not 0 (no overflow): we can stop */
      56         159 :                 goto leave;
      57             :         }
      58           0 :         return 1; /* return carry (size of s1 to small) */
      59             :     }
      60             : 
      61             :   leave:
      62    11933230 :     if( res_ptr != s1_ptr ) { /* not the same variable */
      63             :         mpi_size_t i;          /* copy the rest */
      64     2571930 :         for( i=0; i < s1_size-1; i++ )
      65     2241731 :             res_ptr[i] = s1_ptr[i];
      66             :     }
      67    11933230 :     return 0; /* no carry */
      68             : }
      69             : 
      70             : 
      71             : 
      72             : G10_MPI_INLINE_DECL mpi_limb_t
      73    10455497 : _gcry_mpih_add(mpi_ptr_t res_ptr, mpi_ptr_t s1_ptr, mpi_size_t s1_size,
      74             :                                mpi_ptr_t s2_ptr, mpi_size_t s2_size)
      75             : {
      76    10455497 :     mpi_limb_t cy = 0;
      77             : 
      78    10455497 :     if( s2_size )
      79    10455497 :         cy = _gcry_mpih_add_n( res_ptr, s1_ptr, s2_ptr, s2_size );
      80             : 
      81    10455497 :     if( s1_size - s2_size )
      82      108123 :         cy = _gcry_mpih_add_1( res_ptr + s2_size, s1_ptr + s2_size,
      83             :                             s1_size - s2_size, cy);
      84    10455497 :     return cy;
      85             : }
      86             : 
      87             : 
      88             : G10_MPI_INLINE_DECL mpi_limb_t
      89     1059093 : _gcry_mpih_sub_1(mpi_ptr_t res_ptr,  mpi_ptr_t s1_ptr,
      90             :               mpi_size_t s1_size, mpi_limb_t s2_limb )
      91             : {
      92             :     mpi_limb_t x;
      93             : 
      94     1059093 :     x = *s1_ptr++;
      95     1059093 :     s2_limb = x - s2_limb;
      96     1059093 :     *res_ptr++ = s2_limb;
      97     1059093 :     if( s2_limb > x ) {
      98          90 :         while( --s1_size ) {
      99          45 :             x = *s1_ptr++;
     100          45 :             *res_ptr++ = x - 1;
     101          45 :             if( x )
     102          43 :                 goto leave;
     103             :         }
     104           1 :         return 1;
     105             :     }
     106             : 
     107             :   leave:
     108     1059092 :     if( res_ptr != s1_ptr ) {
     109             :         mpi_size_t i;
     110     3139390 :         for( i=0; i < s1_size-1; i++ )
     111     2087134 :             res_ptr[i] = s1_ptr[i];
     112             :     }
     113     1059092 :     return 0;
     114             : }
     115             : 
     116             : 
     117             : 
     118             : G10_MPI_INLINE_DECL   mpi_limb_t
     119     1043073 : _gcry_mpih_sub( mpi_ptr_t res_ptr, mpi_ptr_t s1_ptr, mpi_size_t s1_size,
     120             :                                 mpi_ptr_t s2_ptr, mpi_size_t s2_size)
     121             : {
     122     1043073 :     mpi_limb_t cy = 0;
     123             : 
     124     1043073 :     if( s2_size )
     125     1043073 :         cy = _gcry_mpih_sub_n(res_ptr, s1_ptr, s2_ptr, s2_size);
     126             : 
     127     1043073 :     if( s1_size - s2_size )
     128     1043073 :         cy = _gcry_mpih_sub_1(res_ptr + s2_size, s1_ptr + s2_size,
     129             :                                       s1_size - s2_size, cy);
     130     1043073 :     return cy;
     131             : }
     132             : 
     133             : /****************
     134             :  * Compare OP1_PTR/OP1_SIZE with OP2_PTR/OP2_SIZE.
     135             :  * There are no restrictions on the relative sizes of
     136             :  * the two arguments.
     137             :  * Return 1 if OP1 > OP2, 0 if they are equal, and -1 if OP1 < OP2.
     138             :  */
     139             : G10_MPI_INLINE_DECL int
     140    58382039 : _gcry_mpih_cmp( mpi_ptr_t op1_ptr, mpi_ptr_t op2_ptr, mpi_size_t size )
     141             : {
     142             :     mpi_size_t i;
     143             :     mpi_limb_t op1_word, op2_word;
     144             : 
     145    63819748 :     for( i = size - 1; i >= 0 ; i--) {
     146    63760947 :         op1_word = op1_ptr[i];
     147    63760947 :         op2_word = op2_ptr[i];
     148    63760947 :         if( op1_word != op2_word )
     149    58323238 :             goto diff;
     150             :     }
     151       58801 :     return 0;
     152             : 
     153             :   diff:
     154             :     /* This can *not* be simplified to
     155             :      *   op2_word - op2_word
     156             :      * since that expression might give signed overflow.  */
     157    58323238 :     return (op1_word > op2_word) ? 1 : -1;
     158             : }
     159             : 
     160             : 
     161             : #endif /*G10_MPI_INLINE_H*/

Generated by: LCOV version 1.11