Skip to content

Commit f260eba

Browse files
alexmarkovathomas
authored andcommitted
[vm/aot] Attach unboxing info to unreachable members
Unreachable members could be used as interface targets of dispatch table calls, so they should have correct unboxing metadata. This change fixes attaching unboxing info to such members. TEST=runtime/tests/vm/dart/regress_44563_test.dart Fixes #44563 Change-Id: I5da6a8d07048904eb94b05bfba11bdf72d655e12 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/177621 Reviewed-by: Aske Simon Christensen <[email protected]> Reviewed-by: Martin Kustermann <[email protected]> Commit-Queue: Alexander Markov <[email protected]>
1 parent 7c148d0 commit f260eba

File tree

3 files changed

+91
-31
lines changed

3 files changed

+91
-31
lines changed

pkg/vm/lib/transformations/type_flow/transformer.dart

Lines changed: 29 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -309,13 +309,6 @@ class AnnotateKernel extends RecursiveVisitor<Null> {
309309
if (_typeFlowAnalysis.isMemberUsed(member)) {
310310
if (member is Field) {
311311
_setInferredType(member, _typeFlowAnalysis.fieldType(member));
312-
313-
final unboxingInfoMetadata =
314-
_unboxingInfo.getUnboxingInfoOfMember(member);
315-
if (unboxingInfoMetadata != null &&
316-
!unboxingInfoMetadata.isFullyBoxed) {
317-
_unboxingInfoMetadata.mapping[member] = unboxingInfoMetadata;
318-
}
319312
} else {
320313
Args<Type> argTypes = _typeFlowAnalysis.argumentTypes(member);
321314
final uncheckedParameters =
@@ -346,36 +339,41 @@ class AnnotateKernel extends RecursiveVisitor<Null> {
346339
skipCheck: uncheckedParameters.contains(param));
347340
}
348341

349-
final unboxingInfoMetadata =
350-
_unboxingInfo.getUnboxingInfoOfMember(member);
351-
if (unboxingInfoMetadata != null &&
352-
!unboxingInfoMetadata.isFullyBoxed) {
353-
_unboxingInfoMetadata.mapping[member] = unboxingInfoMetadata;
354-
}
355-
356342
// TODO(alexmarkov): figure out how to pass receiver type.
357343
}
358-
} else if (!member.isAbstract &&
359-
!fieldMorpher.isExtraMemberWithReachableBody(member)) {
360-
_setUnreachable(member);
361-
} else if (member is! Field) {
344+
362345
final unboxingInfoMetadata =
363346
_unboxingInfo.getUnboxingInfoOfMember(member);
364-
if (unboxingInfoMetadata != null) {
365-
// Check for partitions that only have abstract methods should be marked as boxed.
366-
if (unboxingInfoMetadata.returnInfo ==
367-
UnboxingInfoMetadata.kUnboxingCandidate) {
368-
unboxingInfoMetadata.returnInfo = UnboxingInfoMetadata.kBoxed;
369-
}
370-
for (int i = 0; i < unboxingInfoMetadata.unboxedArgsInfo.length; i++) {
371-
if (unboxingInfoMetadata.unboxedArgsInfo[i] ==
347+
if (unboxingInfoMetadata != null && !unboxingInfoMetadata.isFullyBoxed) {
348+
_unboxingInfoMetadata.mapping[member] = unboxingInfoMetadata;
349+
}
350+
} else {
351+
if (!member.isAbstract &&
352+
!fieldMorpher.isExtraMemberWithReachableBody(member)) {
353+
_setUnreachable(member);
354+
}
355+
356+
if (member is! Field) {
357+
final unboxingInfoMetadata =
358+
_unboxingInfo.getUnboxingInfoOfMember(member);
359+
if (unboxingInfoMetadata != null) {
360+
// Check for partitions that only have abstract methods should be marked as boxed.
361+
if (unboxingInfoMetadata.returnInfo ==
372362
UnboxingInfoMetadata.kUnboxingCandidate) {
373-
unboxingInfoMetadata.unboxedArgsInfo[i] =
374-
UnboxingInfoMetadata.kBoxed;
363+
unboxingInfoMetadata.returnInfo = UnboxingInfoMetadata.kBoxed;
364+
}
365+
for (int i = 0;
366+
i < unboxingInfoMetadata.unboxedArgsInfo.length;
367+
i++) {
368+
if (unboxingInfoMetadata.unboxedArgsInfo[i] ==
369+
UnboxingInfoMetadata.kUnboxingCandidate) {
370+
unboxingInfoMetadata.unboxedArgsInfo[i] =
371+
UnboxingInfoMetadata.kBoxed;
372+
}
373+
}
374+
if (!unboxingInfoMetadata.isFullyBoxed) {
375+
_unboxingInfoMetadata.mapping[member] = unboxingInfoMetadata;
375376
}
376-
}
377-
if (!unboxingInfoMetadata.isFullyBoxed) {
378-
_unboxingInfoMetadata.mapping[member] = unboxingInfoMetadata;
379377
}
380378
}
381379
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
// Copyright (c) 2021, the Dart project authors. Please see the AUTHORS file
2+
// for details. All rights reserved. Use of this source code is governed by a
3+
// BSD-style license that can be found in the LICENSE file.
4+
5+
// Verifies that unboxing info is attached to a member with unreachable body,
6+
// which is still used as an interface target.
7+
// Regression test for https://github.com/dart-lang/sdk/issues/44563.
8+
9+
import 'package:expect/expect.dart';
10+
11+
class BaseClass {
12+
int get value => 0;
13+
}
14+
15+
class Class1 extends BaseClass {
16+
@pragma('vm:never-inline')
17+
int get value => 1;
18+
}
19+
20+
class Class2 extends BaseClass {
21+
@pragma('vm:never-inline')
22+
int get value => 2;
23+
}
24+
25+
bool nonConstantCondition = int.parse("1") == 1;
26+
27+
void main() {
28+
BaseClass obj = BaseClass();
29+
obj = nonConstantCondition ? Class1() : Class2();
30+
Expect.equals(1, obj.value);
31+
}
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
// Copyright (c) 2021, the Dart project authors. Please see the AUTHORS file
2+
// for details. All rights reserved. Use of this source code is governed by a
3+
// BSD-style license that can be found in the LICENSE file.
4+
5+
// Verifies that unboxing info is attached to a member with unreachable body,
6+
// which is still used as an interface target.
7+
// Regression test for https://github.com/dart-lang/sdk/issues/44563.
8+
9+
import 'package:expect/expect.dart';
10+
11+
class BaseClass {
12+
int get value => 0;
13+
}
14+
15+
class Class1 extends BaseClass {
16+
@pragma('vm:never-inline')
17+
int get value => 1;
18+
}
19+
20+
class Class2 extends BaseClass {
21+
@pragma('vm:never-inline')
22+
int get value => 2;
23+
}
24+
25+
bool nonConstantCondition = int.parse("1") == 1;
26+
27+
void main() {
28+
BaseClass obj = BaseClass();
29+
obj = nonConstantCondition ? Class1() : Class2();
30+
Expect.equals(1, obj.value);
31+
}

0 commit comments

Comments
 (0)