From 252e89fde77a562b989d51a2f8d13099e06db399 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=91=D0=BE=D0=BD=D0=B4=D0=B0=D1=80=D0=B5=D0=B2=20=D0=98?= =?UTF-8?q?=D0=B2=D0=B0=D0=BD?= Date: Sun, 22 Oct 2017 14:12:03 +0200 Subject: [PATCH] bug fix #531 --- NETGenerator/NETGenerator.cs | 16 ++++++++++------ TestSuite/boxing2.pas | 22 ++++++++++++++++++++++ 2 files changed, 32 insertions(+), 6 deletions(-) create mode 100644 TestSuite/boxing2.pas diff --git a/NETGenerator/NETGenerator.cs b/NETGenerator/NETGenerator.cs index b6c4b4c50..bfe1aa479 100644 --- a/NETGenerator/NETGenerator.cs +++ b/NETGenerator/NETGenerator.cs @@ -7550,11 +7550,11 @@ namespace PascalABCCompiler.NETGenerator private void BoxAssignToParameter(IExpressionNode to, IExpressionNode from) { ICompiledTypeNode ctn2 = to.type as ICompiledTypeNode; - if ((from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && ctn2.compiled_type == TypeFactory.ObjectType) + if ((from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && (ctn2.compiled_type == TypeFactory.ObjectType || ctn2.IsInterface)) { il.Emit(OpCodes.Box, helper.GetTypeReference(from.type).tp); } - else if (from.conversion_type != null && (from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && ctn2.compiled_type == TypeFactory.ObjectType) + else if (from.conversion_type != null && (from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && (ctn2.compiled_type == TypeFactory.ObjectType || ctn2.IsInterface)) { il.Emit(OpCodes.Box, helper.GetTypeReference(from.conversion_type).tp); } @@ -7940,11 +7940,15 @@ namespace PascalABCCompiler.NETGenerator return; } ICompiledTypeNode ctn2 = to.type as ICompiledTypeNode; - if ((from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && ctn2.compiled_type == TypeFactory.ObjectType) + if ((from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && (ctn2.compiled_type == TypeFactory.ObjectType || ctn2.IsInterface)) { il.Emit(OpCodes.Box, helper.GetTypeReference(from.type).tp); } - else if (from.conversion_type != null && (from.conversion_type.is_value_type || from.conversion_type.is_generic_parameter) && ctn2 != null && ctn2.compiled_type == TypeFactory.ObjectType) + else if ((from.type.is_value_type || from.type.is_generic_parameter) && to.type.IsInterface) + { + il.Emit(OpCodes.Box, helper.GetTypeReference(from.type).tp); + } + else if (from.conversion_type != null && (from.conversion_type.is_value_type || from.conversion_type.is_generic_parameter) && ctn2 != null && (ctn2.compiled_type == TypeFactory.ObjectType || ctn2.IsInterface)) { il.Emit(OpCodes.Box, helper.GetTypeReference(from.conversion_type).tp); } @@ -7977,11 +7981,11 @@ namespace PascalABCCompiler.NETGenerator } //ICompiledTypeNode ctn = from.type as ICompiledTypeNode; ICompiledTypeNode ctn2 = to.type as ICompiledTypeNode; - if ((from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && ctn2.compiled_type == TypeFactory.ObjectType) + if ((from.type.is_value_type || from.type.is_generic_parameter) && ctn2 != null && (ctn2.compiled_type == TypeFactory.ObjectType || (ctn2.compiled_type == TypeFactory.ObjectType || ctn2.compiled_type.IsInterface))) { il.Emit(OpCodes.Box, helper.GetTypeReference(from.type).tp); } - else if (from.conversion_type != null && (from.conversion_type.is_value_type || from.conversion_type.is_generic_parameter) && ctn2 != null && ctn2.compiled_type == TypeFactory.ObjectType) + else if (from.conversion_type != null && (from.conversion_type.is_value_type || from.conversion_type.is_generic_parameter) && ctn2 != null && (ctn2.compiled_type == TypeFactory.ObjectType || ctn2.compiled_type.IsInterface)) { il.Emit(OpCodes.Box, helper.GetTypeReference(from.conversion_type).tp); } diff --git a/TestSuite/boxing2.pas b/TestSuite/boxing2.pas new file mode 100644 index 000000000..95fc9291b --- /dev/null +++ b/TestSuite/boxing2.pas @@ -0,0 +1,22 @@ +type + Ir1=interface end; + + r1=record(Ir1) + i: integer; + end; + +procedure Test(i: Ir1); +begin + assert(r1(i).i = 2); +end; + +begin + var a := new Ir1[1]; + var rrr: r1; + rrr.i := 2; + a[0] := rrr; + var i1: Ir1 := rrr; + assert(r1(a[0]).i = 2); + assert(r1(i1).i = 2); + Test(a[0]); +end. \ No newline at end of file