custom SynchronizedMap

This commit is contained in:
Bixilon 2021-06-02 22:11:36 +02:00 committed by Lukas
parent 92027d93e4
commit aa84df400e
4 changed files with 203 additions and 8 deletions

View File

@ -47,6 +47,7 @@ import de.bixilon.minosoft.util.KUtil.synchronizedMapOf
import de.bixilon.minosoft.util.KUtil.synchronizedSetOf
import de.bixilon.minosoft.util.KUtil.toSynchronizedMap
import de.bixilon.minosoft.util.MMath
import de.bixilon.minosoft.util.collections.SynchronizedMap
import de.bixilon.minosoft.util.task.ThreadPoolRunnable
import glm_.vec2.Vec2i
import glm_.vec3.Vec3i
@ -61,10 +62,10 @@ class WorldRenderer(
lateinit var chunkShader: Shader
val allChunkSections: MutableMap<Vec2i, MutableMap<Int, ChunkMeshCollection>> = synchronizedMapOf()
val visibleChunks: MutableMap<Vec2i, MutableMap<Int, ChunkMeshCollection>> = synchronizedMapOf()
val allChunkSections: SynchronizedMap<Vec2i, SynchronizedMap<Int, ChunkMeshCollection>> = synchronizedMapOf()
val visibleChunks: SynchronizedMap<Vec2i, SynchronizedMap<Int, ChunkMeshCollection>> = synchronizedMapOf()
val queuedChunks: MutableSet<Vec2i> = synchronizedSetOf()
private val preparationTasks: MutableMap<Vec2i, MutableMap<Int, ThreadPoolRunnable>> = synchronizedMapOf()
private val preparationTasks: SynchronizedMap<Vec2i, SynchronizedMap<Int, ThreadPoolRunnable>> = synchronizedMapOf()
private var allBlocks: Collection<BlockState>? = null
@ -428,7 +429,7 @@ class WorldRenderer(
private fun onFrustumChange(frustum: Frustum) {
visibleChunks.clear()
for ((chunkLocation, indexMap) in allChunkSections.toSynchronizedMap()) {
val visibleIndexMap: MutableMap<Int, ChunkMeshCollection> = synchronizedMapOf()
val visibleIndexMap: SynchronizedMap<Int, ChunkMeshCollection> = synchronizedMapOf()
for ((index, mesh) in indexMap.toSynchronizedMap()) {
if (frustum.containsChunk(chunkLocation, mesh.lowestBlockHeight, mesh.highestBlockHeight)) {
visibleIndexMap[index] = mesh

View File

@ -17,6 +17,7 @@ import de.bixilon.minosoft.data.entities.entities.Entity
import de.bixilon.minosoft.data.mappings.ResourceLocation
import de.bixilon.minosoft.protocol.network.connection.PlayConnection
import de.bixilon.minosoft.protocol.protocol.ProtocolDefinition
import de.bixilon.minosoft.util.collections.SynchronizedMap
import de.bixilon.minosoft.util.enum.AliasableEnum
import sun.misc.Unsafe
import java.util.*
@ -60,8 +61,8 @@ object KUtil {
return ResourceLocation(this)
}
fun <K, V> synchronizedMapOf(vararg pairs: Pair<K, V>): MutableMap<K, V> {
return Collections.synchronizedMap(mutableMapOf(*pairs))
fun <K, V> synchronizedMapOf(vararg pairs: Pair<K, V>): SynchronizedMap<K, V> {
return SynchronizedMap(mutableMapOf(*pairs))
}
fun <V> synchronizedSetOf(vararg values: V): MutableSet<V> {
@ -84,11 +85,11 @@ object KUtil {
return synchronizedCopy { Collections.synchronizedMap(this.toMutableMap()) }
}
fun <V> List<V>.toSynchronizedList(): MutableList<V> {
fun <V> Collection<V>.toSynchronizedList(): MutableList<V> {
return synchronizedCopy { Collections.synchronizedList(this.toMutableList()) }
}
fun <V> Set<V>.toSynchronizedSet(): MutableSet<V> {
fun <V> Collection<V>.toSynchronizedSet(): MutableSet<V> {
return synchronizedCopy { Collections.synchronizedSet(this.toMutableSet()) }
}

View File

@ -19,6 +19,7 @@ import de.bixilon.minosoft.util.KUtil.toSynchronizedList
class Queue {
private val queue: MutableList<Runnable> = synchronizedListOf()
@Synchronized
fun add(runnable: Runnable) {
queue += runnable
}

View File

@ -0,0 +1,192 @@
/*
* Minosoft
* Copyright (C) 2021 Moritz Zwerger
*
* This program is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with this program. If not, see <https://www.gnu.org/licenses/>.
*
* This software is not affiliated with Mojang AB, the original developer of Minecraft.
*/
package de.bixilon.minosoft.util.collections
import de.bixilon.minosoft.util.KUtil.toSynchronizedList
import de.bixilon.minosoft.util.KUtil.toSynchronizedSet
import java.util.function.BiConsumer
import java.util.function.BiFunction
import java.util.function.Function
class SynchronizedMap<K, V>(
private val original: MutableMap<K, V>,
) : MutableMap<K, V> {
private val lock = Object()
override val size: Int
get() = synchronized(lock) { original.size }
override fun containsKey(key: K): Boolean {
synchronized(lock) {
return original.containsKey(key)
}
}
override fun containsValue(value: V): Boolean {
synchronized(lock) {
return original.containsValue(value)
}
}
override fun get(key: K): V? {
synchronized(lock) {
return original[key]
}
}
override fun isEmpty(): Boolean {
synchronized(lock) {
return original.isEmpty()
}
}
override val entries: MutableSet<MutableMap.MutableEntry<K, V>>
get() {
synchronized(lock) {
return original.entries.toSynchronizedSet()
}
}
override val keys: MutableSet<K>
get() {
synchronized(lock) {
return original.keys.toSynchronizedSet()
}
}
override val values: MutableCollection<V>
get() {
synchronized(lock) {
return original.values.toSynchronizedList()
}
}
override fun clear() {
synchronized(lock) {
original.clear()
}
}
override fun put(key: K, value: V): V? {
synchronized(lock) {
return original.put(key, value)
}
}
override fun putAll(from: Map<out K, V>) {
synchronized(lock) {
return original.putAll(from)
}
}
override fun remove(key: K): V? {
synchronized(lock) {
return original.remove(key)
}
}
override fun hashCode(): Int {
synchronized(lock) {
return original.hashCode()
}
}
override fun toString(): String {
synchronized(lock) {
return original.toString()
}
}
override fun putIfAbsent(key: K, value: V): V? {
synchronized(lock) {
return original.putIfAbsent(key, value)
}
}
override fun forEach(action: BiConsumer<in K, in V>) {
synchronized(lock) {
return original.forEach(action)
}
}
override fun getOrDefault(key: K, defaultValue: V): V {
synchronized(lock) {
return original.getOrDefault(key, defaultValue)
}
}
fun getOrPut(key: K, defaultValue: () -> V): V {
synchronized(lock) {
var value = get(key)
return if (value == null) {
value = defaultValue()
put(key, value)
value
} else {
value
}
}
}
override fun remove(key: K, value: V): Boolean {
synchronized(lock) {
return original.remove(key, value)
}
}
override fun equals(other: Any?): Boolean {
synchronized(lock) {
return original == other
}
}
override fun replaceAll(function: BiFunction<in K, in V, out V>) {
synchronized(lock) {
return original.replaceAll(function)
}
}
override fun compute(key: K, remappingFunction: BiFunction<in K, in V?, out V?>): V? {
synchronized(lock) {
return original.compute(key, remappingFunction)
}
}
override fun computeIfAbsent(key: K, mappingFunction: Function<in K, out V>): V {
synchronized(lock) {
return original.computeIfAbsent(key, mappingFunction)
}
}
override fun computeIfPresent(key: K, remappingFunction: BiFunction<in K, in V, out V?>): V? {
synchronized(lock) {
return original.computeIfPresent(key, remappingFunction)
}
}
override fun replace(key: K, value: V): V? {
synchronized(lock) {
return original.replace(key, value)
}
}
override fun merge(key: K, value: V, remappingFunction: BiFunction<in V, in V, out V?>): V? {
synchronized(lock) {
return original.merge(key, value, remappingFunction)
}
}
override fun replace(key: K, oldValue: V, newValue: V): Boolean {
synchronized(lock) {
return original.replace(key, oldValue, newValue)
}
}
}