cvsuser 02/12/14 01:04:36
Modified: . build_nativecall.pl method_util.c
classes nci.pmc
include/parrot jit.h nci.h
jit/i386 jit_emit.h
t/pmc nci.t
Log:
fixed memory leak in jitted i386 nci code; clone nci
Revision Changes Path
1.7 +5 -3 parrot/build_nativecall.pl
Index: build_nativecall.pl
===================================================================
RCS file: /cvs/public/parrot/build_nativecall.pl,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -w -r1.6 -r1.7
--- build_nativecall.pl 3 Dec 2002 10:42:05 -0000 1.6
+++ build_nativecall.pl 14 Dec 2002 09:04:09 -0000 1.7
@@ -65,7 +65,7 @@
/* nci.c
* Copyright: 2001, 2002 Yet Another Society
* CVS Info
- * $Id: build_nativecall.pl,v 1.6 2002/12/03 10:42:05 leo Exp $
+ * $Id: build_nativecall.pl,v 1.7 2002/12/14 09:04:09 leo Exp $
* Overview:
* Native Call Interface routines. The code needed to build a
* parrot to C call frame is in here
@@ -140,16 +140,18 @@
/* This function serves a single purpose. It takes the function
signature for a C function we want to call and returns a pointer
to a function that can call it. */
-void *build_call_func(struct Parrot_Interp *interpreter, String *signature) {
+void *build_call_func(struct Parrot_Interp *interpreter, PMC *pmc_nci,
+ String *signature) {
#if defined(CAN_BUILD_CALL_FRAMES)
/* This would be a good place to put the code that builds the
frames. Undoubtedly painfully platform-dependent */
- return Parrot_jit_build_call_func(interpreter, signature);
+ return Parrot_jit_build_call_func(interpreter, pmc_nci, signature);
#else
/* And in here is the platform-independent way. Which is to say
"here there be hacks" */
+ UNUSED(pmc_nci);
if (0 == string_length(signature)) return F2DPTR(pcf_v_v);
$icky_global_bit
PANIC("Unknown signature type");
1.9 +4 -3 parrot/method_util.c
Index: method_util.c
===================================================================
RCS file: /cvs/public/parrot/method_util.c,v
retrieving revision 1.8
retrieving revision 1.9
diff -u -w -r1.8 -r1.9
--- method_util.c 21 Nov 2002 01:47:44 -0000 1.8
+++ method_util.c 14 Dec 2002 09:04:09 -0000 1.9
@@ -1,7 +1,7 @@
/* method_util.c
* Copyright: (When this is determined...it will go here)
* CVS Info
- * $Id: method_util.c,v 1.8 2002/11/21 01:47:44 dan Exp $
+ * $Id: method_util.c,v 1.9 2002/12/14 09:04:09 leo Exp $
* Overview:
* Utility functions to handle Parrot calling conventions, lookup
* methods, etc.
@@ -19,11 +19,12 @@
* Create a new native sub. (new way)
*/
PMC *
-Parrot_new_nci(struct Parrot_Interp *interp, Parrot_csub_t func, String *signature)
+Parrot_new_nci(struct Parrot_Interp *interp, Parrot_csub_t func,
+ String *signature)
{
PMC *ret = pmc_new(interp, enum_class_NCI);
ret->cache.struct_val = (DPOINTER *)F2DPTR(func);
- ret->data = build_call_func(interp, signature);
+ ret->data = build_call_func(interp, ret, signature);
return ret;
}
1.3 +28 -2 parrot/classes/nci.pmc
Index: nci.pmc
===================================================================
RCS file: /cvs/public/parrot/classes/nci.pmc,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -w -r1.2 -r1.3
--- nci.pmc 30 Nov 2002 03:12:09 -0000 1.2
+++ nci.pmc 14 Dec 2002 09:04:14 -0000 1.3
@@ -1,7 +1,7 @@
/* NCI.pmc
* Copyright: 2002 Yet Another Society
* CVS Info
- * $Id: nci.pmc,v 1.2 2002/11/30 03:12:09 josh Exp $
+ * $Id: nci.pmc,v 1.3 2002/12/14 09:04:14 leo Exp $
* Overview:
* The vtable functions for the native C call functions
* Data Structure and Algorithms:
@@ -17,6 +17,18 @@
pmclass NCI {
void init () {
+ PObj_custom_mark_SET(SELF);
+ }
+
+
+ PMC* mark (PMC *end_of_used_list) {
+ PMC *f = SELF->cache.struct_val;
+ if (f) {
+ return mark_used(f, end_of_used_list);
+ }
+ else {
+ return end_of_used_list;
+ }
}
INTVAL type () {
@@ -27,8 +39,22 @@
return whoami;
}
+ void destroy() {
+ if (SELF->data)
+ free(SELF->data);
+ }
+
PMC* clone () {
- return Parrot_new_csub(INTERP,
(Parrot_csub_t)D2FPTR(SELF->cache.struct_val));
+ PMC *ret = pmc_new(INTERP, enum_class_NCI);
+ ret->cache.struct_val = (DPOINTER *)
+ (Parrot_csub_t)D2FPTR(SELF->cache.struct_val);
+ /* FIXME if data is malloced (JIT/i386!) then we need
+ * the length of data here, to memcpy it
+ * ManagedStruct or Buffer?
+ */
+ ret->data = SELF->data;
+ PObj_custom_mark_SET(ret);
+ return ret;
}
PMC* get_pmc () {
1.30 +2 -2 parrot/include/parrot/jit.h
Index: jit.h
===================================================================
RCS file: /cvs/public/parrot/include/parrot/jit.h,v
retrieving revision 1.29
retrieving revision 1.30
diff -u -w -r1.29 -r1.30
--- jit.h 3 Dec 2002 10:42:08 -0000 1.29
+++ jit.h 14 Dec 2002 09:04:21 -0000 1.30
@@ -1,7 +1,7 @@
/*
* jit.h
*
- * $Id: jit.h,v 1.29 2002/12/03 10:42:08 leo Exp $
+ * $Id: jit.h,v 1.30 2002/12/14 09:04:21 leo Exp $
*/
#ifndef JIT_H_GUARD
@@ -232,7 +232,7 @@
void Parrot_jit_emit_mov_rm(
struct Parrot_Interp *interpreter, int reg, char *mem);
-void *Parrot_jit_build_call_func(struct Parrot_Interp *, String *signature);
+void *Parrot_jit_build_call_func(struct Parrot_Interp *, PMC *, String *);
#endif /* JIT_H_GUARD */
1.3 +2 -2 parrot/include/parrot/nci.h
Index: nci.h
===================================================================
RCS file: /cvs/public/parrot/include/parrot/nci.h,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -w -r1.2 -r1.3
--- nci.h 21 Nov 2002 01:47:47 -0000 1.2
+++ nci.h 14 Dec 2002 09:04:21 -0000 1.3
@@ -1,7 +1,7 @@
/* nci.h
* Copyright: 2002 Yet Another Society
* CVS Info
- * $Id: nci.h,v 1.2 2002/11/21 01:47:47 dan Exp $
+ * $Id: nci.h,v 1.3 2002/12/14 09:04:21 leo Exp $
* Overview:
* The nci api handles building native call frames
* Data Structure and Algorithms:
@@ -15,6 +15,6 @@
#include "parrot/parrot.h"
-void *build_call_func(struct Parrot_Interp *, String *);
+void *build_call_func(struct Parrot_Interp *, PMC *, String *);
#endif
1.43 +3 -4 parrot/jit/i386/jit_emit.h
Index: jit_emit.h
===================================================================
RCS file: /cvs/public/parrot/jit/i386/jit_emit.h,v
retrieving revision 1.42
retrieving revision 1.43
diff -u -w -r1.42 -r1.43
--- jit_emit.h 12 Dec 2002 11:21:23 -0000 1.42
+++ jit_emit.h 14 Dec 2002 09:04:28 -0000 1.43
@@ -3,7 +3,7 @@
*
* i386
*
- * $Id: jit_emit.h,v 1.42 2002/12/12 11:21:23 leo Exp $
+ * $Id: jit_emit.h,v 1.43 2002/12/14 09:04:28 leo Exp $
*/
#include <assert.h>
@@ -2040,10 +2040,8 @@
Parrot_emit_jump_to_eax(jit_info, interpreter);
}
-void * Parrot_jit_build_call_func(struct Parrot_Interp *, String *);
-
void *
-Parrot_jit_build_call_func(struct Parrot_Interp *interpreter,
+Parrot_jit_build_call_func(struct Parrot_Interp *interpreter, PMC *pmc_nci,
String *signature)
{
Parrot_jit_info_t jit_info;
@@ -2206,6 +2204,7 @@
emitm_ret(pc);
assert(pc - jit_info.arena.start <= size);
/* could shrink arena.start here to used size */
+ PObj_active_destroy_SET(pmc_nci);
return (jit_f)D2FPTR(jit_info.arena.start);
}
1.4 +77 -1 parrot/t/pmc/nci.t
Index: nci.t
===================================================================
RCS file: /cvs/public/parrot/t/pmc/nci.t,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -w -r1.3 -r1.4
--- nci.t 3 Dec 2002 10:42:10 -0000 1.3
+++ nci.t 14 Dec 2002 09:04:36 -0000 1.4
@@ -1,4 +1,4 @@
-use Parrot::Test tests => 9;
+use Parrot::Test tests => 11;
use Test::More qw/skip/;
use Parrot::Config;
@@ -304,5 +304,81 @@
}
+output_is(gen_test(<<'CODE'), <<'OUTPUT', "nci_d_d - stress test");
+ loadlib P1, "libnci.so"
+ print "loaded\n"
+ set I10, 1000000
+ print "dlfunced\n"
+loop:
+ dlfunc P0, P1, "nci_dd", "dd"
+ set I0, 1 # prototype used - unchecked
+ set I1, 0 # items on stack - unchecked
+ set N5, 4.0
+ invoke
+ ne N5, 8.0, nok_1
+ dec I10
+ gt I10, 0, loop
+ print "ok 1\n"
+ ne I0, 0, nok_2 # test return value convention
+ ne I1, 0, nok_2
+ ne I2, 0, nok_2
+ ne I3, 0, nok_2
+ ne I4, 1, nok_2
+ print "ok 2\n"
+ end
+nok_1: print "nok 1\n"
+ print N5
+ print "\n"
+ end
+nok_2: print "nok 2\n"
+ end
+CODE
+loaded
+dlfunced
+ok 1
+ok 2
+OUTPUT
+
+output_is(gen_test(<<'CODE'), <<'OUTPUT', "nci_d_d - clone");
+ loadlib P1, "libnci.so"
+ print "loaded\n"
+ dlfunc P0, P1, "nci_dd", "dd"
+ print "dlfunced\n"
+ clone P2, P0
+ print "ok 1\n"
+ set I0, 1 # prototype used - unchecked
+ set I1, 0 # items on stack - unchecked
+ set N5, 4.0
+ invoke
+ ne N5, 8.0, nok_1
+ print "ok 2\n"
+ set I0, 1
+ set I1, 0
+ set N5, 4.0
+ set P0, P2
+ invoke
+ ne N5, 8.0, nok_1
+ print "ok 3\n"
+ ne I0, 0, nok_2 # test return value convention
+ ne I1, 0, nok_2
+ ne I2, 0, nok_2
+ ne I3, 0, nok_2
+ ne I4, 1, nok_2
+ print "ok 4\n"
+ end
+nok_1: print "nok 1\n"
+ print N5
+ print "\n"
+ end
+nok_2: print "nok 2\n"
+ end
+CODE
+loaded
+dlfunced
+ok 1
+ok 2
+ok 3
+ok 4
+OUTPUT
1;