[pypy-commit] creflect default: Streamline the declaration of functions.
arigo
noreply at buildbot.pypy.org
Tue Nov 18 01:16:52 CET 2014
Author: Armin Rigo <arigo at tunes.org>
Branch:
Changeset: r66:9cc3ae087730
Date: 2014-11-18 01:17 +0100
http://bitbucket.org/cffi/creflect/changeset/9cc3ae087730/
Log: Streamline the declaration of functions.
diff --git a/creflect/cparser.py b/creflect/cparser.py
--- a/creflect/cparser.py
+++ b/creflect/cparser.py
@@ -95,7 +95,7 @@
if isinstance(node, pycparser.c_ast.FuncDecl):
tp = self._get_type(node)
assert isinstance(tp, model.FunctionType)
- self.declarations.append(model.VarDecl(decl.name, tp))
+ self.declarations.append(model.FuncDecl(decl.name, tp))
else:
xxxxxxxxxxxxxx
const = 'const' in decl.quals
diff --git a/creflect/creflect.h b/creflect/creflect.h
--- a/creflect/creflect.h
+++ b/creflect/creflect.h
@@ -10,7 +10,8 @@
} crx_field_t;
typedef struct crx_type_s crx_type_t; /* opaque */
-typedef void (*crx_trampoline_fn)(void *fn, void *args[], void *res);
+typedef void (*crx_trampoline0_fn)(void *args[], void *res);
+typedef void (*crx_trampoline1_fn)(void *fn, void *args[], void *res);
#define CRX_SELF struct _crx_builder_s *
typedef struct _crx_builder_s {
@@ -24,7 +25,7 @@
crx_type_t *(*get_float_type)(CRX_SELF, size_t,
const char *);
crx_type_t *(*get_function_type)(CRX_SELF, crx_type_t *,
- crx_type_t *[], int, crx_trampoline_fn);
+ crx_type_t *[], int, crx_trampoline1_fn);
crx_type_t *(*get_ellipsis_function_type)(CRX_SELF, crx_type_t *,
crx_type_t *[], int);
crx_type_t *(*get_pointer_type)(CRX_SELF, crx_type_t *);
@@ -40,6 +41,8 @@
void (*define_type)(CRX_SELF, const char *, crx_type_t *);
void (*define_var)(CRX_SELF, const char *, crx_type_t *,
void *);
+ void (*define_func)(CRX_SELF, const char *, crx_type_t *,
+ crx_type_t *[], int, crx_trampoline0_fn, void *);
void (*error)(CRX_SELF, const char *);
} crx_builder_t;
#undef CRX_SELF
diff --git a/creflect/model.py b/creflect/model.py
--- a/creflect/model.py
+++ b/creflect/model.py
@@ -160,20 +160,14 @@
# limitations so far:
assert not self.ellipsis, "XXX"
assert inspect is not None, "XXX"
- if inspect.started:
- assert inspect.levels == ['*'], "XXX"
-
- if inspect.started:
- localvar = 'f'
- else:
- assert inspect.varname is not None
- localvar = inspect.varname
+ assert inspect.started, "XXX"
+ assert inspect.levels == ['*'], "XXX"
t1 = self.result.inspect_type(block, None)
call = [' ']
if not isinstance(self.result, VoidType):
call.append('*(%s)result = ' % (self.result.get_c_name('*'),))
- call.append('%s(' % localvar)
+ call.append('f(')
t_args = [arg.inspect_type(block, None) for arg in self.args]
a2 = block.add_array_crx_types(len(t_args))
for i, t in enumerate(t_args):
@@ -194,7 +188,7 @@
crx_func_name,))
if inspect.started:
assert inspect.levels == ['*']
- wrline(' %s %s = func;' % (inspect.typename, localvar))
+ wrline(' %s f = func;' % inspect.typename)
wrline(''.join(call))
wrline('}')
wrline('')
@@ -216,6 +210,34 @@
wrline('')
return shadowname
+ def write_func_decl(self, block, fnname):
+ # XXX code duplication!
+ t1 = self.result.inspect_type(block, None)
+ call = [' ']
+ if not isinstance(self.result, VoidType):
+ call.append('*(%s)result = ' % (self.result.get_c_name('*'),))
+ call.append('%s(' % fnname)
+ t_args = [arg.inspect_type(block, None) for arg in self.args]
+ a2 = block.add_array_crx_types(len(t_args))
+ for i, t in enumerate(t_args):
+ block.writeline('%s[%d] = %s;' % (a2, i, t))
+ if i > 0:
+ call.append(', ')
+ call.append('*(%s)args[%d]' % (self.args[i].get_c_name('*'), i))
+ call.append(');')
+ #
+ toplevel = block.crx_top_level
+ crx_func_name = '%s__c_%s' % (toplevel.crx_func_name, fnname)
+ wrline = toplevel.writeline
+ wrline('static void %s(void *args[], void *result) {' % (
+ crx_func_name,))
+ wrline(''.join(call))
+ wrline('}')
+ wrline('')
+ shadow = self.shadow_global_var(toplevel, fnname)
+ block.writeline('cb->define_func(cb, "%s", %s, %s, %d, &%s, &%s);' % (
+ fnname, t1, a2, len(t_args), crx_func_name, shadow))
+
class PointerType(BaseType):
_attrs_ = ('totype',)
@@ -512,3 +534,14 @@
block.writeline('cb->define_var(cb, "%s", %s, &%s);' % (
self.name, t1, shadow))
funcblock.write_subblock(block)
+
+
+class FuncDecl(object):
+ def __init__(self, name, type):
+ self.name = name
+ self.type = type
+
+ def write_declaration(self, funcblock):
+ block = CodeBlock(funcblock)
+ self.type.write_func_decl(block, self.name)
+ funcblock.write_subblock(block)
diff --git a/test/cgcompile.c b/test/cgcompile.c
--- a/test/cgcompile.c
+++ b/test/cgcompile.c
@@ -80,7 +80,7 @@
static crx_type_t *tst_get_function_type(crx_builder_t *cb, crx_type_t *ret,
crx_type_t *args[], int nargs,
- crx_trampoline_fn trampl)
+ crx_trampoline1_fn trampl)
{
int i;
const char *prev = "FUNC( ";
@@ -162,6 +162,17 @@
printf("VAR %s: %s\n", name, t->text);
}
+static void tst_define_func(crx_builder_t *cb, const char *name,
+ crx_type_t *ret, crx_type_t *args[], int nargs,
+ crx_trampoline0_fn trampl, void *directcall)
+{
+ int i;
+ printf("FUNC %s: ", name);
+ for (i = 0; i < nargs; i++)
+ printf("%s -> ", args[i]->text);
+ printf("%s\n", ret->text);
+}
+
static void tst_error(crx_builder_t *cb, const char *msg)
{
printf("ERROR: %s\n", msg);
@@ -187,6 +198,7 @@
tst_complete_enum,
tst_define_type,
tst_define_var,
+ tst_define_func,
tst_error,
};
diff --git a/test/codegen/func-001.c b/test/codegen/func-001.c
--- a/test/codegen/func-001.c
+++ b/test/codegen/func-001.c
@@ -6,7 +6,7 @@
# ____________________________________________________________
-static void testfunc_001__c_f(void *func, void *args[], void *result) {
+static void testfunc_001__c_f(void *args[], void *result) {
*(int *)result = f();
}
@@ -16,11 +16,10 @@
void testfunc_001(crx_builder_t *cb)
{
- crx_type_t *t1, *t2;
+ crx_type_t *t1;
{
t1 = cb->get_signed_type(cb, sizeof(int), "int");
- t2 = cb->get_function_type(cb, t1, 0, 0, &testfunc_001__c_f);
- cb->define_var(cb, "f", t2, &testfunc_001__d_f);
-#expect VAR f: FUNC( int )
+ cb->define_func(cb, "f", t1, 0, 0, &testfunc_001__c_f, &testfunc_001__d_f);
+#expect FUNC f: int
}
}
diff --git a/test/codegen/func-001b.c b/test/codegen/func-001b.c
--- a/test/codegen/func-001b.c
+++ b/test/codegen/func-001b.c
@@ -10,7 +10,7 @@
# ____________________________________________________________
-static void testfunc_001b__c_f(void *func, void *args[], void *result) {
+static void testfunc_001b__c_f(void *args[], void *result) {
*(unsigned int *)result = f(*(long *)args[0]);
}
@@ -18,7 +18,7 @@
return f(a0);
}
-static void testfunc_001b__c_g(void *func, void *args[], void *result) {
+static void testfunc_001b__c_g(void *args[], void *result) {
*(long *)result = g(*(int *)args[0], *(int *)args[1]);
}
@@ -26,7 +26,7 @@
return g(a0, a1);
}
-static void testfunc_001b__c_h(void *func, void *args[], void *result) {
+static void testfunc_001b__c_h(void *args[], void *result) {
*(long *)result = h(*(int *)args[0], *(int *)args[1]);
}
@@ -36,28 +36,25 @@
void testfunc_001b(crx_builder_t *cb)
{
- crx_type_t *t1, *t2, *a3[1], *t4, *t5, *a6[2], *t7, *a8[2], *t9;
+ crx_type_t *t1, *t2, *a3[1], *t4, *a5[2], *a6[2];
{
t1 = cb->get_unsigned_type(cb, sizeof(unsigned int), "unsigned int");
t2 = cb->get_signed_type(cb, sizeof(long), "long");
a3[0] = t2;
- t4 = cb->get_function_type(cb, t1, a3, 1, &testfunc_001b__c_f);
- cb->define_var(cb, "f", t4, &testfunc_001b__d_f);
-#expect VAR f: FUNC( long -> unsigned int )
+ cb->define_func(cb, "f", t1, a3, 1, &testfunc_001b__c_f, &testfunc_001b__d_f);
+#expect FUNC f: long -> unsigned int
}
{
- t5 = cb->get_signed_type(cb, sizeof(int), "int");
- a6[0] = t5;
- a6[1] = t5;
- t7 = cb->get_function_type(cb, t2, a6, 2, &testfunc_001b__c_g);
- cb->define_var(cb, "g", t7, &testfunc_001b__d_g);
-#expect VAR g: FUNC( int -> int -> long )
+ t4 = cb->get_signed_type(cb, sizeof(int), "int");
+ a5[0] = t4;
+ a5[1] = t4;
+ cb->define_func(cb, "g", t2, a5, 2, &testfunc_001b__c_g, &testfunc_001b__d_g);
+#expect FUNC g: int -> int -> long
}
{
- a8[0] = t5;
- a8[1] = t5;
- t9 = cb->get_function_type(cb, t2, a8, 2, &testfunc_001b__c_h);
- cb->define_var(cb, "h", t9, &testfunc_001b__d_h);
-#expect VAR h: FUNC( int -> int -> long )
+ a6[0] = t4;
+ a6[1] = t4;
+ cb->define_func(cb, "h", t2, a6, 2, &testfunc_001b__c_h, &testfunc_001b__d_h);
+#expect FUNC h: int -> int -> long
}
}
More information about the pypy-commit
mailing list