File tree Expand file tree Collapse file tree 6 files changed +42
-5
lines changed
compiler/src/dotty/tools/dotc
library/src/scala/annotation Expand file tree Collapse file tree 6 files changed +42
-5
lines changed Original file line number Diff line number Diff line change @@ -1101,6 +1101,7 @@ class Definitions {
1101
1101
@ tu lazy val RetainsByNameAnnot : ClassSymbol = requiredClass(" scala.annotation.retainsByName" )
1102
1102
@ tu lazy val PublicInBinaryAnnot : ClassSymbol = requiredClass(" scala.annotation.publicInBinary" )
1103
1103
@ tu lazy val WitnessNamesAnnot : ClassSymbol = requiredClass(" scala.annotation.internal.WitnessNames" )
1104
+ @ tu lazy val StableNullAnnot : ClassSymbol = requiredClass(" scala.annotation.stableNull" )
1104
1105
1105
1106
@ tu lazy val JavaRepeatableAnnot : ClassSymbol = requiredClass(" java.lang.annotation.Repeatable" )
1106
1107
Original file line number Diff line number Diff line change @@ -186,15 +186,21 @@ object Nullables:
186
186
* Check `usedOutOfOrder` to see the explaination and example of "out of order".
187
187
* See more examples in `tests/explicit-nulls/neg/var-ref-in-closure.scala`.
188
188
*/
189
- def isTracked (ref : TermRef )(using Context ) =
189
+ def isTracked (ref : TermRef )(using Context ) = // true
190
+ val sym = ref.symbol
191
+
192
+ def isNullStableField : Boolean =
193
+ ref.prefix.isStable
194
+ && sym.isField
195
+ && sym.hasAnnotation(defn.StableNullAnnot )
196
+
190
197
ref.isStable
191
- || { val sym = ref.symbol
192
- val unit = ctx.compilationUnit
198
+ || isNullStableField
199
+ || { val unit = ctx.compilationUnit
193
200
! ref.usedOutOfOrder
194
201
&& sym.span.exists
195
202
&& (unit ne NoCompilationUnit ) // could be null under -Ytest-pickler
196
- && unit.assignmentSpans.contains(sym.span.start)
197
- }
203
+ && unit.assignmentSpans.contains(sym.span.start) }
198
204
199
205
/** The nullability context to be used after a case that matches pattern `pat`.
200
206
* If `pat` is `null`, this will assert that the selector `sel` is not null afterwards.
Original file line number Diff line number Diff line change
1
+ package scala .annotation
2
+
3
+ /** An annotation that can be used to mark a mutable field as trackable for nullability.
4
+ * With explicit nulls, a normal mutable field cannot be tracked for nullability by flow typing,
5
+ * since it can be updated to a null value at the same time.
6
+ * This annotation will force the compiler to track the field for nullability, as long as the
7
+ * prefix is a stable path.
8
+ * See `tests/explicit-nulls/pos/force-track-var-fields.scala` for an example.
9
+ */
10
+ private [scala] final class stableNull extends StaticAnnotation
Original file line number Diff line number Diff line change @@ -1141,6 +1141,7 @@ object Build {
1141
1141
file(s " ${baseDirectory.value}/src/scala/annotation/init.scala " ),
1142
1142
file(s " ${baseDirectory.value}/src/scala/annotation/unroll.scala " ),
1143
1143
file(s " ${baseDirectory.value}/src/scala/annotation/targetName.scala " ),
1144
+ file(s " ${baseDirectory.value}/src/scala/annotation/stableNull.scala " ),
1144
1145
file(s " ${baseDirectory.value}/src/scala/deriving/Mirror.scala " ),
1145
1146
file(s " ${baseDirectory.value}/src/scala/compiletime/package.scala " ),
1146
1147
file(s " ${baseDirectory.value}/src/scala/quoted/Type.scala " ),
@@ -1278,6 +1279,7 @@ object Build {
1278
1279
file(s " ${baseDirectory.value}/src/scala/annotation/init.scala " ),
1279
1280
file(s " ${baseDirectory.value}/src/scala/annotation/unroll.scala " ),
1280
1281
file(s " ${baseDirectory.value}/src/scala/annotation/targetName.scala " ),
1282
+ file(s " ${baseDirectory.value}/src/scala/annotation/stableNull.scala " ),
1281
1283
file(s " ${baseDirectory.value}/src/scala/deriving/Mirror.scala " ),
1282
1284
file(s " ${baseDirectory.value}/src/scala/compiletime/package.scala " ),
1283
1285
file(s " ${baseDirectory.value}/src/scala/quoted/Type.scala " ),
Original file line number Diff line number Diff line change @@ -22,6 +22,8 @@ object MiMaFilters {
22
22
23
23
ProblemFilters .exclude[DirectMissingMethodProblem ](" scala.Conversion.underlying" ),
24
24
ProblemFilters .exclude[MissingClassProblem ](" scala.Conversion$" ),
25
+
26
+ ProblemFilters .exclude[MissingClassProblem ](" scala.annotation.stableNull" ),
25
27
),
26
28
27
29
// Additions since last LTS
Original file line number Diff line number Diff line change
1
+ package scala
2
+
3
+ import scala .annotation .stableNull
4
+
5
+ class A :
6
+ @ stableNull var s : String | Null = null
7
+ def getS : String =
8
+ if s == null then s = " "
9
+ s
10
+
11
+ def test (a : A ): String =
12
+ if a.s == null then
13
+ a.s = " "
14
+ a.s
15
+ else
16
+ a.s
You can’t perform that action at this time.
0 commit comments