Example program to test AES-GCM functionality. Used for a workshop

Dependencies:   mbed

Committer:
HannesTschofenig
Date:
Thu Sep 27 06:34:22 2018 +0000
Revision:
0:796d0f61a05b
Example AES-GCM test program

Who changed what in which revision?

UserRevisionLine numberNew contents of line
HannesTschofenig 0:796d0f61a05b 1 /**
HannesTschofenig 0:796d0f61a05b 2 * \file bignum.h
HannesTschofenig 0:796d0f61a05b 3 *
HannesTschofenig 0:796d0f61a05b 4 * \brief Multi-precision integer library
HannesTschofenig 0:796d0f61a05b 5 *
HannesTschofenig 0:796d0f61a05b 6 * Copyright (C) 2006-2014, Brainspark B.V.
HannesTschofenig 0:796d0f61a05b 7 *
HannesTschofenig 0:796d0f61a05b 8 * This file is part of PolarSSL (http://www.polarssl.org)
HannesTschofenig 0:796d0f61a05b 9 * Lead Maintainer: Paul Bakker <polarssl_maintainer at polarssl.org>
HannesTschofenig 0:796d0f61a05b 10 *
HannesTschofenig 0:796d0f61a05b 11 * All rights reserved.
HannesTschofenig 0:796d0f61a05b 12 *
HannesTschofenig 0:796d0f61a05b 13 * This program is free software; you can redistribute it and/or modify
HannesTschofenig 0:796d0f61a05b 14 * it under the terms of the GNU General Public License as published by
HannesTschofenig 0:796d0f61a05b 15 * the Free Software Foundation; either version 2 of the License, or
HannesTschofenig 0:796d0f61a05b 16 * (at your option) any later version.
HannesTschofenig 0:796d0f61a05b 17 *
HannesTschofenig 0:796d0f61a05b 18 * This program is distributed in the hope that it will be useful,
HannesTschofenig 0:796d0f61a05b 19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
HannesTschofenig 0:796d0f61a05b 20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
HannesTschofenig 0:796d0f61a05b 21 * GNU General Public License for more details.
HannesTschofenig 0:796d0f61a05b 22 *
HannesTschofenig 0:796d0f61a05b 23 * You should have received a copy of the GNU General Public License along
HannesTschofenig 0:796d0f61a05b 24 * with this program; if not, write to the Free Software Foundation, Inc.,
HannesTschofenig 0:796d0f61a05b 25 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
HannesTschofenig 0:796d0f61a05b 26 */
HannesTschofenig 0:796d0f61a05b 27 #ifndef POLARSSL_BIGNUM_H
HannesTschofenig 0:796d0f61a05b 28 #define POLARSSL_BIGNUM_H
HannesTschofenig 0:796d0f61a05b 29
HannesTschofenig 0:796d0f61a05b 30 #include <stdio.h>
HannesTschofenig 0:796d0f61a05b 31 #include <string.h>
HannesTschofenig 0:796d0f61a05b 32
HannesTschofenig 0:796d0f61a05b 33 #if !defined(POLARSSL_CONFIG_FILE)
HannesTschofenig 0:796d0f61a05b 34 #include "config.h"
HannesTschofenig 0:796d0f61a05b 35 #else
HannesTschofenig 0:796d0f61a05b 36 #include POLARSSL_CONFIG_FILE
HannesTschofenig 0:796d0f61a05b 37 #endif
HannesTschofenig 0:796d0f61a05b 38
HannesTschofenig 0:796d0f61a05b 39 #if defined(_MSC_VER) && !defined(EFIX64) && !defined(EFI32)
HannesTschofenig 0:796d0f61a05b 40 #include <basetsd.h>
HannesTschofenig 0:796d0f61a05b 41 #if (_MSC_VER <= 1200)
HannesTschofenig 0:796d0f61a05b 42 typedef signed short int16_t;
HannesTschofenig 0:796d0f61a05b 43 typedef unsigned short uint16_t;
HannesTschofenig 0:796d0f61a05b 44 #else
HannesTschofenig 0:796d0f61a05b 45 typedef INT16 int16_t;
HannesTschofenig 0:796d0f61a05b 46 typedef UINT16 uint16_t;
HannesTschofenig 0:796d0f61a05b 47 #endif
HannesTschofenig 0:796d0f61a05b 48 typedef INT32 int32_t;
HannesTschofenig 0:796d0f61a05b 49 typedef INT64 int64_t;
HannesTschofenig 0:796d0f61a05b 50 typedef UINT32 uint32_t;
HannesTschofenig 0:796d0f61a05b 51 typedef UINT64 uint64_t;
HannesTschofenig 0:796d0f61a05b 52 #else
HannesTschofenig 0:796d0f61a05b 53 #include <inttypes.h>
HannesTschofenig 0:796d0f61a05b 54 #endif /* _MSC_VER && !EFIX64 && !EFI32 */
HannesTschofenig 0:796d0f61a05b 55
HannesTschofenig 0:796d0f61a05b 56 #define POLARSSL_ERR_MPI_FILE_IO_ERROR -0x0002 /**< An error occurred while reading from or writing to a file. */
HannesTschofenig 0:796d0f61a05b 57 #define POLARSSL_ERR_MPI_BAD_INPUT_DATA -0x0004 /**< Bad input parameters to function. */
HannesTschofenig 0:796d0f61a05b 58 #define POLARSSL_ERR_MPI_INVALID_CHARACTER -0x0006 /**< There is an invalid character in the digit string. */
HannesTschofenig 0:796d0f61a05b 59 #define POLARSSL_ERR_MPI_BUFFER_TOO_SMALL -0x0008 /**< The buffer is too small to write to. */
HannesTschofenig 0:796d0f61a05b 60 #define POLARSSL_ERR_MPI_NEGATIVE_VALUE -0x000A /**< The input arguments are negative or result in illegal output. */
HannesTschofenig 0:796d0f61a05b 61 #define POLARSSL_ERR_MPI_DIVISION_BY_ZERO -0x000C /**< The input argument for division is zero, which is not allowed. */
HannesTschofenig 0:796d0f61a05b 62 #define POLARSSL_ERR_MPI_NOT_ACCEPTABLE -0x000E /**< The input arguments are not acceptable. */
HannesTschofenig 0:796d0f61a05b 63 #define POLARSSL_ERR_MPI_MALLOC_FAILED -0x0010 /**< Memory allocation failed. */
HannesTschofenig 0:796d0f61a05b 64
HannesTschofenig 0:796d0f61a05b 65 #define MPI_CHK(f) do { if( ( ret = f ) != 0 ) goto cleanup; } while( 0 )
HannesTschofenig 0:796d0f61a05b 66
HannesTschofenig 0:796d0f61a05b 67 /*
HannesTschofenig 0:796d0f61a05b 68 * Maximum size MPIs are allowed to grow to in number of limbs.
HannesTschofenig 0:796d0f61a05b 69 */
HannesTschofenig 0:796d0f61a05b 70 #define POLARSSL_MPI_MAX_LIMBS 10000
HannesTschofenig 0:796d0f61a05b 71
HannesTschofenig 0:796d0f61a05b 72 #if !defined(POLARSSL_CONFIG_OPTIONS)
HannesTschofenig 0:796d0f61a05b 73 /*
HannesTschofenig 0:796d0f61a05b 74 * Maximum window size used for modular exponentiation. Default: 6
HannesTschofenig 0:796d0f61a05b 75 * Minimum value: 1. Maximum value: 6.
HannesTschofenig 0:796d0f61a05b 76 *
HannesTschofenig 0:796d0f61a05b 77 * Result is an array of ( 2 << POLARSSL_MPI_WINDOW_SIZE ) MPIs used
HannesTschofenig 0:796d0f61a05b 78 * for the sliding window calculation. (So 64 by default)
HannesTschofenig 0:796d0f61a05b 79 *
HannesTschofenig 0:796d0f61a05b 80 * Reduction in size, reduces speed.
HannesTschofenig 0:796d0f61a05b 81 */
HannesTschofenig 0:796d0f61a05b 82 #define POLARSSL_MPI_WINDOW_SIZE 6 /**< Maximum windows size used. */
HannesTschofenig 0:796d0f61a05b 83
HannesTschofenig 0:796d0f61a05b 84 /*
HannesTschofenig 0:796d0f61a05b 85 * Maximum size of MPIs allowed in bits and bytes for user-MPIs.
HannesTschofenig 0:796d0f61a05b 86 * ( Default: 512 bytes => 4096 bits, Maximum tested: 2048 bytes => 16384 bits )
HannesTschofenig 0:796d0f61a05b 87 *
HannesTschofenig 0:796d0f61a05b 88 * Note: Calculations can results temporarily in larger MPIs. So the number
HannesTschofenig 0:796d0f61a05b 89 * of limbs required (POLARSSL_MPI_MAX_LIMBS) is higher.
HannesTschofenig 0:796d0f61a05b 90 */
HannesTschofenig 0:796d0f61a05b 91 #define POLARSSL_MPI_MAX_SIZE 512 /**< Maximum number of bytes for usable MPIs. */
HannesTschofenig 0:796d0f61a05b 92
HannesTschofenig 0:796d0f61a05b 93 #endif /* !POLARSSL_CONFIG_OPTIONS */
HannesTschofenig 0:796d0f61a05b 94
HannesTschofenig 0:796d0f61a05b 95 #define POLARSSL_MPI_MAX_BITS ( 8 * POLARSSL_MPI_MAX_SIZE ) /**< Maximum number of bits for usable MPIs. */
HannesTschofenig 0:796d0f61a05b 96
HannesTschofenig 0:796d0f61a05b 97 /*
HannesTschofenig 0:796d0f61a05b 98 * When reading from files with mpi_read_file() and writing to files with
HannesTschofenig 0:796d0f61a05b 99 * mpi_write_file() the buffer should have space
HannesTschofenig 0:796d0f61a05b 100 * for a (short) label, the MPI (in the provided radix), the newline
HannesTschofenig 0:796d0f61a05b 101 * characters and the '\0'.
HannesTschofenig 0:796d0f61a05b 102 *
HannesTschofenig 0:796d0f61a05b 103 * By default we assume at least a 10 char label, a minimum radix of 10
HannesTschofenig 0:796d0f61a05b 104 * (decimal) and a maximum of 4096 bit numbers (1234 decimal chars).
HannesTschofenig 0:796d0f61a05b 105 * Autosized at compile time for at least a 10 char label, a minimum radix
HannesTschofenig 0:796d0f61a05b 106 * of 10 (decimal) for a number of POLARSSL_MPI_MAX_BITS size.
HannesTschofenig 0:796d0f61a05b 107 *
HannesTschofenig 0:796d0f61a05b 108 * This used to be statically sized to 1250 for a maximum of 4096 bit
HannesTschofenig 0:796d0f61a05b 109 * numbers (1234 decimal chars).
HannesTschofenig 0:796d0f61a05b 110 *
HannesTschofenig 0:796d0f61a05b 111 * Calculate using the formula:
HannesTschofenig 0:796d0f61a05b 112 * POLARSSL_MPI_RW_BUFFER_SIZE = ceil(POLARSSL_MPI_MAX_BITS / ln(10) * ln(2)) +
HannesTschofenig 0:796d0f61a05b 113 * LabelSize + 6
HannesTschofenig 0:796d0f61a05b 114 */
HannesTschofenig 0:796d0f61a05b 115 #define POLARSSL_MPI_MAX_BITS_SCALE100 ( 100 * POLARSSL_MPI_MAX_BITS )
HannesTschofenig 0:796d0f61a05b 116 #define LN_2_DIV_LN_10_SCALE100 332
HannesTschofenig 0:796d0f61a05b 117 #define POLARSSL_MPI_RW_BUFFER_SIZE ( ((POLARSSL_MPI_MAX_BITS_SCALE100 + LN_2_DIV_LN_10_SCALE100 - 1) / LN_2_DIV_LN_10_SCALE100) + 10 + 6 )
HannesTschofenig 0:796d0f61a05b 118
HannesTschofenig 0:796d0f61a05b 119 /*
HannesTschofenig 0:796d0f61a05b 120 * Define the base integer type, architecture-wise
HannesTschofenig 0:796d0f61a05b 121 */
HannesTschofenig 0:796d0f61a05b 122 #if defined(POLARSSL_HAVE_INT8)
HannesTschofenig 0:796d0f61a05b 123 typedef signed char t_sint;
HannesTschofenig 0:796d0f61a05b 124 typedef unsigned char t_uint;
HannesTschofenig 0:796d0f61a05b 125 typedef uint16_t t_udbl;
HannesTschofenig 0:796d0f61a05b 126 #define POLARSSL_HAVE_UDBL
HannesTschofenig 0:796d0f61a05b 127 #else
HannesTschofenig 0:796d0f61a05b 128 #if defined(POLARSSL_HAVE_INT16)
HannesTschofenig 0:796d0f61a05b 129 typedef int16_t t_sint;
HannesTschofenig 0:796d0f61a05b 130 typedef uint16_t t_uint;
HannesTschofenig 0:796d0f61a05b 131 typedef uint32_t t_udbl;
HannesTschofenig 0:796d0f61a05b 132 #define POLARSSL_HAVE_UDBL
HannesTschofenig 0:796d0f61a05b 133 #else
HannesTschofenig 0:796d0f61a05b 134 /*
HannesTschofenig 0:796d0f61a05b 135 * 32-bit integers can be forced on 64-bit arches (eg. for testing purposes)
HannesTschofenig 0:796d0f61a05b 136 * by defining POLARSSL_HAVE_INT32 and undefining POARSSL_HAVE_ASM
HannesTschofenig 0:796d0f61a05b 137 */
HannesTschofenig 0:796d0f61a05b 138 #if ( ! defined(POLARSSL_HAVE_INT32) && \
HannesTschofenig 0:796d0f61a05b 139 defined(_MSC_VER) && defined(_M_AMD64) )
HannesTschofenig 0:796d0f61a05b 140 #define POLARSSL_HAVE_INT64
HannesTschofenig 0:796d0f61a05b 141 typedef int64_t t_sint;
HannesTschofenig 0:796d0f61a05b 142 typedef uint64_t t_uint;
HannesTschofenig 0:796d0f61a05b 143 #else
HannesTschofenig 0:796d0f61a05b 144 #if ( ! defined(POLARSSL_HAVE_INT32) && \
HannesTschofenig 0:796d0f61a05b 145 defined(__GNUC__) && ( \
HannesTschofenig 0:796d0f61a05b 146 defined(__amd64__) || defined(__x86_64__) || \
HannesTschofenig 0:796d0f61a05b 147 defined(__ppc64__) || defined(__powerpc64__) || \
HannesTschofenig 0:796d0f61a05b 148 defined(__ia64__) || defined(__alpha__) || \
HannesTschofenig 0:796d0f61a05b 149 (defined(__sparc__) && defined(__arch64__)) || \
HannesTschofenig 0:796d0f61a05b 150 defined(__s390x__) ) )
HannesTschofenig 0:796d0f61a05b 151 #define POLARSSL_HAVE_INT64
HannesTschofenig 0:796d0f61a05b 152 typedef int64_t t_sint;
HannesTschofenig 0:796d0f61a05b 153 typedef uint64_t t_uint;
HannesTschofenig 0:796d0f61a05b 154 typedef unsigned int t_udbl __attribute__((mode(TI)));
HannesTschofenig 0:796d0f61a05b 155 #define POLARSSL_HAVE_UDBL
HannesTschofenig 0:796d0f61a05b 156 #else
HannesTschofenig 0:796d0f61a05b 157 #define POLARSSL_HAVE_INT32
HannesTschofenig 0:796d0f61a05b 158 typedef int32_t t_sint;
HannesTschofenig 0:796d0f61a05b 159 typedef uint32_t t_uint;
HannesTschofenig 0:796d0f61a05b 160 #if ( defined(_MSC_VER) && defined(_M_IX86) )
HannesTschofenig 0:796d0f61a05b 161 typedef uint64_t t_udbl;
HannesTschofenig 0:796d0f61a05b 162 #define POLARSSL_HAVE_UDBL
HannesTschofenig 0:796d0f61a05b 163 #else
HannesTschofenig 0:796d0f61a05b 164 #if defined( POLARSSL_HAVE_LONGLONG )
HannesTschofenig 0:796d0f61a05b 165 typedef unsigned long long t_udbl;
HannesTschofenig 0:796d0f61a05b 166 #define POLARSSL_HAVE_UDBL
HannesTschofenig 0:796d0f61a05b 167 #endif
HannesTschofenig 0:796d0f61a05b 168 #endif
HannesTschofenig 0:796d0f61a05b 169 #endif
HannesTschofenig 0:796d0f61a05b 170 #endif
HannesTschofenig 0:796d0f61a05b 171 #endif /* POLARSSL_HAVE_INT16 */
HannesTschofenig 0:796d0f61a05b 172 #endif /* POLARSSL_HAVE_INT8 */
HannesTschofenig 0:796d0f61a05b 173
HannesTschofenig 0:796d0f61a05b 174 #ifdef __cplusplus
HannesTschofenig 0:796d0f61a05b 175 extern "C" {
HannesTschofenig 0:796d0f61a05b 176 #endif
HannesTschofenig 0:796d0f61a05b 177
HannesTschofenig 0:796d0f61a05b 178 /**
HannesTschofenig 0:796d0f61a05b 179 * \brief MPI structure
HannesTschofenig 0:796d0f61a05b 180 */
HannesTschofenig 0:796d0f61a05b 181 typedef struct
HannesTschofenig 0:796d0f61a05b 182 {
HannesTschofenig 0:796d0f61a05b 183 int s; /*!< integer sign */
HannesTschofenig 0:796d0f61a05b 184 size_t n; /*!< total # of limbs */
HannesTschofenig 0:796d0f61a05b 185 t_uint *p; /*!< pointer to limbs */
HannesTschofenig 0:796d0f61a05b 186 }
HannesTschofenig 0:796d0f61a05b 187 mpi;
HannesTschofenig 0:796d0f61a05b 188
HannesTschofenig 0:796d0f61a05b 189 /**
HannesTschofenig 0:796d0f61a05b 190 * \brief Initialize one MPI
HannesTschofenig 0:796d0f61a05b 191 *
HannesTschofenig 0:796d0f61a05b 192 * \param X One MPI to initialize.
HannesTschofenig 0:796d0f61a05b 193 */
HannesTschofenig 0:796d0f61a05b 194 void mpi_init( mpi *X );
HannesTschofenig 0:796d0f61a05b 195
HannesTschofenig 0:796d0f61a05b 196 /**
HannesTschofenig 0:796d0f61a05b 197 * \brief Unallocate one MPI
HannesTschofenig 0:796d0f61a05b 198 *
HannesTschofenig 0:796d0f61a05b 199 * \param X One MPI to unallocate.
HannesTschofenig 0:796d0f61a05b 200 */
HannesTschofenig 0:796d0f61a05b 201 void mpi_free( mpi *X );
HannesTschofenig 0:796d0f61a05b 202
HannesTschofenig 0:796d0f61a05b 203 /**
HannesTschofenig 0:796d0f61a05b 204 * \brief Enlarge to the specified number of limbs
HannesTschofenig 0:796d0f61a05b 205 *
HannesTschofenig 0:796d0f61a05b 206 * \param X MPI to grow
HannesTschofenig 0:796d0f61a05b 207 * \param nblimbs The target number of limbs
HannesTschofenig 0:796d0f61a05b 208 *
HannesTschofenig 0:796d0f61a05b 209 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 210 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 211 */
HannesTschofenig 0:796d0f61a05b 212 int mpi_grow( mpi *X, size_t nblimbs );
HannesTschofenig 0:796d0f61a05b 213
HannesTschofenig 0:796d0f61a05b 214 /**
HannesTschofenig 0:796d0f61a05b 215 * \brief Resize down, keeping at least the specified number of limbs
HannesTschofenig 0:796d0f61a05b 216 *
HannesTschofenig 0:796d0f61a05b 217 * \param X MPI to shrink
HannesTschofenig 0:796d0f61a05b 218 * \param nblimbs The minimum number of limbs to keep
HannesTschofenig 0:796d0f61a05b 219 *
HannesTschofenig 0:796d0f61a05b 220 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 221 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 222 */
HannesTschofenig 0:796d0f61a05b 223 int mpi_shrink( mpi *X, size_t nblimbs );
HannesTschofenig 0:796d0f61a05b 224
HannesTschofenig 0:796d0f61a05b 225 /**
HannesTschofenig 0:796d0f61a05b 226 * \brief Copy the contents of Y into X
HannesTschofenig 0:796d0f61a05b 227 *
HannesTschofenig 0:796d0f61a05b 228 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 229 * \param Y Source MPI
HannesTschofenig 0:796d0f61a05b 230 *
HannesTschofenig 0:796d0f61a05b 231 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 232 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 233 */
HannesTschofenig 0:796d0f61a05b 234 int mpi_copy( mpi *X, const mpi *Y );
HannesTschofenig 0:796d0f61a05b 235
HannesTschofenig 0:796d0f61a05b 236 /**
HannesTschofenig 0:796d0f61a05b 237 * \brief Swap the contents of X and Y
HannesTschofenig 0:796d0f61a05b 238 *
HannesTschofenig 0:796d0f61a05b 239 * \param X First MPI value
HannesTschofenig 0:796d0f61a05b 240 * \param Y Second MPI value
HannesTschofenig 0:796d0f61a05b 241 */
HannesTschofenig 0:796d0f61a05b 242 void mpi_swap( mpi *X, mpi *Y );
HannesTschofenig 0:796d0f61a05b 243
HannesTschofenig 0:796d0f61a05b 244 /**
HannesTschofenig 0:796d0f61a05b 245 * \brief Safe conditional assignement X = Y if assign is 1
HannesTschofenig 0:796d0f61a05b 246 *
HannesTschofenig 0:796d0f61a05b 247 * \param X MPI to conditionally assign to
HannesTschofenig 0:796d0f61a05b 248 * \param Y Value to be assigned
HannesTschofenig 0:796d0f61a05b 249 * \param assign 1: perform the assignment, 0: keep X's original value
HannesTschofenig 0:796d0f61a05b 250 *
HannesTschofenig 0:796d0f61a05b 251 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 252 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 253 *
HannesTschofenig 0:796d0f61a05b 254 * \note This function is equivalent to
HannesTschofenig 0:796d0f61a05b 255 * if( assign ) mpi_copy( X, Y );
HannesTschofenig 0:796d0f61a05b 256 * except that it avoids leaking any information about whether
HannesTschofenig 0:796d0f61a05b 257 * the assignment was done or not (the above code may leak
HannesTschofenig 0:796d0f61a05b 258 * information through branch prediction and/or memory access
HannesTschofenig 0:796d0f61a05b 259 * patterns analysis).
HannesTschofenig 0:796d0f61a05b 260 */
HannesTschofenig 0:796d0f61a05b 261 int mpi_safe_cond_assign( mpi *X, const mpi *Y, unsigned char assign );
HannesTschofenig 0:796d0f61a05b 262
HannesTschofenig 0:796d0f61a05b 263 /**
HannesTschofenig 0:796d0f61a05b 264 * \brief Safe conditional swap X <-> Y if swap is 1
HannesTschofenig 0:796d0f61a05b 265 *
HannesTschofenig 0:796d0f61a05b 266 * \param X First mpi value
HannesTschofenig 0:796d0f61a05b 267 * \param Y Second mpi value
HannesTschofenig 0:796d0f61a05b 268 * \param assign 1: perform the swap, 0: keep X and Y's original values
HannesTschofenig 0:796d0f61a05b 269 *
HannesTschofenig 0:796d0f61a05b 270 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 271 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 272 *
HannesTschofenig 0:796d0f61a05b 273 * \note This function is equivalent to
HannesTschofenig 0:796d0f61a05b 274 * if( assign ) mpi_swap( X, Y );
HannesTschofenig 0:796d0f61a05b 275 * except that it avoids leaking any information about whether
HannesTschofenig 0:796d0f61a05b 276 * the assignment was done or not (the above code may leak
HannesTschofenig 0:796d0f61a05b 277 * information through branch prediction and/or memory access
HannesTschofenig 0:796d0f61a05b 278 * patterns analysis).
HannesTschofenig 0:796d0f61a05b 279 */
HannesTschofenig 0:796d0f61a05b 280 int mpi_safe_cond_swap( mpi *X, mpi *Y, unsigned char assign );
HannesTschofenig 0:796d0f61a05b 281
HannesTschofenig 0:796d0f61a05b 282 /**
HannesTschofenig 0:796d0f61a05b 283 * \brief Set value from integer
HannesTschofenig 0:796d0f61a05b 284 *
HannesTschofenig 0:796d0f61a05b 285 * \param X MPI to set
HannesTschofenig 0:796d0f61a05b 286 * \param z Value to use
HannesTschofenig 0:796d0f61a05b 287 *
HannesTschofenig 0:796d0f61a05b 288 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 289 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 290 */
HannesTschofenig 0:796d0f61a05b 291 int mpi_lset( mpi *X, t_sint z );
HannesTschofenig 0:796d0f61a05b 292
HannesTschofenig 0:796d0f61a05b 293 /**
HannesTschofenig 0:796d0f61a05b 294 * \brief Get a specific bit from X
HannesTschofenig 0:796d0f61a05b 295 *
HannesTschofenig 0:796d0f61a05b 296 * \param X MPI to use
HannesTschofenig 0:796d0f61a05b 297 * \param pos Zero-based index of the bit in X
HannesTschofenig 0:796d0f61a05b 298 *
HannesTschofenig 0:796d0f61a05b 299 * \return Either a 0 or a 1
HannesTschofenig 0:796d0f61a05b 300 */
HannesTschofenig 0:796d0f61a05b 301 int mpi_get_bit( const mpi *X, size_t pos );
HannesTschofenig 0:796d0f61a05b 302
HannesTschofenig 0:796d0f61a05b 303 /**
HannesTschofenig 0:796d0f61a05b 304 * \brief Set a bit of X to a specific value of 0 or 1
HannesTschofenig 0:796d0f61a05b 305 *
HannesTschofenig 0:796d0f61a05b 306 * \note Will grow X if necessary to set a bit to 1 in a not yet
HannesTschofenig 0:796d0f61a05b 307 * existing limb. Will not grow if bit should be set to 0
HannesTschofenig 0:796d0f61a05b 308 *
HannesTschofenig 0:796d0f61a05b 309 * \param X MPI to use
HannesTschofenig 0:796d0f61a05b 310 * \param pos Zero-based index of the bit in X
HannesTschofenig 0:796d0f61a05b 311 * \param val The value to set the bit to (0 or 1)
HannesTschofenig 0:796d0f61a05b 312 *
HannesTschofenig 0:796d0f61a05b 313 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 314 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 315 * POLARSSL_ERR_MPI_BAD_INPUT_DATA if val is not 0 or 1
HannesTschofenig 0:796d0f61a05b 316 */
HannesTschofenig 0:796d0f61a05b 317 int mpi_set_bit( mpi *X, size_t pos, unsigned char val );
HannesTschofenig 0:796d0f61a05b 318
HannesTschofenig 0:796d0f61a05b 319 /**
HannesTschofenig 0:796d0f61a05b 320 * \brief Return the number of zero-bits before the least significant
HannesTschofenig 0:796d0f61a05b 321 * '1' bit
HannesTschofenig 0:796d0f61a05b 322 *
HannesTschofenig 0:796d0f61a05b 323 * Note: Thus also the zero-based index of the least significant '1' bit
HannesTschofenig 0:796d0f61a05b 324 *
HannesTschofenig 0:796d0f61a05b 325 * \param X MPI to use
HannesTschofenig 0:796d0f61a05b 326 */
HannesTschofenig 0:796d0f61a05b 327 size_t mpi_lsb( const mpi *X );
HannesTschofenig 0:796d0f61a05b 328
HannesTschofenig 0:796d0f61a05b 329 /**
HannesTschofenig 0:796d0f61a05b 330 * \brief Return the number of bits up to and including the most
HannesTschofenig 0:796d0f61a05b 331 * significant '1' bit'
HannesTschofenig 0:796d0f61a05b 332 *
HannesTschofenig 0:796d0f61a05b 333 * Note: Thus also the one-based index of the most significant '1' bit
HannesTschofenig 0:796d0f61a05b 334 *
HannesTschofenig 0:796d0f61a05b 335 * \param X MPI to use
HannesTschofenig 0:796d0f61a05b 336 */
HannesTschofenig 0:796d0f61a05b 337 size_t mpi_msb( const mpi *X );
HannesTschofenig 0:796d0f61a05b 338
HannesTschofenig 0:796d0f61a05b 339 /**
HannesTschofenig 0:796d0f61a05b 340 * \brief Return the total size in bytes
HannesTschofenig 0:796d0f61a05b 341 *
HannesTschofenig 0:796d0f61a05b 342 * \param X MPI to use
HannesTschofenig 0:796d0f61a05b 343 */
HannesTschofenig 0:796d0f61a05b 344 size_t mpi_size( const mpi *X );
HannesTschofenig 0:796d0f61a05b 345
HannesTschofenig 0:796d0f61a05b 346 /**
HannesTschofenig 0:796d0f61a05b 347 * \brief Import from an ASCII string
HannesTschofenig 0:796d0f61a05b 348 *
HannesTschofenig 0:796d0f61a05b 349 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 350 * \param radix Input numeric base
HannesTschofenig 0:796d0f61a05b 351 * \param s Null-terminated string buffer
HannesTschofenig 0:796d0f61a05b 352 *
HannesTschofenig 0:796d0f61a05b 353 * \return 0 if successful, or a POLARSSL_ERR_MPI_XXX error code
HannesTschofenig 0:796d0f61a05b 354 */
HannesTschofenig 0:796d0f61a05b 355 int mpi_read_string( mpi *X, int radix, const char *s );
HannesTschofenig 0:796d0f61a05b 356
HannesTschofenig 0:796d0f61a05b 357 /**
HannesTschofenig 0:796d0f61a05b 358 * \brief Export into an ASCII string
HannesTschofenig 0:796d0f61a05b 359 *
HannesTschofenig 0:796d0f61a05b 360 * \param X Source MPI
HannesTschofenig 0:796d0f61a05b 361 * \param radix Output numeric base
HannesTschofenig 0:796d0f61a05b 362 * \param s String buffer
HannesTschofenig 0:796d0f61a05b 363 * \param slen String buffer size
HannesTschofenig 0:796d0f61a05b 364 *
HannesTschofenig 0:796d0f61a05b 365 * \return 0 if successful, or a POLARSSL_ERR_MPI_XXX error code.
HannesTschofenig 0:796d0f61a05b 366 * *slen is always updated to reflect the amount
HannesTschofenig 0:796d0f61a05b 367 * of data that has (or would have) been written.
HannesTschofenig 0:796d0f61a05b 368 *
HannesTschofenig 0:796d0f61a05b 369 * \note Call this function with *slen = 0 to obtain the
HannesTschofenig 0:796d0f61a05b 370 * minimum required buffer size in *slen.
HannesTschofenig 0:796d0f61a05b 371 */
HannesTschofenig 0:796d0f61a05b 372 int mpi_write_string( const mpi *X, int radix, char *s, size_t *slen );
HannesTschofenig 0:796d0f61a05b 373
HannesTschofenig 0:796d0f61a05b 374 #if defined(POLARSSL_FS_IO)
HannesTschofenig 0:796d0f61a05b 375 /**
HannesTschofenig 0:796d0f61a05b 376 * \brief Read X from an opened file
HannesTschofenig 0:796d0f61a05b 377 *
HannesTschofenig 0:796d0f61a05b 378 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 379 * \param radix Input numeric base
HannesTschofenig 0:796d0f61a05b 380 * \param fin Input file handle
HannesTschofenig 0:796d0f61a05b 381 *
HannesTschofenig 0:796d0f61a05b 382 * \return 0 if successful, POLARSSL_ERR_MPI_BUFFER_TOO_SMALL if
HannesTschofenig 0:796d0f61a05b 383 * the file read buffer is too small or a
HannesTschofenig 0:796d0f61a05b 384 * POLARSSL_ERR_MPI_XXX error code
HannesTschofenig 0:796d0f61a05b 385 */
HannesTschofenig 0:796d0f61a05b 386 int mpi_read_file( mpi *X, int radix, FILE *fin );
HannesTschofenig 0:796d0f61a05b 387
HannesTschofenig 0:796d0f61a05b 388 /**
HannesTschofenig 0:796d0f61a05b 389 * \brief Write X into an opened file, or stdout if fout is NULL
HannesTschofenig 0:796d0f61a05b 390 *
HannesTschofenig 0:796d0f61a05b 391 * \param p Prefix, can be NULL
HannesTschofenig 0:796d0f61a05b 392 * \param X Source MPI
HannesTschofenig 0:796d0f61a05b 393 * \param radix Output numeric base
HannesTschofenig 0:796d0f61a05b 394 * \param fout Output file handle (can be NULL)
HannesTschofenig 0:796d0f61a05b 395 *
HannesTschofenig 0:796d0f61a05b 396 * \return 0 if successful, or a POLARSSL_ERR_MPI_XXX error code
HannesTschofenig 0:796d0f61a05b 397 *
HannesTschofenig 0:796d0f61a05b 398 * \note Set fout == NULL to print X on the console.
HannesTschofenig 0:796d0f61a05b 399 */
HannesTschofenig 0:796d0f61a05b 400 int mpi_write_file( const char *p, const mpi *X, int radix, FILE *fout );
HannesTschofenig 0:796d0f61a05b 401 #endif /* POLARSSL_FS_IO */
HannesTschofenig 0:796d0f61a05b 402
HannesTschofenig 0:796d0f61a05b 403 /**
HannesTschofenig 0:796d0f61a05b 404 * \brief Import X from unsigned binary data, big endian
HannesTschofenig 0:796d0f61a05b 405 *
HannesTschofenig 0:796d0f61a05b 406 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 407 * \param buf Input buffer
HannesTschofenig 0:796d0f61a05b 408 * \param buflen Input buffer size
HannesTschofenig 0:796d0f61a05b 409 *
HannesTschofenig 0:796d0f61a05b 410 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 411 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 412 */
HannesTschofenig 0:796d0f61a05b 413 int mpi_read_binary( mpi *X, const unsigned char *buf, size_t buflen );
HannesTschofenig 0:796d0f61a05b 414
HannesTschofenig 0:796d0f61a05b 415 /**
HannesTschofenig 0:796d0f61a05b 416 * \brief Export X into unsigned binary data, big endian
HannesTschofenig 0:796d0f61a05b 417 *
HannesTschofenig 0:796d0f61a05b 418 * \param X Source MPI
HannesTschofenig 0:796d0f61a05b 419 * \param buf Output buffer
HannesTschofenig 0:796d0f61a05b 420 * \param buflen Output buffer size
HannesTschofenig 0:796d0f61a05b 421 *
HannesTschofenig 0:796d0f61a05b 422 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 423 * POLARSSL_ERR_MPI_BUFFER_TOO_SMALL if buf isn't large enough
HannesTschofenig 0:796d0f61a05b 424 */
HannesTschofenig 0:796d0f61a05b 425 int mpi_write_binary( const mpi *X, unsigned char *buf, size_t buflen );
HannesTschofenig 0:796d0f61a05b 426
HannesTschofenig 0:796d0f61a05b 427 /**
HannesTschofenig 0:796d0f61a05b 428 * \brief Left-shift: X <<= count
HannesTschofenig 0:796d0f61a05b 429 *
HannesTschofenig 0:796d0f61a05b 430 * \param X MPI to shift
HannesTschofenig 0:796d0f61a05b 431 * \param count Amount to shift
HannesTschofenig 0:796d0f61a05b 432 *
HannesTschofenig 0:796d0f61a05b 433 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 434 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 435 */
HannesTschofenig 0:796d0f61a05b 436 int mpi_shift_l( mpi *X, size_t count );
HannesTschofenig 0:796d0f61a05b 437
HannesTschofenig 0:796d0f61a05b 438 /**
HannesTschofenig 0:796d0f61a05b 439 * \brief Right-shift: X >>= count
HannesTschofenig 0:796d0f61a05b 440 *
HannesTschofenig 0:796d0f61a05b 441 * \param X MPI to shift
HannesTschofenig 0:796d0f61a05b 442 * \param count Amount to shift
HannesTschofenig 0:796d0f61a05b 443 *
HannesTschofenig 0:796d0f61a05b 444 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 445 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 446 */
HannesTschofenig 0:796d0f61a05b 447 int mpi_shift_r( mpi *X, size_t count );
HannesTschofenig 0:796d0f61a05b 448
HannesTschofenig 0:796d0f61a05b 449 /**
HannesTschofenig 0:796d0f61a05b 450 * \brief Compare unsigned values
HannesTschofenig 0:796d0f61a05b 451 *
HannesTschofenig 0:796d0f61a05b 452 * \param X Left-hand MPI
HannesTschofenig 0:796d0f61a05b 453 * \param Y Right-hand MPI
HannesTschofenig 0:796d0f61a05b 454 *
HannesTschofenig 0:796d0f61a05b 455 * \return 1 if |X| is greater than |Y|,
HannesTschofenig 0:796d0f61a05b 456 * -1 if |X| is lesser than |Y| or
HannesTschofenig 0:796d0f61a05b 457 * 0 if |X| is equal to |Y|
HannesTschofenig 0:796d0f61a05b 458 */
HannesTschofenig 0:796d0f61a05b 459 int mpi_cmp_abs( const mpi *X, const mpi *Y );
HannesTschofenig 0:796d0f61a05b 460
HannesTschofenig 0:796d0f61a05b 461 /**
HannesTschofenig 0:796d0f61a05b 462 * \brief Compare signed values
HannesTschofenig 0:796d0f61a05b 463 *
HannesTschofenig 0:796d0f61a05b 464 * \param X Left-hand MPI
HannesTschofenig 0:796d0f61a05b 465 * \param Y Right-hand MPI
HannesTschofenig 0:796d0f61a05b 466 *
HannesTschofenig 0:796d0f61a05b 467 * \return 1 if X is greater than Y,
HannesTschofenig 0:796d0f61a05b 468 * -1 if X is lesser than Y or
HannesTschofenig 0:796d0f61a05b 469 * 0 if X is equal to Y
HannesTschofenig 0:796d0f61a05b 470 */
HannesTschofenig 0:796d0f61a05b 471 int mpi_cmp_mpi( const mpi *X, const mpi *Y );
HannesTschofenig 0:796d0f61a05b 472
HannesTschofenig 0:796d0f61a05b 473 /**
HannesTschofenig 0:796d0f61a05b 474 * \brief Compare signed values
HannesTschofenig 0:796d0f61a05b 475 *
HannesTschofenig 0:796d0f61a05b 476 * \param X Left-hand MPI
HannesTschofenig 0:796d0f61a05b 477 * \param z The integer value to compare to
HannesTschofenig 0:796d0f61a05b 478 *
HannesTschofenig 0:796d0f61a05b 479 * \return 1 if X is greater than z,
HannesTschofenig 0:796d0f61a05b 480 * -1 if X is lesser than z or
HannesTschofenig 0:796d0f61a05b 481 * 0 if X is equal to z
HannesTschofenig 0:796d0f61a05b 482 */
HannesTschofenig 0:796d0f61a05b 483 int mpi_cmp_int( const mpi *X, t_sint z );
HannesTschofenig 0:796d0f61a05b 484
HannesTschofenig 0:796d0f61a05b 485 /**
HannesTschofenig 0:796d0f61a05b 486 * \brief Unsigned addition: X = |A| + |B|
HannesTschofenig 0:796d0f61a05b 487 *
HannesTschofenig 0:796d0f61a05b 488 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 489 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 490 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 491 *
HannesTschofenig 0:796d0f61a05b 492 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 493 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 494 */
HannesTschofenig 0:796d0f61a05b 495 int mpi_add_abs( mpi *X, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 496
HannesTschofenig 0:796d0f61a05b 497 /**
HannesTschofenig 0:796d0f61a05b 498 * \brief Unsigned subtraction: X = |A| - |B|
HannesTschofenig 0:796d0f61a05b 499 *
HannesTschofenig 0:796d0f61a05b 500 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 501 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 502 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 503 *
HannesTschofenig 0:796d0f61a05b 504 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 505 * POLARSSL_ERR_MPI_NEGATIVE_VALUE if B is greater than A
HannesTschofenig 0:796d0f61a05b 506 */
HannesTschofenig 0:796d0f61a05b 507 int mpi_sub_abs( mpi *X, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 508
HannesTschofenig 0:796d0f61a05b 509 /**
HannesTschofenig 0:796d0f61a05b 510 * \brief Signed addition: X = A + B
HannesTschofenig 0:796d0f61a05b 511 *
HannesTschofenig 0:796d0f61a05b 512 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 513 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 514 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 515 *
HannesTschofenig 0:796d0f61a05b 516 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 517 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 518 */
HannesTschofenig 0:796d0f61a05b 519 int mpi_add_mpi( mpi *X, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 520
HannesTschofenig 0:796d0f61a05b 521 /**
HannesTschofenig 0:796d0f61a05b 522 * \brief Signed subtraction: X = A - B
HannesTschofenig 0:796d0f61a05b 523 *
HannesTschofenig 0:796d0f61a05b 524 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 525 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 526 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 527 *
HannesTschofenig 0:796d0f61a05b 528 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 529 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 530 */
HannesTschofenig 0:796d0f61a05b 531 int mpi_sub_mpi( mpi *X, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 532
HannesTschofenig 0:796d0f61a05b 533 /**
HannesTschofenig 0:796d0f61a05b 534 * \brief Signed addition: X = A + b
HannesTschofenig 0:796d0f61a05b 535 *
HannesTschofenig 0:796d0f61a05b 536 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 537 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 538 * \param b The integer value to add
HannesTschofenig 0:796d0f61a05b 539 *
HannesTschofenig 0:796d0f61a05b 540 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 541 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 542 */
HannesTschofenig 0:796d0f61a05b 543 int mpi_add_int( mpi *X, const mpi *A, t_sint b );
HannesTschofenig 0:796d0f61a05b 544
HannesTschofenig 0:796d0f61a05b 545 /**
HannesTschofenig 0:796d0f61a05b 546 * \brief Signed subtraction: X = A - b
HannesTschofenig 0:796d0f61a05b 547 *
HannesTschofenig 0:796d0f61a05b 548 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 549 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 550 * \param b The integer value to subtract
HannesTschofenig 0:796d0f61a05b 551 *
HannesTschofenig 0:796d0f61a05b 552 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 553 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 554 */
HannesTschofenig 0:796d0f61a05b 555 int mpi_sub_int( mpi *X, const mpi *A, t_sint b );
HannesTschofenig 0:796d0f61a05b 556
HannesTschofenig 0:796d0f61a05b 557 /**
HannesTschofenig 0:796d0f61a05b 558 * \brief Baseline multiplication: X = A * B
HannesTschofenig 0:796d0f61a05b 559 *
HannesTschofenig 0:796d0f61a05b 560 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 561 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 562 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 563 *
HannesTschofenig 0:796d0f61a05b 564 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 565 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 566 */
HannesTschofenig 0:796d0f61a05b 567 int mpi_mul_mpi( mpi *X, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 568
HannesTschofenig 0:796d0f61a05b 569 /**
HannesTschofenig 0:796d0f61a05b 570 * \brief Baseline multiplication: X = A * b
HannesTschofenig 0:796d0f61a05b 571 * Note: despite the functon signature, b is treated as a
HannesTschofenig 0:796d0f61a05b 572 * t_uint. Negative values of b are treated as large positive
HannesTschofenig 0:796d0f61a05b 573 * values.
HannesTschofenig 0:796d0f61a05b 574 *
HannesTschofenig 0:796d0f61a05b 575 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 576 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 577 * \param b The integer value to multiply with
HannesTschofenig 0:796d0f61a05b 578 *
HannesTschofenig 0:796d0f61a05b 579 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 580 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 581 */
HannesTschofenig 0:796d0f61a05b 582 int mpi_mul_int( mpi *X, const mpi *A, t_sint b );
HannesTschofenig 0:796d0f61a05b 583
HannesTschofenig 0:796d0f61a05b 584 /**
HannesTschofenig 0:796d0f61a05b 585 * \brief Division by mpi: A = Q * B + R
HannesTschofenig 0:796d0f61a05b 586 *
HannesTschofenig 0:796d0f61a05b 587 * \param Q Destination MPI for the quotient
HannesTschofenig 0:796d0f61a05b 588 * \param R Destination MPI for the rest value
HannesTschofenig 0:796d0f61a05b 589 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 590 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 591 *
HannesTschofenig 0:796d0f61a05b 592 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 593 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 594 * POLARSSL_ERR_MPI_DIVISION_BY_ZERO if B == 0
HannesTschofenig 0:796d0f61a05b 595 *
HannesTschofenig 0:796d0f61a05b 596 * \note Either Q or R can be NULL.
HannesTschofenig 0:796d0f61a05b 597 */
HannesTschofenig 0:796d0f61a05b 598 int mpi_div_mpi( mpi *Q, mpi *R, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 599
HannesTschofenig 0:796d0f61a05b 600 /**
HannesTschofenig 0:796d0f61a05b 601 * \brief Division by int: A = Q * b + R
HannesTschofenig 0:796d0f61a05b 602 *
HannesTschofenig 0:796d0f61a05b 603 * \param Q Destination MPI for the quotient
HannesTschofenig 0:796d0f61a05b 604 * \param R Destination MPI for the rest value
HannesTschofenig 0:796d0f61a05b 605 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 606 * \param b Integer to divide by
HannesTschofenig 0:796d0f61a05b 607 *
HannesTschofenig 0:796d0f61a05b 608 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 609 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 610 * POLARSSL_ERR_MPI_DIVISION_BY_ZERO if b == 0
HannesTschofenig 0:796d0f61a05b 611 *
HannesTschofenig 0:796d0f61a05b 612 * \note Either Q or R can be NULL.
HannesTschofenig 0:796d0f61a05b 613 */
HannesTschofenig 0:796d0f61a05b 614 int mpi_div_int( mpi *Q, mpi *R, const mpi *A, t_sint b );
HannesTschofenig 0:796d0f61a05b 615
HannesTschofenig 0:796d0f61a05b 616 /**
HannesTschofenig 0:796d0f61a05b 617 * \brief Modulo: R = A mod B
HannesTschofenig 0:796d0f61a05b 618 *
HannesTschofenig 0:796d0f61a05b 619 * \param R Destination MPI for the rest value
HannesTschofenig 0:796d0f61a05b 620 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 621 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 622 *
HannesTschofenig 0:796d0f61a05b 623 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 624 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 625 * POLARSSL_ERR_MPI_DIVISION_BY_ZERO if B == 0,
HannesTschofenig 0:796d0f61a05b 626 * POLARSSL_ERR_MPI_NEGATIVE_VALUE if B < 0
HannesTschofenig 0:796d0f61a05b 627 */
HannesTschofenig 0:796d0f61a05b 628 int mpi_mod_mpi( mpi *R, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 629
HannesTschofenig 0:796d0f61a05b 630 /**
HannesTschofenig 0:796d0f61a05b 631 * \brief Modulo: r = A mod b
HannesTschofenig 0:796d0f61a05b 632 *
HannesTschofenig 0:796d0f61a05b 633 * \param r Destination t_uint
HannesTschofenig 0:796d0f61a05b 634 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 635 * \param b Integer to divide by
HannesTschofenig 0:796d0f61a05b 636 *
HannesTschofenig 0:796d0f61a05b 637 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 638 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 639 * POLARSSL_ERR_MPI_DIVISION_BY_ZERO if b == 0,
HannesTschofenig 0:796d0f61a05b 640 * POLARSSL_ERR_MPI_NEGATIVE_VALUE if b < 0
HannesTschofenig 0:796d0f61a05b 641 */
HannesTschofenig 0:796d0f61a05b 642 int mpi_mod_int( t_uint *r, const mpi *A, t_sint b );
HannesTschofenig 0:796d0f61a05b 643
HannesTschofenig 0:796d0f61a05b 644 /**
HannesTschofenig 0:796d0f61a05b 645 * \brief Sliding-window exponentiation: X = A^E mod N
HannesTschofenig 0:796d0f61a05b 646 *
HannesTschofenig 0:796d0f61a05b 647 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 648 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 649 * \param E Exponent MPI
HannesTschofenig 0:796d0f61a05b 650 * \param N Modular MPI
HannesTschofenig 0:796d0f61a05b 651 * \param _RR Speed-up MPI used for recalculations
HannesTschofenig 0:796d0f61a05b 652 *
HannesTschofenig 0:796d0f61a05b 653 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 654 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 655 * POLARSSL_ERR_MPI_BAD_INPUT_DATA if N is negative or even or
HannesTschofenig 0:796d0f61a05b 656 * if E is negative
HannesTschofenig 0:796d0f61a05b 657 *
HannesTschofenig 0:796d0f61a05b 658 * \note _RR is used to avoid re-computing R*R mod N across
HannesTschofenig 0:796d0f61a05b 659 * multiple calls, which speeds up things a bit. It can
HannesTschofenig 0:796d0f61a05b 660 * be set to NULL if the extra performance is unneeded.
HannesTschofenig 0:796d0f61a05b 661 */
HannesTschofenig 0:796d0f61a05b 662 int mpi_exp_mod( mpi *X, const mpi *A, const mpi *E, const mpi *N, mpi *_RR );
HannesTschofenig 0:796d0f61a05b 663
HannesTschofenig 0:796d0f61a05b 664 /**
HannesTschofenig 0:796d0f61a05b 665 * \brief Fill an MPI X with size bytes of random
HannesTschofenig 0:796d0f61a05b 666 *
HannesTschofenig 0:796d0f61a05b 667 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 668 * \param size Size in bytes
HannesTschofenig 0:796d0f61a05b 669 * \param f_rng RNG function
HannesTschofenig 0:796d0f61a05b 670 * \param p_rng RNG parameter
HannesTschofenig 0:796d0f61a05b 671 *
HannesTschofenig 0:796d0f61a05b 672 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 673 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 674 */
HannesTschofenig 0:796d0f61a05b 675 int mpi_fill_random( mpi *X, size_t size,
HannesTschofenig 0:796d0f61a05b 676 int (*f_rng)(void *, unsigned char *, size_t),
HannesTschofenig 0:796d0f61a05b 677 void *p_rng );
HannesTschofenig 0:796d0f61a05b 678
HannesTschofenig 0:796d0f61a05b 679 /**
HannesTschofenig 0:796d0f61a05b 680 * \brief Greatest common divisor: G = gcd(A, B)
HannesTschofenig 0:796d0f61a05b 681 *
HannesTschofenig 0:796d0f61a05b 682 * \param G Destination MPI
HannesTschofenig 0:796d0f61a05b 683 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 684 * \param B Right-hand MPI
HannesTschofenig 0:796d0f61a05b 685 *
HannesTschofenig 0:796d0f61a05b 686 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 687 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed
HannesTschofenig 0:796d0f61a05b 688 */
HannesTschofenig 0:796d0f61a05b 689 int mpi_gcd( mpi *G, const mpi *A, const mpi *B );
HannesTschofenig 0:796d0f61a05b 690
HannesTschofenig 0:796d0f61a05b 691 /**
HannesTschofenig 0:796d0f61a05b 692 * \brief Modular inverse: X = A^-1 mod N
HannesTschofenig 0:796d0f61a05b 693 *
HannesTschofenig 0:796d0f61a05b 694 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 695 * \param A Left-hand MPI
HannesTschofenig 0:796d0f61a05b 696 * \param N Right-hand MPI
HannesTschofenig 0:796d0f61a05b 697 *
HannesTschofenig 0:796d0f61a05b 698 * \return 0 if successful,
HannesTschofenig 0:796d0f61a05b 699 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 700 * POLARSSL_ERR_MPI_BAD_INPUT_DATA if N is negative or nil
HannesTschofenig 0:796d0f61a05b 701 POLARSSL_ERR_MPI_NOT_ACCEPTABLE if A has no inverse mod N
HannesTschofenig 0:796d0f61a05b 702 */
HannesTschofenig 0:796d0f61a05b 703 int mpi_inv_mod( mpi *X, const mpi *A, const mpi *N );
HannesTschofenig 0:796d0f61a05b 704
HannesTschofenig 0:796d0f61a05b 705 /**
HannesTschofenig 0:796d0f61a05b 706 * \brief Miller-Rabin primality test
HannesTschofenig 0:796d0f61a05b 707 *
HannesTschofenig 0:796d0f61a05b 708 * \param X MPI to check
HannesTschofenig 0:796d0f61a05b 709 * \param f_rng RNG function
HannesTschofenig 0:796d0f61a05b 710 * \param p_rng RNG parameter
HannesTschofenig 0:796d0f61a05b 711 *
HannesTschofenig 0:796d0f61a05b 712 * \return 0 if successful (probably prime),
HannesTschofenig 0:796d0f61a05b 713 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 714 * POLARSSL_ERR_MPI_NOT_ACCEPTABLE if X is not prime
HannesTschofenig 0:796d0f61a05b 715 */
HannesTschofenig 0:796d0f61a05b 716 int mpi_is_prime( mpi *X,
HannesTschofenig 0:796d0f61a05b 717 int (*f_rng)(void *, unsigned char *, size_t),
HannesTschofenig 0:796d0f61a05b 718 void *p_rng );
HannesTschofenig 0:796d0f61a05b 719
HannesTschofenig 0:796d0f61a05b 720 /**
HannesTschofenig 0:796d0f61a05b 721 * \brief Prime number generation
HannesTschofenig 0:796d0f61a05b 722 *
HannesTschofenig 0:796d0f61a05b 723 * \param X Destination MPI
HannesTschofenig 0:796d0f61a05b 724 * \param nbits Required size of X in bits
HannesTschofenig 0:796d0f61a05b 725 * ( 3 <= nbits <= POLARSSL_MPI_MAX_BITS )
HannesTschofenig 0:796d0f61a05b 726 * \param dh_flag If 1, then (X-1)/2 will be prime too
HannesTschofenig 0:796d0f61a05b 727 * \param f_rng RNG function
HannesTschofenig 0:796d0f61a05b 728 * \param p_rng RNG parameter
HannesTschofenig 0:796d0f61a05b 729 *
HannesTschofenig 0:796d0f61a05b 730 * \return 0 if successful (probably prime),
HannesTschofenig 0:796d0f61a05b 731 * POLARSSL_ERR_MPI_MALLOC_FAILED if memory allocation failed,
HannesTschofenig 0:796d0f61a05b 732 * POLARSSL_ERR_MPI_BAD_INPUT_DATA if nbits is < 3
HannesTschofenig 0:796d0f61a05b 733 */
HannesTschofenig 0:796d0f61a05b 734 int mpi_gen_prime( mpi *X, size_t nbits, int dh_flag,
HannesTschofenig 0:796d0f61a05b 735 int (*f_rng)(void *, unsigned char *, size_t),
HannesTschofenig 0:796d0f61a05b 736 void *p_rng );
HannesTschofenig 0:796d0f61a05b 737
HannesTschofenig 0:796d0f61a05b 738 /**
HannesTschofenig 0:796d0f61a05b 739 * \brief Checkup routine
HannesTschofenig 0:796d0f61a05b 740 *
HannesTschofenig 0:796d0f61a05b 741 * \return 0 if successful, or 1 if the test failed
HannesTschofenig 0:796d0f61a05b 742 */
HannesTschofenig 0:796d0f61a05b 743 int mpi_self_test( int verbose );
HannesTschofenig 0:796d0f61a05b 744
HannesTschofenig 0:796d0f61a05b 745 #ifdef __cplusplus
HannesTschofenig 0:796d0f61a05b 746 }
HannesTschofenig 0:796d0f61a05b 747 #endif
HannesTschofenig 0:796d0f61a05b 748
HannesTschofenig 0:796d0f61a05b 749 #endif /* bignum.h */
HannesTschofenig 0:796d0f61a05b 750
HannesTschofenig 0:796d0f61a05b 751