summaryrefslogtreecommitdiff
path: root/mpi
diff options
context:
space:
mode:
authorWerner Koch <wk@gnupg.org>2017-10-17 15:00:08 +0200
committerWerner Koch <wk@gnupg.org>2017-10-17 15:02:33 +0200
commitc6e42e7ec3d1046969d783c443c13aad7cb61bb8 (patch)
tree25a50e8a5174be9244841fa96fe037185f23270f /mpi
parente4dc458b0b7dc9b8417a2177ef17822d9b9064ec (diff)
downloadlibgcrypt-c6e42e7ec3d1046969d783c443c13aad7cb61bb8.tar.gz
api: New function gcry_mpi_get_ui.
* src/gcrypt.h.in (gcry_mpi_get_ui): New. (mpi_get_ui): New macro. * src/libgcrypt.def, src/libgcrypt.vers: Add new function. * src/visibility.c (gcry_mpi_get_ui): New. * src/visibility.h: Mark that function. (gcry_mpi_get_ui): New. * mpi/mpiutil.c (MY_UINT_MAX): New macro. (_gcry_mpi_get_ui): Re-implemented. This function existed but was never imported or used. * tests/mpitests.c (test_maxsize): Add some test for this function. -- Note that in libgcrypt.def the cardinal 91 is used which was never used in the past. Signed-off-by: Werner Koch <wk@gnupg.org>
Diffstat (limited to 'mpi')
-rw-r--r--mpi/mpiutil.c43
1 files changed, 31 insertions, 12 deletions
diff --git a/mpi/mpiutil.c b/mpi/mpiutil.c
index 3ae84c30..9dde37fb 100644
--- a/mpi/mpiutil.c
+++ b/mpi/mpiutil.c
@@ -28,6 +28,21 @@
#include "mpi-internal.h"
#include "mod-source-info.h"
+
+#if SIZEOF_UNSIGNED_INT == 2
+# define MY_UINT_MAX 0xffff
+/* (visual check: 0123 ) */
+#elif SIZEOF_UNSIGNED_INT == 4
+# define MY_UINT_MAX 0xffffffff
+/* (visual check: 01234567 ) */
+#elif SIZEOF_UNSIGNED_INT == 8
+# define MY_UINT_MAX 0xffffffffffffffff
+/* (visual check: 0123456789abcdef ) */
+#else
+# error Need MY_UINT_MAX for this limb size
+#endif
+
+
/* Constants allocated right away at startup. */
static gcry_mpi_t constants[MPI_NUMBER_OF_CONSTANTS];
@@ -539,23 +554,27 @@ _gcry_mpi_set_ui (gcry_mpi_t w, unsigned long u)
return w;
}
+/* If U is non-negative and small enough store it as an unsigned int
+ * at W. If the value does not fit into an unsigned int or is
+ * negative return GPG_ERR_ERANGE. Note that we return an unsigned
+ * int so that the value can be used with the bit test functions; in
+ * contrast the other _ui functions take an unsigned long so that on
+ * some platforms they may accept a larger value. On error the value
+ * at U is not changed. */
gcry_err_code_t
-_gcry_mpi_get_ui (gcry_mpi_t w, unsigned long *u)
+_gcry_mpi_get_ui (unsigned int *w, gcry_mpi_t u)
{
- gcry_err_code_t err = GPG_ERR_NO_ERROR;
- unsigned long x = 0;
+ mpi_limb_t x;
- if (w->nlimbs > 1)
- err = GPG_ERR_TOO_LARGE;
- else if (w->nlimbs == 1)
- x = w->d[0];
- else
- x = 0;
+ if (u->nlimbs > 1 || u->sign)
+ return GPG_ERR_ERANGE;
- if (! err)
- *u = x;
+ x = (u->nlimbs == 1) ? u->d[0] : 0;
+ if (sizeof (x) > sizeof (unsigned int) && x > MY_UINT_MAX)
+ return GPG_ERR_ERANGE;
- return err;
+ *w = x;
+ return 0;
}