Skip to content

Commit bd042ac

Browse files
committed
Only save UUID in classfile
1 parent 2882c56 commit bd042ac

File tree

3 files changed

+25
-20
lines changed

3 files changed

+25
-20
lines changed

compiler/src/dotty/tools/backend/jvm/GenBCode.scala

Lines changed: 12 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ import scala.tools.asm
2626
import scala.tools.asm.tree._
2727
import tpd._
2828
import StdNames._
29-
import dotty.tools.dotc.core.tasty.TastyPickler
29+
import dotty.tools.dotc.core.tasty.{TastyBuffer, TastyHeaderUnpickler, TastyPickler}
3030
import dotty.tools.io._
3131

3232
class GenBCode extends Phase {
@@ -222,9 +222,17 @@ class GenBCodePipeline(val entryPoints: List[Symbol], val int: DottyBackendInter
222222
val outstream = new DataOutputStream(outTastyFile.bufferedOutput)
223223
try outstream.write(binary)
224224
finally outstream.close()
225-
// TASTY attribute is created but only the header bytes are stored in it.
226-
// A TASTY attribute has length `headerSize` if and only if the .tasty file exists.
227-
java.util.Arrays.copyOf(binary, TastyPickler.headerSize)
225+
226+
val uuid = new TastyHeaderUnpickler(binary).readHeader()
227+
val lo = uuid.getMostSignificantBits
228+
val hi = uuid.getLeastSignificantBits
229+
230+
// TASTY attribute is created but only the UUID bytes are stored in it.
231+
// A TASTY attribute has length 16 if and only if the .tasty file exists.
232+
val buffer = new TastyBuffer(16)
233+
buffer.writeUncompressedLong(lo)
234+
buffer.writeUncompressedLong(hi)
235+
buffer.bytes
228236
} else {
229237
// Create an empty file to signal that a tasty section exist in the corresponding .class
230238
// This is much cheaper and simpler to check than doing classfile parsing

compiler/src/dotty/tools/dotc/core/classfile/ClassfileParser.scala

Lines changed: 12 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -5,15 +5,16 @@ package classfile
55

66
import Contexts._, Symbols._, Types._, Names._, StdNames._, NameOps._, Scopes._, Decorators._
77
import SymDenotations._, unpickleScala2.Scala2Unpickler._, Constants._, Annotations._, util.Positions._
8-
import NameKinds.{ModuleClassName, DefaultGetterName}
9-
import dotty.tools.dotc.core.tasty.{TastyHeaderUnpickler, TastyPickler}
8+
import NameKinds.DefaultGetterName
9+
import dotty.tools.dotc.core.tasty.{TastyHeaderUnpickler, TastyReader}
1010
import ast.tpd._
11-
import java.io.{ ByteArrayInputStream, ByteArrayOutputStream, DataInputStream, File, IOException }
12-
import java.nio
11+
import java.io.{ ByteArrayInputStream, ByteArrayOutputStream, DataInputStream, IOException }
12+
1313
import java.lang.Integer.toHexString
1414
import java.net.URLClassLoader
15+
import java.util.UUID
1516

16-
import scala.collection.{ mutable, immutable }
17+
import scala.collection.immutable
1718
import scala.collection.mutable.{ ListBuffer, ArrayBuffer }
1819
import scala.annotation.switch
1920
import typer.Checking.checkNonCyclic
@@ -787,9 +788,7 @@ class ClassfileParser(
787788
if (scan(tpnme.TASTYATTR)) {
788789
val attrLen = in.nextInt
789790
val bytes = in.nextBytes(attrLen)
790-
val headerUnpickler = new TastyHeaderUnpickler(bytes)
791-
headerUnpickler.readHeader()
792-
if (headerUnpickler.isAtEnd) { // A tasty attribute with that has only a header implies the existence of the .tasty file
791+
if (bytes.length == 16) { // A tasty attribute with that has only a UUID implies the existence of the .tasty file
793792
val tastyBytes: Array[Byte] = classfile.underlyingSource match { // TODO: simplify when #3552 is fixed
794793
case None =>
795794
ctx.error("Could not load TASTY from .tasty for virtual file " + classfile)
@@ -821,8 +820,11 @@ class ClassfileParser(
821820
}
822821
}
823822
if (tastyBytes.nonEmpty) {
824-
if (!tastyBytes.startsWith(bytes))
825-
ctx.error("Header of TASTY file did not correspond to header in classfile. One of the files might be outdated or corrupted.")
823+
val reader = new TastyReader(bytes, 0, 16)
824+
val expectedUUID = new UUID(reader.readUncompressedLong(), reader.readUncompressedLong())
825+
val tastyUUID = new TastyHeaderUnpickler(tastyBytes).readHeader()
826+
if (expectedUUID != tastyUUID)
827+
ctx.error(s"Tasty UUID ($tastyUUID) file did not correspond the tasty UUID declared in the classfile ($expectedUUID).")
826828
return unpickleTASTY(tastyBytes)
827829
}
828830
}

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

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -29,13 +29,12 @@ class TastyPickler(val rootCls: ClassSymbol) {
2929
val uuidHi: Long = sections.iterator.map(x => pjwHash64(x._2.bytes)).fold(0L)(_ ^ _)
3030

3131
val headerBuffer = {
32-
val buf = new TastyBuffer(TastyPickler.headerSize)
32+
val buf = new TastyBuffer(header.length + 24)
3333
for (ch <- header) buf.writeByte(ch.toByte)
3434
buf.writeNat(MajorVersion)
3535
buf.writeNat(MinorVersion)
3636
buf.writeUncompressedLong(uuidLow)
3737
buf.writeUncompressedLong(uuidHi)
38-
assert(buf.length == TastyPickler.headerSize)
3938
buf
4039
}
4140

@@ -91,7 +90,3 @@ class TastyPickler(val rootCls: ClassSymbol) {
9190
h
9291
}
9392
}
94-
95-
object TastyPickler {
96-
val headerSize = header.length + 18
97-
}

0 commit comments

Comments
 (0)