[Runtime testing] Fix link errors caused by duplicated symbol __throw_length_error

This commit is contained in:
Ilya Matveev
2020-10-06 13:26:10 +07:00
committed by Ilya Matveev
parent a452346385
commit 788dd1c210
2 changed files with 78 additions and 31 deletions
@@ -9,6 +9,7 @@ import groovy.lang.Closure
import java.io.File
import javax.inject.Inject
import org.gradle.api.*
import org.gradle.api.file.ConfigurableFileCollection
import org.gradle.api.tasks.*
import org.jetbrains.kotlin.ExecClang
import org.jetbrains.kotlin.bitcode.CompileToBitcode
@@ -17,7 +18,7 @@ import org.jetbrains.kotlin.konan.target.*
open class CompileNativeTest @Inject constructor(
@InputFile val inputFile: File,
@Input val target: String
) : DefaultTask () {
) : DefaultTask() {
@OutputFile
var outputFile = project.buildDir.resolve("bin/test/$target/${inputFile.nameWithoutExtension}.o")
@@ -27,10 +28,54 @@ open class CompileNativeTest @Inject constructor(
@TaskAction
fun compile() {
val plugin = project.convention.getPlugin(ExecClang::class.java)
plugin.execBareClang(Action {
plugin.execBareClang {
it.executable = "clang++"
it.args = clangArgs + listOf(inputFile.absolutePath, "-o", outputFile.absolutePath)
})
}
}
}
open class LlvmLinkNativeTest @Inject constructor(
val baseName: String,
@Input val target: String,
@InputFile val mainFile: File
) : DefaultTask() {
@SkipWhenEmpty
@InputFiles
var inputFiles: ConfigurableFileCollection = project.files()
@OutputFile
var outputFile: File = project.buildDir.resolve("bitcode/test/$target/$baseName.bc")
@TaskAction
fun llvmLink() {
val llvmDir = project.property("llvmDir")
val tmpOutput = File.createTempFile("runtimeTests", ".bc").apply {
deleteOnExit()
}
// The runtime provides our implementations for some standard functions (see StdCppStubs.cpp).
// We need to internalize these symbols to avoid clashes with symbols provided by the C++ stdlib.
// But llvm-link -internalize is kinda broken: it links modules one by one and can't see usages
// of a symbol in subsequent modules. So it will mangle such symbols causing "unresolved symbol"
// errors at the link stage. So we have to run llvm-link twice: the first one links all modules
// except the one containing the entry point to a single *.bc without internalization. The second
// run internalizes this big module and links it with a module containing the entry point.
project.exec {
it.executable = "$llvmDir/bin/llvm-link"
it.args = listOf("-o", tmpOutput.absolutePath) + inputFiles.map { it.absolutePath }
}
project.exec {
it.executable = "$llvmDir/bin/llvm-link"
it.args = listOf(
"-o", outputFile.absolutePath,
mainFile.absolutePath,
tmpOutput.absolutePath,
"-internalize"
)
}
}
}
@@ -106,15 +151,6 @@ open class LinkNativeTest @Inject constructor(
}
}
@Suppress("UNCHECKED_CAST")
private fun <T: Task> T.configure(f: T.() -> Unit): T =
this.configure(object: Closure<Unit>(this) {
// Dynamically invoked by Groovy
fun doCall() {
f()
}
}) as T
fun createTestTask(
project: Project,
testTaskName: String,
@@ -137,7 +173,7 @@ fun createTestTask(
it.srcRoot,
"${it.folderName}Tests",
target, "test"
).configure {
).apply {
excludeFiles = emptyList()
includeFiles = listOf("**/*Test.cpp", "**/*Test.mm")
dependsOn(it)
@@ -153,29 +189,42 @@ fun createTestTask(
project.tasks.getByName("${target}Googletest") as CompileToBitcode,
project.tasks.getByName("${target}Googlemock") as CompileToBitcode
)
val compileToObjectFileTasks = (compileToBitcodeTasks + testedTasks + testFrameworkTasks).map {
val name = "${it.name}Object"
val clangFlags = platformManager.platform(konanTarget).configurables as ClangFlags
project.tasks.findByName(name) as? CompileNativeTest ?:
project.tasks.create(name,
CompileNativeTest::class.java,
it.outFile,
target
).configure {
dependsOn(it)
clangArgs.addAll(clangFlags.clangFlags)
clangArgs.addAll(clangFlags.clangNooptFlags)
}
val testSupportTask = project.tasks.getByName("${target}TestSupport") as CompileToBitcode
// TODO: It may make sense to merge llvm-link, compile and link to a single task.
val llvmLinkTask = project.tasks.create(
"${testTaskName}LlvmLink",
LlvmLinkNativeTest::class.java,
testTaskName, target, testSupportTask.outFile
).apply {
val tasksToLink = (compileToBitcodeTasks + testedTasks + testFrameworkTasks)
inputFiles = project.files(tasksToLink.map { it.outFile })
dependsOn(testSupportTask)
dependsOn(tasksToLink)
}
val clangFlags = platformManager.platform(konanTarget).configurables as ClangFlags
val compileTask = project.tasks.create(
"${testTaskName}Compile",
CompileNativeTest::class.java,
llvmLinkTask.outputFile,
target
).apply {
dependsOn(llvmLinkTask)
clangArgs.addAll(clangFlags.clangFlags)
clangArgs.addAll(clangFlags.clangNooptFlags)
}
val linkTask = LinkNativeTest.create(
project,
platformManager,
"${testTaskName}Link",
compileToObjectFileTasks.map { it.outputFile },
listOf(compileTask.outputFile),
target,
testTaskName
).configure {
dependsOn(compileToObjectFileTasks)
).apply {
dependsOn(compileTask)
}
return project.tasks.create(testTaskName, Exec::class.java).apply {
-2
View File
@@ -100,7 +100,6 @@ targetList.forEach { targetName ->
"${targetName}StdAllocRuntimeTests",
listOf(
"${targetName}Runtime",
"${targetName}TestSupport",
"${targetName}Strict",
"${targetName}Release",
"${targetName}StdAlloc"
@@ -112,7 +111,6 @@ targetList.forEach { targetName ->
"${targetName}MimallocRuntimeTests",
listOf(
"${targetName}Runtime",
"${targetName}TestSupport",
"${targetName}Strict",
"${targetName}Release",
"${targetName}Mimalloc",