For the love of god

This commit is contained in:
DBotThePony 2023-02-24 14:31:26 +07:00
parent 10e71d2ab8
commit a36e47c629
Signed by: DBot
GPG Key ID: DCC23B5715498507

View File

@ -1,14 +1,20 @@
package ru.dbotthepony.mc.otm.network
import it.unimi.dsi.fastutil.io.FastByteArrayInputStream
import it.unimi.dsi.fastutil.objects.Object2ObjectFunction
import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap
import net.minecraft.core.BlockPos
import net.minecraft.network.FriendlyByteBuf
import net.minecraft.world.level.Level
import net.minecraftforge.network.NetworkDirection
import net.minecraftforge.network.NetworkEvent
import org.apache.logging.log4j.LogManager
import ru.dbotthepony.mc.otm.android.feature.ItemEntityDataPacket
import ru.dbotthepony.mc.otm.block.entity.MatteryBlockEntity
import ru.dbotthepony.mc.otm.client.minecraft
import ru.dbotthepony.mc.otm.client.onceClient
import java.lang.ref.SoftReference
import java.util.WeakHashMap
import java.util.function.Supplier
class BlockEntitySyncPacket(val position: BlockPos, val buffer: ByteArray, val validBytes: Int) : MatteryPacket {
@ -17,23 +23,63 @@ class BlockEntitySyncPacket(val position: BlockPos, val buffer: ByteArray, val v
buff.writeBytes(buffer, 0, validBytes)
}
private fun execute() {
val level = minecraft.player?.level
if (level == null) {
LOGGER.error("Received BlockEntitySyncPacket before we are in valid level.")
onceClient {
execute()
}
return
}
val blockEntity = level.getBlockEntity(position)
if (blockEntity == null) {
LOGGER.warn("Putting BlockEntitySyncPacket received for $position into backlog because there is literally no block entity there!")
LOGGER.warn("This is CERTAINLY a bug in one of optimizing mods you have or server has installed!")
LOGGER.warn("This can cause memory leak.")
backlog.computeIfAbsent(level) { Object2ObjectOpenHashMap() }
.computeIfAbsent(position, Object2ObjectFunction { ArrayList() })
.add(this)
return
} else if (blockEntity !is MatteryBlockEntity) {
LOGGER.warn("Dropping BlockEntitySyncPacket received for $position, because there is $blockEntity which is not MatteryBlockEntity!")
backlog[level]?.remove(position)
return
}
val packets = backlog[level]?.remove(position)
try {
if (packets != null) {
for (packet in packets) {
blockEntity.synchronizer.read(FastByteArrayInputStream(packet.buffer, 0, packet.validBytes))
}
}
blockEntity.synchronizer.read(FastByteArrayInputStream(buffer, 0, validBytes))
} catch(err: Throwable) {
LOGGER.error("Exception while reading synchronized BlockEntity data!\nPosition: $position\nBlock: ${level.getBlockState(position)}\nBlock entity: $blockEntity", err)
}
}
override fun play(context: Supplier<NetworkEvent.Context>) {
context.packetHandled = true
context.enqueueWork {
val level = minecraft.player?.level ?: return@enqueueWork
val blockEntity = level.getBlockEntity(position) as? MatteryBlockEntity ?: return@enqueueWork
try {
blockEntity.synchronizer.read(FastByteArrayInputStream(buffer, 0, validBytes))
} catch(err: Throwable) {
LOGGER.error("Exception while reading synchronized BlockEntity data!\nPosition: $position\nBlock: ${level.getBlockState(position)}\nBlock entity: $blockEntity", err)
throw err
}
execute()
}
}
companion object {
private val backlog = WeakHashMap<Level, Object2ObjectOpenHashMap<BlockPos, ArrayList<BlockEntitySyncPacket>>>()
fun read(buff: FriendlyByteBuf): BlockEntitySyncPacket {
val position = buff.readBlockPos()
val size = buff.readableBytes()
@ -47,7 +93,7 @@ class BlockEntitySyncPacket(val position: BlockPos, val buffer: ByteArray, val v
}
object WorldNetworkChannel : MatteryNetworkChannel(
version = "2",
version = "3",
name = "world"
) {
fun register() {