[svn:parrot] r49745 - in branches/gsoc_nci: include/parrot src/pmc
plobsing at svn.parrot.org
plobsing at svn.parrot.org
Sun Oct 31 06:13:46 UTC 2010
Author: plobsing
Date: Sun Oct 31 06:13:45 2010
New Revision: 49745
URL: https://trac.parrot.org/parrot/changeset/49745
Log:
avoid rebuilding the pcc cif every call
Modified:
branches/gsoc_nci/include/parrot/parrot.h
branches/gsoc_nci/src/pmc/nci.pmc
Modified: branches/gsoc_nci/include/parrot/parrot.h
==============================================================================
--- branches/gsoc_nci/include/parrot/parrot.h Sun Oct 31 01:55:10 2010 (r49744)
+++ branches/gsoc_nci/include/parrot/parrot.h Sun Oct 31 06:13:45 2010 (r49745)
@@ -106,6 +106,10 @@
# include <limits.h>
#endif /* PARROT_HAS_HEADER_LIMITS */
+#ifdef PARROT_HAS_LIBFFI
+# include <ffi.h>
+#endif
+
#define NUM_REGISTERS 32
#define PARROT_MAGIC 0x13155a1
Modified: branches/gsoc_nci/src/pmc/nci.pmc
==============================================================================
--- branches/gsoc_nci/src/pmc/nci.pmc Sun Oct 31 01:55:10 2010 (r49744)
+++ branches/gsoc_nci/src/pmc/nci.pmc Sun Oct 31 06:13:45 2010 (r49745)
@@ -144,6 +144,43 @@
}
}
+/*
+
+=item C<void sig_to_pcc_cif(PARROT_INTERP, Parrot_NCI_attributes *nci)>
+
+generate Parrot_pcc_fill_params_from_c_args dynamic call infrastructure
+
+=cut
+
+*/
+
+static void
+sig_to_pcc_cif(PARROT_INTERP, Parrot_NCI_attributes *nci)
+{
+ INTVAL argc = Parrot_str_length(interp, nci->pcc_params_signature) + 3;
+ ffi_type **arg_t = nci->pcc_arg_types =
+ mem_gc_allocate_n_zeroed_typed(interp, argc, ffi_type *);
+ int i;
+
+ arg_t[0] = &ffi_type_pointer; /* interp */
+ arg_t[1] = &ffi_type_pointer; /* call object */
+ arg_t[2] = &ffi_type_pointer; /* pcc signature */
+ for (i = 3; i < argc; i++)
+ arg_t[i] = &ffi_type_pointer; /* INSP pointer */
+
+ if (ffi_prep_cif(&nci->pcc_cif, FFI_DEFAULT_ABI, argc, &ffi_type_void, arg_t) !=
+ FFI_OK)
+ Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_JIT_ERROR, "invalid ffi signature");
+}
+
+/*
+
+=item C<void build_libffi_func(PARROT_INTERP, Parrot_NCI_attributes *nci)>
+
+=cut
+
+*/
+
static void
build_libffi_func(PARROT_INTERP, ARGMOD(Parrot_NCI_attributes *nci))
{
@@ -159,6 +196,7 @@
nci->arity = VTABLE_elements(interp, nci->signature) - 1;
sig_to_cif(interp, nci);
+ sig_to_pcc_cif(interp, nci);
}
pmclass NCI auto_attrs provides invokable {
@@ -168,14 +206,18 @@
ATTR void *func; /* Function pointer to call. */
ATTR void *orig_func;
ATTR PMC *fb_info; /* Frame-builder info */
- ATTR void *cif; /* Function interface */
- ATTR void *arg_types; /* Used for building the libffi call interface */
/* Parrot Sub-ish attributes */
ATTR STRING *pcc_params_signature;
ATTR STRING *pcc_return_signature;
ATTR INTVAL arity;
+ /* LibFFI attributes */
+ ATTR void *cif;
+ ATTR void *arg_types;
+ ATTR ffi_cif pcc_cif;
+ ATTR ffi_type **pcc_arg_types;
+
/* MMD fields */
ATTR STRING *long_signature; /* The full signature. */
ATTR PMC *multi_sig; /* type tuple array (?) */
@@ -290,9 +332,10 @@
VTABLE void destroy() {
if (PARROT_NCI(SELF)) {
- Parrot_NCI_attributes * const nci_info = PARROT_NCI(SELF);
- mem_sys_free(nci_info->cif);
- mem_sys_free(nci_info->arg_types);
+ Parrot_NCI_attributes *nci = PARROT_NCI(SELF);
+ mem_gc_free(INTERP, nci->cif);
+ mem_gc_free(INTERP, nci->arg_types);
+ mem_gc_free(INTERP, nci->pcc_arg_types);
}
}
@@ -380,8 +423,7 @@
void *return_data; /* Holds return data from FFI call */
size_t count, i, j_offset;
char *tmp_sig;
- ffi_cif *cif, pcc_cif;
- ffi_type **pcc_args;
+ ffi_cif *cif;
cif = (ffi_cif*)nci_info->cif;
func = (void (*)(void*, void*, void*))nci_info->func;
@@ -400,12 +442,8 @@
if (nci_info->arity > 0) {
size_t pcc_argc, pcc_values_offset, pcc_values_size, values_size;
/* Function has arguments */
- pcc_args = mem_internal_allocate_n_zeroed_typed(nci_info->arity + 4, ffi_type*);
tmp_sig = Parrot_str_to_cstring(interp, nci_info->pcc_params_signature);
- pcc_args[0] = &ffi_type_pointer;
- pcc_args[1] = &ffi_type_pointer;
- pcc_args[2] = &ffi_type_pointer;
pcc_values_size = 0;
values_size = 0;
pcc_argc = Parrot_str_length(interp, nci_info->pcc_params_signature);
@@ -431,7 +469,6 @@
/* Add up the size of the pcc arguments */
for (i = 0; i < pcc_argc; i++) {
- pcc_args[i + 3] = &ffi_type_pointer;
if (tmp_sig[i] == 'N') {
pcc_val[i] = mem_internal_allocate_typed(FLOATVAL);
pcc_ptr[i+3] = &pcc_val[i];
@@ -446,16 +483,9 @@
}
}
- if (ffi_prep_cif(&pcc_cif, FFI_DEFAULT_ABI, 3 + pcc_argc,
- &ffi_type_void, pcc_args) != FFI_OK) {
- Parrot_ex_throw_from_c_args(INTERP, NULL,
- EXCEPTION_INVALID_OPERATION,
- "Bad signature generated for Parrot_pcc_fill_params_from_c_args in NCI");
- }
-
{
ffi_arg ret;
- ffi_call(&pcc_cif, FFI_FN(Parrot_pcc_fill_params_from_c_args), &ret, pcc_ptr);
+ ffi_call(&nci_info->pcc_cif, FFI_FN(Parrot_pcc_fill_params_from_c_args), &ret, pcc_ptr);
}
Parrot_str_free_cstring(tmp_sig);
@@ -577,9 +607,6 @@
}
}
- if (pcc_args) {
- mem_sys_free(pcc_args);
- }
if (pcc_ptr) {
mem_sys_free(pcc_ptr);
}
More information about the parrot-commits
mailing list