]> git.ipfire.org Git - thirdparty/vala.git/commitdiff
codegen: Correct field declaration for captured inline-allocated array
authorRico Tzschichholz <ricotz@ubuntu.com>
Tue, 31 Mar 2020 12:55:59 +0000 (14:55 +0200)
committerRico Tzschichholz <ricotz@ubuntu.com>
Mon, 20 Apr 2020 19:15:48 +0000 (21:15 +0200)
Also pass proper size to memset for local temp variables of
inline-allocated arrays in asynchronous context.

Fixes https://gitlab.gnome.org/GNOME/vala/issues/954

codegen/valaccodebasemodule.vala
codegen/valagasyncmodule.vala
tests/Makefile.am
tests/asynchronous/captured-fixed-array.vala [new file with mode: 0644]

index 189b0fcdeccd1190a34ccabba6c4ea086caf7f5b..f2c146f1fd31ed31ed9d28b7eee3535a8001dbf8 100644 (file)
@@ -1982,7 +1982,7 @@ public abstract class Vala.CCodeBaseModule : CodeGenerator {
                if (!param.variable_type.value_owned) {
                        param_type.value_owned = !no_implicit_copy (param.variable_type);
                }
-               data.add_field (get_ccode_name (param_type), get_ccode_name (param));
+               data.add_field (get_ccode_name (param_type), get_ccode_name (param), 0, get_ccode_declarator_suffix (param_type));
 
                // create copy if necessary as captured variables may need to be kept alive
                param.captured = false;
@@ -1991,7 +1991,7 @@ public abstract class Vala.CCodeBaseModule : CodeGenerator {
                var array_type = param.variable_type as ArrayType;
                var deleg_type = param.variable_type as DelegateType;
 
-               if (array_type != null && get_ccode_array_length (param)) {
+               if (array_type != null && get_ccode_array_length (param) && !((ArrayType) array_type).fixed_length) {
                        var length_ctype = get_ccode_array_length_type (array_type);
                        for (int dim = 1; dim <= array_type.rank; dim++) {
                                data.add_field (length_ctype, get_variable_array_length_cname (param, dim));
@@ -3732,7 +3732,7 @@ public abstract class Vala.CCodeBaseModule : CodeGenerator {
        public void emit_temp_var (LocalVariable local, bool on_error = false) {
                var init = (!local.name.has_prefix ("*") && local.init);
                if (is_in_coroutine ()) {
-                       closure_struct.add_field (get_ccode_name (local.variable_type), local.name);
+                       closure_struct.add_field (get_ccode_name (local.variable_type), local.name, 0, get_ccode_declarator_suffix (local.variable_type));
 
                        // even though closure struct is zerod, we need to initialize temporary variables
                        // as they might be used multiple times when declared in a loop
@@ -3744,7 +3744,12 @@ public abstract class Vala.CCodeBaseModule : CodeGenerator {
                                        var memset_call = new CCodeFunctionCall (new CCodeIdentifier ("memset"));
                                        memset_call.add_argument (new CCodeUnaryExpression (CCodeUnaryOperator.ADDRESS_OF, get_variable_cexpression (local.name)));
                                        memset_call.add_argument (new CCodeConstant ("0"));
-                                       memset_call.add_argument (new CCodeIdentifier ("sizeof (%s)".printf (get_ccode_name (local.variable_type))));
+                                       CCodeExpression? size = null;
+                                       requires_memset_init (local, out size);
+                                       if (size == null) {
+                                               size = new CCodeIdentifier ("sizeof (%s)".printf (get_ccode_name (local.variable_type)));
+                                       }
+                                       memset_call.add_argument (size);
                                        ccode.add_expression (memset_call);
                                } else {
                                        ccode.add_assignment (get_variable_cexpression (local.name), initializer);
@@ -6441,11 +6446,11 @@ public abstract class Vala.CCodeBaseModule : CodeGenerator {
 
        public bool requires_memset_init (Variable variable, out CCodeExpression? size) {
                unowned ArrayType? array_type = variable.variable_type as ArrayType;
-               if (array_type != null && array_type.fixed_length && !is_constant_ccode (array_type.length)) {
+               if (array_type != null && array_type.fixed_length) {
                        var sizeof_call = new CCodeFunctionCall (new CCodeIdentifier ("sizeof"));
                        sizeof_call.add_argument (new CCodeIdentifier (get_ccode_name (array_type.element_type)));
                        size = new CCodeBinaryExpression (CCodeBinaryOperator.MUL, get_ccodenode (array_type.length), sizeof_call);
-                       return true;
+                       return !is_constant_ccode (array_type.length);
                }
                size = null;
                return false;
index 68a13dd29e019be8acd3b856d5e2907ea03f88e4..14898451828c0f302526e7d801c7ab2d4a8f27be 100644 (file)
@@ -48,11 +48,11 @@ public class Vala.GAsyncModule : GtkModule {
                foreach (Parameter param in m.get_parameters ()) {
                        var param_type = param.variable_type.copy ();
                        param_type.value_owned = true;
-                       data.add_field (get_ccode_name (param_type), get_ccode_name (param));
+                       data.add_field (get_ccode_name (param_type), get_ccode_name (param), 0, get_ccode_declarator_suffix (param_type));
 
                        if (param.variable_type is ArrayType) {
                                var array_type = (ArrayType) param.variable_type;
-                               if (get_ccode_array_length (param)) {
+                               if (get_ccode_array_length (param) && !((ArrayType) array_type).fixed_length) {
                                        var length_ctype = get_ccode_array_length_type (array_type);
                                        for (int dim = 1; dim <= array_type.rank; dim++) {
                                                data.add_field (length_ctype, get_variable_array_length_cname (param, dim));
index 313a4380834fb5e32258e42ef322a338cead244e..5153bf67ffac1d30d70de70a1b1abeafe4c6797d 100644 (file)
@@ -518,6 +518,7 @@ TESTS = \
        asynchronous/bug792660.vala \
        asynchronous/bug792942.vala \
        asynchronous/bug793158.vala \
+       asynchronous/captured-fixed-array.vala \
        asynchronous/catch-error-scope.vala \
        asynchronous/catch-in-finally.vala \
        asynchronous/creation-missing-yield.test \
diff --git a/tests/asynchronous/captured-fixed-array.vala b/tests/asynchronous/captured-fixed-array.vala
new file mode 100644 (file)
index 0000000..30a9c38
--- /dev/null
@@ -0,0 +1,14 @@
+async void foo (int array_param[3]) {
+    int array[] = { 23, 42 };
+
+    assert (array.length == 2);
+    assert (array[1] == 42);
+
+    assert (array_param.length == 3);
+    assert (array_param[2] == 4711);
+}
+
+void main() {
+       int array[3] = { 42, 23, 4711 };
+       foo.begin (array);
+}