Author: Armin Rigo <[email protected]>
Branch: 
Changeset: r193:94b9f2a44589
Date: 2014-12-07 11:18 +0100
http://bitbucket.org/cffi/creflect/changeset/94b9f2a44589/

Log:    avoid generating tons of 'a%d[n]' local variables if we declare tons
        of functions with the same argument types

diff --git a/creflect/codegen.py b/creflect/codegen.py
--- a/creflect/codegen.py
+++ b/creflect/codegen.py
@@ -9,12 +9,14 @@
             self.crx_type_cache = {}
             self.crx_qualtype_vars = []
             self.crx_field_vars = []
+            self.crx_args_cache = {}
             self.crx_top_level = self
         else:
             self.crx_type_vars = parent.crx_type_vars
             self.crx_type_cache = parent.crx_type_cache
             self.crx_qualtype_vars = parent.crx_qualtype_vars
             self.crx_field_vars = parent.crx_field_vars
+            self.crx_args_cache = parent.crx_args_cache
             self.crx_top_level = parent.crx_top_level
 
     def writedecl(self, line):
diff --git a/creflect/model.py b/creflect/model.py
--- a/creflect/model.py
+++ b/creflect/model.py
@@ -271,11 +271,16 @@
     def _get_arg_ret_types(self, block):
         inspect = MissingInspector()
         t1, q1_ignored = self.result.inspect_type(block, inspect, 0)
-        a2 = block.write_crx_qualtype_var(len(self.args))
-        for i, arg in enumerate(self.args):
-            t3, q3 = arg.inspect_qualtype(block, inspect)
-            block.writeline('%s[%d].type = %s;' % (a2, i, t3))
-            block.writeline('%s[%d].qualifiers = %s;' % (a2, i, q3))
+        all_args = [arg.inspect_qualtype(block, inspect) for arg in self.args]
+        key = tuple(all_args)
+        try:
+            a2 = block.crx_args_cache[key]
+        except KeyError:
+            a2 = block.write_crx_qualtype_var(len(self.args))
+            block.crx_args_cache[key] = a2
+            for i, (t3, q3) in enumerate(all_args):
+                block.writeline('%s[%d].type = %s;' % (a2, i, t3))
+                block.writeline('%s[%d].qualifiers = %s;' % (a2, i, q3))
         return t1, a2
 
     def _get_c_call_sequence(self, varname):
diff --git a/creflect/test/codegen/func-001b.c 
b/creflect/test/codegen/func-001b.c
--- a/creflect/test/codegen/func-001b.c
+++ b/creflect/test/codegen/func-001b.c
@@ -39,7 +39,6 @@
     _crx_type_t *t1, *t2, *t3;
     _crx_qual_type a1[1];
     _crx_qual_type a2[2];
-    _crx_qual_type a3[2];
     {
         t1 = cb->get_unsigned_type(cb, sizeof(unsigned int), "int");
         t2 = cb->get_signed_type(cb, sizeof(long), "long");
@@ -58,11 +57,7 @@
 #expect FUNC g: int -> int -> long
     }
     {
-        a3[0].type = t3;
-        a3[0].qualifiers = 0;
-        a3[1].type = t3;
-        a3[1].qualifiers = 0;
-        cb->define_func(cb, "h", t2, a3, 2, &testfunc_001b__c_h, 
&testfunc_001b__d_h);
+        cb->define_func(cb, "h", t2, a2, 2, &testfunc_001b__c_h, 
&testfunc_001b__d_h);
 #expect FUNC h: int -> int -> long
     }
 }
diff --git a/creflect/test/codegen/func-005.c b/creflect/test/codegen/func-005.c
--- a/creflect/test/codegen/func-005.c
+++ b/creflect/test/codegen/func-005.c
@@ -28,19 +28,19 @@
         t1 = cb->get_void_type(cb);
         t2 = cb->get_signed_type(cb, sizeof(int), "int");
         t3 = cb->get_incomplete_array_type(cb, t2);
-        a1[0].type = t3;
-        a1[0].qualifiers = _CRX_CONST;
         t4 = cb->get_signed_type(cb, sizeof(long), "long");
         t5 = cb->get_char_type(cb);
-        a2[0].type = t5;
-        a2[0].qualifiers = 0;
         t6 = cb->get_signed_type(cb, sizeof(short), "short");
-        a2[1].type = t6;
+        a1[0].type = t5;
+        a1[0].qualifiers = 0;
+        a1[1].type = t6;
+        a1[1].qualifiers = 0;
+        t7 = cb->get_function_type(cb, t4, a1, 2, &testfunc_005__f4);
+        a2[0].type = t3;
+        a2[0].qualifiers = _CRX_CONST;
+        a2[1].type = t7;
         a2[1].qualifiers = 0;
-        t7 = cb->get_function_type(cb, t4, a2, 2, &testfunc_005__f4);
-        a1[1].type = t7;
-        a1[1].qualifiers = 0;
-        cb->define_func(cb, "f", t1, a1, 2, &testfunc_005__c_f, 
&testfunc_005__d_f);
+        cb->define_func(cb, "f", t1, a2, 2, &testfunc_005__c_f, 
&testfunc_005__d_f);
 #expect FUNC f: CONST ARRAY[] int -> FUNC( char -> short -> long ) -> void
     }
 }
_______________________________________________
pypy-commit mailing list
[email protected]
https://mail.python.org/mailman/listinfo/pypy-commit

Reply via email to