[sdb] Fix passing of nullable parameters in invokes. Fixes #57160. (#5012)
authorZoltan Varga <vargaz@gmail.com>
Sat, 10 Jun 2017 03:53:39 +0000 (23:53 -0400)
committerGitHub <noreply@github.com>
Sat, 10 Jun 2017 03:53:39 +0000 (23:53 -0400)
mcs/class/Mono.Debugger.Soft/Test/dtest-app.cs
mcs/class/Mono.Debugger.Soft/Test/dtest.cs
mono/mini/debugger-agent.c

index 400b43ce34f599f808362bdbeaaac26778451e68..d2b408a68eddb940fcbbcb85275ba88d2336bb1e 100644 (file)
@@ -1165,10 +1165,18 @@ public class Tests : TestsBase, ITest2
                return 42;
        }
 
+       public int invoke_pass_nullable (int? i) {
+               return (int)i;
+       }
+
        public int? invoke_return_nullable_null () {
                return null;
        }
 
+       public int invoke_pass_nullable_null (int? i) {
+               return i.HasValue ? 1 : 2;
+       }
+
        public void invoke_type_load () {
                new Class3 ();
        }
index 631b5985db1ff7129d11b1443984be1b7c2fabcb..5f80228fe2fb2c43dc7d2a131888664db4574174 100644 (file)
@@ -2617,6 +2617,11 @@ public class DebuggerTests
                m = s.Type.GetMethod ("ToString");
                v = s.InvokeMethod (e.Thread, m, null);
 
+               // pass nullable as argument
+               m = t.GetMethod ("invoke_pass_nullable");
+               v = this_obj.InvokeMethod (e.Thread, m, new Value [] { s });
+               AssertValue (42, v);
+
                // return nullable null
                m = t.GetMethod ("invoke_return_nullable_null");
                v = this_obj.InvokeMethod (e.Thread, m, null);
@@ -2630,6 +2635,13 @@ public class DebuggerTests
                m = s.Type.GetMethod ("ToString");
                v = s.InvokeMethod (e.Thread, m, null);
 
+               // pass nullable null as argument
+               m = t.GetMethod ("invoke_pass_nullable_null");
+               v = this_obj.InvokeMethod (e.Thread, m, new Value [] { s });
+               AssertValue (2, v);
+
+               return;
+
                // pass primitive
                m = t.GetMethod ("invoke_pass_primitive");
                Value[] args = new Value [] {
index bfdddb37547e5dac5d9f4f094b1084d87b359826..88b1b18b68b8e0492dc328d8b4347d14843a43b8 100644 (file)
@@ -7096,11 +7096,17 @@ do_invoke_method (DebuggerTlsData *tls, Buffer *buf, InvokeData *invoke, guint8
                                args [i] = arg_buf [i];
                        }
                } else {
-                       arg_buf [i] = (guint8 *)g_alloca (mono_class_instance_size (mono_class_from_mono_type (sig->params [i])));
+                       MonoClass *arg_class = mono_class_from_mono_type (sig->params [i]);
+                       arg_buf [i] = (guint8 *)g_alloca (mono_class_instance_size (arg_class));
                        err = decode_value (sig->params [i], domain, arg_buf [i], p, &p, end);
                        if (err != ERR_NONE)
                                break;
-                       args [i] = arg_buf [i];
+                       if (mono_class_is_nullable (arg_class)) {
+                               args [i] = mono_nullable_box (arg_buf [i], arg_class, &error);
+                               mono_error_assert_ok (&error);
+                       } else {
+                               args [i] = arg_buf [i];
+                       }
                }
        }