fix: improve threaded world compatibility and chunk reads in 1.1.15
Add regression tests and per-dimension progress diagnostics. Document the unresolved C2ME random-initialization redirect conflict.
This commit is contained in:
1 parent
74cae0b581
commit
32b11aee87
42 files changed
+1506
-381
No files matched your search
@@ -6,6 +6,8 @@ import dev.modzuozhi.core.dimthread.EntityTickParallel;
|
||||
import dev.modzuozhi.core.dimthread.ISectionKeyAccessor;
|
||||
import java.util.stream.Collectors;
|
||||
import java.util.stream.Stream;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import net.minecraft.util.AbortableIterationConsumer;
|
||||
import net.minecraft.world.level.entity.EntityAccess;
|
||||
import net.minecraft.world.level.entity.EntitySection;
|
||||
@@ -75,27 +77,46 @@ public abstract class EntitySectionMixin implements ISectionKeyAccessor {
|
||||
AABB aabb, AbortableIterationConsumer<EntityAccess> consumer,
|
||||
Operation<AbortableIterationConsumer.Continuation> original
|
||||
) {
|
||||
// 内容遍历/查询:分片读锁(共享,传感器/碰撞查询并发执行)
|
||||
// Never invoke arbitrary mod callbacks under a read lock: a callback can move/remove
|
||||
// an entity, attempting to upgrade this lock to a write lock and deadlocking itself.
|
||||
List<EntityAccess> matches = new ArrayList<>();
|
||||
AbortableIterationConsumer.Continuation result;
|
||||
EntityTickParallel.lockSectionRead(this.modzuozhi_sectionKey);
|
||||
try {
|
||||
return original.call(aabb, consumer);
|
||||
result = original.call(aabb, (AbortableIterationConsumer<EntityAccess>) entity -> {
|
||||
matches.add(entity);
|
||||
return AbortableIterationConsumer.Continuation.CONTINUE;
|
||||
});
|
||||
} finally {
|
||||
EntityTickParallel.unlockSectionRead(this.modzuozhi_sectionKey);
|
||||
}
|
||||
for (EntityAccess entity : matches) {
|
||||
if (consumer.accept(entity).shouldAbort()) return AbortableIterationConsumer.Continuation.ABORT;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@WrapMethod(method = "getEntities(Lnet/minecraft/world/level/entity/EntityTypeTest;Lnet/minecraft/world/phys/AABB;Lnet/minecraft/util/AbortableIterationConsumer;)Lnet/minecraft/util/AbortableIterationConsumer$Continuation;")
|
||||
private AbortableIterationConsumer.Continuation modzuozhi_lockedGetEntitiesTyped(
|
||||
EntityTypeTest<EntityAccess, ?> typeTest, AABB aabb,
|
||||
AbortableIterationConsumer<?> consumer,
|
||||
private <U extends EntityAccess> AbortableIterationConsumer.Continuation modzuozhi_lockedGetEntitiesTyped(
|
||||
EntityTypeTest<EntityAccess, U> typeTest, AABB aabb,
|
||||
AbortableIterationConsumer<U> consumer,
|
||||
Operation<AbortableIterationConsumer.Continuation> original
|
||||
) {
|
||||
List<U> matches = new ArrayList<>();
|
||||
AbortableIterationConsumer.Continuation result;
|
||||
EntityTickParallel.lockSectionRead(this.modzuozhi_sectionKey);
|
||||
try {
|
||||
return original.call(typeTest, aabb, consumer);
|
||||
result = original.call(typeTest, aabb, (AbortableIterationConsumer<U>) entity -> {
|
||||
matches.add(entity);
|
||||
return AbortableIterationConsumer.Continuation.CONTINUE;
|
||||
});
|
||||
} finally {
|
||||
EntityTickParallel.unlockSectionRead(this.modzuozhi_sectionKey);
|
||||
}
|
||||
for (U entity : matches) {
|
||||
if (consumer.accept(entity).shouldAbort()) return AbortableIterationConsumer.Continuation.ABORT;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
Reference in new issue
Block a user