Skip to content

Commit

Permalink
py/objtype: Allow passing keyword arguments to native base __init__.
Browse files Browse the repository at this point in the history
Fixes issue micropython#15465.

Signed-off-by: stijn <[email protected]>
  • Loading branch information
stinos committed Aug 22, 2024
1 parent 185116e commit dcabe46
Show file tree
Hide file tree
Showing 2 changed files with 32 additions and 3 deletions.
6 changes: 3 additions & 3 deletions py/objtype.c
Original file line number Diff line number Diff line change
Expand Up @@ -85,14 +85,14 @@ static int instance_count_native_bases(const mp_obj_type_t *type, const mp_obj_t

// This wrapper function allows a subclass of a native type to call the
// __init__() method (corresponding to type->make_new) of the native type.
static mp_obj_t native_base_init_wrapper(size_t n_args, const mp_obj_t *args) {
static mp_obj_t native_base_init_wrapper(size_t n_args, const mp_obj_t *args, mp_map_t *kw_args) {
mp_obj_instance_t *self = MP_OBJ_TO_PTR(args[0]);
const mp_obj_type_t *native_base = NULL;
instance_count_native_bases(self->base.type, &native_base);
self->subobj[0] = MP_OBJ_TYPE_GET_SLOT(native_base, make_new)(native_base, n_args - 1, 0, args + 1);
self->subobj[0] = MP_OBJ_TYPE_GET_SLOT(native_base, make_new)(native_base, n_args - 1, kw_args->used, args + 1);
return mp_const_none;
}
static MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(native_base_init_wrapper_obj, 1, MP_OBJ_FUN_ARGS_MAX, native_base_init_wrapper);
static MP_DEFINE_CONST_FUN_OBJ_KW(native_base_init_wrapper_obj, 1, native_base_init_wrapper);

#if !MICROPY_CPYTHON_COMPAT
static
Expand Down
29 changes: 29 additions & 0 deletions tests/basics/subclass_native_init.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,35 @@ def __init__(self, a, b):
super().__init__([a, b])
print(L(2, 3))

# with keyword arguments, with star arguments and without because those use different C calls
class D(dict):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
print(D())
print(D([('a', 1)]))
print(D([('a', 1)], a=2, b=3))
print(D(a=2, b=3))

class D(dict):
def __init__(self):
super().__init__()
print(D())

class D(dict):
def __init__(self):
super().__init__([])
print(D())

class D(dict):
def __init__(self):
super().__init__(a=1)
print(D())

class D(dict):
def __init__(self):
super().__init__([], a=1)
print(D())

# inherits implicitly from object
class A:
def __init__(self):
Expand Down

0 comments on commit dcabe46

Please sign in to comment.