Coveralls logob
Coveralls logo
  • Home
  • Features
  • Pricing
  • Docs
  • Sign In

micropython / micropython / 968087856

24 Jun 2021 - 13:25 coverage decreased (-0.01%) to 98.316%
968087856

Pull #7432

github

GitHub
Merge cd05e2c08 into b51ae20c0
Pull Request #7432: Rp2 rtc weekday

20605 of 20958 relevant lines covered (98.32%)

443512.7 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

99.25
/py/runtime.c
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
 * Copyright (c) 2014-2018 Paul Sokolovsky
8
 *
9
 * Permission is hereby granted, free of charge, to any person obtaining a copy
10
 * of this software and associated documentation files (the "Software"), to deal
11
 * in the Software without restriction, including without limitation the rights
12
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
13
 * copies of the Software, and to permit persons to whom the Software is
14
 * furnished to do so, subject to the following conditions:
15
 *
16
 * The above copyright notice and this permission notice shall be included in
17
 * all copies or substantial portions of the Software.
18
 *
19
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
20
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
21
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
22
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
23
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
24
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
25
 * THE SOFTWARE.
26
 */
27

28
#include <stdarg.h>
29
#include <stdio.h>
30
#include <string.h>
31
#include <assert.h>
32

33
#include "py/parsenum.h"
34
#include "py/compile.h"
35
#include "py/objstr.h"
36
#include "py/objtuple.h"
37
#include "py/objlist.h"
38
#include "py/objtype.h"
39
#include "py/objmodule.h"
40
#include "py/objgenerator.h"
41
#include "py/smallint.h"
42
#include "py/runtime.h"
43
#include "py/builtin.h"
44
#include "py/stackctrl.h"
45
#include "py/gc.h"
46

47
#if MICROPY_DEBUG_VERBOSE // print debugging info
48
#define DEBUG_PRINT (1)
49
#define DEBUG_printf DEBUG_printf
50
#define DEBUG_OP_printf(...) DEBUG_printf(__VA_ARGS__)
51
#else // don't print debugging info
52
#define DEBUG_printf(...) (void)0
53
#define DEBUG_OP_printf(...) (void)0
54
#endif
55

56
const mp_obj_module_t mp_module___main__ = {
57
    .base = { &mp_type_module },
58
    .globals = (mp_obj_dict_t *)&MP_STATE_VM(dict_main),
59
};
60

61
void mp_init(void) {
3,076×
62
    qstr_init();
3,076×
63

64
    // no pending exceptions to start with
65
    MP_STATE_THREAD(mp_pending_exception) = MP_OBJ_NULL;
3,076×
66
    #if MICROPY_ENABLE_SCHEDULER
67
    MP_STATE_VM(sched_state) = MP_SCHED_IDLE;
3,076×
68
    MP_STATE_VM(sched_idx) = 0;
3,076×
69
    MP_STATE_VM(sched_len) = 0;
3,076×
70
    #endif
71

72
    #if MICROPY_ENABLE_EMERGENCY_EXCEPTION_BUF
73
    mp_init_emergency_exception_buf();
3,076×
74
    #endif
75

76
    #if MICROPY_KBD_EXCEPTION
77
    // initialise the exception object for raising KeyboardInterrupt
78
    MP_STATE_VM(mp_kbd_exception).base.type = &mp_type_KeyboardInterrupt;
3,076×
79
    MP_STATE_VM(mp_kbd_exception).traceback_alloc = 0;
3,076×
80
    MP_STATE_VM(mp_kbd_exception).traceback_len = 0;
3,076×
81
    MP_STATE_VM(mp_kbd_exception).traceback_data = NULL;
3,076×
82
    MP_STATE_VM(mp_kbd_exception).args = (mp_obj_tuple_t *)&mp_const_empty_tuple_obj;
3,076×
83
    #endif
84

85
    #if MICROPY_ENABLE_COMPILER
86
    // optimization disabled by default
87
    MP_STATE_VM(mp_optimise_value) = 0;
3,076×
88
    #if MICROPY_EMIT_NATIVE
89
    MP_STATE_VM(default_emit_opt) = MP_EMIT_OPT_NONE;
3,076×
90
    #endif
91
    #endif
92

93
    // init global module dict
94
    mp_obj_dict_init(&MP_STATE_VM(mp_loaded_modules_dict), MICROPY_LOADED_MODULES_DICT_SIZE);
3,076×
95

96
    // initialise the __main__ module
97
    mp_obj_dict_init(&MP_STATE_VM(dict_main), 1);
3,076×
98
    mp_obj_dict_store(MP_OBJ_FROM_PTR(&MP_STATE_VM(dict_main)), MP_OBJ_NEW_QSTR(MP_QSTR___name__), MP_OBJ_NEW_QSTR(MP_QSTR___main__));
3,076×
99

100
    // locals = globals for outer module (see Objects/frameobject.c/PyFrame_New())
101
    mp_locals_set(&MP_STATE_VM(dict_main));
3,076×
102
    mp_globals_set(&MP_STATE_VM(dict_main));
3,076×
103

104
    #if MICROPY_CAN_OVERRIDE_BUILTINS
105
    // start with no extensions to builtins
106
    MP_STATE_VM(mp_module_builtins_override_dict) = NULL;
3,076×
107
    #endif
108

109
    #if MICROPY_PERSISTENT_CODE_TRACK_RELOC_CODE
110
    MP_STATE_VM(track_reloc_code_list) = MP_OBJ_NULL;
111
    #endif
112

113
    #if MICROPY_PY_OS_DUPTERM
114
    for (size_t i = 0; i < MICROPY_PY_OS_DUPTERM; ++i) {
115
        MP_STATE_VM(dupterm_objs[i]) = MP_OBJ_NULL;
116
    }
117
    #endif
118

119
    #if MICROPY_VFS
120
    // initialise the VFS sub-system
121
    MP_STATE_VM(vfs_cur) = NULL;
3,076×
122
    MP_STATE_VM(vfs_mount_table) = NULL;
3,076×
123
    #endif
124

125
    #if MICROPY_PY_SYS_ATEXIT
126
    MP_STATE_VM(sys_exitfunc) = mp_const_none;
3,076×
127
    #endif
128

129
    #if MICROPY_PY_SYS_SETTRACE
130
    MP_STATE_THREAD(prof_trace_callback) = MP_OBJ_NULL;
131
    MP_STATE_THREAD(prof_callback_is_executing) = false;
132
    MP_STATE_THREAD(current_code_state) = NULL;
133
    #endif
134

135
    #if MICROPY_PY_BLUETOOTH
136
    MP_STATE_VM(bluetooth) = MP_OBJ_NULL;
137
    #endif
138

139
    #if MICROPY_PY_THREAD_GIL
140
    mp_thread_mutex_init(&MP_STATE_VM(gil_mutex));
141
    #endif
142

143
    // call port specific initialization if any
144
    #ifdef MICROPY_PORT_INIT_FUNC
145
    MICROPY_PORT_INIT_FUNC;
146
    #endif
147

148
    MP_THREAD_GIL_ENTER();
149
}
3,076×
150

151
void mp_deinit(void) {
3,074×
152
    MP_THREAD_GIL_EXIT();
153

154
    // call port specific deinitialization if any
155
    #ifdef MICROPY_PORT_DEINIT_FUNC
156
    MICROPY_PORT_DEINIT_FUNC;
157
    #endif
158
}
3,074×
159

160
mp_obj_t mp_load_name(qstr qst) {
596,343×
161
    // logic: search locals, globals, builtins
162
    DEBUG_OP_printf("load name %s\n", qstr_str(qst));
163
    // If we're at the outer scope (locals == globals), dispatch to load_global right away
164
    if (mp_locals_get() != mp_globals_get()) {
596,343×
165
        mp_map_elem_t *elem = mp_map_lookup(&mp_locals_get()->map, MP_OBJ_NEW_QSTR(qst), MP_MAP_LOOKUP);
1,730×
166
        if (elem != NULL) {
1,730×
167
            return elem->value;
16×
168
        }
169
    }
170
    return mp_load_global(qst);
596,327×
171
}
172

173
mp_obj_t mp_load_global(qstr qst) {
1,725,210×
174
    // logic: search globals, builtins
175
    DEBUG_OP_printf("load global %s\n", qstr_str(qst));
176
    mp_map_elem_t *elem = mp_map_lookup(&mp_globals_get()->map, MP_OBJ_NEW_QSTR(qst), MP_MAP_LOOKUP);
1,725,210×
177
    if (elem == NULL) {
1,725,210×
178
        #if MICROPY_CAN_OVERRIDE_BUILTINS
179
        if (MP_STATE_VM(mp_module_builtins_override_dict) != NULL) {
693,981×
180
            // lookup in additional dynamic table of builtins first
181
            elem = mp_map_lookup(&MP_STATE_VM(mp_module_builtins_override_dict)->map, MP_OBJ_NEW_QSTR(qst), MP_MAP_LOOKUP);
210×
182
            if (elem != NULL) {
210×
183
                return elem->value;
8×
184
            }
185
        }
186
        #endif
187
        elem = mp_map_lookup((mp_map_t *)&mp_module_builtins_globals.map, MP_OBJ_NEW_QSTR(qst), MP_MAP_LOOKUP);
693,973×
188
        if (elem == NULL) {
693,973×
189
            #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
190
            mp_raise_msg(&mp_type_NameError, MP_ERROR_TEXT("name not defined"));
191
            #else
192
            mp_raise_msg_varg(&mp_type_NameError, MP_ERROR_TEXT("name '%q' isn't defined"), qst);
200×
193
            #endif
194
        }
195
    }
196
    return elem->value;
1,725,000×
197
}
198

199
mp_obj_t mp_load_build_class(void) {
1,488×
200
    DEBUG_OP_printf("load_build_class\n");
201
    #if MICROPY_CAN_OVERRIDE_BUILTINS
202
    if (MP_STATE_VM(mp_module_builtins_override_dict) != NULL) {
1,488×
203
        // lookup in additional dynamic table of builtins first
204
        mp_map_elem_t *elem = mp_map_lookup(&MP_STATE_VM(mp_module_builtins_override_dict)->map, MP_OBJ_NEW_QSTR(MP_QSTR___build_class__), MP_MAP_LOOKUP);
34×
205
        if (elem != NULL) {
34×
206
            return elem->value;
32×
207
        }
208
    }
209
    #endif
210
    return MP_OBJ_FROM_PTR(&mp_builtin___build_class___obj);
1,456×
211
}
212

213
void mp_store_name(qstr qst, mp_obj_t obj) {
739,852×
214
    DEBUG_OP_printf("store name %s <- %p\n", qstr_str(qst), obj);
215
    mp_obj_dict_store(MP_OBJ_FROM_PTR(mp_locals_get()), MP_OBJ_NEW_QSTR(qst), obj);
739,852×
216
}
739,850×
217

218
void mp_delete_name(qstr qst) {
453×
219
    DEBUG_OP_printf("delete name %s\n", qstr_str(qst));
220
    // TODO convert KeyError to NameError if qst not found
221
    mp_obj_dict_delete(MP_OBJ_FROM_PTR(mp_locals_get()), MP_OBJ_NEW_QSTR(qst));
453×
222
}
449×
223

224
void mp_store_global(qstr qst, mp_obj_t obj) {
111,092×
225
    DEBUG_OP_printf("store global %s <- %p\n", qstr_str(qst), obj);
226
    mp_obj_dict_store(MP_OBJ_FROM_PTR(mp_globals_get()), MP_OBJ_NEW_QSTR(qst), obj);
111,092×
227
}
111,092×
228

229
void mp_delete_global(qstr qst) {
8×
230
    DEBUG_OP_printf("delete global %s\n", qstr_str(qst));
231
    // TODO convert KeyError to NameError if qst not found
232
    mp_obj_dict_delete(MP_OBJ_FROM_PTR(mp_globals_get()), MP_OBJ_NEW_QSTR(qst));
8×
233
}
4×
234

235
mp_obj_t mp_unary_op(mp_unary_op_t op, mp_obj_t arg) {
730,483×
236
    DEBUG_OP_printf("unary " UINT_FMT " %q %p\n", op, mp_unary_op_method_name[op], arg);
237

238
    if (op == MP_UNARY_OP_NOT) {
730,483×
239
        // "not x" is the negative of whether "x" is true per Python semantics
240
        return mp_obj_new_bool(mp_obj_is_true(arg) == 0);
207,172×
241
    } else if (mp_obj_is_small_int(arg)) {
523,311×
242
        mp_int_t val = MP_OBJ_SMALL_INT_VALUE(arg);
396,057×
243
        switch (op) {
396,057×
244
            case MP_UNARY_OP_BOOL:
4×
245
                return mp_obj_new_bool(val != 0);
4×
246
            case MP_UNARY_OP_HASH:
394,080×
247
                return arg;
394,080×
248
            case MP_UNARY_OP_POSITIVE:
39×
249
            case MP_UNARY_OP_INT:
250
                return arg;
39×
251
            case MP_UNARY_OP_NEGATIVE:
1,740×
252
                // check for overflow
253
                if (val == MP_SMALL_INT_MIN) {
1,740×
254
                    return mp_obj_new_int(-val);
2×
255
                } else {
256
                    return MP_OBJ_NEW_SMALL_INT(-val);
1,738×
257
                }
258
            case MP_UNARY_OP_ABS:
64×
259
                if (val >= 0) {
64×
260
                    return arg;
30×
261
                } else if (val == MP_SMALL_INT_MIN) {
34×
262
                    // check for overflow
263
                    return mp_obj_new_int(-val);
2×
264
                } else {
265
                    return MP_OBJ_NEW_SMALL_INT(-val);
32×
266
                }
267
            default:
130×
268
                assert(op == MP_UNARY_OP_INVERT);
130×
269
                return MP_OBJ_NEW_SMALL_INT(~val);
130×
270
        }
271
    } else if (op == MP_UNARY_OP_HASH && mp_obj_is_str_or_bytes(arg)) {
127,254×
272
        // fast path for hashing str/bytes
273
        GET_STR_HASH(arg, h);
95,195×
274
        if (h == 0) {
95,195×
275
            GET_STR_DATA_LEN(arg, data, len);
4×
276
            h = qstr_compute_hash(data, len);
4×
277
        }
278
        return MP_OBJ_NEW_SMALL_INT(h);
95,195×
279
    } else {
280
        const mp_obj_type_t *type = mp_obj_get_type(arg);
32,059×
281
        if (type->unary_op != NULL) {
32,059×
282
            mp_obj_t result = type->unary_op(op, arg);
32,055×
283
            if (result != MP_OBJ_NULL) {
32,047×
284
                return result;
31,959×
285
            }
286
        }
287
        // With MP_UNARY_OP_INT, mp_unary_op() becomes a fallback for mp_obj_get_int().
288
        // In this case provide a more focused error message to not confuse, e.g. chr(1.0)
289
        #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
290
        if (op == MP_UNARY_OP_INT) {
291
            mp_raise_TypeError(MP_ERROR_TEXT("can't convert to int"));
292
        } else {
293
            mp_raise_TypeError(MP_ERROR_TEXT("unsupported type for operator"));
294
        }
295
        #else
296
        if (op == MP_UNARY_OP_INT) {
92×
297
            mp_raise_msg_varg(&mp_type_TypeError,
30×
298
                MP_ERROR_TEXT("can't convert %s to int"), mp_obj_get_type_str(arg));
30×
299
        } else {
300
            mp_raise_msg_varg(&mp_type_TypeError,
62×
301
                MP_ERROR_TEXT("unsupported type for %q: '%s'"),
62×
302
                mp_unary_op_method_name[op], mp_obj_get_type_str(arg));
62×
303
        }
304
        #endif
305
    }
306
}
307

308
mp_obj_t mp_binary_op(mp_binary_op_t op, mp_obj_t lhs, mp_obj_t rhs) {
43,802,300×
309
    DEBUG_OP_printf("binary " UINT_FMT " %q %p %p\n", op, mp_binary_op_method_name[op], lhs, rhs);
310

311
    // TODO correctly distinguish inplace operators for mutable objects
312
    // lookup logic that CPython uses for +=:
313
    //   check for implemented +=
314
    //   then check for implemented +
315
    //   then check for implemented seq.inplace_concat
316
    //   then check for implemented seq.concat
317
    //   then fail
318
    // note that list does not implement + or +=, so that inplace_concat is reached first for +=
319

320
    // deal with is
321
    if (op == MP_BINARY_OP_IS) {
43,802,300×
322
        return mp_obj_new_bool(lhs == rhs);
307,932×
323
    }
324

325
    // deal with == and != for all types
326
    if (op == MP_BINARY_OP_EQUAL || op == MP_BINARY_OP_NOT_EQUAL) {
43,494,400×
327
        // mp_obj_equal_not_equal supports a bunch of shortcuts
328
        return mp_obj_equal_not_equal(op, lhs, rhs);
!
329
    }
330

331
    // deal with exception_match for all types
332
    if (op == MP_BINARY_OP_EXCEPTION_MATCH) {
49,735,700×
333
        // rhs must be issubclass(rhs, BaseException)
334
        if (mp_obj_is_exception_type(rhs)) {
4,922×
335
            if (mp_obj_exception_match(lhs, rhs)) {
4,389×
336
                return mp_const_true;
4,135×
337
            } else {
338
                return mp_const_false;
254×
339
            }
340
        } else if (mp_obj_is_type(rhs, &mp_type_tuple)) {
533×
341
            mp_obj_tuple_t *tuple = MP_OBJ_TO_PTR(rhs);
529×
342
            for (size_t i = 0; i < tuple->len; i++) {
941×
343
                rhs = tuple->items[i];
937×
344
                if (!mp_obj_is_exception_type(rhs)) {
937×
345
                    goto unsupported_op;
4×
346
                }
347
                if (mp_obj_exception_match(lhs, rhs)) {
933×
348
                    return mp_const_true;
521×
349
                }
350
            }
351
            return mp_const_false;
4×
352
        }
353
        goto unsupported_op;
4×
354
    }
355

356
    if (mp_obj_is_small_int(lhs)) {
49,730,700×
357
        mp_int_t lhs_val = MP_OBJ_SMALL_INT_VALUE(lhs);
48,679,800×
358
        if (mp_obj_is_small_int(rhs)) {
48,679,800×
359
            mp_int_t rhs_val = MP_OBJ_SMALL_INT_VALUE(rhs);
57,737,100×
360
            // This is a binary operation: lhs_val op rhs_val
361
            // We need to be careful to handle overflow; see CERT INT32-C
362
            // Operations that can overflow:
363
            //      +       result always fits in mp_int_t, then handled by SMALL_INT check
364
            //      -       result always fits in mp_int_t, then handled by SMALL_INT check
365
            //      *       checked explicitly
366
            //      /       if lhs=MIN and rhs=-1; result always fits in mp_int_t, then handled by SMALL_INT check
367
            //      %       if lhs=MIN and rhs=-1; result always fits in mp_int_t, then handled by SMALL_INT check
368
            //      <<      checked explicitly
369
            switch (op) {
57,737,100×
370
                case MP_BINARY_OP_OR:
488×
371
                case MP_BINARY_OP_INPLACE_OR:
372
                    lhs_val |= rhs_val;
488×
373
                    break;
488×
374
                case MP_BINARY_OP_XOR:
13,285,700×
375
                case MP_BINARY_OP_INPLACE_XOR:
376
                    lhs_val ^= rhs_val;
13,285,700×
377
                    break;
13,285,700×
378
                case MP_BINARY_OP_AND:
6,212,690×
379
                case MP_BINARY_OP_INPLACE_AND:
380
                    lhs_val &= rhs_val;
6,212,690×
381
                    break;
6,212,690×
382
                case MP_BINARY_OP_LSHIFT:
4,397,210×
383
                case MP_BINARY_OP_INPLACE_LSHIFT: {
384
                    if (rhs_val < 0) {
4,397,210×
385
                        // negative shift not allowed
386
                        mp_raise_ValueError(MP_ERROR_TEXT("negative shift count"));
8×
387
                    } else if (rhs_val >= (mp_int_t)(sizeof(lhs_val) * MP_BITS_PER_BYTE)
4,397,200×
388
                               || lhs_val > (MP_SMALL_INT_MAX >> rhs_val)
4,428,900×
389
                               || lhs_val < (MP_SMALL_INT_MIN >> rhs_val)) {
4,672,200×
390
                        // left-shift will overflow, so use higher precision integer
UNCOV
391
                        lhs = mp_obj_new_int_from_ll(lhs_val);
!
392
                        goto generic_binary_op;
836×
393
                    } else {
394
                        // use standard precision
395
                        lhs_val = (mp_uint_t)lhs_val << rhs_val;
4,546,540×
396
                    }
397
                    break;
4,546,540×
398
                }
399
                case MP_BINARY_OP_RSHIFT:
1,000×
400
                case MP_BINARY_OP_INPLACE_RSHIFT:
401
                    if (rhs_val < 0) {
1,000×
402
                        // negative shift not allowed
403
                        mp_raise_ValueError(MP_ERROR_TEXT("negative shift count"));
4×
404
                    } else {
405
                        // standard precision is enough for right-shift
406
                        if (rhs_val >= (mp_int_t)(sizeof(lhs_val) * MP_BITS_PER_BYTE)) {
996×
407
                            // Shifting to big amounts is underfined behavior
408
                            // in C and is CPU-dependent; propagate sign bit.
409
                            rhs_val = sizeof(lhs_val) * MP_BITS_PER_BYTE - 1;
12×
410
                        }
411
                        lhs_val >>= rhs_val;
996×
412
                    }
413
                    break;
996×
414
                case MP_BINARY_OP_ADD:
14,954,300×
415
                case MP_BINARY_OP_INPLACE_ADD:
416
                    lhs_val += rhs_val;
14,954,300×
417
                    break;
14,954,300×
418
                case MP_BINARY_OP_SUBTRACT:
94,186×
419
                case MP_BINARY_OP_INPLACE_SUBTRACT:
420
                    lhs_val -= rhs_val;
94,186×
421
                    break;
94,186×
422
                case MP_BINARY_OP_MULTIPLY:
3,152,110×
423
                case MP_BINARY_OP_INPLACE_MULTIPLY: {
424

425
                    // If long long type exists and is larger than mp_int_t, then
426
                    // we can use the following code to perform overflow-checked multiplication.
427
                    // Otherwise (eg in x64 case) we must use mp_small_int_mul_overflow.
428
                    #if 0
429
                    // compute result using long long precision
430
                    long long res = (long long)lhs_val * (long long)rhs_val;
431
                    if (res > MP_SMALL_INT_MAX || res < MP_SMALL_INT_MIN) {
432
                        // result overflowed SMALL_INT, so return higher precision integer
433
                        return mp_obj_new_int_from_ll(res);
434
                    } else {
435
                        // use standard precision
436
                        lhs_val = (mp_int_t)res;
437
                    }
438
                    #endif
439

440
                    if (mp_small_int_mul_overflow(lhs_val, rhs_val)) {
3,152,110×
441
                        // use higher precision
442
                        lhs = mp_obj_new_int_from_ll(lhs_val);
!
443
                        goto generic_binary_op;
147×
444
                    } else {
445
                        // use standard precision
446
                        return MP_OBJ_NEW_SMALL_INT(lhs_val * rhs_val);
3,206,620×
447
                    }
448
                }
449
                case MP_BINARY_OP_FLOOR_DIVIDE:
5,640×
450
                case MP_BINARY_OP_INPLACE_FLOOR_DIVIDE:
451
                    if (rhs_val == 0) {
5,640×
452
                        goto zero_division;
9×
453
                    }
454
                    lhs_val = mp_small_int_floor_divide(lhs_val, rhs_val);
5,631×
455
                    break;
5,631×
456

457
                #if MICROPY_PY_BUILTINS_FLOAT
458
                case MP_BINARY_OP_TRUE_DIVIDE:
244×
459
                case MP_BINARY_OP_INPLACE_TRUE_DIVIDE:
460
                    if (rhs_val == 0) {
244×
461
                        goto zero_division;
60×
462
                    }
463
                    return mp_obj_new_float((mp_float_t)lhs_val / (mp_float_t)rhs_val);
184×
464
                #endif
465

466
                case MP_BINARY_OP_MODULO:
97,365×
467
                case MP_BINARY_OP_INPLACE_MODULO: {
468
                    if (rhs_val == 0) {
97,365×
469
                        goto zero_division;
4×
470
                    }
471
                    lhs_val = mp_small_int_modulo(lhs_val, rhs_val);
97,361×
472
                    break;
97,360×
473
                }
474

475
                case MP_BINARY_OP_POWER:
1,240×
476
                case MP_BINARY_OP_INPLACE_POWER:
477
                    if (rhs_val < 0) {
1,240×
478
                        #if MICROPY_PY_BUILTINS_FLOAT
479
                        return mp_obj_float_binary_op(op, (mp_float_t)lhs_val, rhs);
520×
480
                        #else
481
                        mp_raise_ValueError(MP_ERROR_TEXT("negative power with no float support"));
482
                        #endif
483
                    } else {
484
                        mp_int_t ans = 1;
720×
485
                        while (rhs_val > 0) {
2,606×
486
                            if (rhs_val & 1) {
2,548×
487
                                if (mp_small_int_mul_overflow(ans, lhs_val)) {
1,308×
488
                                    goto power_overflow;
160×
489
                                }
490
                                ans *= lhs_val;
1,148×
491
                            }
492
                            if (rhs_val == 1) {
2,388×
493
                                break;
300×
494
                            }
495
                            rhs_val /= 2;
2,088×
496
                            if (mp_small_int_mul_overflow(lhs_val, lhs_val)) {
2,088×
497
                                goto power_overflow;
202×
498
                            }
499
                            lhs_val *= lhs_val;
1,886×
500
                        }
501
                        lhs_val = ans;
358×
502
                    }
503
                    break;
358×
504

505
                power_overflow:
362×
506
                    // use higher precision
507
                    lhs = mp_obj_new_int_from_ll(MP_OBJ_SMALL_INT_VALUE(lhs));
362×
508
                    goto generic_binary_op;
362×
509

510
                case MP_BINARY_OP_DIVMOD: {
178×
511
                    if (rhs_val == 0) {
178×
512
                        goto zero_division;
4×
513
                    }
514
                    // to reduce stack usage we don't pass a temp array of the 2 items
515
                    mp_obj_tuple_t *tuple = MP_OBJ_TO_PTR(mp_obj_new_tuple(2, NULL));
174×
516
                    tuple->items[0] = MP_OBJ_NEW_SMALL_INT(mp_small_int_floor_divide(lhs_val, rhs_val));
174×
517
                    tuple->items[1] = MP_OBJ_NEW_SMALL_INT(mp_small_int_modulo(lhs_val, rhs_val));
174×
518
                    return MP_OBJ_FROM_PTR(tuple);
174×
519
                }
520

521
                case MP_BINARY_OP_LESS:
15,011,500×
522
                    return mp_obj_new_bool(lhs_val < rhs_val);
15,011,500×
523
                case MP_BINARY_OP_MORE:
508,370×
524
                    return mp_obj_new_bool(lhs_val > rhs_val);
508,370×
525
                case MP_BINARY_OP_LESS_EQUAL:
1,320×
526
                    return mp_obj_new_bool(lhs_val <= rhs_val);
1,320×
527
                case MP_BINARY_OP_MORE_EQUAL:
13,617×
528
                    return mp_obj_new_bool(lhs_val >= rhs_val);
13,617×
529

530
                default:
8×
531
                    goto unsupported_op;
8×
532
            }
533
            // This is an inlined version of mp_obj_new_int, for speed
534
            if (MP_SMALL_INT_FITS(lhs_val)) {
39,198,300×
535
                return MP_OBJ_NEW_SMALL_INT(lhs_val);
28,953,000×
536
            } else {
537
                return mp_obj_new_int_from_ll(lhs_val);
10,245,300×
538
            }
539
        #if MICROPY_PY_BUILTINS_FLOAT
540
        } else if (mp_obj_is_float(rhs)) {
!
541
            mp_obj_t res = mp_obj_float_binary_op(op, (mp_float_t)lhs_val, rhs);
6,056×
542
            if (res == MP_OBJ_NULL) {
6,056×
543
                goto unsupported_op;
4×
544
            } else {
545
                return res;
6,052×
546
            }
547
        #endif
548
        #if MICROPY_PY_BUILTINS_COMPLEX
549
        } else if (mp_obj_is_type(rhs, &mp_type_complex)) {
3,407×
550
            mp_obj_t res = mp_obj_complex_binary_op(op, (mp_float_t)lhs_val, 0, rhs);
44×
551
            if (res == MP_OBJ_NULL) {
44×
552
                goto unsupported_op;
4×
553
            } else {
554
                return res;
40×
555
            }
556
        #endif
557
        }
558
    }
559

560
    // Convert MP_BINARY_OP_IN to MP_BINARY_OP_CONTAINS with swapped args.
561
    if (op == MP_BINARY_OP_IN) {
498,466×
562
        op = MP_BINARY_OP_CONTAINS;
23,509×
563
        mp_obj_t temp = lhs;
23,509×
564
        lhs = rhs;
23,509×
565
        rhs = temp;
23,509×
566
    }
567

568
    // generic binary_op supplied by type
569
    const mp_obj_type_t *type;
570
generic_binary_op:
499,811×
571
    type = mp_obj_get_type(lhs);
499,895×
572
    if (type->binary_op != NULL) {
499,895×
573
        mp_obj_t result = type->binary_op(op, lhs, rhs);
499,875×
574
        if (result != MP_OBJ_NULL) {
499,701×
575
            return result;
499,007×
576
        }
577
    }
578

579
    #if MICROPY_PY_REVERSE_SPECIAL_METHODS
580
    if (op >= MP_BINARY_OP_OR && op <= MP_BINARY_OP_POWER) {
714×
581
        mp_obj_t t = rhs;
84×
582
        rhs = lhs;
84×
583
        lhs = t;
84×
584
        op += MP_BINARY_OP_REVERSE_OR - MP_BINARY_OP_OR;
84×
585
        goto generic_binary_op;
84×
586
    } else if (op >= MP_BINARY_OP_REVERSE_OR) {
630×
587
        // Convert __rop__ back to __op__ for error message
588
        mp_obj_t t = rhs;
71×
589
        rhs = lhs;
71×
590
        lhs = t;
71×
591
        op -= MP_BINARY_OP_REVERSE_OR - MP_BINARY_OP_OR;
71×
592
    }
593
    #endif
594

595
    if (op == MP_BINARY_OP_CONTAINS) {
630×
596
        // If type didn't support containment then explicitly walk the iterator.
597
        // mp_getiter will raise the appropriate exception if lhs is not iterable.
598
        mp_obj_iter_buf_t iter_buf;
599
        mp_obj_t iter = mp_getiter(lhs, &iter_buf);
513×
600
        mp_obj_t next;
601
        while ((next = mp_iternext(iter)) != MP_OBJ_STOP_ITERATION) {
1,425×
602
            if (mp_obj_equal(next, rhs)) {
1,326×
603
                return mp_const_true;
402×
604
            }
605
        }
606
        return mp_const_false;
99×
607
    }
608

609
unsupported_op:
117×
610
    #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
611
    mp_raise_TypeError(MP_ERROR_TEXT("unsupported type for operator"));
612
    #else
613
    mp_raise_msg_varg(&mp_type_TypeError,
141×
614
        MP_ERROR_TEXT("unsupported types for %q: '%s', '%s'"),
141×
615
        mp_binary_op_method_name[op], mp_obj_get_type_str(lhs), mp_obj_get_type_str(rhs));
141×
616
    #endif
617

618
zero_division:
77×
619
    mp_raise_msg(&mp_type_ZeroDivisionError, MP_ERROR_TEXT("divide by zero"));
77×
620
}
621

622
mp_obj_t mp_call_function_0(mp_obj_t fun) {
5,828×
623
    return mp_call_function_n_kw(fun, 0, 0, NULL);
5,828×
624
}
625

626
mp_obj_t mp_call_function_1(mp_obj_t fun, mp_obj_t arg) {
5,632×
627
    return mp_call_function_n_kw(fun, 1, 0, &arg);
5,632×
628
}
629

630
mp_obj_t mp_call_function_2(mp_obj_t fun, mp_obj_t arg1, mp_obj_t arg2) {
4×
631
    mp_obj_t args[2];
632
    args[0] = arg1;
4×
633
    args[1] = arg2;
4×
634
    return mp_call_function_n_kw(fun, 2, 0, args);
4×
635
}
636

637
// args contains, eg: arg0  arg1  key0  value0  key1  value1
638
mp_obj_t mp_call_function_n_kw(mp_obj_t fun_in, size_t n_args, size_t n_kw, const mp_obj_t *args) {
9,432,300×
639
    // TODO improve this: fun object can specify its type and we parse here the arguments,
640
    // passing to the function arrays of fixed and keyword arguments
641

642
    DEBUG_OP_printf("calling function %p(n_args=" UINT_FMT ", n_kw=" UINT_FMT ", args=%p)\n", fun_in, n_args, n_kw, args);
643

644
    // get the type
645
    const mp_obj_type_t *type = mp_obj_get_type(fun_in);
9,432,300×
646

647
    // do the call
648
    if (type->call != NULL) {
9,644,760×
649
        return type->call(fun_in, n_args, n_kw, args);
9,670,020×
650
    }
651

652
    #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
653
    mp_raise_TypeError(MP_ERROR_TEXT("object not callable"));
654
    #else
655
    mp_raise_msg_varg(&mp_type_TypeError,
!
656
        MP_ERROR_TEXT("'%s' object isn't callable"), mp_obj_get_type_str(fun_in));
4×
657
    #endif
658
}
659

660
// args contains: fun  self/NULL  arg(0)  ...  arg(n_args-2)  arg(n_args-1)  kw_key(0)  kw_val(0)  ... kw_key(n_kw-1)  kw_val(n_kw-1)
661
// if n_args==0 and n_kw==0 then there are only fun and self/NULL
662
mp_obj_t mp_call_method_n_kw(size_t n_args, size_t n_kw, const mp_obj_t *args) {
1,260,460×
663
    DEBUG_OP_printf("call method (fun=%p, self=%p, n_args=" UINT_FMT ", n_kw=" UINT_FMT ", args=%p)\n", args[0], args[1], n_args, n_kw, args);
664
    int adjust = (args[1] == MP_OBJ_NULL) ? 0 : 1;
1,260,460×
665
    return mp_call_function_n_kw(args[0], n_args + adjust, n_kw, args + 2 - adjust);
1,260,460×
666
}
667

668
// This function only needs to be exposed externally when in stackless mode.
669
#if !MICROPY_STACKLESS
670
STATIC
671
#endif
672
void mp_call_prepare_args_n_kw_var(bool have_self, size_t n_args_n_kw, const mp_obj_t *args, mp_call_args_t *out_args) {
8,230×
673
    mp_obj_t fun = *args++;
8,230×
674
    mp_obj_t self = MP_OBJ_NULL;
8,230×
675
    if (have_self) {
8,230×
676
        self = *args++; // may be MP_OBJ_NULL
3,710×
677
    }
678
    uint n_args = n_args_n_kw & 0xff;
8,230×
679
    uint n_kw = (n_args_n_kw >> 8) & 0xff;
8,230×
680
    mp_obj_t pos_seq = args[n_args + 2 * n_kw]; // may be MP_OBJ_NULL
8,230×
681
    mp_obj_t kw_dict = args[n_args + 2 * n_kw + 1]; // may be MP_OBJ_NULL
8,230×
682

683
    DEBUG_OP_printf("call method var (fun=%p, self=%p, n_args=%u, n_kw=%u, args=%p, seq=%p, dict=%p)\n", fun, self, n_args, n_kw, args, pos_seq, kw_dict);
684

685
    // We need to create the following array of objects:
686
    //     args[0 .. n_args]  unpacked(pos_seq)  args[n_args .. n_args + 2 * n_kw]  unpacked(kw_dict)
687
    // TODO: optimize one day to avoid constructing new arg array? Will be hard.
688

689
    // The new args array
690
    mp_obj_t *args2;
691
    uint args2_alloc;
692
    uint args2_len = 0;
8,230×
693

694
    // Try to get a hint for the size of the kw_dict
695
    uint kw_dict_len = 0;
8,230×
696
    if (kw_dict != MP_OBJ_NULL && mp_obj_is_type(kw_dict, &mp_type_dict)) {
8,230×
697
        kw_dict_len = mp_obj_dict_len(kw_dict);
238×
698
    }
699

700
    // Extract the pos_seq sequence to the new args array.
701
    // Note that it can be arbitrary iterator.
702
    if (pos_seq == MP_OBJ_NULL) {
8,230×
703
        // no sequence
704

705
        // allocate memory for the new array of args
706
        args2_alloc = 1 + n_args + 2 * (n_kw + kw_dict_len);
226×
707
        args2 = mp_nonlocal_alloc(args2_alloc * sizeof(mp_obj_t));
226×
708

709
        // copy the self
710
        if (self != MP_OBJ_NULL) {
226×
711
            args2[args2_len++] = self;
18×
712
        }
713

714
        // copy the fixed pos args
715
        mp_seq_copy(args2 + args2_len, args, n_args, mp_obj_t);
226×
716
        args2_len += n_args;
226×
717

718
    } else if (mp_obj_is_type(pos_seq, &mp_type_tuple) || mp_obj_is_type(pos_seq, &mp_type_list)) {
8,004×
719
        // optimise the case of a tuple and list
720

721
        // get the items
722
        size_t len;
723
        mp_obj_t *items;
724
        mp_obj_get_array(pos_seq, &len, &items);
7,908×
725

726
        // allocate memory for the new array of args
727
        args2_alloc = 1 + n_args + len + 2 * (n_kw + kw_dict_len);
7,908×
728
        args2 = mp_nonlocal_alloc(args2_alloc * sizeof(mp_obj_t));
7,908×
729

730
        // copy the self
731
        if (self != MP_OBJ_NULL) {
7,908×
732
            args2[args2_len++] = self;
3,684×
733
        }
734

735
        // copy the fixed and variable position args
736
        mp_seq_cat(args2 + args2_len, args, n_args, items, len, mp_obj_t);
7,908×
737
        args2_len += n_args + len;
7,908×
738

739
    } else {
740
        // generic iterator
741

742
        // allocate memory for the new array of args
743
        args2_alloc = 1 + n_args + 2 * (n_kw + kw_dict_len) + 3;
96×
744
        args2 = mp_nonlocal_alloc(args2_alloc * sizeof(mp_obj_t));
96×
745

746
        // copy the self
747
        if (self != MP_OBJ_NULL) {
96×
748
            args2[args2_len++] = self;
4×
749
        }
750

751
        // copy the fixed position args
752
        mp_seq_copy(args2 + args2_len, args, n_args, mp_obj_t);
96×
753
        args2_len += n_args;
96×
754

755
        // extract the variable position args from the iterator
756
        mp_obj_iter_buf_t iter_buf;
757
        mp_obj_t iterable = mp_getiter(pos_seq, &iter_buf);
96×
758
        mp_obj_t item;
759
        while ((item = mp_iternext(iterable)) != MP_OBJ_STOP_ITERATION) {
472×
760
            if (args2_len >= args2_alloc) {
376×
761
                args2 = mp_nonlocal_realloc(args2, args2_alloc * sizeof(mp_obj_t), args2_alloc * 2 * sizeof(mp_obj_t));
56×
762
                args2_alloc *= 2;
56×
763
            }
764
            args2[args2_len++] = item;
376×
765
        }
766
    }
767

768
    // The size of the args2 array now is the number of positional args.
769
    uint pos_args_len = args2_len;
8,230×
770

771
    // Copy the fixed kw args.
772
    mp_seq_copy(args2 + args2_len, args + n_args, 2 * n_kw, mp_obj_t);
8,230×
773
    args2_len += 2 * n_kw;
8,230×
774

775
    // Extract (key,value) pairs from kw_dict dictionary and append to args2.
776
    // Note that it can be arbitrary iterator.
777
    if (kw_dict == MP_OBJ_NULL) {
8,230×
778
        // pass
779
    } else if (mp_obj_is_type(kw_dict, &mp_type_dict)) {
470×
780
        // dictionary
781
        mp_map_t *map = mp_obj_dict_get_map(kw_dict);
238×
782
        assert(args2_len + 2 * map->used <= args2_alloc); // should have enough, since kw_dict_len is in this case hinted correctly above
238×
783
        for (size_t i = 0; i < map->alloc; i++) {
422×
784
            if (mp_map_slot_is_filled(map, i)) {
194×
785
                // the key must be a qstr, so intern it if it's a string
786
                mp_obj_t key = map->table[i].key;
186×
787
                if (!mp_obj_is_qstr(key)) {
186×
788
                    key = mp_obj_str_intern_checked(key);
14×
789
                }
790
                args2[args2_len++] = key;
176×
791
                args2[args2_len++] = map->table[i].value;
176×
792
            }
793
        }
794
    } else {
795
        // generic mapping:
796
        // - call keys() to get an iterable of all keys in the mapping
797
        // - call __getitem__ for each key to get the corresponding value
798

799
        // get the keys iterable
800
        mp_obj_t dest[3];
801
        mp_load_method(kw_dict, MP_QSTR_keys, dest);
4×
802
        mp_obj_t iterable = mp_getiter(mp_call_method_n_kw(0, 0, dest), NULL);
4×
803

804
        mp_obj_t key;
805
        while ((key = mp_iternext(iterable)) != MP_OBJ_STOP_ITERATION) {
20×
806
            // expand size of args array if needed
807
            if (args2_len + 1 >= args2_alloc) {
16×
808
                uint new_alloc = args2_alloc * 2;
8×
809
                if (new_alloc < 4) {
8×
810
                    new_alloc = 4;
4×
811
                }
812
                args2 = mp_nonlocal_realloc(args2, args2_alloc * sizeof(mp_obj_t), new_alloc * sizeof(mp_obj_t));
8×
813
                args2_alloc = new_alloc;
8×
814
            }
815

816
            // the key must be a qstr, so intern it if it's a string
817
            if (!mp_obj_is_qstr(key)) {
16×
818
                key = mp_obj_str_intern_checked(key);
4×
819
            }
820

821
            // get the value corresponding to the key
822
            mp_load_method(kw_dict, MP_QSTR___getitem__, dest);
16×
823
            dest[2] = key;
16×
824
            mp_obj_t value = mp_call_method_n_kw(1, 0, dest);
16×
825

826
            // store the key/value pair in the argument array
827
            args2[args2_len++] = key;
16×
828
            args2[args2_len++] = value;
16×
829
        }
830
    }
831

832
    out_args->fun = fun;
8,220×
833
    out_args->args = args2;
8,220×
834
    out_args->n_args = pos_args_len;
8,220×
835
    out_args->n_kw = (args2_len - pos_args_len) / 2;
8,220×
836
    out_args->n_alloc = args2_alloc;
8,220×
837
}
8,220×
838

839
mp_obj_t mp_call_method_n_kw_var(bool have_self, size_t n_args_n_kw, const mp_obj_t *args) {
8,230×
840
    mp_call_args_t out_args;
841
    mp_call_prepare_args_n_kw_var(have_self, n_args_n_kw, args, &out_args);
8,230×
842

843
    mp_obj_t res = mp_call_function_n_kw(out_args.fun, out_args.n_args, out_args.n_kw, out_args.args);
8,220×
844
    mp_nonlocal_free(out_args.args, out_args.n_alloc * sizeof(mp_obj_t));
8,184×
845

846
    return res;
8,184×
847
}
848

849
// unpacked items are stored in reverse order into the array pointed to by items
850
void mp_unpack_sequence(mp_obj_t seq_in, size_t num, mp_obj_t *items) {
39,960×
851
    size_t seq_len;
852
    if (mp_obj_is_type(seq_in, &mp_type_tuple) || mp_obj_is_type(seq_in, &mp_type_list)) {
79,860×
853
        mp_obj_t *seq_items;
854
        mp_obj_get_array(seq_in, &seq_len, &seq_items);
39,908×
855
        if (seq_len < num) {
39,908×
856
            goto too_short;
4×
857
        } else if (seq_len > num) {
39,904×
858
            goto too_long;
4×
859
        }
860
        for (size_t i = 0; i < num; i++) {
120,029×
861
            items[i] = seq_items[num - 1 - i];
80,129×
862
        }
863
    } else {
864
        mp_obj_iter_buf_t iter_buf;
865
        mp_obj_t iterable = mp_getiter(seq_in, &iter_buf);
52×
866

867
        for (seq_len = 0; seq_len < num; seq_len++) {
164×
868
            mp_obj_t el = mp_iternext(iterable);
116×
869
            if (el == MP_OBJ_STOP_ITERATION) {
116×
870
                goto too_short;
4×
871
            }
872
            items[num - 1 - seq_len] = el;
112×
873
        }
874
        if (mp_iternext(iterable) != MP_OBJ_STOP_ITERATION) {
48×
875
            goto too_long;
4×
876
        }
877
    }
878
    return;
39,944×
879

880
too_short:
8×
881
    #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
882
    mp_raise_ValueError(MP_ERROR_TEXT("wrong number of values to unpack"));
883
    #else
884
    mp_raise_msg_varg(&mp_type_ValueError, MP_ERROR_TEXT("need more than %d values to unpack"), (int)seq_len);
16×
885
    #endif
886
too_long:
8×
887
    #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
888
    mp_raise_ValueError(MP_ERROR_TEXT("wrong number of values to unpack"));
889
    #else
890
    mp_raise_msg_varg(&mp_type_ValueError, MP_ERROR_TEXT("too many values to unpack (expected %d)"), (int)num);
16×
891
    #endif
892
}
893

894
// unpacked items are stored in reverse order into the array pointed to by items
895
void mp_unpack_ex(mp_obj_t seq_in, size_t num_in, mp_obj_t *items) {
120×
896
    size_t num_left = num_in & 0xff;
120×
897
    size_t num_right = (num_in >> 8) & 0xff;
120×
898
    DEBUG_OP_printf("unpack ex " UINT_FMT " " UINT_FMT "\n", num_left, num_right);
899
    size_t seq_len;
900
    if (mp_obj_is_type(seq_in, &mp_type_tuple) || mp_obj_is_type(seq_in, &mp_type_list)) {
120×
901
        // Make the seq variable volatile so the compiler keeps a reference to it,
902
        // since if it's a tuple then seq_items points to the interior of the GC cell
903
        // and mp_obj_new_list may trigger a GC which doesn't trace this and reclaims seq.
904
        volatile mp_obj_t seq = seq_in;
76×
905
        mp_obj_t *seq_items;
906
        mp_obj_get_array(seq, &seq_len, &seq_items);
76×
907
        if (seq_len < num_left + num_right) {
76×
908
            goto too_short;
4×
909
        }
910
        for (size_t i = 0; i < num_right; i++) {
104×
911
            items[i] = seq_items[seq_len - 1 - i];
32×
912
        }
913
        items[num_right] = mp_obj_new_list(seq_len - num_left - num_right, seq_items + num_left);
72×
914
        for (size_t i = 0; i < num_left; i++) {
104×
915
            items[num_right + 1 + i] = seq_items[num_left - 1 - i];
32×
916
        }
917
        seq = MP_OBJ_NULL;
72×
918
    } else {
919
        // Generic iterable; this gets a bit messy: we unpack known left length to the
920
        // items destination array, then the rest to a dynamically created list.  Once the
921
        // iterable is exhausted, we take from this list for the right part of the items.
922
        // TODO Improve to waste less memory in the dynamically created list.
923
        mp_obj_t iterable = mp_getiter(seq_in, NULL);
44×
924
        mp_obj_t item;
925
        for (seq_len = 0; seq_len < num_left; seq_len++) {
84×
926
            item = mp_iternext(iterable);
44×
927
            if (item == MP_OBJ_STOP_ITERATION) {
44×
928
                goto too_short;
4×
929
            }
930
            items[num_left + num_right + 1 - 1 - seq_len] = item;
40×
931
        }
932
        mp_obj_list_t *rest = MP_OBJ_TO_PTR(mp_obj_new_list(0, NULL));
40×
933
        while ((item = mp_iternext(iterable)) != MP_OBJ_STOP_ITERATION) {
184×
934
            mp_obj_list_append(MP_OBJ_FROM_PTR(rest), item);
144×
935
        }
936
        if (rest->len < num_right) {
40×
937
            goto too_short;
4×
938
        }
939
        items[num_right] = MP_OBJ_FROM_PTR(rest);
36×
940
        for (size_t i = 0; i < num_right; i++) {
72×
941
            items[num_right - 1 - i] = rest->items[rest->len - num_right + i];
36×
942
        }
943
        mp_obj_list_set_len(MP_OBJ_FROM_PTR(rest), rest->len - num_right);
36×
944
    }
945
    return;
108×
946

947
too_short:
12×
948
    #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
949
    mp_raise_ValueError(MP_ERROR_TEXT("wrong number of values to unpack"));
950
    #else
951
    mp_raise_msg_varg(&mp_type_ValueError, MP_ERROR_TEXT("need more than %d values to unpack"), (int)seq_len);
24×
952
    #endif
953
}
954

955
mp_obj_t mp_load_attr(mp_obj_t base, qstr attr) {
1,711,980×
956
    DEBUG_OP_printf("load attr %p.%s\n", base, qstr_str(attr));
957
    // use load_method
958
    mp_obj_t dest[2];
959
    mp_load_method(base, attr, dest);
1,711,980×
960
    if (dest[1] == MP_OBJ_NULL) {
1,711,900×
961
        // load_method returned just a normal attribute
962
        return dest[0];
1,711,820×
963
    } else {
964
        // load_method returned a method, so build a bound method object
965
        return mp_obj_new_bound_meth(dest[0], dest[1]);
84×
966
    }
967
}
968

969
#if MICROPY_BUILTIN_METHOD_CHECK_SELF_ARG
970

971
// The following "checked fun" type is local to the mp_convert_member_lookup
972
// function, and serves to check that the first argument to a builtin function
973
// has the correct type.
974

975
typedef struct _mp_obj_checked_fun_t {
976
    mp_obj_base_t base;
977
    const mp_obj_type_t *type;
978
    mp_obj_t fun;
979
} mp_obj_checked_fun_t;
980

981
STATIC mp_obj_t checked_fun_call(mp_obj_t self_in, size_t n_args, size_t n_kw, const mp_obj_t *args) {
26×
982
    mp_obj_checked_fun_t *self = MP_OBJ_TO_PTR(self_in);
26×
983
    if (n_args > 0) {
26×
984
        const mp_obj_type_t *arg0_type = mp_obj_get_type(args[0]);
22×
985
        if (arg0_type != self->type) {
22×
986
            #if MICROPY_ERROR_REPORTING != MICROPY_ERROR_REPORTING_DETAILED
987
            mp_raise_TypeError(MP_ERROR_TEXT("argument has wrong type"));
988
            #else
989
            mp_raise_msg_varg(&mp_type_TypeError,
24×
990
                MP_ERROR_TEXT("argument should be a '%q' not a '%q'"), self->type->name, arg0_type->name);
24×
991
            #endif
992
        }
993
    }
994
    return mp_call_function_n_kw(self->fun, n_args, n_kw, args);
14×
995
}
996

997
STATIC const mp_obj_type_t mp_type_checked_fun = {
998
    { &mp_type_type },
999
    .flags = MP_TYPE_FLAG_BINDS_SELF,
1000
    .name = MP_QSTR_function,
1001
    .call = checked_fun_call,
1002
};
1003

1004
STATIC mp_obj_t mp_obj_new_checked_fun(const mp_obj_type_t *type, mp_obj_t fun) {
105×
1005
    mp_obj_checked_fun_t *o = m_new_obj(mp_obj_checked_fun_t);
105×
1006
    o->base.type = &mp_type_checked_fun;
105×
1007
    o->type = type;
105×
1008
    o->fun = fun;
105×
1009
    return MP_OBJ_FROM_PTR(o);
105×
1010
}
1011

1012
#endif // MICROPY_BUILTIN_METHOD_CHECK_SELF_ARG
1013

1014
// Given a member that was extracted from an instance, convert it correctly
1015
// and put the result in the dest[] array for a possible method call.
1016
// Conversion means dealing with static/class methods, callables, and values.
1017
// see http://docs.python.org/3/howto/descriptor.html
1018
// and also https://mail.python.org/pipermail/python-dev/2015-March/138950.html
1019
void mp_convert_member_lookup(mp_obj_t self, const mp_obj_type_t *type, mp_obj_t member, mp_obj_t *dest) {
1,446,390×
1020
    if (mp_obj_is_obj(member)) {
1,446,390×
1021
        const mp_obj_type_t *m_type = ((mp_obj_base_t *)MP_OBJ_TO_PTR(member))->type;
998,020×
1022
        if (m_type->flags & MP_TYPE_FLAG_BINDS_SELF) {
998,020×
1023
            // `member` is a function that binds self as its first argument.
1024
            if (m_type->flags & MP_TYPE_FLAG_BUILTIN_FUN) {
997,523×
1025
                // `member` is a built-in function, which has special behaviour.
1026
                if (mp_obj_is_instance_type(type)) {
559,837×
1027
                    // Built-in functions on user types always behave like a staticmethod.
1028
                    dest[0] = member;
8×
1029
                }
1030
                #if MICROPY_BUILTIN_METHOD_CHECK_SELF_ARG
1031
                else if (self == MP_OBJ_NULL && type != &mp_type_object) {
559,829×
1032
                    // `member` is a built-in method without a first argument, so wrap
1033
                    // it in a type checker that will check self when it's supplied.
1034
                    // Note that object will do its own checking so shouldn't be wrapped.
1035
                    dest[0] = mp_obj_new_checked_fun(type, member);
105×
1036
                }
1037
                #endif
1038
                else {
1039
                    // Return a (built-in) bound method, with self being this object.
1040
                    dest[0] = member;
559,724×
1041
                    dest[1] = self;
559,724×
1042
                }
1043
            } else {
1044
                // Return a bound method, with self being this object.
1045
                dest[0] = member;
437,686×
1046
                dest[1] = self;
437,686×
1047
            }
1048
        } else if (m_type == &mp_type_staticmethod) {
497×
1049
            // `member` is a staticmethod, return the function that it wraps.
1050
            dest[0] = ((mp_obj_static_class_method_t *)MP_OBJ_TO_PTR(member))->fun;
217×
1051
        } else if (m_type == &mp_type_classmethod) {
280×
1052
            // `member` is a classmethod, return a bound method with self being the type of
1053
            // this object.  This type should be the type of the original instance, not the
1054
            // base type (which is what is passed in the `type` argument to this function).
1055
            if (self != MP_OBJ_NULL) {
88×
1056
                type = mp_obj_get_type(self);
12×
1057
            }
1058
            dest[0] = ((mp_obj_static_class_method_t *)MP_OBJ_TO_PTR(member))->fun;
88×
1059
            dest[1] = MP_OBJ_FROM_PTR(type);
88×
1060
        } else {
1061
            // `member` is a value, so just return that value.
1062
            dest[0] = member;
192×
1063
        }
1064
    } else {
1065
        // `member` is a value, so just return that value.
1066
        dest[0] = member;
448,373×
1067
    }
1068
}
1,446,390×
1069

1070
// no attribute found, returns:     dest[0] == MP_OBJ_NULL, dest[1] == MP_OBJ_NULL
1071
// normal attribute found, returns: dest[0] == <attribute>, dest[1] == MP_OBJ_NULL
1072
// method attribute found, returns: dest[0] == <method>,    dest[1] == <self>
1073
void mp_load_method_maybe(mp_obj_t obj, qstr attr, mp_obj_t *dest) {
2,923,460×
1074
    // clear output to indicate no attribute/method found yet
1075
    dest[0] = MP_OBJ_NULL;
2,923,460×
1076
    dest[1] = MP_OBJ_NULL;
2,923,460×
1077

1078
    // get the type
1079
    const mp_obj_type_t *type = mp_obj_get_type(obj);
2,923,460×
1080

1081
    // look for built-in names
1082
    #if MICROPY_CPYTHON_COMPAT
1083
    if (attr == MP_QSTR___class__) {
2,923,460×
1084
        // a.__class__ is equivalent to type(a)
1085
        dest[0] = MP_OBJ_FROM_PTR(type);
41×
1086
        return;
41×
1087
    }
1088
    #endif
1089

1090
    if (attr == MP_QSTR___next__ && type->iternext != NULL) {
2,923,420×
1091
        dest[0] = MP_OBJ_FROM_PTR(&mp_builtin_next_obj);
4×
1092
        dest[1] = obj;
4×
1093

1094
    } else if (type->attr != NULL) {
2,923,410×
1095
        // this type can do its own load, so call it
1096
        type->attr(obj, attr, dest);
2,349,630×
1097

1098
    } else if (type->locals_dict != NULL) {
573,788×
1099
        // generic method lookup
1100
        // this is a lookup in the object (ie not class or type)
1101
        assert(type->locals_dict->base.type == &mp_type_dict); // MicroPython restriction, for now
568,862×
1102
        mp_map_t *locals_map = &type->locals_dict->map;
568,862×
1103
        mp_map_elem_t *elem = mp_map_lookup(locals_map, MP_OBJ_NEW_QSTR(attr), MP_MAP_LOOKUP);
568,862×
1104
        if (elem != NULL) {
568,862×
1105
            mp_convert_member_lookup(obj, type, elem->value, dest);
559,643×
1106
        }
1107
    }
1108
}
1109

1110
void mp_load_method(mp_obj_t base, qstr attr, mp_obj_t *dest) {
2,655,500×
1111
    DEBUG_OP_printf("load method %p.%s\n", base, qstr_str(attr));
1112

1113
    mp_load_method_maybe(base, attr, dest);
2,655,500×
1114

1115
    if (dest[0] == MP_OBJ_NULL) {
2,655,480×
1116
        // no attribute/method called attr
1117
        #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
1118
        mp_raise_msg(&mp_type_AttributeError, MP_ERROR_TEXT("no such attribute"));
1119
        #else
1120
        // following CPython, we give a more detailed error message for type objects
1121
        if (mp_obj_is_type(base, &mp_type_type)) {
80×
1122
            mp_raise_msg_varg(&mp_type_AttributeError,
16×
1123
                MP_ERROR_TEXT("type object '%q' has no attribute '%q'"),
8×
1124
                ((mp_obj_type_t *)MP_OBJ_TO_PTR(base))->name, attr);
8×
1125
        } else {
1126
            mp_raise_msg_varg(&mp_type_AttributeError,
72×
1127
                MP_ERROR_TEXT("'%s' object has no attribute '%q'"),
72×
1128
                mp_obj_get_type_str(base), attr);
1129
        }
1130
        #endif
1131
    }
1132
}
2,655,400×
1133

1134
// Acts like mp_load_method_maybe but catches AttributeError, and all other exceptions if requested
1135
void mp_load_method_protected(mp_obj_t obj, qstr attr, mp_obj_t *dest, bool catch_all_exc) {
44,190×
1136
    nlr_buf_t nlr;
1137
    if (nlr_push(&nlr) == 0) {
44,190×
1138
        mp_load_method_maybe(obj, attr, dest);
44,190×
1139
        nlr_pop();
44,178×
1140
    } else {
1141
        if (!catch_all_exc
12×
1142
            && !mp_obj_is_subclass_fast(MP_OBJ_FROM_PTR(((mp_obj_base_t *)nlr.ret_val)->type),
12×
1143
                MP_OBJ_FROM_PTR(&mp_type_AttributeError))) {
1144
            // Re-raise the exception
1145
            nlr_raise(MP_OBJ_FROM_PTR(nlr.ret_val));
4×
1146
        }
1147
    }
1148
}
44,186×
1149

1150
void mp_store_attr(mp_obj_t base, qstr attr, mp_obj_t value) {
205,018×
1151
    DEBUG_OP_printf("store attr %p.%s <- %p\n", base, qstr_str(attr), value);
1152
    const mp_obj_type_t *type = mp_obj_get_type(base);
205,018×
1153
    if (type->attr != NULL) {
205,018×
1154
        mp_obj_t dest[2] = {MP_OBJ_SENTINEL, value};
205,017×
1155
        type->attr(base, attr, dest);
205,017×
1156
        if (dest[0] == MP_OBJ_NULL) {
205,009×
1157
            // success
1158
            return;
204,940×
1159
        }
1160
    }
1161
    #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
1162
    mp_raise_msg(&mp_type_AttributeError, MP_ERROR_TEXT("no such attribute"));
1163
    #else
1164
    mp_raise_msg_varg(&mp_type_AttributeError,
70×
1165
        MP_ERROR_TEXT("'%s' object has no attribute '%q'"),
70×
1166
        mp_obj_get_type_str(base), attr);
1167
    #endif
1168
}
1169

1170
mp_obj_t mp_getiter(mp_obj_t o_in, mp_obj_iter_buf_t *iter_buf) {
296,992×
1171
    assert(o_in);
296,992×
1172
    const mp_obj_type_t *type = mp_obj_get_type(o_in);
296,992×
1173

1174
    // Check for native getiter which is the identity.  We handle this case explicitly
1175
    // so we don't unnecessarily allocate any RAM for the iter_buf, which won't be used.
1176
    if (type->getiter == mp_identity_getiter) {
296,992×
1177
        return o_in;
149,685×
1178
    }
1179

1180
    // check for native getiter (corresponds to __iter__)
1181
    if (type->getiter != NULL) {
147,307×
1182
        if (iter_buf == NULL && type->getiter != mp_obj_instance_getiter) {
147,287×
1183
            // if caller did not provide a buffer then allocate one on the heap
1184
            // mp_obj_instance_getiter is special, it will allocate only if needed
1185
            iter_buf = m_new_obj(mp_obj_iter_buf_t);
40,044×
1186
        }
1187
        mp_obj_t iter = type->getiter(o_in, iter_buf);
147,287×
1188
        if (iter != MP_OBJ_NULL) {
147,287×
1189
            return iter;
147,263×
1190
        }
1191
    }
1192

1193
    // check for __getitem__
1194
    mp_obj_t dest[2];
1195
    mp_load_method_maybe(o_in, MP_QSTR___getitem__, dest);
44×
1196
    if (dest[0] != MP_OBJ_NULL) {
44×
1197
        // __getitem__ exists, create and return an iterator
1198
        if (iter_buf == NULL) {
16×
1199
            // if caller did not provide a buffer then allocate one on the heap
1200
            iter_buf = m_new_obj(mp_obj_iter_buf_t);
8×
1201
        }
1202
        return mp_obj_new_getitem_iter(dest, iter_buf);
16×
1203
    }
1204

1205
    // object not iterable
1206
    #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
1207
    mp_raise_TypeError(MP_ERROR_TEXT("object not iterable"));
1208
    #else
1209
    mp_raise_msg_varg(&mp_type_TypeError,
28×
1210
        MP_ERROR_TEXT("'%s' object isn't iterable"), mp_obj_get_type_str(o_in));
28×
1211
    #endif
1212

1213
}
1214

1215
// may return MP_OBJ_STOP_ITERATION as an optimisation instead of raise StopIteration()
1216
// may also raise StopIteration()
1217
mp_obj_t mp_iternext_allow_raise(mp_obj_t o_in) {
102,012×
1218
    const mp_obj_type_t *type = mp_obj_get_type(o_in);
102,012×
1219
    if (type->iternext != NULL) {
102,011×
1220
        return type->iternext(o_in);
101,975×
1221
    } else {
1222
        // check for __next__ method
1223
        mp_obj_t dest[2];
1224
        mp_load_method_maybe(o_in, MP_QSTR___next__, dest);
36×
1225
        if (dest[0] != MP_OBJ_NULL) {
36×
1226
            // __next__ exists, call it and return its result
1227
            return mp_call_method_n_kw(0, 0, dest);
32×
1228
        } else {
1229
            #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
1230
            mp_raise_TypeError(MP_ERROR_TEXT("object not an iterator"));
1231
            #else
1232
            mp_raise_msg_varg(&mp_type_TypeError,
4×
1233
                MP_ERROR_TEXT("'%s' object isn't an iterator"), mp_obj_get_type_str(o_in));
4×
1234
            #endif
1235
        }
1236
    }
1237
}
1238

1239
// will always return MP_OBJ_STOP_ITERATION instead of raising StopIteration() (or any subclass thereof)
1240
// may raise other exceptions
1241
mp_obj_t mp_iternext(mp_obj_t o_in) {
806,386×
1242
    MP_STACK_CHECK(); // enumerate, filter, map and zip can recursively call mp_iternext
806,386×
1243
    const mp_obj_type_t *type = mp_obj_get_type(o_in);
806,363×
1244
    if (type->iternext != NULL) {
806,362×
1245
        return type->iternext(o_in);
806,246×
1246
    } else {
1247
        // check for __next__ method
1248
        mp_obj_t dest[2];
1249
        mp_load_method_maybe(o_in, MP_QSTR___next__, dest);
116×
1250
        if (dest[0] != MP_OBJ_NULL) {
116×
1251
            // __next__ exists, call it and return its result
1252
            nlr_buf_t nlr;
1253
            if (nlr_push(&nlr) == 0) {
112×
1254
                mp_obj_t ret = mp_call_method_n_kw(0, 0, dest);
112×
1255
                nlr_pop();
72×
1256
                return ret;
72×
1257
            } else {
1258
                if (mp_obj_is_subclass_fast(MP_OBJ_FROM_PTR(((mp_obj_base_t *)nlr.ret_val)->type), MP_OBJ_FROM_PTR(&mp_type_StopIteration))) {
40×
1259
                    return MP_OBJ_STOP_ITERATION;
34×
1260
                } else {
1261
                    nlr_jump(nlr.ret_val);
6×
1262
                }
1263
            }
1264
        } else {
1265
            #if MICROPY_ERROR_REPORTING <= MICROPY_ERROR_REPORTING_TERSE
1266
            mp_raise_TypeError(MP_ERROR_TEXT("object not an iterator"));
1267
            #else
1268
            mp_raise_msg_varg(&mp_type_TypeError,
4×
1269
                MP_ERROR_TEXT("'%s' object isn't an iterator"), mp_obj_get_type_str(o_in));
4×
1270
            #endif
1271
        }
1272
    }
1273
}
1274

1275
// TODO: Unclear what to do with StopIterarion exception here.
1276
mp_vm_return_kind_t mp_resume(mp_obj_t self_in, mp_obj_t send_value, mp_obj_t throw_value, mp_obj_t *ret_val) {
205,946×
1277
    assert((send_value != MP_OBJ_NULL) ^ (throw_value != MP_OBJ_NULL));
205,946×
1278
    const mp_obj_type_t *type = mp_obj_get_type(self_in);
205,946×
1279

1280
    if (type == &mp_type_gen_instance) {
205,946×
1281
        return mp_obj_gen_resume(self_in, send_value, throw_value, ret_val);
1,179×
1282
    }
1283

1284
    if (type->iternext != NULL && send_value == mp_const_none) {
204,767×
1285
        mp_obj_t ret = type->iternext(self_in);
251×
1286
        *ret_val = ret;
158×
1287
        if (ret != MP_OBJ_STOP_ITERATION) {
158×
1288
            return MP_VM_RETURN_YIELD;
142×
1289
        } else {
1290
            // Emulate raise StopIteration()
1291
            // Special case, handled in vm.c
1292
            return MP_VM_RETURN_NORMAL;
16×
1293
        }
1294
    }
1295

1296
    mp_obj_t dest[3]; // Reserve slot for send() arg
1297

1298
    // Python instance iterator protocol
1299
    if (send_value == mp_const_none) {
204,516×
1300
        mp_load_method_maybe(self_in, MP_QSTR___next__, dest);
204,423×
1301
        if (dest[0] != MP_OBJ_NULL) {
204,423×
1302
            *ret_val = mp_call_method_n_kw(0, 0, dest);
204,423×
1303
            return MP_VM_RETURN_YIELD;
102,277×
1304
        }
1305
    }
1306

1307
    // Either python instance generator protocol, or native object
1308
    // generator protocol.
1309
    if (send_value != MP_OBJ_NULL) {
93×
1310
        mp_load_method(self_in, MP_QSTR_send, dest);
8×
1311
        dest[2] = send_value;
8×
1312
        *ret_val = mp_call_method_n_kw(1, 0, dest);
8×
1313
        return MP_VM_RETURN_YIELD;
8×
1314
    }
1315

1316
    assert(throw_value != MP_OBJ_NULL);
85×
1317
    {
1318
        if (mp_obj_is_subclass_fast(MP_OBJ_FROM_PTR(mp_obj_get_type(throw_value)), MP_OBJ_FROM_PTR(&mp_type_GeneratorExit))) {
85×
1319
            mp_load_method_maybe(self_in, MP_QSTR_close, dest);
8×
1320
            if (dest[0] != MP_OBJ_NULL) {
8×
1321
                // TODO: Exceptions raised in close() are not propagated,
1322
                // printed to sys.stderr
1323
                *ret_val = mp_call_method_n_kw(0, 0, dest);
2×
1324
                // We assume one can't "yield" from close()
1325
                return MP_VM_RETURN_NORMAL;
2×
1326
            }
1327
        } else {
1328
            mp_load_method_maybe(self_in, MP_QSTR_throw, dest);
77×
1329
            if (dest[0] != MP_OBJ_NULL) {
77×
1330
                dest[2] = throw_value;
8×
1331
                *ret_val = mp_call_method_n_kw(1, 0, dest);
8×
1332
                // If .throw() method returned, we assume it's value to yield
1333
                // - any exception would be thrown with nlr_raise().
1334
                return MP_VM_RETURN_YIELD;
8×
1335
            }
1336
        }
1337
        // If there's nowhere to throw exception into, then we assume that object
1338
        // is just incapable to handle it, so any exception thrown into it
1339
        // will be propagated up. This behavior is approved by test_pep380.py
1340
        // test_delegation_of_close_to_non_generator(),
1341
        //  test_delegating_throw_to_non_generator()
1342
        if (mp_obj_exception_match(throw_value, MP_OBJ_FROM_PTR(&mp_type_StopIteration))) {
75×
1343
            // PEP479: if StopIteration is raised inside a generator it is replaced with RuntimeError
1344
            *ret_val = mp_obj_new_exception_msg(&mp_type_RuntimeError, MP_ERROR_TEXT("generator raised StopIteration"));
4×
1345
        } else {
1346
            *ret_val = mp_make_raise_obj(throw_value);
71×
1347
        }
1348
        return MP_VM_RETURN_EXCEPTION;
75×
1349
    }
1350
}
1351

1352
mp_obj_t mp_make_raise_obj(mp_obj_t o) {
152,623×
1353
    DEBUG_printf("raise %p\n", o);
1354
    if (mp_obj_is_exception_type(o)) {
152,623×
1355
        // o is an exception type (it is derived from BaseException (or is BaseException))
1356
        // create and return a new exception instance by calling o
1357
        // TODO could have an option to disable traceback, then builtin exceptions (eg TypeError)
1358
        // could have const instances in ROM which we return here instead
1359
        return mp_call_function_n_kw(o, 0, 0, NULL);
742×
1360
    } else if (mp_obj_is_exception_instance(o)) {
151,881×
1361
        // o is an instance of an exception, so use it as the exception
1362
        return o;
151,873×
1363
    } else {
1364
        // o cannot be used as an exception, so return a type error (which will be raised by the caller)
1365
        return mp_obj_new_exception_msg(&mp_type_TypeError, MP_ERROR_TEXT("exceptions must derive from BaseException"));
8×
1366
    }
1367
}
1368

1369
mp_obj_t mp_import_name(qstr name, mp_obj_t fromlist, mp_obj_t level) {
1,756×
1370
    DEBUG_printf("import name '%s' level=%d\n", qstr_str(name), MP_OBJ_SMALL_INT_VALUE(level));
1371

1372
    // build args array
1373
    mp_obj_t args[5];
1374
    args[0] = MP_OBJ_NEW_QSTR(name);
1,756×
1375
    args[1] = mp_const_none; // TODO should be globals
1,756×
1376
    args[2] = mp_const_none; // TODO should be locals
1,756×
1377
    args[3] = fromlist;
1,756×
1378
    args[4] = level;
1,756×
1379

1380
    #if MICROPY_CAN_OVERRIDE_BUILTINS
1381
    // Lookup __import__ and call that if it exists
1382
    mp_obj_dict_t *bo_dict = MP_STATE_VM(mp_module_builtins_override_dict);
1,756×
1383
    if (bo_dict != NULL) {
1,756×
1384
        mp_map_elem_t *import = mp_map_lookup(&bo_dict->map, MP_OBJ_NEW_QSTR(MP_QSTR___import__), MP_MAP_LOOKUP);
26×
1385
        if (import != NULL) {
26×
1386
            return mp_call_function_n_kw(import->value, 5, 0, args);
26×
1387
        }
1388
    }
1389
    #endif
1390

1391
    return mp_builtin___import__(5, args);
1,730×
1392
}
1393

1394
mp_obj_t mp_import_from(mp_obj_t module, qstr name) {
572×
1395
    DEBUG_printf("import from %p %s\n", module, qstr_str(name));
1396

1397
    mp_obj_t dest[2];
1398

1399
    mp_load_method_maybe(module, name, dest);
572×
1400

1401
    if (dest[1] != MP_OBJ_NULL) {
572×
1402
        // Hopefully we can't import bound method from an object
1403
    import_error:
4×
1404
        mp_raise_msg_varg(&mp_type_ImportError, MP_ERROR_TEXT("can't import name %q"), name);
4×
1405
    }
1406

1407
    if (dest[0] != MP_OBJ_NULL) {
572×
1408
        return dest[0];
558×
1409
    }
1410

1411
    #if MICROPY_ENABLE_EXTERNAL_IMPORT
1412

1413
    // See if it's a package, then can try FS import
1414
    if (!mp_obj_is_package(module)) {
14×
1415
        goto import_error;
4×
1416
    }
1417

1418
    mp_load_method_maybe(module, MP_QSTR___name__, dest);
10×
1419
    size_t pkg_name_len;
1420
    const char *pkg_name = mp_obj_str_get_data(dest[0], &pkg_name_len);
10×
1421

1422
    const uint dot_name_len = pkg_name_len + 1 + qstr_len(name);
10×
1423
    char *dot_name = mp_local_alloc(dot_name_len);
10×
1424
    memcpy(dot_name, pkg_name, pkg_name_len);
10×
1425
    dot_name[pkg_name_len] = '.';
10×
1426
    memcpy(dot_name + pkg_name_len + 1, qstr_str(name), qstr_len(name));
10×
1427
    qstr dot_name_q = qstr_from_strn(dot_name, dot_name_len);
10×
1428
    mp_local_free(dot_name);
10×
1429

1430
    // For fromlist, pass sentinel "non empty" value to force returning of leaf module
1431
    return mp_import_name(dot_name_q, mp_const_true, MP_OBJ_NEW_SMALL_INT(0));
10×
1432

1433
    #else
1434

1435
    // Package import not supported with external imports disabled
1436
    goto import_error;
1437

1438
    #endif
1439
}
1440

1441
void mp_import_all(mp_obj_t module) {
86×
1442
    DEBUG_printf("import all %p\n", module);
1443

1444
    // TODO: Support __all__
1445
    mp_map_t *map = &mp_obj_module_get_globals(module)->map;
86×
1446
    for (size_t i = 0; i < map->alloc; i++) {
2,330×
1447
        if (mp_map_slot_is_filled(map, i)) {
2,244×
1448
            // Entry in module global scope may be generated programmatically
1449
            // (and thus be not a qstr for longer names). Avoid turning it in
1450
            // qstr if it has '_' and was used exactly to save memory.
1451
            const char *name = mp_obj_str_get_str(map->table[i].key);
2,182×
1452
            if (*name != '_') {
2,182×
1453
                qstr qname = mp_obj_str_get_qstr(map->table[i].key);
1,666×
1454
                mp_store_name(qname, map->table[i].value);
1,666×
1455
            }
1456
        }
1457
    }
1458
}
86×
1459

1460
#if MICROPY_ENABLE_COMPILER
1461

1462
mp_obj_t mp_parse_compile_execute(mp_lexer_t *lex, mp_parse_input_kind_t parse_input_kind, mp_obj_dict_t *globals, mp_obj_dict_t *locals) {
1,484×
1463
    // save context
1464
    mp_obj_dict_t *volatile old_globals = mp_globals_get();
1,484×
1465
    mp_obj_dict_t *volatile old_locals = mp_locals_get();
1,484×
1466

1467
    // set new context
1468
    mp_globals_set(globals);
1,484×
1469
    mp_locals_set(locals);
1,484×
1470

1471
    nlr_buf_t nlr;
1472
    if (nlr_push(&nlr) == 0) {
1,484×
1473
        qstr source_name = lex->source_name;
1,484×
1474
        mp_parse_tree_t parse_tree = mp_parse(lex, parse_input_kind);
1,484×
1475
        mp_obj_t module_fun = mp_compile(&parse_tree, source_name, parse_input_kind == MP_PARSE_SINGLE_INPUT);
1,350×
1476

1477
        mp_obj_t ret;
1478
        if (MICROPY_PY_BUILTINS_COMPILE && globals == NULL) {
1,040×
1479
            // for compile only, return value is the module function
1480
            ret = module_fun;
28×
1481
        } else {
1482
            // execute module function and get return value
1483
            ret = mp_call_function_0(module_fun);
1,012×
1484
        }
1485

1486
        // finish nlr block, restore context and return value
1487
        nlr_pop();
1,030×
1488
        mp_globals_set(old_globals);
1,030×
1489
        mp_locals_set(old_locals);
1,030×
1490
        return ret;
1,030×
1491
    } else {
1492
        // exception; restore context and re-raise same exception
1493
        mp_globals_set(old_globals);
454×
1494
        mp_locals_set(old_locals);
454×
1495
        nlr_jump(nlr.ret_val);
454×
1496
    }
1497
}
1498

1499
#endif // MICROPY_ENABLE_COMPILER
1500

1501
NORETURN void m_malloc_fail(size_t num_bytes) {
104×
1502
    DEBUG_printf("memory allocation failed, allocating %u bytes\n", (uint)num_bytes);
1503
    #if MICROPY_ENABLE_GC
1504
    if (gc_is_locked()) {
104×
1505
        mp_raise_msg(&mp_type_MemoryError, MP_ERROR_TEXT("memory allocation failed, heap is locked"));
90×
1506
    }
1507
    #endif
1508
    mp_raise_msg_varg(&mp_type_MemoryError,
14×
1509
        MP_ERROR_TEXT("memory allocation failed, allocating %u bytes"), (uint)num_bytes);
14×
1510
}
1511

1512
#if MICROPY_ERROR_REPORTING == MICROPY_ERROR_REPORTING_NONE
1513

1514
NORETURN void mp_raise_type(const mp_obj_type_t *exc_type) {
1515
    nlr_raise(mp_obj_new_exception(exc_type));
1516
}
1517

1518
NORETURN void mp_raise_ValueError_no_msg(void) {
1519
    mp_raise_type(&mp_type_ValueError);
1520
}
1521

1522
NORETURN void mp_raise_TypeError_no_msg(void) {
1523
    mp_raise_type(&mp_type_TypeError);
1524
}
1525

1526
NORETURN void mp_raise_NotImplementedError_no_msg(void) {
1527
    mp_raise_type(&mp_type_NotImplementedError);
1528
}
1529

1530
#else
1531

1532
NORETURN void mp_raise_msg(const mp_obj_type_t *exc_type, mp_rom_error_text_t msg) {
2,272×
1533
    if (msg == NULL) {
2,272×
1534
        nlr_raise(mp_obj_new_exception(exc_type));
804×
1535
    } else {
1536
        nlr_raise(mp_obj_new_exception_msg(exc_type, msg));
1,468×
1537
    }
1538
}
1539

1540
NORETURN void mp_raise_msg_varg(const mp_obj_type_t *exc_type, mp_rom_error_text_t fmt, ...) {
1,067×
1541
    va_list args;
1542
    va_start(args, fmt);
1,067×
1543
    mp_obj_t exc = mp_obj_new_exception_msg_vlist(exc_type, fmt, args);
1,067×
1544
    va_end(args);
1,067×
1545
    nlr_raise(exc);
1,067×
1546
}
1547

1548
NORETURN void mp_raise_ValueError(mp_rom_error_text_t msg) {
778×
1549
    mp_raise_msg(&mp_type_ValueError, msg);
778×
1550
}
1551

1552
NORETURN void mp_raise_TypeError(mp_rom_error_text_t msg) {
256×
1553
    mp_raise_msg(&mp_type_TypeError, msg);
256×
1554
}
1555

1556
NORETURN void mp_raise_NotImplementedError(mp_rom_error_text_t msg) {
414×
1557
    mp_raise_msg(&mp_type_NotImplementedError, msg);
414×
1558
}
1559

1560
#endif
1561

1562
NORETURN void mp_raise_OSError(int errno_) {
230×
1563
    nlr_raise(mp_obj_new_exception_arg1(&mp_type_OSError, MP_OBJ_NEW_SMALL_INT(errno_)));
230×
1564
}
1565

1566
#if MICROPY_STACK_CHECK || MICROPY_ENABLE_PYSTACK
1567
NORETURN void mp_raise_recursion_depth(void) {
23×
1568
    nlr_raise(mp_obj_new_exception_arg1(&mp_type_RuntimeError,
23×
1569
        MP_OBJ_NEW_QSTR(MP_QSTR_maximum_space_recursion_space_depth_space_exceeded)));
1570
}
1571
#endif
Troubleshooting · Open an Issue · Sales · Support · ENTERPRISE · CAREERS · STATUS
BLOG · TWITTER · Legal & Privacy · Supported CI Services · What's a CI service? · Automated Testing

© 2022 Coveralls, Inc