summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAyke van Laethem <aykevanlaethem@gmail.com>2018-01-27 18:37:38 +0100
committerDamien George <damien.p.george@gmail.com>2018-02-19 15:58:49 +1100
commitea7cf2b738c3b103b472547500fb0107b956fc0c (patch)
tree982e88b05505162de1b663f42bb3fab39c1b6479
parenta3e01d3642d6c287bf2d0c14b3d75bf305327819 (diff)
py/gc: Reduce code size by specialising VERIFY_MARK_AND_PUSH macro.
This macro is written out explicitly in the two locations that it is used and then the code is optimised, opening possibilities for further optimisations and reducing code size: unix: -48 minimal CROSS=1: -32 stm32: -32
-rw-r--r--py/gc.c46
1 files changed, 25 insertions, 21 deletions
diff --git a/py/gc.c b/py/gc.c
index 5196954e2..9089a26be 100644
--- a/py/gc.c
+++ b/py/gc.c
@@ -203,24 +203,6 @@ bool gc_is_locked(void) {
#endif
#endif
-// ptr should be of type void*
-#define VERIFY_MARK_AND_PUSH(ptr) \
- do { \
- if (VERIFY_PTR(ptr)) { \
- size_t _block = BLOCK_FROM_PTR(ptr); \
- if (ATB_GET_KIND(_block) == AT_HEAD) { \
- /* an unmarked head, mark it, and push it on gc stack */ \
- TRACE_MARK(_block, ptr); \
- ATB_HEAD_TO_MARK(_block); \
- if (MP_STATE_MEM(gc_sp) < &MP_STATE_MEM(gc_stack)[MICROPY_ALLOC_GC_STACK_SIZE]) { \
- *MP_STATE_MEM(gc_sp)++ = _block; \
- } else { \
- MP_STATE_MEM(gc_stack_overflow) = 1; \
- } \
- } \
- } \
- } while (0)
-
STATIC void gc_drain_stack(void) {
while (MP_STATE_MEM(gc_sp) > MP_STATE_MEM(gc_stack)) {
// pop the next block off the stack
@@ -236,7 +218,20 @@ STATIC void gc_drain_stack(void) {
void **ptrs = (void**)PTR_FROM_BLOCK(block);
for (size_t i = n_blocks * BYTES_PER_BLOCK / sizeof(void*); i > 0; i--, ptrs++) {
void *ptr = *ptrs;
- VERIFY_MARK_AND_PUSH(ptr);
+ if (VERIFY_PTR(ptr)) {
+ // Mark and push this pointer
+ size_t childblock = BLOCK_FROM_PTR(ptr);
+ if (ATB_GET_KIND(childblock) == AT_HEAD) {
+ // an unmarked head, mark it, and push it on gc stack
+ TRACE_MARK(childblock, ptr);
+ ATB_HEAD_TO_MARK(childblock);
+ if (MP_STATE_MEM(gc_sp) < &MP_STATE_MEM(gc_stack)[MICROPY_ALLOC_GC_STACK_SIZE]) {
+ *MP_STATE_MEM(gc_sp)++ = childblock;
+ } else {
+ MP_STATE_MEM(gc_stack_overflow) = 1;
+ }
+ }
+ }
}
}
}
@@ -337,8 +332,17 @@ void gc_collect_start(void) {
void gc_collect_root(void **ptrs, size_t len) {
for (size_t i = 0; i < len; i++) {
void *ptr = ptrs[i];
- VERIFY_MARK_AND_PUSH(ptr);
- gc_drain_stack();
+ if (VERIFY_PTR(ptr)) {
+ // Mark and push this pointer
+ size_t block = BLOCK_FROM_PTR(ptr);
+ if (ATB_GET_KIND(block) == AT_HEAD) {
+ // an unmarked head, mark it, and push it on gc stack
+ TRACE_MARK(block, ptr);
+ ATB_HEAD_TO_MARK(block);
+ *MP_STATE_MEM(gc_sp)++ = block;
+ gc_drain_stack();
+ }
+ }
}
}