summaryrefslogtreecommitdiff
path: root/py
diff options
context:
space:
mode:
authorDan Halbert <halbert@halwitz.org>2020-03-05 17:47:01 -0500
committerDan Halbert <halbert@halwitz.org>2020-03-05 17:47:01 -0500
commit210c3274e5b91b603dad6ddeadd3ba2b743b24ae (patch)
treeff1a56e4cbca38068db152aea994b382c45cdaa8 /py
parent817b5be320b36b9cac59b195b1c19359783fe032 (diff)
parent4fa90261a37f0f729b52289cf54492ec7108e16b (diff)
Merge remote-tracking branch 'adafruit/master' into assert_pin-and-mp_const_none-cleanup
Diffstat (limited to 'py')
-rw-r--r--py/builtin.h7
-rw-r--r--py/builtinimport.c30
-rw-r--r--py/circuitpy_defns.mk13
-rw-r--r--py/circuitpy_mpconfig.h6
-rw-r--r--py/compile.c17
-rwxr-xr-xpy/gc_long_lived.c2
-rwxr-xr-xpy/mpconfig.h4
-rw-r--r--py/objmodule.c15
-rw-r--r--py/parse.c3
-rw-r--r--py/py.mk16
10 files changed, 102 insertions, 11 deletions
diff --git a/py/builtin.h b/py/builtin.h
index 84b99a8a4..6e0d5d9be 100644
--- a/py/builtin.h
+++ b/py/builtin.h
@@ -117,6 +117,13 @@ extern const mp_obj_module_t mp_module_websocket;
extern const mp_obj_module_t mp_module_webrepl;
extern const mp_obj_module_t mp_module_framebuf;
extern const mp_obj_module_t mp_module_btree;
+extern const mp_obj_module_t ulab_user_cmodule;
+extern mp_obj_module_t ulab_fft_module;
+extern mp_obj_module_t ulab_filter_module;
+extern mp_obj_module_t ulab_linalg_module;
+extern mp_obj_module_t ulab_numerical_module;
+extern mp_obj_module_t ulab_poly_module;
+
extern const char MICROPY_PY_BUILTINS_HELP_TEXT[];
diff --git a/py/builtinimport.c b/py/builtinimport.c
index 6ed0a7594..2be779c6c 100644
--- a/py/builtinimport.c
+++ b/py/builtinimport.c
@@ -400,21 +400,31 @@ mp_obj_t mp_builtin___import__(size_t n_args, const mp_obj_t *args) {
DEBUG_printf("Current path: %.*s\n", vstr_len(&path), vstr_str(&path));
if (stat == MP_IMPORT_STAT_NO_EXIST) {
- #if MICROPY_MODULE_WEAK_LINKS
- // check if there is a weak link to this module
- if (i == mod_len) {
- mp_map_elem_t *el = mp_map_lookup((mp_map_t*)&mp_builtin_module_weak_links_map, MP_OBJ_NEW_QSTR(mod_name), MP_MAP_LOOKUP);
+ // This is just the module name after the previous .
+ qstr current_module_name = qstr_from_strn(mod_str + last, i - last);
+ mp_map_elem_t *el = NULL;
+ if (outer_module_obj == MP_OBJ_NULL) {
+ el = mp_map_lookup((mp_map_t*)&mp_builtin_module_map,
+ MP_OBJ_NEW_QSTR(current_module_name),
+ MP_MAP_LOOKUP);
+ #if MICROPY_MODULE_WEAK_LINKS
+ // check if there is a weak link to this module
if (el == NULL) {
- goto no_exist;
+ el = mp_map_lookup((mp_map_t*)&mp_builtin_module_weak_links_map,
+ MP_OBJ_NEW_QSTR(current_module_name),
+ MP_MAP_LOOKUP);
}
- // found weak linked module
+ #endif
+ } else {
+ el = mp_map_lookup(&((mp_obj_module_t*) outer_module_obj)->globals->map,
+ MP_OBJ_NEW_QSTR(current_module_name),
+ MP_MAP_LOOKUP);
+ }
+
+ if (el != NULL && MP_OBJ_IS_TYPE(el->value, &mp_type_module)) {
module_obj = el->value;
mp_module_call_init(mod_name, module_obj);
} else {
- no_exist:
- #else
- {
- #endif
// couldn't find the file, so fail
if (MICROPY_ERROR_REPORTING == MICROPY_ERROR_REPORTING_TERSE) {
mp_raise_ImportError(translate("module not found"));
diff --git a/py/circuitpy_defns.mk b/py/circuitpy_defns.mk
index 68fa25d8d..92021d0d0 100644
--- a/py/circuitpy_defns.mk
+++ b/py/circuitpy_defns.mk
@@ -431,6 +431,19 @@ $(addprefix lib/,\
libm/atanf.c \
libm/atan2f.c \
)
+ifeq ($(MICROPY_PY_ULAB),1)
+SRC_LIBM += \
+$(addprefix lib/,\
+ libm/acoshf.c \
+ libm/asinhf.c \
+ libm/atanhf.c \
+ libm/erf_lgamma.c \
+ libm/log1pf.c \
+ libm/sf_erf.c \
+ libm/wf_lgamma.c \
+ libm/wf_tgamma.c \
+ )
+endif
endif
ifdef LD_TEMPLATE_FILE
diff --git a/py/circuitpy_mpconfig.h b/py/circuitpy_mpconfig.h
index 53cd7b0bb..61dd901ed 100644
--- a/py/circuitpy_mpconfig.h
+++ b/py/circuitpy_mpconfig.h
@@ -578,6 +578,12 @@ extern const struct _mp_obj_module_t ustack_module;
#define JSON_MODULE
#endif
+#if defined(MICROPY_PY_ULAB) && MICROPY_PY_ULAB
+#define ULAB_MODULE \
+ { MP_ROM_QSTR(MP_QSTR_ulab), MP_ROM_PTR(&ulab_user_cmodule) },
+#else
+#define ULAB_MODULE
+#endif
#if MICROPY_PY_URE
#define RE_MODULE { MP_ROM_QSTR(MP_QSTR_re), MP_ROM_PTR(&mp_module_ure) },
#else
diff --git a/py/compile.c b/py/compile.c
index 77715d3fe..d5fae0299 100644
--- a/py/compile.c
+++ b/py/compile.c
@@ -1711,6 +1711,16 @@ STATIC void compile_yield_from(compiler_t *comp) {
}
#if MICROPY_PY_ASYNC_AWAIT
+STATIC bool compile_require_async_context(compiler_t *comp, mp_parse_node_struct_t *pns) {
+ int scope_flags = comp->scope_cur->scope_flags;
+ if(scope_flags & MP_SCOPE_FLAG_GENERATOR) {
+ return true;
+ }
+ compile_syntax_error(comp, (mp_parse_node_t)pns,
+ translate("'async for' or 'async with' outside async function"));
+ return false;
+}
+
STATIC void compile_await_object_method(compiler_t *comp, qstr method) {
EMIT_ARG(load_method, method, false);
EMIT_ARG(call_method, 0, 0, 0);
@@ -1720,6 +1730,10 @@ STATIC void compile_await_object_method(compiler_t *comp, qstr method) {
STATIC void compile_async_for_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) {
// comp->break_label |= MP_EMIT_BREAK_FROM_FOR;
+ if(!compile_require_async_context(comp, pns)) {
+ return;
+ }
+
qstr context = MP_PARSE_NODE_LEAF_ARG(pns->nodes[1]);
uint while_else_label = comp_next_label(comp);
uint try_exception_label = comp_next_label(comp);
@@ -1857,6 +1871,9 @@ STATIC void compile_async_with_stmt_helper(compiler_t *comp, int n, mp_parse_nod
}
STATIC void compile_async_with_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) {
+ if(!compile_require_async_context(comp, pns)) {
+ return;
+ }
// get the nodes for the pre-bit of the with (the a as b, c as d, ... bit)
mp_parse_node_t *nodes;
int n = mp_parse_node_extract_list(&pns->nodes[0], PN_with_stmt_list, &nodes);
diff --git a/py/gc_long_lived.c b/py/gc_long_lived.c
index 01c22a7af..0e94390e9 100755
--- a/py/gc_long_lived.c
+++ b/py/gc_long_lived.c
@@ -89,7 +89,7 @@ mp_obj_dict_t *make_dict_long_lived(mp_obj_dict_t *dict, uint8_t max_depth) {
#ifndef MICROPY_ENABLE_GC
return dict;
#endif
- if (dict == NULL || max_depth == 0 || dict == &MP_STATE_VM(dict_main)) {
+ if (dict == NULL || max_depth == 0 || dict == &MP_STATE_VM(dict_main) || dict->map.is_fixed) {
return dict;
}
// Don't recurse unnecessarily. Return immediately if we've already seen this dict.
diff --git a/py/mpconfig.h b/py/mpconfig.h
index 1512c7d3a..8f78ade5c 100755
--- a/py/mpconfig.h
+++ b/py/mpconfig.h
@@ -1173,6 +1173,10 @@ typedef double mp_float_t;
#define MICROPY_PY_UJSON (0)
#endif
+#ifndef MICROPY_PY_ULAB
+#define MICROPY_PY_ULAB (0)
+#endif
+
#ifndef MICROPY_PY_URE
#define MICROPY_PY_URE (0)
#endif
diff --git a/py/objmodule.c b/py/objmodule.c
index 627ba79e8..7405a6919 100644
--- a/py/objmodule.c
+++ b/py/objmodule.c
@@ -69,6 +69,13 @@ STATIC void module_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) {
// delete/store attribute
mp_obj_dict_t *dict = self->globals;
if (dict->map.is_fixed) {
+ mp_map_elem_t *elem = mp_map_lookup(&dict->map, MP_OBJ_NEW_QSTR(attr), MP_MAP_LOOKUP);
+ // Return success if the given value is already in the dictionary. This is the case for
+ // native packages with native submodules.
+ if (elem != NULL && elem->value == dest[1]) {
+ dest[0] = MP_OBJ_NULL; // indicate success
+ return;
+ } else
#if MICROPY_CAN_OVERRIDE_BUILTINS
if (dict == &mp_module_builtins_globals) {
if (MP_STATE_VM(mp_module_builtins_override_dict) == NULL) {
@@ -206,6 +213,14 @@ STATIC const mp_rom_map_elem_t mp_builtin_module_table[] = {
{ MP_ROM_QSTR(MP_QSTR_ujson), MP_ROM_PTR(&mp_module_ujson) },
#endif
#endif
+#if MICROPY_PY_ULAB
+#if CIRCUITPY
+// CircuitPython: Defined in MICROPY_PORT_BUILTIN_MODULES, so not defined here.
+// TODO: move to shared-bindings/
+#else
+ { MP_ROM_QSTR(MP_QSTR_ulab), MP_ROM_PTR(&ulab_user_cmodule) },
+#endif
+#endif
#if MICROPY_PY_URE
#if CIRCUITPY
// CircuitPython: Defined in MICROPY_PORT_BUILTIN_MODULES, so not defined here.
diff --git a/py/parse.c b/py/parse.c
index 911b891e0..864528470 100644
--- a/py/parse.c
+++ b/py/parse.c
@@ -477,6 +477,9 @@ STATIC void push_result_token(parser_t *parser, uint8_t rule_id) {
mp_parse_node_t pn;
mp_lexer_t *lex = parser->lexer;
if (lex->tok_kind == MP_TOKEN_NAME) {
+ if(lex->vstr.len >= (1 << (8 * MICROPY_QSTR_BYTES_IN_LEN))) {
+ mp_raise_msg(&mp_type_SyntaxError, translate("Name too long"));
+ }
qstr id = qstr_from_strn(lex->vstr.buf, lex->vstr.len);
#if MICROPY_COMP_CONST
// if name is a standalone identifier, look it up in the table of dynamic constants
diff --git a/py/py.mk b/py/py.mk
index a73b47f37..5e044947a 100644
--- a/py/py.mk
+++ b/py/py.mk
@@ -105,6 +105,22 @@ $(BUILD)/$(BTREE_DIR)/%.o: CFLAGS += -Wno-old-style-definition -Wno-sign-compare
$(BUILD)/extmod/modbtree.o: CFLAGS += $(BTREE_DEFS)
endif
+ifeq ($(MICROPY_PY_ULAB),1)
+SRC_MOD += $(addprefix extmod/ulab/code/, \
+create.c \
+fft.c \
+filter.c \
+linalg.c \
+ndarray.c \
+numerical.c \
+poly.c \
+ulab.c \
+vectorise.c \
+ )
+CFLAGS_MOD += -DMICROPY_PY_ULAB=1 -DMODULE_ULAB_ENABLED=1
+$(BUILD)/extmod/ulab/code/%.o: CFLAGS += -Wno-sign-compare -Wno-missing-prototypes -Wno-unused-parameter -Wno-missing-declarations -Wno-error -Wno-shadow -Wno-maybe-uninitialized -DCIRCUITPY
+endif
+
# External modules written in C.
ifneq ($(USER_C_MODULES),)
# pre-define USERMOD variables as expanded so that variables are immediate