Sparkling icon indicating copy to clipboard operation
Sparkling copied to clipboard

Possible leak in vm

Open tarkin000 opened this issue 7 years ago • 1 comments

Hello, I am seeing a leak of 24 bytes with with the context convenience API.

Valgrind output:

==24387== Command: ./leak 123
==24387==
123
==24387==
==24387== HEAP SUMMARY:
==24387==     in use at exit: 8,384 bytes in 126 blocks
==24387==   total heap usage: 24,625 allocs, 24,499 frees, 1,129,725 bytes allocated
==24387==
==24387== 8,384 (24 direct, 8,360 indirect) bytes in 1 blocks are definitely lost in loss record 8 of 8
==24387==    at 0x4028308: malloc (vg_replace_malloc.c:263)
==24387==    by 0x804DA52: spn_malloc (misc.c:30)
==24387==    by 0x8049B8B: spn_object_new (api.c:99)
==24387==    by 0x804CFF2: spn_hashmap_new (hashmap.c:101)
==24387==    by 0x804D09D: spn_makehashmap (hashmap.c:124)
==24387==    by 0x80621AC: dispatch_loop (vm.c:1427)
==24387==    by 0x805F563: spn_vm_callfunc (vm.c:444)
==24387==    by 0x804BD12: spn_ctx_callfunc (ctx.c:270)
==24387==    by 0x804BBF1: spn_ctx_execsrcfile (ctx.c:241)
==24387==    by 0x804C0A7: spn_ctx_load_script_stdlib (ctx.c:380)
==24387==    by 0x804B5FA: spn_ctx_init (ctx.c:40)
==24387==    by 0x80498C5: main (leak.c:19)
==24387==
==24387== LEAK SUMMARY:
==24387==    definitely lost: 24 bytes in 1 blocks
==24387==    indirectly lost: 8,360 bytes in 125 blocks
==24387==      possibly lost: 0 bytes in 0 blocks
==24387==    still reachable: 0 bytes in 0 blocks
==24387==         suppressed: 0 bytes in 0 blocks 

Test case:

#include <stdio.h>
#include "spn.h"

int main(int argc, char *argv[]) {
  SpnContext ctx;
  SpnValue rv;
  char buf[BUFSIZ] = {0};

  if (argc == 1) {
    puts("Must supply a spn exression string argument");
    return 1;
  }
  snprintf(buf,(BUFSIZ - 1),"let x = %s; print(x);",argv[1]);
  spn_ctx_init(&ctx);
  if (spn_ctx_execstring(&ctx,buf,&rv)) {
    printf("failed: %s\n",spn_ctx_geterrmsg(&ctx));
  } else {
    spn_value_release(&rv);
  }
  spn_ctx_free(&ctx);
  return 0;
}

spn_ctx_execsrcfile() does the same, and although I didn't test them, I assume that spn_ctx_execobjfile(), and spn_ctx_compile_*() will, too, because spn_ctx_init() calls spn_ctx_load_script_stdlib(), which is the real culprit.

If you do everything that the context convenience API does, except load the Sparkling libraries, you get no leak, as demonstrated by: noleak.c

I think that the HashMap allocated at the top of ast_validator.spn is never free'd,

tarkin000 avatar Feb 14 '17 06:02 tarkin000

Hi!

Yes, that's a correct observation. This is a known issue with Sparkling. Since the VM uses reference counting for memory management, circular references currently cause a leak — and the standard library contains some of those.

I didn't have time to fix this issue yet, but it's one of the priorities being considered.

H2CO3 avatar Feb 14 '17 08:02 H2CO3