From f1256edb02f191287fcdf3d08a4a46d8882953a7 Mon Sep 17 00:00:00 2001 From: Ilya Matveev Date: Wed, 24 May 2017 18:36:37 +0700 Subject: [PATCH] build: Use konan.properties values for some building constants. This patch uses values provided by konan.properties to specify build dependencies (libffi and sysroots) and the "target" parameter for LLVM. --- backend.native/build.gradle | 2 +- build.gradle | 269 ++++++++++++++++++------------------ dependencies/build.gradle | 93 ++++++++----- 3 files changed, 199 insertions(+), 165 deletions(-) diff --git a/backend.native/build.gradle b/backend.native/build.gradle index 149dd7ad473..55375404510 100644 --- a/backend.native/build.gradle +++ b/backend.native/build.gradle @@ -239,7 +239,7 @@ targetList.each { target -> '-target', target, '-library', project(':runtime').file("build/${target}Stdlib"), '-runtime', project(':runtime').file("build/${target}/runtime.bc"), - '-properties', project(':backend.native').file('konan.properties'), + '-properties', rootProject.konanPropertiesFile.canonicalPath, project(':runtime').file('src/launcher/kotlin'), *project.globalBuildArgs) diff --git a/build.gradle b/build.gradle index 9aa3bd692f3..303599e54ca 100644 --- a/build.gradle +++ b/build.gradle @@ -23,11 +23,11 @@ convention.plugins.platformInfo = new PlatformInfo() allprojects { if (path != ":dependencies") { - evaluationDependsOn(":dependencies") + evaluationDependsOn(":dependencies") } repositories { - mavenCentral() + mavenCentral() } loadCommandLineProperties() @@ -41,25 +41,33 @@ void setupClang(Project project) { project.convention.plugins.execClang = new org.jetbrains.kotlin.ExecClang(project) project.plugins.withType(NativeComponentPlugin) { - project.model { - toolChains { - clang(Clang) { - clangPath.each { - path it - } + project.model { + toolChains { + clang(Clang) { + clangPath.each { + path it + } - eachPlatform { // TODO: will not work when cross-compiling - [cCompiler, cppCompiler, linker].each { - it.withArguments { it.addAll(hostClangArgs) } - } + eachPlatform { // TODO: will not work when cross-compiling + [cCompiler, cppCompiler, linker].each { + it.withArguments { it.addAll(hostClangArgs) } + } - } - } - } - } + } + } + } + } } } +String getTargetArg(String target) { + def result = konanProperties.getProperty("quadruple.$target") + if (result == null) { + throw IllegalArgumentException("konan.properties has no LLVM target args for target: $target") + } + return result +} + void setupCompilationFlags() { ext.clangPath = ["$llvmDir/bin"] ext.clangArgs = [] @@ -67,55 +75,54 @@ void setupCompilationFlags() { final String binDir if (isLinux()) { - ext.host = "linux" - ext.targetArgs << - [(ext.host): - ["--sysroot=${gccToolchainDir}/${gnuTriplet}/sysroot", - "-DUSE_GCC_UNWIND=1", "-DELFSIZE=64"], - "raspberrypi": - ["-target", "armv6-unknown-linux-gnueabihf", - "-mfpu=vfp", "-mfloat-abi=hard", - "-DUSE_GCC_UNWIND=1", "-DELFSIZE=32", - "--sysroot=$raspberryPiSysrootDir", - // TODO: those two are hacks. - "-I$raspberryPiSysrootDir/usr/include/c++/4.8.3", - "-I$raspberryPiSysrootDir/usr/include/c++/4.8.3/arm-linux-gnueabihf"] - ] + ext.host = "linux" + ext.targetArgs << + [(ext.host): + ["--sysroot=${gccToolchainDir}/${gnuTriplet}/sysroot", + "-DUSE_GCC_UNWIND=1", "-DELFSIZE=64"], + "raspberrypi": + ["-target", getTargetArg("raspberrypi"), + "-mfpu=vfp", "-mfloat-abi=hard", + "-DUSE_GCC_UNWIND=1", "-DELFSIZE=32", + "--sysroot=$raspberrypiSysrootDir", + // TODO: those two are hacks. + "-I$raspberrypiSysrootDir/usr/include/c++/4.8.3", + "-I$raspberrypiSysrootDir/usr/include/c++/4.8.3/arm-linux-gnueabihf"] + ] } else { - ext.host = "macbook" - ext.targetArgs << - [(ext.host): - ["--sysroot=$macbookSysrootDir", "-mmacosx-version-min=$minMacOsVersion"], - "iphone": - ["-stdlib=libc++", "-arch", "arm64", "-isysroot", "$iphoneSysrootDir", - "-miphoneos-version-min=8.0.0"] + ext.host = "macbook" + ext.targetArgs << + [(ext.host): + ["--sysroot=$macbookSysrootDir", "-mmacosx-version-min=$minMacOsVersion"], + "iphone": + ["-stdlib=libc++", "-arch", "arm64", "-isysroot", "$iphoneSysrootDir", + "-miphoneos-version-min=8.0.0"] // TODO: re-enable after simulator sysroot is available in the dependencies // "iphone_sim": // ["-stdlib=libc++", "-isysroot", "$iphoneSimSysrootDir", "-miphoneos-version-min=8.0.0"], - ] + ] } ext.targetArgs << [ - "android_arm32": - ["-target", "arm-linux-androideabi", - "--sysroot=$android_arm32SysrootDir", - "-D__ANDROID__", "-DUSE_GCC_UNWIND=1", "-DELFSIZE=32", - // HACKS! - "-I$android_arm32SysrootDir/usr/include/c++/4.9.x", - "-I$android_arm32SysrootDir/usr/include/c++/4.9.x/arm-linux-androideabi" - ] + "android_arm32": + ["-target", getTargetArg("android_arm32"), + "--sysroot=$android_arm32SysrootDir", + "-D__ANDROID__", "-DUSE_GCC_UNWIND=1", "-DELFSIZE=32", + // HACKS! + "-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 if (isLinux()) { - binDir = "$gccToolchainDir/$gnuTriplet/bin" - ext.clangArgs.addAll([ - "--gcc-toolchain=$gccToolchainDir" - ]) + binDir = "$gccToolchainDir/$gnuTriplet/bin" + ext.clangArgs.addAll([ + "--gcc-toolchain=$gccToolchainDir" + ]) } else { - binDir = "$macbookSysrootDir/usr/bin" + binDir = "$macbookSysrootDir/usr/bin" } ext.clangArgs << "-B$binDir" - ext.hostClangArgs = ext.clangArgs.clone() + ext.hostClangArgs = ext.clangArgs.clone() ext.hostClangArgs.addAll(ext.targetArgs[host]) ext.clangPath << binDir @@ -124,22 +131,22 @@ void setupCompilationFlags() { void loadLocalProperties() { if (new File("$project.rootDir/local.properties").exists()) { - Properties props = new Properties() - props.load(new FileInputStream("$project.rootDir/local.properties")) - props.each {prop -> project.ext.set(prop.key, prop.value)} + Properties props = new Properties() + props.load(new FileInputStream("$project.rootDir/local.properties")) + props.each {prop -> project.ext.set(prop.key, prop.value)} } } void loadCommandLineProperties() { if (project.hasProperty("konanc_flags")) { - throw new Error("Specify either -Ptest_flags or -Pbuild_flags.") + throw new Error("Specify either -Ptest_flags or -Pbuild_flags.") } ext.globalBuildArgs = project.hasProperty("build_flags") - ? ext.build_flags.split(' ') : [] + ? ext.build_flags.split(' ') : [] ext.globalTestArgs = project.hasProperty("test_flags") - ? ext.test_flags.split(' ') : [] + ? ext.test_flags.split(' ') : [] ext.testTarget = project.hasProperty("test_target") - ? ext.test_target : null + ? ext.test_target : null } class PlatformInfo { @@ -147,33 +154,33 @@ class PlatformInfo { private final String osArch = System.properties['os.arch'] boolean isMac() { - return osName == 'Mac OS X' + return osName == 'Mac OS X' } boolean isLinux() { - return osName == 'Linux' + return osName == 'Linux' } boolean isAmd64() { - return osArch in ['x86_64', 'amd64'] + return osArch in ['x86_64', 'amd64'] } String getGnuTriplet() { - if (isLinux() && isAmd64()) { - return "x86_64-unknown-linux-gnu" - } else { - throw unsupportedPlatformException() - } + if (isLinux() && isAmd64()) { + return "x86_64-unknown-linux-gnu" + } else { + throw unsupportedPlatformException() + } } String simpleOsName() { - if (isMac()) return 'macos' - if (isLinux()) return 'linux' - throw unsupportedPlatformException() + if (isMac()) return 'macos' + if (isLinux()) return 'linux' + throw unsupportedPlatformException() } Throwable unsupportedPlatformException() { - return new Error("unsupported platform: $osName/$osArch") + return new Error("unsupported platform: $osName/$osArch") } } @@ -189,53 +196,53 @@ task distCompiler(type: Copy) { destinationDir file('dist') from(project(':backend.native').file('build/libs')) { - into('konan/lib') + into('konan/lib') } from(project('Interop').file('Runtime/build/libs')) { - into('konan/lib') + into('konan/lib') } from(project('Interop').file('Indexer/build/libs')) { - into('konan/lib') + into('konan/lib') } from(project('Interop').file('StubGenerator/build/libs')) { - into('konan/lib') + into('konan/lib') } from(project(':backend.native').file('build/external_jars')) { - into('konan/lib') + into('konan/lib') } from(project(':backend.native').file('build/nativelibs')) { - into('konan/nativelib') + into('konan/nativelib') } from(project(':Interop').file('Indexer/build/nativelibs')) { - into('konan/nativelib') + into('konan/nativelib') } from(project(':Interop').file('Runtime/build/nativelibs')) { - into('konan/nativelib') + into('konan/nativelib') } from(project(':llvmDebugInfoC').file('build/libs/debugInfo/shared')) { - into('konan/nativelib') + into('konan/nativelib') } from(file('cmd')) { - fileMode(0755) - into('bin') + fileMode(0755) + into('bin') } - from(project(':backend.native').file('konan.properties')) { - into('konan') + from(konanPropertiesFile) { + into('konan') } // TODO: check if we use native libraries copied to dist (see above) or not. from(project(':tools:helpers').file('build/libs')) { - into('konan/lib') + into('konan/lib') } } @@ -253,8 +260,8 @@ task commonDistRuntime(type: Copy) { // Target independant common part. from(project(':runtime').file("build/${host}Stdlib")) { - include('**') - into('klib/stdlib') + include('**') + into('klib/stdlib') } } @@ -265,25 +272,25 @@ task crossDistRuntime(type: Copy) { targetList.each { target -> task("${target}CrossDistRuntime", type: Copy) { - dependsOn ":runtime:${target}Runtime" - dependsOn ":backend.native:${target}Stdlib" - dependsOn ":backend.native:${target}Start" + dependsOn ":runtime:${target}Runtime" + dependsOn ":backend.native:${target}Stdlib" + dependsOn ":backend.native:${target}Start" - destinationDir file('dist') + destinationDir file('dist') - from(project(':runtime').file("build/$target")) { - include("*.bc") - into("klib/stdlib/$target/native") - } - from(project(':runtime').file("build/${target}Stdlib")) { - include('**') - into('klib/stdlib') - } - from(project(':runtime').file("build/${target}Start/$target/kotlin")) { - include("program.kt.bc") - rename('program.kt.bc', 'start.kt.bc') - into("klib/stdlib/$target/native") - } + from(project(':runtime').file("build/$target")) { + include("*.bc") + into("klib/stdlib/$target/native") + } + from(project(':runtime').file("build/${target}Stdlib")) { + include('**') + into('klib/stdlib') + } + from(project(':runtime').file("build/${target}Start/$target/kotlin")) { + include("program.kt.bc") + rename('program.kt.bc', 'start.kt.bc') + into("klib/stdlib/$target/native") + } } } @@ -299,33 +306,33 @@ task bundle(type: Tar) { dependsOn('crossDist') baseName = "kotlin-native-${simpleOsName()}-${project.konanVersion}" from("$project.rootDir/dist") { - include '**' - exclude 'dependencies' - into baseName + include '**' + exclude 'dependencies' + into baseName } from(project.rootDir) { - include 'DISTRO_README.md' - rename { - return "README.md" - } - into baseName + include 'DISTRO_README.md' + rename { + return "README.md" + } + into baseName } from(project.rootDir) { - include 'samples/**' - include 'INTEROP.md' - include 'RELEASE_NOTES.md' - include 'GRADLE_PLUGIN.md' - exclude '**/gradle.properties' - exclude '**/build' - exclude '**/.gradle' - rename { String fileName -> - if (fileName == "gradle.properties.for_bundle") { - return "gradle.properties" - } else { - return fileName - } - } - into baseName + include 'samples/**' + include 'INTEROP.md' + include 'RELEASE_NOTES.md' + include 'GRADLE_PLUGIN.md' + exclude '**/gradle.properties' + exclude '**/build' + exclude '**/.gradle' + rename { String fileName -> + if (fileName == "gradle.properties.for_bundle") { + return "gradle.properties" + } else { + return fileName + } + } + into baseName } destinationDir = file('.') extension = 'tar.gz' @@ -340,9 +347,9 @@ task demo(type: Exec) { task clean { doLast { - file('dist').traverse(type: FileType.ANY, excludeNameFilter: "dependencies", maxDepth: 0) { - delete it - } - delete bundle.outputs.files + file('dist').traverse(type: FileType.ANY, excludeNameFilter: "dependencies", maxDepth: 0) { + delete it + } + delete bundle.outputs.files } } diff --git a/dependencies/build.gradle b/dependencies/build.gradle index b98bb50c1ed..a94e8749a32 100644 --- a/dependencies/build.gradle +++ b/dependencies/build.gradle @@ -14,6 +14,8 @@ * limitations under the License. */ +import static DependencyTaskKind.* + buildscript { repositories { mavenCentral() @@ -28,6 +30,10 @@ buildscript { apply plugin: 'com.jfrog.bintray' +rootProject.ext.konanPropertiesFile = project(':backend.native').file('konan.properties') +rootProject.ext.konanProperties = new Properties() +rootProject.konanProperties.load(new FileInputStream(rootProject.konanPropertiesFile)) + configurations { kotlin_compiler_jar kotlin_compiler_pom @@ -184,50 +190,71 @@ class HelperNativeDep extends TgzNativeDep { } } +static String substituteName(String name) { + switch (name) { + case "macbook": return "osx" + case "iphone": return "ios" + case "iphoneSim": return "ios_sim" + } + return name +} + +enum DependencyTaskKind { + LIBFFI("Libffi"), SYSROOT("Sysroot") + + DependencyTaskKind(String name) { + this.name = name + } + + String name = "" + String toString() { return name } +} + +void dependencyTask(String target, DependencyTaskKind kind) { + String dependencyBaseName + def properties = rootProject.konanProperties + switch (kind) { + case LIBFFI: + dependencyBaseName = properties.getProperty("libffiDir.${substituteName(target)}") + break + case SYSROOT: + dependencyBaseName = properties.getProperty("targetSysRoot.${substituteName(target)}") + break + } + if (dependencyBaseName == null) { + throw project.unsupportedPlatformException() + } + + task "${target}${kind}"(type: HelperNativeDep) { + baseName = dependencyBaseName + } +} + task llvm(type: HelperNativeDep) { baseName = "clang-llvm-$llvmVersion-$host" } if (isLinux()) { - task linuxLibffi(type: HelperNativeDep) { - baseName = "libffi-3.2.1-2-$host" - } + // The gcc toolchain contains the sysroot for linux platform. task gccToolchain(type: HelperNativeDep) { baseName = "target-gcc-toolchain-3-$host" } - task raspberryPiSysroot(type: HelperNativeDep) { - baseName = "target-sysroot-1-raspberrypi" - } - task raspberrypiLibffi(type: HelperNativeDep) { - baseName = "libffi-3.2.1-2-raspberrypi" - } + + dependencyTask("linux", LIBFFI) + dependencyTask("raspberrypi", SYSROOT) + dependencyTask("raspberrypi", LIBFFI) } else { - task macbookLibffi(type: HelperNativeDep) { - baseName = "libffi-3.2.1-2-$host" - } - task macbookSysroot(type: HelperNativeDep) { - baseName = "target-sysroot-1-$host" - } - task iphoneSysroot(type: HelperNativeDep) { - baseName = "target-sysroot-2-darwin-ios" - } - task iphoneLibffi(type: HelperNativeDep) { - baseName = "libffi-3.2.1-2-darwin-ios" - } - // TODO: re-enable when we known how to bring the simulator - // sysroot to dependencies. - // task iphoneSimSysroot(type: TgzNativeDep) { - // baseName = "target-sysroot-1-darwin-ios-sim" - // } + dependencyTask("macbook", SYSROOT) + dependencyTask("macbook", LIBFFI) + dependencyTask("iphone", SYSROOT) + dependencyTask("iphone", LIBFFI) + + // TODO: re-enable when we known how to bring the simulator sysroot to dependencies. + // dependencyTask("iphoneSim", SYSROOT) } -task android_arm32Sysroot(type: HelperNativeDep) { - baseName = "target-sysroot-21-android_arm32" -} - -task android_arm32Libffi(type: HelperNativeDep) { - baseName = "libffi-3.2.1-2-android_arm32" -} +dependencyTask("android_arm32", SYSROOT) +dependencyTask("android_arm32", LIBFFI) task update(type: Copy) { dependsOn tasks.withType(NativeDep)