Skip to content

Commit 5268c6f

Browse files
committed
Store source file in TASTY attributes
1 parent cb48537 commit 5268c6f

16 files changed

+104
-36
lines changed

compiler/src/dotty/tools/dotc/core/CompilationUnitInfo.scala

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,8 @@ import dotty.tools.tasty.TastyVersion
1414
class CompilationUnitInfo(
1515
val associatedFile: AbstractFile,
1616
val tastyVersion: Option[TastyVersion],
17-
val explicitNulls: Boolean
17+
val explicitNulls: Boolean,
18+
val sourceFile: Option[String],
1819
) {
1920

2021
override def toString(): String =
@@ -28,4 +29,5 @@ object CompilationUnitInfo:
2829
assocFile,
2930
tastyVersion = None,
3031
explicitNulls = explicitNulls,
32+
sourceFile = if assocFile.path.endsWith(".scala") then Some(assocFile.path) else None,
3133
)

compiler/src/dotty/tools/dotc/core/SymbolLoaders.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -434,6 +434,7 @@ class TastyLoader(val tastyFile: AbstractFile) extends SymbolLoader {
434434
tastyFile,
435435
tastyVersion = Some(tastyVersion),
436436
explicitNulls = attributes.explicitNulls,
437+
sourceFile = attributes.sourceFile,
437438
)
438439

439440
def description(using Context): String = "TASTy file " + tastyFile.toString

compiler/src/dotty/tools/dotc/core/Symbols.scala

Lines changed: 15 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -293,6 +293,20 @@ object Symbols {
293293
val compUnitInfo = compilationUnitInfo
294294
compUnitInfo != null && compUnitInfo.explicitNulls
295295

296+
/** The source file from which the symbol was compiled, None if not applicable. */
297+
def sourceFile(using Context): Option[String] =
298+
def sourceFromSourceFileAnnot = atPhaseNoLater(flattenPhase) {
299+
// Annotation present in sources compiled with 3.0-3.3
300+
denot.topLevelClass.unforcedAnnotation(defn.SourceFileAnnot) match
301+
case Some(sourceAnnot) => sourceAnnot.argumentConstant(0) match
302+
case Some(Constant(path: String)) => Some(path)
303+
case none => None
304+
case none => None
305+
}
306+
val compUnitInfo = compilationUnitInfo
307+
if compUnitInfo == null then sourceFromSourceFileAnnot
308+
else compUnitInfo.sourceFile.orElse(sourceFromSourceFileAnnot)
309+
296310
/** The class file from which this class was generated, null if not applicable. */
297311
final def binaryFile(using Context): AbstractFile | Null = {
298312
val file = associatedFile
@@ -493,13 +507,7 @@ object Symbols {
493507
else
494508
mySource = defn.patchSource(this)
495509
if !mySource.exists then
496-
mySource = atPhaseNoLater(flattenPhase) {
497-
denot.topLevelClass.unforcedAnnotation(defn.SourceFileAnnot) match
498-
case Some(sourceAnnot) => sourceAnnot.argumentConstant(0) match
499-
case Some(Constant(path: String)) => ctx.getSource(path)
500-
case none => NoSource
501-
case none => NoSource
502-
}
510+
mySource = sourceFile.map(ctx.getSource).getOrElse(NoSource)
503511
mySource
504512
}
505513

compiler/src/dotty/tools/dotc/core/tasty/AttributePickler.scala

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -12,11 +12,14 @@ object AttributePickler:
1212
pickler: TastyPickler,
1313
buf: TastyBuffer
1414
): Unit =
15-
if attributes.scala2StandardLibrary || attributes.explicitNulls then // or any other attribute is set
16-
pickler.newSection(AttributesSection, buf)
15+
pickler.newSection(AttributesSection, buf)
1716

18-
for tag <- attributes.booleanTags do
19-
buf.writeByte(tag)
17+
for tag <- attributes.booleanTags do
18+
buf.writeByte(tag)
19+
20+
for (tag, value) <- attributes.stringTagValues do
21+
buf.writeByte(tag)
22+
buf.writeUTF8(value)
2023

2124
end pickleAttributes
2225

compiler/src/dotty/tools/dotc/core/tasty/AttributeUnpickler.scala

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,16 @@ class AttributeUnpickler(reader: TastyReader):
1010

1111
lazy val attributes: Attributes = {
1212
val booleanTags = List.newBuilder[Int]
13+
val stringTagValue = List.newBuilder[(Int, String)]
1314

1415
while !isAtEnd do
15-
booleanTags += readByte()
16+
val tag = readByte()
17+
if tag < TastyFormat.firstStringAttrTag then
18+
booleanTags += tag
19+
else
20+
stringTagValue += ((tag, readUTF8()))
1621

17-
new Attributes(booleanTags.result())
22+
new Attributes(booleanTags.result(), stringTagValue.result())
1823
}
1924

2025
end AttributeUnpickler

compiler/src/dotty/tools/dotc/core/tasty/Attributes.scala

Lines changed: 10 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -4,20 +4,29 @@ import dotty.tools.tasty.TastyFormat
44

55
class Attributes(
66
val booleanTags: List[Int],
7+
val stringTagValues: List[(Int, String)],
78
) {
89
def scala2StandardLibrary: Boolean =
910
booleanTags.contains(TastyFormat.SCALA2STANDARDLIBRARYattr)
1011
def explicitNulls: Boolean =
1112
booleanTags.contains(TastyFormat.EXPLICITNULLSattr)
13+
def sourceFile: Option[String] =
14+
stringTagValues.find(_._1 == TastyFormat.SOURCEFILEattr).map(_._2)
1215
}
1316

1417
object Attributes:
1518
def apply(
19+
sourceFile: String,
1620
scala2StandardLibrary: Boolean,
1721
explicitNulls: Boolean,
1822
): Attributes =
1923
val booleanTags = List.newBuilder[Int]
2024
if scala2StandardLibrary then booleanTags += TastyFormat.SCALA2STANDARDLIBRARYattr
2125
if explicitNulls then booleanTags += TastyFormat.EXPLICITNULLSattr
22-
new Attributes(booleanTags.result())
26+
27+
val stringTagValues = List(
28+
(TastyFormat.SOURCEFILEattr, sourceFile)
29+
)
30+
31+
new Attributes(booleanTags.result(), stringTagValues)
2332
end apply

compiler/src/dotty/tools/dotc/core/tasty/CommentPickler.scala

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -22,11 +22,8 @@ object CommentPickler:
2222

2323
def pickleComment(addr: Addr, comment: Comment): Unit =
2424
if addr != NoAddr then
25-
val bytes = comment.raw.getBytes(StandardCharsets.UTF_8).nn
26-
val length = bytes.length
2725
buf.writeAddr(addr)
28-
buf.writeNat(length)
29-
buf.writeBytes(bytes, length)
26+
buf.writeUTF8(comment.raw)
3027
buf.writeLongInt(comment.span.coords)
3128

3229
def traverse(x: Any): Unit = x match

compiler/src/dotty/tools/dotc/core/tasty/CommentUnpickler.scala

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -19,11 +19,9 @@ class CommentUnpickler(reader: TastyReader) {
1919
val comments = new HashMap[Addr, Comment]
2020
while (!isAtEnd) {
2121
val addr = readAddr()
22-
val length = readNat()
23-
if (length > 0) {
24-
val bytes = readBytes(length)
22+
val rawComment = readUTF8()
23+
if (rawComment != "") {
2524
val position = new Span(readLongInt())
26-
val rawComment = new String(bytes, StandardCharsets.UTF_8)
2725
comments(addr) = Comment(position, rawComment)
2826
}
2927
}

compiler/src/dotty/tools/dotc/core/tasty/DottyUnpickler.scala

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,7 @@ class DottyUnpickler(bytes: Array[Byte], mode: UnpickleMode = UnpickleMode.TopLe
5757
private val treeUnpickler = unpickler.unpickle(treeSectionUnpickler(posUnpicklerOpt, commentUnpicklerOpt, attributeUnpicklerOpt)).get
5858

5959
def tastyAttributes: Attributes =
60-
attributeUnpicklerOpt.map(_.attributes).getOrElse(new Attributes(booleanTags = Nil))
60+
attributeUnpicklerOpt.map(_.attributes).getOrElse(new Attributes(booleanTags = Nil, stringTagValues = Nil))
6161

6262
/** Enter all toplevel classes and objects into their scopes
6363
* @param roots a set of SymDenotations that should be overwritten by unpickling

compiler/src/dotty/tools/dotc/core/tasty/TastyPrinter.scala

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@ import util.Spans.offsetToInt
1212
import dotty.tools.tasty.TastyFormat.{ASTsSection, PositionsSection, CommentsSection, AttributesSection}
1313
import java.nio.file.{Files, Paths}
1414
import dotty.tools.io.{JarArchive, Path}
15+
import java.nio.charset.StandardCharsets
1516

1617
object TastyPrinter:
1718

@@ -237,6 +238,9 @@ class TastyPrinter(bytes: Array[Byte]) {
237238

238239
for tag <- attributes.booleanTags do
239240
sb.append(" ").append(attributeTagToString(tag)).append("\n")
241+
for (tag, value) <- attributes.stringTagValues do
242+
sb.append(" ").append(attributeTagToString(tag))
243+
.append(" ").append(value).append("\n")
240244

241245
sb.result
242246
}

0 commit comments

Comments
 (0)