From c6c9e654f8d36d90621ecb1a9c9ac0df5d684f5f Mon Sep 17 00:00:00 2001 From: Emmanuel Leblond Date: Tue, 7 Feb 2017 00:33:49 +0100 Subject: [PATCH 1/4] py: Implement __dict__ for class --- py/objtype.c | 11 +++++++++++ tests/basics/class_dict.py | 12 ++++++++++++ 2 files changed, 23 insertions(+) create mode 100644 tests/basics/class_dict.py diff --git a/py/objtype.c b/py/objtype.c index c20b0693e522f..3776efca75771 100644 --- a/py/objtype.c +++ b/py/objtype.c @@ -828,6 +828,17 @@ STATIC void type_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) { dest[0] = MP_OBJ_NEW_QSTR(self->name); return; } + if (attr == MP_QSTR___dict__) { + mp_map_t *map = mp_obj_dict_get_map(self->locals_dict); + mp_obj_t attr_dict = mp_obj_new_dict(0); + for (mp_uint_t i = 0; i < map->alloc; ++i) { + if (MP_MAP_SLOT_IS_FILLED(map, i)) { + mp_obj_dict_store(attr_dict, map->table[i].key, map->table[i].value); + } + } + dest[0] = attr_dict; + return; + } #endif struct class_lookup_data lookup = { .obj = (mp_obj_instance_t*)self, diff --git a/tests/basics/class_dict.py b/tests/basics/class_dict.py new file mode 100644 index 0000000000000..4744d580f2092 --- /dev/null +++ b/tests/basics/class_dict.py @@ -0,0 +1,12 @@ +import sys + +class Foo: + a = 1 + def b(): + pass + +if not hasattr(Foo, "__dict__"): + print("SKIP") + sys.exit() + +print(Foo.__dict__ == {'a': 1, 'b': Foo.b}) From 6247e5111b3679377ad4ea1bd31a8ef8adbc2ea1 Mon Sep 17 00:00:00 2001 From: Emmanuel Leblond Date: Tue, 7 Feb 2017 09:58:05 +0100 Subject: [PATCH 2/4] py: Fix __dict__ for C class without locals_attr field --- py/objtype.c | 10 ++++++---- tests/basics/class_dict.py | 4 +++- tests/basics/class_dict.py.exp | 2 ++ 3 files changed, 11 insertions(+), 5 deletions(-) create mode 100644 tests/basics/class_dict.py.exp diff --git a/py/objtype.c b/py/objtype.c index 3776efca75771..77f1a9bd2bb6e 100644 --- a/py/objtype.c +++ b/py/objtype.c @@ -829,11 +829,13 @@ STATIC void type_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) { return; } if (attr == MP_QSTR___dict__) { - mp_map_t *map = mp_obj_dict_get_map(self->locals_dict); mp_obj_t attr_dict = mp_obj_new_dict(0); - for (mp_uint_t i = 0; i < map->alloc; ++i) { - if (MP_MAP_SLOT_IS_FILLED(map, i)) { - mp_obj_dict_store(attr_dict, map->table[i].key, map->table[i].value); + if (self->locals_dict != MP_OBJ_NULL) { + mp_map_t *map = mp_obj_dict_get_map(self->locals_dict); + for (mp_uint_t i = 0; i < map->alloc; ++i) { + if (MP_MAP_SLOT_IS_FILLED(map, i)) { + mp_obj_dict_store(attr_dict, map->table[i].key, map->table[i].value); + } } } dest[0] = attr_dict; diff --git a/tests/basics/class_dict.py b/tests/basics/class_dict.py index 4744d580f2092..f80f45d87c53e 100644 --- a/tests/basics/class_dict.py +++ b/tests/basics/class_dict.py @@ -9,4 +9,6 @@ def b(): print("SKIP") sys.exit() -print(Foo.__dict__ == {'a': 1, 'b': Foo.b}) +print(Foo.__dict__ == {'a': 1, 'b': Foo.b, '__qualname__': 'Foo', '__module__': '__main__'}) +# Also test C implemented class without `locals_attr` +print(type.__dict__ == {}) diff --git a/tests/basics/class_dict.py.exp b/tests/basics/class_dict.py.exp new file mode 100644 index 0000000000000..dbde422651c9a --- /dev/null +++ b/tests/basics/class_dict.py.exp @@ -0,0 +1,2 @@ +True +True From 2551e993bb68337502825c622e06fa75abd60c61 Mon Sep 17 00:00:00 2001 From: Emmanuel Leblond Date: Sat, 11 Feb 2017 10:14:56 +0100 Subject: [PATCH 3/4] py: Fix cast error with __dict__ for C class on picky compiler --- py/objtype.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/py/objtype.c b/py/objtype.c index 77f1a9bd2bb6e..c0819efe8dde7 100644 --- a/py/objtype.c +++ b/py/objtype.c @@ -830,8 +830,8 @@ STATIC void type_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) { } if (attr == MP_QSTR___dict__) { mp_obj_t attr_dict = mp_obj_new_dict(0); - if (self->locals_dict != MP_OBJ_NULL) { - mp_map_t *map = mp_obj_dict_get_map(self->locals_dict); + if (self->locals_dict != NULL) { + mp_map_t *map = mp_obj_dict_get_map(MP_OBJ_FROM_PTR(self->locals_dict)); for (mp_uint_t i = 0; i < map->alloc; ++i) { if (MP_MAP_SLOT_IS_FILLED(map, i)) { mp_obj_dict_store(attr_dict, map->table[i].key, map->table[i].value); From 5fb42efecb56e155b4dea4e6ea92b42ae8d9e6d9 Mon Sep 17 00:00:00 2001 From: Emmanuel Leblond Date: Sun, 26 Feb 2017 22:51:19 +0100 Subject: [PATCH 4/4] py: Simplify implementation of __dict__ for class --- py/objtype.c | 13 ++++--------- 1 file changed, 4 insertions(+), 9 deletions(-) diff --git a/py/objtype.c b/py/objtype.c index c0819efe8dde7..93c45203bfacb 100644 --- a/py/objtype.c +++ b/py/objtype.c @@ -829,16 +829,11 @@ STATIC void type_attr(mp_obj_t self_in, qstr attr, mp_obj_t *dest) { return; } if (attr == MP_QSTR___dict__) { - mp_obj_t attr_dict = mp_obj_new_dict(0); - if (self->locals_dict != NULL) { - mp_map_t *map = mp_obj_dict_get_map(MP_OBJ_FROM_PTR(self->locals_dict)); - for (mp_uint_t i = 0; i < map->alloc; ++i) { - if (MP_MAP_SLOT_IS_FILLED(map, i)) { - mp_obj_dict_store(attr_dict, map->table[i].key, map->table[i].value); - } - } + if (self->locals_dict == NULL) { + dest[0] = mp_obj_new_dict(0); + } else { + dest[0] = self->locals_dict; } - dest[0] = attr_dict; return; } #endif pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy