Merge 1.19.4 into 1.20
This commit is contained in:
commit
84bd756cdf
9
.github/workflows/gradle.yml
vendored
9
.github/workflows/gradle.yml
vendored
|
|
@ -21,11 +21,12 @@ jobs:
|
||||||
with:
|
with:
|
||||||
distribution: 'temurin'
|
distribution: 'temurin'
|
||||||
java-version: 17
|
java-version: 17
|
||||||
cache: 'gradle'
|
|
||||||
- name: Build ModernFix using Gradle
|
- name: Build ModernFix using Gradle
|
||||||
run: |
|
uses: gradle/gradle-build-action@v2
|
||||||
chmod +x gradlew
|
with:
|
||||||
./gradlew --no-daemon build
|
cache-read-only: ${{ !startsWith(github.ref, 'refs/heads/1.') }}
|
||||||
|
gradle-home-cache-cleanup: true
|
||||||
|
arguments: build
|
||||||
- name: Upload Artifacts to GitHub
|
- name: Upload Artifacts to GitHub
|
||||||
uses: actions/upload-artifact@v3
|
uses: actions/upload-artifact@v3
|
||||||
with:
|
with:
|
||||||
|
|
|
||||||
|
|
@ -199,19 +199,6 @@ public class ModernFixEarlyConfig {
|
||||||
// Defines the default rules which can be configured by the user or other mods.
|
// Defines the default rules which can be configured by the user or other mods.
|
||||||
// You must manually add a rule for any new mixins not covered by an existing package rule.
|
// You must manually add a rule for any new mixins not covered by an existing package rule.
|
||||||
this.addMixinRule("launch.class_search_cache", true);
|
this.addMixinRule("launch.class_search_cache", true);
|
||||||
/*
|
|
||||||
this.addMixinRule("perf.use_integrated_resources.jepb", modPresent("jepb"));
|
|
||||||
this.addMixinRule("perf.use_integrated_resources.jeresources", modPresent("jeresources"));
|
|
||||||
this.addMixinRule("perf.jeresources_startup", modPresent("jeresources"));
|
|
||||||
this.addMixinRule("perf.state_definition_construct", modPresent("ferritecore"));
|
|
||||||
this.addMixinRule("bugfix.starlight_emptiness", modPresent("starlight"));
|
|
||||||
this.addMixinRule("bugfix.chunk_deadlock.valhesia", modPresent("valhelsia_structures"));
|
|
||||||
this.addMixinRule("bugfix.tf_cme_on_load", modPresent("twilightforest"));
|
|
||||||
this.addMixinRule("bugfix.refinedstorage", modPresent("refinedstorage"));
|
|
||||||
this.addMixinRule("perf.async_jei", modPresent("jei"));
|
|
||||||
this.addMixinRule("perf.patchouli_deduplicate_books", modPresent("patchouli"));
|
|
||||||
this.addMixinRule("perf.kubejs", modPresent("kubejs"));
|
|
||||||
*/
|
|
||||||
|
|
||||||
/* Mod compat */
|
/* Mod compat */
|
||||||
disableIfModPresent("mixin.perf.thread_priorities", "smoothboot", "threadtweak");
|
disableIfModPresent("mixin.perf.thread_priorities", "smoothboot", "threadtweak");
|
||||||
|
|
|
||||||
|
|
@ -11,7 +11,7 @@
|
||||||
"modernfix.option.off": "关闭",
|
"modernfix.option.off": "关闭",
|
||||||
"modernfix.option.disabled": "已禁用",
|
"modernfix.option.disabled": "已禁用",
|
||||||
"modernfix.option.enabled": "已启用",
|
"modernfix.option.enabled": "已启用",
|
||||||
"modernfix.option.mod_override": ",原因是安装了 [%s] 模组",
|
"modernfix.option.mod_override": ",原因是安装了这些模组:[%s]",
|
||||||
"modernfix.config.not_default": "(已修改)",
|
"modernfix.config.not_default": "(已修改)",
|
||||||
"asynclocator.map.locating": "地图(定位中……)",
|
"asynclocator.map.locating": "地图(定位中……)",
|
||||||
"asynclocator.map.none": "地图(未能在附近找到相关地物)",
|
"asynclocator.map.none": "地图(未能在附近找到相关地物)",
|
||||||
|
|
@ -69,5 +69,47 @@
|
||||||
"modernfix.option.mixin.feature.branding": "将现代化修复相关信息添加到标题界面和F3屏幕中。",
|
"modernfix.option.mixin.feature.branding": "将现代化修复相关信息添加到标题界面和F3屏幕中。",
|
||||||
"modernfix.option.mixin.feature.direct_stack_trace": "通常关闭,启用后,在发生崩溃时,它会将原始堆栈踪迹强制转储到日志里。因为原版的崩溃报告系统偶尔不能正常工作,只能给出一个完全不相关的堆栈跟踪/报告。",
|
"modernfix.option.mixin.feature.direct_stack_trace": "通常关闭,启用后,在发生崩溃时,它会将原始堆栈踪迹强制转储到日志里。因为原版的崩溃报告系统偶尔不能正常工作,只能给出一个完全不相关的堆栈跟踪/报告。",
|
||||||
"modernfix.option.mixin.feature.measure_time": "借助几个注入来测量世界加载时间、数据包重载时间、资源重载时间、启动时间,并添加必要的挂钩,以启用原版未使用的分析器逻辑,该逻辑用于分析资源重载过程。",
|
"modernfix.option.mixin.feature.measure_time": "借助几个注入来测量世界加载时间、数据包重载时间、资源重载时间、启动时间,并添加必要的挂钩,以启用原版未使用的分析器逻辑,该逻辑用于分析资源重载过程。",
|
||||||
"modernfix.option.mixin.feature.spam_thread_dump": "§l仅用于调试目的。§r使线程转储每 60 秒向日志输出一次数据。这可以帮助诊断加载/游戏过程中无法解释的冻结现象。"
|
"modernfix.option.mixin.feature.spam_thread_dump": "§l仅用于调试目的。§r使线程转储每60秒向日志输出一次数据。这可以帮助诊断加载/游戏过程中无法解释的冻结现象。",
|
||||||
|
"modernfix.option.mixin.bugfix.chunk_deadlock": "尝试预防区块系统死锁,或者,仍然发生死锁时,在日志中提供额外的调试信息。这些死锁通常表现为服务端无限期冻结(其表现例如实体不移动),而客户端继续正常工作。",
|
||||||
|
"modernfix.option.mixin.bugfix.chunk_deadlock.valhesia": "为Valhesia Structures模组打补丁,修复其代码的问题,具体表现:频繁产生世界生成/区块加载死锁。",
|
||||||
|
"modernfix.option.mixin.bugfix.cofh_core_crash": "修复了CoFH核心(CoFH Core)模组的一个多线程问题,具体表现:启动游戏时偶尔崩溃。",
|
||||||
|
"modernfix.option.mixin.bugfix.ctm_resourceutil_cme": "修复了连接纹理(ConnectedTexturesMod)模组的一个多线程问题,具体表现:启动游戏时偶尔崩溃。",
|
||||||
|
"modernfix.option.mixin.bugfix.ender_dragon_leak": "修复了一处原版内存泄漏,它由末影龙保留对先前客户端世界的引用而产生。",
|
||||||
|
"modernfix.option.mixin.bugfix.entity_load_deadlock": "针对§b实体加入世界事件(EntityJoinWorldEvent/EntityJoinLevelEvent)§r,稍微推迟了实体加载,修复了许多会产生世界生成死锁的问题。不过,这应该不会在游戏中引起任何明显的行为变化。",
|
||||||
|
"modernfix.option.mixin.bugfix.fix_config_crashes": "修复了Forge配置在启动游戏时偶尔损坏的问题。",
|
||||||
|
"modernfix.option.mixin.bugfix.item_cache_flag": "修复了MC-258939(非原子缓存状态可能产生多线程崩溃)",
|
||||||
|
"modernfix.option.mixin.bugfix.preserve_early_window_pos": "在控制权被从Forge的早期加载移交给Minecraft代码时,使游戏窗口保留其现有大小。修复了窗口被拖动后还会传送回屏幕中央等问题。",
|
||||||
|
"modernfix.option.mixin.bugfix.refinedstorage.te_bug": "如果安装了精致存储模组,会修复它的一些问题,比如,外部存储总线偶尔无法显示抽屉内容。这是精致存储PR #3435的向后移植,仅适用于1.18及更高版本。",
|
||||||
|
"modernfix.option.mixin.bugfix.remove_block_chunkloading": "修复了Forge上僵尸猪人使(0, 0)区块永久加载的问题。这是Forge PR #8583的向后移植。",
|
||||||
|
"modernfix.option.mixin.bugfix.starlight_emptiness": "修复了星光偶尔崩溃的问题,崩溃元凶是空地图未初始化。这是星光(Starlight)1.18.x中相同修复的向后移植。",
|
||||||
|
"modernfix.option.mixin.core": "现代化修复正常运作所需的核心补丁",
|
||||||
|
"modernfix.option.mixin.devenv": "在开发环境中运行时,用于提高速度和/或测试目的的补丁",
|
||||||
|
"modernfix.option.mixin.safety": "并发补丁,用于预防启动时崩溃",
|
||||||
|
"modernfix.option.mixin.feature.integrated_server_watchdog": "将原版看门狗添加到单人游戏世界中,但只是打印出堆栈跟踪,而不会强制终止世界。此版本包括全栈看门狗的功能,但多人游戏仍然需要后者。",
|
||||||
|
"modernfix.option.mixin.feature.snapshot_easter_egg": "在快照版本上运行时,添加复活节彩蛋功能(不影响任何原版视觉效果或行为)。",
|
||||||
|
"modernfix.option.mixin.feature.spark_profile_launch": "如果安装了兼容版本的火花(Spark)模组,启用后将分析主菜单之前的完整启动序列。",
|
||||||
|
"modernfix.option.mixin.feature.warn_missing_perf_mods": "一些性能模组被认为是必不可少且高度兼容的,如果没有安装这些模组,会在启动时显示警告",
|
||||||
|
"modernfix.option.mixin.launch.class_search_cache": "将Forge的资源查找器(用于查找游戏和模组的代码)替换为明显更快的版本,从而加快启动速度",
|
||||||
|
"modernfix.option.mixin.perf.clear_fabric_mapping_tables": "清除Fabric加载器中冗余或很少被模组使用的映射数据结构,来减少内存占用。出于兼容性原因,默认关闭。",
|
||||||
|
"modernfix.option.mixin.perf.clear_mixin_classinfo": "在启动结束时强制加载所有mixin,然后清除mixin数据结构,使Mixin减少大半内存占用。出于兼容性原因,默认禁用。",
|
||||||
|
"modernfix.option.mixin.perf.deduplicate_wall_shapes": "使大多数墙方块共享同一个形状对象,而不是每个墙方块都拥有属于自己的副本。当模组添加大量墙方块时,可以大大减少其带来的内存占用。",
|
||||||
|
"modernfix.option.mixin.perf.dynamic_resources.ae2": "动态资源功能的兼容性补丁,用于应用能源2模组",
|
||||||
|
"modernfix.option.mixin.perf.dynamic_resources.ctm": "动态资源功能的兼容性补丁,用于连接纹理(CTM)模组",
|
||||||
|
"modernfix.option.mixin.perf.dynamic_resources.rs": "动态资源功能的兼容性补丁,用于精致存储模组",
|
||||||
|
"modernfix.option.mixin.perf.dynamic_resources.supermartijncore": "动态资源功能的兼容性补丁,用于SuperMartijn642CoreLib模组",
|
||||||
|
"modernfix.option.mixin.perf.dynamic_resources.diagonalfences": "动态资源功能的兼容性补丁,用于对角线栅栏(Diagonal Fences)模组",
|
||||||
|
"modernfix.option.mixin.perf.faster_advancements": "重写进度检查逻辑,使其更快,且在大型整合包里不再会产生§b堆栈溢出错误(StackOverflowError)§r。这是Fabric进度调试功能的移植。",
|
||||||
|
"modernfix.option.mixin.perf.patchouli_deduplicate_books": "针对帕秋莉手册模组,修复其书籍会存储许多带有NBT标签的空条目的问题,减少了内存占用。",
|
||||||
|
"modernfix.option.mixin.perf.remove_spawn_chunks": "从游戏中完全删除出生点区块(spawn chunks)。它们彻底不再加载了,这点与Ksyxis不同。",
|
||||||
|
"modernfix.option.mixin.perf.use_integrated_resources.jepb": "",
|
||||||
|
"modernfix.option.mixin.perf.use_integrated_resources.jeresources": "",
|
||||||
|
"modernfix.option.mixin.bugfix.blueprint_modif_memory_leak": "针对蓝图(Blueprint)模组,修复其§bObjectModificationManager§r泄漏原版资源的问题,减少了内存占用。尽管我已经贡献了修复代码(PR #195),但包含此修复代码的新版本尚未发布。",
|
||||||
|
"modernfix.option.mixin.bugfix.removed_dimensions": "修复了删除维度模组后游戏无法加载世界的问题。这是Forge PR #8959的向后移植。",
|
||||||
|
"modernfix.option.mixin.perf.compact_bit_storage": "某些传统服务器(例如Hypixel)会认为空区块包含方块,照常发送这些区块,从而浪费内存。此项修复了这个问题,显著减少了这些服务器上的内存占用。",
|
||||||
|
"modernfix.option.mixin.perf.deduplicate_climate_parameters": "新的生物群系系统使用了气候参数(climate parameter)对象,对其进行去重,可以节省约2MB内存,但也在一定程度上减慢了数据包的重载速度。",
|
||||||
|
"modernfix.option.mixin.perf.dynamic_entity_renderers": "实体模型在实体首次出现时构造,而不是在启动时构造。某些模组与此项不兼容,会导致§b实体渲染器(EntityRenderer)§r崩溃。",
|
||||||
|
"modernfix.option.mixin.perf.twilightforest.structure_spawn_fix": "针对暮色森林模组,修复了其世界生成检查结构效率极低导致卡顿的问题",
|
||||||
|
"modernfix.option.mixin.perf.fast_forge_dummies": "使用更快的代码路径,加快启动时Forge注册表的冻结速度",
|
||||||
|
"modernfix.option.mixin.perf.tag_id_caching": "缓存位置对象,不再每次都重新创建它,这可以加快标签条目的使用速度",
|
||||||
|
"modernfix.option.mixin.feature.disable_unihex_font": "删除Unicode字体,可以节省10MB内存,但会导致特殊字符不再渲染"
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -5,6 +5,7 @@ import com.google.common.cache.CacheBuilder;
|
||||||
import com.google.common.cache.RemovalNotification;
|
import com.google.common.cache.RemovalNotification;
|
||||||
import com.google.common.collect.ForwardingMap;
|
import com.google.common.collect.ForwardingMap;
|
||||||
import com.google.common.collect.ImmutableList;
|
import com.google.common.collect.ImmutableList;
|
||||||
|
import net.minecraft.client.Minecraft;
|
||||||
import net.minecraft.client.color.block.BlockColors;
|
import net.minecraft.client.color.block.BlockColors;
|
||||||
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
|
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
|
||||||
import net.minecraft.client.resources.model.*;
|
import net.minecraft.client.resources.model.*;
|
||||||
|
|
@ -280,7 +281,7 @@ public abstract class ModelBakeryMixin implements IExtendedModelBakery {
|
||||||
}
|
}
|
||||||
@Redirect(method = "loadModel", at = @At(value = "INVOKE", target = "Lnet/minecraft/world/level/block/state/StateDefinition;getPossibleStates()Lcom/google/common/collect/ImmutableList;"))
|
@Redirect(method = "loadModel", at = @At(value = "INVOKE", target = "Lnet/minecraft/world/level/block/state/StateDefinition;getPossibleStates()Lcom/google/common/collect/ImmutableList;"))
|
||||||
private ImmutableList<BlockState> loadOnlyRelevantBlockState(StateDefinition<Block, BlockState> stateDefinition, ResourceLocation location) {
|
private ImmutableList<BlockState> loadOnlyRelevantBlockState(StateDefinition<Block, BlockState> stateDefinition, ResourceLocation location) {
|
||||||
if(!(location instanceof ModelResourceLocation))
|
if(!(location instanceof ModelResourceLocation) || Minecraft.getInstance().level == null)
|
||||||
return stateDefinition.getPossibleStates();
|
return stateDefinition.getPossibleStates();
|
||||||
return ModelBakeryHelpers.getBlockStatesForMRL(stateDefinition, (ModelResourceLocation)location);
|
return ModelBakeryHelpers.getBlockStatesForMRL(stateDefinition, (ModelResourceLocation)location);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -2,15 +2,14 @@ package org.embeddedt.modernfix.forge.mixin.bugfix.cofh_core_crash;
|
||||||
|
|
||||||
import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
|
import it.unimi.dsi.fastutil.objects.Object2ObjectOpenHashMap;
|
||||||
import org.embeddedt.modernfix.annotation.RequiresMod;
|
import org.embeddedt.modernfix.annotation.RequiresMod;
|
||||||
import org.spongepowered.asm.mixin.Final;
|
import org.spongepowered.asm.mixin.*;
|
||||||
import org.spongepowered.asm.mixin.Mixin;
|
|
||||||
import org.spongepowered.asm.mixin.Pseudo;
|
|
||||||
import org.spongepowered.asm.mixin.Shadow;
|
|
||||||
import org.spongepowered.asm.mixin.injection.At;
|
import org.spongepowered.asm.mixin.injection.At;
|
||||||
import org.spongepowered.asm.mixin.injection.Coerce;
|
import org.spongepowered.asm.mixin.injection.Coerce;
|
||||||
import org.spongepowered.asm.mixin.injection.Redirect;
|
import org.spongepowered.asm.mixin.injection.Redirect;
|
||||||
|
|
||||||
import java.util.function.Supplier;
|
import java.lang.invoke.MethodHandle;
|
||||||
|
import java.lang.invoke.MethodHandles;
|
||||||
|
import java.lang.reflect.Method;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Fix getOrCreateFlag accessing the FLAGS map without synchronization by wrapping all calls to it
|
* Fix getOrCreateFlag accessing the FLAGS map without synchronization by wrapping all calls to it
|
||||||
|
|
@ -21,19 +20,36 @@ import java.util.function.Supplier;
|
||||||
@RequiresMod("cofh_core")
|
@RequiresMod("cofh_core")
|
||||||
public class FlagManagerMixin {
|
public class FlagManagerMixin {
|
||||||
@Shadow @Final
|
@Shadow @Final
|
||||||
private static Object2ObjectOpenHashMap<String, Supplier<Boolean>> FLAGS;
|
private static Object2ObjectOpenHashMap<String, ?> FLAGS;
|
||||||
|
|
||||||
@Shadow
|
@Unique
|
||||||
private Supplier<Boolean> getOrCreateFlag(String flag) {
|
private static final MethodHandle mfix$getOrCreateFlag;
|
||||||
throw new AssertionError();
|
|
||||||
|
static {
|
||||||
|
// use this reflection dance to avoid depending on whether it's implemented via BooleanSupplier or Supplier<Boolean>
|
||||||
|
try {
|
||||||
|
Method m = MethodHandles.lookup().lookupClass().getDeclaredMethod("getOrCreateFlag", String.class);
|
||||||
|
m.setAccessible(true);
|
||||||
|
mfix$getOrCreateFlag = MethodHandles.lookup().unreflect(m);
|
||||||
|
} catch(ReflectiveOperationException e) {
|
||||||
|
throw new AssertionError(e);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Redirect(method = "*", at = @At(value = "INVOKE", target = "getOrCreateFlag"), require = 0)
|
@Redirect(method = "*", at = @At(value = "INVOKE", target = "getOrCreateFlag"), require = 0)
|
||||||
private Supplier<Boolean> getFlag(@Coerce Object flagHandler, String flag) {
|
@Coerce
|
||||||
|
private Object getFlag(@Coerce Object flagHandler, String flag) {
|
||||||
if(flagHandler != this)
|
if(flagHandler != this)
|
||||||
throw new AssertionError("Redirect targeted bad getOrCreateFlag invocation");
|
throw new AssertionError("Redirect targeted bad getOrCreateFlag invocation");
|
||||||
synchronized (FLAGS) {
|
synchronized (FLAGS) {
|
||||||
return this.getOrCreateFlag(flag);
|
try {
|
||||||
|
return mfix$getOrCreateFlag.invoke((Object)this, flag);
|
||||||
|
} catch(Throwable e) {
|
||||||
|
if(e instanceof RuntimeException)
|
||||||
|
throw (RuntimeException)e;
|
||||||
|
else
|
||||||
|
throw new RuntimeException(e);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -4,6 +4,7 @@ import com.google.common.cache.Cache;
|
||||||
import com.google.common.cache.CacheBuilder;
|
import com.google.common.cache.CacheBuilder;
|
||||||
import com.google.common.cache.RemovalNotification;
|
import com.google.common.cache.RemovalNotification;
|
||||||
import com.google.common.collect.ImmutableList;
|
import com.google.common.collect.ImmutableList;
|
||||||
|
import net.minecraft.client.Minecraft;
|
||||||
import net.minecraft.client.color.block.BlockColors;
|
import net.minecraft.client.color.block.BlockColors;
|
||||||
import net.minecraft.client.renderer.block.model.BlockModel;
|
import net.minecraft.client.renderer.block.model.BlockModel;
|
||||||
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
|
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
|
||||||
|
|
@ -256,7 +257,7 @@ public abstract class ModelBakeryMixin implements IExtendedModelBakery {
|
||||||
}
|
}
|
||||||
@Redirect(method = "loadModel", at = @At(value = "INVOKE", target = "Lnet/minecraft/world/level/block/state/StateDefinition;getPossibleStates()Lcom/google/common/collect/ImmutableList;"))
|
@Redirect(method = "loadModel", at = @At(value = "INVOKE", target = "Lnet/minecraft/world/level/block/state/StateDefinition;getPossibleStates()Lcom/google/common/collect/ImmutableList;"))
|
||||||
private ImmutableList<BlockState> loadOnlyRelevantBlockState(StateDefinition<Block, BlockState> stateDefinition, ResourceLocation location) {
|
private ImmutableList<BlockState> loadOnlyRelevantBlockState(StateDefinition<Block, BlockState> stateDefinition, ResourceLocation location) {
|
||||||
if(!(location instanceof ModelResourceLocation))
|
if(!(location instanceof ModelResourceLocation) || Minecraft.getInstance().level == null)
|
||||||
return stateDefinition.getPossibleStates();
|
return stateDefinition.getPossibleStates();
|
||||||
return ModelBakeryHelpers.getBlockStatesForMRL(stateDefinition, (ModelResourceLocation)location);
|
return ModelBakeryHelpers.getBlockStatesForMRL(stateDefinition, (ModelResourceLocation)location);
|
||||||
}
|
}
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue
Block a user