Coverage Report

Created: 2024-11-25 06:30

/src/nettle/gmp-glue.c
Line
Count
Source (jump to first uncovered line)
1
/* gmp-glue.c
2
3
   Copyright (C) 2013 Niels Möller
4
   Copyright (C) 2013 Red Hat
5
6
   This file is part of GNU Nettle.
7
8
   GNU Nettle is free software: you can redistribute it and/or
9
   modify it under the terms of either:
10
11
     * the GNU Lesser General Public License as published by the Free
12
       Software Foundation; either version 3 of the License, or (at your
13
       option) any later version.
14
15
   or
16
17
     * the GNU General Public License as published by the Free
18
       Software Foundation; either version 2 of the License, or (at your
19
       option) any later version.
20
21
   or both in parallel, as here.
22
23
   GNU Nettle is distributed in the hope that it will be useful,
24
   but WITHOUT ANY WARRANTY; without even the implied warranty of
25
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
26
   General Public License for more details.
27
28
   You should have received copies of the GNU General Public License and
29
   the GNU Lesser General Public License along with this program.  If
30
   not, see http://www.gnu.org/licenses/.
31
*/
32
33
#if HAVE_CONFIG_H
34
# include "config.h"
35
#endif
36
37
#include <assert.h>
38
#include <stdlib.h>
39
40
#include "gmp-glue.h"
41
42
#if NETTLE_USE_MINI_GMP
43
mp_limb_t
44
mpn_cnd_add_n (mp_limb_t cnd, mp_limb_t *rp,
45
         const mp_limb_t *ap, const mp_limb_t *bp, mp_size_t n)
46
{
47
  mp_limb_t cy, mask;
48
  mp_size_t  i;
49
50
  mask = -(mp_limb_t) (cnd != 0);
51
52
  for (i = 0, cy = 0; i < n; i++)
53
    {
54
      mp_limb_t rl = ap[i] + cy;
55
      mp_limb_t bl = bp[i] & mask;
56
      cy = (rl < cy);
57
      rl += bl;
58
      cy += (rl < bl);
59
      rp[i] = rl;
60
    }
61
  return cy;
62
}
63
64
mp_limb_t
65
mpn_cnd_sub_n (mp_limb_t cnd, mp_limb_t *rp,
66
         const mp_limb_t *ap, const mp_limb_t *bp, mp_size_t n)
67
{
68
  mp_limb_t cy, mask;
69
  mp_size_t  i;
70
71
  mask = -(mp_limb_t) (cnd != 0);
72
73
  for (i = 0, cy = 0; i < n; i++)
74
    {
75
      mp_limb_t al = ap[i];
76
      mp_limb_t bl = bp[i] & mask;
77
      mp_limb_t sl;
78
      sl = al - cy;
79
      cy = (al < cy) + (sl < bl);
80
      sl -= bl;
81
      rp[i] = sl;
82
    }
83
  return cy;
84
}
85
86
void
87
mpn_cnd_swap (mp_limb_t cnd, volatile mp_limb_t *ap, volatile mp_limb_t *bp, mp_size_t n)
88
{
89
  volatile mp_limb_t mask = - (mp_limb_t) (cnd != 0);
90
  mp_size_t i;
91
  for (i = 0; i < n; i++)
92
    {
93
      mp_limb_t a, b, t;
94
      a = ap[i];
95
      b = bp[i];
96
      t = (a ^ b) & mask;
97
      ap[i] = a ^ t;
98
      bp[i] = b ^ t;
99
    }
100
}
101
102
/* Copy the k'th element of the table out tn elements, each of size
103
   rn. Always read complete table. Similar to gmp's mpn_tabselect. */
104
void
105
mpn_sec_tabselect (volatile mp_limb_t *rp, volatile const mp_limb_t *table,
106
       mp_size_t rn, unsigned tn, unsigned k)
107
{
108
  volatile const mp_limb_t *end = table + tn * rn;
109
  volatile const mp_limb_t *p;
110
  mp_size_t i;
111
112
  assert (k < tn);
113
  for (p = table; p < end; p += rn, k--)
114
    {
115
      mp_limb_t mask = - (mp_limb_t) (k == 0);
116
      for (i = 0; i < rn; i++)
117
  rp[i] = (~mask & rp[i]) | (mask & p[i]);
118
    }
119
}
120
121
122
#endif /* NETTLE_USE_MINI_GMP */
123
124
int
125
sec_zero_p (const mp_limb_t *ap, mp_size_t n)
126
3.76k
{
127
3.76k
  volatile mp_limb_t w;
128
3.76k
  mp_size_t i;
129
130
19.2k
  for (i = 0, w = 0; i < n; i++)
131
15.4k
    w |= ap[i];
132
133
3.76k
  return is_zero_limb (w);
134
3.76k
}
135
136
/* Additional convenience functions. */
137
138
void
139
mpz_limbs_copy (mp_limb_t *xp, mpz_srcptr x, mp_size_t n)
140
20.4k
{
141
20.4k
  mp_size_t xn = mpz_size (x);
142
143
20.4k
  assert (xn <= n);
144
20.4k
  mpn_copyi (xp, mpz_limbs_read (x), xn);
145
20.4k
  if (xn < n)
146
33
    mpn_zero (xp + xn, n - xn);
147
20.4k
}
148
149
void
150
mpz_set_n (mpz_t r, const mp_limb_t *xp, mp_size_t xn)
151
1.10k
{
152
1.10k
  mpn_copyi (mpz_limbs_write (r, xn), xp, xn);
153
1.10k
  mpz_limbs_finish (r, xn);
154
1.10k
}
155
156
void
157
mpn_set_base256 (mp_limb_t *rp, mp_size_t rn,
158
     const uint8_t *xp, size_t xn)
159
13.9k
{
160
13.9k
  size_t xi;
161
13.9k
  mp_limb_t out;
162
13.9k
  unsigned bits;
163
1.23M
  for (xi = xn, out = bits = 0; xi > 0 && rn > 0; )
164
1.22M
    {
165
1.22M
      mp_limb_t in = xp[--xi];
166
1.22M
      out |= (in << bits) & GMP_NUMB_MASK;
167
1.22M
      bits += 8;
168
1.22M
      if (bits >= GMP_NUMB_BITS)
169
152k
  {
170
152k
    *rp++ = out;
171
152k
    rn--;
172
173
152k
    bits -= GMP_NUMB_BITS;
174
152k
    out = in >> (8 - bits);
175
152k
  }
176
1.22M
    }
177
13.9k
  if (rn > 0)
178
55
    {
179
55
      *rp++ = out;
180
55
      if (--rn > 0)
181
0
  mpn_zero (rp, rn);
182
55
    }
183
13.9k
}
184
185
void
186
mpn_set_base256_le (mp_limb_t *rp, mp_size_t rn,
187
        const uint8_t *xp, size_t xn)
188
13.6k
{
189
13.6k
  size_t xi;
190
13.6k
  mp_limb_t out;
191
13.6k
  unsigned bits;
192
614k
  for (xi = 0, out = bits = 0; xi < xn && rn > 0; )
193
600k
    {
194
600k
      mp_limb_t in = xp[xi++];
195
600k
      out |= (in << bits) & GMP_NUMB_MASK;
196
600k
      bits += 8;
197
600k
      if (bits >= GMP_NUMB_BITS)
198
75.1k
  {
199
75.1k
    *rp++ = out;
200
75.1k
    rn--;
201
202
75.1k
    bits -= GMP_NUMB_BITS;
203
75.1k
    out = in >> (8 - bits);
204
75.1k
  }
205
600k
    }
206
13.6k
  if (rn > 0)
207
0
    {
208
0
      *rp++ = out;
209
0
      if (--rn > 0)
210
0
  mpn_zero (rp, rn);
211
0
    }
212
13.6k
}
213
214
void
215
mpn_get_base256 (uint8_t *rp, size_t rn,
216
     const mp_limb_t *xp, mp_size_t xn)
217
49
{
218
49
  unsigned bits;
219
49
  mp_limb_t in;
220
12.2k
  for (bits = in = 0; xn > 0 && rn > 0; )
221
12.2k
    {
222
12.2k
      if (bits >= 8)
223
10.6k
  {
224
10.6k
    rp[--rn] = in;
225
10.6k
    in >>= 8;
226
10.6k
    bits -= 8;
227
10.6k
  }
228
1.56k
      else
229
1.56k
  {
230
1.56k
    uint8_t old = in;
231
1.56k
    in = *xp++;
232
1.56k
    xn--;
233
1.56k
    rp[--rn] = old | (in << bits);
234
1.56k
    in >>= (8 - bits);
235
1.56k
    bits += GMP_NUMB_BITS - 8;
236
1.56k
  }
237
12.2k
    }
238
392
  while (rn > 0)
239
343
    {
240
343
      rp[--rn] = in;
241
343
      in >>= 8;
242
343
    }
243
49
}
244
245
void
246
mpn_get_base256_le (uint8_t *rp, size_t rn,
247
        const mp_limb_t *xp, mp_size_t xn)
248
13.6k
{
249
13.6k
  unsigned bits;
250
13.6k
  mp_limb_t in;
251
518k
  for (bits = in = 0; xn > 0 && rn > 0; )
252
505k
    {
253
505k
      if (bits >= 8)
254
430k
  {
255
430k
    *rp++ = in;
256
430k
    rn--;
257
430k
    in >>= 8;
258
430k
    bits -= 8;
259
430k
  }
260
75.1k
      else
261
75.1k
  {
262
75.1k
    uint8_t old = in;
263
75.1k
    in = *xp++;
264
75.1k
    xn--;
265
75.1k
    *rp++ = old | (in << bits);
266
75.1k
    rn--;
267
75.1k
    in >>= (8 - bits);
268
75.1k
    bits += GMP_NUMB_BITS - 8;
269
75.1k
  }
270
505k
    }
271
116k
  while (rn > 0)
272
102k
    {
273
102k
      *rp++ = in;
274
102k
      rn--;
275
102k
      in >>= 8;
276
102k
    }
277
13.6k
}
278
279
mp_limb_t *
280
gmp_alloc_limbs (mp_size_t n)
281
26.9k
{
282
283
26.9k
  void *(*alloc_func)(size_t);
284
285
26.9k
  assert (n > 0);
286
287
26.9k
  mp_get_memory_functions (&alloc_func, NULL, NULL);
288
26.9k
  return (mp_limb_t *) alloc_func ( (size_t) n * sizeof(mp_limb_t));
289
26.9k
}
290
291
void
292
gmp_free_limbs (mp_limb_t *p, mp_size_t n)
293
26.9k
{
294
26.9k
  void (*free_func)(void *, size_t);
295
26.9k
  assert (n > 0);
296
26.9k
  assert (p != 0);
297
26.9k
  mp_get_memory_functions (NULL, NULL, &free_func);
298
299
26.9k
  free_func (p, (size_t) n * sizeof(mp_limb_t));
300
26.9k
}
301
302
void *
303
gmp_alloc(size_t n)
304
39.1k
{
305
39.1k
  void *(*alloc_func)(size_t);
306
39.1k
  assert (n > 0);
307
308
39.1k
  mp_get_memory_functions(&alloc_func, NULL, NULL);
309
310
39.1k
  return alloc_func (n);
311
39.1k
}
312
313
void
314
gmp_free(void *p, size_t n)
315
39.1k
{
316
39.1k
  void (*free_func)(void *, size_t);
317
39.1k
  assert (n > 0);
318
39.1k
  assert (p != 0);
319
39.1k
  mp_get_memory_functions (NULL, NULL, &free_func);
320
321
39.1k
  free_func (p, (size_t) n);
322
39.1k
}