Branch data Line data Source code
1 : : /*
2 : : * This file is part of the MicroPython project, http://micropython.org/
3 : : *
4 : : * The MIT License (MIT)
5 : : *
6 : : * Copyright (c) 2013, 2014 Damien P. George
7 : : *
8 : : * Permission is hereby granted, free of charge, to any person obtaining a copy
9 : : * of this software and associated documentation files (the "Software"), to deal
10 : : * in the Software without restriction, including without limitation the rights
11 : : * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
12 : : * copies of the Software, and to permit persons to whom the Software is
13 : : * furnished to do so, subject to the following conditions:
14 : : *
15 : : * The above copyright notice and this permission notice shall be included in
16 : : * all copies or substantial portions of the Software.
17 : : *
18 : : * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 : : * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 : : * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
21 : : * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22 : : * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23 : : * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
24 : : * THE SOFTWARE.
25 : : */
26 : :
27 : : #include <string.h>
28 : : #include <stdio.h>
29 : : #include <assert.h>
30 : :
31 : : #include "py/parsenumbase.h"
32 : : #include "py/smallint.h"
33 : : #include "py/objint.h"
34 : : #include "py/runtime.h"
35 : :
36 : : #if MICROPY_PY_BUILTINS_FLOAT
37 : : #include <math.h>
38 : : #endif
39 : :
40 : : #if MICROPY_LONGINT_IMPL == MICROPY_LONGINT_IMPL_MPZ
41 : :
42 : : #if MICROPY_PY_SYS_MAXSIZE
43 : : // Export value for sys.maxsize
44 : : // *FORMAT-OFF*
45 : : #define DIG_MASK ((MPZ_LONG_1 << MPZ_DIG_SIZE) - 1)
46 : : STATIC const mpz_dig_t maxsize_dig[] = {
47 : : #define NUM_DIG 1
48 : : (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 0) & DIG_MASK,
49 : : #if (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 0) > DIG_MASK
50 : : #undef NUM_DIG
51 : : #define NUM_DIG 2
52 : : (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 1) & DIG_MASK,
53 : : #if (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 1) > DIG_MASK
54 : : #undef NUM_DIG
55 : : #define NUM_DIG 3
56 : : (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 2) & DIG_MASK,
57 : : #if (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 2) > DIG_MASK
58 : : #undef NUM_DIG
59 : : #define NUM_DIG 4
60 : : (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 3) & DIG_MASK,
61 : : #if (MP_SSIZE_MAX >> MPZ_DIG_SIZE * 3) > DIG_MASK
62 : : #error cannot encode MP_SSIZE_MAX as mpz
63 : : #endif
64 : : #endif
65 : : #endif
66 : : #endif
67 : : };
68 : : // *FORMAT-ON*
69 : : const mp_obj_int_t mp_sys_maxsize_obj = {
70 : : {&mp_type_int},
71 : : {.fixed_dig = 1, .len = NUM_DIG, .alloc = NUM_DIG, .dig = (mpz_dig_t *)maxsize_dig}
72 : : };
73 : : #undef DIG_MASK
74 : : #undef NUM_DIG
75 : : #endif
76 : :
77 : 32234 : mp_obj_int_t *mp_obj_int_new_mpz(void) {
78 : 32234 : mp_obj_int_t *o = mp_obj_malloc(mp_obj_int_t, &mp_type_int);
79 : 32234 : mpz_init_zero(&o->mpz);
80 : 32234 : return o;
81 : : }
82 : :
83 : : // This routine expects you to pass in a buffer and size (in *buf and buf_size).
84 : : // If, for some reason, this buffer is too small, then it will allocate a
85 : : // buffer and return the allocated buffer and size in *buf and *buf_size. It
86 : : // is the callers responsibility to free this allocated buffer.
87 : : //
88 : : // The resulting formatted string will be returned from this function and the
89 : : // formatted size will be in *fmt_size.
90 : : //
91 : : // This particular routine should only be called for the mpz representation of the int.
92 : 41074 : char *mp_obj_int_formatted_impl(char **buf, size_t *buf_size, size_t *fmt_size, mp_const_obj_t self_in,
93 : : int base, const char *prefix, char base_char, char comma) {
94 [ + - - + ]: 41074 : assert(mp_obj_is_exact_type(self_in, &mp_type_int));
95 : 41074 : const mp_obj_int_t *self = MP_OBJ_TO_PTR(self_in);
96 : :
97 : 41074 : size_t needed_size = mp_int_format_size(mpz_max_num_bits(&self->mpz), base, prefix, comma);
98 [ + + ]: 41074 : if (needed_size > *buf_size) {
99 : 12908 : *buf = m_new(char, needed_size);
100 : 12908 : *buf_size = needed_size;
101 : : }
102 : 41074 : char *str = *buf;
103 : :
104 : 41074 : *fmt_size = mpz_as_str_inpl(&self->mpz, base, prefix, base_char, comma, str);
105 : :
106 : 41074 : return str;
107 : : }
108 : :
109 : 16 : mp_obj_t mp_obj_int_from_bytes_impl(bool big_endian, size_t len, const byte *buf) {
110 : 16 : mp_obj_int_t *o = mp_obj_int_new_mpz();
111 : 16 : mpz_set_from_bytes(&o->mpz, big_endian, len, buf);
112 : 16 : return MP_OBJ_FROM_PTR(o);
113 : : }
114 : :
115 : 72 : void mp_obj_int_to_bytes_impl(mp_obj_t self_in, bool big_endian, size_t len, byte *buf) {
116 [ + - - + ]: 72 : assert(mp_obj_is_exact_type(self_in, &mp_type_int));
117 : 72 : mp_obj_int_t *self = MP_OBJ_TO_PTR(self_in);
118 : 72 : mpz_as_bytes(&self->mpz, big_endian, len, buf);
119 : 72 : }
120 : :
121 : 79291 : int mp_obj_int_sign(mp_obj_t self_in) {
122 [ + + ]: 79291 : if (mp_obj_is_small_int(self_in)) {
123 : 74801 : mp_int_t val = MP_OBJ_SMALL_INT_VALUE(self_in);
124 [ + + ]: 74801 : if (val < 0) {
125 : : return -1;
126 [ + + ]: 73945 : } else if (val > 0) {
127 : : return 1;
128 : : } else {
129 : 37353 : return 0;
130 : : }
131 : : }
132 : 4490 : mp_obj_int_t *self = MP_OBJ_TO_PTR(self_in);
133 [ + + ]: 4490 : if (self->mpz.len == 0) {
134 : : return 0;
135 [ + + ]: 4480 : } else if (self->mpz.neg == 0) {
136 : : return 1;
137 : : } else {
138 : 2 : return -1;
139 : : }
140 : : }
141 : :
142 : 1496 : mp_obj_t mp_obj_int_unary_op(mp_unary_op_t op, mp_obj_t o_in) {
143 : 1496 : mp_obj_int_t *o = MP_OBJ_TO_PTR(o_in);
144 [ + + + + : 1496 : switch (op) {
+ + + ]
145 : 814 : case MP_UNARY_OP_BOOL:
146 [ + + ]: 814 : return mp_obj_new_bool(!mpz_is_zero(&o->mpz));
147 : 12 : case MP_UNARY_OP_HASH:
148 : 12 : return MP_OBJ_NEW_SMALL_INT(mpz_hash(&o->mpz));
149 : : case MP_UNARY_OP_POSITIVE:
150 : : return o_in;
151 : 580 : case MP_UNARY_OP_NEGATIVE: { mp_obj_int_t *o2 = mp_obj_int_new_mpz();
152 : 580 : mpz_neg_inpl(&o2->mpz, &o->mpz);
153 : 580 : return MP_OBJ_FROM_PTR(o2);
154 : : }
155 : 72 : case MP_UNARY_OP_INVERT: { mp_obj_int_t *o2 = mp_obj_int_new_mpz();
156 : 72 : mpz_not_inpl(&o2->mpz, &o->mpz);
157 : 72 : return MP_OBJ_FROM_PTR(o2);
158 : : }
159 : 10 : case MP_UNARY_OP_ABS: {
160 : 10 : mp_obj_int_t *self = MP_OBJ_TO_PTR(o_in);
161 [ + + ]: 10 : if (self->mpz.neg == 0) {
162 : : return o_in;
163 : : }
164 : 6 : mp_obj_int_t *self2 = mp_obj_int_new_mpz();
165 : 6 : mpz_abs_inpl(&self2->mpz, &self->mpz);
166 : 6 : return MP_OBJ_FROM_PTR(self2);
167 : : }
168 : 4 : default:
169 : 4 : return MP_OBJ_NULL; // op not supported
170 : : }
171 : : }
172 : :
173 : 43525 : mp_obj_t mp_obj_int_binary_op(mp_binary_op_t op, mp_obj_t lhs_in, mp_obj_t rhs_in) {
174 : 43525 : const mpz_t *zlhs;
175 : 43525 : const mpz_t *zrhs;
176 : 43525 : mpz_t z_int;
177 : 43525 : mpz_dig_t z_int_dig[MPZ_NUM_DIG_FOR_INT];
178 : :
179 : : // lhs could be a small int (eg small-int + mpz)
180 [ + + ]: 43525 : if (mp_obj_is_small_int(lhs_in)) {
181 : 1721 : mpz_init_fixed_from_int(&z_int, z_int_dig, MPZ_NUM_DIG_FOR_INT, MP_OBJ_SMALL_INT_VALUE(lhs_in));
182 : 1721 : zlhs = &z_int;
183 : : } else {
184 [ + - - + ]: 41804 : assert(mp_obj_is_exact_type(lhs_in, &mp_type_int));
185 : 41804 : zlhs = &((mp_obj_int_t *)MP_OBJ_TO_PTR(lhs_in))->mpz;
186 : : }
187 : :
188 : : // if rhs is small int, then lhs was not (otherwise mp_binary_op handles it)
189 [ + + ]: 43525 : if (mp_obj_is_small_int(rhs_in)) {
190 : 26796 : mpz_init_fixed_from_int(&z_int, z_int_dig, MPZ_NUM_DIG_FOR_INT, MP_OBJ_SMALL_INT_VALUE(rhs_in));
191 : 26796 : zrhs = &z_int;
192 [ + + + + ]: 16729 : } else if (mp_obj_is_exact_type(rhs_in, &mp_type_int)) {
193 : 16250 : zrhs = &((mp_obj_int_t *)MP_OBJ_TO_PTR(rhs_in))->mpz;
194 : : #if MICROPY_PY_BUILTINS_FLOAT
195 [ - + - + : 479 : } else if (mp_obj_is_float(rhs_in)) {
- + - + +
+ + + ]
196 : 8 : return mp_obj_float_binary_op(op, mpz_as_float(zlhs), rhs_in);
197 : : #endif
198 : : #if MICROPY_PY_BUILTINS_COMPLEX
199 [ - + - + : 471 : } else if (mp_obj_is_type(rhs_in, &mp_type_complex)) {
- + - + +
+ + + ]
200 : 4 : return mp_obj_complex_binary_op(op, mpz_as_float(zlhs), 0, rhs_in);
201 : : #endif
202 : : } else {
203 : : // delegate to generic function to check for extra cases
204 : 467 : return mp_obj_int_binary_op_extra_cases(op, lhs_in, rhs_in);
205 : : }
206 : :
207 : : #if MICROPY_PY_BUILTINS_FLOAT
208 [ + + ]: 43046 : if (op == MP_BINARY_OP_TRUE_DIVIDE || op == MP_BINARY_OP_INPLACE_TRUE_DIVIDE) {
209 [ + + ]: 8 : if (mpz_is_zero(zrhs)) {
210 : 4 : goto zero_division_error;
211 : : }
212 : 4 : mp_float_t flhs = mpz_as_float(zlhs);
213 : 4 : mp_float_t frhs = mpz_as_float(zrhs);
214 : 4 : return mp_obj_new_float(flhs / frhs);
215 : : }
216 : : #endif
217 : :
218 [ + + ]: 43038 : if (op >= MP_BINARY_OP_INPLACE_OR && op < MP_BINARY_OP_CONTAINS) {
219 : 24606 : mp_obj_int_t *res = mp_obj_int_new_mpz();
220 : :
221 [ + + + + : 24606 : switch (op) {
+ + + + +
+ + + ]
222 : 1118 : case MP_BINARY_OP_ADD:
223 : : case MP_BINARY_OP_INPLACE_ADD:
224 : 1118 : mpz_add_inpl(&res->mpz, zlhs, zrhs);
225 : 1118 : break;
226 : 1110 : case MP_BINARY_OP_SUBTRACT:
227 : : case MP_BINARY_OP_INPLACE_SUBTRACT:
228 : 1110 : mpz_sub_inpl(&res->mpz, zlhs, zrhs);
229 : 1110 : break;
230 : 6366 : case MP_BINARY_OP_MULTIPLY:
231 : : case MP_BINARY_OP_INPLACE_MULTIPLY:
232 : 6366 : mpz_mul_inpl(&res->mpz, zlhs, zrhs);
233 : 6366 : break;
234 : : case MP_BINARY_OP_FLOOR_DIVIDE:
235 : : case MP_BINARY_OP_INPLACE_FLOOR_DIVIDE: {
236 [ + + ]: 8928 : if (mpz_is_zero(zrhs)) {
237 : 4 : zero_division_error:
238 : 16 : mp_raise_msg(&mp_type_ZeroDivisionError, MP_ERROR_TEXT("divide by zero"));
239 : : }
240 : 8924 : mpz_t rem;
241 : 8924 : mpz_init_zero(&rem);
242 : 8924 : mpz_divmod_inpl(&res->mpz, &rem, zlhs, zrhs);
243 : 8924 : mpz_deinit(&rem);
244 : 8924 : break;
245 : : }
246 : : case MP_BINARY_OP_MODULO:
247 : : case MP_BINARY_OP_INPLACE_MODULO: {
248 [ + + ]: 496 : if (mpz_is_zero(zrhs)) {
249 : 4 : goto zero_division_error;
250 : : }
251 : 492 : mpz_t quo;
252 : 492 : mpz_init_zero(&quo);
253 : 492 : mpz_divmod_inpl(&quo, &res->mpz, zlhs, zrhs);
254 : 492 : mpz_deinit(&quo);
255 : 492 : break;
256 : : }
257 : :
258 : 1220 : case MP_BINARY_OP_AND:
259 : : case MP_BINARY_OP_INPLACE_AND:
260 : 1220 : mpz_and_inpl(&res->mpz, zlhs, zrhs);
261 : 1220 : break;
262 : 1148 : case MP_BINARY_OP_OR:
263 : : case MP_BINARY_OP_INPLACE_OR:
264 : 1148 : mpz_or_inpl(&res->mpz, zlhs, zrhs);
265 : 1148 : break;
266 : 1144 : case MP_BINARY_OP_XOR:
267 : : case MP_BINARY_OP_INPLACE_XOR:
268 : 1144 : mpz_xor_inpl(&res->mpz, zlhs, zrhs);
269 : 1144 : break;
270 : :
271 : 2660 : case MP_BINARY_OP_LSHIFT:
272 : : case MP_BINARY_OP_INPLACE_LSHIFT:
273 : : case MP_BINARY_OP_RSHIFT:
274 : : case MP_BINARY_OP_INPLACE_RSHIFT: {
275 : 2660 : mp_int_t irhs = mp_obj_int_get_checked(rhs_in);
276 [ + + ]: 2660 : if (irhs < 0) {
277 : 8 : mp_raise_ValueError(MP_ERROR_TEXT("negative shift count"));
278 : : }
279 [ + + ]: 2652 : if (op == MP_BINARY_OP_LSHIFT || op == MP_BINARY_OP_INPLACE_LSHIFT) {
280 : 1352 : mpz_shl_inpl(&res->mpz, zlhs, irhs);
281 : : } else {
282 : 1300 : mpz_shr_inpl(&res->mpz, zlhs, irhs);
283 : : }
284 : : break;
285 : : }
286 : :
287 : : case MP_BINARY_OP_POWER:
288 : : case MP_BINARY_OP_INPLACE_POWER:
289 [ + + ]: 388 : if (mpz_is_neg(zrhs)) {
290 : : #if MICROPY_PY_BUILTINS_FLOAT
291 : 8 : return mp_obj_float_binary_op(op, mpz_as_float(zlhs), rhs_in);
292 : : #else
293 : : mp_raise_ValueError(MP_ERROR_TEXT("negative power with no float support"));
294 : : #endif
295 : : }
296 : 380 : mpz_pow_inpl(&res->mpz, zlhs, zrhs);
297 : 380 : break;
298 : :
299 : : case MP_BINARY_OP_DIVMOD: {
300 [ + + ]: 20 : if (mpz_is_zero(zrhs)) {
301 : 4 : goto zero_division_error;
302 : : }
303 : 16 : mp_obj_int_t *quo = mp_obj_int_new_mpz();
304 : 16 : mpz_divmod_inpl(&quo->mpz, &res->mpz, zlhs, zrhs);
305 : 16 : mp_obj_t tuple[2] = {MP_OBJ_FROM_PTR(quo), MP_OBJ_FROM_PTR(res)};
306 : 16 : return mp_obj_new_tuple(2, tuple);
307 : : }
308 : :
309 : : default:
310 : : return MP_OBJ_NULL; // op not supported
311 : : }
312 : :
313 : 24554 : return MP_OBJ_FROM_PTR(res);
314 : :
315 : : } else {
316 : 18432 : int cmp = mpz_cmp(zlhs, zrhs);
317 [ + + + + : 18432 : switch (op) {
+ + ]
318 : 186 : case MP_BINARY_OP_LESS:
319 [ + + ]: 290 : return mp_obj_new_bool(cmp < 0);
320 : 7168 : case MP_BINARY_OP_MORE:
321 [ + + ]: 7268 : return mp_obj_new_bool(cmp > 0);
322 : 164 : case MP_BINARY_OP_LESS_EQUAL:
323 [ + + ]: 240 : return mp_obj_new_bool(cmp <= 0);
324 : 160 : case MP_BINARY_OP_MORE_EQUAL:
325 [ + + ]: 232 : return mp_obj_new_bool(cmp >= 0);
326 : 10742 : case MP_BINARY_OP_EQUAL:
327 [ + + ]: 20258 : return mp_obj_new_bool(cmp == 0);
328 : :
329 : : default:
330 : : return MP_OBJ_NULL; // op not supported
331 : : }
332 : : }
333 : : }
334 : :
335 : : #if MICROPY_PY_BUILTINS_POW3
336 : 144 : STATIC mpz_t *mp_mpz_for_int(mp_obj_t arg, mpz_t *temp) {
337 [ + + ]: 144 : if (mp_obj_is_small_int(arg)) {
338 : 96 : mpz_init_from_int(temp, MP_OBJ_SMALL_INT_VALUE(arg));
339 : 96 : return temp;
340 : : } else {
341 : 48 : mp_obj_int_t *arp_p = MP_OBJ_TO_PTR(arg);
342 : 48 : return &(arp_p->mpz);
343 : : }
344 : : }
345 : :
346 : 60 : mp_obj_t mp_obj_int_pow3(mp_obj_t base, mp_obj_t exponent, mp_obj_t modulus) {
347 [ + + + + : 60 : if (!mp_obj_is_int(base) || !mp_obj_is_int(exponent) || !mp_obj_is_int(modulus)) {
+ - + + +
+ + - + +
+ + - + ]
348 : 12 : mp_raise_TypeError(MP_ERROR_TEXT("pow() with 3 arguments requires integers"));
349 : : } else {
350 : 48 : mp_obj_t result = mp_obj_new_int_from_ull(0); // Use the _from_ull version as this forces an mpz int
351 : 48 : mp_obj_int_t *res_p = (mp_obj_int_t *)MP_OBJ_TO_PTR(result);
352 : :
353 : 48 : mpz_t l_temp, r_temp, m_temp;
354 : 48 : mpz_t *lhs = mp_mpz_for_int(base, &l_temp);
355 : 48 : mpz_t *rhs = mp_mpz_for_int(exponent, &r_temp);
356 : 48 : mpz_t *mod = mp_mpz_for_int(modulus, &m_temp);
357 : :
358 : 48 : mpz_pow3_inpl(&(res_p->mpz), lhs, rhs, mod);
359 : :
360 [ + + ]: 48 : if (lhs == &l_temp) {
361 : 36 : mpz_deinit(lhs);
362 : : }
363 [ + + ]: 48 : if (rhs == &r_temp) {
364 : 32 : mpz_deinit(rhs);
365 : : }
366 [ + + ]: 48 : if (mod == &m_temp) {
367 : 28 : mpz_deinit(mod);
368 : : }
369 : 48 : return result;
370 : : }
371 : : }
372 : : #endif
373 : :
374 : 121666 : mp_obj_t mp_obj_new_int(mp_int_t value) {
375 [ + + ]: 121666 : if (MP_SMALL_INT_FITS(value)) {
376 : 121662 : return MP_OBJ_NEW_SMALL_INT(value);
377 : : }
378 : 4 : return mp_obj_new_int_from_ll(value);
379 : : }
380 : :
381 : 1417 : mp_obj_t mp_obj_new_int_from_ll(long long val) {
382 : 1417 : mp_obj_int_t *o = mp_obj_int_new_mpz();
383 : 1417 : mpz_set_from_ll(&o->mpz, val, true);
384 : 1417 : return MP_OBJ_FROM_PTR(o);
385 : : }
386 : :
387 : 162 : mp_obj_t mp_obj_new_int_from_ull(unsigned long long val) {
388 : 162 : mp_obj_int_t *o = mp_obj_int_new_mpz();
389 : 162 : mpz_set_from_ll(&o->mpz, val, false);
390 : 162 : return MP_OBJ_FROM_PTR(o);
391 : : }
392 : :
393 : 1871 : mp_obj_t mp_obj_new_int_from_uint(mp_uint_t value) {
394 : : // SMALL_INT accepts only signed numbers, so make sure the input
395 : : // value fits completely in the small-int positive range.
396 [ + + ]: 1871 : if ((value & ~MP_SMALL_INT_POSITIVE_MASK) == 0) {
397 : 1811 : return MP_OBJ_NEW_SMALL_INT(value);
398 : : }
399 : 60 : return mp_obj_new_int_from_ull(value);
400 : : }
401 : :
402 : 903 : mp_obj_t mp_obj_new_int_from_str_len(const char **str, size_t len, bool neg, unsigned int base) {
403 : 903 : mp_obj_int_t *o = mp_obj_int_new_mpz();
404 : 903 : size_t n = mpz_set_from_str(&o->mpz, *str, len, neg, base);
405 : 903 : *str += n;
406 : 903 : return MP_OBJ_FROM_PTR(o);
407 : : }
408 : :
409 : 1776 : mp_int_t mp_obj_int_get_truncated(mp_const_obj_t self_in) {
410 [ + + ]: 1776 : if (mp_obj_is_small_int(self_in)) {
411 : 1772 : return MP_OBJ_SMALL_INT_VALUE(self_in);
412 : : } else {
413 : 4 : const mp_obj_int_t *self = MP_OBJ_TO_PTR(self_in);
414 : : // hash returns actual int value if it fits in mp_int_t
415 : 4 : return mpz_hash(&self->mpz);
416 : : }
417 : : }
418 : :
419 : 2730 : mp_int_t mp_obj_int_get_checked(mp_const_obj_t self_in) {
420 [ + + ]: 2730 : if (mp_obj_is_small_int(self_in)) {
421 : 2708 : return MP_OBJ_SMALL_INT_VALUE(self_in);
422 : : } else {
423 : 22 : const mp_obj_int_t *self = MP_OBJ_TO_PTR(self_in);
424 : 22 : mp_int_t value;
425 [ + + ]: 22 : if (mpz_as_int_checked(&self->mpz, &value)) {
426 : 18 : return value;
427 : : } else {
428 : : // overflow
429 : 4 : mp_raise_msg(&mp_type_OverflowError, MP_ERROR_TEXT("overflow converting long int to machine word"));
430 : : }
431 : : }
432 : : }
433 : :
434 : 8 : mp_uint_t mp_obj_int_get_uint_checked(mp_const_obj_t self_in) {
435 [ + + ]: 8 : if (mp_obj_is_small_int(self_in)) {
436 [ + + ]: 4 : if (MP_OBJ_SMALL_INT_VALUE(self_in) >= 0) {
437 : 2 : return MP_OBJ_SMALL_INT_VALUE(self_in);
438 : : }
439 : : } else {
440 : 4 : const mp_obj_int_t *self = MP_OBJ_TO_PTR(self_in);
441 : 4 : mp_uint_t value;
442 [ + + ]: 4 : if (mpz_as_uint_checked(&self->mpz, &value)) {
443 : 2 : return value;
444 : : }
445 : : }
446 : :
447 : 4 : mp_raise_msg(&mp_type_OverflowError, MP_ERROR_TEXT("overflow converting long int to machine word"));
448 : : }
449 : :
450 : : #if MICROPY_PY_BUILTINS_FLOAT
451 : 21624 : mp_float_t mp_obj_int_as_float_impl(mp_obj_t self_in) {
452 [ + - - + ]: 21624 : assert(mp_obj_is_exact_type(self_in, &mp_type_int));
453 : 21624 : mp_obj_int_t *self = MP_OBJ_TO_PTR(self_in);
454 : 21624 : return mpz_as_float(&self->mpz);
455 : : }
456 : : #endif
457 : :
458 : : #endif
|