Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Commit ac137cf

Browse files
Dmitry Stefantsovcommit-bot@chromium.org
authored andcommitted
[cfe] Fix crash on conflicting generative and factory constructors
Closes #46745. Bug: dart-lang/sdk#46745 Change-Id: I5dba3433322a3358cf1c5b719e925800b9bf964d Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/208400 Reviewed-by: Johnni Winther <johnniwinther@google.com> Commit-Queue: Dmitry Stefantsov <dmitryas@google.com>
1 parent ec1fd6a commit ac137cf

14 files changed

+333
-5
lines changed

pkg/front_end/lib/src/fasta/kernel/kernel_target.dart

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1053,8 +1053,12 @@ class KernelTarget extends TargetImplementation {
10531053
// To report errors on the first definition of a constructor, we need to
10541054
// iterate until that last element.
10551055
ConstructorBuilder earliest = constructorBuilder;
1056-
while (earliest.next != null) {
1057-
earliest = earliest.next as ConstructorBuilder;
1056+
Builder earliestBuilder = constructorBuilder;
1057+
while (earliestBuilder.next != null) {
1058+
earliestBuilder = earliestBuilder.next!;
1059+
if (earliestBuilder is ConstructorBuilder) {
1060+
earliest = earliestBuilder;
1061+
}
10581062
}
10591063

10601064
bool isRedirecting = false;

pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart.strong.expect

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,34 @@ library /*isNonNullableByDefault*/;
1616
// D.new();
1717
// ^
1818
//
19+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:26:11: Error: 'E1' is already declared in this scope.
20+
// factory E1.new() => E1._(); // Error.
21+
// ^^
22+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:25:3: Context: Previous declaration of 'E1'.
23+
// E1();
24+
// ^^
25+
//
26+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:32:3: Error: 'E2' is already declared in this scope.
27+
// E2();
28+
// ^^
29+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:31:11: Context: Previous declaration of 'E2'.
30+
// factory E2.new() => E2._(); // Error.
31+
// ^^
32+
//
33+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:38:11: Error: 'E3' is already declared in this scope.
34+
// factory E3.new() = E3._; // Error.
35+
// ^^
36+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:37:3: Context: Previous declaration of 'E3'.
37+
// E3();
38+
// ^^
39+
//
40+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:44:3: Error: 'E4' is already declared in this scope.
41+
// E4(); // Error.
42+
// ^^
43+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:43:11: Context: Previous declaration of 'E4'.
44+
// factory E4.new() = E4._;
45+
// ^^
46+
//
1947
import self as self;
2048
import "dart:core" as core;
2149

@@ -39,4 +67,35 @@ class D extends core::Object {
3967
: super core::Object::•()
4068
;
4169
}
70+
class E1 extends core::Object {
71+
constructor _() → self::E1
72+
: super core::Object::•()
73+
;
74+
constructor •() → self::E1
75+
: super core::Object::•()
76+
;
77+
}
78+
class E2 extends core::Object {
79+
constructor _() → self::E2
80+
: super core::Object::•()
81+
;
82+
static factory •() → self::E2
83+
return new self::E2::_();
84+
}
85+
class E3 extends core::Object {
86+
constructor _() → self::E3
87+
: super core::Object::•()
88+
;
89+
constructor •() → self::E3
90+
: super core::Object::•()
91+
;
92+
}
93+
class E4 extends core::Object {
94+
static final field dynamic _redirecting# = <dynamic>[self::E4::•]/*isLegacy*/;
95+
constructor _() → self::E4
96+
: super core::Object::•()
97+
;
98+
static factory •() → self::E4
99+
let dynamic #redirecting_factory = self::E4::_ in invalid-expression;
100+
}
42101
static method main() → dynamic {}

pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart.strong.transformed.expect

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,34 @@ library /*isNonNullableByDefault*/;
1616
// D.new();
1717
// ^
1818
//
19+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:26:11: Error: 'E1' is already declared in this scope.
20+
// factory E1.new() => E1._(); // Error.
21+
// ^^
22+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:25:3: Context: Previous declaration of 'E1'.
23+
// E1();
24+
// ^^
25+
//
26+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:32:3: Error: 'E2' is already declared in this scope.
27+
// E2();
28+
// ^^
29+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:31:11: Context: Previous declaration of 'E2'.
30+
// factory E2.new() => E2._(); // Error.
31+
// ^^
32+
//
33+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:38:11: Error: 'E3' is already declared in this scope.
34+
// factory E3.new() = E3._; // Error.
35+
// ^^
36+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:37:3: Context: Previous declaration of 'E3'.
37+
// E3();
38+
// ^^
39+
//
40+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:44:3: Error: 'E4' is already declared in this scope.
41+
// E4(); // Error.
42+
// ^^
43+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:43:11: Context: Previous declaration of 'E4'.
44+
// factory E4.new() = E4._;
45+
// ^^
46+
//
1947
import self as self;
2048
import "dart:core" as core;
2149

@@ -39,4 +67,35 @@ class D extends core::Object {
3967
: super core::Object::•()
4068
;
4169
}
70+
class E1 extends core::Object {
71+
constructor _() → self::E1
72+
: super core::Object::•()
73+
;
74+
constructor •() → self::E1
75+
: super core::Object::•()
76+
;
77+
}
78+
class E2 extends core::Object {
79+
constructor _() → self::E2
80+
: super core::Object::•()
81+
;
82+
static factory •() → self::E2
83+
return new self::E2::_();
84+
}
85+
class E3 extends core::Object {
86+
constructor _() → self::E3
87+
: super core::Object::•()
88+
;
89+
constructor •() → self::E3
90+
: super core::Object::•()
91+
;
92+
}
93+
class E4 extends core::Object {
94+
static final field dynamic _redirecting# = <dynamic>[self::E4::•]/*isLegacy*/;
95+
constructor _() → self::E4
96+
: super core::Object::•()
97+
;
98+
static factory •() → self::E4
99+
let Never #redirecting_factory = self::E4::_ in invalid-expression;
100+
}
42101
static method main() → dynamic {}

pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart.weak.expect

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,34 @@ library /*isNonNullableByDefault*/;
1616
// D.new();
1717
// ^
1818
//
19+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:26:11: Error: 'E1' is already declared in this scope.
20+
// factory E1.new() => E1._(); // Error.
21+
// ^^
22+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:25:3: Context: Previous declaration of 'E1'.
23+
// E1();
24+
// ^^
25+
//
26+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:32:3: Error: 'E2' is already declared in this scope.
27+
// E2();
28+
// ^^
29+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:31:11: Context: Previous declaration of 'E2'.
30+
// factory E2.new() => E2._(); // Error.
31+
// ^^
32+
//
33+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:38:11: Error: 'E3' is already declared in this scope.
34+
// factory E3.new() = E3._; // Error.
35+
// ^^
36+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:37:3: Context: Previous declaration of 'E3'.
37+
// E3();
38+
// ^^
39+
//
40+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:44:3: Error: 'E4' is already declared in this scope.
41+
// E4(); // Error.
42+
// ^^
43+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:43:11: Context: Previous declaration of 'E4'.
44+
// factory E4.new() = E4._;
45+
// ^^
46+
//
1947
import self as self;
2048
import "dart:core" as core;
2149

@@ -39,4 +67,35 @@ class D extends core::Object {
3967
: super core::Object::•()
4068
;
4169
}
70+
class E1 extends core::Object {
71+
constructor _() → self::E1
72+
: super core::Object::•()
73+
;
74+
constructor •() → self::E1
75+
: super core::Object::•()
76+
;
77+
}
78+
class E2 extends core::Object {
79+
constructor _() → self::E2
80+
: super core::Object::•()
81+
;
82+
static factory •() → self::E2
83+
return new self::E2::_();
84+
}
85+
class E3 extends core::Object {
86+
constructor _() → self::E3
87+
: super core::Object::•()
88+
;
89+
constructor •() → self::E3
90+
: super core::Object::•()
91+
;
92+
}
93+
class E4 extends core::Object {
94+
static final field dynamic _redirecting# = <dynamic>[self::E4::•]/*isLegacy*/;
95+
constructor _() → self::E4
96+
: super core::Object::•()
97+
;
98+
static factory •() → self::E4
99+
let dynamic #redirecting_factory = self::E4::_ in invalid-expression;
100+
}
42101
static method main() → dynamic {}

pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart.weak.transformed.expect

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,34 @@ library /*isNonNullableByDefault*/;
1616
// D.new();
1717
// ^
1818
//
19+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:26:11: Error: 'E1' is already declared in this scope.
20+
// factory E1.new() => E1._(); // Error.
21+
// ^^
22+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:25:3: Context: Previous declaration of 'E1'.
23+
// E1();
24+
// ^^
25+
//
26+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:32:3: Error: 'E2' is already declared in this scope.
27+
// E2();
28+
// ^^
29+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:31:11: Context: Previous declaration of 'E2'.
30+
// factory E2.new() => E2._(); // Error.
31+
// ^^
32+
//
33+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:38:11: Error: 'E3' is already declared in this scope.
34+
// factory E3.new() = E3._; // Error.
35+
// ^^
36+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:37:3: Context: Previous declaration of 'E3'.
37+
// E3();
38+
// ^^
39+
//
40+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:44:3: Error: 'E4' is already declared in this scope.
41+
// E4(); // Error.
42+
// ^^
43+
// pkg/front_end/testcases/constructor_tearoffs/explicit_new_as_unnamed.dart:43:11: Context: Previous declaration of 'E4'.
44+
// factory E4.new() = E4._;
45+
// ^^
46+
//
1947
import self as self;
2048
import "dart:core" as core;
2149

@@ -39,4 +67,35 @@ class D extends core::Object {
3967
: super core::Object::•()
4068
;
4169
}
70+
class E1 extends core::Object {
71+
constructor _() → self::E1
72+
: super core::Object::•()
73+
;
74+
constructor •() → self::E1
75+
: super core::Object::•()
76+
;
77+
}
78+
class E2 extends core::Object {
79+
constructor _() → self::E2
80+
: super core::Object::•()
81+
;
82+
static factory •() → self::E2
83+
return new self::E2::_();
84+
}
85+
class E3 extends core::Object {
86+
constructor _() → self::E3
87+
: super core::Object::•()
88+
;
89+
constructor •() → self::E3
90+
: super core::Object::•()
91+
;
92+
}
93+
class E4 extends core::Object {
94+
static final field dynamic _redirecting# = <dynamic>[self::E4::•]/*isLegacy*/;
95+
constructor _() → self::E4
96+
: super core::Object::•()
97+
;
98+
static factory •() → self::E4
99+
let Never #redirecting_factory = self::E4::_ in invalid-expression;
100+
}
42101
static method main() → dynamic {}
Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
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+
class A {
6+
A._();
7+
factory A.foo() => A._();
8+
A.foo();
9+
}
10+
11+
main() {}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
class A {
2+
A._();
3+
factory A.foo() => A._();
4+
A.foo();
5+
}
6+
7+
main() {}
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
class A {
2+
A._();
3+
A.foo();
4+
factory A.foo() => A._();
5+
}
6+
7+
main() {}
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
library /*isNonNullableByDefault*/;
2+
//
3+
// Problems in library:
4+
//
5+
// pkg/front_end/testcases/general/issue46745.dart:8:3: Error: 'A.foo' is already declared in this scope.
6+
// A.foo();
7+
// ^^^^^
8+
// pkg/front_end/testcases/general/issue46745.dart:7:11: Context: Previous declaration of 'A.foo'.
9+
// factory A.foo() => A._();
10+
// ^^^^^
11+
//
12+
import self as self;
13+
import "dart:core" as core;
14+
15+
class A extends core::Object {
16+
constructor _() → self::A
17+
: super core::Object::•()
18+
;
19+
static factory foo() → self::A
20+
return new self::A::_();
21+
}
22+
static method main() → dynamic {}
Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
library /*isNonNullableByDefault*/;
2+
//
3+
// Problems in library:
4+
//
5+
// pkg/front_end/testcases/general/issue46745.dart:8:3: Error: 'A.foo' is already declared in this scope.
6+
// A.foo();
7+
// ^^^^^
8+
// pkg/front_end/testcases/general/issue46745.dart:7:11: Context: Previous declaration of 'A.foo'.
9+
// factory A.foo() => A._();
10+
// ^^^^^
11+
//
12+
import self as self;
13+
import "dart:core" as core;
14+
15+
class A extends core::Object {
16+
constructor _() → self::A
17+
;
18+
static factory foo() → self::A
19+
;
20+
}
21+
static method main() → dynamic
22+
;

0 commit comments

Comments
 (0)