summaryrefslogtreecommitdiffstatshomepage
path: root/py
diff options
context:
space:
mode:
Diffstat (limited to 'py')
-rw-r--r--py/obj.h5
-rw-r--r--py/objlist.c19
2 files changed, 19 insertions, 5 deletions
diff --git a/py/obj.h b/py/obj.h
index 5f2b9d3bef..611873d2ea 100644
--- a/py/obj.h
+++ b/py/obj.h
@@ -578,3 +578,8 @@ mp_obj_t mp_seq_count_obj(const mp_obj_t *items, uint len, mp_obj_t value);
memcpy(dest + beg, slice, slice_len * sizeof(item_t)); \
/*printf("memcpy(%p, %p, %d)\n", dest + (beg + slice_len), dest + end, (dest_len - end) * sizeof(item_t));*/ \
memcpy(dest + (beg + slice_len), dest + end, (dest_len - end) * sizeof(item_t));
+
+#define mp_seq_replace_slice_grow_inplace(dest, dest_len, beg, end, slice, slice_len, len_adj, item_t) \
+ /*printf("memmove(%p, %p, %d)\n", dest + beg + len_adj, dest + beg, (dest_len - beg) * sizeof(item_t));*/ \
+ memmove(dest + beg + len_adj, dest + beg, (dest_len - beg) * sizeof(item_t)); \
+ memcpy(dest + beg, slice, slice_len * sizeof(item_t));
diff --git a/py/objlist.c b/py/objlist.c
index 7a15006adf..7d9f56d2e4 100644
--- a/py/objlist.c
+++ b/py/objlist.c
@@ -199,12 +199,21 @@ STATIC mp_obj_t list_subscr(mp_obj_t self_in, mp_obj_t index, mp_obj_t value) {
}
int len_adj = slice->len - (stop - start);
//printf("Len adj: %d\n", len_adj);
- assert(len_adj <= 0);
- mp_seq_replace_slice_no_grow(self->items, self->len, start, stop, slice->items, slice->len, mp_obj_t);
- // Clear "freed" elements at the end of list
- mp_seq_clear(self->items, self->len + len_adj, self->len, sizeof(*self->items));
+ if (len_adj > 0) {
+ if (self->len + len_adj > self->alloc) {
+ // TODO: Might optimize memory copies here by checking if block can
+ // be grown inplace or not
+ self->items = m_renew(mp_obj_t, self->items, self->alloc, self->len + len_adj);
+ self->alloc = self->len + len_adj;
+ }
+ mp_seq_replace_slice_grow_inplace(self->items, self->len, start, stop, slice->items, slice->len, len_adj, mp_obj_t);
+ } else {
+ mp_seq_replace_slice_no_grow(self->items, self->len, start, stop, slice->items, slice->len, mp_obj_t);
+ // Clear "freed" elements at the end of list
+ mp_seq_clear(self->items, self->len + len_adj, self->len, sizeof(*self->items));
+ // TODO: apply allocation policy re: alloc_size
+ }
self->len += len_adj;
- // TODO: apply allocation policy re: alloc_size
return mp_const_none;
}
#endif