Android NDK support and build system refactoring (#585)
This commit is contained in:
+1
-1
@@ -169,7 +169,7 @@ internal class NativeIndexImpl(val library: NativeLibrary) : NativeIndex() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if (name == "__gnuc_va_list" || name == "va_list") {
|
if (name == "__gnuc_va_list" || name == "va_list" || name == "__va_list") {
|
||||||
// TODO: fix GNUC varargs support.
|
// TODO: fix GNUC varargs support.
|
||||||
return UnsupportedType
|
return UnsupportedType
|
||||||
}
|
}
|
||||||
|
|||||||
+69
-66
@@ -26,10 +26,9 @@ import kotlin.reflect.KFunction
|
|||||||
fun main(args: Array<String>) {
|
fun main(args: Array<String>) {
|
||||||
val konanHome = File(System.getProperty("konan.home")).absolutePath
|
val konanHome = File(System.getProperty("konan.home")).absolutePath
|
||||||
|
|
||||||
// TODO: remove OSX defaults.
|
|
||||||
val substitutions = mapOf(
|
val substitutions = mapOf(
|
||||||
"arch" to (System.getenv("TARGET_ARCH") ?: "x86-64"),
|
"arch" to (System.getenv("TARGET_ARCH") ?: "x86-64"),
|
||||||
"os" to (System.getenv("TARGET_OS") ?: detectHost())
|
"os" to (System.getenv("TARGET_OS") ?: host)
|
||||||
)
|
)
|
||||||
|
|
||||||
processLib(konanHome, substitutions, parseArgs(args))
|
processLib(konanHome, substitutions, parseArgs(args))
|
||||||
@@ -37,46 +36,54 @@ fun main(args: Array<String>) {
|
|||||||
|
|
||||||
private fun parseArgs(args: Array<String>): Map<String, List<String>> {
|
private fun parseArgs(args: Array<String>): Map<String, List<String>> {
|
||||||
val commandLine = mutableMapOf<String, MutableList<String>>()
|
val commandLine = mutableMapOf<String, MutableList<String>>()
|
||||||
for(index in 0..args.size-1 step 2) {
|
for (index in 0..args.size - 1 step 2) {
|
||||||
val key = args[index]
|
val key = args[index]
|
||||||
if (key[0] != '-') {
|
if (key[0] != '-') {
|
||||||
throw IllegalArgumentException("Expected a flag with initial dash: $key")
|
throw IllegalArgumentException("Expected a flag with initial dash: $key")
|
||||||
}
|
}
|
||||||
if (index+1 == args.size) {
|
if (index + 1 == args.size) {
|
||||||
throw IllegalArgumentException("Expected an value after $key")
|
throw IllegalArgumentException("Expected an value after $key")
|
||||||
}
|
}
|
||||||
val value = args[index+1]
|
val value = args[index + 1]
|
||||||
commandLine[key] ?. add(value) ?: commandLine.put(key, mutableListOf(value))
|
commandLine[key]?.add(value) ?: commandLine.put(key, mutableListOf(value))
|
||||||
}
|
}
|
||||||
return commandLine
|
return commandLine
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun detectHost(): String {
|
private val host: String by lazy {
|
||||||
val os = System.getProperty("os.name")
|
val os = System.getProperty("os.name")
|
||||||
when (os) {
|
when (os) {
|
||||||
"Linux" -> return "linux"
|
"Linux" -> "linux"
|
||||||
"Windows" -> return "win"
|
"Windows" -> "win"
|
||||||
"Mac OS X" -> return "osx"
|
"Mac OS X" -> "osx"
|
||||||
"FreeBSD" -> return "freebsd"
|
"FreeBSD" -> "freebsd"
|
||||||
else -> {
|
else -> {
|
||||||
throw IllegalArgumentException("we don't know ${os} value")
|
throw IllegalArgumentException("we don't know ${os} value")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun defaultTarget() = detectHost()
|
private val defaultTarget: String by lazy {
|
||||||
|
host
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: share KonanTarget class here.
|
||||||
private val knownTargets = mapOf(
|
private val knownTargets = mapOf(
|
||||||
"host" to defaultTarget(),
|
"host" to host,
|
||||||
"linux" to "linux",
|
"linux" to "linux",
|
||||||
"macbook" to "osx",
|
"macbook" to "osx",
|
||||||
"iphone" to "osx-ios",
|
"osx" to "osx",
|
||||||
"iphone_sim" to "osx-ios-sim",
|
"iphone" to "ios",
|
||||||
"raspberrypi" to "linux-raspberrypi")
|
"ios" to "ios",
|
||||||
|
"iphone_sim" to "ios_sim",
|
||||||
|
"ios_sim" to "ios_sim",
|
||||||
|
"raspberrypi" to "raspberrypi",
|
||||||
|
"android_arm32" to "android_arm32"
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
private fun String.targetSuffix(): String =
|
private fun String.targetSuffix(): String =
|
||||||
knownTargets[this] ?: error("Unsupported target $this.")
|
knownTargets[this] ?: error("Unsupported target $this.")
|
||||||
|
|
||||||
// Performs substitution similar to:
|
// Performs substitution similar to:
|
||||||
// foo = ${foo} ${foo.${arch}} ${foo.${os}}
|
// foo = ${foo} ${foo.${arch}} ${foo.${os}}
|
||||||
@@ -118,11 +125,17 @@ private fun String.matchesToGlob(glob: String): Boolean =
|
|||||||
java.nio.file.FileSystems.getDefault()
|
java.nio.file.FileSystems.getDefault()
|
||||||
.getPathMatcher("glob:$glob").matches(java.nio.file.Paths.get(this))
|
.getPathMatcher("glob:$glob").matches(java.nio.file.Paths.get(this))
|
||||||
|
|
||||||
private fun Properties.getOsSpecific(name: String,
|
private fun Properties.getHostSpecific(
|
||||||
host: String = detectHost()): String? {
|
name: String) = getProperty("$name.$host")
|
||||||
|
|
||||||
return this.getProperty("$name.$host")
|
private fun Properties.getTargetSpecific(
|
||||||
}
|
name: String, target: String) = getProperty("$name.$target")
|
||||||
|
|
||||||
|
private fun Properties.getHostTargetSpecific(
|
||||||
|
name: String, target: String) = if (host != target)
|
||||||
|
getProperty("$name.$host-$target")
|
||||||
|
else
|
||||||
|
getProperty("$name.$host")
|
||||||
|
|
||||||
private fun List<String>?.isTrue(): Boolean {
|
private fun List<String>?.isTrue(): Boolean {
|
||||||
// The rightmost wins, null != "true".
|
// The rightmost wins, null != "true".
|
||||||
@@ -176,51 +189,41 @@ private fun maybeExecuteHelper(dependenciesRoot: String, properties: Properties,
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun Properties.defaultCompilerOpts(target: String, dependencies: String): List<String> {
|
private fun Properties.defaultCompilerOpts(target: String, dependencies: String): List<String> {
|
||||||
|
val targetToolchainDir = getHostTargetSpecific("targetToolchain", target)!!
|
||||||
val arch = this.getOsSpecific("arch", target)!!
|
val targetToolchain = "$dependencies/$targetToolchainDir"
|
||||||
val hostSysRootDir = this.getOsSpecific("sysRoot")!!
|
val targetSysRootDir = getTargetSpecific("targetSysRoot", target)!!
|
||||||
val hostSysRoot = "$dependencies/$hostSysRootDir"
|
|
||||||
val targetSysRootDir = this.getOsSpecific("targetSysRoot", target) ?: hostSysRootDir
|
|
||||||
val targetSysRoot = "$dependencies/$targetSysRootDir"
|
val targetSysRoot = "$dependencies/$targetSysRootDir"
|
||||||
val sysRoot = targetSysRoot
|
val llvmHomeDir = getHostSpecific("llvmHome")!!
|
||||||
val llvmHomeDir = this.getOsSpecific("llvmHome")!!
|
|
||||||
val llvmHome = "$dependencies/$llvmHomeDir"
|
val llvmHome = "$dependencies/$llvmHomeDir"
|
||||||
|
|
||||||
System.load("$llvmHome/lib/${System.mapLibraryName("clang")}")
|
System.load("$llvmHome/lib/${System.mapLibraryName("clang")}")
|
||||||
|
|
||||||
val llvmVersion = this.getProperty("llvmVersion")!!
|
val llvmVersion = getProperty("llvmVersion")!!
|
||||||
|
|
||||||
// StubGenerator passes the arguments to libclang which
|
// StubGenerator passes the arguments to libclang which
|
||||||
// works not exactly the same way as the clang binary and
|
// works not exactly the same way as the clang binary and
|
||||||
// (in particular) uses different default header search path.
|
// (in particular) uses different default header search path.
|
||||||
// See e.g. http://lists.llvm.org/pipermail/cfe-dev/2013-November/033680.html
|
// See e.g. http://lists.llvm.org/pipermail/cfe-dev/2013-November/033680.html
|
||||||
// We workaround the problem with -isystem flag below.
|
// We workaround the problem with -isystem flag below.
|
||||||
val isystem = "$llvmHome/lib/clang/$llvmVersion/include"
|
val isystem = "$llvmHome/lib/clang/$llvmVersion/include"
|
||||||
|
val quadruple = getTargetSpecific("quadruple", target)
|
||||||
when (detectHost()) {
|
val arch = getTargetSpecific("arch", target)
|
||||||
|
val archSelector = if (quadruple != null)
|
||||||
|
listOf("-target", quadruple) else listOf("-arch", arch!!)
|
||||||
|
val commonArgs = listOf("-isystem", isystem, "--sysroot=$targetSysRoot")
|
||||||
|
when (host) {
|
||||||
"osx" -> {
|
"osx" -> {
|
||||||
val osVersionMinFlag = this.getOsSpecific("osVersionMinFlagClang", target)!!
|
val osVersionMinFlag = getTargetSpecific("osVersionMinFlagClang", target)
|
||||||
val osVersionMinValue = this.getOsSpecific("osVersionMin", target)!!
|
val osVersionMinValue = getTargetSpecific("osVersionMin", target)
|
||||||
|
return archSelector + commonArgs + listOf("-B$targetToolchain/bin") +
|
||||||
return listOf(
|
(if (osVersionMinFlag != null && osVersionMinValue != null)
|
||||||
"-arch", arch,
|
listOf("$osVersionMinFlag=$osVersionMinValue") else emptyList())
|
||||||
"-isystem", isystem,
|
|
||||||
"-B$hostSysRoot/usr/bin",
|
|
||||||
"--sysroot=$sysRoot",
|
|
||||||
"$osVersionMinFlag=$osVersionMinValue")
|
|
||||||
}
|
}
|
||||||
"linux" -> {
|
"linux" -> {
|
||||||
val gccToolChainDir = this.getOsSpecific("gccToolChain", target)!!
|
val libGcc = getTargetSpecific("libGcc", target)
|
||||||
val gccToolChain= "$dependencies/$gccToolChainDir"
|
val binDir = "$targetSysRoot/${libGcc ?: "bin"}"
|
||||||
val quadruple = this.getOsSpecific("quadruple", target)!!
|
return archSelector + commonArgs + listOf(
|
||||||
|
"-B$binDir", "--gcc-toolchain=$targetToolchain")
|
||||||
return listOf(
|
|
||||||
"-target", quadruple,
|
|
||||||
"-isystem", isystem,
|
|
||||||
"--gcc-toolchain=$gccToolChain",
|
|
||||||
"-L$llvmHome/lib",
|
|
||||||
"-B$hostSysRoot/../bin",
|
|
||||||
"--sysroot=$sysRoot")
|
|
||||||
}
|
}
|
||||||
else -> error("Unexpected target: ${target}")
|
else -> error("Unexpected target: ${target}")
|
||||||
}
|
}
|
||||||
@@ -280,7 +283,7 @@ Following flags are supported:
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun downloadDependencies(dependenciesRoot: String, target: String, konanProperties: Properties) {
|
private fun downloadDependencies(dependenciesRoot: String, target: String, konanProperties: Properties) {
|
||||||
val dependencyList = konanProperties.getOsSpecific("dependencies", target)?.split(' ') ?: listOf<String>()
|
val dependencyList = konanProperties.getHostTargetSpecific("dependencies", target)?.split(' ') ?: listOf<String>()
|
||||||
maybeExecuteHelper(dependenciesRoot, konanProperties, dependencyList)
|
maybeExecuteHelper(dependenciesRoot, konanProperties, dependencyList)
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -293,7 +296,7 @@ private fun processLib(konanHome: String,
|
|||||||
val nativeLibsDir = args["-natives"]?.single() ?: userDir
|
val nativeLibsDir = args["-natives"]?.single() ?: userDir
|
||||||
val flavorName = args["-flavor"]?.single() ?: "jvm"
|
val flavorName = args["-flavor"]?.single() ?: "jvm"
|
||||||
val flavor = KotlinPlatform.values().single { it.name.equals(flavorName, ignoreCase = true) }
|
val flavor = KotlinPlatform.values().single { it.name.equals(flavorName, ignoreCase = true) }
|
||||||
val target = args["-target"]?.single()?.targetSuffix() ?: defaultTarget()
|
val target = args["-target"]?.single()?.targetSuffix() ?: defaultTarget
|
||||||
val defFile = args["-def"]?.single()?.let { File(it) }
|
val defFile = args["-def"]?.single()?.let { File(it) }
|
||||||
|
|
||||||
if (defFile == null && args["-pkg"] == null) {
|
if (defFile == null && args["-pkg"] == null) {
|
||||||
@@ -304,14 +307,14 @@ private fun processLib(konanHome: String,
|
|||||||
val (config, defHeaderLines) = parseDefFile(defFile, substitutions)
|
val (config, defHeaderLines) = parseDefFile(defFile, substitutions)
|
||||||
|
|
||||||
val konanFileName = args["-properties"]?.single() ?:
|
val konanFileName = args["-properties"]?.single() ?:
|
||||||
"${konanHome}/konan/konan.properties"
|
"${konanHome}/konan/konan.properties"
|
||||||
val konanFile = File(konanFileName)
|
val konanFile = File(konanFileName)
|
||||||
val konanProperties = loadProperties(konanFile, mapOf())
|
val konanProperties = loadProperties(konanFile, mapOf())
|
||||||
val dependencies = "$konanHome/dependencies"
|
val dependencies = "$konanHome/dependencies"
|
||||||
downloadDependencies(dependencies, target, konanProperties)
|
downloadDependencies(dependencies, target, konanProperties)
|
||||||
|
|
||||||
// TODO: We can provide a set of flags to find the components in the absence of 'dist' or 'dist/dependencies'.
|
// TODO: We can provide a set of flags to find the components in the absence of 'dist' or 'dist/dependencies'.
|
||||||
val llvmHome = konanProperties.getOsSpecific("llvmHome")!!
|
val llvmHome = konanProperties.getHostSpecific("llvmHome")!!
|
||||||
val llvmInstallPath = "$dependencies/$llvmHome"
|
val llvmInstallPath = "$dependencies/$llvmHome"
|
||||||
val additionalHeaders = args["-h"].orEmpty()
|
val additionalHeaders = args["-h"].orEmpty()
|
||||||
val additionalCompilerOpts = args["-copt"].orEmpty()
|
val additionalCompilerOpts = args["-copt"].orEmpty()
|
||||||
@@ -321,18 +324,18 @@ private fun processLib(konanHome: String,
|
|||||||
|
|
||||||
val defaultOpts = konanProperties.defaultCompilerOpts(target, dependencies)
|
val defaultOpts = konanProperties.defaultCompilerOpts(target, dependencies)
|
||||||
val headerFiles = config.getSpaceSeparated("headers") + additionalHeaders
|
val headerFiles = config.getSpaceSeparated("headers") + additionalHeaders
|
||||||
val compilerOpts =
|
val compilerOpts =
|
||||||
config.getSpaceSeparated("compilerOpts") +
|
config.getSpaceSeparated("compilerOpts") +
|
||||||
defaultOpts + additionalCompilerOpts
|
defaultOpts + additionalCompilerOpts
|
||||||
val compiler = "clang"
|
val compiler = "clang"
|
||||||
val language = Language.C
|
val language = Language.C
|
||||||
val excludeSystemLibs = config.getProperty("excludeSystemLibs")?.toBoolean() ?: false
|
val excludeSystemLibs = config.getProperty("excludeSystemLibs")?.toBoolean() ?: false
|
||||||
val excludeDependentModules = config.getProperty("excludeDependentModules")?.toBoolean() ?: false
|
val excludeDependentModules = config.getProperty("excludeDependentModules")?.toBoolean() ?: false
|
||||||
|
|
||||||
val entryPoint = config.getSpaceSeparated("entryPoint").atMostOne()
|
val entryPoint = config.getSpaceSeparated("entryPoint").atMostOne()
|
||||||
val linkerOpts =
|
val linkerOpts =
|
||||||
config.getSpaceSeparated("linkerOpts").toTypedArray() +
|
config.getSpaceSeparated("linkerOpts").toTypedArray() +
|
||||||
defaultOpts + additionalLinkerOpts
|
defaultOpts + additionalLinkerOpts
|
||||||
val linker = args["-linker"]?.atMostOne() ?: config.getProperty("linker") ?: "clang"
|
val linker = args["-linker"]?.atMostOne() ?: config.getProperty("linker") ?: "clang"
|
||||||
val excludedFunctions = config.getSpaceSeparated("excludedFunctions").toSet()
|
val excludedFunctions = config.getSpaceSeparated("excludedFunctions").toSet()
|
||||||
|
|
||||||
|
|||||||
@@ -49,8 +49,10 @@ private fun maybeExecuteHelper(configuration: CompilerConfiguration) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
class K2Native : CLICompiler<K2NativeCompilerArguments>() {
|
private fun suffixIfNot(name: String, suffix: String) =
|
||||||
|
if (name.endsWith(suffix)) name else "$name$suffix"
|
||||||
|
|
||||||
|
class K2Native : CLICompiler<K2NativeCompilerArguments>() {
|
||||||
|
|
||||||
override fun doExecute(arguments : K2NativeCompilerArguments,
|
override fun doExecute(arguments : K2NativeCompilerArguments,
|
||||||
configuration : CompilerConfiguration,
|
configuration : CompilerConfiguration,
|
||||||
@@ -109,11 +111,11 @@ class K2Native : CLICompiler<K2NativeCompilerArguments>() {
|
|||||||
val library = arguments.outputFile ?: "library"
|
val library = arguments.outputFile ?: "library"
|
||||||
if (arguments.nolink)
|
if (arguments.nolink)
|
||||||
put(LIBRARY_NAME, library)
|
put(LIBRARY_NAME, library)
|
||||||
put(LIBRARY_FILE, "${library}.klib")
|
put(LIBRARY_FILE, suffixIfNot(library, ".klib"))
|
||||||
val program = arguments.outputFile ?: "program"
|
val program = arguments.outputFile ?: "program"
|
||||||
if (!arguments.nolink) {
|
if (!arguments.nolink) {
|
||||||
put(PROGRAM_NAME,program)
|
put(PROGRAM_NAME, program)
|
||||||
put(EXECUTABLE_FILE,"${program}.kexe")
|
put(EXECUTABLE_FILE, suffixIfNot(program, ".kexe"))
|
||||||
}
|
}
|
||||||
// This is a decision we could change
|
// This is a decision we could change
|
||||||
val module = if (arguments.nolink) library else program
|
val module = if (arguments.nolink) library else program
|
||||||
|
|||||||
+9
-18
@@ -23,9 +23,9 @@ class Distribution(val config: CompilerConfiguration) {
|
|||||||
|
|
||||||
val targetManager = TargetManager(config)
|
val targetManager = TargetManager(config)
|
||||||
val target = targetManager.currentName
|
val target = targetManager.currentName
|
||||||
val suffix = targetManager.currentSuffix()
|
val hostSuffix = targetManager.hostSuffix()
|
||||||
val hostSuffix = TargetManager.host.suffix
|
val hostTargetSuffix = targetManager.hostTargetSuffix()
|
||||||
init { if (!targetManager.crossCompile) assert(suffix == hostSuffix) }
|
val targetSuffix = targetManager.targetSuffix()
|
||||||
|
|
||||||
private fun findUserHome() = File(System.getProperty("user.home")).absolutePath
|
private fun findUserHome() = File(System.getProperty("user.home")).absolutePath
|
||||||
val userHome = findUserHome()
|
val userHome = findUserHome()
|
||||||
@@ -45,32 +45,23 @@ class Distribution(val config: CompilerConfiguration) {
|
|||||||
val klib = "$konanHome/klib"
|
val klib = "$konanHome/klib"
|
||||||
|
|
||||||
val dependenciesDir = "$konanHome/dependencies"
|
val dependenciesDir = "$konanHome/dependencies"
|
||||||
val dependencies = properties.propertyList("dependencies.$suffix")
|
val dependencies = properties.propertyList("dependencies.$hostTargetSuffix")
|
||||||
|
|
||||||
val stdlib = "$klib/stdlib"
|
val stdlib = "$klib/stdlib"
|
||||||
val runtime = config.get(KonanConfigKeys.RUNTIME_FILE)
|
val runtime = config.get(KonanConfigKeys.RUNTIME_FILE)
|
||||||
?: "$stdlib/$target/native/runtime.bc"
|
?: "$stdlib/$target/native/runtime.bc"
|
||||||
|
|
||||||
val llvmHome = "$dependenciesDir/${properties.propertyString("llvmHome.$hostSuffix")}"
|
val llvmHome = "$dependenciesDir/${properties.propertyString("llvmHome.$hostSuffix")}"
|
||||||
val sysRoot = "$dependenciesDir/${properties.propertyString("sysRoot.$hostSuffix")}"
|
val hostSysRoot = "$dependenciesDir/${properties.propertyString("targetSysRoot.$hostSuffix")}"
|
||||||
|
val targetSysRoot = "$dependenciesDir/${properties.propertyString("targetSysRoot.$targetSuffix")}"
|
||||||
val libGcc = "$dependenciesDir/${properties.propertyString("libGcc.$suffix")}"
|
val targetToolchain = "$dependenciesDir/${properties.propertyString("targetToolchain.$hostTargetSuffix")}"
|
||||||
val targetSysRoot = if (properties.hasProperty("targetSysRoot.$suffix")) {
|
val libffi =
|
||||||
"$dependenciesDir/${properties.propertyString("targetSysRoot.$suffix")}"
|
"$dependenciesDir/${properties.propertyString("libffiDir.$targetSuffix")}/lib/libffi.a"
|
||||||
} else {
|
|
||||||
sysRoot
|
|
||||||
}
|
|
||||||
|
|
||||||
val libffi = "$dependenciesDir/${properties.propertyString("libffiDir.$suffix")}/lib/libffi.a"
|
|
||||||
|
|
||||||
val llvmBin = "$llvmHome/bin"
|
val llvmBin = "$llvmHome/bin"
|
||||||
val llvmLib = "$llvmHome/lib"
|
val llvmLib = "$llvmHome/lib"
|
||||||
|
|
||||||
val llvmOpt = "$llvmBin/opt"
|
|
||||||
val llvmLlc = "$llvmBin/llc"
|
|
||||||
val llvmLto = "$llvmBin/llvm-lto"
|
val llvmLto = "$llvmBin/llvm-lto"
|
||||||
val llvmLink = "$llvmBin/llvm-link"
|
|
||||||
val libCppAbi = "$llvmLib/libc++abi.a"
|
|
||||||
val libLTO = when (TargetManager.host) {
|
val libLTO = when (TargetManager.host) {
|
||||||
KonanTarget.MACBOOK -> "$llvmLib/libLTO.dylib"
|
KonanTarget.MACBOOK -> "$llvmLib/libLTO.dylib"
|
||||||
KonanTarget.LINUX -> "$llvmLib/libLTO.so"
|
KonanTarget.LINUX -> "$llvmLib/libLTO.so"
|
||||||
|
|||||||
-1
@@ -23,7 +23,6 @@ import org.jetbrains.kotlin.backend.konan.library.KonanLibrarySearchPathResolver
|
|||||||
import org.jetbrains.kotlin.backend.konan.util.profile
|
import org.jetbrains.kotlin.backend.konan.util.profile
|
||||||
import org.jetbrains.kotlin.config.CommonConfigurationKeys
|
import org.jetbrains.kotlin.config.CommonConfigurationKeys
|
||||||
import org.jetbrains.kotlin.config.CompilerConfiguration
|
import org.jetbrains.kotlin.config.CompilerConfiguration
|
||||||
import org.jetbrains.kotlin.config.LanguageVersionSettings
|
|
||||||
import org.jetbrains.kotlin.descriptors.impl.ModuleDescriptorImpl
|
import org.jetbrains.kotlin.descriptors.impl.ModuleDescriptorImpl
|
||||||
import org.jetbrains.kotlin.backend.konan.util.File
|
import org.jetbrains.kotlin.backend.konan.util.File
|
||||||
|
|
||||||
|
|||||||
+1
-1
@@ -39,7 +39,7 @@ public class KonanProperties(val propertyFile: String) {
|
|||||||
|
|
||||||
fun propertyList(key: String, suffix: String? = null): List<String> {
|
fun propertyList(key: String, suffix: String? = null): List<String> {
|
||||||
val value = properties.getProperty(key.suffix(suffix))
|
val value = properties.getProperty(key.suffix(suffix))
|
||||||
return value?.split(' ') ?: listOf<String>()
|
return value?.split(' ') ?: emptyList()
|
||||||
}
|
}
|
||||||
|
|
||||||
fun hasProperty(key: String, suffix: String? = null): Boolean
|
fun hasProperty(key: String, suffix: String? = null): Boolean
|
||||||
|
|||||||
+8
-8
@@ -16,12 +16,12 @@
|
|||||||
|
|
||||||
package org.jetbrains.kotlin.backend.konan
|
package org.jetbrains.kotlin.backend.konan
|
||||||
|
|
||||||
import org.jetbrains.kotlin.config.CommonConfigurationKeys
|
|
||||||
import org.jetbrains.kotlin.config.CompilerConfiguration
|
import org.jetbrains.kotlin.config.CompilerConfiguration
|
||||||
|
|
||||||
enum class KonanTarget(val suffix: String, var enabled: Boolean = false) {
|
enum class KonanTarget(val suffix: String, var enabled: Boolean = false) {
|
||||||
|
ANDROID_ARM32("android_arm32"),
|
||||||
IPHONE("ios"),
|
IPHONE("ios"),
|
||||||
IPHONE_SIM("ios-sim"),
|
IPHONE_SIM("ios_sim"),
|
||||||
LINUX("linux"),
|
LINUX("linux"),
|
||||||
MACBOOK("osx"),
|
MACBOOK("osx"),
|
||||||
RASPBERRYPI("raspberrypi")
|
RASPBERRYPI("raspberrypi")
|
||||||
@@ -38,11 +38,13 @@ class TargetManager(val config: CompilerConfiguration) {
|
|||||||
KonanTarget.LINUX -> {
|
KonanTarget.LINUX -> {
|
||||||
KonanTarget.LINUX.enabled = true
|
KonanTarget.LINUX.enabled = true
|
||||||
KonanTarget.RASPBERRYPI.enabled = true
|
KonanTarget.RASPBERRYPI.enabled = true
|
||||||
|
KonanTarget.ANDROID_ARM32.enabled = true
|
||||||
}
|
}
|
||||||
KonanTarget.MACBOOK -> {
|
KonanTarget.MACBOOK -> {
|
||||||
KonanTarget.MACBOOK.enabled = true
|
KonanTarget.MACBOOK.enabled = true
|
||||||
KonanTarget.IPHONE.enabled = true
|
KonanTarget.IPHONE.enabled = true
|
||||||
KonanTarget.IPHONE_SIM.enabled = true
|
KonanTarget.IPHONE_SIM.enabled = true
|
||||||
|
KonanTarget.ANDROID_ARM32.enabled = true
|
||||||
}
|
}
|
||||||
else ->
|
else ->
|
||||||
error("Unknown host platform: $host")
|
error("Unknown host platform: $host")
|
||||||
@@ -78,10 +80,10 @@ class TargetManager(val config: CompilerConfiguration) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fun currentSuffix(): String {
|
fun hostSuffix() = host.suffix
|
||||||
return host.suffix +
|
fun hostTargetSuffix() =
|
||||||
if (host != current) "-${current.suffix}" else ""
|
if (current == host) host.suffix else "${host.suffix}-${current.suffix}"
|
||||||
}
|
fun targetSuffix() = current.suffix
|
||||||
|
|
||||||
companion object {
|
companion object {
|
||||||
fun host_os(): String {
|
fun host_os(): String {
|
||||||
@@ -109,7 +111,5 @@ class TargetManager(val config: CompilerConfiguration) {
|
|||||||
else -> error("Unknown host target: ${host_os()} ${host_arch()}")
|
else -> error("Unknown host target: ${host_os()} ${host_arch()}")
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
val crossCompile = (host != current)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+58
-77
@@ -29,67 +29,72 @@ typealias ExecutableFile = String
|
|||||||
internal abstract class PlatformFlags(val distribution: Distribution) {
|
internal abstract class PlatformFlags(val distribution: Distribution) {
|
||||||
val properties = distribution.properties
|
val properties = distribution.properties
|
||||||
|
|
||||||
val hostSuffix = TargetManager.host.suffix
|
val hostSuffix = distribution.hostTargetSuffix
|
||||||
val targetSuffix = distribution.suffix
|
val targetSuffix = distribution.targetSuffix
|
||||||
val arch = propertyTargetString("arch")
|
|
||||||
|
|
||||||
open val llvmLtoNooptFlags
|
open val llvmLtoNooptFlags
|
||||||
= propertyHostList("llvmLtoNooptFlags")
|
= propertyTargetList("llvmLtoNooptFlags")
|
||||||
open val llvmLtoOptFlags
|
open val llvmLtoOptFlags
|
||||||
= propertyHostList("llvmLtoOptFlags")
|
= propertyTargetList("llvmLtoOptFlags")
|
||||||
open val llvmLtoFlags
|
open val llvmLtoFlags
|
||||||
= propertyHostList("llvmLtoFlags")
|
= propertyTargetList("llvmLtoFlags")
|
||||||
open val entrySelector
|
open val entrySelector
|
||||||
= propertyHostList("entrySelector")
|
= propertyTargetList("entrySelector")
|
||||||
open val linkerOptimizationFlags
|
open val linkerOptimizationFlags
|
||||||
= propertyHostList("linkerOptimizationFlags")
|
= propertyTargetList("linkerOptimizationFlags")
|
||||||
open val linkerKonanFlags
|
open val linkerKonanFlags
|
||||||
= propertyHostList("linkerKonanFlags")
|
= propertyTargetList("linkerKonanFlags")
|
||||||
|
|
||||||
abstract val linker: String
|
abstract fun linkCommand(objectFiles: List<ObjectFile>,
|
||||||
|
|
||||||
abstract fun linkCommand(objectFiles: List<ObjectFile>,
|
|
||||||
executable: ExecutableFile, optimize: Boolean): List<String>
|
executable: ExecutableFile, optimize: Boolean): List<String>
|
||||||
|
|
||||||
protected fun propertyHostString(name: String)
|
protected fun propertyHostString(name: String)
|
||||||
= properties.propertyString(name, hostSuffix)!!
|
= properties.propertyString(name, hostSuffix)!!
|
||||||
protected fun propertyHostList(name: String)
|
protected fun propertyHostList(name: String)
|
||||||
= properties.propertyList(name, hostSuffix)
|
= properties.propertyList(name, hostSuffix)
|
||||||
protected fun propertyTargetString(name: String)
|
protected fun propertyTargetString(name: String)
|
||||||
= properties.propertyString(name, targetSuffix)!!
|
= properties.propertyString(name, targetSuffix)!!
|
||||||
protected fun propertyTargetList(name: String)
|
protected fun propertyTargetList(name: String)
|
||||||
= properties.propertyList(name, targetSuffix)
|
= properties.propertyList(name, targetSuffix)
|
||||||
protected fun propertyCommonString(name: String)
|
}
|
||||||
= properties.propertyString(name, null)!!
|
|
||||||
protected fun propertyCommonList(name: String)
|
|
||||||
= properties.propertyList(name, null)
|
internal open class AndroidPlatform(distribution: Distribution)
|
||||||
|
: PlatformFlags(distribution) {
|
||||||
|
|
||||||
|
private val prefix = "${distribution.targetToolchain}/bin/"
|
||||||
|
private val clang = "$prefix/clang"
|
||||||
|
|
||||||
|
override fun linkCommand(objectFiles: List<String>, executable: String, optimize: Boolean): List<String> {
|
||||||
|
return mutableListOf<String>(clang, "-o", executable, "-fPIC", "-shared") +
|
||||||
|
objectFiles +
|
||||||
|
(if (optimize) linkerOptimizationFlags else emptyList()) +
|
||||||
|
linkerKonanFlags
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
internal open class MacOSBasedPlatform(distribution: Distribution)
|
internal open class MacOSBasedPlatform(distribution: Distribution)
|
||||||
: PlatformFlags(distribution) {
|
: PlatformFlags(distribution) {
|
||||||
|
|
||||||
override val linker = "${distribution.sysRoot}/usr/bin/ld"
|
// TODO: move 'ld' out of the host sysroot, as it doesn't belong here.
|
||||||
|
private val linker = "${distribution.hostSysRoot}/usr/bin/ld"
|
||||||
private val dsymutil = "${distribution.llvmBin}/llvm-dsymutil"
|
private val dsymutil = "${distribution.llvmBin}/llvm-dsymutil"
|
||||||
|
|
||||||
open val osVersionMin = listOf(
|
open val osVersionMin by lazy {
|
||||||
propertyTargetString("osVersionMinFlagLd"),
|
listOf(
|
||||||
propertyTargetString("osVersionMin")+".0")
|
propertyTargetString("osVersionMinFlagLd"),
|
||||||
|
propertyTargetString("osVersionMin") + ".0")
|
||||||
open val sysRoot = distribution.sysRoot
|
}
|
||||||
open val targetSysRoot = distribution.targetSysRoot
|
|
||||||
|
|
||||||
override fun linkCommand(objectFiles: List<String>, executable: String, optimize: Boolean): List<String> {
|
override fun linkCommand(objectFiles: List<String>, executable: String, optimize: Boolean): List<String> {
|
||||||
|
return mutableListOf(linker, "-demangle") +
|
||||||
return mutableListOf<String>(linker, "-demangle") +
|
listOf("-object_path_lto", "temporary.o", "-lto_library", distribution.libLTO) +
|
||||||
listOf("-object_path_lto", "temporary.o", "-lto_library", distribution.libLTO) +
|
listOf("-dynamic", "-arch", propertyTargetString("arch")) +
|
||||||
listOf( "-dynamic", "-arch", arch) +
|
osVersionMin +
|
||||||
osVersionMin +
|
listOf("-syslibroot", distribution.targetSysRoot, "-o", executable) +
|
||||||
listOf("-syslibroot", "$targetSysRoot",
|
objectFiles +
|
||||||
"-o", executable) +
|
(if (optimize) linkerOptimizationFlags else emptyList()) +
|
||||||
objectFiles +
|
linkerKonanFlags + listOf("-lSystem")
|
||||||
if (optimize) linkerOptimizationFlags else {listOf<String>()} +
|
|
||||||
linkerKonanFlags +
|
|
||||||
listOf("-lSystem")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
open fun dsymutilCommand(executable: ExecutableFile): List<String> {
|
open fun dsymutilCommand(executable: ExecutableFile): List<String> {
|
||||||
@@ -104,29 +109,21 @@ internal open class MacOSBasedPlatform(distribution: Distribution)
|
|||||||
internal open class LinuxBasedPlatform(distribution: Distribution)
|
internal open class LinuxBasedPlatform(distribution: Distribution)
|
||||||
: PlatformFlags(distribution) {
|
: PlatformFlags(distribution) {
|
||||||
|
|
||||||
open val sysRoot = distribution.sysRoot
|
val targetSysRoot = distribution.targetSysRoot
|
||||||
open val targetSysRoot = distribution.targetSysRoot
|
|
||||||
|
|
||||||
val llvmLib = distribution.llvmLib
|
val llvmLib = distribution.llvmLib
|
||||||
val libGcc = distribution.libGcc
|
val libGcc = "$targetSysRoot/${propertyTargetString("libGcc")!!}"
|
||||||
|
val linker = "${distribution.targetToolchain}/bin/ld.gold"
|
||||||
override val linker = "${distribution.sysRoot}/../bin/ld.gold"
|
val pluginOptimizationFlags = propertyTargetList("pluginOptimizationFlags")
|
||||||
|
val specificLibs
|
||||||
open val pluginOptimizationFlags =
|
|
||||||
propertyHostList("pluginOptimizationFlags")
|
|
||||||
open val dynamicLinker =
|
|
||||||
propertyTargetString("dynamicLinker")
|
|
||||||
|
|
||||||
open val specificLibs
|
|
||||||
= propertyTargetList("abiSpecificLibraries").map{it -> "-L${targetSysRoot}/$it"}
|
= propertyTargetList("abiSpecificLibraries").map{it -> "-L${targetSysRoot}/$it"}
|
||||||
|
|
||||||
override fun linkCommand(objectFiles: List<String>, executable: String, optimize: Boolean): List<String> {
|
override fun linkCommand(objectFiles: List<String>, executable: String, optimize: Boolean): List<String> {
|
||||||
// TODO: Can we extract more to the konan.properties?
|
// TODO: Can we extract more to the konan.properties?
|
||||||
return mutableListOf<String>("$linker",
|
return mutableListOf(linker,
|
||||||
"--sysroot=${targetSysRoot}",
|
"--sysroot=${targetSysRoot}",
|
||||||
"-export-dynamic", "-z", "relro", "--hash-style=gnu",
|
"-export-dynamic", "-z", "relro", "--hash-style=gnu",
|
||||||
"--build-id", "--eh-frame-hdr", // "-m", "elf_x86_64",
|
"--build-id", "--eh-frame-hdr", // "-m", "elf_x86_64",
|
||||||
"-dynamic-linker", dynamicLinker,
|
"-dynamic-linker", propertyTargetString("dynamicLinker"),
|
||||||
"-o", executable,
|
"-o", executable,
|
||||||
"${targetSysRoot}/usr/lib64/crt1.o", "${targetSysRoot}/usr/lib64/crti.o", "${libGcc}/crtbegin.o",
|
"${targetSysRoot}/usr/lib64/crt1.o", "${targetSysRoot}/usr/lib64/crti.o", "${libGcc}/crtbegin.o",
|
||||||
"-L${llvmLib}", "-L${libGcc}") +
|
"-L${llvmLib}", "-L${libGcc}") +
|
||||||
@@ -147,22 +144,19 @@ internal class LinkStage(val context: Context) {
|
|||||||
|
|
||||||
val config = context.config.configuration
|
val config = context.config.configuration
|
||||||
|
|
||||||
val targetManager = context.config.targetManager
|
private val distribution = context.config.distribution
|
||||||
private val distribution =
|
|
||||||
context.config.distribution
|
|
||||||
private val properties = distribution.properties
|
|
||||||
|
|
||||||
val platform = when (TargetManager.host) {
|
val platform = when (context.config.targetManager.current) {
|
||||||
KonanTarget.LINUX ->
|
KonanTarget.LINUX, KonanTarget.RASPBERRYPI ->
|
||||||
LinuxBasedPlatform(distribution)
|
LinuxBasedPlatform(distribution)
|
||||||
KonanTarget.MACBOOK ->
|
KonanTarget.MACBOOK, KonanTarget.IPHONE, KonanTarget.IPHONE_SIM ->
|
||||||
MacOSBasedPlatform(distribution)
|
MacOSBasedPlatform(distribution)
|
||||||
|
KonanTarget.ANDROID_ARM32 ->
|
||||||
|
AndroidPlatform(distribution)
|
||||||
else ->
|
else ->
|
||||||
error("Unexpected host platform")
|
error("Unexpected target platform: ${context.config.targetManager.current}")
|
||||||
}
|
}
|
||||||
|
|
||||||
val suffix = targetManager.currentSuffix()
|
|
||||||
|
|
||||||
val optimize = config.get(KonanConfigKeys.OPTIMIZATION) ?: false
|
val optimize = config.get(KonanConfigKeys.OPTIMIZATION) ?: false
|
||||||
val nomain = config.get(KonanConfigKeys.NOMAIN) ?: false
|
val nomain = config.get(KonanConfigKeys.NOMAIN) ?: false
|
||||||
val emitted = context.bitcodeFileName
|
val emitted = context.bitcodeFileName
|
||||||
@@ -187,18 +181,6 @@ internal class LinkStage(val context: Context) {
|
|||||||
return combined
|
return combined
|
||||||
}
|
}
|
||||||
|
|
||||||
fun llvmLlc(file: BitcodeFile): ObjectFile {
|
|
||||||
val tmpObjectFile = File.createTempFile(File(file).name, ".o")
|
|
||||||
tmpObjectFile.deleteOnExit()
|
|
||||||
val objectFile = tmpObjectFile.absolutePath
|
|
||||||
|
|
||||||
val command = listOf(distribution.llvmLlc, "-o", objectFile, "-filetype=obj") +
|
|
||||||
properties.propertyList("llvmLlcFlags.$suffix") + listOf(file)
|
|
||||||
runTool(*command.toTypedArray())
|
|
||||||
|
|
||||||
return objectFile
|
|
||||||
}
|
|
||||||
|
|
||||||
fun asLinkerArgs(args: List<String>): List<String> {
|
fun asLinkerArgs(args: List<String>): List<String> {
|
||||||
val result = mutableListOf<String>()
|
val result = mutableListOf<String>()
|
||||||
for (arg in args) {
|
for (arg in args) {
|
||||||
@@ -220,8 +202,7 @@ internal class LinkStage(val context: Context) {
|
|||||||
// So we stick to "-alias _main _konan_main" on Mac.
|
// So we stick to "-alias _main _konan_main" on Mac.
|
||||||
// And just do the same on Linux.
|
// And just do the same on Linux.
|
||||||
val entryPointSelector: List<String>
|
val entryPointSelector: List<String>
|
||||||
get() = if (nomain) listOf()
|
get() = if (nomain) emptyList() else platform.entrySelector
|
||||||
else platform.entrySelector
|
|
||||||
|
|
||||||
fun link(objectFiles: List<ObjectFile>): ExecutableFile {
|
fun link(objectFiles: List<ObjectFile>): ExecutableFile {
|
||||||
val executable = config.get(KonanConfigKeys.EXECUTABLE_FILE)!!
|
val executable = config.get(KonanConfigKeys.EXECUTABLE_FILE)!!
|
||||||
@@ -265,7 +246,7 @@ internal class LinkStage(val context: Context) {
|
|||||||
fun linkStage() {
|
fun linkStage() {
|
||||||
context.log{"# Compiler root: ${distribution.konanHome}"}
|
context.log{"# Compiler root: ${distribution.konanHome}"}
|
||||||
|
|
||||||
val bitcodeFiles = listOf<BitcodeFile>(emitted) +
|
val bitcodeFiles = listOf(emitted) +
|
||||||
libraries.map{it -> it.bitcodePaths}.flatten()
|
libraries.map{it -> it.bitcodePaths}.flatten()
|
||||||
|
|
||||||
var objectFiles: List<String> = listOf()
|
var objectFiles: List<String> = listOf()
|
||||||
|
|||||||
+3
-3
@@ -187,7 +187,7 @@ internal fun ContextUtils.addGlobal(name: String, type: LLVMTypeRef,
|
|||||||
assert(LLVMGetNamedGlobal(context.llvmModule, name) == null)
|
assert(LLVMGetNamedGlobal(context.llvmModule, name) == null)
|
||||||
val result = LLVMAddGlobal(context.llvmModule, type, name)!!
|
val result = LLVMAddGlobal(context.llvmModule, type, name)!!
|
||||||
if (threadLocal)
|
if (threadLocal)
|
||||||
LLVMSetThreadLocalMode(result, LLVMThreadLocalMode.LLVMLocalExecTLSModel)
|
LLVMSetThreadLocalMode(result, runtime.tlsMode)
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -198,12 +198,12 @@ internal fun ContextUtils.importGlobal(name: String, type: LLVMTypeRef,
|
|||||||
assert (getGlobalType(found) == type)
|
assert (getGlobalType(found) == type)
|
||||||
assert (LLVMGetInitializer(found) == null)
|
assert (LLVMGetInitializer(found) == null)
|
||||||
if (threadLocal)
|
if (threadLocal)
|
||||||
assert(LLVMGetThreadLocalMode(found) == LLVMThreadLocalMode.LLVMLocalExecTLSModel)
|
assert(LLVMGetThreadLocalMode(found) == runtime.tlsMode)
|
||||||
return found
|
return found
|
||||||
} else {
|
} else {
|
||||||
val result = LLVMAddGlobal(context.llvmModule, type, name)!!
|
val result = LLVMAddGlobal(context.llvmModule, type, name)!!
|
||||||
if (threadLocal)
|
if (threadLocal)
|
||||||
LLVMSetThreadLocalMode(result, LLVMThreadLocalMode.LLVMLocalExecTLSModel)
|
LLVMSetThreadLocalMode(result, runtime.tlsMode)
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
+4
@@ -42,6 +42,10 @@ class Runtime(bitcodeFile: String) {
|
|||||||
|
|
||||||
val target = LLVMGetTarget(llvmModule)!!.toKString()
|
val target = LLVMGetTarget(llvmModule)!!.toKString()
|
||||||
|
|
||||||
|
// TODO: deduce TLS model from explicit config parameter.
|
||||||
|
val tlsMode = if (target.indexOf("android") != -1)
|
||||||
|
LLVMThreadLocalMode.LLVMGeneralDynamicTLSModel else LLVMThreadLocalMode.LLVMLocalExecTLSModel
|
||||||
|
|
||||||
val dataLayout = LLVMGetDataLayout(llvmModule)!!.toKString()
|
val dataLayout = LLVMGetDataLayout(llvmModule)!!.toKString()
|
||||||
|
|
||||||
val targetData = LLVMCreateTargetData(dataLayout)!!
|
val targetData = LLVMCreateTargetData(dataLayout)!!
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
|
|
||||||
#
|
#
|
||||||
# Copyright 2010-2017 JetBrains s.r.o.
|
# Copyright 2010-2017 JetBrains s.r.o.
|
||||||
#
|
#
|
||||||
@@ -19,11 +18,13 @@
|
|||||||
llvmVersion = 3.9.0
|
llvmVersion = 3.9.0
|
||||||
dependenciesUrl = http://download.jetbrains.com/kotlin/native
|
dependenciesUrl = http://download.jetbrains.com/kotlin/native
|
||||||
|
|
||||||
# macbook
|
# Mac OS X.
|
||||||
arch.osx = x86_64
|
|
||||||
sysRoot.osx = target-sysroot-1-darwin-macos
|
|
||||||
libffiDir.osx = libffi-3.2.1-2-darwin-macos
|
|
||||||
llvmHome.osx = clang-llvm-3.9.0-darwin-macos
|
llvmHome.osx = clang-llvm-3.9.0-darwin-macos
|
||||||
|
targetToolchain.osx = clang-llvm-3.9.0-darwin-macos
|
||||||
|
|
||||||
|
arch.osx = x86_64
|
||||||
|
targetSysRoot.osx = target-sysroot-1-darwin-macos
|
||||||
|
libffiDir.osx = libffi-3.2.1-2-darwin-macos
|
||||||
llvmLtoFlags.osx = -exported-symbol=_Konan_main
|
llvmLtoFlags.osx = -exported-symbol=_Konan_main
|
||||||
llvmLtoOptFlags.osx = -O3 -function-sections
|
llvmLtoOptFlags.osx = -O3 -function-sections
|
||||||
llvmLtoNooptFlags.osx = -O1
|
llvmLtoNooptFlags.osx = -O1
|
||||||
@@ -37,38 +38,55 @@ dependencies.osx = target-sysroot-1-darwin-macos \
|
|||||||
libffi-3.2.1-2-darwin-macos \
|
libffi-3.2.1-2-darwin-macos \
|
||||||
clang-llvm-3.9.0-darwin-macos
|
clang-llvm-3.9.0-darwin-macos
|
||||||
|
|
||||||
# iphone
|
# Apple iOS.
|
||||||
arch.osx-ios = arm64
|
targetToolchain.osx-ios = clang-llvm-3.9.0-darwin-macos
|
||||||
targetSysRoot.osx-ios = target-sysroot-2-darwin-ios
|
|
||||||
libffiDir.osx-ios = libffi-3.2.1-2-darwin-ios
|
|
||||||
osVersionMinFlagLd.osx-ios = -iphoneos_version_min
|
|
||||||
osVersionMinFlagClang.osx-ios = -miphoneos-version-min
|
|
||||||
osVersionMin.osx-ios = 8.0
|
|
||||||
dependencies.osx-ios = target-sysroot-1-darwin-macos \
|
dependencies.osx-ios = target-sysroot-1-darwin-macos \
|
||||||
libffi-3.2.1-2-darwin-ios \
|
libffi-3.2.1-2-darwin-ios \
|
||||||
clang-llvm-3.9.0-darwin-macos \
|
clang-llvm-3.9.0-darwin-macos \
|
||||||
target-sysroot-2-darwin-ios
|
target-sysroot-2-darwin-ios
|
||||||
|
|
||||||
# iphone_sim
|
arch.ios = arm64
|
||||||
arch.osx-ios-sim = x86_64
|
entrySelector.ios = -alias _Konan_main _main
|
||||||
targetSysRoot.osx-ios-sim = target-sysroot-1-darwin-ios-sim
|
targetSysRoot.ios = target-sysroot-2-darwin-ios
|
||||||
libffiDir.osx-ios-sim = libffi-3.2.1-2-darwin-ios-sim
|
libffiDir.ios = libffi-3.2.1-2-darwin-ios
|
||||||
osVersionMinFlagLd.osx-ios-sim = -ios_simulator_version_min
|
llvmLtoFlags.ios = -exported-symbol=_Konan_main
|
||||||
osVersionMinFlagClang.osx-ios-sim = -mios-simulator-version-min
|
llvmLtoOptFlags.ios = -O3 -function-sections
|
||||||
osVersionMin.osx-ios-sim = 8.0
|
llvmLtoNooptFlags.ios = -O1
|
||||||
dependencies.osx-ios-sim = target-sysroot-1-darwin-macos \
|
linkerKonanFlags.ios = -lc++
|
||||||
libffi-3.2.1-2-darwin-ios-sim \
|
linkerOptimizationFlags.ios = -dead_strip
|
||||||
clang-llvm-3.9.0-darwin-macos \
|
osVersionMinFlagLd.ios = -iphoneos_version_min
|
||||||
target-sysroot-1-darwin-ios-sim
|
osVersionMinFlagClang.ios = -miphoneos-version-min
|
||||||
|
osVersionMin.ios = 8.0
|
||||||
|
|
||||||
# linux
|
# Apple iOS simulator.
|
||||||
arch.linux = x86_64
|
targetToolchain.osx-ios_sim = clang-llvm-3.9.0-darwin-macos
|
||||||
quadruple.linux = x86_64-unknown-linux-gnu
|
dependencies.osx-ios_sim = target-sysroot-1-darwin-macos \
|
||||||
sysRoot.linux = target-gcc-toolchain-3-linux-x86-64/x86_64-unknown-linux-gnu/sysroot
|
libffi-3.2.1-2-darwin-ios_sim \
|
||||||
libffiDir.linux = libffi-3.2.1-2-linux-x86-64
|
clang-llvm-3.9.0-darwin-macos \
|
||||||
|
target-sysroot-1-darwin-ios_sim
|
||||||
|
|
||||||
|
arch.ios_sim = x86_64
|
||||||
|
entrySelector.ios_sim = -alias _Konan_main _main
|
||||||
|
targetSysRoot.ios_sim = target-sysroot-1-darwin-ios-sim
|
||||||
|
libffiDir.ios_sim = libffi-3.2.1-2-darwin-ios-sim
|
||||||
|
llvmLtoFlags.ios_sim = -exported-symbol=_Konan_main
|
||||||
|
llvmLtoOptFlags.ios_sim = -O3 -function-sections
|
||||||
|
llvmLtoNooptFlags.ios_sim = -O1
|
||||||
|
linkerKonanFlags.ios_sim = -lc++
|
||||||
|
linkerOptimizationFlags.ios_sim = -dead_strip
|
||||||
|
osVersionMinFlagLd.ios_sim = -ios_simulator_version_min
|
||||||
|
osVersionMinFlagClang.ios_sim = -mios-simulator-version-min
|
||||||
|
osVersionMin.ios_sim = 8.0
|
||||||
|
|
||||||
|
# Linux x86-64.
|
||||||
llvmHome.linux = clang-llvm-3.9.0-linux-x86-64
|
llvmHome.linux = clang-llvm-3.9.0-linux-x86-64
|
||||||
libGcc.linux = target-gcc-toolchain-3-linux-x86-64/lib/gcc/x86_64-unknown-linux-gnu/4.8.5
|
targetToolchain.linux = target-gcc-toolchain-3-linux-x86-64/x86_64-unknown-linux-gnu
|
||||||
gccToolChain.linux = target-gcc-toolchain-3-linux-x86-64
|
|
||||||
|
quadruple.linux = x86_64-unknown-linux-gnu
|
||||||
|
targetSysRoot.linux = target-gcc-toolchain-3-linux-x86-64/x86_64-unknown-linux-gnu/sysroot
|
||||||
|
libffiDir.linux = libffi-3.2.1-2-linux-x86-64
|
||||||
|
# targetSysroot-relative.
|
||||||
|
libGcc.linux = ../../lib/gcc/x86_64-unknown-linux-gnu/4.8.5
|
||||||
llvmLtoFlags.linux = -exported-symbol=Konan_main
|
llvmLtoFlags.linux = -exported-symbol=Konan_main
|
||||||
llvmLtoOptFlags.linux = -O3 -function-sections
|
llvmLtoOptFlags.linux = -O3 -function-sections
|
||||||
llvmLtoNooptFlags.linux = -O1
|
llvmLtoNooptFlags.linux = -O1
|
||||||
@@ -79,28 +97,57 @@ pluginOptimizationFlags.linux = -plugin-opt=mcpu=x86-64 -plugin-opt=O3
|
|||||||
dynamicLinker.linux = /lib64/ld-linux-x86-64.so.2
|
dynamicLinker.linux = /lib64/ld-linux-x86-64.so.2
|
||||||
entrySelector.linux = --defsym main=Konan_main
|
entrySelector.linux = --defsym main=Konan_main
|
||||||
# targetSysRoot relative
|
# targetSysRoot relative
|
||||||
abiSpecificLibraries = ../lib64 lib64 usr/lib64
|
abiSpecificLibraries.linux = ../lib64 lib64 usr/lib64
|
||||||
dependencies.linux = \
|
dependencies.linux = \
|
||||||
clang-llvm-3.9.0-linux-x86-64 \
|
clang-llvm-3.9.0-linux-x86-64 \
|
||||||
target-gcc-toolchain-3-linux-x86-64 \
|
target-gcc-toolchain-3-linux-x86-64 \
|
||||||
libffi-3.2.1-2-linux-x86-64
|
libffi-3.2.1-2-linux-x86-64
|
||||||
|
|
||||||
# Raspberry Pi
|
# Raspberry Pi
|
||||||
arch.linux-raspberrypi = armv6
|
targetToolchain.linux-raspberrypi = target-gcc-toolchain-3-linux-x86-64/x86_64-unknown-linux-gnu
|
||||||
quadruple.linux-raspberrypi = armv6-unknown-linux-gnueabihf
|
|
||||||
targetSysRoot.linux-raspberrypi = target-sysroot-1-raspberrypi
|
|
||||||
libffiDir.linux-raspberrypi = libffi-3.2.1-2-raspberrypi
|
|
||||||
libGcc.linux-raspberrypi = target-sysroot-1-raspberrypi/lib/gcc/arm-linux-gnueabihf/4.8.3/
|
|
||||||
gccToolChain.linux-raspberrypi = target-gcc-toolchain-3-linux-x86-64
|
|
||||||
dynamicLinker.linux-raspberrypi = /lib/ld-linux-armhf.so.3
|
|
||||||
# targetSysRoot relative
|
|
||||||
abiSpecificLibraries = \
|
|
||||||
../lib/arm-linux-gnueabihf \
|
|
||||||
lib/arm-linux-gnueabihf \
|
|
||||||
usr/lib/arm-linux-gnueabihf
|
|
||||||
dependencies.linux-raspberrypi = \
|
dependencies.linux-raspberrypi = \
|
||||||
clang-llvm-3.9.0-linux-x86-64 \
|
clang-llvm-3.9.0-linux-x86-64 \
|
||||||
target-gcc-toolchain-3-linux-x86-64 \
|
target-gcc-toolchain-3-linux-x86-64 \
|
||||||
target-sysroot-1-raspberrypi \
|
target-sysroot-1-raspberrypi \
|
||||||
libffi-3.2.1-2-linux-x86-64 \
|
libffi-3.2.1-2-linux-x86-64 \
|
||||||
libffi-3.2.1-2-raspberrypi
|
libffi-3.2.1-2-raspberrypi
|
||||||
|
|
||||||
|
quadruple.raspberrypi = armv6-unknown-linux-gnueabihf
|
||||||
|
entrySelector.raspberrypi = --defsym main=Konan_main
|
||||||
|
linkerOptimizationFlags.raspberrypi = --gc-sections
|
||||||
|
targetSysRoot.raspberrypi = target-sysroot-1-raspberrypi
|
||||||
|
# We could reuse host toolchain here.
|
||||||
|
libffiDir.raspberrypi = libffi-3.2.1-2-raspberrypi
|
||||||
|
linkerKonanFlags.raspberrypi = -Bstatic -lstdc++ -Bdynamic -ldl -lm -lpthread
|
||||||
|
# targetSysroot-relative.
|
||||||
|
libGcc.raspberrypi = lib/gcc/arm-linux-gnueabihf/4.8.3
|
||||||
|
llvmLtoFlags.raspberrypi = -exported-symbol=Konan_main
|
||||||
|
dynamicLinker.raspberrypi = /lib/ld-linux-armhf.so.3
|
||||||
|
llvmLtoFlags.linux = -exported-symbol=Konan_main
|
||||||
|
# targetSysRoot relative
|
||||||
|
abiSpecificLibraries.raspberrypi = \
|
||||||
|
../lib/arm-linux-gnueabihf \
|
||||||
|
lib/arm-linux-gnueabihf \
|
||||||
|
usr/lib/arm-linux-gnueabihf
|
||||||
|
|
||||||
|
# Android ARM32, based on NDK for android-21.
|
||||||
|
targetToolchain.osx-android_arm32 = target-toolchain-21-osx-android_arm32
|
||||||
|
# TODO: split dependencies to host-dependent and host-independent parts.
|
||||||
|
dependencies.osx-android_arm32 = \
|
||||||
|
clang-llvm-3.9.0-darwin-macos \
|
||||||
|
target-sysroot-21-android_arm32 \
|
||||||
|
target-toolchain-21-osx-android_arm32 \
|
||||||
|
libffi-3.2.1-2-android_arm32
|
||||||
|
targetToolchain.linux-android_arm32 = target-toolchain-21-linux-android_arm32
|
||||||
|
dependencies.linux-android_arm32 = \
|
||||||
|
clang-llvm-3.9.0-linux-x86-64 \
|
||||||
|
target-sysroot-21-android_arm32 \
|
||||||
|
target-toolchain-21-linux-android_arm32 \
|
||||||
|
libffi-3.2.1-2-android_arm32
|
||||||
|
|
||||||
|
quadruple.android_arm32 = arm-linux-androideabi
|
||||||
|
entrySelector.android_arm32 = -Wl,--defsym -Wl,main=Konan_main
|
||||||
|
llvmLtoFlags.android_arm32 = -exported-symbol=Konan_main -emulated-tls
|
||||||
|
targetSysRoot.android_arm32 = target-sysroot-21-android_arm32
|
||||||
|
libffiDir.android_arm32 = libffi-3.2.1-2-android_arm32
|
||||||
|
linkerKonanFlags.android_arm32 = -lm -latomic -lstdc++
|
||||||
@@ -92,6 +92,16 @@ void setupCompilationFlags() {
|
|||||||
// ["-stdlib=libc++", "-isysroot", "$iphoneSimSysrootDir", "-miphoneos-version-min=8.0.0"],
|
// ["-stdlib=libc++", "-isysroot", "$iphoneSimSysrootDir", "-miphoneos-version-min=8.0.0"],
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
ext.targetArgs << [
|
||||||
|
"android_arm32":
|
||||||
|
["-target", "arm-linux-androideabi",
|
||||||
|
"--sysroot=$android_arm32SysrootDir",
|
||||||
|
// HACKS!
|
||||||
|
/*"-D_LIBCPP_HAS_MUSL_LIBC",*/ "-DOMIT_BACKTRACE", "-D__ANDROID__",
|
||||||
|
"-I$android_arm32SysrootDir/usr/include/c++/4.9.x",
|
||||||
|
"-I$android_arm32SysrootDir/usr/include/c++/4.9.x/arm-linux-androideabi"
|
||||||
|
]
|
||||||
|
]
|
||||||
ext.targetList = ext.targetArgs.keySet() as List
|
ext.targetList = ext.targetArgs.keySet() as List
|
||||||
|
|
||||||
if (isLinux()) {
|
if (isLinux()) {
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <stdint.h>
|
#include <stdint.h>
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
#include "City.h"
|
#include "City.h"
|
||||||
|
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
#include <cassert>
|
#include <cassert>
|
||||||
|
|
||||||
#include "Names.h"
|
#include "Names.h"
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
/*
|
/*
|
||||||
SHA-1 in C
|
SHA-1 in C
|
||||||
By Steve Reid <steve@edmweb.com>
|
By Steve Reid <steve@edmweb.com>
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
#ifndef COMMON_BASE64_H
|
#ifndef COMMON_BASE64_H
|
||||||
#define COMMON_BASE64_H
|
#define COMMON_BASE64_H
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
#ifndef COMMON_CITY_H
|
#ifndef COMMON_CITY_H
|
||||||
#define COMMON_CITY_H
|
#define COMMON_CITY_H
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
#ifndef COMMON_NAMES_H
|
#ifndef COMMON_NAMES_H
|
||||||
#define COMMON_NAMES_H
|
#define COMMON_NAMES_H
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,18 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-2017 JetBrains s.r.o.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
#ifndef COMMON_SHA1_H
|
#ifndef COMMON_SHA1_H
|
||||||
#define COMMON_SHA1_H
|
#define COMMON_SHA1_H
|
||||||
|
|
||||||
|
|||||||
Vendored
+7
@@ -221,6 +221,13 @@ if (isLinux()) {
|
|||||||
// }
|
// }
|
||||||
}
|
}
|
||||||
|
|
||||||
|
task android_arm32Sysroot(type: HelperNativeDep) {
|
||||||
|
baseName = "target-sysroot-21-android_arm32"
|
||||||
|
}
|
||||||
|
|
||||||
|
task android_arm32Libffi(type: HelperNativeDep) {
|
||||||
|
baseName = "libffi-3.2.1-2-android_arm32"
|
||||||
|
}
|
||||||
|
|
||||||
task update(type: Copy) {
|
task update(type: Copy) {
|
||||||
dependsOn tasks.withType(NativeDep)
|
dependsOn tasks.withType(NativeDep)
|
||||||
|
|||||||
@@ -13,8 +13,9 @@
|
|||||||
* See the License for the specific language governing permissions and
|
* See the License for the specific language governing permissions and
|
||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
|
#ifndef OMIT_BACKTRACE
|
||||||
#include <execinfo.h>
|
#include <execinfo.h>
|
||||||
|
#endif
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
@@ -59,6 +60,12 @@ extern "C" {
|
|||||||
// TODO: this implementation is just a hack, e.g. the result is inexact;
|
// TODO: this implementation is just a hack, e.g. the result is inexact;
|
||||||
// however it is better to have an inexact stacktrace than not to have any.
|
// however it is better to have an inexact stacktrace than not to have any.
|
||||||
OBJ_GETTER0(GetCurrentStackTrace) {
|
OBJ_GETTER0(GetCurrentStackTrace) {
|
||||||
|
#if OMIT_BACKTRACE
|
||||||
|
ObjHeader* result = AllocArrayInstance(theArrayTypeInfo, 1, OBJ_RESULT);
|
||||||
|
ArrayHeader* array = result->array();
|
||||||
|
CreateStringFromCString("<UNIMPLEMENTED>", ArrayAddressOfElementAt(array, 0));
|
||||||
|
return result;
|
||||||
|
#else
|
||||||
const int maxSize = 32;
|
const int maxSize = 32;
|
||||||
void* buffer[maxSize];
|
void* buffer[maxSize];
|
||||||
|
|
||||||
@@ -74,6 +81,7 @@ OBJ_GETTER0(GetCurrentStackTrace) {
|
|||||||
symbols[index], ArrayAddressOfElementAt(array, index));
|
symbols[index], ArrayAddressOfElementAt(array, index));
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
void ThrowException(KRef exception) {
|
void ThrowException(KRef exception) {
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
# HTTP client
|
# HTTP client
|
||||||
|
|
||||||
This example shows how to communicate with libcurl, HTTP/HTTPS/FTP/etc client library.
|
This example shows how to communicate with libcurl, HTTP/HTTPS/FTP/etc client library.
|
||||||
|
Debian-like distros may need to `apt-get install libcurl4-openssl-dev`.
|
||||||
To build use `./build.sh` script without arguments (or specify `TARGET` variable if cross-compiling).
|
To build use `./build.sh` script without arguments (or specify `TARGET` variable if cross-compiling).
|
||||||
You also may use Gradle to build this sample: `../gradlew build`.
|
You also may use Gradle to build this sample: `../gradlew build`.
|
||||||
|
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ PATH=../../dist/bin:../../bin:$PATH
|
|||||||
DIR=.
|
DIR=.
|
||||||
|
|
||||||
CFLAGS_macbook=-I/opt/local/include
|
CFLAGS_macbook=-I/opt/local/include
|
||||||
CFLAGS_linux=-I/usr/include
|
CFLAGS_linux=-I/usr/include/x86_64-linux-gnu
|
||||||
LINKER_ARGS_macbook="-L/opt/local/lib -lcurl"
|
LINKER_ARGS_macbook="-L/opt/local/lib -lcurl"
|
||||||
LINKER_ARGS_linux="-L/usr/lib/x86_64-linux-gnu -lcurl"
|
LINKER_ARGS_linux="-L/usr/lib/x86_64-linux-gnu -lcurl"
|
||||||
|
|
||||||
@@ -23,5 +23,5 @@ LINKER_ARGS=${!var}
|
|||||||
var=COMPILER_ARGS_${TARGET}
|
var=COMPILER_ARGS_${TARGET}
|
||||||
COMPILER_ARGS=${!var} # add -opt for an optimized build.
|
COMPILER_ARGS=${!var} # add -opt for an optimized build.
|
||||||
|
|
||||||
cinterop -copt "$CFLAGS" -copt -I. -def $DIR/libcurl.def -target $TARGET -o libcurl.bc || exit 1
|
cinterop -copt "$CFLAGS" -copt -I. -copt -I/usr/include -def $DIR/libcurl.def -target $TARGET -o libcurl.bc || exit 1
|
||||||
konanc -target $TARGET src -library libcurl.bc -linkerArgs "$LINKER_ARGS" -o Curl.kexe || exit 1
|
konanc -target $TARGET src -library libcurl.bc -linkerArgs "$LINKER_ARGS" -o Curl.kexe || exit 1
|
||||||
|
|||||||
@@ -54,7 +54,7 @@ fun main(args: Array<String>) {
|
|||||||
val length = read(commFd, buffer, bufferLength)
|
val length = read(commFd, buffer, bufferLength)
|
||||||
.ensureUnixCallResult { it >= 0 }
|
.ensureUnixCallResult { it >= 0 }
|
||||||
|
|
||||||
if (length == 0L) {
|
if (length.toInt() == 0) {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -81,4 +81,4 @@ inline fun Long.ensureUnixCallResult(predicate: (Long) -> Boolean): Long {
|
|||||||
throw Error(strerror(errno)!!.toKString())
|
throw Error(strerror(errno)!!.toKString())
|
||||||
}
|
}
|
||||||
return this
|
return this
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -37,11 +37,10 @@ class DependencyDownloader(dependenciesRoot: File, val dependenciesUrl: String,
|
|||||||
|
|
||||||
class DependencyFile(directory: File, fileName: String) {
|
class DependencyFile(directory: File, fileName: String) {
|
||||||
val file = File(directory, fileName).apply { createNewFile() }
|
val file = File(directory, fileName).apply { createNewFile() }
|
||||||
private val dependencies_ = file.readLines().toMutableSet()
|
private val dependencies = file.readLines().toMutableSet()
|
||||||
val dependencies = dependencies_.toSet()
|
|
||||||
|
|
||||||
fun contains(dependency: String) = dependencies_.contains(dependency)
|
fun contains(dependency: String) = dependencies.contains(dependency)
|
||||||
fun add(dependency: String) = dependencies_.add(dependency)
|
fun add(dependency: String) = dependencies.add(dependency)
|
||||||
fun addWithSave(dependency: String) {
|
fun addWithSave(dependency: String) {
|
||||||
add(dependency)
|
add(dependency)
|
||||||
save()
|
save()
|
||||||
@@ -50,7 +49,7 @@ class DependencyDownloader(dependenciesRoot: File, val dependenciesUrl: String,
|
|||||||
fun save() {
|
fun save() {
|
||||||
val writer = file.writer()
|
val writer = file.writer()
|
||||||
writer.use {
|
writer.use {
|
||||||
dependencies_.forEach {
|
dependencies.forEach {
|
||||||
writer.write(it)
|
writer.write(it)
|
||||||
writer.write("\n")
|
writer.write("\n")
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user