guile-commits
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Guile-commits] 186/437: Add code to release all memory used by the jit


From: Andy Wingo
Subject: [Guile-commits] 186/437: Add code to release all memory used by the jit state.
Date: Mon, 2 Jul 2018 05:14:14 -0400 (EDT)

wingo pushed a commit to branch lightning
in repository guile.

commit 8f020fe0442a92a92119fdce6b15f7ba20008434
Author: pcpa <address@hidden>
Date:   Mon Feb 11 15:51:55 2013 -0200

    Add code to release all memory used by the jit state.
    
        * include/lightning.h, lib/lightning.c: Implement the new
        jit_clear_state and jit_destroy_state calls. jit_clear_state
        releases all memory not required during jit_execution; that
        is, leaves only the mmap'ed data and code buffers allocated.
        jit_destroy_state releases the mmap'ed buffers as well as
        the jit_state_t object itself, that holds pointers to the
        code and data buffers, as well as annotation pointers (for
        disassembly or backtrace) in the data buffer.
    
        * lib/jit_note.c: Correct invalid vector offset access.
    
        * check/ccall.c, check/lightning.c, doc/ifib.c, doc/incr.c,
        doc/printf.c, doc/rfib.c, doc/rpn.c: Use the new jit_clear_state
        and jit_destroy_state calls, to demonstrate the new code to
        release all jit memory.
    
        * doc/body.texi: Add basic documentation and usage description
        of jit_clear_state and jit_destroy_state.
---
 ChangeLog           | 21 ++++++++++++++++++
 check/ccall.c       |  4 ++++
 check/lightning.c   | 11 +++++++--
 doc/body.texi       | 24 ++++++++++++++++++++
 doc/ifib.c          |  2 ++
 doc/incr.c          |  2 ++
 doc/printf.c        |  2 ++
 doc/rfib.c          |  2 ++
 doc/rpn.c           |  2 ++
 include/lightning.h |  4 ++++
 lib/jit_note.c      |  4 ++--
 lib/lightning.c     | 64 +++++++++++++++++++++++++++++++++++++++++++++++++++++
 12 files changed, 138 insertions(+), 4 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index c02440d..5d8ac84 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,26 @@
 2013-02-11 Paulo Andrade <address@hidden>
 
+       * include/lightning.h, lib/lightning.c: Implement the new
+       jit_clear_state and jit_destroy_state calls. jit_clear_state
+       releases all memory not required during jit_execution; that
+       is, leaves only the mmap'ed data and code buffers allocated.
+       jit_destroy_state releases the mmap'ed buffers as well as
+       the jit_state_t object itself, that holds pointers to the
+       code and data buffers, as well as annotation pointers (for
+       disassembly or backtrace) in the data buffer.
+
+       * lib/jit_note.c: Correct invalid vector offset access.
+
+       * check/ccall.c, check/lightning.c, doc/ifib.c, doc/incr.c,
+       doc/printf.c, doc/rfib.c, doc/rpn.c: Use the new jit_clear_state
+       and jit_destroy_state calls, to demonstrate the new code to
+       release all jit memory.
+
+       * doc/body.texi: Add basic documentation and usage description
+       of jit_clear_state and jit_destroy_state.
+
+2013-02-11 Paulo Andrade <address@hidden>
+
        * include/lightning/jit_private.h, lib/jit_note.c, lib/lightning.c:
          Store all annotation information in the mmap'ed area reserved for
        read only data. This adds code to not allocate memory for jit_note_t
diff --git a/check/ccall.c b/check/ccall.c
index ac44cb6..14ae7cf 100644
--- a/check/ccall.c
+++ b/check/ccall.c
@@ -890,7 +890,11 @@ main(int argc, char *argv[])
     jit_print();
     jit_disassemble();
 #endif
+
+    jit_clear_state();
     (*function)();
+    jit_destroy_state();
+
     finish_jit();
 
     printf("ok\n");
diff --git a/check/lightning.c b/check/lightning.c
index 9722011..58bca38 100644
--- a/check/lightning.c
+++ b/check/lightning.c
@@ -3542,6 +3542,7 @@ parse(void)
 static int
 execute(int argc, char *argv[])
 {
+    int                 result;
     label_t    *label;
     function_t  function;
     patch_t    *patch, *next;
@@ -3573,9 +3574,15 @@ execute(int argc, char *argv[])
        jit_disassemble();
        fprintf(stdout, "  - - - - - - - - - - - - - - - - - - - - - - - - - - 
- - - - - - - - - - - -\n");
     }
+
+    jit_clear_state();
     if (flag_disasm)
-       return (0);
-    return ((*function)(argc, argv));
+       result = 0;
+    else
+       result = (*function)(argc, argv);
+    jit_destroy_state();
+
+    return (result);
 }
 
 static void *
diff --git a/doc/body.texi b/doc/body.texi
index 1c14544..3eef13b 100644
--- a/doc/body.texi
+++ b/doc/body.texi
@@ -615,10 +615,12 @@ int main(int argc, char *argv[])
   jit_retr(JIT_R0);                @rem{/* @t{     retr   R0          } */}
 
   incr = jit_emit();
+  jit_clear_state();
 
   @rem{/* call the generated address@hidden passing 5 as an argument */}
   printf("%d + 1 = %d\n", 5, incr(5));
 
+  jit_destroy_state();
   finish_jit();
   return 0;
 @}
@@ -682,11 +684,21 @@ This instruction is very important.  It actually 
translates the
 code area out of the processor's instruction cache and return a
 pointer to the start of the code.
 
address@hidden jit_clear_state();
+This call cleanups any data not required for jit execution. Note
+that it must be called after any call to @code{jit_print} or
address@hidden, as this call destroy the @lightning{}
+intermediate representation.
+
 @item printf("%d + 1 = %d", 5, incr(5));
 Calling our function is this simple---it is not distinguishable from
 a normal C function call, the only difference being that @code{incr}
 is a variable.
 
address@hidden jit_destroy_state();
+Releases all memory associated with the jit context. It should be
+called after known the jit will no longer be called.
+
 @item finish_jit();
 This call cleanups any global state hold by @lightning{}, and is
 advisable to call it once jit code will no longer be generated.
@@ -765,6 +777,7 @@ int main(int argc, char *argv[])
 
   @rem{/* call the generated address@hidden passing its size as argument */}
   myFunction((char*)jit_address(end) - (char*)jit_address(start));
+  jit_clear_state();
 
   jit_disassemble();
 
@@ -822,6 +835,11 @@ call must be done after the @code{emit} call or either a 
fatal error
 will happen (if @lightning{} is built with assertions enable) or an
 undefined value will be returned.
 
address@hidden jit_clear_state();
+Note that @code{jit_clear_state} was called after executing jit in
+this example. It was done because it must be called after any call
+to @code{jit_address} or @code{jit_print}.
+
 @item jit_disassemble();
 @code{disassemble} will dump the generated code to standard output,
 unless @lightning{} was built with the disassembler disabled, in which
@@ -948,6 +966,7 @@ int main(int argc, char *argv[])
   (void)jit_emit();
   c2f = (pifi)jit_address(nc);
   f2c = (pifi)jit_address(nf);
+  jit_clear_state();
 
   printf("\nC:");
   for (i = 0; i <= 100; i += 10) printf("%3d ", i);
@@ -961,6 +980,7 @@ int main(int argc, char *argv[])
   for (i = 32; i <= 212; i += 18) printf("%3d ", f2c(i));
   printf("\n");
 
+  jit_destroy_state();
   finish_jit();
   return 0;
 @}
@@ -1049,7 +1069,9 @@ int main(int argc, char *argv[])
 
   @rem{/* call the generated address@hidden passing 32 as an argument */}
   fib = jit_emit();
+  jit_clear_state();
   printf("fib(%d) = %d\n", 32, fib(32));
+  jit_destroy_state();
   finish_jit();
   return 0;
 @}
@@ -1117,7 +1139,9 @@ int main(int argc, char *argv[])
 
   @rem{/* call the generated address@hidden passing 36 as an argument */}
   fib = jit_emit();
+  jit_clear_state();
   printf("fib(%d) = %d\n", 36, fib(36));
+  jit_destroy_state();
   finish_jit();
   return 0;
 @}
diff --git a/doc/ifib.c b/doc/ifib.c
index 7e098cb..769e4a9 100644
--- a/doc/ifib.c
+++ b/doc/ifib.c
@@ -38,7 +38,9 @@ int main(int argc, char *argv[])
 
   /* call the generated code, passing 36 as an argument */
   fib = jit_emit();
+  jit_clear_state();
   printf("fib(%d) = %d\n", 36, fib(36));
+  jit_destroy_state();
   finish_jit();
   return 0;
 }
diff --git a/doc/incr.c b/doc/incr.c
index 5d5e438..88859a8 100644
--- a/doc/incr.c
+++ b/doc/incr.c
@@ -20,10 +20,12 @@ int main(int argc, char *argv[])
   jit_retr(JIT_R0);                /* @t{     retr   R0          } */
 
   incr = jit_emit();
+  jit_clear_state();
 
   /* call the generated code\, passing 5 as an argument */
   printf("%d + 1 = %d\n", 5, incr(5));
 
+  jit_destroy_state();
   finish_jit();
   return 0;
 }
diff --git a/doc/printf.c b/doc/printf.c
index 52bd2aa..8548541 100644
--- a/doc/printf.c
+++ b/doc/printf.c
@@ -30,9 +30,11 @@ int main(int argc, char *argv[])
 
   /* call the generated code, passing its size as argument */
   myFunction((char*)jit_address(end) - (char*)jit_address(start));
+  jit_clear_state();
 
   jit_disassemble();
 
+  jit_destroy_state();
   finish_jit();
   return 0;
 }
diff --git a/doc/rfib.c b/doc/rfib.c
index 1ce02d5..97d74f6 100644
--- a/doc/rfib.c
+++ b/doc/rfib.c
@@ -43,7 +43,9 @@ int main(int argc, char *argv[])
 
   /* call the generated code, passing 32 as an argument */
   fib = jit_emit();
+  jit_clear_state();
   printf("fib(%d) = %d\n", 32, fib(32));
+  jit_destroy_state();
   finish_jit();
   return 0;
 }
diff --git a/doc/rpn.c b/doc/rpn.c
index f02cef3..8131484 100644
--- a/doc/rpn.c
+++ b/doc/rpn.c
@@ -76,6 +76,7 @@ int main(int argc, char *argv[])
   (void)jit_emit();
   c2f = (pifi)jit_address(nc);
   f2c = (pifi)jit_address(nf);
+  jit_clear_state();
 
   printf("\nC:");
   for (i = 0; i <= 100; i += 10) printf("%3d ", i);
@@ -89,6 +90,7 @@ int main(int argc, char *argv[])
   for (i = 32; i <= 212; i += 18) printf("%3d ", f2c(i));
   printf("\n");
 
+  jit_destroy_state();
   finish_jit();
   return 0;
 }
diff --git a/include/lightning.h b/include/lightning.h
index 057b45a..bd9e37d 100644
--- a/include/lightning.h
+++ b/include/lightning.h
@@ -752,6 +752,10 @@ extern void init_jit(char*);
 extern void finish_jit(void);
 
 extern jit_state_t *jit_new_state(void);
+#define jit_clear_state()      _jit_clear_state(_jit)
+extern void _jit_clear_state(jit_state_t*);
+#define jit_destroy_state()    _jit_destroy_state(_jit)
+extern void _jit_destroy_state(jit_state_t*);
 
 #define jit_address(node)      _jit_address(_jit, node)
 extern jit_pointer_t _jit_address(jit_state_t*, jit_node_t*);
diff --git a/lib/jit_note.c b/lib/jit_note.c
index 13ead7f..284f02d 100644
--- a/lib/jit_note.c
+++ b/lib/jit_note.c
@@ -177,12 +177,12 @@ _jit_set_note(jit_state_t *_jit, jit_note_t *note,
     else {
        line = note->lines + index;
        index = offset_insert_index(line, offset);
-       if (line->offsets[index] == offset) {
+       if (index < line->length && line->offsets[index] == offset) {
            /* common case if no code was generated for several source lines */
            if (line->linenos[index] < lineno)
                line->linenos[index] = lineno;
        }
-       else if (line->linenos[index] == lineno) {
+       else if (index < line->length && line->linenos[index] == lineno) {
            /* common case of extending entry */
            if (line->offsets[index] > offset)
                line->offsets[index] = offset;
diff --git a/lib/lightning.c b/lib/lightning.c
index a408cf9..59ab8a7 100644
--- a/lib/lightning.c
+++ b/lib/lightning.c
@@ -539,6 +539,70 @@ jit_new_state(void)
     return (_jit);
 }
 
+void
+_jit_clear_state(jit_state_t *_jit)
+{
+    jit_word_t          offset;
+    jit_function_t     *function;
+
+    /* release memory not required at jit execution time and set
+     * pointers to NULL to explicitly know they are released */
+    _jit->head = _jit->tail = NULL;
+
+    mpz_clear(_jit->blockmask);
+
+    free(_jit->data.table);
+    _jit->data.table = NULL;
+    _jit->data.size = _jit->data.count = 0;
+
+    free(_jit->spill);
+    _jit->spill = NULL;
+    free(_jit->gen);
+    _jit->gen = NULL;
+    free(_jit->values);
+    _jit->values = NULL;
+
+    free(_jit->blocks.ptr);
+    _jit->blocks.ptr = NULL;
+
+    free(_jit->patches.ptr);
+    _jit->patches.ptr = NULL;
+    _jit->patches.offset = _jit->patches.length = 0;
+
+    for (offset = 0; offset < _jit->functions.offset; offset++) {
+       function = _jit->functions.ptr + offset;
+       free(function->regoff);
+       function->regoff = NULL;
+    }
+    free(_jit->functions.ptr);
+    _jit->functions.offset = _jit->functions.length = 0;
+    _jit->function = NULL;
+
+    for (offset = 0; offset < _jit->pool.length; offset++)
+       free(_jit->pool.ptr[offset]);
+    free(_jit->pool.ptr);
+    _jit->pool.ptr = NULL;
+    _jit->pool.offset = _jit->pool.length = 0;
+    _jit->list = NULL;
+
+    _jit->note.head = _jit->note.tail =
+       _jit->note.name = _jit->note.note = NULL;
+    _jit->note.base = NULL;
+
+#if __arm__ && DISASSEMBLER
+    free(_jit->data_info.ptr);
+    _jit->data_info.ptr = NULL;
+#endif
+}
+
+void
+_jit_destroy_state(jit_state_t *_jit)
+{
+    munmap(_jit->code.ptr, _jit->code.length);
+    munmap(_jit->data.ptr, _jit->data.length);
+    free(_jit);
+}
+
 jit_node_t *
 _jit_new_node(jit_state_t *_jit, jit_code_t code)
 {



reply via email to

[Prev in Thread] Current Thread [Next in Thread]