From c90c0f68a2f1ee8563497a5380a16e71d18d702a Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 01:57:00 +0200 Subject: [PATCH 01/29] Move INT_FMT, etc. declaration into global mpconfig.h . This in particular makes it available for stm port. --- py/mpconfig.h | 14 ++++++++++++++ unix-cpy/mpconfigport.h | 4 ---- unix/mpconfigport.h | 4 ---- 3 files changed, 14 insertions(+), 8 deletions(-) diff --git a/py/mpconfig.h b/py/mpconfig.h index 17c5a770c4..44095bd10b 100644 --- a/py/mpconfig.h +++ b/py/mpconfig.h @@ -4,6 +4,20 @@ #include +#ifndef INT_FMT +// printf format spec to use for machine_int_t and friends +#ifdef __LP64__ +// Archs where machine_int_t == long, long != int +#define UINT_FMT "%lu" +#define INT_FMT "%ld" +#else +// Archs where machine_int_t == int +#define UINT_FMT "%u" +#define INT_FMT "%d" +#endif +#endif //INT_FMT + + // Any options not explicitly set in mpconfigport.h will get default // values below. diff --git a/unix-cpy/mpconfigport.h b/unix-cpy/mpconfigport.h index db72b31455..983b166a55 100644 --- a/unix-cpy/mpconfigport.h +++ b/unix-cpy/mpconfigport.h @@ -11,15 +11,11 @@ #ifdef __LP64__ typedef long machine_int_t; // must be pointer size typedef unsigned long machine_uint_t; // must be pointer size -#define UINT_FMT "%lu" -#define INT_FMT "%ld" #else // These are definitions for machines where sizeof(int) == sizeof(void*), // regardless for actual size. typedef int machine_int_t; // must be pointer size typedef unsigned int machine_uint_t; // must be pointer size -#define UINT_FMT "%u" -#define INT_FMT "%d" #endif #define BYTES_PER_WORD sizeof(machine_int_t) diff --git a/unix/mpconfigport.h b/unix/mpconfigport.h index 3d0dc8a567..36cf138c17 100644 --- a/unix/mpconfigport.h +++ b/unix/mpconfigport.h @@ -11,15 +11,11 @@ #ifdef __LP64__ typedef long machine_int_t; // must be pointer size typedef unsigned long machine_uint_t; // must be pointer size -#define UINT_FMT "%lu" -#define INT_FMT "%ld" #else // These are definitions for machines where sizeof(int) == sizeof(void*), // regardless for actual size. typedef int machine_int_t; // must be pointer size typedef unsigned int machine_uint_t; // must be pointer size -#define UINT_FMT "%u" -#define INT_FMT "%d" #endif #define BYTES_PER_WORD sizeof(machine_int_t) From 1c6de11f772afae9b4155f8a654cadd05125a2de Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Fri, 3 Jan 2014 02:41:17 +0200 Subject: [PATCH 02/29] Add basic implementation of slice object. So far, only start and stop integer indexes are supported. Step is not supported, as well as objects of arbitrary types. --- py/obj.h | 5 ++++ py/objslice.c | 59 +++++++++++++++++++++++++++++++++++++++++++++++ stm/Makefile | 1 + unix-cpy/Makefile | 1 + unix/Makefile | 1 + 5 files changed, 67 insertions(+) create mode 100644 py/objslice.c diff --git a/py/obj.h b/py/obj.h index 7b4b0656f2..16c7c36dd1 100644 --- a/py/obj.h +++ b/py/obj.h @@ -144,6 +144,7 @@ mp_obj_t mp_obj_new_list(uint n, mp_obj_t *items); mp_obj_t mp_obj_new_list_reverse(uint n, mp_obj_t *items); mp_obj_t mp_obj_new_dict(int n_args); mp_obj_t mp_obj_new_set(int n_args, mp_obj_t *items); +mp_obj_t mp_obj_new_slice(mp_obj_t start, mp_obj_t stop, mp_obj_t step); mp_obj_t mp_obj_new_bound_meth(mp_obj_t self, mp_obj_t meth); mp_obj_t mp_obj_new_class(struct _mp_map_t *class_locals); mp_obj_t mp_obj_new_instance(mp_obj_t clas); @@ -214,6 +215,10 @@ mp_obj_t mp_obj_dict_store(mp_obj_t self_in, mp_obj_t key, mp_obj_t value); // set void mp_obj_set_store(mp_obj_t self_in, mp_obj_t item); +// slice +extern const mp_obj_type_t slice_type; +void mp_obj_slice_get(mp_obj_t self_in, machine_int_t *start, machine_int_t *stop, machine_int_t *step); + // functions typedef struct _mp_obj_fun_native_t { // need this so we can define const objects (to go in ROM) mp_obj_base_t base; diff --git a/py/objslice.c b/py/objslice.c new file mode 100644 index 0000000000..619899b232 --- /dev/null +++ b/py/objslice.c @@ -0,0 +1,59 @@ +#include +#include +#include +#include + +#include "nlr.h" +#include "misc.h" +#include "mpconfig.h" +#include "obj.h" +#include "runtime0.h" + +#if MICROPY_ENABLE_SLICE + +// TODO: This implements only variant of slice with 2 integer args only. +// CPython supports 3rd arg (step), plus args can be arbitrary Python objects. +typedef struct _mp_obj_slice_t { + mp_obj_base_t base; + machine_int_t start; + machine_int_t stop; +} mp_obj_slice_t; + +void slice_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t o_in) { + mp_obj_slice_t *o = o_in; + print(env, "slice(" INT_FMT ", " INT_FMT ")", o->start, o->stop); +} + +const mp_obj_type_t slice_type = { + { &mp_const_type }, + "slice", + slice_print, + NULL, // call_n + NULL, // unary_op + NULL, // binary_op + NULL, // getiter + NULL, // iternext + { { NULL, NULL }, }, // method list +}; + +// TODO: Make sure to handle "empty" values, which are signified by None in CPython +mp_obj_t mp_obj_new_slice(mp_obj_t ostart, mp_obj_t ostop, mp_obj_t ostep) { + assert(ostep == NULL); + machine_int_t start = mp_obj_get_int(ostart); + machine_int_t stop = mp_obj_get_int(ostop); + mp_obj_slice_t *o = m_new(mp_obj_slice_t, 1); + o->base.type = &slice_type; + o->start = start; + o->stop = stop; + return (mp_obj_t)o; +} + +void mp_obj_slice_get(mp_obj_t self_in, machine_int_t *start, machine_int_t *stop, machine_int_t *step) { + assert(MP_OBJ_IS_TYPE(self_in, &slice_type)); + mp_obj_slice_t *self = self_in; + *start = self->start; + *stop = self->stop; + *step = 1; +} + +#endif diff --git a/stm/Makefile b/stm/Makefile index d6c77e2bd7..e84e21eae2 100644 --- a/stm/Makefile +++ b/stm/Makefile @@ -78,6 +78,7 @@ PY_O = \ objnone.o \ objrange.o \ objset.o \ + objslice.o \ objstr.o \ objtuple.o \ objtype.o \ diff --git a/unix-cpy/Makefile b/unix-cpy/Makefile index 48c3179460..7fee3438fb 100644 --- a/unix-cpy/Makefile +++ b/unix-cpy/Makefile @@ -43,6 +43,7 @@ PY_O = \ objnone.o \ objrange.o \ objset.o \ + objslice.o \ objstr.o \ objtuple.o \ objtype.o \ diff --git a/unix/Makefile b/unix/Makefile index fd5b6b43e0..38d6ba8e15 100644 --- a/unix/Makefile +++ b/unix/Makefile @@ -50,6 +50,7 @@ PY_O = \ objnone.o \ objrange.o \ objset.o \ + objslice.o \ objstr.o \ objtuple.o \ objtype.o \ From ded0a1efa5744235fbb4cd07c96598018a3661eb Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Fri, 3 Jan 2014 02:48:56 +0200 Subject: [PATCH 03/29] Implement BUILD_SLICE opcode (2-arg version). --- py/vm.c | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/py/vm.c b/py/vm.c index c549e2b490..35dcbea523 100644 --- a/py/vm.c +++ b/py/vm.c @@ -410,6 +410,18 @@ bool mp_execute_byte_code_2(const byte **ip_in_out, mp_obj_t *fastn, mp_obj_t ** sp++; break; + case MP_BC_BUILD_SLICE: + DECODE_UINT; + if (unum == 2) { + obj2 = POP(); + obj1 = TOP(); + SET_TOP(mp_obj_new_slice(obj1, obj2, NULL)); + } else { + printf("3-argument slice is not supported\n"); + assert(0); + } + break; + case MP_BC_UNPACK_SEQUENCE: DECODE_UINT; rt_unpack_sequence(sp[0], unum, sp - unum + 1); From 31ba60f8364a4009ddc3d45fee90c84b43d88d2c Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Fri, 3 Jan 2014 02:51:16 +0200 Subject: [PATCH 04/29] str: Initial implementation of string slicing. Only step=1 and non-negative indexes are supported so far. --- py/objstr.c | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/py/objstr.c b/py/objstr.c index 48abf4951d..46adabcec9 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -29,7 +29,21 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { case RT_BINARY_OP_SUBSCR: // string access // XXX a massive hack! - return mp_obj_new_int(lhs_str[mp_obj_get_int(rhs_in)]); + + // TODO: need predicate to check for int-like type (bools are such for example) + // ["no", "yes"][1 == 2] is common idiom + if (MP_OBJ_IS_SMALL_INT(rhs_in)) { + // TODO: This implements byte string access for single index so far + return mp_obj_new_int(lhs_str[mp_obj_get_int(rhs_in)]); + } else if (MP_OBJ_IS_TYPE(rhs_in, &slice_type)) { + int start, stop, step; + mp_obj_slice_get(rhs_in, &start, &stop, &step); + assert(step == 1); + return mp_obj_new_str(qstr_from_strn_copy(lhs_str + start, stop - start)); + } else { + // Throw TypeError here + assert(0); + } case RT_BINARY_OP_ADD: case RT_BINARY_OP_INPLACE_ADD: From cd22627f781080fb245dd6999f2158c8099379b0 Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Fri, 3 Jan 2014 03:01:12 +0200 Subject: [PATCH 05/29] Enable slice support in config. --- py/mpconfig.h | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/py/mpconfig.h b/py/mpconfig.h index 44095bd10b..56495d9156 100644 --- a/py/mpconfig.h +++ b/py/mpconfig.h @@ -25,3 +25,9 @@ #ifndef MICROPY_MEM_STATS #define MICROPY_MEM_STATS (1) #endif + +// Whether to support slice object and correspondingly +// slice subscript operators +#ifndef MICROPY_ENABLE_SLICE +#define MICROPY_ENABLE_SLICE (1) +#endif From 59800afae9f74571eea5bb463a28fd9bd8251150 Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Fri, 3 Jan 2014 23:35:32 +0200 Subject: [PATCH 06/29] slice: Implement special handling of omitted start/stop indexes. --- py/objslice.c | 19 +++++++++++++++++-- 1 file changed, 17 insertions(+), 2 deletions(-) diff --git a/py/objslice.c b/py/objslice.c index 619899b232..03607e4c3e 100644 --- a/py/objslice.c +++ b/py/objslice.c @@ -39,8 +39,23 @@ const mp_obj_type_t slice_type = { // TODO: Make sure to handle "empty" values, which are signified by None in CPython mp_obj_t mp_obj_new_slice(mp_obj_t ostart, mp_obj_t ostop, mp_obj_t ostep) { assert(ostep == NULL); - machine_int_t start = mp_obj_get_int(ostart); - machine_int_t stop = mp_obj_get_int(ostop); + machine_int_t start = 0, stop = 0; + if (ostart != mp_const_none) { + start = mp_obj_get_int(ostart); + } + if (ostop != mp_const_none) { + stop = mp_obj_get_int(ostop); + if (stop == 0) { + // [x:0] is a special case - in our slice object, stop = 0 means + // "end of sequence". Fortunately, [x:0] is an empty seqence for + // any x (including negative). [x:x] is also always empty sequence. + // but x also can be 0. But note that b""[x:x] is b"" for any x (i.e. + // no IndexError, at least in Python 3.3.3). So, we just use -1's to + // signify that. -1 is catchy "special" number in case someone will + // try to print [x:0] slice ever. + start = stop = -1; + } + } mp_obj_slice_t *o = m_new(mp_obj_slice_t, 1); o->base.type = &slice_type; o->start = start; From decad08ef57aa3cf3960ce65e29b194cb97c6d22 Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Fri, 3 Jan 2014 23:36:56 +0200 Subject: [PATCH 07/29] str: Handle non-positive slice indexes. --- py/objstr.c | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/py/objstr.c b/py/objstr.c index 46adabcec9..54dd087a45 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -39,6 +39,13 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { int start, stop, step; mp_obj_slice_get(rhs_in, &start, &stop, &step); assert(step == 1); + int len = strlen(lhs_str); + if (start < 0) { + start = len + start; + } + if (stop <= 0) { + stop = len + stop; + } return mp_obj_new_str(qstr_from_strn_copy(lhs_str + start, stop - start)); } else { // Throw TypeError here From 26534cec8510323e8d1a313991b76320821c666b Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Fri, 3 Jan 2014 23:38:16 +0200 Subject: [PATCH 08/29] Add test for byte string slicing. --- tests/basics/tests/slice-bstr1.py | 27 +++++++++++++++++++++++++++ 1 file changed, 27 insertions(+) create mode 100644 tests/basics/tests/slice-bstr1.py diff --git a/tests/basics/tests/slice-bstr1.py b/tests/basics/tests/slice-bstr1.py new file mode 100644 index 0000000000..8b492b35cc --- /dev/null +++ b/tests/basics/tests/slice-bstr1.py @@ -0,0 +1,27 @@ +b"123"[0:1] + +b"123"[0:2] + +b"123"[:1] + +b"123"[1:] + +# Idiom for copying sequence +b"123"[:] + +b"123"[:-1] + +# Weird cases +b"123"[0:0] +b"123"[1:0] +b"123"[1:1] +b"123"[-1:-1] +b"123"[-3:] +b"123"[-3:3] +b"123"[0:] +b"123"[:0] +b"123"[:-3] +b"123"[:-4] +# No IndexError! +b""[1:1] +b""[-1:-1] From e606cb656165aff2424fb6ca45f09d606246d073 Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 01:34:23 +0200 Subject: [PATCH 09/29] slice: Allow building with MICROPY_ENABLE_SLICE=0. --- py/objstr.c | 2 ++ py/vm.c | 2 ++ 2 files changed, 4 insertions(+) diff --git a/py/objstr.c b/py/objstr.c index 54dd087a45..8e3e9d9025 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -35,6 +35,7 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { if (MP_OBJ_IS_SMALL_INT(rhs_in)) { // TODO: This implements byte string access for single index so far return mp_obj_new_int(lhs_str[mp_obj_get_int(rhs_in)]); +#if MICROPY_ENABLE_SLICE } else if (MP_OBJ_IS_TYPE(rhs_in, &slice_type)) { int start, stop, step; mp_obj_slice_get(rhs_in, &start, &stop, &step); @@ -47,6 +48,7 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { stop = len + stop; } return mp_obj_new_str(qstr_from_strn_copy(lhs_str + start, stop - start)); +#endif } else { // Throw TypeError here assert(0); diff --git a/py/vm.c b/py/vm.c index 35dcbea523..382780640b 100644 --- a/py/vm.c +++ b/py/vm.c @@ -410,6 +410,7 @@ bool mp_execute_byte_code_2(const byte **ip_in_out, mp_obj_t *fastn, mp_obj_t ** sp++; break; +#if MICROPY_ENABLE_SLICE case MP_BC_BUILD_SLICE: DECODE_UINT; if (unum == 2) { @@ -421,6 +422,7 @@ bool mp_execute_byte_code_2(const byte **ip_in_out, mp_obj_t *fastn, mp_obj_t ** assert(0); } break; +#endif case MP_BC_UNPACK_SEQUENCE: DECODE_UINT; From f8b9d3c41addea79851c355f014db9f0f256cdaf Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 01:38:26 +0200 Subject: [PATCH 10/29] str: Throw TypeError for invalid index type and clean up comments. --- py/objstr.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/py/objstr.c b/py/objstr.c index 8e3e9d9025..6a0721d45f 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -27,13 +27,11 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { const char *lhs_str = qstr_str(lhs->qstr); switch (op) { case RT_BINARY_OP_SUBSCR: - // string access - // XXX a massive hack! - // TODO: need predicate to check for int-like type (bools are such for example) // ["no", "yes"][1 == 2] is common idiom if (MP_OBJ_IS_SMALL_INT(rhs_in)) { // TODO: This implements byte string access for single index so far + // TODO: Handle negative indexes. return mp_obj_new_int(lhs_str[mp_obj_get_int(rhs_in)]); #if MICROPY_ENABLE_SLICE } else if (MP_OBJ_IS_TYPE(rhs_in, &slice_type)) { @@ -50,8 +48,9 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { return mp_obj_new_str(qstr_from_strn_copy(lhs_str + start, stop - start)); #endif } else { - // Throw TypeError here - assert(0); + // Message doesn't match CPython, but we don't have so much bytes as they + // to spend them on verbose wording + nlr_jump(mp_obj_new_exception_msg(rt_q_TypeError, "index must be int")); } case RT_BINARY_OP_ADD: From c8d1384fc0c7aafa5dee3445ece20f4e43dfa9c1 Mon Sep 17 00:00:00 2001 From: Damien George Date: Sat, 4 Jan 2014 01:06:10 +0000 Subject: [PATCH 11/29] Fix int -> machine_int_t; add print to slice test. --- py/objstr.c | 2 +- tests/basics/tests/slice-bstr1.py | 36 +++++++++++++++---------------- 2 files changed, 19 insertions(+), 19 deletions(-) diff --git a/py/objstr.c b/py/objstr.c index 6a0721d45f..59547e3cd6 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -35,7 +35,7 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { return mp_obj_new_int(lhs_str[mp_obj_get_int(rhs_in)]); #if MICROPY_ENABLE_SLICE } else if (MP_OBJ_IS_TYPE(rhs_in, &slice_type)) { - int start, stop, step; + machine_int_t start, stop, step; mp_obj_slice_get(rhs_in, &start, &stop, &step); assert(step == 1); int len = strlen(lhs_str); diff --git a/tests/basics/tests/slice-bstr1.py b/tests/basics/tests/slice-bstr1.py index 8b492b35cc..0bed959141 100644 --- a/tests/basics/tests/slice-bstr1.py +++ b/tests/basics/tests/slice-bstr1.py @@ -1,27 +1,27 @@ -b"123"[0:1] +print(b"123"[0:1]) -b"123"[0:2] +print(b"123"[0:2]) -b"123"[:1] +print(b"123"[:1]) -b"123"[1:] +print(b"123"[1:]) # Idiom for copying sequence -b"123"[:] +print(b"123"[:]) -b"123"[:-1] +print(b"123"[:-1]) # Weird cases -b"123"[0:0] -b"123"[1:0] -b"123"[1:1] -b"123"[-1:-1] -b"123"[-3:] -b"123"[-3:3] -b"123"[0:] -b"123"[:0] -b"123"[:-3] -b"123"[:-4] +print(b"123"[0:0]) +print(b"123"[1:0]) +print(b"123"[1:1]) +print(b"123"[-1:-1]) +print(b"123"[-3:]) +print(b"123"[-3:3]) +print(b"123"[0:]) +print(b"123"[:0]) +print(b"123"[:-3]) +print(b"123"[:-4]) # No IndexError! -b""[1:1] -b""[-1:-1] +print(b""[1:1]) +print(b""[-1:-1]) From 6ee1e383d6b95d0bb5f2902ec91b8d831e4b5803 Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 03:47:34 +0200 Subject: [PATCH 12/29] str slice: Trim slice indexes to be in range. --- py/objstr.c | 11 +++++++++++ tests/basics/tests/slice-bstr1.py | 5 +++++ 2 files changed, 16 insertions(+) diff --git a/py/objstr.c b/py/objstr.c index 59547e3cd6..54e6f37705 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -41,9 +41,20 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { int len = strlen(lhs_str); if (start < 0) { start = len + start; + if (start < 0) { + start = 0; + } + } else if (start > len) { + start = len; } if (stop <= 0) { stop = len + stop; + // CPython returns empty string in such case + if (stop < 0) { + stop = start; + } + } else if (stop > len) { + stop = len; } return mp_obj_new_str(qstr_from_strn_copy(lhs_str + start, stop - start)); #endif diff --git a/tests/basics/tests/slice-bstr1.py b/tests/basics/tests/slice-bstr1.py index 0bed959141..74dbc20617 100644 --- a/tests/basics/tests/slice-bstr1.py +++ b/tests/basics/tests/slice-bstr1.py @@ -22,6 +22,11 @@ print(b"123"[0:]) print(b"123"[:0]) print(b"123"[:-3]) print(b"123"[:-4]) +# Range check testing, don't segfault, please ;-) +print(b"123"[:1000000]) +print(b"123"[1000000:]) +print(b"123"[:-1000000]) +print(b"123"[-1000000:]) # No IndexError! print(b""[1:1]) print(b""[-1:-1]) From 2c62e262b2c84b077355d67c6302bd02f6a28552 Mon Sep 17 00:00:00 2001 From: stevie67 Date: Sat, 4 Jan 2014 03:02:32 +0100 Subject: [PATCH 13/29] Fix issue #62: Cache loses data Use the storage cache not only for writing but also for reading. This avoids reading stale data and thus data loss. --- stm/storage.c | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/stm/storage.c b/stm/storage.c index 6878de22e6..7342a53ac3 100644 --- a/stm/storage.c +++ b/stm/storage.c @@ -49,6 +49,16 @@ static uint8_t *cache_get_addr_for_write(uint32_t flash_addr) { return (uint8_t*)CACHE_MEM_START_ADDR + flash_addr - flash_sector_start; } +static uint8_t *cache_get_addr_for_read(uint32_t flash_addr) { + uint32_t flash_sector_start; + uint32_t flash_sector_size; + uint32_t flash_sector_id = flash_get_sector_info(flash_addr, &flash_sector_start, &flash_sector_size); + if (cache_flash_sector_id == flash_sector_id) + return (uint8_t*)CACHE_MEM_START_ADDR + flash_addr - flash_sector_start; + // not in cache, copy straight from flash + return (uint8_t*)flash_addr; +} + void storage_init(void) { if (!is_initialised) { cache_flash_sector_id = 0; @@ -131,8 +141,8 @@ bool storage_read_block(uint8_t *dest, uint32_t block) { return true; } else if (FLASH_PART1_START_BLOCK <= block && block < FLASH_PART1_START_BLOCK + FLASH_PART1_NUM_BLOCKS) { - // non-MBR block, just copy straight from flash - uint8_t *src = (uint8_t*)FLASH_MEM_START_ADDR + (block - FLASH_PART1_START_BLOCK) * BLOCK_SIZE; + uint32_t flash_addr = FLASH_MEM_START_ADDR + (block - FLASH_PART1_START_BLOCK) * BLOCK_SIZE; + uint8_t *src = cache_get_addr_for_read(flash_addr); memcpy(dest, src, BLOCK_SIZE); return true; From 2a5e6538b941d1fc9c1c0ef0bb0827b5ed2425d2 Mon Sep 17 00:00:00 2001 From: Damien George Date: Sat, 4 Jan 2014 12:34:36 +0000 Subject: [PATCH 14/29] stm: Add comments for storage read from cache. --- stm/storage.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/stm/storage.c b/stm/storage.c index 7342a53ac3..daee4adb5e 100644 --- a/stm/storage.c +++ b/stm/storage.c @@ -53,8 +53,10 @@ static uint8_t *cache_get_addr_for_read(uint32_t flash_addr) { uint32_t flash_sector_start; uint32_t flash_sector_size; uint32_t flash_sector_id = flash_get_sector_info(flash_addr, &flash_sector_start, &flash_sector_size); - if (cache_flash_sector_id == flash_sector_id) + if (cache_flash_sector_id == flash_sector_id) { + // in cache, copy from there return (uint8_t*)CACHE_MEM_START_ADDR + flash_addr - flash_sector_start; + } // not in cache, copy straight from flash return (uint8_t*)flash_addr; } @@ -141,6 +143,7 @@ bool storage_read_block(uint8_t *dest, uint32_t block) { return true; } else if (FLASH_PART1_START_BLOCK <= block && block < FLASH_PART1_START_BLOCK + FLASH_PART1_NUM_BLOCKS) { + // non-MBR block, get data from flash memory, possibly via cache uint32_t flash_addr = FLASH_MEM_START_ADDR + (block - FLASH_PART1_START_BLOCK) * BLOCK_SIZE; uint8_t *src = cache_get_addr_for_read(flash_addr); memcpy(dest, src, BLOCK_SIZE); From 9b8f424944a6144a1528e5d21dd474e6d833d1a1 Mon Sep 17 00:00:00 2001 From: Jonathan Greig Date: Sat, 4 Jan 2014 06:53:06 -0600 Subject: [PATCH 15/29] Added SVG vector text. --- logo/vector-text.svg | 137 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 137 insertions(+) create mode 100644 logo/vector-text.svg diff --git a/logo/vector-text.svg b/logo/vector-text.svg new file mode 100644 index 0000000000..fa8f9ba332 --- /dev/null +++ b/logo/vector-text.svg @@ -0,0 +1,137 @@ + + + + + + + + + + + + + + + + + + + + image/svg+xml + + + + + + + + + + + + + + + + + + + + + + + + From 116e6e0551dee938b4378c89e044a5eea38c009b Mon Sep 17 00:00:00 2001 From: Jonathan Greig Date: Sat, 4 Jan 2014 06:54:54 -0600 Subject: [PATCH 16/29] Added DXF R2000 vector text. --- logo/vector-text-R2000.dxf | 9888 ++++++++++++++++++++++++++++++++++++ 1 file changed, 9888 insertions(+) create mode 100644 logo/vector-text-R2000.dxf diff --git a/logo/vector-text-R2000.dxf b/logo/vector-text-R2000.dxf new file mode 100644 index 0000000000..a963203b3f --- /dev/null +++ b/logo/vector-text-R2000.dxf @@ -0,0 +1,9888 @@ + 0 +SECTION + 2 +HEADER + 9 +$ACADVER + 1 +AC1015 + 9 +$ACADMAINTVER + 70 + 6 + 9 +$DWGCODEPAGE + 3 +ANSI_1252 + 9 +$INSBASE + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$EXTMIN + 10 +0.0000000000000001 + 20 +0.0 + 30 +0.0 + 9 +$EXTMAX + 10 +3.692708053216686 + 20 +0.6839852852251591 + 30 +0.0 + 9 +$LIMMIN + 10 +0.0 + 20 +0.0 + 9 +$LIMMAX + 10 +12.0 + 20 +9.0 + 9 +$ORTHOMODE + 70 + 0 + 9 +$REGENMODE + 70 + 1 + 9 +$FILLMODE + 70 + 1 + 9 +$QTEXTMODE + 70 + 0 + 9 +$MIRRTEXT + 70 + 1 + 9 +$LTSCALE + 40 +1.0 + 9 +$ATTMODE + 70 + 1 + 9 +$TEXTSIZE + 40 +0.2 + 9 +$TRACEWID + 40 +0.05 + 9 +$TEXTSTYLE + 7 +Standard + 9 +$CLAYER + 8 +TEXT-RED + 9 +$CELTYPE + 6 +ByLayer + 9 +$CECOLOR + 62 + 256 + 9 +$CELTSCALE + 40 +1.0 + 9 +$DISPSILH + 70 + 0 + 9 +$DIMSCALE + 40 +1.0 + 9 +$DIMASZ + 40 +0.18 + 9 +$DIMEXO + 40 +0.0625 + 9 +$DIMDLI + 40 +0.38 + 9 +$DIMRND + 40 +0.0 + 9 +$DIMDLE + 40 +0.0 + 9 +$DIMEXE + 40 +0.18 + 9 +$DIMTP + 40 +0.0 + 9 +$DIMTM + 40 +0.0 + 9 +$DIMTXT + 40 +0.18 + 9 +$DIMCEN + 40 +0.09 + 9 +$DIMTSZ + 40 +0.0 + 9 +$DIMTOL + 70 + 0 + 9 +$DIMLIM + 70 + 0 + 9 +$DIMTIH + 70 + 1 + 9 +$DIMTOH + 70 + 1 + 9 +$DIMSE1 + 70 + 0 + 9 +$DIMSE2 + 70 + 0 + 9 +$DIMTAD + 70 + 0 + 9 +$DIMZIN + 70 + 0 + 9 +$DIMBLK + 1 + + 9 +$DIMASO + 70 + 1 + 9 +$DIMSHO + 70 + 1 + 9 +$DIMPOST + 1 + + 9 +$DIMAPOST + 1 + + 9 +$DIMALT + 70 + 0 + 9 +$DIMALTD + 70 + 2 + 9 +$DIMALTF + 40 +25.4 + 9 +$DIMLFAC + 40 +1.0 + 9 +$DIMTOFL + 70 + 0 + 9 +$DIMTVP + 40 +0.0 + 9 +$DIMTIX + 70 + 0 + 9 +$DIMSOXD + 70 + 0 + 9 +$DIMSAH + 70 + 0 + 9 +$DIMBLK1 + 1 + + 9 +$DIMBLK2 + 1 + + 9 +$DIMSTYLE + 2 +Standard + 9 +$DIMCLRD + 70 + 0 + 9 +$DIMCLRE + 70 + 0 + 9 +$DIMCLRT + 70 + 0 + 9 +$DIMTFAC + 40 +1.0 + 9 +$DIMGAP + 40 +0.09 + 9 +$DIMJUST + 70 + 0 + 9 +$DIMSD1 + 70 + 0 + 9 +$DIMSD2 + 70 + 0 + 9 +$DIMTOLJ + 70 + 1 + 9 +$DIMTZIN + 70 + 0 + 9 +$DIMALTZ + 70 + 0 + 9 +$DIMALTTZ + 70 + 0 + 9 +$DIMUPT + 70 + 0 + 9 +$DIMDEC + 70 + 3 + 9 +$DIMTDEC + 70 + 3 + 9 +$DIMALTU + 70 + 2 + 9 +$DIMALTTD + 70 + 2 + 9 +$DIMTXSTY + 7 +Standard + 9 +$DIMAUNIT + 70 + 0 + 9 +$DIMADEC + 70 + 0 + 9 +$DIMALTRND + 40 +0.0 + 9 +$DIMAZIN + 70 + 0 + 9 +$DIMDSEP + 70 + 46 + 9 +$DIMATFIT + 70 + 3 + 9 +$DIMFRAC + 70 + 0 + 9 +$DIMLDRBLK + 1 + + 9 +$DIMLUNIT + 70 + 2 + 9 +$DIMLWD + 70 + -2 + 9 +$DIMLWE + 70 + -2 + 9 +$DIMTMOVE + 70 + 2 + 9 +$LUNITS + 70 + 2 + 9 +$LUPREC + 70 + 3 + 9 +$SKETCHINC + 40 +0.1 + 9 +$FILLETRAD + 40 +0.5 + 9 +$AUNITS + 70 + 0 + 9 +$AUPREC + 70 + 0 + 9 +$MENU + 1 +. + 9 +$ELEVATION + 40 +0.0 + 9 +$PELEVATION + 40 +0.0 + 9 +$THICKNESS + 40 +0.0 + 9 +$LIMCHECK + 70 + 0 + 9 +$CHAMFERA + 40 +0.0 + 9 +$CHAMFERB + 40 +0.0 + 9 +$CHAMFERC + 40 +0.0 + 9 +$CHAMFERD + 40 +0.0 + 9 +$SKPOLY + 70 + 0 + 9 +$TDCREATE + 40 +2456662.269745891 + 9 +$TDUCREATE + 40 +2456662.519745903 + 9 +$TDUPDATE + 40 +2456662.282164352 + 9 +$TDUUPDATE + 40 +2456662.532164352 + 9 +$TDINDWG + 40 +0.0000000116 + 9 +$TDUSRTIMER + 40 +2456662.519895833 + 9 +$USRTIMER + 70 + 1 + 9 +$ANGBASE + 50 +0.0 + 9 +$ANGDIR + 70 + 0 + 9 +$PDMODE + 70 + 0 + 9 +$PDSIZE + 40 +0.0 + 9 +$PLINEWID + 40 +0.0 + 9 +$SPLFRAME + 70 + 0 + 9 +$SPLINETYPE + 70 + 6 + 9 +$SPLINESEGS + 70 + 8 + 9 +$HANDSEED + 5 +1D7 + 9 +$SURFTAB1 + 70 + 6 + 9 +$SURFTAB2 + 70 + 6 + 9 +$SURFTYPE + 70 + 6 + 9 +$SURFU + 70 + 6 + 9 +$SURFV + 70 + 6 + 9 +$UCSBASE + 2 + + 9 +$UCSNAME + 2 + + 9 +$UCSORG + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$UCSXDIR + 10 +1.0 + 20 +0.0 + 30 +0.0 + 9 +$UCSYDIR + 10 +0.0 + 20 +1.0 + 30 +0.0 + 9 +$UCSORTHOREF + 2 + + 9 +$UCSORTHOVIEW + 70 + 0 + 9 +$UCSORGTOP + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$UCSORGBOTTOM + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$UCSORGLEFT + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$UCSORGRIGHT + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$UCSORGFRONT + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$UCSORGBACK + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSBASE + 2 + + 9 +$PUCSNAME + 2 + + 9 +$PUCSORG + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSXDIR + 10 +1.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSYDIR + 10 +0.0 + 20 +1.0 + 30 +0.0 + 9 +$PUCSORTHOREF + 2 + + 9 +$PUCSORTHOVIEW + 70 + 0 + 9 +$PUCSORGTOP + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSORGBOTTOM + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSORGLEFT + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSORGRIGHT + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSORGFRONT + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PUCSORGBACK + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$USERI1 + 70 + 0 + 9 +$USERI2 + 70 + 0 + 9 +$USERI3 + 70 + 0 + 9 +$USERI4 + 70 + 0 + 9 +$USERI5 + 70 + 0 + 9 +$USERR1 + 40 +0.0 + 9 +$USERR2 + 40 +0.0 + 9 +$USERR3 + 40 +0.0 + 9 +$USERR4 + 40 +0.0 + 9 +$USERR5 + 40 +0.0 + 9 +$WORLDVIEW + 70 + 1 + 9 +$SHADEDGE + 70 + 3 + 9 +$SHADEDIF + 70 + 70 + 9 +$TILEMODE + 70 + 1 + 9 +$MAXACTVP + 70 + 64 + 9 +$PINSBASE + 10 +0.0 + 20 +0.0 + 30 +0.0 + 9 +$PLIMCHECK + 70 + 0 + 9 +$PEXTMIN + 10 +1.000000000000000E+20 + 20 +1.000000000000000E+20 + 30 +1.000000000000000E+20 + 9 +$PEXTMAX + 10 +-1.000000000000000E+20 + 20 +-1.000000000000000E+20 + 30 +-1.000000000000000E+20 + 9 +$PLIMMIN + 10 +0.0 + 20 +0.0 + 9 +$PLIMMAX + 10 +0.0 + 20 +0.0 + 9 +$UNITMODE + 70 + 0 + 9 +$VISRETAIN + 70 + 1 + 9 +$PLINEGEN + 70 + 0 + 9 +$PSLTSCALE + 70 + 1 + 9 +$TREEDEPTH + 70 + 3020 + 9 +$CMLSTYLE + 2 +Standard + 9 +$CMLJUST + 70 + 0 + 9 +$CMLSCALE + 40 +1.0 + 9 +$PROXYGRAPHICS + 70 + 1 + 9 +$MEASUREMENT + 70 + 0 + 9 +$CELWEIGHT +370 + -1 + 9 +$ENDCAPS +280 + 0 + 9 +$JOINSTYLE +280 + 0 + 9 +$LWDISPLAY +290 + 0 + 9 +$INSUNITS + 70 + 0 + 9 +$HYPERLINKBASE + 1 + + 9 +$STYLESHEET + 1 + + 9 +$XEDIT +290 + 1 + 9 +$CEPSNTYPE +380 + 0 + 9 +$PSTYLEMODE +290 + 1 + 9 +$FINGERPRINTGUID + 2 +{394BC0E0-D500-95D9-65ED-9BB4C8BE75F1} + 9 +$VERSIONGUID + 2 +{FAEB1C32-E019-11D5-929B-00C0DF256EC4} + 9 +$EXTNAMES +290 + 1 + 9 +$PSVPSCALE + 40 +0.0 + 9 +$OLESTARTUP +290 + 0 + 0 +ENDSEC + 0 +SECTION + 2 +CLASSES + 0 +CLASS + 1 +ACDBDICTIONARYWDFLT + 2 +AcDbDictionaryWithDefault + 3 +ObjectDBX Classes + 90 + 0 +280 + 0 +281 + 0 + 0 +CLASS + 1 +SCALE + 2 +AcDbScale + 3 +ObjectDBX Classes + 90 + 1153 +280 + 0 +281 + 0 + 0 +CLASS + 1 +VISUALSTYLE + 2 +AcDbVisualStyle + 3 +ObjectDBX Classes + 90 + 4095 +280 + 0 +281 + 0 + 0 +CLASS + 1 +MATERIAL + 2 +AcDbMaterial + 3 +ObjectDBX Classes + 90 + 1153 +280 + 0 +281 + 0 + 0 +CLASS + 1 +TABLESTYLE + 2 +AcDbTableStyle + 3 +ObjectDBX Classes + 90 + 4095 +280 + 0 +281 + 0 + 0 +CLASS + 1 +SUN + 2 +AcDbSun + 3 +SCENEOE + 90 + 1153 +280 + 0 +281 + 0 + 0 +CLASS + 1 +RASTERVARIABLES + 2 +AcDbRasterVariables + 3 +ISM + 90 + 0 +280 + 0 +281 + 0 + 0 +CLASS + 1 +DICTIONARYVAR + 2 +AcDbDictionaryVar + 3 +ObjectDBX Classes + 90 + 0 +280 + 0 +281 + 0 + 0 +CLASS + 1 +ACDBPLACEHOLDER + 2 +AcDbPlaceHolder + 3 +ObjectDBX Classes + 90 + 0 +280 + 0 +281 + 0 + 0 +CLASS + 1 +LAYOUT + 2 +AcDbLayout + 3 +ObjectDBX Classes + 90 + 0 +280 + 0 +281 + 0 + 0 +ENDSEC + 0 +SECTION + 2 +TABLES + 0 +TABLE + 2 +VPORT + 5 +8 +330 +0 +100 +AcDbSymbolTable + 70 + 1 + 0 +VPORT + 5 +22 +330 +8 +100 +AcDbSymbolTableRecord +100 +AcDbViewportTableRecord + 2 +*ACTIVE + 70 + 0 + 10 +0.0 + 20 +0.0 + 11 +1.0 + 21 +1.0 + 12 +1.846354026608343 + 22 +0.3419926426125796 + 13 +0.0 + 23 +0.0 + 14 +10.0 + 24 +10.0 + 15 +10.0 + 25 +10.0 + 16 +0.0 + 26 +0.0 + 36 +1.0 + 17 +0.0 + 27 +0.0 + 37 +0.0 + 40 +1.733730323509535 + 41 +2.172519083969465 + 42 +50.0 + 43 +0.0 + 44 +0.0 + 50 +0.0 + 51 +0.0 + 71 + 16 + 72 + 100 + 73 + 1 + 74 + 1 + 75 + 0 + 76 + 0 + 77 + 0 + 78 + 0 +281 + 0 + 65 + 0 +110 +0.0 +120 +0.0 +130 +0.0 +111 +1.0 +121 +0.0 +131 +0.0 +112 +0.0 +122 +1.0 +132 +0.0 + 79 + 0 +146 +0.0 + 0 +ENDTAB + 0 +TABLE + 2 +LTYPE + 5 +5 +330 +0 +100 +AcDbSymbolTable + 70 + 1 + 0 +LTYPE + 5 +14 +330 +5 +100 +AcDbSymbolTableRecord +100 +AcDbLinetypeTableRecord + 2 +ByBlock + 70 + 0 + 3 + + 72 + 65 + 73 + 0 + 40 +0.0 + 0 +LTYPE + 5 +15 +330 +5 +100 +AcDbSymbolTableRecord +100 +AcDbLinetypeTableRecord + 2 +ByLayer + 70 + 0 + 3 + + 72 + 65 + 73 + 0 + 40 +0.0 + 0 +LTYPE + 5 +16 +330 +5 +100 +AcDbSymbolTableRecord +100 +AcDbLinetypeTableRecord + 2 +CONTINUOUS + 70 + 0 + 3 +Solid line + 72 + 65 + 73 + 0 + 40 +0.0 + 0 +ENDTAB + 0 +TABLE + 2 +LAYER + 5 +2 +102 +{ACAD_XDICTIONARY +360 +1B3 +102 +} +330 +0 +100 +AcDbSymbolTable + 70 + 3 + 0 +LAYER + 5 +10 +330 +2 +100 +AcDbSymbolTableRecord +100 +AcDbLayerTableRecord + 2 +0 + 70 + 0 + 62 + 7 + 6 +CONTINUOUS +370 + -3 +390 +F + 0 +LAYER + 5 +21 +330 +2 +100 +AcDbSymbolTableRecord +100 +AcDbLayerTableRecord + 2 +TEXT-GRAY + 70 + 0 + 62 + 254 + 6 +CONTINUOUS +370 + -3 +390 +F + 0 +LAYER + 5 +1B9 +330 +2 +100 +AcDbSymbolTableRecord +100 +AcDbLayerTableRecord + 2 +TEXT-RED + 70 + 0 + 62 + 1 + 6 +CONTINUOUS +370 + -3 +390 +F +1001 +AcAecLayerStandard +1000 + +1000 + + 0 +ENDTAB + 0 +TABLE + 2 +STYLE + 5 +3 +330 +0 +100 +AcDbSymbolTable + 70 + 1 + 0 +STYLE + 5 +11 +330 +3 +100 +AcDbSymbolTableRecord +100 +AcDbTextStyleTableRecord + 2 +Standard + 70 + 0 + 40 +0.0 + 41 +1.0 + 50 +0.0 + 71 + 0 + 42 +0.2 + 3 +txt + 4 + + 0 +ENDTAB + 0 +TABLE + 2 +VIEW + 5 +6 +330 +0 +100 +AcDbSymbolTable + 70 + 0 + 0 +ENDTAB + 0 +TABLE + 2 +UCS + 5 +7 +330 +0 +100 +AcDbSymbolTable + 70 + 0 + 0 +ENDTAB + 0 +TABLE + 2 +APPID + 5 +9 +330 +0 +100 +AcDbSymbolTable + 70 + 2 + 0 +APPID + 5 +12 +330 +9 +100 +AcDbSymbolTableRecord +100 +AcDbRegAppTableRecord + 2 +ACAD + 70 + 0 + 0 +APPID + 5 +1BA +330 +9 +100 +AcDbSymbolTableRecord +100 +AcDbRegAppTableRecord + 2 +AcAecLayerStandard + 70 + 0 + 0 +ENDTAB + 0 +TABLE + 2 +DIMSTYLE + 5 +A +330 +0 +100 +AcDbSymbolTable + 70 + 1 +100 +AcDbDimStyleTable + 0 +DIMSTYLE +105 +23 +330 +A +100 +AcDbSymbolTableRecord +100 +AcDbDimStyleTableRecord + 2 +Standard + 70 + 0 +178 + 0 +340 +11 + 0 +ENDTAB + 0 +TABLE + 2 +BLOCK_RECORD + 5 +1 +330 +0 +100 +AcDbSymbolTable + 70 + 0 + 0 +BLOCK_RECORD + 5 +1D +330 +1 +100 +AcDbSymbolTableRecord +100 +AcDbBlockTableRecord + 2 +*Model_Space +340 +1E + 0 +BLOCK_RECORD + 5 +1B +330 +1 +100 +AcDbSymbolTableRecord +100 +AcDbBlockTableRecord + 2 +*Paper_Space +340 +1C + 0 +ENDTAB + 0 +ENDSEC + 0 +SECTION + 2 +BLOCKS + 0 +BLOCK + 5 +18D +330 +1D +100 +AcDbEntity + 8 +0 +100 +AcDbBlockBegin + 2 +*Model_Space + 70 + 0 + 10 +0.0 + 20 +0.0 + 30 +0.0 + 3 +*Model_Space + 1 +*Model_Space + 0 +ENDBLK + 5 +18E +330 +1D +100 +AcDbEntity + 8 +0 +100 +AcDbBlockEnd + 0 +BLOCK + 5 +18F +330 +1B +100 +AcDbEntity + 67 + 1 + 8 +0 +100 +AcDbBlockBegin + 2 +*Paper_Space + 70 + 0 + 10 +0.0 + 20 +0.0 + 30 +0.0 + 3 +*Paper_Space + 1 +*Paper_Space + 0 +ENDBLK + 5 +190 +330 +1B +100 +AcDbEntity + 67 + 1 + 8 +0 +100 +AcDbBlockEnd + 0 +ENDSEC + 0 +SECTION + 2 +ENTITIES + 0 +LWPOLYLINE + 5 +24 +102 +{ACAD_REACTORS +330 +1BD +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbPolyline + 90 + 14 + 70 + 1 + 43 +0.0 + 10 +0.0000000000000001 + 20 +0.1752767944487085 + 10 +0.0416193345059499 + 20 +0.6506897567371471 + 10 +0.1681431038010463 + 20 +0.6506897567371471 + 10 +0.247338516041492 + 20 +0.3260572124180542 + 10 +0.3260590389156172 + 20 +0.6506897567371471 + 10 +0.4521056357224397 + 20 +0.6506897567371471 + 10 +0.4963403625301471 + 20 +0.1752767944487085 + 10 +0.4066806413363264 + 20 +0.1752767944487085 + 10 +0.3752877144762009 + 20 +0.4930112663057366 + 10 +0.2987087599944248 + 20 +0.1752767944487085 + 10 +0.1973944622688229 + 20 +0.1752767944487085 + 10 +0.1174851938975943 + 20 +0.4930112663057366 + 10 +0.0896600256100814 + 20 +0.1752767944487085 + 10 +0.0000000000000001 + 20 +0.1752767944487085 + 0 +LWPOLYLINE + 5 +34 +102 +{ACAD_REACTORS +330 +1BE +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbPolyline + 90 + 5 + 70 + 1 + 43 +0.0 + 10 +0.5505660310062117 + 20 +0.1752767944487085 + 10 +0.5505660310062117 + 20 +0.5201225784624666 + 10 +0.6416519423802962 + 20 +0.5201225784624666 + 10 +0.6416519423802962 + 20 +0.1752767944487085 + 10 +0.5505660310062117 + 20 +0.1752767944487085 + 0 +LWPOLYLINE + 5 +3B +102 +{ACAD_REACTORS +330 +1BF +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbPolyline + 90 + 13 + 70 + 1 + 43 +0.0 + 10 +0.5474731617999196 + 20 +0.5714928224153991 + 10 +0.5474731617999196 + 20 +0.6288098380164536 + 42 +-0.1883074803638932 + 10 +0.5513377262264826 + 20 +0.6414735544516654 + 42 +-0.2159435161643535 + 10 +0.5629314195061711 + 20 +0.6456942859029685 + 10 +0.6311876334269211 + 20 +0.6456942859029685 + 42 +-0.2288445935800111 + 10 +0.6418909091447587 + 20 +0.6414735544516654 + 42 +-0.1763562374232752 + 10 +0.6454571456360689 + 20 +0.6288098380164536 + 10 +0.6454571456360689 + 20 +0.5714928224153991 + 42 +-0.1943541296589125 + 10 +0.6418909091447587 + 20 +0.5602568182417533 + 42 +-0.2096410684182619 + 10 +0.6311876334269211 + 20 +0.5565109761567706 + 10 +0.5629314195061711 + 20 +0.5565109761567706 + 42 +-0.1965331617699563 + 10 +0.551636054161735 + 20 +0.5604349017541234 + 42 +-0.2135460038275524 + 10 +0.5474731617999196 + 20 +0.5714928224153991 + 0 +LWPOLYLINE + 5 +4A +102 +{ACAD_REACTORS +330 +1C5 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 12 + 70 + 1 + 43 +0.0 + 10 +1.855753791898883 + 20 +0.5703040769182958 + 10 +1.749208100737245 + 20 +0.5703040769182958 + 10 +1.749208100737245 + 20 +0.4311767133994287 + 10 +1.855281946695168 + 20 +0.4311767133994287 + 42 +0.1378892503752188 + 10 +1.880487613061407 + 20 +0.4371219629662482 + 42 +0.1061516643405155 + 10 +1.890061504452931 + 20 +0.4460702789425233 + 42 +0.0752237691491799 + 10 +1.896895649500299 + 20 +0.460071904842465 + 42 +0.0778530288832081 + 10 +1.902359921375588 + 20 +0.5032381305759515 + 42 +0.0564276025149389 + 10 +1.899452746088178 + 20 +0.5325792918405643 + 42 +0.095076106856608 + 10 +1.890715999412924 + 20 +0.5535383513733607 + 42 +0.1319298941216669 + 10 +1.876149681349825 + 20 +0.5661122650117364 + 42 +0.1129501247093477 + 10 +1.855753791898883 + 20 +0.5703040769182958 + 0 +LWPOLYLINE + 5 +58 +102 +{ACAD_REACTORS +330 +1C7 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 23 + 70 + 1 + 43 +0.0 + 10 +2.401085080890193 + 20 +0.451391475175396 + 10 +2.401085080890193 + 20 +0.502049385078848 + 10 +2.456975906310984 + 20 +0.5208364345932495 + 10 +2.471953186325706 + 20 +0.6169178168015124 + 10 +2.547828939245814 + 20 +0.6169178168015124 + 10 +2.547828939245814 + 20 +0.5208364345932495 + 10 +2.625120227777072 + 20 +0.5208364345932495 + 10 +2.625120227777072 + 20 +0.451391475175396 + 10 +2.547828939245814 + 20 +0.451391475175396 + 10 +2.547828939245814 + 20 +0.312977967787312 + 42 +0.0356379455033458 + 10 +2.549609774369517 + 20 +0.2833386307955768 + 42 +0.0811642329835157 + 10 +2.554952279740622 + 20 +0.2643422951021078 + 42 +0.1858874482849488 + 10 +2.577068121063173 + 20 +0.244721753866562 + 42 +0.0076184446139192 + 10 +2.607448863857263 + 20 +0.2345547073915278 + 42 +0.0469611640188665 + 10 +2.620599646309214 + 20 +0.2311657933719365 + 10 +2.620599646309214 + 20 +0.1752767944487085 + 10 +2.541405756150071 + 20 +0.1752767944487085 + 42 +-0.1146121843643247 + 10 +2.504464842943029 + 20 +0.1829913113213321 + 42 +-0.132229815857891 + 10 +2.478071953160988 + 20 +0.2061345575229422 + 42 +-0.0940182241125145 + 10 +2.462242307616974 + 20 +0.2447068374697993 + 42 +-0.0555506677049525 + 10 +2.456975906310984 + 20 +0.2987081511619036 + 10 +2.456975906310984 + 20 +0.451391475175396 + 10 +2.401085080890193 + 20 +0.451391475175396 + 0 +LWPOLYLINE + 5 +71 +102 +{ACAD_REACTORS +330 +1CA +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 22 + 70 + 1 + 43 +0.0 + 10 +3.589495720107105 + 20 +0.5260693501105883 + 42 +-0.0932412511784359 + 10 +3.634655872346617 + 20 +0.5185183047698327 + 42 +-0.1254375778784052 + 10 +3.666908775142547 + 20 +0.4958651687475662 + 42 +-0.1084619648488494 + 10 +3.686254428494896 + 20 +0.4581099420437885 + 42 +-0.0689905889343237 + 10 +3.692708053216686 + 20 +0.4052541467398021 + 10 +3.692708053216686 + 20 +0.1752767944487085 + 10 +3.601870241094878 + 20 +0.1752767944487085 + 10 +3.601870241094878 + 20 +0.4064428922369056 + 42 +0.0660852200863579 + 10 +3.59946535263723 + 20 +0.4269407611351025 + 42 +0.1056585132217627 + 10 +3.592296349703354 + 20 +0.4415816611820138 + 42 +0.1272161701661909 + 10 +3.580317569854181 + 20 +0.4503655923776398 + 42 +0.0972102752618352 + 10 +3.56357467552878 + 20 +0.4532940768032824 + 42 +0.0885878555139059 + 10 +3.519221226379493 + 20 +0.4465162487641 + 42 +0.077710311269079 + 10 +3.480332049105495 + 20 +0.4233288622047228 + 10 +3.480332049105495 + 20 +0.1752767944487085 + 10 +3.389479016170664 + 20 +0.1752767944487085 + 10 +3.389479016170664 + 20 +0.5201225784624666 + 10 +3.462264944047086 + 20 +0.5201225784624666 + 10 +3.480332049105495 + 20 +0.4832608134831443 + 42 +-0.0353892151285229 + 10 +3.522843779878989 + 20 +0.5102534032982943 + 42 +-0.0728322192286089 + 10 +3.555720736008866 + 20 +0.5227390362211358 + 42 +-0.0544633437581111 + 10 +3.589495720107105 + 20 +0.5260693501105883 + 0 +LWPOLYLINE + 5 +89 +102 +{ACAD_REACTORS +330 +1C6 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 17 + 70 + 1 + 43 +0.0 + 10 +2.026516093204943 + 20 +0.5201225784624666 + 10 +2.12187448679461 + 20 +0.5201225784624666 + 10 +2.181814048479542 + 20 +0.2784929327615455 + 42 +0.1680883445175794 + 10 +2.192925241986399 + 20 +0.2601209548182838 + 42 +0.1691212946679427 + 10 +2.213442897941526 + 20 +0.2539970129065732 + 42 +0.0518086164809523 + 10 +2.216060877781497 + 20 +0.2532834611920508 + 10 +2.285026381589124 + 20 +0.5201225784624666 + 10 +2.379912929975073 + 20 +0.5201225784624666 + 10 +2.2602925604266 + 20 +0.0661149499446615 + 10 +2.21297105273781 + 20 +0.0 + 10 +2.147795531372934 + 20 +0.0 + 10 +2.196547795485895 + 20 +0.1752767944487085 + 42 +-0.0815316895695442 + 10 +2.160444026995122 + 20 +0.1807616144215795 + 42 +-0.0970784439939463 + 10 +2.131326611681949 + 20 +0.1972162265483224 + 42 +-0.0875143454723418 + 10 +2.109195549546374 + 20 +0.2246403264126769 + 42 +-0.0638836232247607 + 10 +2.094050840588399 + 20 +0.2630342184309034 + 10 +2.026516093204943 + 20 +0.5201225784624666 + 0 +LWPOLYLINE + 5 +9C +102 +{ACAD_REACTORS +330 +1C8 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 22 + 70 + 1 + 43 +0.0 + 10 +2.66863653221009 + 20 +0.1752767944487085 + 10 +2.66863653221009 + 20 +0.683985285225159 + 10 +2.758774186932835 + 20 +0.683985285225159 + 10 +2.758774186932835 + 20 +0.4832608134831443 + 42 +-0.0349812911378511 + 10 +2.80104238469796 + 20 +0.5100159586151339 + 42 +-0.0697958386932639 + 10 +2.834162873836206 + 20 +0.5227390362211358 + 42 +-0.0522006296457192 + 10 +2.868653236146531 + 20 +0.5260693501105883 + 42 +-0.0932412511784358 + 10 +2.913798167573019 + 20 +0.5185183047698327 + 42 +-0.1254375778784047 + 10 +2.946066291181972 + 20 +0.4958651687475662 + 42 +-0.1084619648488494 + 10 +2.965411944534321 + 20 +0.4581099420437885 + 42 +-0.0689905889343073 + 10 +2.971865569256112 + 20 +0.4052541467398021 + 10 +2.971865569256112 + 20 +0.1752767944487085 + 10 +2.881012536321281 + 20 +0.1752767944487085 + 10 +2.881012536321281 + 20 +0.4064428922369056 + 42 +0.0660852200863579 + 10 +2.878622868676655 + 20 +0.4269407611351025 + 42 +0.1056585132217627 + 10 +2.871438644929757 + 20 +0.4415816611820138 + 42 +0.1272161701661909 + 10 +2.859475085893608 + 20 +0.4503655923776398 + 42 +0.0972102752618352 + 10 +2.842716970755184 + 20 +0.4532940768032824 + 42 +0.088587855513906 + 10 +2.798363521605896 + 20 +0.4465162487641 + 42 +0.0777103112690791 + 10 +2.759489565144921 + 20 +0.4233288622047228 + 10 +2.759489565144921 + 20 +0.1752767944487085 + 10 +2.66863653221009 + 20 +0.1752767944487085 + 0 +LWPOLYLINE + 5 +B4 +102 +{ACAD_REACTORS +330 +1C0 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbPolyline + 90 + 34 + 70 + 1 + 43 +0.0 + 10 +0.6946873432779551 + 20 +0.3481760979032103 + 42 +-0.0229891281782208 + 10 +0.6967086672474216 + 20 +0.3959192221127403 + 42 +-0.0328228697904816 + 10 +0.7027741612371234 + 20 +0.4354583281028243 + 42 +-0.0483316739793035 + 10 +0.7128214199136659 + 20 +0.4666716493692773 + 42 +-0.0727828188712317 + 10 +0.7267941262688635 + 20 +0.489443507733124 + 42 +-0.1227899169725496 + 10 +0.762229701067922 + 20 +0.5157237634987931 + 42 +-0.0944303865644604 + 10 +0.8083670295035159 + 20 +0.5234528923519188 + 42 +-0.0315898411800418 + 10 +0.8956492597031299 + 20 +0.5183995824282526 + 42 +-0.0456865147865019 + 10 +0.9667593760657095 + 20 +0.5032381305759515 + 10 +0.9667593760657095 + 20 +0.448776539498029 + 42 +0.0070437593452633 + 10 +0.8389882611433709 + 20 +0.4484492920180325 + 42 +0.0290350112768282 + 10 +0.82418297631581 + 20 +0.4474675495780431 + 42 +0.0847606935358247 + 10 +0.8076546954540353 + 20 +0.4410458885636011 + 42 +0.1825489438203349 + 10 +0.7945739287419907 + 20 +0.4249924970681467 + 42 +0.0517789759014607 + 10 +0.7877961007028083 + 20 +0.3930348780448645 + 42 +0.0296456838705223 + 10 +0.7855358099688792 + 20 +0.3499599771895165 + 42 +0.0216618761660938 + 10 +0.7870822445720254 + 20 +0.3081910220915498 + 42 +0.0471796273319681 + 10 +0.7917200263001613 + 20 +0.280157633081881 + 42 +0.072662787539697 + 10 +0.7993608744377529 + 20 +0.262588400817457 + 42 +0.1214661602111968 + 10 +0.8099134641066621 + 20 +0.2522132858283972 + 42 +0.0832516876593145 + 10 +0.8254021634389597 + 20 +0.247129686486815 + 42 +0.0435906078463293 + 10 +0.8478467743228099 + 20 +0.2454353055810845 + 42 +0.021166726074658 + 10 +0.9539175761181276 + 20 +0.2499539083432495 + 10 +0.9712784354522652 + 20 +0.2513808595641643 + 10 +0.9712784354522652 + 20 +0.1940650616281518 + 42 +-0.0978017422898016 + 10 +0.9130101190372676 + 20 +0.1759903461632311 + 42 +-0.0233934475797722 + 10 +0.8395225116804813 + 20 +0.1719472415999074 + 10 +0.8357173084247086 + 20 +0.1719472415999074 + 42 +-0.1019475670653864 + 10 +0.7625265069218723 + 20 +0.1805684623043164 + 42 +-0.117873950403685 + 10 +0.7277454270828068 + 20 +0.2064319722094134 + 42 +-0.0715503088956374 + 10 +0.7132826105482655 + 20 +0.2296496481867064 + 42 +-0.0491245187935067 + 10 +0.7029522447494936 + 20 +0.2610127422533067 + 42 +-0.0334830700706472 + 10 +0.6967528076051885 + 20 +0.3005215588254747 + 42 +-0.023527584931374 + 10 +0.6946873432779551 + 20 +0.3481760979032103 + 0 +LWPOLYLINE + 5 +D8 +102 +{ACAD_REACTORS +330 +1C1 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbPolyline + 90 + 16 + 70 + 1 + 43 +0.0 + 10 +1.020746077777311 + 20 +0.1752767944487085 + 10 +1.020746077777311 + 20 +0.5201225784624666 + 10 +1.097325032259088 + 20 +0.5201225784624666 + 10 +1.111594544468236 + 20 +0.4766017077855419 + 42 +-0.0805753976673698 + 10 +1.160646658597752 + 20 +0.5117404767306502 + 42 +-0.1124747672601628 + 10 +1.210292384435168 + 20 +0.5234528923519188 + 42 +-0.0241299749672376 + 10 +1.233896821271378 + 20 +0.5225015915379756 + 42 +-0.060832138395251 + 10 +1.248581861676056 + 20 +0.519647689096146 + 10 +1.248581861676056 + 20 +0.4318905695302117 + 42 +0.0248536783236681 + 10 +1.199353186115472 + 20 +0.4337931711580981 + 42 +0.0387057739818888 + 10 +1.170873522867967 + 20 +0.4317718471886316 + 42 +0.0551847743452131 + 10 +1.147743975398077 + 20 +0.4257063531989297 + 42 +0.080499651857314 + 10 +1.128480514436053 + 20 +0.4141126599192412 + 42 +0.0645077730986141 + 10 +1.111594544468236 + 20 +0.39550369391721 + 10 +1.111594544468236 + 20 +0.1752767944487085 + 10 +1.020746077777311 + 20 +0.1752767944487085 + 0 +LWPOLYLINE + 5 +EA +102 +{ACAD_REACTORS +330 +1C9 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 30 + 70 + 1 + 43 +0.0 + 10 +3.020617833369073 + 20 +0.3410405807579851 + 42 +-0.0409081205529831 + 10 +3.025732026544832 + 20 +0.4159559003763376 + 42 +-0.0781599297384411 + 10 +3.041896529975355 + 20 +0.4673261443292702 + 42 +-0.1364366144086533 + 10 +3.072459922525721 + 20 +0.5006216728172821 + 42 +-0.0882009175036989 + 10 +3.116752488422916 + 20 +0.5177450874682596 + 42 +-0.0529086836461284 + 10 +3.177818390271558 + 20 +0.5234528923519188 + 42 +-0.0321103580647159 + 10 +3.218868922994835 + 20 +0.5210145181056196 + 42 +-0.0444041287441238 + 10 +3.253054869044698 + 20 +0.5137024395293266 + 42 +-0.0605636228964518 + 10 +3.280406670047193 + 20 +0.5015136124604352 + 42 +-0.0762678881360705 + 10 +3.300893884376273 + 20 +0.4844495589802478 + 42 +-0.0695139514449708 + 10 +3.315825501951926 + 20 +0.4611571488110112 + 42 +-0.0499044136612151 + 10 +3.326495291881113 + 20 +0.4302847737562754 + 42 +-0.0350340529330662 + 10 +3.332888033350811 + 20 +0.3918309117347381 + 42 +-0.0250615206333876 + 10 +3.335018947174044 + 20 +0.3457970848277011 + 42 +-0.0247570817049555 + 10 +3.332933695789881 + 20 +0.2998822846785048 + 42 +-0.035093333100506 + 10 +3.326632279198321 + 20 +0.2617856551386192 + 42 +-0.0509721690967282 + 10 +3.316160359838434 + 20 +0.2315076528324352 + 42 +-0.0726634493786117 + 10 +3.301487496084174 + 20 +0.2090479733436921 + 42 +-0.0773754337522631 + 10 +3.281182931511371 + 20 +0.1928163461277374 + 42 +-0.0591962390389137 + 10 +3.253800688882829 + 20 +0.1812223484317884 + 42 +-0.0423681953096553 + 10 +3.219355989011574 + 20 +0.174265980255845 + 42 +-0.0302514249026995 + 10 +3.177818390271558 + 20 +0.1719472415999074 + 42 +-0.0327640807112059 + 10 +3.136935286491535 + 20 +0.1744296039958433 + 42 +-0.0448781589059774 + 10 +3.10273411962865 + 20 +0.1818763867673907 + 42 +-0.060332284523739 + 10 +3.075214889682901 + 20 +0.1942878943308099 + 42 +-0.0746618379907621 + 10 +3.054392817467312 + 20 +0.2116639744779708 + 42 +-0.0666236365557017 + 10 +3.03961340802189 + 20 +0.2341087375699512 + 42 +-0.0504061851560683 + 10 +3.029065384596889 + 20 +0.2631532451887439 + 42 +-0.0367317311855017 + 10 +3.022733526379283 + 20 +0.2987971929180886 + 42 +-0.0269050519350767 + 10 +3.020617833369073 + 20 +0.3410405807579851 + 0 +LWPOLYLINE + 5 +10A +102 +{ACAD_REACTORS +330 +1C2 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbPolyline + 90 + 21 + 70 + 1 + 43 +0.0 + 10 +1.390325682953593 + 20 +0.4318905695302117 + 42 +0.0242919032698246 + 10 +1.38033778544784 + 20 +0.3839084785562191 + 42 +0.0375411437912006 + 10 +1.377007471558388 + 20 +0.3446083393305977 + 42 +0.0398730504554166 + 10 +1.38033778544784 + 20 +0.2901464438364147 + 42 +0.0541422102818605 + 10 +1.38500448672072 + 20 +0.2730230291854372 + 42 +0.0823828350418203 + 10 +1.392347006923059 + 20 +0.2606561186041756 + 42 +0.1602559612730944 + 10 +1.412086879332706 + 20 +0.2480513067153631 + 42 +0.0555482263236158 + 10 +1.442053616012568 + 20 +0.2454353055810845 + 42 +0.0316904222703728 + 10 +1.470353673666401 + 20 +0.2467432300441587 + 42 +0.1007429782984575 + 10 +1.488551677716809 + 20 +0.2532834611920508 + 42 +0.1818370389300056 + 10 +1.501154510899928 + 20 +0.2694555750290851 + 42 +0.0526041808970857 + 10 +1.507395044239396 + 20 +0.2969244240837275 + 42 +0.0324432335036989 + 10 +1.50948029562356 + 20 +0.3327178401969589 + 42 +0.018652937942289 + 10 +1.507927772695204 + 20 +0.3912220792138144 + 42 +0.0530768467862457 + 10 +1.502463500819915 + 20 +0.4224962837323597 + 42 +0.1914595274942226 + 10 +1.48998243414098 + 20 +0.4402133100912379 + 42 +0.0889989641192241 + 10 +1.472167994578754 + 20 +0.4475269107488332 + 42 +0.0570509400215991 + 10 +1.448236310262548 + 20 +0.4499652849951324 + 42 +0.0204219730568417 + 10 +1.425137204418705 + 20 +0.4491616260675131 + 42 +0.045760246847436 + 10 +1.409828110680079 + 20 +0.4467536934472601 + 42 +0.1785155631256146 + 10 +1.390325682953593 + 20 +0.4318905695302117 + 0 +LWPOLYLINE + 5 +121 +102 +{ACAD_REACTORS +330 +1C9 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 21 + 70 + 1 + 43 +0.0 + 10 +3.124789077699108 + 20 +0.4318905695302117 + 42 +0.0242919032698246 + 10 +3.114804224355961 + 20 +0.3839084785562191 + 42 +0.0375411437912007 + 10 +3.111470866303904 + 20 +0.3446083393305977 + 42 +0.0398730504554166 + 10 +3.114804224355961 + 20 +0.2901464438364147 + 42 +0.0541422102818607 + 10 +3.119461793141027 + 20 +0.2730230291854372 + 42 +0.0823828350418199 + 10 +3.12681344583118 + 20 +0.2606561186041756 + 42 +0.1602559612730945 + 10 +3.146539619509106 + 20 +0.2480513067153631 + 42 +0.0555482263236158 + 10 +3.176509400351572 + 20 +0.2454353055810845 + 42 +0.0316904222703728 + 10 +3.204820112574522 + 20 +0.2467432300441587 + 42 +0.1007429782984576 + 10 +3.223008984137115 + 20 +0.2532834611920508 + 42 +0.1818370389300056 + 10 +3.235611817320236 + 20 +0.2694555750290851 + 42 +0.0526041808970857 + 10 +3.241852350659703 + 20 +0.2969244240837275 + 42 +0.0324432335036989 + 10 +3.243937602043866 + 20 +0.3327178401969589 + 42 +0.018652937942289 + 10 +3.242385079115511 + 20 +0.3912220792138144 + 42 +0.0530768467862456 + 10 +3.236920807240222 + 20 +0.4224962837323597 + 42 +0.1914595274942226 + 10 +3.224439740561286 + 20 +0.4402133100912379 + 42 +0.0889989641192241 + 10 +3.20663138932427 + 20 +0.4475269107488332 + 42 +0.0570509400215991 + 10 +3.182689050438947 + 20 +0.4499652849951324 + 42 +0.0204219730568417 + 10 +3.159599077082918 + 20 +0.4491616260675131 + 42 +0.045760246847436 + 10 +3.144286939181689 + 20 +0.4467536934472601 + 42 +0.178515563125615 + 10 +3.124789077699108 + 20 +0.4318905695302117 + 0 +LWPOLYLINE + 5 +138 +102 +{ACAD_REACTORS +330 +1C5 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbPolyline + 90 + 17 + 70 + 1 + 43 +0.0 + 10 +1.658111534794044 + 20 +0.1752767944487085 + 10 +1.658111534794044 + 20 +0.6506897567371471 + 10 +1.862892353206713 + 20 +0.6506897567371471 + 42 +-0.0918352741933524 + 10 +1.923821267738147 + 20 +0.6408190594916725 + 42 +-0.133922059302927 + 10 +1.965389308104209 + 20 +0.6112100119178533 + 42 +-0.1060028202258852 + 10 +1.987322499670483 + 20 +0.566558234833313 + 42 +-0.0661506729116568 + 10 +1.99464371073459 + 20 +0.5039519867067345 + 42 +-0.0710178368558241 + 10 +1.985846080807243 + 20 +0.4324841812381122 + 42 +-0.0374247138640044 + 10 +1.976089539659442 + 20 +0.4061156447569091 + 42 +-0.057718769966508 + 10 +1.964430396883754 + 20 +0.3867030198272586 + 42 +-0.1271250474471338 + 10 +1.932329702218055 + 20 +0.3624456101123582 + 42 +-0.110827379232239 + 10 +1.875723498585179 + 20 +0.3505535888974171 + 42 +-0.0258396192335467 + 10 +1.802480946318064 + 20 +0.3564988384642365 + 42 +-0.0037744416271255 + 10 +1.763835302052436 + 20 +0.3612568646152548 + 42 +-0.0304647996844293 + 10 +1.749208100737245 + 20 +0.3636343556094617 + 10 +1.749208100737245 + 20 +0.1752767944487085 + 10 +1.658111534794044 + 20 +0.1752767944487085 + 0 +LWPOLYLINE + 5 +14B +102 +{ACAD_REACTORS +330 +1C2 +102 +} +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbPolyline + 90 + 30 + 70 + 1 + 43 +0.0 + 10 +1.286159004867464 + 20 +0.3410405807579851 + 42 +-0.040908120552983 + 10 +1.29127167596192 + 20 +0.4159559003763376 + 42 +-0.0781599297384411 + 10 +1.307443789798954 + 20 +0.4673261443292702 + 42 +-0.1364366144086534 + 10 +1.338004138186717 + 20 +0.5006216728172821 + 42 +-0.088200917503699 + 10 +1.382299748246516 + 20 +0.5177450874682596 + 42 +-0.0529086836461285 + 10 +1.443361083851251 + 20 +0.5234528923519188 + 42 +-0.0321103580647177 + 10 +1.484408572411924 + 20 +0.5210145181056196 + 42 +-0.0444041287441238 + 10 +1.518597562624391 + 20 +0.5137024395293266 + 42 +-0.0605636228964518 + 10 +1.545949363626886 + 20 +0.5015136124604352 + 42 +-0.0762678881361016 + 10 +1.566436577955966 + 20 +0.4844495589802478 + 42 +-0.0695139514449315 + 10 +1.581368195531619 + 20 +0.4611571488110112 + 42 +-0.0499044136612151 + 10 +1.592037985460806 + 20 +0.4302847737562754 + 42 +-0.0350340529330662 + 10 +1.598430726930504 + 20 +0.3918309117347381 + 42 +-0.0250615206333974 + 10 +1.600561640753737 + 20 +0.3457970848277011 + 42 +-0.0247570817049556 + 10 +1.59846116855655 + 20 +0.2998822846785048 + 42 +-0.035093333100506 + 10 +1.592174972778014 + 20 +0.2617856551386192 + 42 +-0.0509721690967282 + 10 +1.581703053418127 + 20 +0.2315076528324352 + 42 +-0.0726634493786118 + 10 +1.567030189663867 + 20 +0.2090479733436921 + 42 +-0.0773754337522942 + 10 +1.546725625091063 + 20 +0.1928163461277374 + 42 +-0.0591962390389137 + 10 +1.519343382462522 + 20 +0.1812223484317884 + 42 +-0.0423681953096553 + 10 +1.484891072184755 + 20 +0.174265980255845 + 42 +-0.0302514249026978 + 10 +1.443361083851251 + 20 +0.1719472415999074 + 42 +-0.0327640807112059 + 10 +1.402470369664717 + 20 +0.1744296039958433 + 42 +-0.0448781589059774 + 10 +1.368267680720529 + 20 +0.1818763867673907 + 42 +-0.060332284523739 + 10 +1.340754539099989 + 20 +0.1942878943308099 + 42 +-0.0746618379907621 + 10 +1.319929422721796 + 20 +0.2116639744779708 + 42 +-0.0666236365556613 + 10 +1.305154579520281 + 20 +0.2341087375699512 + 42 +-0.0504061851560684 + 10 +1.294601989851372 + 20 +0.2631532451887439 + 42 +-0.0367317311855017 + 10 +1.288268609552464 + 20 +0.2987971929180886 + 42 +-0.0269050519351071 + 10 +1.286159004867464 + 20 +0.3410405807579851 + 0 +HATCH + 5 +1BD +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 14 + 72 + 1 + 10 +0.0000000000000001 + 20 +0.1752767944487085 + 11 +0.0416193345059499 + 21 +0.6506897567371471 + 72 + 1 + 10 +0.0416193345059499 + 20 +0.6506897567371471 + 11 +0.1681431038010463 + 21 +0.6506897567371471 + 72 + 1 + 10 +0.1681431038010463 + 20 +0.6506897567371471 + 11 +0.247338516041492 + 21 +0.3260572124180542 + 72 + 1 + 10 +0.247338516041492 + 20 +0.3260572124180542 + 11 +0.3260590389156172 + 21 +0.6506897567371471 + 72 + 1 + 10 +0.3260590389156172 + 20 +0.6506897567371471 + 11 +0.4521056357224397 + 21 +0.6506897567371471 + 72 + 1 + 10 +0.4521056357224397 + 20 +0.6506897567371471 + 11 +0.4963403625301471 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.4963403625301471 + 20 +0.1752767944487085 + 11 +0.4066806413363264 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.4066806413363264 + 20 +0.1752767944487085 + 11 +0.3752877144762009 + 21 +0.4930112663057366 + 72 + 1 + 10 +0.3752877144762009 + 20 +0.4930112663057366 + 11 +0.2987087599944248 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.2987087599944248 + 20 +0.1752767944487085 + 11 +0.1973944622688229 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.1973944622688229 + 20 +0.1752767944487085 + 11 +0.1174851938975943 + 21 +0.4930112663057366 + 72 + 1 + 10 +0.1174851938975943 + 20 +0.4930112663057366 + 11 +0.0896600256100814 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.0896600256100814 + 20 +0.1752767944487085 + 11 +0.0000000000000001 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.0000000000000001 + 20 +0.1752767944487085 + 11 +0.0000000000000001 + 21 +0.1752767944487085 + 97 + 1 +330 +24 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1BE +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 5 + 72 + 1 + 10 +0.5505660310062117 + 20 +0.1752767944487085 + 11 +0.5505660310062117 + 21 +0.5201225784624666 + 72 + 1 + 10 +0.5505660310062117 + 20 +0.5201225784624666 + 11 +0.6416519423802962 + 21 +0.5201225784624666 + 72 + 1 + 10 +0.6416519423802962 + 20 +0.5201225784624666 + 11 +0.6416519423802962 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.6416519423802962 + 20 +0.1752767944487085 + 11 +0.5505660310062117 + 21 +0.1752767944487085 + 72 + 1 + 10 +0.5505660310062117 + 20 +0.1752767944487085 + 11 +0.5505660310062117 + 21 +0.1752767944487085 + 97 + 1 +330 +34 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1BF +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 13 + 72 + 1 + 10 +0.5474731617999196 + 20 +0.5714928224153991 + 11 +0.5474731617999196 + 21 +0.6288098380164536 + 72 + 2 + 10 +0.5656218268345913 + 20 +0.630192970755272 + 40 +0.0182012938747197 + 50 +175.6418407014946 + 51 +218.2992114073367 + 73 + 0 + 72 + 2 + 10 +0.5617930966007493 + 20 +0.6307876795407876 + 40 +0.0149500064305679 + 50 +225.6246753032742 + 51 +274.3668398711414 + 73 + 0 + 72 + 1 + 10 +0.5629314195061711 + 20 +0.6456942859029685 + 11 +0.6311876334269211 + 21 +0.6456942859029685 + 72 + 2 + 10 +0.6321698296440981 + 20 +0.6325035330064808 + 40 +0.0132272699898821 + 50 +265.7415594617891 + 51 +317.3010585925538 + 73 + 0 + 72 + 2 + 10 +0.6262804611730807 + 20 +0.6302434840168466 + 40 +0.0192301993709753 + 50 +324.2689673804306 + 51 +364.2754703081528 + 73 + 0 + 72 + 1 + 10 +0.6454571456360689 + 20 +0.6288098380164536 + 11 +0.6454571456360689 + 21 +0.5714928224153991 + 72 + 2 + 10 +0.6297669641888812 + 20 +0.5702888340215038 + 40 +0.0157363077593922 + 50 +355.611999000231 + 51 +399.6062175218991 + 73 + 0 + 72 + 2 + 10 +0.6322686211170757 + 20 +0.5705867464421508 + 40 +0.0141172179806454 + 50 +47.03124341518984 + 51 +94.39156764264102 + 73 + 0 + 72 + 1 + 10 +0.6311876334269211 + 20 +0.5565109761567706 + 11 +0.5629314195061711 + 21 +0.5565109761567706 + 72 + 2 + 10 +0.5620823708457157 + 20 +0.572286229491247 + 40 +0.0157980853711685 + 50 +86.91922452913958 + 51 +131.3944660406891 + 73 + 0 + 72 + 2 + 10 +0.5619098596911134 + 20 +0.570615150925454 + 40 +0.0144633520750158 + 50 +135.2620677004958 + 51 +183.4789850614727 + 73 + 0 + 72 + 1 + 10 +0.5474731617999196 + 20 +0.5714928224153991 + 11 +0.5474731617999196 + 21 +0.5714928224153991 + 97 + 1 +330 +3B + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C0 +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 34 + 72 + 2 + 10 +1.214616030315336 + 20 +0.350077974119305 + 40 +0.5199321655154222 + 50 +179.7904154992175 + 51 +185.0582076977404 + 73 + 0 + 72 + 2 + 10 +1.000572124284262 + 20 +0.3695398595471971 + 40 +0.3050063463138826 + 50 +184.961591177561 + 51 +192.4813391512255 + 73 + 0 + 72 + 2 + 10 +0.8688743989493632 + 20 +0.3992160253637114 + 40 +0.170008215907044 + 50 +192.3087569665484 + 51 +203.3769478223085 + 73 + 0 + 72 + 2 + 10 +0.7976119460679242 + 20 +0.4303172999651613 + 40 +0.0922554716323781 + 50 +203.2074684948184 + 51 +219.8587008780153 + 73 + 0 + 72 + 2 + 10 +0.7972117188097253 + 20 +0.4315246663413517 + 40 +0.0911769133466147 + 50 +219.4374770529955 + 51 +247.4386863416477 + 73 + 0 + 72 + 2 + 10 +0.8055784036639897 + 20 +0.398531115770543 + 40 +0.124952897918856 + 50 +249.7009350090099 + 51 +271.2787999327404 + 73 + 0 + 72 + 2 + 10 +0.8120564786102148 + 20 +-0.1691304899318403 + 40 +0.6925932092147039 + 50 +269.6947835186498 + 51 +276.9322349981942 + 73 + 0 + 72 + 2 + 10 +0.8484128964611991 + 20 +0.1225112149529162 + 40 +0.3986964678983381 + 50 +276.8042143326444 + 51 +287.2675164228719 + 73 + 0 + 72 + 1 + 10 +0.9667593760657095 + 20 +0.5032381305759515 + 11 +0.9667593760657095 + 21 +0.448776539498029 + 72 + 2 + 10 +0.9144880443227094 + 20 +-4.086066981505726 + 40 +4.535144766389704 + 50 +89.3396036583715 + 51 +90.9538876909594 + 73 + 1 + 72 + 2 + 10 +0.8400315841062043 + 20 +0.3205880251107224 + 40 +0.1278655234922502 + 50 +90.46751199340585 + 51 +97.1199774171112 + 73 + 1 + 72 + 2 + 10 +0.8347233227483223 + 20 +0.3958571165940125 + 40 +0.0526757600392865 + 50 +101.54272561012 + 51 +120.9221245987022 + 73 + 1 + 72 + 2 + 10 +0.8223667308685831 + 20 +0.4157021086294436 + 40 +0.029304456442492 + 50 +120.1351163505028 + 51 +161.5166003585789 + 73 + 1 + 72 + 2 + 10 +0.9450695696956614 + 20 +0.3763766174814469 + 40 +0.1581532222056973 + 50 +162.0975481756131 + 51 +173.9538270794763 + 73 + 1 + 72 + 2 + 10 +1.149594366372439 + 20 +0.3524533042818777 + 40 +0.3640670943255288 + 50 +173.6000944629489 + 51 +180.3923953532557 + 73 + 1 + 72 + 2 + 10 +1.268138893295446 + 20 +0.346914547227496 + 40 +0.4826126922076991 + 50 +179.638444150984 + 51 +184.6022041776311 + 73 + 1 + 72 + 2 + 10 +0.9376165336263994 + 20 +0.3186947544718952 + 40 +0.1509003001157511 + 50 +183.9914206989488 + 51 +194.7961827171795 + 73 + 1 + 72 + 2 + 10 +0.8556691262907683 + 20 +0.2975229405501065 + 40 +0.0662649326044679 + 50 +195.1922580686626 + 51 +211.8161260167849 + 73 + 1 + 72 + 2 + 10 +0.8256760335810848 + 20 +0.2787995943136916 + 40 +0.0309077724093995 + 50 +211.6347351863199 + 51 +239.3370203444206 + 73 + 1 + 72 + 2 + 10 +0.8328177638353177 + 20 +0.2958607887822569 + 40 +0.0492921034260791 + 50 +242.3114767787511 + 51 +261.3474606529535 + 73 + 1 + 72 + 2 + 10 +0.8463235842781011 + 20 +0.3747617950344397 + 40 +0.1293354591063143 + 50 +260.6908797927596 + 51 +270.6747908046021 + 73 + 1 + 72 + 2 + 10 +0.8475369120546362 + 20 +1.499934543466537 + 40 +1.25449927615356 + 50 +270.0141521009336 + 51 +274.864484102984 + 73 + 1 + 72 + 1 + 10 +0.9539175761181276 + 20 +0.2499539083432495 + 11 +0.9712784354522652 + 21 +0.2513808595641643 + 72 + 1 + 10 +0.9712784354522652 + 20 +0.2513808595641643 + 11 +0.9712784354522652 + 21 +0.1940650616281518 + 72 + 2 + 10 +0.8963837746081258 + 20 +0.3325480038481863 + 40 +0.1574380370459314 + 50 +61.59448955636654 + 51 +83.93793890179708 + 73 + 0 + 72 + 2 + 10 +0.8330823004026875 + 20 +0.9588829323823655 + 40 +0.7869620433976263 + 50 +84.17070136778845 + 51 +89.53110693540054 + 73 + 0 + 72 + 1 + 10 +0.8395225116804813 + 20 +0.1719472415999074 + 11 +0.8357173084247086 + 21 +0.1719472415999074 + 72 + 2 + 10 +0.8200434901136805 + 20 +0.3538739274501789 + 40 +0.1826006232325358 + 50 +85.075865127039 + 51 +108.3600821200968 + 73 + 0 + 72 + 2 + 10 +0.7992279764644755 + 20 +0.2662427996310877 + 40 +0.093204559668334 + 50 +113.1894915396505 + 51 +140.0801272454766 + 73 + 0 + 72 + 2 + 10 +0.8012223158134221 + 20 +0.2683158374418412 + 40 +0.0960649049009913 + 50 +139.8951733394063 + 51 +156.2653987660679 + 73 + 0 + 72 + 2 + 10 +0.867342438096846 + 20 +0.2977766777590661 + 40 +0.168450950198126 + 50 +156.1444339138709 + 51 +167.3939009796797 + 73 + 0 + 72 + 2 + 10 +0.99451280167804 + 20 +0.3270031053307328 + 40 +0.2989352544876143 + 50 +167.2468323736907 + 51 +174.9177209790342 + 73 + 0 + 72 + 2 + 10 +1.20180856877263 + 20 +0.3462839419889538 + 40 +0.5071247554608478 + 50 +174.8226486749857 + 51 +180.2137793480696 + 73 + 0 + 72 + 1 + 10 +0.6946873432779551 + 20 +0.3481760979032103 + 11 +0.6946873432779551 + 21 +0.3481760979032103 + 97 + 1 +330 +B4 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C1 +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 16 + 72 + 1 + 10 +1.020746077777311 + 20 +0.1752767944487085 + 11 +1.020746077777311 + 21 +0.5201225784624666 + 72 + 1 + 10 +1.020746077777311 + 20 +0.5201225784624666 + 11 +1.097325032259088 + 21 +0.5201225784624666 + 72 + 1 + 10 +1.097325032259088 + 20 +0.5201225784624666 + 11 +1.111594544468236 + 21 +0.4766017077855419 + 72 + 2 + 10 +1.244437268897258 + 20 +0.3429659792394641 + 40 +0.1884295554783436 + 50 +225.1705040479414 + 51 +243.5972159016927 + 73 + 0 + 72 + 2 + 10 +1.211173613045121 + 20 +0.4086440720149234 + 40 +0.114812202274129 + 50 +243.8907918763913 + 51 +269.5602281386679 + 73 + 0 + 72 + 2 + 10 +1.212244334515651 + 20 +0.2785645037372034 + 40 +0.2448961677679514 + 50 +269.5433179430547 + 51 +275.0724278925614 + 73 + 0 + 72 + 2 + 10 +1.229554147138809 + 20 +0.4609473043473566 + 40 +0.0617072855517635 + 50 +274.0355485122913 + 51 +287.9600884366593 + 73 + 0 + 72 + 1 + 10 +1.248581861676056 + 20 +0.519647689096146 + 11 +1.248581861676056 + 21 +0.4318905695302117 + 72 + 2 + 10 +1.204841316941958 + 20 +-0.0620372588614032 + 40 +0.4958608019528185 + 50 +84.9392850010685 + 51 +90.63415610337293 + 73 + 1 + 72 + 2 + 10 +1.198149495755201 + 20 +0.2491083832840643 + 40 +0.1846887103819838 + 50 +89.62657779356016 + 51 +98.49286189291752 + 73 + 1 + 72 + 2 + 10 +1.186703181985212 + 20 +0.32427591283572 + 40 +0.1086552070090232 + 50 +98.37706810352306 + 51 +111.0116715202816 + 73 + 1 + 72 + 2 + 10 +1.173884337196004 + 20 +0.3604725103818166 + 40 +0.070276402608659 + 50 +111.8368548044861 + 51 +130.2463188715139 + 73 + 1 + 72 + 2 + 10 +1.191856507616234 + 20 +0.3396388865736808 + 40 +0.0977898738515406 + 50 +130.3972532514171 + 51 +145.1608900952568 + 73 + 1 + 72 + 1 + 10 +1.111594544468236 + 20 +0.39550369391721 + 11 +1.111594544468236 + 21 +0.1752767944487085 + 72 + 1 + 10 +1.111594544468236 + 20 +0.1752767944487085 + 11 +1.020746077777311 + 21 +0.1752767944487085 + 72 + 1 + 10 +1.020746077777311 + 20 +0.1752767944487085 + 11 +1.020746077777311 + 21 +0.1752767944487085 + 97 + 1 +330 +D8 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C2 +330 +1D +100 +AcDbEntity + 8 +TEXT-GRAY +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 2 + 92 + 1 + 93 + 30 + 72 + 2 + 10 +1.745775880860402 + 20 +0.3473056857538349 + 40 +0.4596595742917985 + 50 +179.219041199578 + 51 +188.5892672078823 + 73 + 0 + 72 + 2 + 10 +1.462665276168372 + 20 +0.3902293883547505 + 40 +0.1733136452000416 + 50 +188.5364777731353 + 51 +206.4130707393759 + 73 + 0 + 72 + 2 + 10 +1.382597433515457 + 20 +0.4290189590384098 + 40 +0.0843534860499277 + 50 +207.0087701028281 + 51 +238.085854021312 + 73 + 0 + 72 + 2 + 10 +1.408309618919584 + 20 +0.3846069642931946 + 40 +0.1356549785854117 + 50 +238.7839320009168 + 51 +258.9459185787553 + 73 + 0 + 72 + 2 + 10 +1.439724993974423 + 20 +0.2328843812063898 + 40 +0.29059126074079 + 50 +258.6024639297659 + 51 +270.7169453069864 + 73 + 0 + 72 + 2 + 10 +1.444920074652102 + 20 +0.2029818501508946 + 40 +0.3204748341784855 + 50 +269.7212762564572 + 51 +277.0779005236373 + 73 + 0 + 72 + 2 + 10 +1.460416453713881 + 20 +0.3252503357550985 + 40 +0.1972288945641309 + 50 +276.9871111277841 + 51 +287.1571071678799 + 73 + 0 + 72 + 2 + 10 +1.482143870267849 + 20 +0.3951169191449219 + 40 +0.1240620704779083 + 50 +287.0876504098538 + 51 +300.9508770078874 + 73 + 0 + 72 + 2 + 10 +1.500583736465673 + 20 +0.4262167749073336 + 40 +0.0879070752171196 + 50 +301.0685629566324 + 51 +318.5141019927507 + 73 + 0 + 72 + 2 + 10 +1.490538341293795 + 20 +0.4193627680062952 + 40 +0.0999841621843878 + 50 +319.38514811862 + 51 +335.2909851831375 + 73 + 0 + 72 + 2 + 10 +1.432430719209494 + 20 +0.3924029450769723 + 40 +0.1640411911207225 + 50 +335.220473520381 + 51 +346.6482421759119 + 73 + 0 + 72 + 2 + 10 +1.321167690210193 + 20 +0.3654957782609066 + 40 +0.2785109168173717 + 50 +346.5482508793782 + 51 +354.5741818072581 + 73 + 0 + 72 + 2 + 10 +1.140576365463508 + 20 +0.34757052037717 + 40 +0.459988693945271 + 50 +354.4784226911817 + 51 +360.2208980900735 + 73 + 0 + 72 + 2 + 10 +1.136142388530695 + 20 +0.3440375062016253 + 40 +0.4644225855321327 + 50 +359.7829203976418 + 51 +365.4556667991741 + 73 + 0 + 72 + 2 + 10 +1.324257241032597 + 20 +0.3255607991203732 + 40 +0.2754036673203588 + 50 +5.350003779949623 + 51 +13.38950403845408 + 73 + 0 + 72 + 2 + 10 +1.438822228558409 + 20 +0.2978741757969074 + 40 +0.1575418848528459 + 50 +13.24247481022855 + 51 +24.9143339913515 + 73 + 0 + 72 + 2 + 10 +1.49750166023149 + 20 +0.2704935387993822 + 40 +0.0927888674313809 + 50 +24.84449572776879 + 51 +41.46851456153187 + 73 + 0 + 72 + 2 + 10 +1.504747507691185 + 20 +0.2661434323058319 + 40 +0.0844927447051385 + 50 +42.51194694689715 + 51 +60.20982750498259 + 73 + 0 + 72 + 2 + 10 +1.484241834436404 + 20 +0.3022559330899828 + 40 +0.1260208208552944 + 50 +60.27608629427618 + 51 +73.82705129133484 + 73 + 0 + 72 + 2 + 10 +1.461143797848464 + 20 +0.3806703565348255 + 40 +0.2077659731176355 + 50 +73.73258141531123 + 51 +83.43685270361343 + 73 + 0 + 72 + 2 + 10 +1.444981387538941 + 20 +0.5159994031828512 + 40 +0.3440559769484268 + 50 +83.33882871764017 + 51 +90.26983081888446 + 73 + 0 + 72 + 2 + 10 +1.441836581268094 + 20 +0.4848621958152928 + 40 +0.3129186678351786 + 50 +89.72086066320244 + 51 +97.22714964633519 + 73 + 0 + 72 + 2 + 10 +1.426768810557204 + 20 +0.3683000729345016 + 40 +0.1953872384683834 + 50 +97.14382290172345 + 51 +107.4222425802834 + 73 + 0 + 72 + 2 + 10 +1.405753699036433 + 20 +0.3016738701941614 + 40 +0.1255254500273459 + 50 +107.3755052356472 + 51 +121.1859060075268 + 73 + 0 + 72 + 2 + 10 +1.388200250824436 + 20 +0.2723186857145772 + 40 +0.091323052757868 + 50 +121.3012045363258 + 51 +138.3807483919028 + 73 + 0 + 72 + 2 + 10 +1.396390386155313 + 20 +0.2780817143578742 + 40 +0.1012797862356359 + 50 +139.0208188923022 + 51 +154.2673000625914 + 73 + 0 + 72 + 2 + 10 +1.443564578953644 + 20 +0.3008357842563767 + 40 +0.153654894821596 + 50 +154.2614231301619 + 51 +165.8039007823683 + 73 + 0 + 72 + 2 + 10 +1.533704415876427 + 20 +0.3240227080426966 + 40 +0.2467287207424286 + 50 +165.7173228384291 + 51 +174.1318325417901 + 73 + 0 + 72 + 2 + 10 +1.679452490871063 + 20 +0.3395070071807061 + 40 +0.3932964759323175 + 50 +174.0587164483615 + 51 +180.2234129253398 + 73 + 0 + 72 + 1 + 10 +1.286159004867464 + 20 +0.3410405807579851 + 11 +1.286159004867464 + 21 +0.3410405807579851 + 97 + 1 +330 +14B + 92 + 16 + 93 + 21 + 72 + 2 + 10 +1.87884778741299 + 20 +0.3051697834906549 + 40 +0.5046900079850218 + 50 +165.4581922653545 + 51 +171.0243917073363 + 73 + 1 + 72 + 2 + 10 +1.640017569701684 + 20 +0.3421119050184488 + 40 +0.2630219456806235 + 50 +170.856419407449 + 51 +179.4561773269252 + 73 + 1 + 72 + 2 + 10 +1.719600323247084 + 20 +0.3382249259339413 + 40 +0.342652316488281 + 50 +178.9325511963493 + 51 +188.0659430044691 + 73 + 1 + 72 + 2 + 10 +1.461506204624639 + 20 +0.3030699205237911 + 40 +0.0821908055767169 + 50 +189.0465869719995 + 51 +201.4429641704123 + 73 + 1 + 72 + 2 + 10 +1.425949825821255 + 20 +0.2889700547677836 + 40 +0.0439411927350844 + 50 +201.2794750422889 + 51 +220.1176890207309 + 73 + 1 + 72 + 2 + 10 +1.421375505703486 + 20 +0.2843571418367111 + 40 +0.0374752217300239 + 50 +219.2307545260716 + 51 +255.6490576647813 + 73 + 1 + 72 + 2 + 10 +1.438807477461641 + 20 +0.3811952640733502 + 40 +0.1357987619432282 + 50 +258.6520849549118 + 51 +271.3697308658793 + 73 + 1 + 72 + 2 + 10 +1.445896027874007 + 20 +0.4691190853840432 + 40 +0.2237167796028082 + 50 +269.0158770897956 + 51 +276.276357003502 + 73 + 1 + 72 + 2 + 10 +1.463387403735492 + 20 +0.2947145002894463 + 40 +0.0484744436347309 + 50 +278.2625944015626 + 51 +301.2735466815289 + 73 + 1 + 72 + 2 + 10 +1.473353916121774 + 20 +0.2781237012056268 + 40 +0.0291206023535156 + 50 +301.4591386210279 + 51 +342.6827079184787 + 73 + 1 + 72 + 2 + 10 +1.374091031750538 + 20 +0.3127659022243659 + 40 +0.1342419911030445 + 50 +341.1780241039497 + 51 +353.2229122868627 + 73 + 1 + 72 + 2 + 10 +1.232912256678613 + 20 +0.3308726804904729 + 40 +0.2765741939881523 + 50 +352.9494162843384 + 51 +360.3822505868759 + 73 + 1 + 72 + 2 + 10 +0.7248612462910731 + 20 +0.3411691780724345 + 40 +0.7846645638024572 + 50 +359.3828759745637 + 51 +363.6573187603917 + 73 + 1 + 72 + 2 + 10 +1.358304373290006 + 20 +0.3811941386031548 + 40 +0.1499590652226746 + 50 +3.834298057692314 + 51 +15.98721166096502 + 73 + 1 + 72 + 2 + 10 +1.473936824340389 + 20 +0.4156549366241289 + 40 +0.0293355637618033 + 50 +13.48613242730697 + 51 +56.84075856181408 + 73 + 1 + 72 + 2 + 10 +1.460693878894012 + 20 +0.3942253340844751 + 40 +0.054522595367914 + 50 +57.50799133160251 + 51 +77.8514521481949 + 73 + 1 + 72 + 2 + 10 +1.449551855505779 + 20 +0.3442176219715277 + 40 +0.1057558456740848 + 50 +77.65179244717869 + 51 +90.71274674017063 + 73 + 1 + 72 + 2 + 10 +1.446520818841627 + 20 +0.1669086878434607 + 40 +0.2830617955533721 + 50 +89.65275773185921 + 51 +94.33247869604129 + 73 + 1 + 72 + 2 + 10 +1.430610265978255 + 20 +0.3644952794934767 + 40 +0.0848430589089613 + 50 +93.69860806412952 + 51 +104.1787730439532 + 73 + 1 + 72 + 2 + 10 +1.420228457430697 + 20 +0.4128805599428683 + 40 +0.0354338310931719 + 50 +107.0684876277999 + 51 +147.5547663680418 + 73 + 1 + 72 + 1 + 10 +1.390325682953593 + 20 +0.4318905695302117 + 11 +1.390325682953593 + 21 +0.4318905695302117 + 97 + 1 +330 +10A + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C5 +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 2 + 92 + 1 + 93 + 17 + 72 + 1 + 10 +1.658111534794044 + 20 +0.1752767944487085 + 11 +1.658111534794044 + 21 +0.6506897567371471 + 72 + 1 + 10 +1.658111534794044 + 20 +0.6506897567371471 + 11 +1.862892353206713 + 21 +0.6506897567371471 + 72 + 2 + 10 +1.866712771298765 + 20 +0.4812885811102773 + 40 +0.1694442501183315 + 50 +268.7080565864779 + 51 +289.696280270266 + 73 + 0 + 72 + 2 + 10 +1.890323704356795 + 20 +0.5498088066581733 + 40 +0.0969791362784035 + 50 +290.2068256429989 + 51 +320.7179581453081 + 73 + 0 + 72 + 2 + 10 +1.872231214265821 + 20 +0.5377375192902893 + 40 +0.1186450067238793 + 50 +321.7376468722154 + 51 +345.941318148983 + 73 + 0 + 72 + 2 + 10 +1.755413737650509 + 20 +0.5077074919349243 + 40 +0.239259448802611 + 50 +345.7608112632561 + 51 +360.8993727822122 + 73 + 0 + 72 + 2 + 10 +1.739929769421669 + 20 +0.4990316766439469 + 40 +0.2547614597035357 + 50 +358.8933548673149 + 51 +375.1421636632072 + 73 + 0 + 72 + 2 + 10 +1.805070643979139 + 20 +0.4843830829172414 + 40 +0.1880777885766737 + 50 +16.01826700445136 + 51 +24.59137858751017 + 73 + 0 + 72 + 2 + 10 +1.886457278838033 + 20 +0.4467408832612785 + 40 +0.098409106202089 + 50 +24.38210075542359 + 51 +37.59560803165674 + 73 + 0 + 72 + 2 + 10 +1.901447144532471 + 20 +0.4366823005906129 + 40 +0.0804040955571766 + 50 +38.43315571073376 + 51 +67.41262732859074 + 73 + 0 + 72 + 2 + 10 +1.877530541683213 + 20 +0.482621245957908 + 40 +0.1320800191028363 + 50 +65.48738102872184 + 51 +90.78391246376287 + 73 + 0 + 72 + 2 + 10 +1.89658449370416 + 20 +1.061679540017775 + 40 +0.711431865658397 + 50 +91.68029910103571 + 51 +97.60098612101147 + 73 + 0 + 72 + 2 + 10 +2.098301318614009 + 20 +2.918534187606983 + 40 +2.579056963876972 + 50 +96.58637858697409 + 51 +97.45141278012369 + 73 + 0 + 72 + 2 + 10 +1.776013741879782 + 20 +0.4823678310216308 + 40 +0.1217217342158525 + 50 +95.74213501202033 + 51 +102.7219939836472 + 73 + 0 + 72 + 1 + 10 +1.749208100737245 + 20 +0.3636343556094617 + 11 +1.749208100737245 + 21 +0.1752767944487085 + 72 + 1 + 10 +1.749208100737245 + 20 +0.1752767944487085 + 11 +1.658111534794044 + 21 +0.1752767944487085 + 72 + 1 + 10 +1.658111534794044 + 20 +0.1752767944487085 + 11 +1.658111534794044 + 21 +0.1752767944487085 + 97 + 1 +330 +138 + 92 + 16 + 93 + 12 + 72 + 1 + 10 +1.855753791898883 + 20 +0.5703040769182958 + 11 +1.749208100737245 + 21 +0.5703040769182958 + 72 + 1 + 10 +1.749208100737245 + 20 +0.5703040769182958 + 11 +1.749208100737245 + 21 +0.4311767133994287 + 72 + 1 + 10 +1.749208100737245 + 20 +0.4311767133994287 + 11 +1.855281946695168 + 21 +0.4311767133994287 + 72 + 2 + 10 +1.857310696196809 + 20 +0.4789795547126073 + 40 +0.0478458719447492 + 50 +267.5698291459668 + 51 +298.9736848744403 + 73 + 1 + 72 + 2 + 10 +1.864437662714773 + 20 +0.4638897212446849 + 40 +0.0312107960389064 + 50 +300.9469057674883 + 51 +325.1843100261158 + 73 + 1 + 72 + 2 + 10 +1.847208640489655 + 20 +0.4756552874383635 + 40 +0.0520734162270339 + 50 +325.3793523193102 + 51 +342.5869620344669 + 73 + 1 + 72 + 2 + 10 +1.761853469548879 + 20 +0.499095419473726 + 40 +0.1405675106851083 + 50 +343.8821453186945 + 51 +361.6888272002417 + 73 + 1 + 72 + 2 + 10 +1.771325527872711 + 20 +0.505069610767784 + 40 +0.1310471922643137 + 50 +359.1992235790916 + 51 +372.1177778779552 + 73 + 1 + 72 + 2 + 10 +1.840471280377904 + 20 +0.5202934512206887 + 40 +0.0602474495482526 + 50 +11.76645972748428 + 51 +33.49099599484823 + 73 + 1 + 72 + 2 + 10 +1.86002067419837 + 20 +0.5327033580204925 + 40 +0.0370985166555385 + 50 +34.16739135196509 + 51 +64.22988058382727 + 73 + 1 + 72 + 2 + 10 +1.856792087819456 + 20 +0.5236405260900577 + 40 +0.0466751007960158 + 50 +65.49764645855024 + 51 +91.27465994990668 + 73 + 1 + 72 + 1 + 10 +1.855753791898883 + 20 +0.5703040769182958 + 11 +1.855753791898883 + 21 +0.5703040769182958 + 97 + 1 +330 +4A + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C6 +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 17 + 72 + 1 + 10 +2.026516093204943 + 20 +0.5201225784624666 + 11 +2.12187448679461 + 21 +0.5201225784624666 + 72 + 1 + 10 +2.12187448679461 + 20 +0.5201225784624666 + 11 +2.181814048479542 + 21 +0.2784929327615455 + 72 + 2 + 10 +2.213922500215711 + 20 +0.2853658521330381 + 40 +0.0328357989636449 + 50 +192.0820235727047 + 51 +230.2482576268844 + 73 + 1 + 72 + 2 + 10 +2.211977736162895 + 20 +0.2865212844941371 + 40 +0.0325572563546005 + 50 +234.1829062182941 + 51 +272.5793312178134 + 73 + 1 + 72 + 2 + 10 +2.218185855487651 + 20 +0.2662392650291758 + 40 +0.0131289140189778 + 50 +248.8223744883709 + 51 +260.6854283382104 + 73 + 1 + 72 + 1 + 10 +2.216060877781497 + 20 +0.2532834611920508 + 11 +2.285026381589124 + 21 +0.5201225784624666 + 72 + 1 + 10 +2.285026381589124 + 20 +0.5201225784624666 + 11 +2.379912929975073 + 21 +0.5201225784624666 + 72 + 1 + 10 +2.379912929975073 + 20 +0.5201225784624666 + 11 +2.2602925604266 + 21 +0.0661149499446615 + 72 + 1 + 10 +2.2602925604266 + 20 +0.0661149499446615 + 11 +2.21297105273781 + 21 +0.0 + 72 + 1 + 10 +2.21297105273781 + 20 +0.0 + 11 +2.147795531372934 + 21 +0.0 + 72 + 1 + 10 +2.147795531372934 + 20 +0.0 + 11 +2.196547795485895 + 21 +0.1752767944487085 + 72 + 2 + 10 +2.195202176373045 + 20 +0.2879880150203464 + 40 +0.1127192527190687 + 50 +89.31599859402309 + 51 +107.9604459396842 + 73 + 0 + 72 + 2 + 10 +2.187860498124107 + 20 +0.2632664971382323 + 40 +0.0869408911919764 + 50 +108.3817089051841 + 51 +130.5609495896915 + 73 + 0 + 72 + 2 + 10 +2.198002807128255 + 20 +0.2736653212156158 + 40 +0.101440520082671 + 50 +131.0937856248721 + 51 +151.0996267706195 + 73 + 0 + 72 + 2 + 10 +2.251259362016389 + 20 +0.3028621870346081 + 40 +0.1621751716283119 + 50 +151.1623473832895 + 51 +165.7835266974244 + 73 + 0 + 72 + 1 + 10 +2.094050840588399 + 20 +0.2630342184309034 + 11 +2.026516093204943 + 21 +0.5201225784624666 + 72 + 1 + 10 +2.026516093204943 + 20 +0.5201225784624666 + 11 +2.026516093204943 + 21 +0.5201225784624666 + 97 + 1 +330 +89 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C7 +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 23 + 72 + 1 + 10 +2.401085080890193 + 20 +0.451391475175396 + 11 +2.401085080890193 + 21 +0.502049385078848 + 72 + 1 + 10 +2.401085080890193 + 20 +0.502049385078848 + 11 +2.456975906310984 + 21 +0.5208364345932495 + 72 + 1 + 10 +2.456975906310984 + 20 +0.5208364345932495 + 11 +2.471953186325706 + 21 +0.6169178168015124 + 72 + 1 + 10 +2.471953186325706 + 20 +0.6169178168015124 + 11 +2.547828939245814 + 21 +0.6169178168015124 + 72 + 1 + 10 +2.547828939245814 + 20 +0.6169178168015124 + 11 +2.547828939245814 + 21 +0.5208364345932495 + 72 + 1 + 10 +2.547828939245814 + 20 +0.5208364345932495 + 11 +2.625120227777072 + 21 +0.5208364345932495 + 72 + 1 + 10 +2.625120227777072 + 20 +0.5208364345932495 + 11 +2.625120227777072 + 21 +0.451391475175396 + 72 + 1 + 10 +2.625120227777072 + 20 +0.451391475175396 + 11 +2.547828939245814 + 21 +0.451391475175396 + 72 + 1 + 10 +2.547828939245814 + 20 +0.451391475175396 + 11 +2.547828939245814 + 21 +0.312977967787312 + 72 + 2 + 10 +2.756375078424425 + 20 +0.3106349819782397 + 40 +0.208559300317214 + 50 +179.3563172584847 + 51 +187.5204775666663 + 73 + 1 + 72 + 2 + 10 +2.610407599922477 + 20 +0.2901879066221412 + 40 +0.0611824171745163 + 50 +186.4276465021346 + 51 +204.9884326299174 + 73 + 1 + 72 + 2 + 10 +2.591486060141609 + 20 +0.2832478516776391 + 40 +0.0411355950463604 + 50 +207.3607300982318 + 51 +249.4822289731461 + 73 + 1 + 72 + 2 + 10 +2.925871745813213 + 20 +1.236527392855755 + 40 +1.05135264976578 + 50 +250.6239679589966 + 51 +252.369953071448 + 73 + 1 + 72 + 2 + 10 +2.632025513918952 + 20 +0.3027146749676596 + 40 +0.0724554546479011 + 50 +250.172060625216 + 51 +260.9268652271251 + 73 + 1 + 72 + 1 + 10 +2.620599646309214 + 20 +0.2311657933719365 + 11 +2.620599646309214 + 21 +0.1752767944487085 + 72 + 1 + 10 +2.620599646309214 + 20 +0.1752767944487085 + 11 +2.541405756150071 + 21 +0.1752767944487085 + 72 + 2 + 10 +2.539541691321775 + 20 +0.2586536504670411 + 40 +0.0833976909583584 + 50 +88.71924580725035 + 51 +114.8723068619946 + 73 + 0 + 72 + 2 + 10 +2.534259066943731 + 20 +0.2435901096002027 + 40 +0.0675271066805567 + 50 +116.1816665503854 + 51 +146.3117142175992 + 73 + 0 + 72 + 2 + 10 +2.571816472169667 + 20 +0.2671405893161746 + 40 +0.1118470865035182 + 50 +146.9451672649385 + 51 +168.4294027765594 + 73 + 0 + 72 + 2 + 10 +2.701886448180166 + 20 +0.2953352474010394 + 40 +0.2449337665542188 + 50 +168.070822892956 + 51 +180.7890266060776 + 73 + 0 + 72 + 1 + 10 +2.456975906310984 + 20 +0.2987081511619036 + 11 +2.456975906310984 + 21 +0.451391475175396 + 72 + 1 + 10 +2.456975906310984 + 20 +0.451391475175396 + 11 +2.401085080890193 + 21 +0.451391475175396 + 72 + 1 + 10 +2.401085080890193 + 20 +0.451391475175396 + 11 +2.401085080890193 + 21 +0.451391475175396 + 97 + 1 +330 +58 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C8 +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 22 + 72 + 1 + 10 +2.66863653221009 + 20 +0.1752767944487085 + 11 +2.66863653221009 + 21 +0.6839852852251591 + 72 + 1 + 10 +2.66863653221009 + 20 +0.683985285225159 + 11 +2.758774186932835 + 21 +0.683985285225159 + 72 + 1 + 10 +2.758774186932835 + 20 +0.683985285225159 + 11 +2.758774186932835 + 21 +0.4832608134831443 + 72 + 2 + 10 +2.970884692343786 + 20 +0.1949308647558484 + 40 +0.3579455626750722 + 50 +233.6598667174819 + 51 +241.6737203338166 + 73 + 0 + 72 + 2 + 10 +2.862953103918855 + 20 +0.398321949096261 + 40 +0.1277046941848677 + 50 +241.0008951743301 + 51 +256.9710241053807 + 73 + 0 + 72 + 2 + 10 +2.867314180648163 + 20 +0.3596725627348979 + 40 +0.1664021752218955 + 50 +258.5084157090225 + 51 +270.4610700343784 + 73 + 0 + 72 + 2 + 10 +2.871155730201377 + 20 +0.4023028257494028 + 40 +0.1237918213330042 + 50 +268.8416672957483 + 51 +290.1493812176847 + 73 + 0 + 72 + 2 + 10 +2.88549439287798 + 20 +0.4438925273392474 + 40 +0.0798129708700709 + 50 +290.7705399537808 + 51 +319.3693426350027 + 73 + 0 + 72 + 2 + 10 +2.86973875277353 + 20 +0.4329212526250472 + 40 +0.0989334609539707 + 50 +320.4891190671877 + 51 +345.2499775321184 + 73 + 0 + 72 + 2 + 10 +2.778017766714932 + 20 +0.4084074663129932 + 40 +0.1938734483480787 + 50 +345.1454837561613 + 51 +360.9319474711875 + 73 + 0 + 72 + 1 + 10 +2.971865569256112 + 20 +0.4052541467398021 + 11 +2.971865569256112 + 21 +0.1752767944487085 + 72 + 1 + 10 +2.971865569256112 + 20 +0.1752767944487085 + 11 +2.881012536321281 + 21 +0.1752767944487085 + 72 + 1 + 10 +2.881012536321281 + 20 +0.1752767944487085 + 11 +2.881012536321281 + 21 +0.4064428922369056 + 72 + 2 + 10 +2.802613036220481 + 20 +0.4076912084297279 + 40 +0.0784094376294883 + 50 +359.0877849241664 + 51 +374.2114110518409 + 73 + 1 + 72 + 2 + 10 +2.840775464266772 + 20 +0.4174522933113873 + 40 +0.0390186755568009 + 50 +14.07416101436572 + 51 +38.19979694511947 + 73 + 1 + 72 + 2 + 10 +2.848474408609313 + 20 +0.4228438207727886 + 40 +0.0296388733419943 + 50 +39.21298268016682 + 51 +68.21300572178883 + 73 + 1 + 72 + 2 + 10 +2.843635884024977 + 20 +0.4091395078042849 + 40 +0.0441641298463429 + 50 +68.98305490508943 + 51 +91.1922266305568 + 73 + 1 + 72 + 2 + 10 +2.839517556631515 + 20 +0.3257194842430624 + 40 +0.1276147049428117 + 50 +88.56339333889899 + 51 +108.8133720429226 + 73 + 1 + 72 + 2 + 10 +2.853071660183995 + 20 +0.3106172986056333 + 40 +0.146497457591775 + 50 +111.9279820567162 + 51 +129.7021521663467 + 73 + 1 + 72 + 1 + 10 +2.759489565144921 + 20 +0.4233288622047228 + 11 +2.759489565144921 + 21 +0.1752767944487085 + 72 + 1 + 10 +2.759489565144921 + 20 +0.1752767944487085 + 11 +2.66863653221009 + 21 +0.1752767944487085 + 72 + 1 + 10 +2.66863653221009 + 20 +0.1752767944487085 + 11 +2.66863653221009 + 21 +0.1752767944487085 + 97 + 1 +330 +9C + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1C9 +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 2 + 92 + 1 + 93 + 30 + 72 + 2 + 10 +3.480235470402663 + 20 +0.3472963994916086 + 40 +0.4596602087851077 + 50 +179.2201999001178 + 51 +188.5904259084221 + 73 + 0 + 72 + 2 + 10 +3.197121821548028 + 20 +0.3902535820648669 + 40 +0.1733062924357386 + 50 +188.5287545821982 + 51 +206.4053475484388 + 73 + 0 + 72 + 2 + 10 +3.11705169577316 + 20 +0.4290134848926255 + 40 +0.084357328189102 + 50 +207.0116131808711 + 51 +238.088697099355 + 73 + 0 + 72 + 2 + 10 +3.142763881177286 + 20 +0.3846155256577634 + 40 +0.1356468679361114 + 50 +238.7826076590414 + 51 +258.9445942368799 + 73 + 0 + 72 + 2 + 10 +3.174180017272777 + 20 +0.2328628655440478 + 40 +0.2906128032937941 + 50 +258.6028609455173 + 51 +270.7173423227377 + 73 + 0 + 72 + 2 + 10 +3.179378903153711 + 20 +0.2029581738044638 + 40 +0.3204985176522159 + 50 +269.7210247461867 + 51 +277.0776490133664 + 73 + 0 + 72 + 2 + 10 +3.19487528221549 + 20 +0.325267440923209 + 40 +0.1972121016147459 + 50 +276.9881545773719 + 51 +287.1581506174676 + 73 + 0 + 72 + 2 + 10 +3.216601176688156 + 20 +0.3951169191449229 + 40 +0.1240620704779073 + 50 +287.0876504098541 + 51 +300.9508770078876 + 73 + 0 + 72 + 2 + 10 +3.235041042885957 + 20 +0.4262167749073067 + 40 +0.0879070752171545 + 50 +301.0685629566362 + 51 +318.5141019927475 + 73 + 0 + 72 + 2 + 10 +3.22499564771415 + 20 +0.4193627680063226 + 40 +0.0999841621843335 + 50 +319.385148118614 + 51 +335.2909851831404 + 73 + 0 + 72 + 2 + 10 +3.166888025629801 + 20 +0.3924029450769745 + 40 +0.1640411911207218 + 50 +335.2204735203817 + 51 +346.6482421759127 + 73 + 0 + 72 + 2 + 10 +3.055624996630501 + 20 +0.3654957782609082 + 40 +0.2785109168173713 + 50 +346.5482508793785 + 51 +354.5741818072585 + 73 + 0 + 72 + 2 + 10 +2.875033671883636 + 20 +0.3475705203771616 + 40 +0.4599886939454501 + 50 +354.4784226911829 + 51 +360.2208980900725 + 73 + 0 + 72 + 2 + 10 +2.870607305357513 + 20 +0.3438838987998202 + 40 +0.4644155825717984 + 50 +359.7639661566379 + 51 +365.4367125581701 + 73 + 0 + 72 + 2 + 10 +3.058722157859415 + 20 +0.3256690965276672 + 40 +0.2754213630050057 + 50 +5.372287081245953 + 51 +13.41178733975041 + 73 + 0 + 72 + 2 + 10 +3.173279534978716 + 20 +0.2978741757969097 + 40 +0.1575418848528468 + 50 +13.24247481022931 + 51 +24.91433399135224 + 73 + 0 + 72 + 2 + 10 +3.231958966651797 + 20 +0.27049353879938 + 40 +0.0927888674313799 + 50 +24.84449572776762 + 51 +41.46851456153065 + 73 + 0 + 72 + 2 + 10 +3.239204814111471 + 20 +0.2661434323058576 + 40 +0.0844927447051714 + 50 +42.51194694690035 + 51 +60.20982750497873 + 73 + 0 + 72 + 2 + 10 +3.218699140856711 + 20 +0.3022559330899847 + 40 +0.1260208208552961 + 50 +60.27608629427653 + 51 +73.8270512913352 + 73 + 0 + 72 + 2 + 10 +3.195604909472027 + 20 +0.3806255307799783 + 40 +0.207721876247583 + 50 +73.73012549511914 + 51 +83.43439678342133 + 73 + 0 + 72 + 2 + 10 +3.179442499162505 + 20 +0.5160622385854792 + 40 +0.3441188295924385 + 50 +83.33941300651419 + 51 +90.27041510775888 + 73 + 0 + 72 + 2 + 10 +3.176297692891656 + 20 +0.4848041884129171 + 40 +0.3128606426025486 + 50 +89.72150576644664 + 51 +97.22779474957937 + 73 + 0 + 72 + 2 + 10 +3.161234488424673 + 20 +0.3682916110468403 + 40 +0.1953789369211231 + 50 +97.14435294680244 + 51 +107.4227726253624 + 73 + 0 + 72 + 2 + 10 +3.140217093781949 + 20 +0.301699006668967 + 40 +0.1255485308215694 + 50 +107.370753656409 + 51 +121.1811544282885 + 73 + 0 + 72 + 2 + 10 +3.12266212348865 + 20 +0.2723085493673603 + 40 +0.0913151827909786 + 50 +121.3053248468621 + 51 +138.3848687024391 + 73 + 0 + 72 + 2 + 10 +3.130851497778824 + 20 +0.2780987727770228 + 40 +0.1012892502687907 + 50 +139.0126872013657 + 51 +154.2591683716641 + 73 + 0 + 72 + 2 + 10 +3.178025690577206 + 20 +0.3008131945580285 + 40 +0.1536471429745666 + 50 +154.2693808990751 + 51 +165.8118585512815 + 73 + 0 + 72 + 2 + 10 +3.268168571662594 + 20 +0.3240123625755021 + 40 +0.2467269061818614 + 50 +165.7196946403268 + 51 +174.1342043436877 + 73 + 0 + 72 + 2 + 10 +3.413914363535721 + 20 +0.3395635385525735 + 40 +0.3932993037049538 + 50 +174.0504793005304 + 51 +180.2151757775018 + 73 + 0 + 72 + 1 + 10 +3.020617833369073 + 20 +0.3410405807579851 + 11 +3.020617833369073 + 21 +0.3410405807579851 + 97 + 1 +330 +EA + 92 + 16 + 93 + 21 + 72 + 2 + 10 +3.613312704239808 + 20 +0.3052010939876257 + 40 +0.5046836205998101 + 50 +165.4616764010741 + 51 +171.0278758430559 + 73 + 1 + 72 + 2 + 10 +3.374482486528501 + 20 +0.3420916614133984 + 40 +0.2630236606104225 + 50 +170.85201298578 + 51 +179.4517709052564 + 73 + 1 + 72 + 2 + 10 +3.454065240073902 + 20 +0.3382439821810626 + 40 +0.3426534838299237 + 50 +178.9357418182288 + 51 +188.0691336263486 + 73 + 1 + 72 + 2 + 10 +3.195968077288853 + 20 +0.3030278751539043 + 40 +0.0821796951545775 + 50 +189.0181381128171 + 51 +201.4145153112299 + 73 + 1 + 72 + 2 + 10 +3.160411698485469 + 20 +0.2889975802415061 + 40 +0.0439554436806379 + 50 +201.3107480863471 + 51 +220.1489620647889 + 73 + 1 + 72 + 2 + 10 +3.155835095245747 + 20 +0.2843363205812091 + 40 +0.037456749731058 + 50 +219.2127101386138 + 51 +255.6310132773234 + 73 + 1 + 72 + 2 + 10 +3.173261739719343 + 20 +0.3812089223380726 + 40 +0.1358124526943521 + 50 +258.6525891616267 + 51 +271.3702350725942 + 73 + 1 + 72 + 2 + 10 +3.180357139497569 + 20 +0.4692030529375931 + 40 +0.2238008263021876 + 50 +269.0148826539333 + 51 +276.2753625676396 + 73 + 1 + 72 + 2 + 10 +3.197849276399706 + 20 +0.2946920674583943 + 40 +0.0484529004947375 + 50 +278.2717501461559 + 51 +301.2827024261222 + 73 + 1 + 72 + 2 + 10 +3.207811222542081 + 20 +0.2781237012056277 + 40 +0.0291206023535162 + 50 +301.4591386210265 + 51 +342.6827079184772 + 73 + 1 + 72 + 2 + 10 +3.108548338170845 + 20 +0.3127659022243659 + 40 +0.1342419911030445 + 50 +341.1780241039497 + 51 +353.2229122868627 + 73 + 1 + 72 + 2 + 10 +2.967369563098919 + 20 +0.330872680490466 + 40 +0.2765741939881519 + 50 +352.9494162843399 + 51 +360.3822505868774 + 73 + 1 + 72 + 2 + 10 +2.459318552711379 + 20 +0.3411691780724464 + 40 +0.7846645638024574 + 50 +359.3828759745628 + 51 +363.6573187603909 + 73 + 1 + 72 + 2 + 10 +3.092761679710313 + 20 +0.3811941386031558 + 40 +0.1499590652226746 + 50 +3.834298057691928 + 51 +15.98721166096461 + 73 + 1 + 72 + 2 + 10 +3.208394130760695 + 20 +0.4156549366241278 + 40 +0.029335563761804 + 50 +13.48613242730889 + 51 +56.84075856181601 + 73 + 1 + 72 + 2 + 10 +3.195154229476923 + 20 +0.3942423008569769 + 40 +0.0545066495896497 + 50 +57.50110974384233 + 51 +77.84457056043473 + 73 + 1 + 72 + 2 + 10 +3.184009922966737 + 20 +0.344171085093621 + 40 +0.1058024453263516 + 50 +77.65436364628005 + 51 +90.71531793927198 + 73 + 1 + 72 + 2 + 10 +3.180978125261934 + 20 +0.1670204385423348 + 40 +0.2829500192598661 + 50 +89.65354521146901 + 51 +94.33326617565109 + 73 + 1 + 72 + 2 + 10 +3.165070616561166 + 20 +0.3644786832754941 + 40 +0.084859522413094 + 50 +93.69685967486203 + 51 +104.1770246546857 + 73 + 1 + 72 + 2 + 10 +3.15468956905426 + 20 +0.4128867508985087 + 40 +0.0354285831761041 + 50 +107.0749560136262 + 51 +147.5612347538681 + 73 + 1 + 72 + 1 + 10 +3.124789077699108 + 20 +0.4318905695302117 + 11 +3.124789077699108 + 21 +0.4318905695302117 + 97 + 1 +330 +121 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +HATCH + 5 +1CA +330 +1D +100 +AcDbEntity + 8 +TEXT-RED +100 +AcDbHatch + 10 +0.0 + 20 +0.0 + 30 +0.0 +210 +0.0 +220 +0.0 +230 +1.0 + 2 +SOLID + 70 + 1 + 71 + 1 + 91 + 1 + 92 + 1 + 93 + 22 + 72 + 2 + 10 +3.592005824568463 + 20 +0.4022623702532142 + 40 +0.1238324225952604 + 50 +268.8385251676425 + 51 +290.1462390895788 + 73 + 0 + 72 + 2 + 10 +3.606344487245067 + 20 +0.4439223854568978 + 40 +0.0797877541011788 + 50 +290.7832534290268 + 51 +319.3820561102488 + 73 + 0 + 72 + 2 + 10 +3.590581236734105 + 20 +0.4329212526250472 + 40 +0.0989334609539707 + 50 +320.4891190671877 + 51 +345.2499775321184 + 73 + 0 + 72 + 2 + 10 +3.498860250675552 + 20 +0.4084074663130021 + 40 +0.1938734483480326 + 50 +345.1454837561604 + 51 +360.9319474711903 + 73 + 0 + 72 + 1 + 10 +3.692708053216686 + 20 +0.4052541467398021 + 11 +3.692708053216686 + 21 +0.1752767944487085 + 72 + 1 + 10 +3.692708053216686 + 20 +0.1752767944487085 + 11 +3.601870241094878 + 21 +0.1752767944487085 + 72 + 1 + 10 +3.601870241094878 + 20 +0.1752767944487085 + 11 +3.601870241094878 + 21 +0.4064428922369056 + 72 + 2 + 10 +3.523463130587567 + 20 +0.4076338796510298 + 40 +0.0784161554089863 + 50 +359.1297561618085 + 51 +374.2533822894829 + 73 + 1 + 72 + 2 + 10 +3.561625558633858 + 20 +0.4174879054254667 + 40 +0.0390026472343202 + 50 +14.02613509500026 + 51 +38.15177102575402 + 73 + 1 + 72 + 2 + 10 +3.569324502976398 + 20 +0.4228143935386817 + 40 +0.029663379390137 + 50 +39.24772886833219 + 51 +68.2477519099542 + 73 + 1 + 72 + 2 + 10 +3.564485978392062 + 20 +0.4091782819430569 + 40 +0.0441252062777969 + 50 +68.97422263922098 + 51 +91.18339436468834 + 73 + 1 + 72 + 2 + 10 +3.560375261405112 + 20 +0.3257194842430623 + 40 +0.1276147049428117 + 50 +88.56339333889899 + 51 +108.8133720429226 + 73 + 1 + 72 + 2 + 10 +3.573921754551081 + 20 +0.3105686277924473 + 40 +0.1465397674015583 + 50 +111.9181151967782 + 51 +129.6922853064086 + 73 + 1 + 72 + 1 + 10 +3.480332049105495 + 20 +0.4233288622047228 + 11 +3.480332049105495 + 21 +0.1752767944487085 + 72 + 1 + 10 +3.480332049105495 + 20 +0.1752767944487085 + 11 +3.389479016170664 + 21 +0.1752767944487085 + 72 + 1 + 10 +3.389479016170664 + 20 +0.1752767944487085 + 11 +3.389479016170664 + 21 +0.5201225784624666 + 72 + 1 + 10 +3.389479016170664 + 20 +0.5201225784624666 + 11 +3.462264944047086 + 21 +0.5201225784624666 + 72 + 1 + 10 +3.462264944047086 + 20 +0.5201225784624666 + 11 +3.480332049105495 + 21 +0.4832608134831443 + 72 + 2 + 10 +3.692032830344103 + 20 +0.1968176418438357 + 40 +0.3561838168078713 + 50 +233.5331050519283 + 51 +241.6403323622616 + 73 + 0 + 72 + 2 + 10 +3.581912438010629 + 20 +0.4042431550954748 + 40 +0.1213560014894028 + 50 +240.8735520743203 + 51 +257.5360464861715 + 73 + 0 + 72 + 2 + 10 +3.587849834142919 + 20 +0.3698286725878678 + 40 +0.1562493464094038 + 50 +258.1337893490277 + 51 +270.603548530042 + 73 + 0 + 72 + 1 + 10 +3.589495720107105 + 20 +0.5260693501105883 + 11 +3.589495720107105 + 21 +0.5260693501105883 + 97 + 1 +330 +71 + 75 + 0 + 76 + 1 + 98 + 1 + 10 +-0.0349603810164775 + 20 +0.1524455749140718 +1001 +ACAD +1010 +0.0 +1020 +0.0 +1030 +0.0 + 0 +ENDSEC + 0 +SECTION + 2 +OBJECTS + 0 +DICTIONARY + 5 +C +330 +0 +100 +AcDbDictionary +281 + 1 + 3 +ACAD_DETAILVIEWSTYLE +350 +1D4 + 3 +ACAD_GROUP +350 +D + 3 +ACAD_IMAGE_VARS +350 +1B2 + 3 +ACAD_LAYOUT +350 +1A + 3 +ACAD_MLINESTYLE +350 +17 + 3 +ACAD_PLOTSETTINGS +350 +19 + 3 +ACAD_PLOTSTYLENAME +350 +E + 3 +ACAD_SCALELIST +350 +16B + 3 +ACAD_SECTIONVIEWSTYLE +350 +1D5 + 3 +AcDbVariableDictionary +350 +1CF + 3 +APPDATA +350 +1B0 + 3 +DWGPROPS +350 +1D6 + 0 +DICTIONARY + 5 +1B3 +330 +2 +100 +AcDbDictionary +280 + 1 +281 + 1 + 3 +ACAD_LAYERSTATES +360 +1B4 + 3 +ACLYDICTIONARY +360 +1BB + 0 +DICTIONARY + 5 +1D4 +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 0 +DICTIONARY + 5 +D +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 0 +RASTERVARIABLES + 5 +1B2 +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbRasterVariables + 90 + 0 + 70 + 1 + 71 + 1 + 72 + 0 + 0 +DICTIONARY + 5 +1A +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 3 +Model +350 +1E + 3 +Sheet 1 +350 +1C + 0 +DICTIONARY + 5 +17 +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 3 +Standard +350 +18 + 0 +DICTIONARY + 5 +19 +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 0 +ACDBDICTIONARYWDFLT + 5 +E +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 3 +Normal +350 +F +100 +AcDbDictionaryWithDefault +340 +F + 0 +DICTIONARY + 5 +16B +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 3 +A0 +350 +16C + 3 +A1 +350 +16D + 3 +A2 +350 +16E + 3 +A3 +350 +16F + 3 +A4 +350 +170 + 3 +A5 +350 +171 + 3 +A6 +350 +172 + 3 +A7 +350 +173 + 3 +A8 +350 +174 + 3 +A9 +350 +175 + 3 +B0 +350 +176 + 3 +B1 +350 +177 + 3 +B2 +350 +178 + 3 +B3 +350 +179 + 3 +B4 +350 +17A + 3 +B5 +350 +17B + 3 +B6 +350 +17C + 3 +B7 +350 +17D + 3 +B8 +350 +17E + 3 +B9 +350 +17F + 3 +C0 +350 +180 + 3 +C1 +350 +181 + 3 +C2 +350 +182 + 3 +C3 +350 +183 + 3 +C4 +350 +184 + 3 +C5 +350 +185 + 3 +C6 +350 +186 + 3 +C7 +350 +187 + 3 +C8 +350 +188 + 3 +C9 +350 +189 + 3 +D0 +350 +18A + 3 +D1 +350 +18B + 3 +D2 +350 +18C + 0 +DICTIONARY + 5 +1D5 +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 0 +DICTIONARY + 5 +1CF +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 0 +DICTIONARY + 5 +1B0 +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbDictionary +281 + 1 + 0 +XRECORD + 5 +1D6 +102 +{ACAD_REACTORS +330 +C +102 +} +330 +C +100 +AcDbXrecord +280 + 1 + 1 +DWGPROPS COOKIE + 2 +vector-text + 3 + + 4 +Jonathan Greig + 6 +Generated outlines with CNCFontFab using the "Exo Bold" font. + 7 +MicroPython Text + 8 + + 9 + +300 += +301 += +302 += +303 += +304 += +305 += +306 += +307 += +308 += +309 += + 40 +0.0 + 41 +2456662.519745903 + 42 +2456662.532164352 + 1 + + 90 + 0 + 0 +DICTIONARY + 5 +1B4 +102 +{ACAD_REACTORS +330 +1B3 +102 +} +330 +1B3 +100 +AcDbDictionary +281 + 1 + 3 +ARGON_LAYERP_1 +350 +1B5 + 3 +ARGON_LAYERP_2 +350 +1B8 + 3 +ARGON_LAYERP_3 +350 +1C3 + 0 +DICTIONARY + 5 +1BB +102 +{ACAD_REACTORS +330 +1B3 +102 +} +330 +1B3 +100 +AcDbDictionary +281 + 1 +1001 +ACAD +1000 + Date: Sat, 4 Jan 2014 13:55:24 +0000 Subject: [PATCH 17/29] Improve configurability for native x64/thumb emitter. With MICROPY_EMIT_X64 and MICROPY_EMIT_THUMB disabled, the respective emitters and assemblers will not be included in the code. This can significantly reduce binary size for unix version. --- py/asmthumb.c | 5 +++++ py/asmx64.c | 6 ++++++ py/compile.c | 7 ++++++- py/emitcpy.c | 1 + py/emitnative.c | 4 ++-- unix/Makefile | 4 ++-- 6 files changed, 22 insertions(+), 5 deletions(-) diff --git a/py/asmthumb.c b/py/asmthumb.c index ee8041ac9f..ba95d80c68 100644 --- a/py/asmthumb.c +++ b/py/asmthumb.c @@ -7,6 +7,9 @@ #include "mpconfig.h" #include "asmthumb.h" +// wrapper around everything in this file +#if MICROPY_EMIT_THUMB || MICROPY_EMIT_INLINE_THUMB + #define UNSIGNED_FIT8(x) (((x) & 0xffffff00) == 0) #define UNSIGNED_FIT16(x) (((x) & 0xffff0000) == 0) #define SIGNED_FIT8(x) (((x) & 0xffffff80) == 0) || (((x) & 0xffffff80) == 0xffffff80) @@ -447,3 +450,5 @@ void asm_thumb_bl_ind(asm_thumb_t *as, void *fun_ptr, uint fun_id, uint reg_temp asm_thumb_write_op16(as, OP_SVC(fun_id)); } } + +#endif // MICROPY_EMIT_THUMB || MICROPY_EMIT_INLINE_THUMB diff --git a/py/asmx64.c b/py/asmx64.c index c425034ba0..ed9ca80f5c 100644 --- a/py/asmx64.c +++ b/py/asmx64.c @@ -6,6 +6,10 @@ #include "misc.h" #include "asmx64.h" +#include "mpconfig.h" + +// wrapper around everything in this file +#if MICROPY_EMIT_X64 #if defined(__OpenBSD__) || defined(__MACH__) #define MAP_ANONYMOUS MAP_ANON @@ -620,3 +624,5 @@ void asm_x64_call_ind(asm_x64_t* as, void *ptr, int temp_r64) { asm_x64_write_word32(as, ptr - (void*)(as->code_base + as->code_offset + 4)); */ } + +#endif // MICROPY_EMIT_X64 diff --git a/py/compile.c b/py/compile.c index 68ac20804d..8db7c6d942 100644 --- a/py/compile.c +++ b/py/compile.c @@ -3083,11 +3083,13 @@ mp_obj_t mp_compile(mp_parse_node_t pn, bool is_repl) { // compile pass 2 and 3 #if !MICROPY_EMIT_CPYTHON emit_t *emit_bc = NULL; +#if MICROPY_EMIT_NATIVE emit_t *emit_native = NULL; #endif #if MICROPY_EMIT_INLINE_THUMB emit_inline_asm_t *emit_inline_thumb = NULL; #endif +#endif // !MICROPY_EMIT_CPYTHON for (scope_t *s = comp->scope_head; s != NULL && !comp->had_error; s = s->next) { if (false) { // dummy @@ -3115,6 +3117,8 @@ mp_obj_t mp_compile(mp_parse_node_t pn, bool is_repl) { comp->emit_method_table = &emit_cpython_method_table; #else switch (s->emit_options) { + +#if MICROPY_EMIT_NATIVE case EMIT_OPT_NATIVE_PYTHON: case EMIT_OPT_VIPER: #if MICROPY_EMIT_X64 @@ -3131,6 +3135,7 @@ mp_obj_t mp_compile(mp_parse_node_t pn, bool is_repl) { comp->emit = emit_native; comp->emit_method_table->set_native_types(comp->emit, s->emit_options == EMIT_OPT_VIPER); break; +#endif // MICROPY_EMIT_NATIVE default: if (emit_bc == NULL) { @@ -3140,7 +3145,7 @@ mp_obj_t mp_compile(mp_parse_node_t pn, bool is_repl) { comp->emit_method_table = &emit_bc_method_table; break; } -#endif +#endif // !MICROPY_EMIT_CPYTHON // compile pass 2 and pass 3 compile_scope(comp, s, PASS_2); diff --git a/py/emitcpy.c b/py/emitcpy.c index 652617cc88..7b2d50fb7e 100644 --- a/py/emitcpy.c +++ b/py/emitcpy.c @@ -13,6 +13,7 @@ #include "runtime0.h" #include "emit.h" +// wrapper around everything in this file #if MICROPY_EMIT_CPYTHON struct _emit_t { diff --git a/py/emitnative.c b/py/emitnative.c index a29922d96c..cc00c57319 100644 --- a/py/emitnative.c +++ b/py/emitnative.c @@ -34,7 +34,7 @@ #include "runtime.h" // wrapper around everything in this file -#if N_X64 || N_THUMB +#if (MICROPY_EMIT_X64 && N_X64) || (MICROPY_EMIT_THUMB && N_THUMB) #if N_X64 @@ -1319,4 +1319,4 @@ const emit_method_table_t EXPORT_FUN(method_table) = { emit_native_yield_from, }; -#endif // N_X64 || N_THUMB +#endif // (MICROPY_EMIT_X64 && N_X64) || (MICROPY_EMIT_THUMB && N_THUMB) diff --git a/unix/Makefile b/unix/Makefile index 38d6ba8e15..a5c6ddcc04 100644 --- a/unix/Makefile +++ b/unix/Makefile @@ -83,10 +83,10 @@ $(BUILD)/%.o: $(PYSRC)/%.S $(BUILD)/%.o: $(PYSRC)/%.c mpconfigport.h $(CC) $(CFLAGS) -c -o $@ $< -$(BUILD)/emitnx64.o: $(PYSRC)/emitnative.c $(PYSRC)/emit.h +$(BUILD)/emitnx64.o: $(PYSRC)/emitnative.c $(PYSRC)/emit.h mpconfigport.h $(CC) $(CFLAGS) -DN_X64 -c -o $@ $< -$(BUILD)/emitnthumb.o: $(PYSRC)/emitnative.c $(PYSRC)/emit.h +$(BUILD)/emitnthumb.o: $(PYSRC)/emitnative.c $(PYSRC)/emit.h mpconfigport.h $(CC) $(CFLAGS) -DN_THUMB -c -o $@ $< # optimising vm for speed, adds only a small amount to code size but makes a huge difference to speed (20% faster) From eb7bfcb28697f6fb2d4d933bc39233aa15423a20 Mon Sep 17 00:00:00 2001 From: Damien George Date: Sat, 4 Jan 2014 15:57:35 +0000 Subject: [PATCH 18/29] Split qstr into pools, and put initial pool in ROM. Qstr's are now split into a linked-list of qstr pools. This has 2 benefits: the first pool can be in ROM (huge benefit, since we no longer use RAM for the core qstrs), and subsequent pools use m_new for the next pool instead of m_renew (thus avoiding a huge single table for all the qstrs). Still would be better to use a hash table, but this scheme takes us part of the way (eventually convert the pools to hash tables). Also fixed bug with import. Also improved the way the module code is referenced (not magic number 1 anymore). --- py/builtin.c | 25 ++++---- py/builtinimport.c | 5 +- py/compile.c | 76 ++++++++-------------- py/mpqstr.h | 13 ++++ py/mpqstrraw.h | 63 ++++++++++++++++++ py/obj.c | 13 ++-- py/objclass.c | 7 +- py/objdict.c | 3 +- py/objfun.c | 11 ++-- py/objgenerator.c | 3 +- py/objinstance.c | 3 +- py/objlist.c | 3 +- py/objstr.c | 7 +- py/qstr.c | 101 ++++++++++++++++++++++------- py/runtime.c | 155 ++++++++++++++++++--------------------------- py/runtime.h | 15 ----- py/runtime0.h | 2 +- stm/main.c | 3 +- unix/main.c | 7 ++ 19 files changed, 294 insertions(+), 221 deletions(-) create mode 100644 py/mpqstr.h create mode 100644 py/mpqstrraw.h diff --git a/py/builtin.c b/py/builtin.c index d29a2bf8c3..b565ed4640 100644 --- a/py/builtin.c +++ b/py/builtin.c @@ -8,6 +8,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" #include "runtime.h" @@ -91,7 +92,7 @@ mp_obj_t mp_builtin_bool(int n_args, const mp_obj_t *args) { switch (n_args) { case 0: return mp_const_false; case 1: if (rt_is_true(args[0])) { return mp_const_true; } else { return mp_const_false; } - default: nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "bool() takes at most 1 argument (%d given)", (void*)(machine_int_t)n_args)); + default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "bool() takes at most 1 argument (%d given)", (void*)(machine_int_t)n_args)); } } @@ -147,7 +148,7 @@ mp_obj_t mp_builtin_chr(mp_obj_t o_in) { str[1] = '\0'; return mp_obj_new_str(qstr_from_str_take(str, 2)); } else { - nlr_jump(mp_obj_new_exception_msg(rt_q_ValueError, "chr() arg not in range(0x110000)")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_ValueError, "chr() arg not in range(0x110000)")); } } @@ -165,7 +166,7 @@ mp_obj_t mp_builtin_divmod(mp_obj_t o1_in, mp_obj_t o2_in) { revs_args[0] = MP_OBJ_NEW_SMALL_INT(i1 % i2); return rt_build_tuple(2, revs_args); } else { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_TypeError, "unsupported operand type(s) for divmod(): '%s' and '%s'", mp_obj_get_type_str(o1_in), mp_obj_get_type_str(o2_in))); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_TypeError, "unsupported operand type(s) for divmod(): '%s' and '%s'", mp_obj_get_type_str(o1_in), mp_obj_get_type_str(o2_in))); } } @@ -235,7 +236,7 @@ mp_obj_t mp_builtin_len(mp_obj_t o_in) { } else if (MP_OBJ_IS_TYPE(o_in, &dict_type)) { len = mp_obj_dict_len(o_in); } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "object of type '%s' has no len()", mp_obj_get_type_str(o_in))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "object of type '%s' has no len()", mp_obj_get_type_str(o_in))); } return MP_OBJ_NEW_SMALL_INT(len); } @@ -254,7 +255,7 @@ mp_obj_t mp_builtin_list(int n_args, const mp_obj_t *args) { } return list; } - default: nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "list() takes at most 1 argument (%d given)", (void*)(machine_int_t)n_args)); + default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "list() takes at most 1 argument (%d given)", (void*)(machine_int_t)n_args)); } } @@ -270,7 +271,7 @@ mp_obj_t mp_builtin_max(int n_args, const mp_obj_t *args) { } } if (max_obj == NULL) { - nlr_jump(mp_obj_new_exception_msg(rt_q_ValueError, "max() arg is an empty sequence")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_ValueError, "max() arg is an empty sequence")); } return max_obj; } else { @@ -297,7 +298,7 @@ mp_obj_t mp_builtin_min(int n_args, const mp_obj_t *args) { } } if (min_obj == NULL) { - nlr_jump(mp_obj_new_exception_msg(rt_q_ValueError, "min() arg is an empty sequence")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_ValueError, "min() arg is an empty sequence")); } return min_obj; } else { @@ -315,7 +316,7 @@ mp_obj_t mp_builtin_min(int n_args, const mp_obj_t *args) { static mp_obj_t mp_builtin_next(mp_obj_t o) { mp_obj_t ret = rt_iternext(o); if (ret == mp_const_stop_iteration) { - nlr_jump(mp_obj_new_exception(qstr_from_str_static("StopIteration"))); + nlr_jump(mp_obj_new_exception(MP_QSTR_StopIteration)); } else { return ret; } @@ -328,7 +329,7 @@ mp_obj_t mp_builtin_ord(mp_obj_t o_in) { if (strlen(str) == 1) { return mp_obj_new_int(str[0]); } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "ord() expected a character, but string of length %d found", (void*)(machine_int_t)strlen(str))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "ord() expected a character, but string of length %d found", (void*)(machine_int_t)strlen(str))); } } @@ -336,7 +337,7 @@ mp_obj_t mp_builtin_pow(int n_args, const mp_obj_t *args) { switch (n_args) { case 2: return rt_binary_op(RT_BINARY_OP_POWER, args[0], args[1]); case 3: return rt_binary_op(RT_BINARY_OP_MODULO, rt_binary_op(RT_BINARY_OP_POWER, args[0], args[1]), args[2]); // TODO optimise... - default: nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "pow expected at most 3 arguments, got %d", (void*)(machine_int_t)n_args)); + default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "pow expected at most 3 arguments, got %d", (void*)(machine_int_t)n_args)); } } @@ -362,7 +363,7 @@ mp_obj_t mp_builtin_range(int n_args, const mp_obj_t *args) { case 1: return mp_obj_new_range(0, mp_obj_get_int(args[0]), 1); case 2: return mp_obj_new_range(mp_obj_get_int(args[0]), mp_obj_get_int(args[1]), 1); case 3: return mp_obj_new_range(mp_obj_get_int(args[0]), mp_obj_get_int(args[1]), mp_obj_get_int(args[2])); - default: nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "range expected at most 3 arguments, got %d", (void*)(machine_int_t)n_args)); + default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "range expected at most 3 arguments, got %d", (void*)(machine_int_t)n_args)); } } @@ -391,7 +392,7 @@ mp_obj_t mp_builtin_sum(int n_args, const mp_obj_t *args) { switch (n_args) { case 1: value = mp_obj_new_int(0); break; case 2: value = args[1]; break; - default: nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "sum expected at most 2 arguments, got %d", (void*)(machine_int_t)n_args)); + default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "sum expected at most 2 arguments, got %d", (void*)(machine_int_t)n_args)); } mp_obj_t iterable = rt_getiter(args[0]); mp_obj_t item; diff --git a/py/builtinimport.c b/py/builtinimport.c index 47dbf21216..90a0fc3394 100644 --- a/py/builtinimport.c +++ b/py/builtinimport.c @@ -58,7 +58,9 @@ mp_obj_t mp_builtin___import__(int n, mp_obj_t *args) { return mp_const_none; } - if (!mp_compile(pn, false)) { + mp_obj_t module_fun = mp_compile(pn, false); + + if (module_fun == mp_const_none) { // TODO handle compile error correctly rt_locals_set(old_locals); rt_globals_set(old_globals); @@ -66,7 +68,6 @@ mp_obj_t mp_builtin___import__(int n, mp_obj_t *args) { } // complied successfully, execute it - mp_obj_t module_fun = rt_make_function_from_id(1); // TODO we should return from mp_compile the unique_code_id for the module nlr_buf_t nlr; if (nlr_push(&nlr) == 0) { rt_call_function_0(module_fun); diff --git a/py/compile.c b/py/compile.c index 8db7c6d942..f8fa2cb2c2 100644 --- a/py/compile.c +++ b/py/compile.c @@ -7,6 +7,7 @@ #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "lexer.h" #include "parse.h" #include "scope.h" @@ -38,20 +39,6 @@ typedef enum { #define EMIT_OPT_ASM_THUMB (4) typedef struct _compiler_t { - qstr qstr___class__; - qstr qstr___locals__; - qstr qstr___name__; - qstr qstr___module__; - qstr qstr___qualname__; - qstr qstr___doc__; - qstr qstr_assertion_error; - qstr qstr_micropython; - qstr qstr_byte_code; - qstr qstr_native; - qstr qstr_viper; - qstr qstr_asm_thumb; - qstr qstr_range; - bool is_repl; pass_kind_t pass; bool had_error; // try to keep compiler clean from nlr @@ -202,7 +189,7 @@ static int comp_next_label(compiler_t *comp) { } static scope_t *scope_new_and_link(compiler_t *comp, scope_kind_t kind, mp_parse_node_t pn, uint emit_options) { - scope_t *scope = scope_new(kind, pn, rt_get_unique_code_id(kind == SCOPE_MODULE), emit_options); + scope_t *scope = scope_new(kind, pn, rt_get_unique_code_id(), emit_options); scope->parent = comp->scope_cur; scope->next = NULL; if (comp->scope_head == NULL) { @@ -903,7 +890,7 @@ qstr compile_classdef_helper(compiler_t *comp, mp_parse_node_struct_t *pns, uint // returns true if it was a built-in decorator (even if the built-in had an error) static bool compile_built_in_decorator(compiler_t *comp, int name_len, mp_parse_node_t *name_nodes, uint *emit_options) { - if (MP_PARSE_NODE_LEAF_ARG(name_nodes[0]) != comp->qstr_micropython) { + if (MP_PARSE_NODE_LEAF_ARG(name_nodes[0]) != MP_QSTR_micropython) { return false; } @@ -913,16 +900,16 @@ static bool compile_built_in_decorator(compiler_t *comp, int name_len, mp_parse_ } qstr attr = MP_PARSE_NODE_LEAF_ARG(name_nodes[1]); - if (attr == comp->qstr_byte_code) { + if (attr == MP_QSTR_byte_code) { *emit_options = EMIT_OPT_BYTE_CODE; #if MICROPY_EMIT_NATIVE - } else if (attr == comp->qstr_native) { + } else if (attr == MP_QSTR_native) { *emit_options = EMIT_OPT_NATIVE_PYTHON; - } else if (attr == comp->qstr_viper) { + } else if (attr == MP_QSTR_viper) { *emit_options = EMIT_OPT_VIPER; #endif #if MICROPY_EMIT_INLINE_THUMB - } else if (attr == comp->qstr_asm_thumb) { + } else if (attr == MP_QSTR_asm_thumb) { *emit_options = EMIT_OPT_ASM_THUMB; #endif } else { @@ -1329,7 +1316,7 @@ void compile_nonlocal_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { void compile_assert_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { int l_end = comp_next_label(comp); c_if_cond(comp, pns->nodes[0], true, l_end); - EMIT(load_id, comp->qstr_assertion_error); + EMIT(load_id, MP_QSTR_assertion_error); if (!MP_PARSE_NODE_IS_NULL(pns->nodes[1])) { // assertion message compile_node(comp, pns->nodes[1]); @@ -1495,7 +1482,7 @@ void compile_for_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { // for viper it will be much, much faster if (/*comp->scope_cur->emit_options == EMIT_OPT_VIPER &&*/ MP_PARSE_NODE_IS_ID(pns->nodes[0]) && MP_PARSE_NODE_IS_STRUCT_KIND(pns->nodes[1], PN_power)) { mp_parse_node_struct_t *pns_it = (mp_parse_node_struct_t*)pns->nodes[1]; - if (MP_PARSE_NODE_IS_ID(pns_it->nodes[0]) && MP_PARSE_NODE_LEAF_ARG(pns_it->nodes[0]) == comp->qstr_range && MP_PARSE_NODE_IS_STRUCT_KIND(pns_it->nodes[1], PN_trailer_paren) && MP_PARSE_NODE_IS_NULL(pns_it->nodes[2])) { + if (MP_PARSE_NODE_IS_ID(pns_it->nodes[0]) && MP_PARSE_NODE_LEAF_ARG(pns_it->nodes[0]) == MP_QSTR_range && MP_PARSE_NODE_IS_STRUCT_KIND(pns_it->nodes[1], PN_trailer_paren) && MP_PARSE_NODE_IS_NULL(pns_it->nodes[2])) { mp_parse_node_t pn_range_args = ((mp_parse_node_struct_t*)pns_it->nodes[1])->nodes[0]; mp_parse_node_t *args; int n_args = list_get(&pn_range_args, PN_arglist, &args); @@ -1743,7 +1730,7 @@ void compile_expr_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { if (MP_PARSE_NODE_IS_NULL(pns->nodes[1])) { if (comp->is_repl && comp->scope_cur->kind == SCOPE_MODULE) { // for REPL, evaluate then print the expression - EMIT(load_id, qstr_from_str_static("__repl_print__")); + EMIT(load_id, MP_QSTR___repl_print__); compile_node(comp, pns->nodes[0]); EMIT(call_function, 1, 0, false, false); EMIT(pop_top); @@ -2683,7 +2670,7 @@ void check_for_doc_string(compiler_t *comp, mp_parse_node_t pn) { if (kind == MP_PARSE_NODE_STRING) { compile_node(comp, pns->nodes[0]); // a doc string // store doc string - EMIT(store_id, comp->qstr___doc__); + EMIT(store_id, MP_QSTR___doc__); } } } @@ -2796,35 +2783,35 @@ void compile_scope(compiler_t *comp, scope_t *scope, pass_kind_t pass) { if (comp->pass == PASS_1) { bool added; - id_info_t *id_info = scope_find_or_add_id(scope, comp->qstr___class__, &added); + id_info_t *id_info = scope_find_or_add_id(scope, MP_QSTR___class__, &added); assert(added); id_info->kind = ID_INFO_KIND_LOCAL; - id_info = scope_find_or_add_id(scope, comp->qstr___locals__, &added); + id_info = scope_find_or_add_id(scope, MP_QSTR___locals__, &added); assert(added); id_info->kind = ID_INFO_KIND_LOCAL; id_info->param = true; scope->num_params = 1; // __locals__ is the parameter } - EMIT(load_id, comp->qstr___locals__); + EMIT(load_id, MP_QSTR___locals__); EMIT(store_locals); - EMIT(load_id, comp->qstr___name__); - EMIT(store_id, comp->qstr___module__); + EMIT(load_id, MP_QSTR___name__); + EMIT(store_id, MP_QSTR___module__); EMIT(load_const_id, MP_PARSE_NODE_LEAF_ARG(pns->nodes[0])); // 0 is class name - EMIT(store_id, comp->qstr___qualname__); + EMIT(store_id, MP_QSTR___qualname__); check_for_doc_string(comp, pns->nodes[2]); compile_node(comp, pns->nodes[2]); // 2 is class body - id_info_t *id = scope_find(scope, comp->qstr___class__); + id_info_t *id = scope_find(scope, MP_QSTR___class__); assert(id != NULL); if (id->kind == ID_INFO_KIND_LOCAL) { EMIT(load_const_tok, MP_TOKEN_KW_NONE); } else { #if MICROPY_EMIT_CPYTHON - EMIT(load_closure, comp->qstr___class__, 0); // XXX check this is the correct local num + EMIT(load_closure, MP_QSTR___class__, 0); // XXX check this is the correct local num #else - EMIT(load_fast, comp->qstr___class__, 0); // XXX check this is the correct local num + EMIT(load_fast, MP_QSTR___class__, 0); // XXX check this is the correct local num #endif } EMIT(return_value); @@ -2917,7 +2904,7 @@ void compile_scope_compute_things(compiler_t *comp, scope_t *scope) { scope->num_locals = 0; for (int i = 0; i < scope->id_info_len; i++) { id_info_t *id = &scope->id_info[i]; - if (scope->kind == SCOPE_CLASS && id->qstr == comp->qstr___class__) { + if (scope->kind == SCOPE_CLASS && id->qstr == MP_QSTR___class__) { // __class__ is not counted as a local; if it's used then it becomes a ID_INFO_KIND_CELL continue; } @@ -3021,20 +3008,6 @@ void compile_scope_compute_things(compiler_t *comp, scope_t *scope) { mp_obj_t mp_compile(mp_parse_node_t pn, bool is_repl) { compiler_t *comp = m_new(compiler_t, 1); - comp->qstr___class__ = qstr_from_str_static("__class__"); - comp->qstr___locals__ = qstr_from_str_static("__locals__"); - comp->qstr___name__ = qstr_from_str_static("__name__"); - comp->qstr___module__ = qstr_from_str_static("__module__"); - comp->qstr___qualname__ = qstr_from_str_static("__qualname__"); - comp->qstr___doc__ = qstr_from_str_static("__doc__"); - comp->qstr_assertion_error = qstr_from_str_static("AssertionError"); - comp->qstr_micropython = qstr_from_str_static("micropython"); - comp->qstr_byte_code = qstr_from_str_static("byte_code"); - comp->qstr_native = qstr_from_str_static("native"); - comp->qstr_viper = qstr_from_str_static("viper"); - comp->qstr_asm_thumb = qstr_from_str_static("asm_thumb"); - comp->qstr_range = qstr_from_str_static("range"); - comp->is_repl = is_repl; comp->had_error = false; @@ -3048,10 +3021,10 @@ mp_obj_t mp_compile(mp_parse_node_t pn, bool is_repl) { pn = fold_constants(pn); // set the outer scope - scope_new_and_link(comp, SCOPE_MODULE, pn, EMIT_OPT_NONE); + scope_t *module_scope = scope_new_and_link(comp, SCOPE_MODULE, pn, EMIT_OPT_NONE); // compile pass 1 - comp->emit = emit_pass1_new(comp->qstr___class__); + comp->emit = emit_pass1_new(MP_QSTR___class__); comp->emit_method_table = &emit_pass1_method_table; comp->emit_inline_asm = NULL; comp->emit_inline_asm_method_table = NULL; @@ -3162,10 +3135,11 @@ mp_obj_t mp_compile(mp_parse_node_t pn, bool is_repl) { } else { #if MICROPY_EMIT_CPYTHON // can't create code, so just return true + (void)module_scope; // to suppress warning that module_scope is unused return mp_const_true; #else // return function that executes the outer module - return rt_make_function_from_id(1); + return rt_make_function_from_id(module_scope->unique_code_id); #endif } } diff --git a/py/mpqstr.h b/py/mpqstr.h new file mode 100644 index 0000000000..1440fb3b80 --- /dev/null +++ b/py/mpqstr.h @@ -0,0 +1,13 @@ +// See mpqstrraw.h for a list of qstr's that are available as constants. +// Reference them as MP_QSTR_xxxx. +// +// Note: it would be possible to define MP_QSTR_xxx as qstr_from_str_static("xxx") +// for qstrs that are referenced this way, but you don't want to have them in ROM. + +enum { + MP_QSTR_nil = 0, +#define Q(id) MP_QSTR_##id, +#include "mpqstrraw.h" +#undef Q + MP_QSTR_number_of, +} category_t; diff --git a/py/mpqstrraw.h b/py/mpqstrraw.h new file mode 100644 index 0000000000..85cf1ff7bd --- /dev/null +++ b/py/mpqstrraw.h @@ -0,0 +1,63 @@ +// All the qstr definitions in this file are available as constants. +// That is, they are in ROM and you can reference them simple as MP_QSTR_xxxx. + +Q(__build_class__) +Q(__class__) +Q(__doc__) +Q(__init__) +Q(__locals__) +Q(__main__) +Q(__module__) +Q(__name__) +Q(__next__) +Q(__qualname__) +Q(__repl_print__) + +Q(assertion_error) +Q(micropython) +Q(byte_code) +Q(native) +Q(viper) +Q(asm_thumb) + +Q(StopIteration) + +Q(AttributeError) +Q(IndexError) +Q(KeyError) +Q(NameError) +Q(TypeError) +Q(SyntaxError) +Q(ValueError) + +Q(abs) +Q(all) +Q(any) +Q(bool) +Q(callable) +Q(chr) +Q(complex) +Q(dict) +Q(divmod) +Q(float) +Q(hash) +Q(int) +Q(iter) +Q(len) +Q(list) +Q(max) +Q(min) +Q(next) +Q(ord) +Q(pow) +Q(print) +Q(range) +Q(set) +Q(sum) +Q(type) + +Q(append) +Q(pop) +Q(sort) +Q(join) +Q(format) diff --git a/py/obj.c b/py/obj.c index d88d0ac3d7..2b834ffe43 100644 --- a/py/obj.c +++ b/py/obj.c @@ -7,6 +7,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" #include "runtime.h" @@ -144,7 +145,7 @@ machine_float_t mp_obj_get_float(mp_obj_t arg) { } else if (MP_OBJ_IS_TYPE(arg, &float_type)) { return mp_obj_float_get(arg); } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "can't convert %s to float", mp_obj_get_type_str(arg))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "can't convert %s to float", mp_obj_get_type_str(arg))); } } @@ -164,7 +165,7 @@ void mp_obj_get_complex(mp_obj_t arg, mp_float_t *real, mp_float_t *imag) { } else if (MP_OBJ_IS_TYPE(arg, &complex_type)) { mp_obj_complex_get(arg, real, imag); } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "can't convert %s to complex", mp_obj_get_type_str(arg))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "can't convert %s to complex", mp_obj_get_type_str(arg))); } } #endif @@ -188,11 +189,11 @@ mp_obj_t *mp_obj_get_array_fixed_n(mp_obj_t o_in, machine_int_t n) { mp_obj_list_get(o_in, &seq_len, &seq_items); } if (seq_len != n) { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_IndexError, "requested length %d but object has length %d", (void*)n, (void*)(machine_uint_t)seq_len)); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_IndexError, "requested length %d but object has length %d", (void*)n, (void*)(machine_uint_t)seq_len)); } return seq_items; } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "object '%s' is not a tuple or list", mp_obj_get_type_str(o_in))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "object '%s' is not a tuple or list", mp_obj_get_type_str(o_in))); } } @@ -204,10 +205,10 @@ uint mp_get_index(const mp_obj_type_t *type, machine_uint_t len, mp_obj_t index) i += len; } if (i < 0 || i >= len) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_IndexError, "%s index out of range", type->name)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_IndexError, "%s index out of range", type->name)); } return i; } else { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_TypeError, "%s indices must be integers, not %s", type->name, mp_obj_get_type_str(index))); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_TypeError, "%s indices must be integers, not %s", type->name, mp_obj_get_type_str(index))); } } diff --git a/py/objclass.c b/py/objclass.c index 203923a722..f223c5ff25 100644 --- a/py/objclass.c +++ b/py/objclass.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime.h" #include "map.h" @@ -25,7 +26,7 @@ mp_obj_t class_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { mp_obj_t o = mp_obj_new_instance(self_in); // look for __init__ function - mp_map_elem_t *init_fn = mp_qstr_map_lookup(self->locals, qstr_from_str_static("__init__"), false); + mp_map_elem_t *init_fn = mp_qstr_map_lookup(self->locals, MP_QSTR___init__, false); if (init_fn != NULL) { // call __init__ function @@ -40,13 +41,13 @@ mp_obj_t class_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { m_del(mp_obj_t, args2, n_args + 1); } if (init_ret != mp_const_none) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "__init__() should return None, not '%s'", mp_obj_get_type_str(init_ret))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "__init__() should return None, not '%s'", mp_obj_get_type_str(init_ret))); } } else { // TODO if (n_args != 0) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "function takes 0 positional arguments but %d were given", (void*)(machine_int_t)n_args)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "function takes 0 positional arguments but %d were given", (void*)(machine_int_t)n_args)); } } diff --git a/py/objdict.c b/py/objdict.c index 50ce279040..acf1a9f801 100644 --- a/py/objdict.c +++ b/py/objdict.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" #include "runtime.h" @@ -42,7 +43,7 @@ mp_obj_t dict_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { // dict load mp_map_elem_t *elem = mp_map_lookup_helper(&o->map, rhs_in, false); if (elem == NULL) { - nlr_jump(mp_obj_new_exception_msg(rt_q_KeyError, "")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_KeyError, "")); } else { return elem->value; } diff --git a/py/objfun.c b/py/objfun.c index e998bd28d2..c4783867a5 100644 --- a/py/objfun.c +++ b/py/objfun.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "map.h" #include "runtime.h" @@ -24,7 +25,7 @@ mp_obj_t fun_native_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { // check number of arguments if (n_args != self->n_args_min) { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)self->n_args_min, (const char*)(machine_int_t)n_args)); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)self->n_args_min, (const char*)(machine_int_t)n_args)); } // dispatch function call @@ -47,9 +48,9 @@ mp_obj_t fun_native_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { // function takes a variable number of arguments if (n_args < self->n_args_min) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "() missing %d required positional arguments: ", (const char*)(machine_int_t)(self->n_args_min - n_args))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "() missing %d required positional arguments: ", (const char*)(machine_int_t)(self->n_args_min - n_args))); } else if (n_args > self->n_args_max) { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_TypeError, " expected at most %d arguments, got %d", (void*)(machine_int_t)self->n_args_max, (void*)(machine_int_t)n_args)); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_TypeError, " expected at most %d arguments, got %d", (void*)(machine_int_t)self->n_args_max, (void*)(machine_int_t)n_args)); } // TODO really the args need to be passed in as a Python tuple, as the form f(*[1,2]) can be used to pass var args @@ -141,7 +142,7 @@ mp_obj_t fun_bc_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { mp_obj_fun_bc_t *self = self_in; if (n_args != self->n_args) { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)self->n_args, (const char*)(machine_int_t)n_args)); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)self->n_args, (const char*)(machine_int_t)n_args)); } // optimisation: allow the compiler to optimise this tail call for @@ -250,7 +251,7 @@ mp_obj_t fun_asm_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { mp_obj_fun_asm_t *self = self_in; if (n_args != self->n_args) { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)self->n_args, (const char*)(machine_int_t)n_args)); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)self->n_args, (const char*)(machine_int_t)n_args)); } machine_uint_t ret; diff --git a/py/objgenerator.c b/py/objgenerator.c index ecdd72dc6d..849212269b 100644 --- a/py/objgenerator.c +++ b/py/objgenerator.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime.h" #include "bc.h" @@ -29,7 +30,7 @@ mp_obj_t gen_wrap_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { const byte *bc_code; mp_obj_fun_bc_get(self_fun, &bc_n_args, &bc_n_state, &bc_code); if (n_args != bc_n_args) { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)bc_n_args, (const char*)(machine_int_t)n_args)); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_TypeError, "function takes %d positional arguments but %d were given", (const char*)(machine_int_t)bc_n_args, (const char*)(machine_int_t)n_args)); } return mp_obj_new_gen_instance(bc_code, self->n_state, n_args, args); diff --git a/py/objinstance.c b/py/objinstance.c index e5d23af2d5..6cfcdf6c15 100644 --- a/py/objinstance.c +++ b/py/objinstance.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime.h" #include "map.h" @@ -44,7 +45,7 @@ mp_obj_t mp_obj_instance_load_attr(mp_obj_t self_in, qstr attr) { return elem->value; } } - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_AttributeError, "'%s' object has no attribute '%s'", mp_obj_get_type_str(self_in), qstr_str(attr))); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_AttributeError, "'%s' object has no attribute '%s'", mp_obj_get_type_str(self_in), qstr_str(attr))); } void mp_obj_instance_load_method(mp_obj_t self_in, qstr attr, mp_obj_t *dest) { diff --git a/py/objlist.c b/py/objlist.c index e371057981..30d3a41e4a 100644 --- a/py/objlist.c +++ b/py/objlist.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" #include "runtime.h" @@ -81,7 +82,7 @@ static mp_obj_t list_pop(int n_args, const mp_obj_t *args) { assert(MP_OBJ_IS_TYPE(args[0], &list_type)); mp_obj_list_t *self = args[0]; if (self->len == 0) { - nlr_jump(mp_obj_new_exception_msg(rt_q_IndexError, "pop from empty list")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_IndexError, "pop from empty list")); } uint index = mp_get_index(self->base.type, self->len, n_args == 1 ? mp_obj_new_int(-1) : args[1]); mp_obj_t ret = self->items[index]; diff --git a/py/objstr.c b/py/objstr.c index 54e6f37705..03a761863f 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -7,6 +7,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" #include "runtime.h" @@ -61,7 +62,7 @@ mp_obj_t str_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { } else { // Message doesn't match CPython, but we don't have so much bytes as they // to spend them on verbose wording - nlr_jump(mp_obj_new_exception_msg(rt_q_TypeError, "index must be int")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_TypeError, "index must be int")); } case RT_BINARY_OP_ADD: @@ -134,7 +135,7 @@ mp_obj_t str_join(mp_obj_t self_in, mp_obj_t arg) { return mp_obj_new_str(qstr_from_str_take(joined_str, required_len + 1)); bad_arg: - nlr_jump(mp_obj_new_exception_msg(rt_q_TypeError, "?str.join expecting a list of str's")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_TypeError, "?str.join expecting a list of str's")); } void vstr_printf_wrapper(void *env, const char *fmt, ...) { @@ -158,7 +159,7 @@ mp_obj_t str_format(int n_args, const mp_obj_t *args) { vstr_add_char(vstr, '{'); } else if (*str == '}') { if (arg_i >= n_args) { - nlr_jump(mp_obj_new_exception_msg(rt_q_IndexError, "tuple index out of range")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_IndexError, "tuple index out of range")); } mp_obj_print_helper(vstr_printf_wrapper, vstr, args[arg_i]); arg_i++; diff --git a/py/qstr.c b/py/qstr.c index 0dd8a04b70..0ed7aa9a24 100644 --- a/py/qstr.c +++ b/py/qstr.c @@ -2,55 +2,110 @@ #include #include "misc.h" +#include "mpqstr.h" -static int qstrs_alloc; -static int qstrs_len; -static const char **qstrs; +// NOTE: we are using linear arrays to store and search for qstr's (unique strings, interned strings) +// ultimately we will replace this with a static hash table of some kind +// also probably need to include the length in the string data, to allow null bytes in the string + +#if 0 // print debugging info +#include +#define DEBUG_printf(args...) printf(args) +#else // don't print debugging info +#define DEBUG_printf(args...) (void)0 +#endif + +typedef struct _qstr_pool_t { + struct _qstr_pool_t *prev; + uint total_prev_len; + uint alloc; + uint len; + const char *qstrs[]; +} qstr_pool_t; + +const static qstr_pool_t const_pool = { + NULL, // no previous pool + 0, // no previous pool + 10, // set so that the first dynamically allocated pool is twice this size; must be <= the len (just below) + MP_QSTR_number_of, // corresponds to number of strings in array just below + { + "nil", // must be first, since 0 qstr is nil +#define Q(id) #id, +#include "mpqstrraw.h" +#undef Q + }, +}; + +static qstr_pool_t *last_pool = (qstr_pool_t*)&const_pool; // we won't modify the const_pool since it has no allocated room left void qstr_init(void) { - qstrs_alloc = 400; - qstrs_len = 1; - qstrs = m_new(const char*, qstrs_alloc); - qstrs[0] = "nil"; + // nothing to do! } static qstr qstr_add(const char *str) { - if (qstrs_len >= qstrs_alloc) { - qstrs = m_renew(const char*, qstrs, qstrs_alloc, qstrs_alloc * 2); - qstrs_alloc *= 2; + DEBUG_printf("QSTR: add %s\n", str); + + // make sure we have room in the pool for a new qstr + if (last_pool->len >= last_pool->alloc) { + qstr_pool_t *pool = m_new_obj_var(qstr_pool_t, const char*, last_pool->alloc * 2); + pool->prev = last_pool; + pool->total_prev_len = last_pool->total_prev_len + last_pool->len; + pool->alloc = last_pool->alloc * 2; + pool->len = 0; + last_pool = pool; + DEBUG_printf("QSTR: allocate new pool of size %d\n", last_pool->alloc); } - qstrs[qstrs_len++] = str; - return qstrs_len - 1; + + // add the new qstr + last_pool->qstrs[last_pool->len++] = str; + + // return id for the newly-added qstr + return last_pool->total_prev_len + last_pool->len - 1; } qstr qstr_from_str_static(const char *str) { - for (int i = 0; i < qstrs_len; i++) { - if (strcmp(qstrs[i], str) == 0) { - return i; + for (qstr_pool_t *pool = last_pool; pool != NULL; pool = pool->prev) { + for (const char **qstr = pool->qstrs, **qstr_top = pool->qstrs + pool->len; qstr < qstr_top; qstr++) { + if (strcmp(*qstr, str) == 0) { + return pool->total_prev_len + (qstr - pool->qstrs); + } } } return qstr_add(str); } qstr qstr_from_str_take(char *str, int alloc_len) { - for (int i = 0; i < qstrs_len; i++) { - if (strcmp(qstrs[i], str) == 0) { - m_del(char, str, alloc_len); - return i; + for (qstr_pool_t *pool = last_pool; pool != NULL; pool = pool->prev) { + for (const char **qstr = pool->qstrs, **qstr_top = pool->qstrs + pool->len; qstr < qstr_top; qstr++) { + if (strcmp(*qstr, str) == 0) { + m_del(char, str, alloc_len); + return pool->total_prev_len + (qstr - pool->qstrs); + } } } return qstr_add(str); } qstr qstr_from_strn_copy(const char *str, int len) { - for (int i = 0; i < qstrs_len; i++) { - if (strncmp(qstrs[i], str, len) == 0 && qstrs[i][len] == '\0') { - return i; + for (qstr_pool_t *pool = last_pool; pool != NULL; pool = pool->prev) { + for (const char **qstr = pool->qstrs, **qstr_top = pool->qstrs + pool->len; qstr < qstr_top; qstr++) { + if (strncmp(*qstr, str, len) == 0 && (*qstr)[len] == '\0') { + return pool->total_prev_len + (qstr - pool->qstrs); + } } } return qstr_add(strndup(str, len)); } +// convert qstr id to pointer to its string const char *qstr_str(qstr qstr) { - return qstrs[qstr]; + // search + for (qstr_pool_t *pool = last_pool; pool != NULL; pool = pool->prev) { + if (qstr >= pool->total_prev_len) { + return pool->qstrs[qstr - pool->total_prev_len]; + } + } + + // not found, return nil + return const_pool.qstrs[0]; } diff --git a/py/runtime.c b/py/runtime.c index 3144321f3a..a1f9ee3b7b 100644 --- a/py/runtime.c +++ b/py/runtime.c @@ -11,6 +11,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" #include "runtime.h" @@ -27,22 +28,6 @@ #define DEBUG_OP_printf(args...) (void)0 #endif -// TODO make these predefined so they don't take up RAM -qstr rt_q_append; -qstr rt_q_pop; -qstr rt_q_sort; -qstr rt_q_join; -qstr rt_q_format; -qstr rt_q___build_class__; -qstr rt_q___next__; -qstr rt_q_AttributeError; -qstr rt_q_IndexError; -qstr rt_q_KeyError; -qstr rt_q_NameError; -qstr rt_q_TypeError; -qstr rt_q_SyntaxError; -qstr rt_q_ValueError; - // locals and globals need to be pointers because they can be the same in outer module scope static mp_map_t *map_locals; static mp_map_t *map_globals; @@ -83,74 +68,58 @@ FILE *fp_write_code = NULL; #endif void rt_init(void) { - rt_q_append = qstr_from_str_static("append"); - rt_q_pop = qstr_from_str_static("pop"); - rt_q_sort = qstr_from_str_static("sort"); - rt_q_join = qstr_from_str_static("join"); - rt_q_format = qstr_from_str_static("format"); - rt_q___build_class__ = qstr_from_str_static("__build_class__"); - rt_q___next__ = qstr_from_str_static("__next__"); - rt_q_AttributeError = qstr_from_str_static("AttributeError"); - rt_q_IndexError = qstr_from_str_static("IndexError"); - rt_q_KeyError = qstr_from_str_static("KeyError"); - rt_q_NameError = qstr_from_str_static("NameError"); - rt_q_TypeError = qstr_from_str_static("TypeError"); - rt_q_SyntaxError = qstr_from_str_static("SyntaxError"); - rt_q_ValueError = qstr_from_str_static("ValueError"); - // locals = globals for outer module (see Objects/frameobject.c/PyFrame_New()) map_locals = map_globals = mp_map_new(MP_MAP_QSTR, 1); - mp_qstr_map_lookup(map_globals, qstr_from_str_static("__name__"), true)->value = mp_obj_new_str(qstr_from_str_static("__main__")); + mp_qstr_map_lookup(map_globals, MP_QSTR___name__, true)->value = mp_obj_new_str(MP_QSTR___main__); // init built-in hash table mp_map_init(&map_builtins, MP_MAP_QSTR, 3); // built-in exceptions (TODO, make these proper classes) - mp_qstr_map_lookup(&map_builtins, rt_q_AttributeError, true)->value = mp_obj_new_exception(rt_q_AttributeError); - mp_qstr_map_lookup(&map_builtins, rt_q_IndexError, true)->value = mp_obj_new_exception(rt_q_IndexError); - mp_qstr_map_lookup(&map_builtins, rt_q_KeyError, true)->value = mp_obj_new_exception(rt_q_KeyError); - mp_qstr_map_lookup(&map_builtins, rt_q_NameError, true)->value = mp_obj_new_exception(rt_q_NameError); - mp_qstr_map_lookup(&map_builtins, rt_q_TypeError, true)->value = mp_obj_new_exception(rt_q_TypeError); - mp_qstr_map_lookup(&map_builtins, rt_q_SyntaxError, true)->value = mp_obj_new_exception(rt_q_SyntaxError); - mp_qstr_map_lookup(&map_builtins, rt_q_ValueError, true)->value = mp_obj_new_exception(rt_q_ValueError); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_AttributeError, true)->value = mp_obj_new_exception(MP_QSTR_AttributeError); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_IndexError, true)->value = mp_obj_new_exception(MP_QSTR_IndexError); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_KeyError, true)->value = mp_obj_new_exception(MP_QSTR_KeyError); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_NameError, true)->value = mp_obj_new_exception(MP_QSTR_NameError); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_TypeError, true)->value = mp_obj_new_exception(MP_QSTR_TypeError); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_SyntaxError, true)->value = mp_obj_new_exception(MP_QSTR_SyntaxError); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_ValueError, true)->value = mp_obj_new_exception(MP_QSTR_ValueError); // built-in core functions - mp_qstr_map_lookup(&map_builtins, rt_q___build_class__, true)->value = rt_make_function_2(mp_builtin___build_class__); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("__repl_print__"), true)->value = rt_make_function_1(mp_builtin___repl_print__); + mp_qstr_map_lookup(&map_builtins, MP_QSTR___build_class__, true)->value = rt_make_function_2(mp_builtin___build_class__); + mp_qstr_map_lookup(&map_builtins, MP_QSTR___repl_print__, true)->value = rt_make_function_1(mp_builtin___repl_print__); // built-in user functions - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("abs"), true)->value = rt_make_function_1(mp_builtin_abs); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("all"), true)->value = rt_make_function_1(mp_builtin_all); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("any"), true)->value = rt_make_function_1(mp_builtin_any); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("bool"), true)->value = rt_make_function_var(0, mp_builtin_bool); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("callable"), true)->value = rt_make_function_1(mp_builtin_callable); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("chr"), true)->value = rt_make_function_1(mp_builtin_chr); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_abs, true)->value = rt_make_function_1(mp_builtin_abs); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_all, true)->value = rt_make_function_1(mp_builtin_all); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_any, true)->value = rt_make_function_1(mp_builtin_any); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_bool, true)->value = rt_make_function_var(0, mp_builtin_bool); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_callable, true)->value = rt_make_function_1(mp_builtin_callable); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_chr, true)->value = rt_make_function_1(mp_builtin_chr); #if MICROPY_ENABLE_FLOAT - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("complex"), true)->value = (mp_obj_t)&mp_builtin_complex_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_complex, true)->value = (mp_obj_t)&mp_builtin_complex_obj; #endif - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("dict"), true)->value = rt_make_function_0(mp_builtin_dict); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("divmod"), true)->value = rt_make_function_2(mp_builtin_divmod); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_dict, true)->value = rt_make_function_0(mp_builtin_dict); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_divmod, true)->value = rt_make_function_2(mp_builtin_divmod); #if MICROPY_ENABLE_FLOAT - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("float"), true)->value = (mp_obj_t)&mp_builtin_float_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_float, true)->value = (mp_obj_t)&mp_builtin_float_obj; #endif - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("hash"), true)->value = (mp_obj_t)&mp_builtin_hash_obj; - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("int"), true)->value = (mp_obj_t)&mp_builtin_int_obj; - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("iter"), true)->value = (mp_obj_t)&mp_builtin_iter_obj; - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("len"), true)->value = rt_make_function_1(mp_builtin_len); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("list"), true)->value = rt_make_function_var(0, mp_builtin_list); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("max"), true)->value = rt_make_function_var(1, mp_builtin_max); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("min"), true)->value = rt_make_function_var(1, mp_builtin_min); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("next"), true)->value = (mp_obj_t)&mp_builtin_next_obj; - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("ord"), true)->value = rt_make_function_1(mp_builtin_ord); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("pow"), true)->value = rt_make_function_var(2, mp_builtin_pow); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("print"), true)->value = rt_make_function_var(0, mp_builtin_print); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("range"), true)->value = rt_make_function_var(1, mp_builtin_range); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("set"), true)->value = (mp_obj_t)&mp_builtin_set_obj; - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("sum"), true)->value = rt_make_function_var(1, mp_builtin_sum); - mp_qstr_map_lookup(&map_builtins, qstr_from_str_static("type"), true)->value = (mp_obj_t)&mp_builtin_type_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_hash, true)->value = (mp_obj_t)&mp_builtin_hash_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_int, true)->value = (mp_obj_t)&mp_builtin_int_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_iter, true)->value = (mp_obj_t)&mp_builtin_iter_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_len, true)->value = rt_make_function_1(mp_builtin_len); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_list, true)->value = rt_make_function_var(0, mp_builtin_list); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_max, true)->value = rt_make_function_var(1, mp_builtin_max); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_min, true)->value = rt_make_function_var(1, mp_builtin_min); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_next, true)->value = (mp_obj_t)&mp_builtin_next_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_ord, true)->value = rt_make_function_1(mp_builtin_ord); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_pow, true)->value = rt_make_function_var(2, mp_builtin_pow); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_print, true)->value = rt_make_function_var(0, mp_builtin_print); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_range, true)->value = rt_make_function_var(1, mp_builtin_range); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_set, true)->value = (mp_obj_t)&mp_builtin_set_obj; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_sum, true)->value = rt_make_function_var(1, mp_builtin_sum); + mp_qstr_map_lookup(&map_builtins, MP_QSTR_type, true)->value = (mp_obj_t)&mp_builtin_type_obj; - - next_unique_code_id = 2; // 1 is reserved for the __main__ module scope + next_unique_code_id = 1; // 0 indicates "no code" unique_codes = NULL; #ifdef WRITE_CODE @@ -166,12 +135,8 @@ void rt_deinit(void) { #endif } -int rt_get_unique_code_id(bool is_main_module) { - if (is_main_module) { - return 1; - } else { - return next_unique_code_id++; - } +int rt_get_unique_code_id(void) { + return next_unique_code_id++; } static void alloc_unique_codes(void) { @@ -186,7 +151,7 @@ static void alloc_unique_codes(void) { void rt_assign_byte_code(int unique_code_id, byte *code, uint len, int n_args, int n_locals, int n_stack, bool is_generator) { alloc_unique_codes(); - assert(unique_code_id < next_unique_code_id); + assert(1 <= unique_code_id && unique_code_id < next_unique_code_id); unique_codes[unique_code_id].kind = MP_CODE_BYTE; unique_codes[unique_code_id].n_args = n_args; unique_codes[unique_code_id].n_locals = n_locals; @@ -355,7 +320,7 @@ mp_obj_t rt_load_const_dec(qstr qstr) { } } if (*s != 0) { - nlr_jump(mp_obj_new_exception_msg(rt_q_SyntaxError, "invalid syntax for number")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_SyntaxError, "invalid syntax for number")); } if (exp_neg) { exp_val = -exp_val; @@ -373,7 +338,7 @@ mp_obj_t rt_load_const_dec(qstr qstr) { return mp_obj_new_float(dec_val); } #else - nlr_jump(mp_obj_new_exception_msg(rt_q_SyntaxError, "decimal numbers not supported")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_SyntaxError, "decimal numbers not supported")); #endif } @@ -391,7 +356,7 @@ mp_obj_t rt_load_name(qstr qstr) { if (elem == NULL) { elem = mp_qstr_map_lookup(&map_builtins, qstr, false); if (elem == NULL) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_NameError, "name '%s' is not defined", qstr_str(qstr))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_NameError, "name '%s' is not defined", qstr_str(qstr))); } } } @@ -405,7 +370,7 @@ mp_obj_t rt_load_global(qstr qstr) { if (elem == NULL) { elem = mp_qstr_map_lookup(&map_builtins, qstr, false); if (elem == NULL) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_NameError, "name '%s' is not defined", qstr_str(qstr))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_NameError, "name '%s' is not defined", qstr_str(qstr))); } } return elem->value; @@ -413,9 +378,9 @@ mp_obj_t rt_load_global(qstr qstr) { mp_obj_t rt_load_build_class(void) { DEBUG_OP_printf("load_build_class\n"); - mp_map_elem_t *elem = mp_qstr_map_lookup(&map_builtins, rt_q___build_class__, false); + mp_map_elem_t *elem = mp_qstr_map_lookup(&map_builtins, MP_QSTR___build_class__, false); if (elem == NULL) { - nlr_jump(mp_obj_new_exception_msg(rt_q_NameError, "name '__build_class__' is not defined")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_NameError, "name '__build_class__' is not defined")); } return elem->value; } @@ -465,7 +430,7 @@ mp_obj_t rt_unary_op(int op, mp_obj_t arg) { } } // TODO specify in error message what the operator is - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "bad operand type for unary operator: '%s'", o->type->name)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "bad operand type for unary operator: '%s'", o->type->name)); } } @@ -544,7 +509,7 @@ mp_obj_t rt_binary_op(int op, mp_obj_t lhs, mp_obj_t rhs) { } // TODO specify in error message what the operator is - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "unsupported operand type for binary operator: '%s'", mp_obj_get_type_str(lhs))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "unsupported operand type for binary operator: '%s'", mp_obj_get_type_str(lhs))); } mp_obj_t rt_compare_op(int op, mp_obj_t lhs, mp_obj_t rhs) { @@ -693,13 +658,13 @@ mp_obj_t rt_call_function_n(mp_obj_t fun_in, int n_args, const mp_obj_t *args) { DEBUG_OP_printf("calling function %p(n_args=%d, args=%p)\n", fun_in, n_args, args); if (MP_OBJ_IS_SMALL_INT(fun_in)) { - nlr_jump(mp_obj_new_exception_msg(rt_q_TypeError, "'int' object is not callable")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_TypeError, "'int' object is not callable")); } else { mp_obj_base_t *fun = fun_in; if (fun->type->call_n != NULL) { return fun->type->call_n(fun_in, n_args, args); } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "'%s' object is not callable", fun->type->name)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "'%s' object is not callable", fun->type->name)); } } } @@ -756,14 +721,14 @@ void rt_unpack_sequence(mp_obj_t seq_in, uint num, mp_obj_t *items) { mp_obj_list_get(seq_in, &seq_len, &seq_items); } if (seq_len < num) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_ValueError, "need more than %d values to unpack", (void*)(machine_uint_t)seq_len)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_ValueError, "need more than %d values to unpack", (void*)(machine_uint_t)seq_len)); } else if (seq_len > num) { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_ValueError, "too many values to unpack (expected %d)", (void*)(machine_uint_t)num)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_ValueError, "too many values to unpack (expected %d)", (void*)(machine_uint_t)num)); } memcpy(items, seq_items, num * sizeof(mp_obj_t)); } else { // TODO call rt_getiter and extract via rt_iternext - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "'%s' object is not iterable", mp_obj_get_type_str(seq_in))); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "'%s' object is not iterable", mp_obj_get_type_str(seq_in))); } } @@ -807,12 +772,12 @@ mp_obj_t rt_load_attr(mp_obj_t base, qstr attr) { } no_attr: - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_AttributeError, "'%s' object has no attribute '%s'", mp_obj_get_type_str(base), qstr_str(attr))); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_AttributeError, "'%s' object has no attribute '%s'", mp_obj_get_type_str(base), qstr_str(attr))); } void rt_load_method(mp_obj_t base, qstr attr, mp_obj_t *dest) { DEBUG_OP_printf("load method %s\n", qstr_str(attr)); - if (MP_OBJ_IS_TYPE(base, &gen_instance_type) && attr == rt_q___next__) { + if (MP_OBJ_IS_TYPE(base, &gen_instance_type) && attr == MP_QSTR___next__) { dest[1] = (mp_obj_t)&mp_builtin_next_obj; dest[0] = base; return; @@ -850,7 +815,7 @@ void rt_store_attr(mp_obj_t base, qstr attr, mp_obj_t value) { mp_map_t *globals = mp_obj_module_get_globals(base); mp_qstr_map_lookup(globals, attr, true)->value = value; } else { - nlr_jump(mp_obj_new_exception_msg_2_args(rt_q_AttributeError, "'%s' object has no attribute '%s'", mp_obj_get_type_str(base), qstr_str(attr))); + nlr_jump(mp_obj_new_exception_msg_2_args(MP_QSTR_AttributeError, "'%s' object has no attribute '%s'", mp_obj_get_type_str(base), qstr_str(attr))); } } @@ -869,26 +834,26 @@ void rt_store_subscr(mp_obj_t base, mp_obj_t index, mp_obj_t value) { mp_obj_t rt_getiter(mp_obj_t o_in) { if (MP_OBJ_IS_SMALL_INT(o_in)) { - nlr_jump(mp_obj_new_exception_msg(rt_q_TypeError, "'int' object is not iterable")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_TypeError, "'int' object is not iterable")); } else { mp_obj_base_t *o = o_in; if (o->type->getiter != NULL) { return o->type->getiter(o_in); } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "'%s' object is not iterable", o->type->name)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "'%s' object is not iterable", o->type->name)); } } } mp_obj_t rt_iternext(mp_obj_t o_in) { if (MP_OBJ_IS_SMALL_INT(o_in)) { - nlr_jump(mp_obj_new_exception_msg(rt_q_TypeError, "? 'int' object is not iterable")); + nlr_jump(mp_obj_new_exception_msg(MP_QSTR_TypeError, "? 'int' object is not iterable")); } else { mp_obj_base_t *o = o_in; if (o->type->iternext != NULL) { return o->type->iternext(o_in); } else { - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_TypeError, "? '%s' object is not iterable", o->type->name)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "? '%s' object is not iterable", o->type->name)); } } } diff --git a/py/runtime.h b/py/runtime.h index cf9180275e..96f1671f67 100644 --- a/py/runtime.h +++ b/py/runtime.h @@ -1,18 +1,3 @@ -extern qstr rt_q_append; -extern qstr rt_q_pop; -extern qstr rt_q_sort; -extern qstr rt_q_join; -extern qstr rt_q_format; -extern qstr rt_q___build_class__; -extern qstr rt_q___next__; -extern qstr rt_q_AttributeError; -extern qstr rt_q_IndexError; -extern qstr rt_q_KeyError; -extern qstr rt_q_NameError; -extern qstr rt_q_TypeError; -extern qstr rt_q_SyntaxError; -extern qstr rt_q_ValueError; - int rt_is_true(mp_obj_t arg); mp_obj_t rt_load_const_dec(qstr qstr); diff --git a/py/runtime0.h b/py/runtime0.h index 8ec2c058f0..97dbe5ddbc 100644 --- a/py/runtime0.h +++ b/py/runtime0.h @@ -81,7 +81,7 @@ extern void *const rt_fun_table[RT_F_NUMBER_OF]; void rt_init(void); void rt_deinit(void); -int rt_get_unique_code_id(bool is_main_module); +int rt_get_unique_code_id(void); void rt_assign_byte_code(int unique_code_id, byte *code, uint len, int n_args, int n_locals, int n_stack, bool is_generator); void rt_assign_native_code(int unique_code_id, void *f, uint len, int n_args); void rt_assign_inline_asm_code(int unique_code_id, void *f, uint len, int n_args); diff --git a/stm/main.c b/stm/main.c index e8db2be2ca..b7ae8aacca 100644 --- a/stm/main.c +++ b/stm/main.c @@ -15,6 +15,7 @@ #include "misc.h" #include "ff.h" #include "mpconfig.h" +#include "mpqstr.h" #include "nlr.h" #include "misc.h" #include "lexer.h" @@ -621,7 +622,7 @@ mp_obj_t pyb_gpio(int n_args, mp_obj_t *args) { } pin_error: - nlr_jump(mp_obj_new_exception_msg_1_arg(rt_q_ValueError, "pin %s does not exist", pin_name)); + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_ValueError, "pin %s does not exist", pin_name)); } MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(pyb_gpio_obj, 1, 2, pyb_gpio); diff --git a/unix/main.c b/unix/main.c index 1aa3331202..e73f69ee24 100644 --- a/unix/main.c +++ b/unix/main.c @@ -217,6 +217,13 @@ int main(int argc, char **argv) { rt_store_name(qstr_from_str_static("test"), test_obj_new(42)); + /* + printf("bytes:\n"); + printf(" total %d\n", m_get_total_bytes_allocated()); + printf(" cur %d\n", m_get_current_bytes_allocated()); + printf(" peak %d\n", m_get_peak_bytes_allocated()); + */ + if (argc == 1) { do_repl(); } else if (argc == 2) { From 5830fae26f7dfeb7a263ba5e1b024694930c64ff Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 18:55:44 +0200 Subject: [PATCH 19/29] Don't error out if build/ directory already exists. --- stm/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/stm/Makefile b/stm/Makefile index e84e21eae2..729913baee 100644 --- a/stm/Makefile +++ b/stm/Makefile @@ -162,7 +162,7 @@ $(BUILD)/flash.elf: $(OBJ) arm-none-eabi-size $@ $(BUILD): - mkdir $@ + mkdir -p $@ $(BUILD)/%.o: %.s $(AS) -o $@ $< From 21dfb55dadb01b135edca9b66ca6b53a82bec60a Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 19:06:34 +0200 Subject: [PATCH 20/29] tests/basics requires python3.3 tests/bytecode/run-tests already uses puthon3.3, so let's just use it here too. Fore reference, errors with python 3.2.3: File "tests/generator1.py", line 12 return None SyntaxError: 'return' with argument inside generator File "tests/list_clear.py", line 3, in x.clear() AttributeError: 'list' object has no attribute 'clear' etc. --- tests/basics/run-tests | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/basics/run-tests b/tests/basics/run-tests index 72e69c2d8e..0037b13045 100755 --- a/tests/basics/run-tests +++ b/tests/basics/run-tests @@ -1,7 +1,7 @@ #!/usr/bin/env bash RM="/bin/rm -f" -CPYTHON3=python3 +CPYTHON3=python3.3 MP_PY=../../unix/py numtests=0 From 9464cde3c94b1c69a9cf433d8b0ac8a7c78f8bf1 Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 19:12:05 +0200 Subject: [PATCH 21/29] Unbreak string slice test by just switching to normal (not byte) strings. --- tests/basics/tests/slice-bstr1.py | 32 ------------------------------ tests/basics/tests/string-slice.py | 32 ++++++++++++++++++++++++++++++ 2 files changed, 32 insertions(+), 32 deletions(-) delete mode 100644 tests/basics/tests/slice-bstr1.py create mode 100644 tests/basics/tests/string-slice.py diff --git a/tests/basics/tests/slice-bstr1.py b/tests/basics/tests/slice-bstr1.py deleted file mode 100644 index 74dbc20617..0000000000 --- a/tests/basics/tests/slice-bstr1.py +++ /dev/null @@ -1,32 +0,0 @@ -print(b"123"[0:1]) - -print(b"123"[0:2]) - -print(b"123"[:1]) - -print(b"123"[1:]) - -# Idiom for copying sequence -print(b"123"[:]) - -print(b"123"[:-1]) - -# Weird cases -print(b"123"[0:0]) -print(b"123"[1:0]) -print(b"123"[1:1]) -print(b"123"[-1:-1]) -print(b"123"[-3:]) -print(b"123"[-3:3]) -print(b"123"[0:]) -print(b"123"[:0]) -print(b"123"[:-3]) -print(b"123"[:-4]) -# Range check testing, don't segfault, please ;-) -print(b"123"[:1000000]) -print(b"123"[1000000:]) -print(b"123"[:-1000000]) -print(b"123"[-1000000:]) -# No IndexError! -print(b""[1:1]) -print(b""[-1:-1]) diff --git a/tests/basics/tests/string-slice.py b/tests/basics/tests/string-slice.py new file mode 100644 index 0000000000..7538ae5700 --- /dev/null +++ b/tests/basics/tests/string-slice.py @@ -0,0 +1,32 @@ +print("123"[0:1]) + +print("123"[0:2]) + +print("123"[:1]) + +print("123"[1:]) + +# Idiom for copying sequence +print("123"[:]) + +print("123"[:-1]) + +# Weird cases +print("123"[0:0]) +print("123"[1:0]) +print("123"[1:1]) +print("123"[-1:-1]) +print("123"[-3:]) +print("123"[-3:3]) +print("123"[0:]) +print("123"[:0]) +print("123"[:-3]) +print("123"[:-4]) +# Range check testing, don't segfault, please ;-) +print("123"[:1000000]) +print("123"[1000000:]) +print("123"[:-1000000]) +print("123"[-1000000:]) +# No IndexError! +print(""[1:1]) +print(""[-1:-1]) From d674bd59890b8f63e6f67415a2107900562a645b Mon Sep 17 00:00:00 2001 From: Paul Sokolovsky Date: Sat, 4 Jan 2014 19:38:19 +0200 Subject: [PATCH 22/29] Convert USE_READLINE config option to be consistent with others. --- unix/Makefile | 2 +- unix/main.c | 4 ++-- unix/mpconfigport.h | 5 +++++ 3 files changed, 8 insertions(+), 3 deletions(-) diff --git a/unix/Makefile b/unix/Makefile index a5c6ddcc04..c7be62e999 100644 --- a/unix/Makefile +++ b/unix/Makefile @@ -2,7 +2,7 @@ PYSRC=../py BUILD=build CC = gcc -CFLAGS = -I. -I$(PYSRC) -Wall -Werror -ansi -std=gnu99 -Os -DUSE_READLINE #-DNDEBUG +CFLAGS = -I. -I$(PYSRC) -Wall -Werror -ansi -std=gnu99 -Os #-DNDEBUG LDFLAGS = -lm SRC_C = \ diff --git a/unix/main.c b/unix/main.c index e73f69ee24..ecb2fa338e 100644 --- a/unix/main.c +++ b/unix/main.c @@ -15,7 +15,7 @@ #include "runtime.h" #include "repl.h" -#ifdef USE_READLINE +#if MICROPY_USE_READLINE #include #include #endif @@ -35,7 +35,7 @@ static char *str_join(const char *s1, int sep_char, const char *s2) { } static char *prompt(char *p) { -#ifdef USE_READLINE +#if MICROPY_USE_READLINE char *line = readline(p); if (line) { add_history(line); diff --git a/unix/mpconfigport.h b/unix/mpconfigport.h index 36cf138c17..7a4622b8b6 100644 --- a/unix/mpconfigport.h +++ b/unix/mpconfigport.h @@ -1,5 +1,10 @@ // options to control how Micro Python is built +// Linking with GNU readline causes binary to be licensed under GPL +#ifndef MICROPY_USE_READLINE +#define MICROPY_USE_READLINE (1) +#endif + #define MICROPY_ENABLE_FLOAT (1) #define MICROPY_EMIT_CPYTHON (0) #define MICROPY_EMIT_X64 (1) From e9906ac3d771a312b05d76e42aee8e806dd0d128 Mon Sep 17 00:00:00 2001 From: Damien George Date: Sat, 4 Jan 2014 18:44:46 +0000 Subject: [PATCH 23/29] Add ellipsis object. --- py/bc0.h | 16 ++++++++++------ py/emitbc.c | 1 + py/grammar.h | 8 ++++---- py/lexer.c | 2 +- py/lexer.h | 2 +- py/mpqstrraw.h | 1 + py/obj.h | 1 + py/objslice.c | 29 +++++++++++++++++++++++++++++ py/runtime.c | 3 +++ py/showbc.c | 4 ++++ py/vm.c | 4 ++++ 11 files changed, 59 insertions(+), 12 deletions(-) diff --git a/py/bc0.h b/py/bc0.h index 773e23d2ea..0a4a49ce66 100644 --- a/py/bc0.h +++ b/py/bc0.h @@ -1,12 +1,16 @@ +// Micro Python byte-codes. +// The comment at the end of the line (if it exists) tells the arguments to the byte-code. + #define MP_BC_LOAD_CONST_FALSE (0x10) #define MP_BC_LOAD_CONST_NONE (0x11) #define MP_BC_LOAD_CONST_TRUE (0x12) -#define MP_BC_LOAD_CONST_SMALL_INT (0x13) // 24-bit, in excess -#define MP_BC_LOAD_CONST_INT (0x14) // qstr -#define MP_BC_LOAD_CONST_DEC (0x15) // qstr -#define MP_BC_LOAD_CONST_ID (0x16) // qstr -#define MP_BC_LOAD_CONST_BYTES (0x17) // qstr -#define MP_BC_LOAD_CONST_STRING (0x18) // qstr +#define MP_BC_LOAD_CONST_ELLIPSIS (0x13) +#define MP_BC_LOAD_CONST_SMALL_INT (0x14) // 24-bit, in excess +#define MP_BC_LOAD_CONST_INT (0x15) // qstr +#define MP_BC_LOAD_CONST_DEC (0x16) // qstr +#define MP_BC_LOAD_CONST_ID (0x17) // qstr +#define MP_BC_LOAD_CONST_BYTES (0x18) // qstr +#define MP_BC_LOAD_CONST_STRING (0x19) // qstr #define MP_BC_LOAD_FAST_0 (0x20) #define MP_BC_LOAD_FAST_1 (0x21) diff --git a/py/emitbc.c b/py/emitbc.c index dc1988582c..c0ec2469a6 100644 --- a/py/emitbc.c +++ b/py/emitbc.c @@ -249,6 +249,7 @@ static void emit_bc_load_const_tok(emit_t *emit, mp_token_kind_t tok) { case MP_TOKEN_KW_FALSE: emit_write_byte_1(emit, MP_BC_LOAD_CONST_FALSE); break; case MP_TOKEN_KW_NONE: emit_write_byte_1(emit, MP_BC_LOAD_CONST_NONE); break; case MP_TOKEN_KW_TRUE: emit_write_byte_1(emit, MP_BC_LOAD_CONST_TRUE); break; + case MP_TOKEN_ELLIPSIS: emit_write_byte_1(emit, MP_BC_LOAD_CONST_ELLIPSIS); break; default: assert(0); } } diff --git a/py/grammar.h b/py/grammar.h index b1faab79e1..4d53bd3fc4 100644 --- a/py/grammar.h +++ b/py/grammar.h @@ -113,11 +113,11 @@ DEF_RULE(import_stmt, nc, or(2), rule(import_name), rule(import_from)) DEF_RULE(import_name, c(import_name), and(2), tok(KW_IMPORT), rule(dotted_as_names)) DEF_RULE(import_from, c(import_from), and(4), tok(KW_FROM), rule(import_from_2), tok(KW_IMPORT), rule(import_from_3)) DEF_RULE(import_from_2, nc, or(2), rule(dotted_name), rule(import_from_2b)) -DEF_RULE(import_from_2b, nc, and(2), rule(one_or_more_period_or_ellipses), opt_rule(dotted_name)) +DEF_RULE(import_from_2b, nc, and(2), rule(one_or_more_period_or_ellipsis), opt_rule(dotted_name)) DEF_RULE(import_from_3, nc, or(3), tok(OP_STAR), rule(import_as_names_paren), rule(import_as_names)) DEF_RULE(import_as_names_paren, nc, and(3), tok(DEL_PAREN_OPEN), rule(import_as_names), tok(DEL_PAREN_CLOSE)) -DEF_RULE(one_or_more_period_or_ellipses, nc, one_or_more, rule(period_or_ellipses)) -DEF_RULE(period_or_ellipses, nc, or(2), tok(DEL_PERIOD), tok(ELLIPSES)) +DEF_RULE(one_or_more_period_or_ellipsis, nc, one_or_more, rule(period_or_ellipsis)) +DEF_RULE(period_or_ellipsis, nc, or(2), tok(DEL_PERIOD), tok(ELLIPSIS)) DEF_RULE(import_as_name, nc, and(2), tok(NAME), opt_rule(as_name)) DEF_RULE(dotted_as_name, nc, and(2), rule(dotted_name), opt_rule(as_name)) DEF_RULE(as_name, nc, and(2), tok(KW_AS), tok(NAME)) @@ -220,7 +220,7 @@ DEF_RULE(power_dbl_star, c(power_dbl_star), and(2), tok(OP_DBL_STAR), rule(facto // testlist_comp: (test|star_expr) ( comp_for | (',' (test|star_expr))* [','] ) // trailer: '(' [arglist] ')' | '[' subscriptlist ']' | '.' NAME -DEF_RULE(atom, nc, or(10), tok(NAME), tok(NUMBER), rule(atom_string), tok(ELLIPSES), tok(KW_NONE), tok(KW_TRUE), tok(KW_FALSE), rule(atom_paren), rule(atom_bracket), rule(atom_brace)) +DEF_RULE(atom, nc, or(10), tok(NAME), tok(NUMBER), rule(atom_string), tok(ELLIPSIS), tok(KW_NONE), tok(KW_TRUE), tok(KW_FALSE), rule(atom_paren), rule(atom_bracket), rule(atom_brace)) DEF_RULE(atom_string, c(atom_string), one_or_more, rule(string_or_bytes)) DEF_RULE(string_or_bytes, nc, or(2), tok(STRING), tok(BYTES)) DEF_RULE(atom_paren, c(atom_paren), and(3), tok(DEL_PAREN_OPEN), opt_rule(atom_2b), tok(DEL_PAREN_CLOSE)) diff --git a/py/lexer.c b/py/lexer.c index 4df91b0365..d4205236c3 100644 --- a/py/lexer.c +++ b/py/lexer.c @@ -239,7 +239,7 @@ static const uint8_t tok_enc_kind[] = { MP_TOKEN_OP_CARET, MP_TOKEN_DEL_CARET_EQUAL, MP_TOKEN_DEL_EQUAL, MP_TOKEN_OP_DBL_EQUAL, MP_TOKEN_OP_NOT_EQUAL, - MP_TOKEN_DEL_PERIOD, MP_TOKEN_ELLIPSES, + MP_TOKEN_DEL_PERIOD, MP_TOKEN_ELLIPSIS, }; // must have the same order as enum in lexer.h diff --git a/py/lexer.h b/py/lexer.h index 27244fde96..3cb48ce9e1 100644 --- a/py/lexer.h +++ b/py/lexer.h @@ -20,7 +20,7 @@ typedef enum _mp_token_kind_t { MP_TOKEN_STRING, MP_TOKEN_BYTES, - MP_TOKEN_ELLIPSES, + MP_TOKEN_ELLIPSIS, MP_TOKEN_KW_FALSE, // 12 MP_TOKEN_KW_NONE, diff --git a/py/mpqstrraw.h b/py/mpqstrraw.h index 85cf1ff7bd..e73bd828eb 100644 --- a/py/mpqstrraw.h +++ b/py/mpqstrraw.h @@ -20,6 +20,7 @@ Q(native) Q(viper) Q(asm_thumb) +Q(Ellipsis) Q(StopIteration) Q(AttributeError) diff --git a/py/obj.h b/py/obj.h index 16c7c36dd1..f0ba6999e9 100644 --- a/py/obj.h +++ b/py/obj.h @@ -110,6 +110,7 @@ extern const mp_obj_type_t mp_const_type; extern const mp_obj_t mp_const_none; extern const mp_obj_t mp_const_false; extern const mp_obj_t mp_const_true; +extern const mp_obj_t mp_const_ellipsis; extern const mp_obj_t mp_const_stop_iteration; // special object indicating end of iteration (not StopIteration exception!) // Need to declare this here so we are not dependent on map.h diff --git a/py/objslice.c b/py/objslice.c index 03607e4c3e..d99325fd73 100644 --- a/py/objslice.c +++ b/py/objslice.c @@ -9,6 +9,35 @@ #include "obj.h" #include "runtime0.h" +/******************************************************************************/ +/* ellipsis object, a singleton */ + +typedef struct _mp_obj_ellipsis_t { + mp_obj_base_t base; +} mp_obj_ellipsis_t; + +void ellipsis_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in) { + print(env, "Ellipsis"); +} + +const mp_obj_type_t ellipsis_type = { + { &mp_const_type }, + "ellipsis", + ellipsis_print, // print + NULL, // call_n + NULL, // unary_op + NULL, // binary_op + NULL, // getiter + NULL, // iternext + {{NULL, NULL},}, // method list +}; + +static const mp_obj_ellipsis_t ellipsis_obj = {{&ellipsis_type}}; +const mp_obj_t mp_const_ellipsis = (mp_obj_t)&ellipsis_obj; + +/******************************************************************************/ +/* slice object */ + #if MICROPY_ENABLE_SLICE // TODO: This implements only variant of slice with 2 integer args only. diff --git a/py/runtime.c b/py/runtime.c index a1f9ee3b7b..72881067d4 100644 --- a/py/runtime.c +++ b/py/runtime.c @@ -84,6 +84,9 @@ void rt_init(void) { mp_qstr_map_lookup(&map_builtins, MP_QSTR_SyntaxError, true)->value = mp_obj_new_exception(MP_QSTR_SyntaxError); mp_qstr_map_lookup(&map_builtins, MP_QSTR_ValueError, true)->value = mp_obj_new_exception(MP_QSTR_ValueError); + // built-in objects + mp_qstr_map_lookup(&map_builtins, MP_QSTR_Ellipsis, true)->value = mp_const_ellipsis; + // built-in core functions mp_qstr_map_lookup(&map_builtins, MP_QSTR___build_class__, true)->value = rt_make_function_2(mp_builtin___build_class__); mp_qstr_map_lookup(&map_builtins, MP_QSTR___repl_print__, true)->value = rt_make_function_1(mp_builtin___repl_print__); diff --git a/py/showbc.c b/py/showbc.c index a3bfa2833b..eb7d41b24d 100644 --- a/py/showbc.c +++ b/py/showbc.c @@ -46,6 +46,10 @@ void mp_show_byte_code(const byte *ip, int len) { printf("LOAD_CONST_TRUE"); break; + case MP_BC_LOAD_CONST_ELLIPSIS: + printf("LOAD_CONST_ELLIPSIS"); + break; + case MP_BC_LOAD_CONST_SMALL_INT: unum = (ip[0] | (ip[1] << 8) | (ip[2] << 16)) - 0x800000; ip += 3; diff --git a/py/vm.c b/py/vm.c index 382780640b..8e7ef7485b 100644 --- a/py/vm.c +++ b/py/vm.c @@ -99,6 +99,10 @@ bool mp_execute_byte_code_2(const byte **ip_in_out, mp_obj_t *fastn, mp_obj_t ** PUSH(mp_const_true); break; + case MP_BC_LOAD_CONST_ELLIPSIS: + PUSH(mp_const_ellipsis); + break; + case MP_BC_LOAD_CONST_SMALL_INT: unum = (ip[0] | (ip[1] << 8) | (ip[2] << 16)) - 0x800000; ip += 3; From 5d02e2d6fa3afcd8aa9ecb475b0c4599da6ca03d Mon Sep 17 00:00:00 2001 From: Mikael Eiman Date: Sat, 4 Jan 2014 20:15:04 +0100 Subject: [PATCH 24/29] OSX: fixes to make nlrx64.S with Apple's clang --- py/nlrx64.S | 23 +++++++++++++++++++++-- 1 file changed, 21 insertions(+), 2 deletions(-) diff --git a/py/nlrx64.S b/py/nlrx64.S index 6d0e2118f7..37d3137785 100644 --- a/py/nlrx64.S +++ b/py/nlrx64.S @@ -5,9 +5,14 @@ .text /* uint nlr_push(rdi=nlr_buf_t *nlr) */ +#ifndef __llvm__ .globl nlr_push .type nlr_push, @function nlr_push: +#else + .globl _nlr_push +_nlr_push: +#endif movq (%rsp), %rax # load return %rip movq %rax, 16(%rdi) # store %rip into nlr_buf movq %rbp, 24(%rdi) # store %rbp into nlr_buf @@ -22,22 +27,32 @@ nlr_push: movq %rdi, nlr_top(%rip) # stor new nlr_buf (to make linked list) xorq %rax, %rax # return 0, normal return ret # return - .size nlr_push, .-nlr_push +// .size nlr_push, .-nlr_push /* void nlr_pop() */ +#ifndef __llvm__ .globl nlr_pop .type nlr_pop, @function nlr_pop: +#else + .globl _nlr_pop +_nlr_pop: +#endif movq nlr_top(%rip), %rax # get nlr_top into %rax movq (%rax), %rax # load prev nlr_buf movq %rax, nlr_top(%rip) # store prev nlr_buf (to unlink list) ret # return - .size nlr_pop, .-nlr_pop +// .size nlr_pop, .-nlr_pop /* void nlr_jump(rdi=uint val) */ +#ifndef __llvm__ .globl nlr_jump .type nlr_jump, @function nlr_jump: +#else + .globl _nlr_jump + _nlr_jump: +#endif movq %rdi, %rax # put return value in %rax movq nlr_top(%rip), %rdi # get nlr_top into %rdi movq %rax, 8(%rdi) # store return value @@ -55,8 +70,12 @@ nlr_jump: xorq %rax, %rax # clear return register inc %al # increase to make 1, non-local return ret # return +#ifndef __llvm__ .size nlr_jump, .-nlr_jump +#endif +#ifndef __llvm__ .local nlr_top +#endif .comm nlr_top,8,8 #endif From f53cdd947cacbe273bcef0c68ced83162a16a24a Mon Sep 17 00:00:00 2001 From: Mikael Eiman Date: Sat, 4 Jan 2014 20:19:19 +0100 Subject: [PATCH 25/29] OSX: fixes to make nlrx64.S with Apple's clang (forgot a few places) --- py/nlrx64.S | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/py/nlrx64.S b/py/nlrx64.S index 37d3137785..20a3704fd4 100644 --- a/py/nlrx64.S +++ b/py/nlrx64.S @@ -27,7 +27,9 @@ _nlr_push: movq %rdi, nlr_top(%rip) # stor new nlr_buf (to make linked list) xorq %rax, %rax # return 0, normal return ret # return -// .size nlr_push, .-nlr_push +#ifndef __llvm__ + .size nlr_push, .-nlr_push +#endif /* void nlr_pop() */ #ifndef __llvm__ @@ -42,7 +44,9 @@ _nlr_pop: movq (%rax), %rax # load prev nlr_buf movq %rax, nlr_top(%rip) # store prev nlr_buf (to unlink list) ret # return -// .size nlr_pop, .-nlr_pop +#ifndef __llvm__ + .size nlr_pop, .-nlr_pop +#endif /* void nlr_jump(rdi=uint val) */ #ifndef __llvm__ From d67091371da5fed82547988864577928e8468b8e Mon Sep 17 00:00:00 2001 From: Mikael Eiman Date: Sat, 4 Jan 2014 20:27:13 +0100 Subject: [PATCH 26/29] OSX: fixes to make nlrx64.S with Apple's clang (switched to Apple-specific define instead of __llvm__) --- py/nlrx64.S | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/py/nlrx64.S b/py/nlrx64.S index 20a3704fd4..441817b4f3 100644 --- a/py/nlrx64.S +++ b/py/nlrx64.S @@ -5,7 +5,7 @@ .text /* uint nlr_push(rdi=nlr_buf_t *nlr) */ -#ifndef __llvm__ +#ifndef __apple_build_version__ .globl nlr_push .type nlr_push, @function nlr_push: @@ -27,12 +27,12 @@ _nlr_push: movq %rdi, nlr_top(%rip) # stor new nlr_buf (to make linked list) xorq %rax, %rax # return 0, normal return ret # return -#ifndef __llvm__ +#ifndef __apple_build_version__ .size nlr_push, .-nlr_push #endif /* void nlr_pop() */ -#ifndef __llvm__ +#ifndef __apple_build_version__ .globl nlr_pop .type nlr_pop, @function nlr_pop: @@ -44,12 +44,12 @@ _nlr_pop: movq (%rax), %rax # load prev nlr_buf movq %rax, nlr_top(%rip) # store prev nlr_buf (to unlink list) ret # return -#ifndef __llvm__ +#ifndef __apple_build_version__ .size nlr_pop, .-nlr_pop #endif /* void nlr_jump(rdi=uint val) */ -#ifndef __llvm__ +#ifndef __apple_build_version__ .globl nlr_jump .type nlr_jump, @function nlr_jump: @@ -74,11 +74,11 @@ nlr_jump: xorq %rax, %rax # clear return register inc %al # increase to make 1, non-local return ret # return -#ifndef __llvm__ +#ifndef __apple_build_version__ .size nlr_jump, .-nlr_jump #endif -#ifndef __llvm__ +#ifndef __apple_build_version__ .local nlr_top #endif .comm nlr_top,8,8 From 71c5181a8dfa69ba9f5ca322a3aba0660be2e166 Mon Sep 17 00:00:00 2001 From: Damien George Date: Sat, 4 Jan 2014 20:21:15 +0000 Subject: [PATCH 27/29] Convert Python types to proper Python type hierarchy. Now much more inline with how CPython does types. --- py/builtin.c | 126 +--------------------------------------------- py/compile.c | 2 +- py/emitpass1.c | 5 +- py/mpqstrraw.h | 5 +- py/obj.c | 12 ++--- py/obj.h | 7 +++ py/objbool.c | 14 +++++- py/objboundmeth.c | 1 + py/objcell.c | 1 + py/objclass.c | 1 + py/objclosure.c | 1 + py/objcomplex.c | 45 ++++++++++++++++- py/objdict.c | 11 +++- py/objexcept.c | 1 + py/objfloat.c | 26 ++++++++-- py/objfun.c | 3 ++ py/objgenerator.c | 2 + py/objinstance.c | 1 + py/objlist.c | 25 +++++++++ py/objmodule.c | 1 + py/objnone.c | 1 + py/objrange.c | 2 + py/objset.c | 28 ++++++++++- py/objslice.c | 2 + py/objstr.c | 1 + py/objtuple.c | 76 ++++++++++++++++++++++++---- py/objtype.c | 21 ++++++-- py/runtime.c | 29 ++++++----- stm/Makefile | 1 + stm/i2c.c | 1 + stm/led.c | 1 + stm/main.c | 1 + stm/servo.c | 1 + unix-cpy/Makefile | 1 + unix/Makefile | 1 + unix/main.c | 1 + 36 files changed, 285 insertions(+), 173 deletions(-) diff --git a/py/builtin.c b/py/builtin.c index b565ed4640..6babc76692 100644 --- a/py/builtin.c +++ b/py/builtin.c @@ -88,14 +88,6 @@ mp_obj_t mp_builtin_any(mp_obj_t o_in) { return mp_const_false; } -mp_obj_t mp_builtin_bool(int n_args, const mp_obj_t *args) { - switch (n_args) { - case 0: return mp_const_false; - case 1: if (rt_is_true(args[0])) { return mp_const_true; } else { return mp_const_false; } - default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "bool() takes at most 1 argument (%d given)", (void*)(machine_int_t)n_args)); - } -} - mp_obj_t mp_builtin_callable(mp_obj_t o_in) { if (mp_obj_is_callable(o_in)) { return mp_const_true; @@ -104,42 +96,6 @@ mp_obj_t mp_builtin_callable(mp_obj_t o_in) { } } -#if MICROPY_ENABLE_FLOAT -mp_obj_t mp_builtin_complex(int n_args, const mp_obj_t *args) { - assert(0 <= n_args && n_args <= 2); - - if (n_args == 0) { - return mp_obj_new_complex(0, 0); - } else if (n_args == 1) { - // TODO allow string as first arg and parse it - if (MP_OBJ_IS_TYPE(args[0], &complex_type)) { - return args[0]; - } else { - return mp_obj_new_complex(mp_obj_get_float(args[0]), 0); - } - } else { - mp_float_t real, imag; - if (MP_OBJ_IS_TYPE(args[0], &complex_type)) { - mp_obj_get_complex(args[0], &real, &imag); - } else { - real = mp_obj_get_float(args[0]); - imag = 0; - } - if (MP_OBJ_IS_TYPE(args[1], &complex_type)) { - mp_float_t real2, imag2; - mp_obj_get_complex(args[1], &real2, &imag2); - real -= imag2; - imag += real2; - } else { - imag += mp_obj_get_float(args[1]); - } - return mp_obj_new_complex(real, imag); - } -} - -MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(mp_builtin_complex_obj, 0, 2, mp_builtin_complex); -#endif - mp_obj_t mp_builtin_chr(mp_obj_t o_in) { int ord = mp_obj_get_int(o_in); if (0 <= ord && ord <= 0x10ffff) { @@ -152,11 +108,6 @@ mp_obj_t mp_builtin_chr(mp_obj_t o_in) { } } -mp_obj_t mp_builtin_dict(void) { - // TODO create from an iterable! - return rt_build_map(0); -} - mp_obj_t mp_builtin_divmod(mp_obj_t o1_in, mp_obj_t o2_in) { if (MP_OBJ_IS_SMALL_INT(o1_in) && MP_OBJ_IS_SMALL_INT(o2_in)) { mp_small_int_t i1 = MP_OBJ_SMALL_INT_VALUE(o1_in); @@ -170,25 +121,6 @@ mp_obj_t mp_builtin_divmod(mp_obj_t o1_in, mp_obj_t o2_in) { } } -#if MICROPY_ENABLE_FLOAT -static mp_obj_t mp_builtin_float(int n_args, const mp_obj_t *args) { - assert(0 <= n_args && n_args <= 1); - - if (n_args == 0) { - return mp_obj_new_float(0); - } else { - // TODO allow string as arg and parse it - if (MP_OBJ_IS_TYPE(args[0], &float_type)) { - return args[0]; - } else { - return mp_obj_new_float(mp_obj_get_float(args[0])); - } - } -} - -MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(mp_builtin_float_obj, 0, 1, mp_builtin_float); -#endif - static mp_obj_t mp_builtin_hash(mp_obj_t o_in) { // TODO hash will generally overflow small integer; can we safely truncate it? return mp_obj_new_int(mp_obj_hash(o_in)); @@ -196,23 +128,6 @@ static mp_obj_t mp_builtin_hash(mp_obj_t o_in) { MP_DEFINE_CONST_FUN_OBJ_1(mp_builtin_hash_obj, mp_builtin_hash); -static mp_obj_t mp_builtin_int(int n_args, const mp_obj_t *args) { - assert(0 <= n_args && n_args <= 2); - - if (n_args == 0) { - return MP_OBJ_NEW_SMALL_INT(0); - } else if (n_args == 1) { - // TODO if arg is a string then parse it - return mp_obj_new_int(mp_obj_get_int(args[0])); - } else { // n_args == 2 - // TODO, parse with given base - assert(0); - return MP_OBJ_NEW_SMALL_INT(0); - } -} - -MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(mp_builtin_int_obj, 0, 2, mp_builtin_int); - static mp_obj_t mp_builtin_iter(mp_obj_t o_in) { return rt_getiter(o_in); } @@ -241,24 +156,6 @@ mp_obj_t mp_builtin_len(mp_obj_t o_in) { return MP_OBJ_NEW_SMALL_INT(len); } -mp_obj_t mp_builtin_list(int n_args, const mp_obj_t *args) { - switch (n_args) { - case 0: return rt_build_list(0, NULL); - case 1: - { - // make list from iterable - mp_obj_t iterable = rt_getiter(args[0]); - mp_obj_t list = rt_build_list(0, NULL); - mp_obj_t item; - while ((item = rt_iternext(iterable)) != mp_const_stop_iteration) { - rt_list_append(list, item); - } - return list; - } - default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "list() takes at most 1 argument (%d given)", (void*)(machine_int_t)n_args)); - } -} - mp_obj_t mp_builtin_max(int n_args, const mp_obj_t *args) { if (n_args == 1) { // given an iterable @@ -367,26 +264,6 @@ mp_obj_t mp_builtin_range(int n_args, const mp_obj_t *args) { } } -static mp_obj_t mp_builtin_set(int n_args, const mp_obj_t *args) { - assert(0 <= n_args && n_args <= 1); - - if (n_args == 0) { - // return a new, empty set - return mp_obj_new_set(0, NULL); - } else { - // 1 argument, an iterable from which we make a new set - mp_obj_t set = mp_obj_new_set(0, NULL); - mp_obj_t iterable = rt_getiter(args[0]); - mp_obj_t item; - while ((item = rt_iternext(iterable)) != mp_const_stop_iteration) { - mp_obj_set_store(set, item); - } - return set; - } -} - -MP_DEFINE_CONST_FUN_OBJ_VAR_BETWEEN(mp_builtin_set_obj, 0, 1, mp_builtin_set); - mp_obj_t mp_builtin_sum(int n_args, const mp_obj_t *args) { mp_obj_t value; switch (n_args) { @@ -405,8 +282,7 @@ mp_obj_t mp_builtin_sum(int n_args, const mp_obj_t *args) { static mp_obj_t mp_builtin_type(mp_obj_t o_in) { // TODO implement the 3 argument version of type() if (MP_OBJ_IS_SMALL_INT(o_in)) { - // TODO implement int-type - return mp_const_none; + return (mp_obj_t)&int_type; } else { mp_obj_base_t *o = o_in; return (mp_obj_t)o->type; diff --git a/py/compile.c b/py/compile.c index f8fa2cb2c2..0e19890315 100644 --- a/py/compile.c +++ b/py/compile.c @@ -1316,7 +1316,7 @@ void compile_nonlocal_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { void compile_assert_stmt(compiler_t *comp, mp_parse_node_struct_t *pns) { int l_end = comp_next_label(comp); c_if_cond(comp, pns->nodes[0], true, l_end); - EMIT(load_id, MP_QSTR_assertion_error); + EMIT(load_id, MP_QSTR_AssertionError); if (!MP_PARSE_NODE_IS_NULL(pns->nodes[1])) { // assertion message compile_node(comp, pns->nodes[1]); diff --git a/py/emitpass1.c b/py/emitpass1.c index 1c11241e0d..f78ec7e27e 100644 --- a/py/emitpass1.c +++ b/py/emitpass1.c @@ -7,6 +7,7 @@ #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "lexer.h" #include "parse.h" #include "scope.h" @@ -44,9 +45,9 @@ static void emit_pass1_load_id(emit_t *emit, qstr qstr) { bool added; id_info_t *id = scope_find_or_add_id(emit->scope, qstr, &added); if (added) { - if (strcmp(qstr_str(qstr), "AssertionError") == 0) { - id->kind = ID_INFO_KIND_GLOBAL_EXPLICIT; + if (qstr == MP_QSTR_AssertionError) { // TODO how much of a hack is this? + id->kind = ID_INFO_KIND_GLOBAL_EXPLICIT; } else if (strcmp(qstr_str(qstr), "super") == 0 && emit->scope->kind == SCOPE_FUNCTION) { // special case, super is a global, and also counts as use of __class__ id->kind = ID_INFO_KIND_GLOBAL_EXPLICIT; diff --git a/py/mpqstrraw.h b/py/mpqstrraw.h index e73bd828eb..fe74c3e927 100644 --- a/py/mpqstrraw.h +++ b/py/mpqstrraw.h @@ -13,7 +13,6 @@ Q(__next__) Q(__qualname__) Q(__repl_print__) -Q(assertion_error) Q(micropython) Q(byte_code) Q(native) @@ -23,12 +22,13 @@ Q(asm_thumb) Q(Ellipsis) Q(StopIteration) +Q(AssertionError) Q(AttributeError) Q(IndexError) Q(KeyError) Q(NameError) -Q(TypeError) Q(SyntaxError) +Q(TypeError) Q(ValueError) Q(abs) @@ -55,6 +55,7 @@ Q(print) Q(range) Q(set) Q(sum) +Q(tuple) Q(type) Q(append) diff --git a/py/obj.c b/py/obj.c index 2b834ffe43..77580e1fee 100644 --- a/py/obj.c +++ b/py/obj.c @@ -13,10 +13,6 @@ #include "runtime.h" #include "map.h" -mp_obj_t mp_obj_new_int(machine_int_t value) { - return MP_OBJ_NEW_SMALL_INT(value); -} - const char *mp_obj_get_type_str(mp_obj_t o_in) { if (MP_OBJ_IS_SMALL_INT(o_in)) { return "int"; @@ -128,9 +124,13 @@ machine_int_t mp_obj_get_int(mp_obj_t arg) { return 1; } else if (MP_OBJ_IS_SMALL_INT(arg)) { return MP_OBJ_SMALL_INT_VALUE(arg); +#if MICROPY_ENABLE_FLOAT + } else if (MP_OBJ_IS_TYPE(arg, &float_type)) { + // TODO work out if this should be floor, ceil or trunc + return (machine_int_t)mp_obj_float_get(arg); +#endif } else { - assert(0); - return 0; + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "can't convert %s to int", mp_obj_get_type_str(arg))); } } diff --git a/py/obj.h b/py/obj.h index f0ba6999e9..03e67dd479 100644 --- a/py/obj.h +++ b/py/obj.h @@ -58,6 +58,7 @@ typedef mp_obj_t (*mp_fun_t)(void); typedef mp_obj_t (*mp_fun_var_t)(int n, const mp_obj_t *); typedef void (*mp_print_fun_t)(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t o); +typedef mp_obj_t (*mp_make_new_fun_t)(mp_obj_t type_in, int n_args, const mp_obj_t *args); // args are in reverse order in the array typedef mp_obj_t (*mp_call_n_fun_t)(mp_obj_t fun, int n_args, const mp_obj_t *args); // args are in reverse order in the array typedef mp_obj_t (*mp_unary_op_fun_t)(int op, mp_obj_t); typedef mp_obj_t (*mp_binary_op_fun_t)(int op, mp_obj_t, mp_obj_t); @@ -71,6 +72,7 @@ struct _mp_obj_type_t { mp_obj_base_t base; const char *name; mp_print_fun_t print; + mp_make_new_fun_t make_new; // to make an instance of the type mp_call_n_fun_t call_n; mp_unary_op_fun_t unary_op; // can return NULL if op not supported @@ -110,6 +112,7 @@ extern const mp_obj_type_t mp_const_type; extern const mp_obj_t mp_const_none; extern const mp_obj_t mp_const_false; extern const mp_obj_t mp_const_true; +extern const mp_obj_t mp_const_empty_tuple; extern const mp_obj_t mp_const_ellipsis; extern const mp_obj_t mp_const_stop_iteration; // special object indicating end of iteration (not StopIteration exception!) @@ -180,6 +183,9 @@ extern const mp_obj_type_t bool_type; mp_obj_t mp_obj_cell_get(mp_obj_t self_in); void mp_obj_cell_set(mp_obj_t self_in, mp_obj_t obj); +// int +extern const mp_obj_type_t int_type; + // exception extern const mp_obj_type_t exception_type; qstr mp_obj_exception_get_type(mp_obj_t self_in); @@ -214,6 +220,7 @@ uint mp_obj_dict_len(mp_obj_t self_in); mp_obj_t mp_obj_dict_store(mp_obj_t self_in, mp_obj_t key, mp_obj_t value); // set +extern const mp_obj_type_t set_type; void mp_obj_set_store(mp_obj_t self_in, mp_obj_t item); // slice diff --git a/py/objbool.c b/py/objbool.c index 9b53ffae94..1d94ee03be 100644 --- a/py/objbool.c +++ b/py/objbool.c @@ -4,14 +4,16 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" +#include "runtime.h" typedef struct _mp_obj_bool_t { mp_obj_base_t base; bool value; } mp_obj_bool_t; -void bool_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in) { +static void bool_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in) { mp_obj_bool_t *self = self_in; if (self->value) { print(env, "True"); @@ -20,10 +22,20 @@ void bool_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_ob } } +// args are reverse in the array +static mp_obj_t bool_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + switch (n_args) { + case 0: return mp_const_false; + case 1: if (rt_is_true(args[0])) { return mp_const_true; } else { return mp_const_false; } + default: nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "bool takes at most 1 argument, %d given", (void*)(machine_int_t)n_args)); + } +} + const mp_obj_type_t bool_type = { { &mp_const_type }, "bool", bool_print, // print + bool_make_new, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objboundmeth.c b/py/objboundmeth.c index 8bd238c65e..264c2effd4 100644 --- a/py/objboundmeth.c +++ b/py/objboundmeth.c @@ -37,6 +37,7 @@ const mp_obj_type_t bound_meth_type = { { &mp_const_type }, "bound_method", NULL, // print + NULL, // make_new bound_meth_call_n, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objcell.c b/py/objcell.c index cba1980579..daaa340a7f 100644 --- a/py/objcell.c +++ b/py/objcell.c @@ -27,6 +27,7 @@ const mp_obj_type_t cell_type = { { &mp_const_type }, "cell", NULL, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objclass.c b/py/objclass.c index f223c5ff25..197dfa7268 100644 --- a/py/objclass.c +++ b/py/objclass.c @@ -64,6 +64,7 @@ const mp_obj_type_t class_type = { { &mp_const_type }, "class", NULL, // print + NULL, // make_new class_call_n, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objclosure.c b/py/objclosure.c index e3354d42d9..550bb5067f 100644 --- a/py/objclosure.c +++ b/py/objclosure.c @@ -36,6 +36,7 @@ const mp_obj_type_t closure_type = { { &mp_const_type }, "closure", NULL, // print + NULL, // make_new closure_call_n, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objcomplex.c b/py/objcomplex.c index ab9c146774..5408d71cf2 100644 --- a/py/objcomplex.c +++ b/py/objcomplex.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" #include "map.h" @@ -29,7 +30,46 @@ void complex_print(void (*print)(void *env, const char *fmt, ...), void *env, mp } } -mp_obj_t complex_unary_op(int op, mp_obj_t o_in) { +// args are reverse in the array +static mp_obj_t complex_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + switch (n_args) { + case 0: + return mp_obj_new_complex(0, 0); + + case 1: + // TODO allow string as first arg and parse it + if (MP_OBJ_IS_TYPE(args[0], &complex_type)) { + return args[0]; + } else { + return mp_obj_new_complex(mp_obj_get_float(args[0]), 0); + } + + case 2: + { + mp_float_t real, imag; + if (MP_OBJ_IS_TYPE(args[1], &complex_type)) { + mp_obj_get_complex(args[1], &real, &imag); + } else { + real = mp_obj_get_float(args[1]); + imag = 0; + } + if (MP_OBJ_IS_TYPE(args[0], &complex_type)) { + mp_float_t real2, imag2; + mp_obj_get_complex(args[0], &real2, &imag2); + real -= imag2; + imag += real2; + } else { + imag += mp_obj_get_float(args[0]); + } + return mp_obj_new_complex(real, imag); + } + + default: + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "complex takes at most 2 arguments, %d given", (void*)(machine_int_t)n_args)); + } +} + +static mp_obj_t complex_unary_op(int op, mp_obj_t o_in) { mp_obj_complex_t *o = o_in; switch (op) { case RT_UNARY_OP_NOT: if (o->real != 0 || o->imag != 0) { return mp_const_true;} else { return mp_const_false; } @@ -39,7 +79,7 @@ mp_obj_t complex_unary_op(int op, mp_obj_t o_in) { } } -mp_obj_t complex_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { +static mp_obj_t complex_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { mp_float_t lhs_real, lhs_imag, rhs_real, rhs_imag; mp_obj_complex_get(lhs_in, &lhs_real, &lhs_imag); mp_obj_complex_get(rhs_in, &rhs_real, &rhs_imag); @@ -79,6 +119,7 @@ const mp_obj_type_t complex_type = { { &mp_const_type }, "complex", complex_print, // print + complex_make_new, // make_new NULL, // call_n complex_unary_op, // unary_op complex_binary_op, // binary_op diff --git a/py/objdict.c b/py/objdict.c index acf1a9f801..3737f5eab0 100644 --- a/py/objdict.c +++ b/py/objdict.c @@ -17,7 +17,7 @@ typedef struct _mp_obj_dict_t { mp_map_t map; } mp_obj_dict_t; -void dict_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in) { +static void dict_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in) { mp_obj_dict_t *self = self_in; bool first = true; print(env, "{"); @@ -35,7 +35,13 @@ void dict_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_ob print(env, "}"); } -mp_obj_t dict_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { +// args are reverse in the array +static mp_obj_t dict_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + // TODO create from an iterable! + return rt_build_map(0); +} + +static mp_obj_t dict_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { mp_obj_dict_t *o = lhs_in; switch (op) { case RT_BINARY_OP_SUBSCR: @@ -58,6 +64,7 @@ const mp_obj_type_t dict_type = { { &mp_const_type }, "dict", dict_print, // print + dict_make_new, // make_new NULL, // call_n NULL, // unary_op dict_binary_op, // binary_op diff --git a/py/objexcept.c b/py/objexcept.c index e735852c37..ec03b9bf1a 100644 --- a/py/objexcept.c +++ b/py/objexcept.c @@ -39,6 +39,7 @@ const mp_obj_type_t exception_type = { { &mp_const_type }, "exception", exception_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objfloat.c b/py/objfloat.c index f151fe25a0..8fc925e0b6 100644 --- a/py/objfloat.c +++ b/py/objfloat.c @@ -6,6 +6,7 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" @@ -18,12 +19,30 @@ typedef struct _mp_obj_float_t { mp_obj_t mp_obj_new_float(mp_float_t value); -void float_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t o_in) { +static void float_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t o_in) { mp_obj_float_t *o = o_in; print(env, "%.8g", o->value); } -mp_obj_t float_unary_op(int op, mp_obj_t o_in) { +static mp_obj_t float_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + switch (n_args) { + case 0: + return mp_obj_new_float(0); + + case 1: + // TODO allow string as arg and parse it + if (MP_OBJ_IS_TYPE(args[0], &float_type)) { + return args[0]; + } else { + return mp_obj_new_float(mp_obj_get_float(args[0])); + } + + default: + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "float takes at most 1 argument, %d given", (void*)(machine_int_t)n_args)); + } +} + +static mp_obj_t float_unary_op(int op, mp_obj_t o_in) { mp_obj_float_t *o = o_in; switch (op) { case RT_UNARY_OP_NOT: if (o->value != 0) { return mp_const_true;} else { return mp_const_false; } @@ -33,7 +52,7 @@ mp_obj_t float_unary_op(int op, mp_obj_t o_in) { } } -mp_obj_t float_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { +static mp_obj_t float_binary_op(int op, mp_obj_t lhs_in, mp_obj_t rhs_in) { if (MP_OBJ_IS_TYPE(rhs_in, &complex_type)) { return complex_type.binary_op(op, lhs_in, rhs_in); } @@ -61,6 +80,7 @@ const mp_obj_type_t float_type = { { &mp_const_type }, "float", float_print, + float_make_new, // make_new NULL, // call_n float_unary_op, float_binary_op, diff --git a/py/objfun.c b/py/objfun.c index c4783867a5..22b82a9ca0 100644 --- a/py/objfun.c +++ b/py/objfun.c @@ -70,6 +70,7 @@ const mp_obj_type_t fun_native_type = { { &mp_const_type }, "function", NULL, // print + NULL, // make_new fun_native_call_n, // call_n NULL, // unary_op NULL, // binary_op @@ -162,6 +163,7 @@ const mp_obj_type_t fun_bc_type = { { &mp_const_type }, "function", NULL, // print + NULL, // make_new fun_bc_call_n, // call_n NULL, // unary_op NULL, // binary_op @@ -275,6 +277,7 @@ static const mp_obj_type_t fun_asm_type = { { &mp_const_type }, "function", NULL, // print + NULL, // make_new fun_asm_call_n, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objgenerator.c b/py/objgenerator.c index 849212269b..7fbca075e2 100644 --- a/py/objgenerator.c +++ b/py/objgenerator.c @@ -40,6 +40,7 @@ const mp_obj_type_t gen_wrap_type = { { &mp_const_type }, "generator", NULL, // print + NULL, // make_new gen_wrap_call_n, // call_n NULL, // unary_op NULL, // binary_op @@ -94,6 +95,7 @@ const mp_obj_type_t gen_instance_type = { { &mp_const_type }, "generator", gen_instance_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objinstance.c b/py/objinstance.c index 6cfcdf6c15..fd8cada7cb 100644 --- a/py/objinstance.c +++ b/py/objinstance.c @@ -93,6 +93,7 @@ const mp_obj_type_t instance_type = { { &mp_const_type }, "instance", NULL, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objlist.c b/py/objlist.c index 967df44fd6..3018826113 100644 --- a/py/objlist.c +++ b/py/objlist.c @@ -36,6 +36,29 @@ static void list_print(void (*print)(void *env, const char *fmt, ...), void *env print(env, "]"); } +static mp_obj_t list_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + switch (n_args) { + case 0: + // return a new, empty list + return rt_build_list(0, NULL); + + case 1: + { + // make list from iterable + mp_obj_t iterable = rt_getiter(args[0]); + mp_obj_t list = rt_build_list(0, NULL); + mp_obj_t item; + while ((item = rt_iternext(iterable)) != mp_const_stop_iteration) { + rt_list_append(list, item); + } + return list; + } + + default: + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "list takes at most 1 argument, %d given", (void*)(machine_int_t)n_args)); + } +} + static mp_obj_t list_binary_op(int op, mp_obj_t lhs, mp_obj_t rhs) { mp_obj_list_t *o = lhs; switch (op) { @@ -165,6 +188,7 @@ const mp_obj_type_t list_type = { { &mp_const_type }, "list", list_print, // print + list_make_new, // make_new NULL, // call_n NULL, // unary_op list_binary_op, // binary_op @@ -242,6 +266,7 @@ static const mp_obj_type_t list_it_type = { { &mp_const_type }, "list_iterator", NULL, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objmodule.c b/py/objmodule.c index addab14b75..9263eb44f0 100644 --- a/py/objmodule.c +++ b/py/objmodule.c @@ -25,6 +25,7 @@ const mp_obj_type_t module_type = { { &mp_const_type }, "module", module_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objnone.c b/py/objnone.c index f7b665e997..11dd4939b1 100644 --- a/py/objnone.c +++ b/py/objnone.c @@ -18,6 +18,7 @@ const mp_obj_type_t none_type = { { &mp_const_type }, "NoneType", none_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objrange.c b/py/objrange.c index b7fd17fa0a..b163f779b8 100644 --- a/py/objrange.c +++ b/py/objrange.c @@ -26,6 +26,7 @@ static const mp_obj_type_t range_type = { { &mp_const_type} , "range", NULL, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op @@ -70,6 +71,7 @@ static const mp_obj_type_t range_it_type = { { &mp_const_type }, "range_iterator", NULL, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objset.c b/py/objset.c index f225ca7f66..826f8bdc86 100644 --- a/py/objset.c +++ b/py/objset.c @@ -5,7 +5,9 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" +#include "runtime.h" #include "map.h" typedef struct _mp_obj_set_t { @@ -29,10 +31,34 @@ void set_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj print(env, "}"); } -static const mp_obj_type_t set_type = { +static mp_obj_t set_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + switch (n_args) { + case 0: + // return a new, empty set + return mp_obj_new_set(0, NULL); + + case 1: + { + // 1 argument, an iterable from which we make a new set + mp_obj_t set = mp_obj_new_set(0, NULL); + mp_obj_t iterable = rt_getiter(args[0]); + mp_obj_t item; + while ((item = rt_iternext(iterable)) != mp_const_stop_iteration) { + mp_obj_set_store(set, item); + } + return set; + } + + default: + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "set takes at most 1 argument, %d given", (void*)(machine_int_t)n_args)); + } +} + +const mp_obj_type_t set_type = { { &mp_const_type }, "set", set_print, // print + set_make_new, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objslice.c b/py/objslice.c index d99325fd73..a624be9631 100644 --- a/py/objslice.c +++ b/py/objslice.c @@ -24,6 +24,7 @@ const mp_obj_type_t ellipsis_type = { { &mp_const_type }, "ellipsis", ellipsis_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op @@ -58,6 +59,7 @@ const mp_obj_type_t slice_type = { "slice", slice_print, NULL, // call_n + NULL, // make_new NULL, // unary_op NULL, // binary_op NULL, // getiter diff --git a/py/objstr.c b/py/objstr.c index 03a761863f..27c9440d03 100644 --- a/py/objstr.c +++ b/py/objstr.c @@ -179,6 +179,7 @@ const mp_obj_type_t str_type = { { &mp_const_type }, "str", str_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op str_binary_op, // binary_op diff --git a/py/objtuple.c b/py/objtuple.c index b98d6ede7b..d55259d1a6 100644 --- a/py/objtuple.c +++ b/py/objtuple.c @@ -1,13 +1,14 @@ #include #include -//#include #include #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" #include "runtime0.h" +#include "runtime.h" typedef struct _mp_obj_tuple_t { mp_obj_base_t base; @@ -20,7 +21,7 @@ static mp_obj_t mp_obj_new_tuple_iterator(mp_obj_tuple_t *tuple, int cur); /******************************************************************************/ /* tuple */ -void tuple_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t o_in) { +static void tuple_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t o_in) { mp_obj_tuple_t *o = o_in; print(env, "("); for (int i = 0; i < o->len; i++) { @@ -35,7 +36,48 @@ void tuple_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_o print(env, ")"); } -mp_obj_t tuple_binary_op(int op, mp_obj_t lhs, mp_obj_t rhs) { +// args are in reverse order in the array +static mp_obj_t tuple_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + switch (n_args) { + case 0: + // return a empty tuple + return mp_const_empty_tuple; + + case 1: + { + // 1 argument, an iterable from which we make a new tuple + if (MP_OBJ_IS_TYPE(args[0], &tuple_type)) { + return args[0]; + } + + // TODO optimise for cases where we know the length of the iterator + + uint alloc = 4; + uint len = 0; + mp_obj_t *items = m_new(mp_obj_t, alloc); + + mp_obj_t iterable = rt_getiter(args[0]); + mp_obj_t item; + while ((item = rt_iternext(iterable)) != mp_const_stop_iteration) { + if (len >= alloc) { + items = m_renew(mp_obj_t, items, alloc, alloc * 2); + alloc *= 2; + } + items[len++] = item; + } + + mp_obj_t tuple = mp_obj_new_tuple(len, items); + m_free(items, alloc); + + return tuple; + } + + default: + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "tuple takes at most 1 argument, %d given", (void*)(machine_int_t)n_args)); + } +} + +static mp_obj_t tuple_binary_op(int op, mp_obj_t lhs, mp_obj_t rhs) { mp_obj_tuple_t *o = lhs; switch (op) { case RT_BINARY_OP_SUBSCR: @@ -50,20 +92,15 @@ mp_obj_t tuple_binary_op(int op, mp_obj_t lhs, mp_obj_t rhs) { } } -mp_obj_t tuple_getiter(mp_obj_t o_in) { +static mp_obj_t tuple_getiter(mp_obj_t o_in) { return mp_obj_new_tuple_iterator(o_in, 0); } -void mp_obj_tuple_get(mp_obj_t self_in, uint *len, mp_obj_t **items) { - mp_obj_tuple_t *self = self_in; - *len = self->len; - *items = &self->items[0]; -} - const mp_obj_type_t tuple_type = { { &mp_const_type }, "tuple", tuple_print, // print + tuple_make_new, // make_new NULL, // call_n NULL, // unary_op tuple_binary_op, // binary_op @@ -72,7 +109,14 @@ const mp_obj_type_t tuple_type = { {{NULL, NULL},}, // method list }; +// the zero-length tuple +static const mp_obj_tuple_t empty_tuple_obj = {{&tuple_type}, 0}; +const mp_obj_t mp_const_empty_tuple = (mp_obj_t)&empty_tuple_obj; + mp_obj_t mp_obj_new_tuple(uint n, mp_obj_t *items) { + if (n == 0) { + return mp_const_empty_tuple; + } mp_obj_tuple_t *o = m_new_obj_var(mp_obj_tuple_t, mp_obj_t, n); o->base.type = &tuple_type; o->len = n; @@ -83,6 +127,9 @@ mp_obj_t mp_obj_new_tuple(uint n, mp_obj_t *items) { } mp_obj_t mp_obj_new_tuple_reverse(uint n, mp_obj_t *items) { + if (n == 0) { + return mp_const_empty_tuple; + } mp_obj_tuple_t *o = m_new_obj_var(mp_obj_tuple_t, mp_obj_t, n); o->base.type = &tuple_type; o->len = n; @@ -92,6 +139,12 @@ mp_obj_t mp_obj_new_tuple_reverse(uint n, mp_obj_t *items) { return o; } +void mp_obj_tuple_get(mp_obj_t self_in, uint *len, mp_obj_t **items) { + mp_obj_tuple_t *self = self_in; + *len = self->len; + *items = &self->items[0]; +} + /******************************************************************************/ /* tuple iterator */ @@ -101,7 +154,7 @@ typedef struct _mp_obj_tuple_it_t { machine_uint_t cur; } mp_obj_tuple_it_t; -mp_obj_t tuple_it_iternext(mp_obj_t self_in) { +static mp_obj_t tuple_it_iternext(mp_obj_t self_in) { mp_obj_tuple_it_t *self = self_in; if (self->cur < self->tuple->len) { mp_obj_t o_out = self->tuple->items[self->cur]; @@ -116,6 +169,7 @@ static const mp_obj_type_t tuple_it_type = { { &mp_const_type }, "tuple_iterator", NULL, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/py/objtype.c b/py/objtype.c index 83ae48d2d1..aeeaebb95d 100644 --- a/py/objtype.c +++ b/py/objtype.c @@ -4,17 +4,30 @@ #include "nlr.h" #include "misc.h" #include "mpconfig.h" +#include "mpqstr.h" #include "obj.h" -void type_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in) { - print(env, ""); +static void type_print(void (*print)(void *env, const char *fmt, ...), void *env, mp_obj_t self_in) { + mp_obj_type_t *self = self_in; + print(env, "", self->name); +} + +static mp_obj_t type_call_n(mp_obj_t self_in, int n_args, const mp_obj_t *args) { + mp_obj_type_t *self = self_in; + if (self->make_new != NULL) { + // TODO we need to init the object if it's an instance of a type + return self->make_new(self, n_args, args); + } else { + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "cannot create '%s' instances", self->name)); + } } const mp_obj_type_t mp_const_type = { { &mp_const_type }, - "", + "type", type_print, // print - NULL, // call_n + NULL, // make_new + type_call_n, // call_n NULL, // unary_op NULL, // binary_op NULL, // getiter diff --git a/py/runtime.c b/py/runtime.c index 72881067d4..197c08b55a 100644 --- a/py/runtime.c +++ b/py/runtime.c @@ -91,26 +91,31 @@ void rt_init(void) { mp_qstr_map_lookup(&map_builtins, MP_QSTR___build_class__, true)->value = rt_make_function_2(mp_builtin___build_class__); mp_qstr_map_lookup(&map_builtins, MP_QSTR___repl_print__, true)->value = rt_make_function_1(mp_builtin___repl_print__); - // built-in user functions + // built-in types + mp_qstr_map_lookup(&map_builtins, MP_QSTR_bool, true)->value = (mp_obj_t)&bool_type; +#if MICROPY_ENABLE_FLOAT + mp_qstr_map_lookup(&map_builtins, MP_QSTR_complex, true)->value = (mp_obj_t)&complex_type; +#endif + mp_qstr_map_lookup(&map_builtins, MP_QSTR_dict, true)->value = (mp_obj_t)&dict_type; +#if MICROPY_ENABLE_FLOAT + mp_qstr_map_lookup(&map_builtins, MP_QSTR_float, true)->value = (mp_obj_t)&float_type; +#endif + mp_qstr_map_lookup(&map_builtins, MP_QSTR_int, true)->value = (mp_obj_t)&int_type; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_list, true)->value = (mp_obj_t)&list_type; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_set, true)->value = (mp_obj_t)&set_type; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_tuple, true)->value = (mp_obj_t)&tuple_type; + mp_qstr_map_lookup(&map_builtins, MP_QSTR_type, true)->value = (mp_obj_t)&mp_builtin_type_obj; // TODO + + // built-in user functions; TODO covert all to &mp_builtin_xxx's mp_qstr_map_lookup(&map_builtins, MP_QSTR_abs, true)->value = rt_make_function_1(mp_builtin_abs); mp_qstr_map_lookup(&map_builtins, MP_QSTR_all, true)->value = rt_make_function_1(mp_builtin_all); mp_qstr_map_lookup(&map_builtins, MP_QSTR_any, true)->value = rt_make_function_1(mp_builtin_any); - mp_qstr_map_lookup(&map_builtins, MP_QSTR_bool, true)->value = rt_make_function_var(0, mp_builtin_bool); mp_qstr_map_lookup(&map_builtins, MP_QSTR_callable, true)->value = rt_make_function_1(mp_builtin_callable); mp_qstr_map_lookup(&map_builtins, MP_QSTR_chr, true)->value = rt_make_function_1(mp_builtin_chr); -#if MICROPY_ENABLE_FLOAT - mp_qstr_map_lookup(&map_builtins, MP_QSTR_complex, true)->value = (mp_obj_t)&mp_builtin_complex_obj; -#endif - mp_qstr_map_lookup(&map_builtins, MP_QSTR_dict, true)->value = rt_make_function_0(mp_builtin_dict); mp_qstr_map_lookup(&map_builtins, MP_QSTR_divmod, true)->value = rt_make_function_2(mp_builtin_divmod); -#if MICROPY_ENABLE_FLOAT - mp_qstr_map_lookup(&map_builtins, MP_QSTR_float, true)->value = (mp_obj_t)&mp_builtin_float_obj; -#endif mp_qstr_map_lookup(&map_builtins, MP_QSTR_hash, true)->value = (mp_obj_t)&mp_builtin_hash_obj; - mp_qstr_map_lookup(&map_builtins, MP_QSTR_int, true)->value = (mp_obj_t)&mp_builtin_int_obj; mp_qstr_map_lookup(&map_builtins, MP_QSTR_iter, true)->value = (mp_obj_t)&mp_builtin_iter_obj; mp_qstr_map_lookup(&map_builtins, MP_QSTR_len, true)->value = rt_make_function_1(mp_builtin_len); - mp_qstr_map_lookup(&map_builtins, MP_QSTR_list, true)->value = rt_make_function_var(0, mp_builtin_list); mp_qstr_map_lookup(&map_builtins, MP_QSTR_max, true)->value = rt_make_function_var(1, mp_builtin_max); mp_qstr_map_lookup(&map_builtins, MP_QSTR_min, true)->value = rt_make_function_var(1, mp_builtin_min); mp_qstr_map_lookup(&map_builtins, MP_QSTR_next, true)->value = (mp_obj_t)&mp_builtin_next_obj; @@ -118,9 +123,7 @@ void rt_init(void) { mp_qstr_map_lookup(&map_builtins, MP_QSTR_pow, true)->value = rt_make_function_var(2, mp_builtin_pow); mp_qstr_map_lookup(&map_builtins, MP_QSTR_print, true)->value = rt_make_function_var(0, mp_builtin_print); mp_qstr_map_lookup(&map_builtins, MP_QSTR_range, true)->value = rt_make_function_var(1, mp_builtin_range); - mp_qstr_map_lookup(&map_builtins, MP_QSTR_set, true)->value = (mp_obj_t)&mp_builtin_set_obj; mp_qstr_map_lookup(&map_builtins, MP_QSTR_sum, true)->value = rt_make_function_var(1, mp_builtin_sum); - mp_qstr_map_lookup(&map_builtins, MP_QSTR_type, true)->value = (mp_obj_t)&mp_builtin_type_obj; next_unique_code_id = 1; // 0 indicates "no code" unique_codes = NULL; diff --git a/stm/Makefile b/stm/Makefile index 729913baee..d75c945bfc 100644 --- a/stm/Makefile +++ b/stm/Makefile @@ -73,6 +73,7 @@ PY_O = \ objfun.o \ objgenerator.o \ objinstance.o \ + objint.o \ objlist.o \ objmodule.o \ objnone.o \ diff --git a/stm/i2c.c b/stm/i2c.c index e00cf41309..3f29f02c0c 100644 --- a/stm/i2c.c +++ b/stm/i2c.c @@ -330,6 +330,7 @@ static const mp_obj_type_t i2c_obj_type = { { &mp_const_type }, "I2C", i2c_obj_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/stm/led.c b/stm/led.c index 08077641a9..9305716be9 100644 --- a/stm/led.c +++ b/stm/led.c @@ -108,6 +108,7 @@ static const mp_obj_type_t led_obj_type = { { &mp_const_type }, "Led", led_obj_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/stm/main.c b/stm/main.c index b7ae8aacca..0ab44ca8d4 100644 --- a/stm/main.c +++ b/stm/main.c @@ -746,6 +746,7 @@ static const mp_obj_type_t file_obj_type = { { &mp_const_type }, "File", file_obj_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/stm/servo.c b/stm/servo.c index ae421048b9..1e31db5140 100644 --- a/stm/servo.c +++ b/stm/servo.c @@ -141,6 +141,7 @@ static const mp_obj_type_t servo_obj_type = { { &mp_const_type }, "Servo", servo_obj_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op diff --git a/unix-cpy/Makefile b/unix-cpy/Makefile index 7fee3438fb..a1eb9b77e4 100644 --- a/unix-cpy/Makefile +++ b/unix-cpy/Makefile @@ -38,6 +38,7 @@ PY_O = \ objfun.o \ objgenerator.o \ objinstance.o \ + objint.o \ objlist.o \ objmodule.o \ objnone.o \ diff --git a/unix/Makefile b/unix/Makefile index c7be62e999..984f1c3bf3 100644 --- a/unix/Makefile +++ b/unix/Makefile @@ -45,6 +45,7 @@ PY_O = \ objfun.o \ objgenerator.o \ objinstance.o \ + objint.o \ objlist.o \ objmodule.o \ objnone.o \ diff --git a/unix/main.c b/unix/main.c index ecb2fa338e..16fcf6ef8d 100644 --- a/unix/main.c +++ b/unix/main.c @@ -192,6 +192,7 @@ static const mp_obj_type_t test_type = { { &mp_const_type }, "Test", test_print, // print + NULL, // make_new NULL, // call_n NULL, // unary_op NULL, // binary_op From 8b2688f893951e93428a91ad8db30b19343febc9 Mon Sep 17 00:00:00 2001 From: Damien George Date: Sat, 4 Jan 2014 23:47:11 +0000 Subject: [PATCH 28/29] Add FONT-LICENSE for Exo font used in Micro Python name-logo. --- logo/FONT-LICENSE.txt | 97 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 97 insertions(+) create mode 100644 logo/FONT-LICENSE.txt diff --git a/logo/FONT-LICENSE.txt b/logo/FONT-LICENSE.txt new file mode 100644 index 0000000000..daa919c440 --- /dev/null +++ b/logo/FONT-LICENSE.txt @@ -0,0 +1,97 @@ +The font used for the Micro Python logo is "Exo", +http://www.google.com/fonts/specimen/Exo. + +Copyright (c) 2013, Natanael Gama (https://plus.google.com/u/0/+NatanaelGama), +with Reserved Font Name Exo. + +This Font Software is licensed under the SIL Open Font License, Version 1.1. +This license is copied below, and is also available with a FAQ at: +http://scripts.sil.org/OFL + + +----------------------------------------------------------- +SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007 +----------------------------------------------------------- + +PREAMBLE +The goals of the Open Font License (OFL) are to stimulate worldwide +development of collaborative font projects, to support the font creation +efforts of academic and linguistic communities, and to provide a free and +open framework in which fonts may be shared and improved in partnership +with others. + +The OFL allows the licensed fonts to be used, studied, modified and +redistributed freely as long as they are not sold by themselves. The +fonts, including any derivative works, can be bundled, embedded, +redistributed and/or sold with any software provided that any reserved +names are not used by derivative works. The fonts and derivatives, +however, cannot be released under any other type of license. The +requirement for fonts to remain under this license does not apply +to any document created using the fonts or their derivatives. + +DEFINITIONS +"Font Software" refers to the set of files released by the Copyright +Holder(s) under this license and clearly marked as such. This may +include source files, build scripts and documentation. + +"Reserved Font Name" refers to any names specified as such after the +copyright statement(s). + +"Original Version" refers to the collection of Font Software components as +distributed by the Copyright Holder(s). + +"Modified Version" refers to any derivative made by adding to, deleting, +or substituting -- in part or in whole -- any of the components of the +Original Version, by changing formats or by porting the Font Software to a +new environment. + +"Author" refers to any designer, engineer, programmer, technical +writer or other person who contributed to the Font Software. + +PERMISSION & CONDITIONS +Permission is hereby granted, free of charge, to any person obtaining +a copy of the Font Software, to use, study, copy, merge, embed, modify, +redistribute, and sell modified and unmodified copies of the Font +Software, subject to the following conditions: + +1) Neither the Font Software nor any of its individual components, +in Original or Modified Versions, may be sold by itself. + +2) Original or Modified Versions of the Font Software may be bundled, +redistributed and/or sold with any software, provided that each copy +contains the above copyright notice and this license. These can be +included either as stand-alone text files, human-readable headers or +in the appropriate machine-readable metadata fields within text or +binary files as long as those fields can be easily viewed by the user. + +3) No Modified Version of the Font Software may use the Reserved Font +Name(s) unless explicit written permission is granted by the corresponding +Copyright Holder. This restriction only applies to the primary font name as +presented to the users. + +4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font +Software shall not be used to promote, endorse or advertise any +Modified Version, except to acknowledge the contribution(s) of the +Copyright Holder(s) and the Author(s) or with their explicit written +permission. + +5) The Font Software, modified or unmodified, in part or in whole, +must be distributed entirely under this license, and must not be +distributed under any other license. The requirement for fonts to +remain under this license does not apply to any document created +using the Font Software. + +TERMINATION +This license becomes null and void if any of the above conditions are +not met. + +DISCLAIMER +THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF +MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT +OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE +COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, +INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL +DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM +OTHER DEALINGS IN THE FONT SOFTWARE. From 45b43c21c4f8e30dcff00c2429eddba20ca002aa Mon Sep 17 00:00:00 2001 From: Damien George Date: Sun, 5 Jan 2014 01:50:45 +0000 Subject: [PATCH 29/29] Oops: add objint.c --- py/objint.c | 48 ++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 48 insertions(+) create mode 100644 py/objint.c diff --git a/py/objint.c b/py/objint.c new file mode 100644 index 0000000000..5bc747e8f0 --- /dev/null +++ b/py/objint.c @@ -0,0 +1,48 @@ +#include +#include +#include +#include + +#include "nlr.h" +#include "misc.h" +#include "mpconfig.h" +#include "mpqstr.h" +#include "obj.h" + +typedef struct _mp_obj_int_t { + mp_obj_base_t base; +} mp_obj_int_t; + +static mp_obj_t int_make_new(mp_obj_t type_in, int n_args, const mp_obj_t *args) { + switch (n_args) { + case 0: + return MP_OBJ_NEW_SMALL_INT(0); + + case 1: + // TODO allow string as arg and parse it + return MP_OBJ_NEW_SMALL_INT(mp_obj_get_int(args[0])); + + //case 2: + // TODO, parse with given base + + default: + nlr_jump(mp_obj_new_exception_msg_1_arg(MP_QSTR_TypeError, "int takes at most 2 arguments, %d given", (void*)(machine_int_t)n_args)); + } +} + +const mp_obj_type_t int_type = { + { &mp_const_type }, + "int", + NULL, + int_make_new, // make_new + NULL, // call_n + NULL, // unary_op + NULL, // binary_op + NULL, // getiter + NULL, // iternext + { { NULL, NULL }, }, // method list +}; + +mp_obj_t mp_obj_new_int(machine_int_t value) { + return MP_OBJ_NEW_SMALL_INT(value); +}