[K/N] Move kotlin-native/utilities/basic-utils to compiler/utils
This commit is contained in:
committed by
Space Team
parent
3ab6e9de28
commit
4468167a64
@@ -139,9 +139,9 @@ sourceSets {
|
||||
dependencies {
|
||||
api(project(":kotlin-stdlib"))
|
||||
api(project(":kotlin-native:Interop:Runtime"))
|
||||
api(project(":kotlin-native:utilities:basic-utils"))
|
||||
|
||||
testImplementation(kotlin("test-junit"))
|
||||
testImplementation(project(":compiler:util"))
|
||||
}
|
||||
|
||||
val nativelibs = project.tasks.register<Copy>("nativelibs") {
|
||||
|
||||
+1
-1
@@ -6,7 +6,7 @@
|
||||
package org.jetbrains.kotlin.native.interop.indexer
|
||||
|
||||
import kotlinx.cinterop.JvmCInteropCallbacks
|
||||
import org.jetbrains.kotlin.konan.util.NativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.NativeMemoryAllocator
|
||||
import java.io.File
|
||||
import kotlin.test.AfterTest
|
||||
import kotlin.test.BeforeTest
|
||||
|
||||
@@ -47,7 +47,7 @@ native {
|
||||
}
|
||||
|
||||
dependencies {
|
||||
implementation(project(":kotlin-native:utilities:basic-utils"))
|
||||
implementation(project(":compiler:util"))
|
||||
implementation(project(":kotlin-stdlib"))
|
||||
implementation(commonDependency("org.jetbrains.kotlin:kotlin-reflect")) { isTransitive = false }
|
||||
}
|
||||
|
||||
@@ -16,8 +16,8 @@
|
||||
|
||||
package kotlinx.cinterop
|
||||
|
||||
import org.jetbrains.kotlin.konan.util.NativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.konan.util.ThreadSafeDisposableHelper
|
||||
import org.jetbrains.kotlin.utils.NativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.ThreadSafeDisposableHelper
|
||||
import sun.misc.Unsafe
|
||||
import java.util.concurrent.ConcurrentHashMap
|
||||
import java.util.function.LongConsumer
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
|
||||
package kotlinx.cinterop
|
||||
|
||||
import org.jetbrains.kotlin.konan.util.nativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.nativeMemoryAllocator
|
||||
import sun.misc.Unsafe
|
||||
|
||||
private val NativePointed.address: Long
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
|
||||
package kotlinx.cinterop
|
||||
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
import java.io.File
|
||||
import java.nio.file.Files
|
||||
import java.nio.file.Paths
|
||||
@@ -192,7 +192,7 @@ fun loadKonanLibrary(name: String) {
|
||||
for (dir in paths) {
|
||||
if (tryLoadKonanLibrary(dir, fullLibraryName, runFromDaemon)) return
|
||||
}
|
||||
val defaultNativeLibsDir = "${KonanHomeProvider.determineKonanHome()}/konan/nativelib"
|
||||
val defaultNativeLibsDir = "${KotlinNativePaths.homePath.absolutePath}/konan/nativelib"
|
||||
if (tryLoadKonanLibrary(defaultNativeLibsDir, fullLibraryName, runFromDaemon))
|
||||
return
|
||||
error("Lib $fullLibraryName is not found in $defaultNativeLibsDir and ${paths.joinToString { it }}")
|
||||
|
||||
@@ -30,7 +30,6 @@ application {
|
||||
|
||||
dependencies {
|
||||
implementation(project(":kotlin-native:Interop:Indexer"))
|
||||
implementation(project(":kotlin-native:utilities:basic-utils"))
|
||||
implementation(project(path = ":kotlin-native:endorsedLibraries:kotlinx.cli", configuration = "jvmRuntimeElements"))
|
||||
|
||||
api(project(":kotlin-stdlib"))
|
||||
|
||||
+1
-1
@@ -2,7 +2,7 @@ package org.jetbrains.kotlin.native.interop.gen
|
||||
|
||||
import kotlinx.cinterop.usingJvmCInteropCallbacks
|
||||
import org.jetbrains.kotlin.konan.util.DefFile
|
||||
import org.jetbrains.kotlin.konan.util.usingNativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.usingNativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.KotlinPlatform
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.buildNativeLibrary
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.prepareTool
|
||||
|
||||
+2
-2
@@ -17,13 +17,13 @@
|
||||
package org.jetbrains.kotlin.native.interop.tool
|
||||
|
||||
import org.jetbrains.kotlin.konan.target.*
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
import org.jetbrains.kotlin.konan.target.AbstractToolConfig
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.KotlinPlatform
|
||||
import org.jetbrains.kotlin.native.interop.indexer.Language
|
||||
|
||||
class ToolConfig(userProvidedTargetName: String?, flavor: KotlinPlatform, propertyOverrides: Map<String, String>, konanDataDir: String? = null)
|
||||
: AbstractToolConfig(KonanHomeProvider.determineKonanHome(), userProvidedTargetName, propertyOverrides, konanDataDir) {
|
||||
: AbstractToolConfig(KotlinNativePaths.homePath.absolutePath, userProvidedTargetName, propertyOverrides, konanDataDir) {
|
||||
|
||||
val clang = when (flavor) {
|
||||
KotlinPlatform.JVM -> platform.clangForJni
|
||||
|
||||
+3
-3
@@ -29,8 +29,8 @@ import org.jetbrains.kotlin.konan.target.CompilerOutputKind
|
||||
import org.jetbrains.kotlin.konan.target.Distribution
|
||||
import org.jetbrains.kotlin.konan.target.KonanTarget
|
||||
import org.jetbrains.kotlin.konan.util.DefFile
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.konan.util.usingNativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
import org.jetbrains.kotlin.utils.usingNativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.library.KLIB_PROPERTY_IR_PROVIDER
|
||||
import org.jetbrains.kotlin.library.KotlinLibrary
|
||||
import org.jetbrains.kotlin.library.metadata.resolver.TopologicalLibraryOrder
|
||||
@@ -486,7 +486,7 @@ private fun getLibraryResolver(
|
||||
repos,
|
||||
libraries.filter { it.contains(org.jetbrains.kotlin.konan.file.File.separator) },
|
||||
target,
|
||||
Distribution(KonanHomeProvider.determineKonanHome(), konanDataDir = cinteropArguments.konanDataDir)
|
||||
Distribution(KotlinNativePaths.homePath.absolutePath, konanDataDir = cinteropArguments.konanDataDir)
|
||||
).libraryResolver()
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -8,7 +8,7 @@ package org.jetbrains.kotlin.native.interop.gen
|
||||
import kotlinx.cinterop.JvmCInteropCallbacks
|
||||
import org.jetbrains.kotlin.konan.target.HostManager
|
||||
import org.jetbrains.kotlin.konan.util.DefFile
|
||||
import org.jetbrains.kotlin.konan.util.NativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.NativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.KotlinPlatform
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.buildNativeLibrary
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.prepareTool
|
||||
|
||||
@@ -154,7 +154,6 @@ dependencies {
|
||||
}
|
||||
kotlin_script_runtime_jar project(":kotlin-script-runtime")
|
||||
|
||||
compilerApi project(":kotlin-native:utilities:basic-utils")
|
||||
compilerApi project(":native:objcexport-header-generator")
|
||||
compilerApi project(":native:objcexport-header-generator-k1")
|
||||
compilerApi project(":native:base")
|
||||
|
||||
+2
-2
@@ -18,7 +18,7 @@ import org.jetbrains.kotlin.konan.file.File
|
||||
import org.jetbrains.kotlin.konan.library.KonanLibrary
|
||||
import org.jetbrains.kotlin.konan.properties.loadProperties
|
||||
import org.jetbrains.kotlin.konan.target.*
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
import org.jetbrains.kotlin.konan.util.visibleName
|
||||
import org.jetbrains.kotlin.library.metadata.resolver.TopologicalLibraryOrder
|
||||
import org.jetbrains.kotlin.util.removeSuffixIfPresent
|
||||
@@ -41,7 +41,7 @@ class KonanConfig(val project: Project, val configuration: CompilerConfiguration
|
||||
}
|
||||
|
||||
Distribution(
|
||||
configuration.get(KonanConfigKeys.KONAN_HOME) ?: KonanHomeProvider.determineKonanHome(),
|
||||
configuration.get(KonanConfigKeys.KONAN_HOME) ?: KotlinNativePaths.homePath.absolutePath,
|
||||
false,
|
||||
configuration.get(KonanConfigKeys.RUNTIME_FILE),
|
||||
overridenProperties,
|
||||
|
||||
+1
-1
@@ -23,7 +23,7 @@ import org.jetbrains.kotlin.cli.jvm.compiler.KotlinCoreEnvironment
|
||||
import org.jetbrains.kotlin.config.CommonConfigurationKeys
|
||||
import org.jetbrains.kotlin.konan.file.File
|
||||
import org.jetbrains.kotlin.konan.target.CompilerOutputKind
|
||||
import org.jetbrains.kotlin.konan.util.usingNativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.usingNativeMemoryAllocator
|
||||
|
||||
/**
|
||||
* Dynamic driver does not "know" upfront which phases will be executed.
|
||||
|
||||
@@ -167,7 +167,6 @@ dependencies {
|
||||
distPack project(':native:objcexport-header-generator-k1')
|
||||
distPack project(':native:base')
|
||||
distPack project(':kotlin-native:utilities:cli-runner')
|
||||
distPack project(':kotlin-native:utilities:basic-utils')
|
||||
distPack project(':kotlin-native:klib')
|
||||
distPack project(path: ':kotlin-native:backend.native', configuration: 'cli_bcApiElements')
|
||||
distPack project(path: ':kotlin-native:endorsedLibraries:kotlinx.cli', configuration: "jvmRuntimeElements")
|
||||
|
||||
@@ -17,7 +17,6 @@ dependencies {
|
||||
implementation(project(":native:frontend.native"))
|
||||
implementation(project(":compiler:ir.psi2ir"))
|
||||
implementation(project(":compiler:ir.serialization.native"))
|
||||
implementation(project(":kotlin-native:utilities:basic-utils"))
|
||||
implementation(project(":kotlin-util-klib-abi"))
|
||||
}
|
||||
|
||||
|
||||
@@ -36,7 +36,7 @@ import org.jetbrains.kotlin.konan.library.KonanLibrary
|
||||
import org.jetbrains.kotlin.konan.library.resolverByName
|
||||
import org.jetbrains.kotlin.konan.target.Distribution
|
||||
import org.jetbrains.kotlin.konan.util.DependencyDirectories
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
import org.jetbrains.kotlin.library.*
|
||||
import org.jetbrains.kotlin.library.abi.*
|
||||
import org.jetbrains.kotlin.library.metadata.KlibMetadataFactories
|
||||
@@ -447,10 +447,10 @@ class Library(val libraryNameOrPath: String, val requestedRepository: String?) {
|
||||
val defaultModules = mutableListOf<ModuleDescriptorImpl>()
|
||||
if (!module.isNativeStdlib()) {
|
||||
val resolver = resolverByName(
|
||||
emptyList(),
|
||||
distributionKlib = Distribution(KonanHomeProvider.determineKonanHome()).klib,
|
||||
skipCurrentDir = true,
|
||||
logger = KlibToolLogger
|
||||
emptyList(),
|
||||
distributionKlib = Distribution(KotlinNativePaths.homePath.absolutePath).klib,
|
||||
skipCurrentDir = true,
|
||||
logger = KlibToolLogger
|
||||
)
|
||||
resolver.defaultLinks(false, true, true).mapTo(defaultModules) {
|
||||
KlibFactories.DefaultDeserializedDescriptorFactory.createDescriptor(it, versionSpec, storageManager, module.builtIns, null)
|
||||
|
||||
@@ -47,7 +47,6 @@ dependencies {
|
||||
kotlinNativeEmbedded(project(":kotlin-native:Interop:Skia"))
|
||||
kotlinNativeEmbedded(project(":kotlin-native:backend.native"))
|
||||
kotlinNativeEmbedded(project(":kotlin-native:utilities:cli-runner"))
|
||||
kotlinNativeEmbedded(project(":kotlin-native:utilities:basic-utils"))
|
||||
kotlinNativeEmbedded(project(":kotlin-native:klib"))
|
||||
kotlinNativeEmbedded(project(":kotlin-native:backend.native", "cli_bcApiElements"))
|
||||
kotlinNativeEmbedded(project(":kotlin-native:endorsedLibraries:kotlinx.cli", "jvmRuntimeElements"))
|
||||
|
||||
@@ -1,25 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license
|
||||
* that can be found in the LICENSE file.
|
||||
*/
|
||||
|
||||
import org.jetbrains.kotlin.gradle.tasks.KotlinCompile
|
||||
|
||||
buildscript {
|
||||
apply(from = "$rootDir/kotlin-native/gradle/kotlinGradlePlugin.gradle")
|
||||
}
|
||||
|
||||
plugins {
|
||||
kotlin("jvm")
|
||||
}
|
||||
|
||||
tasks.named<KotlinCompile>("compileKotlin") {
|
||||
kotlinOptions {
|
||||
freeCompilerArgs += listOf("-Xskip-metadata-version-check")
|
||||
}
|
||||
}
|
||||
|
||||
dependencies {
|
||||
api(project(":kotlin-stdlib"))
|
||||
implementation(project(":compiler:util"))
|
||||
}
|
||||
@@ -1,46 +0,0 @@
|
||||
package org.jetbrains.kotlin.konan.util
|
||||
|
||||
import org.jetbrains.kotlin.utils.PathUtil
|
||||
import org.jetbrains.kotlin.*
|
||||
import java.io.File
|
||||
import java.nio.file.Paths
|
||||
|
||||
object KonanHomeProvider {
|
||||
internal val validPropertiesNames = listOf("kotlin.native.home",
|
||||
"org.jetbrains.kotlin.native.home",
|
||||
"konan.home")
|
||||
internal val kotlinNativeHome
|
||||
get() = validPropertiesNames.mapNotNull(System::getProperty).firstOrNull()
|
||||
/**
|
||||
* Determines a path to the current Kotlin/Native distribution.
|
||||
*
|
||||
* - If the system property "konan.home" is set, the method returns its normalized value.
|
||||
* - Otherwise, it determines a path to a jar containing this class. If this path corresponds to the jar path
|
||||
* inside a distribution, the method calculates the path to the distribution on the basis of this jar path.
|
||||
* Otherwise an IllegalStateException is thrown.
|
||||
*/
|
||||
fun determineKonanHome(): String {
|
||||
val propertyValue = kotlinNativeHome
|
||||
return if (propertyValue != null) {
|
||||
// KT-58979: KonanLibraryImpl needs normalized klib paths to correctly provide symbols from resolved klibs
|
||||
// For extra safety, path to "konan.home" is also normalized here
|
||||
Paths.get(File(propertyValue).absolutePath).normalize().toString()
|
||||
} else {
|
||||
val jarPath = PathUtil.getResourcePathForClass(this::class.java)
|
||||
|
||||
// Check that the path obtained really points to the distribution.
|
||||
check(jarPath.toPath().endsWith(Paths.get("konan/lib/kotlin-native.jar")) ||
|
||||
jarPath.toPath().endsWith(Paths.get("konan/lib/kotlin-native-compiler-embeddable.jar"))) {
|
||||
val classesPath = if (jarPath.extension == "jar") jarPath else jarPath.parentFile
|
||||
"""
|
||||
Cannot determine a compiler distribution directory.
|
||||
A path to compiler classes is not a part of a distribution: ${classesPath.absolutePath}.
|
||||
Please set the konan.home system property to specify the distribution path manually.
|
||||
""".trimIndent()
|
||||
}
|
||||
|
||||
// The compiler jar is located in <dist>/konan/lib.
|
||||
jarPath.parentFile.parentFile.parentFile.absolutePath
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,248 +0,0 @@
|
||||
/*
|
||||
* Copyright 2010-2020 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license
|
||||
* that can be found in the LICENSE file.
|
||||
*/
|
||||
|
||||
package org.jetbrains.kotlin.konan.util
|
||||
|
||||
import sun.misc.Unsafe
|
||||
|
||||
class ThreadSafeDisposableHelper<T>(create: () -> T, private val dispose: (T) -> Unit) {
|
||||
private val create_ = create
|
||||
|
||||
var holder: T? = null
|
||||
private set
|
||||
|
||||
private var counter = 0
|
||||
private val lock = Any()
|
||||
|
||||
fun create() {
|
||||
synchronized(lock) {
|
||||
if (counter++ == 0) {
|
||||
check(holder == null)
|
||||
holder = create_()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fun dispose() {
|
||||
synchronized(lock) {
|
||||
if (--counter == 0) {
|
||||
dispose(holder!!)
|
||||
holder = null
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
inline fun <R> usingDisposable(block: () -> R): R {
|
||||
create()
|
||||
return try {
|
||||
block()
|
||||
} finally {
|
||||
dispose()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@PublishedApi
|
||||
internal val allocatorDisposeHelper = ThreadSafeDisposableHelper({ NativeMemoryAllocator() }, { it.freeAll() })
|
||||
|
||||
inline fun <R> usingNativeMemoryAllocator(block: () -> R) = allocatorDisposeHelper.usingDisposable(block)
|
||||
|
||||
val nativeMemoryAllocator: NativeMemoryAllocator
|
||||
get() = allocatorDisposeHelper.holder ?: error("Native memory allocator hasn't been created")
|
||||
|
||||
// 256 buckets for sizes <= 2048 padded to 8
|
||||
// 256 buckets for sizes <= 64KB padded to 256
|
||||
// 256 buckets for sizes <= 1MB padded to 4096
|
||||
private const val ChunkBucketSize = 256
|
||||
// Alignments are such that overhead is approx 10%.
|
||||
private const val SmallChunksSizeAlignment = 8
|
||||
private const val MediumChunksSizeAlignment = 256
|
||||
private const val BigChunksSizeAlignment = 4096
|
||||
private const val MaxSmallSize = ChunkBucketSize * SmallChunksSizeAlignment
|
||||
private const val MaxMediumSize = ChunkBucketSize * MediumChunksSizeAlignment
|
||||
private const val MaxBigSize = ChunkBucketSize * BigChunksSizeAlignment
|
||||
private const val ChunkHeaderSize = 3 * Int.SIZE_BYTES // chunk size + raw chunk ref + alignment hop size.
|
||||
|
||||
private const val RawChunkSizeBits = 22 // 4MB
|
||||
private const val RawChunkSize = 1L shl RawChunkSizeBits
|
||||
private const val ChunkSizeAlignmentBits = 3 // All chunk sizes are aligned to at least 8.
|
||||
private const val RawChunkOffsetBits = RawChunkSizeBits - ChunkSizeAlignmentBits
|
||||
private const val MinChunkSize = 8
|
||||
private const val MaxRawChunksCount = 1024 // 4GB in total.
|
||||
|
||||
class NativeMemoryAllocator {
|
||||
companion object {
|
||||
fun init() = allocatorDisposeHelper.create()
|
||||
fun dispose() = allocatorDisposeHelper.dispose()
|
||||
}
|
||||
|
||||
private fun alignUp(x: Long, align: Int) = (x + align - 1) and (align - 1).toLong().inv()
|
||||
private fun alignUp(x: Int, align: Int) = (x + align - 1) and (align - 1).inv()
|
||||
|
||||
private val unsafe = with(Unsafe::class.java.getDeclaredField("theUnsafe")) {
|
||||
isAccessible = true
|
||||
return@with this.get(null) as Unsafe
|
||||
}
|
||||
|
||||
private val longArrayBaseOffset = unsafe.arrayBaseOffset(LongArray::class.java).toLong()
|
||||
|
||||
private val rawOffsetFieldOffset = unsafe.objectFieldOffset(this::class.java.getDeclaredField("rawOffset"))
|
||||
|
||||
@JvmInline
|
||||
private value class ChunkRef(val value: Int) {
|
||||
val offset get() = (value and ((1 shl RawChunkOffsetBits) - 1)) shl ChunkSizeAlignmentBits
|
||||
|
||||
val index get() = (value ushr RawChunkOffsetBits) - 1
|
||||
|
||||
companion object {
|
||||
init {
|
||||
// Ensure that pair (index, offset) fits in 32-bit integer.
|
||||
check(MaxRawChunksCount < 1L shl (32 - RawChunkOffsetBits))
|
||||
}
|
||||
|
||||
fun encode(index: Int, offset: Int) = ChunkRef(((index + 1) shl RawChunkOffsetBits) or (offset ushr ChunkSizeAlignmentBits))
|
||||
|
||||
val Invalid = ChunkRef(0)
|
||||
}
|
||||
}
|
||||
|
||||
// Timestamps here solve the ABA problem.
|
||||
@JvmInline
|
||||
private value class ChunkRefWithTimestamp(val value: Long) {
|
||||
val chunkRef get() = ChunkRef(value.toInt())
|
||||
|
||||
val timestamp get() = (value ushr 32).toInt()
|
||||
|
||||
companion object {
|
||||
fun encode(chunkRef: Int, timestamp: Int) = ChunkRefWithTimestamp(chunkRef.toLong() or (timestamp.toLong() shl 32))
|
||||
}
|
||||
}
|
||||
|
||||
private fun getChunkSize(chunk: Long) = unsafe.getInt(chunk)
|
||||
private fun setChunkSize(chunk: Long, size: Int) = unsafe.putInt(chunk, size)
|
||||
|
||||
private fun getChunkRef(chunk: Long): ChunkRef = ChunkRef(unsafe.getInt(chunk + Int.SIZE_BYTES /* skip chunk size */))
|
||||
private fun setChunkRef(chunk: Long, chunkRef: ChunkRef) = unsafe.putInt(chunk + Int.SIZE_BYTES /* skip chunk size */, chunkRef.value)
|
||||
|
||||
private val smallChunks = LongArray(ChunkBucketSize)
|
||||
private val mediumChunks = LongArray(ChunkBucketSize)
|
||||
private val bigChunks = LongArray(ChunkBucketSize)
|
||||
|
||||
// Chunk layout: [chunk size, raw chunk ref,...padding...,diff to start,aligned data start,.....data.....]
|
||||
fun alloc(size: Long, align: Int): Long {
|
||||
val totalChunkSize = ChunkHeaderSize + size + align
|
||||
val chunkStart = when {
|
||||
totalChunkSize <= MaxSmallSize -> allocFromFreeList(totalChunkSize.toInt(), SmallChunksSizeAlignment, smallChunks)
|
||||
totalChunkSize <= MaxMediumSize -> allocFromFreeList(totalChunkSize.toInt(), MediumChunksSizeAlignment, mediumChunks)
|
||||
totalChunkSize <= MaxBigSize -> allocFromFreeList(totalChunkSize.toInt(), BigChunksSizeAlignment, bigChunks)
|
||||
else -> unsafe.allocateMemory(totalChunkSize).also {
|
||||
// The actual size is not used. Just put value bigger than the biggest threshold.
|
||||
setChunkSize(it, Int.MAX_VALUE)
|
||||
}
|
||||
}
|
||||
val chunkWithSkippedHeader = chunkStart + ChunkHeaderSize
|
||||
val alignedPtr = alignUp(chunkWithSkippedHeader, align)
|
||||
unsafe.putInt(alignedPtr - Int.SIZE_BYTES, (alignedPtr - chunkStart).toInt())
|
||||
return alignedPtr
|
||||
}
|
||||
|
||||
fun free(mem: Long) {
|
||||
val chunkStart = mem - unsafe.getInt(mem - Int.SIZE_BYTES)
|
||||
val chunkSize = getChunkSize(chunkStart)
|
||||
when {
|
||||
chunkSize <= MaxSmallSize -> freeToFreeList(chunkSize, SmallChunksSizeAlignment, smallChunks, chunkStart)
|
||||
chunkSize <= MaxMediumSize -> freeToFreeList(chunkSize, MediumChunksSizeAlignment, mediumChunks, chunkStart)
|
||||
chunkSize <= MaxBigSize -> freeToFreeList(chunkSize, BigChunksSizeAlignment, bigChunks, chunkStart)
|
||||
else -> unsafe.freeMemory(chunkStart)
|
||||
}
|
||||
}
|
||||
|
||||
private val rawChunks = LongArray(MaxRawChunksCount)
|
||||
|
||||
private fun ChunkRef.dereference() = rawChunks[index] + offset
|
||||
|
||||
private val rawChunksLock = Any()
|
||||
|
||||
@Volatile
|
||||
private var rawOffset = 0L
|
||||
|
||||
private fun allocRaw(size: Int): Long {
|
||||
require(size % MinChunkSize == 0) { "Sizes should be multiples of $MinChunkSize" }
|
||||
while (true) {
|
||||
val offset = rawOffset
|
||||
val remainedInCurChunk = (alignUp(offset + 1, RawChunkSize.toInt()) - offset).toInt()
|
||||
val newOffset = offset + if (remainedInCurChunk >= size) size else remainedInCurChunk + size
|
||||
if (!unsafe.compareAndSwapLong(this, rawOffsetFieldOffset, offset, newOffset)) continue
|
||||
val dataStartOffset = newOffset - size
|
||||
val rawChunkIndex = (dataStartOffset ushr RawChunkSizeBits).toInt()
|
||||
val rawChunkOffset = (dataStartOffset and (RawChunkSize - 1)).toInt()
|
||||
var rawChunk = rawChunks[rawChunkIndex]
|
||||
if (rawChunk == 0L) {
|
||||
synchronized(rawChunksLock) {
|
||||
rawChunk = rawChunks[rawChunkIndex]
|
||||
if (rawChunk == 0L) {
|
||||
rawChunk = unsafe.allocateMemory(RawChunkSize)
|
||||
rawChunks[rawChunkIndex] = rawChunk
|
||||
}
|
||||
}
|
||||
}
|
||||
val ptr = rawChunk + rawChunkOffset
|
||||
setChunkRef(ptr, ChunkRef.encode(rawChunkIndex, rawChunkOffset))
|
||||
return ptr
|
||||
}
|
||||
}
|
||||
|
||||
private fun allocFromFreeList(size: Int, align: Int, freeList: LongArray): Long {
|
||||
val paddedSize = alignUp(size, align)
|
||||
val index = paddedSize / align - 1
|
||||
val ptr: Long
|
||||
while (true) {
|
||||
val chunkRefWithTimestamp = ChunkRefWithTimestamp(freeList[index])
|
||||
val chunkRef = chunkRefWithTimestamp.chunkRef
|
||||
if (chunkRef == ChunkRef.Invalid) {
|
||||
ptr = allocRaw(paddedSize)
|
||||
break
|
||||
} else {
|
||||
val chunk = chunkRef.dereference()
|
||||
val nextChunkRef = unsafe.getInt(chunk)
|
||||
val nextChunkRefWithTimestamp = ChunkRefWithTimestamp.encode(nextChunkRef, chunkRefWithTimestamp.timestamp + 1)
|
||||
if (unsafe.compareAndSwapLong(freeList, longArrayBaseOffset + index * Long.SIZE_BYTES,
|
||||
chunkRefWithTimestamp.value, nextChunkRefWithTimestamp.value)) {
|
||||
ptr = chunk
|
||||
break
|
||||
}
|
||||
}
|
||||
}
|
||||
setChunkSize(ptr, paddedSize)
|
||||
return ptr
|
||||
}
|
||||
|
||||
private fun freeToFreeList(paddedSize: Int, align: Int, freeList: LongArray, chunk: Long) {
|
||||
require(paddedSize > 0 && paddedSize % align == 0)
|
||||
val index = paddedSize / align - 1
|
||||
do {
|
||||
val nextChunkRefWithTimestamp = ChunkRefWithTimestamp(freeList[index])
|
||||
unsafe.putInt(chunk, nextChunkRefWithTimestamp.chunkRef.value)
|
||||
val chunkRef = getChunkRef(chunk)
|
||||
val chunkRefWithTimestamp = ChunkRefWithTimestamp.encode(chunkRef.value, nextChunkRefWithTimestamp.timestamp + 1)
|
||||
} while (!unsafe.compareAndSwapLong(freeList, longArrayBaseOffset + index * Long.SIZE_BYTES,
|
||||
nextChunkRefWithTimestamp.value, chunkRefWithTimestamp.value))
|
||||
}
|
||||
|
||||
internal fun freeAll() {
|
||||
for (i in 0 until ChunkBucketSize) {
|
||||
smallChunks[i] = 0L
|
||||
mediumChunks[i] = 0L
|
||||
bigChunks[i] = 0L
|
||||
}
|
||||
for (index in rawChunks.indices) {
|
||||
val rawChunk = rawChunks[index]
|
||||
if (rawChunk != 0L)
|
||||
unsafe.freeMemory(rawChunk)
|
||||
rawChunks[index] = 0L
|
||||
}
|
||||
rawOffset = 0L
|
||||
}
|
||||
}
|
||||
@@ -22,7 +22,6 @@ dependencies {
|
||||
implementation project(":compiler:cli-common")
|
||||
implementation project(':kotlin-native:Interop:StubGenerator')
|
||||
implementation project(':kotlin-native:klib')
|
||||
implementation project(":kotlin-native:utilities:basic-utils")
|
||||
implementation project(path: ":kotlin-native:endorsedLibraries:kotlinx.cli", configuration: "jvmRuntimeElements")
|
||||
implementation project(":native:kotlin-native-utils")
|
||||
}
|
||||
|
||||
+3
-3
@@ -13,7 +13,7 @@ import org.jetbrains.kotlin.backend.konan.CachedLibraries
|
||||
import org.jetbrains.kotlin.backend.konan.OutputFiles
|
||||
import org.jetbrains.kotlin.backend.konan.files.renameAtomic
|
||||
import org.jetbrains.kotlin.konan.target.*
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
import org.jetbrains.kotlin.konan.util.PlatformLibsInfo
|
||||
import org.jetbrains.kotlin.konan.util.visibleName
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.parseKeyValuePairs
|
||||
@@ -24,7 +24,7 @@ import java.nio.file.Files
|
||||
import java.nio.file.Paths
|
||||
import java.util.concurrent.atomic.AtomicInteger
|
||||
import kotlin.system.exitProcess
|
||||
import org.jetbrains.kotlin.konan.util.usingNativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.usingNativeMemoryAllocator
|
||||
|
||||
// TODO: We definitely need to unify logging in different parts of the compiler.
|
||||
private class Logger(val level: Level = Level.NORMAL) {
|
||||
@@ -126,7 +126,7 @@ fun generatePlatformLibraries(args: Array<String>) = usingNativeMemoryAllocator
|
||||
argParser.parse(args)
|
||||
|
||||
val distribution = Distribution(
|
||||
KonanHomeProvider.determineKonanHome(),
|
||||
KotlinNativePaths.homePath.absolutePath,
|
||||
onlyDefaultProfiles = false,
|
||||
runtimeFileOverride = null,
|
||||
propertyOverrides = parseKeyValuePairs(overrideKonanProperties),
|
||||
|
||||
+3
-3
@@ -7,7 +7,7 @@ package org.jetbrains.kotlin.cli.utilities
|
||||
import org.jetbrains.kotlin.cli.common.arguments.K2NativeCompilerArguments
|
||||
import org.jetbrains.kotlin.konan.file.File
|
||||
import org.jetbrains.kotlin.konan.target.PlatformManager
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.InternalInteropOptions
|
||||
import org.jetbrains.kotlin.native.interop.gen.jvm.Interop
|
||||
import org.jetbrains.kotlin.native.interop.tool.*
|
||||
@@ -43,8 +43,8 @@ fun invokeInterop(flavor: String, args: Array<String>, runFromDaemon: Boolean):
|
||||
val repos = arguments.repo
|
||||
val targetRequest = arguments.target
|
||||
val target = PlatformManager(
|
||||
KonanHomeProvider.determineKonanHome(),
|
||||
konanDataDir = arguments.konanDataDir).targetManager(targetRequest).target
|
||||
KotlinNativePaths.homePath.absolutePath,
|
||||
konanDataDir = arguments.konanDataDir).targetManager(targetRequest).target
|
||||
|
||||
val cinteropArgsToCompiler = Interop().interop("native", args,
|
||||
InternalInteropOptions(generatedDir.absolutePath,
|
||||
|
||||
+2
-2
@@ -6,7 +6,7 @@ package org.jetbrains.kotlin.cli.utilities
|
||||
|
||||
import org.jetbrains.kotlin.konan.exec.Command
|
||||
import org.jetbrains.kotlin.konan.target.PlatformManager
|
||||
import org.jetbrains.kotlin.konan.util.KonanHomeProvider
|
||||
import org.jetbrains.kotlin.utils.KotlinNativePaths
|
||||
|
||||
fun runLlvmTool(args: Array<String>) {
|
||||
val toolName = args[0]
|
||||
@@ -40,7 +40,7 @@ fun runLlvmClangToolWithTarget(args: Array<String>) {
|
||||
runCommand(toolPath, *compilerArgs, *toolArguments.toTypedArray())
|
||||
}
|
||||
|
||||
private fun platformManager() = PlatformManager(KonanHomeProvider.determineKonanHome())
|
||||
private fun platformManager() = PlatformManager(KotlinNativePaths.homePath.absolutePath)
|
||||
|
||||
private fun runCommand(vararg args: String) {
|
||||
Command(*args)
|
||||
|
||||
+1
-1
@@ -10,7 +10,7 @@ import org.jetbrains.kotlin.cli.klib.main as klibMain
|
||||
import org.jetbrains.kotlin.cli.bc.mainNoExitWithGradleRenderer as konancMainWithGradleRenderer
|
||||
import org.jetbrains.kotlin.cli.bc.mainNoExitWithXcodeRenderer as konancMainWithXcodeRenderer
|
||||
import org.jetbrains.kotlin.backend.konan.env.setEnv
|
||||
import org.jetbrains.kotlin.konan.util.usingNativeMemoryAllocator
|
||||
import org.jetbrains.kotlin.utils.usingNativeMemoryAllocator
|
||||
|
||||
private fun mainImpl(args: Array<String>, runFromDaemon: Boolean, konancMain: (Array<String>) -> Unit) {
|
||||
val utilityName = args[0]
|
||||
|
||||
Reference in New Issue
Block a user