Add qemu 2.4.0
[kvmfornfv.git] / qemu / roms / ipxe / src / include / ipxe / bigint.h
diff --git a/qemu/roms/ipxe/src/include/ipxe/bigint.h b/qemu/roms/ipxe/src/include/ipxe/bigint.h
new file mode 100644 (file)
index 0000000..97fbce2
--- /dev/null
@@ -0,0 +1,301 @@
+#ifndef _IPXE_BIGINT_H
+#define _IPXE_BIGINT_H
+
+/** @file
+ *
+ * Big integer support
+ */
+
+FILE_LICENCE ( GPL2_OR_LATER );
+
+/**
+ * Define a big-integer type
+ *
+ * @v size             Number of elements
+ * @ret bigint_t       Big integer type
+ */
+#define bigint_t( size )                                               \
+       struct {                                                        \
+               bigint_element_t element[ (size) ];                     \
+       }
+
+/**
+ * Determine number of elements required for a big-integer type
+ *
+ * @v len              Maximum length of big integer, in bytes
+ * @ret size           Number of elements
+ */
+#define bigint_required_size( len )                                    \
+       ( ( (len) + sizeof ( bigint_element_t ) - 1 ) /                 \
+         sizeof ( bigint_element_t ) )
+
+/**
+ * Determine number of elements in big-integer type
+ *
+ * @v bigint           Big integer
+ * @ret size           Number of elements
+ */
+#define bigint_size( bigint )                                          \
+       ( sizeof ( *(bigint) ) / sizeof ( (bigint)->element[0] ) )
+
+/**
+ * Initialise big integer
+ *
+ * @v value            Big integer to initialise
+ * @v data             Raw data
+ * @v len              Length of raw data
+ */
+#define bigint_init( value, data, len ) do {                           \
+       unsigned int size = bigint_size (value);                        \
+       assert ( (len) <= ( size * sizeof ( (value)->element[0] ) ) );  \
+       bigint_init_raw ( (value)->element, size, (data), (len) );      \
+       } while ( 0 )
+
+/**
+ * Finalise big integer
+ *
+ * @v value            Big integer to finalise
+ * @v out              Output buffer
+ * @v len              Length of output buffer
+ */
+#define bigint_done( value, out, len ) do {                            \
+       unsigned int size = bigint_size (value);                        \
+       bigint_done_raw ( (value)->element, size, (out), (len) );       \
+       } while ( 0 )
+
+/**
+ * Add big integers
+ *
+ * @v addend           Big integer to add
+ * @v value            Big integer to be added to
+ */
+#define bigint_add( addend, value ) do {                               \
+       unsigned int size = bigint_size (addend);                       \
+       bigint_add_raw ( (addend)->element, (value)->element, size );   \
+       } while ( 0 )
+
+/**
+ * Subtract big integers
+ *
+ * @v subtrahend       Big integer to subtract
+ * @v value            Big integer to be subtracted from
+ */
+#define bigint_subtract( subtrahend, value ) do {                      \
+       unsigned int size = bigint_size (subtrahend);                   \
+       bigint_subtract_raw ( (subtrahend)->element, (value)->element,  \
+                             size );                                   \
+       } while ( 0 )
+
+/**
+ * Rotate big integer left
+ *
+ * @v value            Big integer
+ */
+#define bigint_rol( value ) do {                                       \
+       unsigned int size = bigint_size (value);                        \
+       bigint_rol_raw ( (value)->element, size );                      \
+       } while ( 0 )
+
+/**
+ * Rotate big integer right
+ *
+ * @v value            Big integer
+ */
+#define bigint_ror( value ) do {                                       \
+       unsigned int size = bigint_size (value);                        \
+       bigint_ror_raw ( (value)->element, size );                      \
+       } while ( 0 )
+
+/**
+ * Test if big integer is equal to zero
+ *
+ * @v value            Big integer
+ * @v size             Number of elements
+ * @ret is_zero                Big integer is equal to zero
+ */
+#define bigint_is_zero( value ) ( {                                    \
+       unsigned int size = bigint_size (value);                        \
+       bigint_is_zero_raw ( (value)->element, size ); } )
+
+/**
+ * Compare big integers
+ *
+ * @v value            Big integer
+ * @v reference                Reference big integer
+ * @ret geq            Big integer is greater than or equal to the reference
+ */
+#define bigint_is_geq( value, reference ) ( {                          \
+       unsigned int size = bigint_size (value);                        \
+       bigint_is_geq_raw ( (value)->element, (reference)->element,     \
+                           size ); } )
+
+/**
+ * Test if bit is set in big integer
+ *
+ * @v value            Big integer
+ * @v bit              Bit to test
+ * @ret is_set         Bit is set
+ */
+#define bigint_bit_is_set( value, bit ) ( {                            \
+       unsigned int size = bigint_size (value);                        \
+       bigint_bit_is_set_raw ( (value)->element, size, bit ); } )
+
+/**
+ * Find highest bit set in big integer
+ *
+ * @v value            Big integer
+ * @ret max_bit                Highest bit set + 1 (or 0 if no bits set)
+ */
+#define bigint_max_set_bit( value ) ( {                                        \
+       unsigned int size = bigint_size (value);                        \
+       bigint_max_set_bit_raw ( (value)->element, size ); } )
+
+/**
+ * Grow big integer
+ *
+ * @v source           Source big integer
+ * @v dest             Destination big integer
+ */
+#define bigint_grow( source, dest ) do {                               \
+       unsigned int source_size = bigint_size (source);                \
+       unsigned int dest_size = bigint_size (dest);                    \
+       bigint_grow_raw ( (source)->element, source_size,               \
+                         (dest)->element, dest_size );                 \
+       } while ( 0 )
+
+/**
+ * Shrink big integer
+ *
+ * @v source           Source big integer
+ * @v dest             Destination big integer
+ */
+#define bigint_shrink( source, dest ) do {                             \
+       unsigned int source_size = bigint_size (source);                \
+       unsigned int dest_size = bigint_size (dest);                    \
+       bigint_shrink_raw ( (source)->element, source_size,             \
+                           (dest)->element, dest_size );               \
+       } while ( 0 )
+
+/**
+ * Multiply big integers
+ *
+ * @v multiplicand     Big integer to be multiplied
+ * @v multiplier       Big integer to be multiplied
+ * @v result           Big integer to hold result
+ */
+#define bigint_multiply( multiplicand, multiplier, result ) do {       \
+       unsigned int size = bigint_size (multiplicand);                 \
+       bigint_multiply_raw ( (multiplicand)->element,                  \
+                             (multiplier)->element, (result)->element, \
+                             size );                                   \
+       } while ( 0 )
+
+/**
+ * Perform modular multiplication of big integers
+ *
+ * @v multiplicand     Big integer to be multiplied
+ * @v multiplier       Big integer to be multiplied
+ * @v modulus          Big integer modulus
+ * @v result           Big integer to hold result
+ * @v tmp              Temporary working space
+ */
+#define bigint_mod_multiply( multiplicand, multiplier, modulus,                \
+                            result, tmp ) do {                         \
+       unsigned int size = bigint_size (multiplicand);                 \
+       bigint_mod_multiply_raw ( (multiplicand)->element,              \
+                                 (multiplier)->element,                \
+                                 (modulus)->element,                   \
+                                 (result)->element, size, tmp );       \
+       } while ( 0 )
+
+/**
+ * Calculate temporary working space required for moduluar multiplication
+ *
+ * @v modulus          Big integer modulus
+ * @ret len            Length of temporary working space
+ */
+#define bigint_mod_multiply_tmp_len( modulus ) ( {                     \
+       unsigned int size = bigint_size (modulus);                      \
+       sizeof ( struct {                                               \
+               bigint_t ( size * 2 ) temp_result;                      \
+               bigint_t ( size * 2 ) temp_modulus;                     \
+       } ); } )
+
+/**
+ * Perform modular exponentiation of big integers
+ *
+ * @v base             Big integer base
+ * @v modulus          Big integer modulus
+ * @v exponent         Big integer exponent
+ * @v result           Big integer to hold result
+ * @v tmp              Temporary working space
+ */
+#define bigint_mod_exp( base, modulus, exponent, result, tmp ) do {    \
+       unsigned int size = bigint_size (base);                         \
+       unsigned int exponent_size = bigint_size (exponent);            \
+       bigint_mod_exp_raw ( (base)->element, (modulus)->element,       \
+                            (exponent)->element, (result)->element,    \
+                            size, exponent_size, tmp );                \
+       } while ( 0 )
+
+/**
+ * Calculate temporary working space required for moduluar exponentiation
+ *
+ * @v modulus          Big integer modulus
+ * @v exponent         Big integer exponent
+ * @ret len            Length of temporary working space
+ */
+#define bigint_mod_exp_tmp_len( modulus, exponent ) ( {                        \
+       unsigned int size = bigint_size (modulus);                      \
+       unsigned int exponent_size = bigint_size (exponent);            \
+       size_t mod_multiply_len =                                       \
+               bigint_mod_multiply_tmp_len (modulus);                  \
+       sizeof ( struct {                                               \
+               bigint_t ( size ) temp_base;                            \
+               bigint_t ( exponent_size ) temp_exponent;               \
+               uint8_t mod_multiply[mod_multiply_len];                 \
+       } ); } )
+
+#include <bits/bigint.h>
+
+void bigint_init_raw ( bigint_element_t *value0, unsigned int size,
+                      const void *data, size_t len );
+void bigint_done_raw ( const bigint_element_t *value0, unsigned int size,
+                      void *out, size_t len );
+void bigint_add_raw ( const bigint_element_t *addend0,
+                     bigint_element_t *value0, unsigned int size );
+void bigint_subtract_raw ( const bigint_element_t *subtrahend0,
+                          bigint_element_t *value0, unsigned int size );
+void bigint_rol_raw ( bigint_element_t *value0, unsigned int size );
+void bigint_ror_raw ( bigint_element_t *value0, unsigned int size );
+int bigint_is_zero_raw ( const bigint_element_t *value0, unsigned int size );
+int bigint_is_geq_raw ( const bigint_element_t *value0,
+                       const bigint_element_t *reference0,
+                       unsigned int size );
+int bigint_bit_is_set_raw ( const bigint_element_t *value0, unsigned int size,
+                           unsigned int bit );
+int bigint_max_set_bit_raw ( const bigint_element_t *value0,
+                            unsigned int size );
+void bigint_grow_raw ( const bigint_element_t *source0,
+                      unsigned int source_size, bigint_element_t *dest0,
+                      unsigned int dest_size );
+void bigint_shrink_raw ( const bigint_element_t *source0,
+                        unsigned int source_size, bigint_element_t *dest0,
+                        unsigned int dest_size );
+void bigint_multiply_raw ( const bigint_element_t *multiplicand0,
+                          const bigint_element_t *multiplier0,
+                          bigint_element_t *result0,
+                          unsigned int size );
+void bigint_mod_multiply_raw ( const bigint_element_t *multiplicand0,
+                              const bigint_element_t *multiplier0,
+                              const bigint_element_t *modulus0,
+                              bigint_element_t *result0,
+                              unsigned int size, void *tmp );
+void bigint_mod_exp_raw ( const bigint_element_t *base0,
+                         const bigint_element_t *modulus0,
+                         const bigint_element_t *exponent0,
+                         bigint_element_t *result0,
+                         unsigned int size, unsigned int exponent_size,
+                         void *tmp );
+
+#endif /* _IPXE_BIGINT_H */