Skip to content

Commit a30fa20

Browse files
authored
Merge pull request #1964 from lwronski/native-lto
Add support for nativeLto options in command line and using directives
2 parents 4a53295 + f1bcec4 commit a30fa20

File tree

16 files changed

+122
-25
lines changed

16 files changed

+122
-25
lines changed

examples/scala-native/test.sc

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,5 +2,6 @@ import scala.scalanative.libc._
22
import scala.scalanative.unsafe._
33

44
Zone { implicit z =>
5-
stdio.printf(toCString("Hello from Scala Native\n"))
6-
}
5+
val io = StdioHelpers(stdio)
6+
io.printf(c"%s\n", c"Hello from Scala Native")
7+
}

modules/cli/src/main/scala/scala/cli/commands/shared/ScalaNativeOptions.scala

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,10 @@ final case class ScalaNativeOptions(
2323
@Tag(tags.should)
2424
nativeMode: Option[String] = None,
2525
@Group(HelpGroup.ScalaNative.toString)
26+
@HelpMessage("Link-time optimisation mode")
27+
@Tag(tags.should)
28+
nativeLto: Option[String] = None,
29+
@Group(HelpGroup.ScalaNative.toString)
2630
@HelpMessage("Set the Scala Native garbage collector")
2731
@Tag(tags.should)
2832
nativeGc: Option[String] = None,

modules/cli/src/main/scala/scala/cli/commands/shared/SharedOptions.scala

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -246,6 +246,7 @@ final case class SharedOptions(
246246
options.ScalaNativeOptions(
247247
nativeVersion,
248248
nativeMode,
249+
nativeLto,
249250
nativeGc,
250251
nativeClang,
251252
nativeClangpp,

modules/directives/src/main/scala/scala/build/preprocessing/directives/ScalaNative.scala

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,8 @@ import scala.cli.commands.SpecificationLevel
1414
|
1515
|`//> using nativeMode` _value_
1616
|
17+
|`//> using nativeLto` _value_
18+
|
1719
|`//> using nativeVersion` _value_
1820
|
1921
|`//> using nativeCompile` _value1_, _value2_
@@ -32,6 +34,7 @@ import scala.cli.commands.SpecificationLevel
3234
final case class ScalaNative(
3335
nativeGc: Option[String] = None,
3436
nativeMode: Option[String] = None,
37+
nativeLto: Option[String] = None,
3538
nativeVersion: Option[String] = None,
3639
nativeCompile: List[String] = Nil,
3740
nativeLinking: List[String] = Nil,
@@ -45,6 +48,7 @@ final case class ScalaNative(
4548
val nativeOptions = ScalaNativeOptions(
4649
gcStr = nativeGc,
4750
modeStr = nativeMode,
51+
ltoStr = nativeLto,
4852
version = nativeVersion,
4953
compileOptions = nativeCompile,
5054
linkingOptions = nativeLinking,

modules/integration/src/test/scala/scala/cli/integration/ExportJsonTestDefinitions.scala

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -98,10 +98,10 @@ abstract class ExportJsonTestDefinitions(val scalaVersionOpt: Option[String])
9898
)
9999

100100
expect(fileContents ==
101-
"""{
101+
s"""{
102102
|"scalaVersion":"3.2.2",
103103
|"platform":"Native",
104-
|"scalaNativeVersion":"0.4.9",
104+
|"scalaNativeVersion":"${Constants.scalaNativeVersion}",
105105
|"scopes": {
106106
| "main": {
107107
| "sources": ["Main.scala"],

modules/integration/src/test/scala/scala/cli/integration/ExportTestProjects.scala

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,8 @@ object ExportTestProjects {
111111
| def main(args: Array[String]): Unit =
112112
| val message = "Hello from " + "exported Scala CLI project" + "$nl"
113113
| Zone { implicit z =>
114-
| stdio.printf(toCString(message))
114+
| val io = StdioHelpers(stdio)
115+
| io.printf(c"%s", toCString(message))
115116
| }
116117
|""".stripMargin
117118
else
@@ -125,7 +126,8 @@ object ExportTestProjects {
125126
| def main(args: Array[String]): Unit = {
126127
| val message = "Hello from " + "exported Scala CLI project" + "$nl"
127128
| Zone { implicit z =>
128-
| stdio.printf(toCString(message))
129+
| val io = StdioHelpers(stdio)
130+
| io.printf(c"%s", toCString(message))
129131
| }
130132
| }
131133
|}

modules/integration/src/test/scala/scala/cli/integration/PackageTestDefinitions.scala

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -400,7 +400,8 @@ abstract class PackageTestDefinitions(val scalaVersionOpt: Option[String])
400400
|import scala.scalanative.unsafe._
401401
|
402402
|Zone { implicit z =>
403-
| stdio.printf(toCString("$message$platformNl"))
403+
| val io = StdioHelpers(stdio)
404+
| io.printf(c"%s$platformNl", c"$message")
404405
|}
405406
|""".stripMargin
406407
)

modules/integration/src/test/scala/scala/cli/integration/RunScalaNativeTestDefinitions.scala

Lines changed: 31 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,8 @@ trait RunScalaNativeTestDefinitions { _: RunTestDefinitions =>
1515
|import scala.scalanative.unsafe._
1616
|
1717
|Zone { implicit z =>
18-
| stdio.printf(toCString("$message$platformNl"))
18+
| val io = StdioHelpers(stdio)
19+
| io.printf(c"%s$platformNl", c"$message")
1920
|}
2021
|""".stripMargin
2122
)
@@ -32,6 +33,29 @@ trait RunScalaNativeTestDefinitions { _: RunTestDefinitions =>
3233
simpleNativeTests()
3334
}
3435

36+
def scalaNativeLtoTests(): Unit = {
37+
val fileName = "hello.sc"
38+
val message = "Hello"
39+
val inputs = TestInputs(
40+
os.rel / fileName ->
41+
s"""//> using nativeLto "thin"
42+
|println("$message")
43+
|""".stripMargin
44+
)
45+
inputs.fromRoot { root =>
46+
val output =
47+
os.proc(TestUtil.cli, extraOptions, fileName, "--native")
48+
.call(cwd = root)
49+
.out.trim()
50+
expect(output == message)
51+
}
52+
}
53+
54+
if (!Properties.isMac)
55+
test("scala native with lto optimisation") {
56+
scalaNativeLtoTests()
57+
}
58+
3559
test("simple script native command") {
3660
val fileName = "simple.sc"
3761
val message = "Hello"
@@ -41,7 +65,8 @@ trait RunScalaNativeTestDefinitions { _: RunTestDefinitions =>
4165
|import scala.scalanative.unsafe._
4266
|
4367
|Zone { implicit z =>
44-
| stdio.printf(toCString("$message$platformNl"))
68+
| val io = StdioHelpers(stdio)
69+
| io.printf(c"%s$platformNl", c"$message")
4570
|}
4671
|""".stripMargin
4772
)
@@ -179,7 +204,8 @@ trait RunScalaNativeTestDefinitions { _: RunTestDefinitions =>
179204
|import scala.scalanative.unsafe._
180205
|
181206
|Zone { implicit z =>
182-
| stdio.printf(toCString(messages.msg + "$platformNl"))
207+
| val io = StdioHelpers(stdio)
208+
| io.printf(c"%s$platformNl", toCString(messages.msg))
183209
|}
184210
|""".stripMargin
185211
)
@@ -207,7 +233,8 @@ trait RunScalaNativeTestDefinitions { _: RunTestDefinitions =>
207233
|import scala.scalanative.unsafe._
208234
|
209235
|Zone { implicit z =>
210-
| stdio.printf(toCString(messages.msg + "$platformNl"))
236+
| val io = StdioHelpers(stdio)
237+
| io.printf(c"%s$platformNl", toCString(messages.msg))
211238
|}
212239
|""".stripMargin
213240
)

modules/integration/src/test/scala/scala/cli/integration/TestTestDefinitions.scala

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -85,7 +85,8 @@ abstract class TestTestDefinitions(val scalaVersionOpt: Option[String])
8585
| test("foo") {
8686
| assert(2 + 2 == 4)
8787
| Zone { implicit z =>
88-
| stdio.printf(toCString("Hello from " + "tests\n"))
88+
| val io = StdioHelpers(stdio)
89+
| io.printf(c"%s %s\n", c"Hello from", c"tests")
8990
| }
9091
| }
9192
| }

modules/options/src/main/scala/scala/build/options/ScalaNativeOptions.scala

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,11 +6,13 @@ import dependency._
66
import java.nio.file.Paths
77

88
import scala.build.internal.Constants
9+
import scala.scalanative.build.LTO
910
import scala.scalanative.{build => sn}
1011

1112
final case class ScalaNativeOptions(
1213
version: Option[String] = None,
1314
modeStr: Option[String] = None,
15+
ltoStr: Option[String] = None,
1416
gcStr: Option[String] = None,
1517
clang: Option[String] = None,
1618
clangpp: Option[String] = None,
@@ -65,7 +67,10 @@ final case class ScalaNativeOptions(
6567

6668
private def compileCliOptions(): List[String] =
6769
finalCompileOptions().flatMap(option => List("--compile-option", option))
68-
70+
private def ltoOptions(): List[String] =
71+
ltoStr.map(_.trim).filter(_.nonEmpty)
72+
.map(lto => LTO.apply(lto))
73+
.map(lto => List("--lto", lto.name)).getOrElse(Nil)
6974
private def resourcesCliOptions(resourcesExist: Boolean): List[String] =
7075
if (embedResources.getOrElse(true))
7176
(numeralVersion, resourcesExist) match {
@@ -113,6 +118,7 @@ final case class ScalaNativeOptions(
113118
def configCliOptions(resourcesExist: Boolean): List[String] =
114119
gcCliOption() ++
115120
modeCliOption() ++
121+
ltoOptions() ++
116122
clangCliOption() ++
117123
clangppCliOption() ++
118124
linkingCliOptions() ++

0 commit comments

Comments
 (0)