From eb0ba67d83aca9c6fb8b6962f31c09b54674c4aa Mon Sep 17 00:00:00 2001 From: granny Date: Fri, 6 Jun 2025 19:30:41 -0700 Subject: [PATCH 1/7] Updated Upstream (Paper) Upstream has released updates that appear to apply and compile correctly Paper Changes: PaperMC/Paper@4eda045b Backport fix for MC-296337 (Fixes #12617) (#12619) PaperMC/Paper@7ebc94c2 Add Registry#getTagValues (#12603) PaperMC/Paper@e87320d5 Fix UOE when using generateTree with pale oak (#12616) --- gradle.properties | 2 +- .../features/0001-Ridables.patch | 12 +++++----- ...018-API-for-any-mob-to-burn-daylight.patch | 10 ++++---- .../minecraft/world/entity/Entity.java.patch | 24 +++++++++---------- 4 files changed, 24 insertions(+), 24 deletions(-) diff --git a/gradle.properties b/gradle.properties index 90f55875d..c1e78b05f 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,7 +2,7 @@ group = org.purpurmc.purpur version = 1.21.5-R0.1-SNAPSHOT mcVersion = 1.21.5 -paperCommit = 2ba1675c7506cadd8a540ea452e5dafb79ae8947 +paperCommit = e87320d5f2c5ef7b784b2680835e0e9c101b9e30 org.gradle.configuration-cache = true org.gradle.caching = true diff --git a/purpur-server/minecraft-patches/features/0001-Ridables.patch b/purpur-server/minecraft-patches/features/0001-Ridables.patch index 009aa9ee9..e9eb00f3d 100644 --- a/purpur-server/minecraft-patches/features/0001-Ridables.patch +++ b/purpur-server/minecraft-patches/features/0001-Ridables.patch @@ -62,7 +62,7 @@ index 5ced523477c2b86e2b46182a77a9d991cf4cdd1f..f55dc4affffd495b4c02b77c8a60f172 private void updatePlayerAttributes() { diff --git a/net/minecraft/server/network/ServerGamePacketListenerImpl.java b/net/minecraft/server/network/ServerGamePacketListenerImpl.java -index c6b2591eb8ba7005919ea4b885f95c4d603305b6..9f695e97d247b24b12a4a115bfb012c7e344ccf8 100644 +index bf8a8124145e4339cadcc83691f076bdad3ec43d..6315f7aa585aa287c3c59c0cabe85faf633374fa 100644 --- a/net/minecraft/server/network/ServerGamePacketListenerImpl.java +++ b/net/minecraft/server/network/ServerGamePacketListenerImpl.java @@ -2831,6 +2831,8 @@ public class ServerGamePacketListenerImpl @@ -75,10 +75,10 @@ index c6b2591eb8ba7005919ea4b885f95c4d603305b6..9f695e97d247b24b12a4a115bfb012c7 if ((target instanceof net.minecraft.world.entity.animal.Bucketable && target instanceof LivingEntity && origItem != null && origItem == Items.WATER_BUCKET) && (event.isCancelled() || ServerGamePacketListenerImpl.this.player.getInventory().getSelectedItem().isEmpty() || !ServerGamePacketListenerImpl.this.player.getInventory().getSelectedItem().is(origItem))) { target.resendPossiblyDesyncedEntityData(ServerGamePacketListenerImpl.this.player); // Paper - The entire mob gets deleted, so resend it diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java -index b8a0abd1cbdc0c86ae9e68ebaeec14cd4728450e..05b936babba4fb9847dedb823406d06fa79a95c2 100644 +index ff6a936093abbd4799f36c2581bb57a529a18e00..ce456b05dc05534b9e2bfe408d96a44fd59f3b59 100644 --- a/net/minecraft/world/entity/Entity.java +++ b/net/minecraft/world/entity/Entity.java -@@ -3110,6 +3110,13 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess +@@ -3114,6 +3114,13 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess this.passengers = ImmutableList.copyOf(list); } @@ -92,7 +92,7 @@ index b8a0abd1cbdc0c86ae9e68ebaeec14cd4728450e..05b936babba4fb9847dedb823406d06f this.gameEvent(GameEvent.ENTITY_MOUNT, passenger); } } -@@ -3151,6 +3158,14 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess +@@ -3155,6 +3162,14 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess return false; } // CraftBukkit end @@ -107,7 +107,7 @@ index b8a0abd1cbdc0c86ae9e68ebaeec14cd4728450e..05b936babba4fb9847dedb823406d06f if (this.passengers.size() == 1 && this.passengers.get(0) == passenger) { this.passengers = ImmutableList.of(); } else { -@@ -5153,4 +5168,44 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess +@@ -5157,4 +5172,44 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess return ((ServerLevel) this.level()).isPositionEntityTicking(this.blockPosition()); } // Paper end - Expose entity id counter @@ -3347,7 +3347,7 @@ index fd33a8b59f40299ab644a4c52921b66a9b6552ca..eccbb27aa7efa6e24e04db114b06c7db return Guardian.createAttributes().add(Attributes.MOVEMENT_SPEED, 0.3F).add(Attributes.ATTACK_DAMAGE, 8.0).add(Attributes.MAX_HEALTH, 80.0); } diff --git a/net/minecraft/world/entity/monster/EnderMan.java b/net/minecraft/world/entity/monster/EnderMan.java -index 19a047c99c3afc6f8b23d7279491b156785a2c28..f991e59e896fc39da8f318871168b4c9bb0d8328 100644 +index ed322ed572cac147acf26ba18a7803685557e0d7..16df35760f7a3057be4caa63e0b59db67622a25e 100644 --- a/net/minecraft/world/entity/monster/EnderMan.java +++ b/net/minecraft/world/entity/monster/EnderMan.java @@ -91,9 +91,27 @@ public class EnderMan extends Monster implements NeutralMob { diff --git a/purpur-server/minecraft-patches/features/0018-API-for-any-mob-to-burn-daylight.patch b/purpur-server/minecraft-patches/features/0018-API-for-any-mob-to-burn-daylight.patch index 09ee6ceb8..85cb84a9a 100644 --- a/purpur-server/minecraft-patches/features/0018-API-for-any-mob-to-burn-daylight.patch +++ b/purpur-server/minecraft-patches/features/0018-API-for-any-mob-to-burn-daylight.patch @@ -6,10 +6,10 @@ Subject: [PATCH] API for any mob to burn daylight Co-authored by: Encode42 diff --git a/net/minecraft/world/entity/Entity.java b/net/minecraft/world/entity/Entity.java -index 1edca56b4bf880460148d00b98225fc34bd15f17..5b0a4ef4ae5a762432dbb0def005f7505197445e 100644 +index ce456b05dc05534b9e2bfe408d96a44fd59f3b59..de389a4db6faf229dad599366d26feff63497126 100644 --- a/net/minecraft/world/entity/Entity.java +++ b/net/minecraft/world/entity/Entity.java -@@ -521,6 +521,24 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess +@@ -525,6 +525,24 @@ public abstract class Entity implements SyncedDataHolder, Nameable, EntityAccess } // Purpur end - Add canSaveToDisk to Entity @@ -35,7 +35,7 @@ index 1edca56b4bf880460148d00b98225fc34bd15f17..5b0a4ef4ae5a762432dbb0def005f750 this.type = entityType; this.level = level; diff --git a/net/minecraft/world/entity/LivingEntity.java b/net/minecraft/world/entity/LivingEntity.java -index 13a1b5dd8b1a07a584f71b1f24da28965f5e2a5d..fb42e31e812f99bf7b74c376ed47fcaee3213238 100644 +index e7b7f09d224a630f61259a0d905b2ad6a6fa6986..b4fc3f22c088849837cb73996a5906515f12bde6 100644 --- a/net/minecraft/world/entity/LivingEntity.java +++ b/net/minecraft/world/entity/LivingEntity.java @@ -273,6 +273,7 @@ public abstract class LivingEntity extends Entity implements Attackable { @@ -96,7 +96,7 @@ index 13a1b5dd8b1a07a584f71b1f24da28965f5e2a5d..fb42e31e812f99bf7b74c376ed47fcae protected void applyInput() { diff --git a/net/minecraft/world/entity/Mob.java b/net/minecraft/world/entity/Mob.java -index b828524d62a940f89f0c0fa926ef0423019ec212..e9344f61a943d610dfabe4918c227ddba166f17f 100644 +index 964c7e60a8b0171ee31b12a277a4e9f8940ab58d..09b4e592255aa2dc49dbd82be35f2f87e0b9b6ba 100644 --- a/net/minecraft/world/entity/Mob.java +++ b/net/minecraft/world/entity/Mob.java @@ -1531,19 +1531,8 @@ public abstract class Mob extends LivingEntity implements EquipmentUser, Leashab @@ -122,7 +122,7 @@ index b828524d62a940f89f0c0fa926ef0423019ec212..e9344f61a943d610dfabe4918c227ddb @Override diff --git a/net/minecraft/world/entity/monster/AbstractSkeleton.java b/net/minecraft/world/entity/monster/AbstractSkeleton.java -index 0a5de00d41c59528e9f85a7cf82363c45e24d2bc..185edd9878f5193c44b75a126e8182caade7e943 100644 +index 607be674b6dcb9b099e9182b268c6bd960c5a87d..21cf84f1d037e3e387a3e254599673125f89ba9c 100644 --- a/net/minecraft/world/entity/monster/AbstractSkeleton.java +++ b/net/minecraft/world/entity/monster/AbstractSkeleton.java @@ -64,11 +64,12 @@ public abstract class AbstractSkeleton extends Monster implements RangedAttackMo diff --git a/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/Entity.java.patch b/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/Entity.java.patch index b88e9207b..c600e0872 100644 --- a/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/Entity.java.patch +++ b/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/Entity.java.patch @@ -38,7 +38,7 @@ public void inactiveTick() { } -@@ -512,10 +_,21 @@ +@@ -516,10 +_,21 @@ } // Paper end - optimise entity tracker @@ -60,7 +60,7 @@ this.position = Vec3.ZERO; this.blockPosition = BlockPos.ZERO; this.chunkPosition = ChunkPos.ZERO; -@@ -885,6 +_,7 @@ +@@ -889,6 +_,7 @@ && this.level.paperConfig().environment.netherCeilingVoidDamageHeight.test(v -> this.getY() >= v) && (!(this instanceof Player player) || !player.getAbilities().invulnerable))) { // Paper end - Configurable nether ceiling damage @@ -68,7 +68,7 @@ this.onBelowWorld(); } } -@@ -1830,7 +_,7 @@ +@@ -1834,7 +_,7 @@ } public boolean fireImmune() { @@ -77,7 +77,7 @@ } public boolean causeFallDamage(double fallDistance, float damageMultiplier, DamageSource damageSource) { -@@ -1890,7 +_,7 @@ +@@ -1894,7 +_,7 @@ return this.isInWater() || flag; } @@ -86,7 +86,7 @@ if (this.getVehicle() instanceof AbstractBoat abstractBoat && !abstractBoat.isUnderWater()) { this.wasTouchingWater = false; } else if (this.updateFluidHeightAndDoFluidPushing(FluidTags.WATER, 0.014)) { -@@ -2516,6 +_,13 @@ +@@ -2520,6 +_,13 @@ compound.putBoolean("Paper.FreezeLock", true); } // Paper end @@ -100,7 +100,7 @@ return compound; } catch (Throwable var8) { CrashReport crashReport = CrashReport.forThrowable(var8, "Saving entity NBT"); -@@ -2646,6 +_,13 @@ +@@ -2650,6 +_,13 @@ freezeLocked = compound.getBooleanOr("Paper.FreezeLock", false); } // Paper end @@ -114,7 +114,7 @@ } catch (Throwable var8) { CrashReport crashReport = CrashReport.forThrowable(var8, "Loading entity NBT"); CrashReportCategory crashReportCategory = crashReport.addCategory("Entity being loaded"); -@@ -2874,6 +_,7 @@ +@@ -2878,6 +_,7 @@ if (this.isAlive() && this instanceof Leashable leashable) { if (leashable.getLeashHolder() == player) { if (!this.level().isClientSide()) { @@ -122,7 +122,7 @@ // CraftBukkit start - fire PlayerUnleashEntityEvent // Paper start - Expand EntityUnleashEvent org.bukkit.event.player.PlayerUnleashEntityEvent event = org.bukkit.craftbukkit.event.CraftEventFactory.callPlayerUnleashEntityEvent(this, player, hand, !player.hasInfiniteMaterials()); -@@ -3190,15 +_,18 @@ +@@ -3194,15 +_,18 @@ return Vec3.directionFromRotation(this.getRotationVector()); } @@ -142,7 +142,7 @@ } } } -@@ -3403,7 +_,7 @@ +@@ -3407,7 +_,7 @@ } public int getMaxAirSupply() { @@ -151,7 +151,7 @@ } public int getAirSupply() { -@@ -3931,7 +_,7 @@ +@@ -3935,7 +_,7 @@ // CraftBukkit end public boolean canUsePortal(boolean allowPassengers) { @@ -160,7 +160,7 @@ } public boolean canTeleport(Level fromLevel, Level toLevel) { -@@ -4468,6 +_,12 @@ +@@ -4472,6 +_,12 @@ return Mth.lerp(partialTick, this.yRotO, this.yRot); } @@ -173,7 +173,7 @@ // Paper start - optimise collisions public boolean updateFluidHeightAndDoFluidPushing(final TagKey fluid, final double flowScale) { if (this.touchingUnloadedChunk()) { -@@ -4876,7 +_,7 @@ +@@ -4880,7 +_,7 @@ } public float maxUpStep() { From 7c6502dc1372c8522ea62ec2e2bd8f9e12a26d67 Mon Sep 17 00:00:00 2001 From: granny Date: Sun, 8 Jun 2025 12:54:36 -0700 Subject: [PATCH 2/7] Updated Upstream (Paper) Upstream has released updates that appear to apply and compile correctly Paper Changes: PaperMC/Paper@94f29035 Do not blow up accessing unregistered memories from API (Fixes #12618) (#12639) PaperMC/Paper@03efecf0 Do not fire PlayerDropItemEvent for /give command PaperMC/Paper@3527ccdf feat: expose updateDemand and restock on Villager (#12608) PaperMC/Paper@320f25cb fix sponge-absorb deleting chest content (#12647) --- gradle.properties | 2 +- purpur-api/build.gradle.kts.patch | 26 ++++++++++++++++++- .../org/bukkit/entity/Villager.java.patch | 6 ++--- .../server/commands/GiveCommand.java.patch | 2 +- .../world/entity/npc/Villager.java.patch | 2 +- .../world/level/block/SpongeBlock.java.patch | 2 +- ...005-API-for-any-mob-to-burn-daylight.patch | 4 +-- .../entity/CraftLivingEntity.java.patch | 2 +- .../entity/CraftVillager.java.patch | 7 +++-- 9 files changed, 38 insertions(+), 15 deletions(-) diff --git a/gradle.properties b/gradle.properties index c1e78b05f..055aa3e06 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,7 +2,7 @@ group = org.purpurmc.purpur version = 1.21.5-R0.1-SNAPSHOT mcVersion = 1.21.5 -paperCommit = e87320d5f2c5ef7b784b2680835e0e9c101b9e30 +paperCommit = 320f25cb04f183c18c16595100897622c88ce073 org.gradle.configuration-cache = true org.gradle.caching = true diff --git a/purpur-api/build.gradle.kts.patch b/purpur-api/build.gradle.kts.patch index 755a5bb4e..7dc5f4924 100644 --- a/purpur-api/build.gradle.kts.patch +++ b/purpur-api/build.gradle.kts.patch @@ -28,7 +28,7 @@ } } } -@@ -165,8 +_,10 @@ +@@ -165,16 +_,18 @@ val services = objects.newInstance() tasks.withType { @@ -40,6 +40,30 @@ options.use() options.isDocFilesSubDirs = true options.links( + "https://guava.dev/releases/33.3.1-jre/api/docs/", +- "https://javadoc.io/doc/org.yaml/snakeyaml/2.2/", +- "https://javadoc.io/doc/org.jetbrains/annotations/$annotationsVersion/", +- "https://javadoc.io/doc/org.joml/joml/1.10.8/", +- "https://www.javadoc.io/doc/com.google.code.gson/gson/2.11.0", ++ // "https://javadoc.io/doc/org.yaml/snakeyaml/2.2/", ++ // "https://javadoc.io/doc/org.jetbrains/annotations/$annotationsVersion/", ++ // "https://javadoc.io/doc/org.joml/joml/1.10.8/", ++ // "https://www.javadoc.io/doc/com.google.code.gson/gson/2.11.0", + "https://jspecify.dev/docs/api/", + "https://jd.advntr.dev/api/$adventureVersion/", + "https://jd.advntr.dev/key/$adventureVersion/", +@@ -183,9 +_,9 @@ + "https://jd.advntr.dev/text-serializer-legacy/$adventureVersion/", + "https://jd.advntr.dev/text-serializer-plain/$adventureVersion/", + "https://jd.advntr.dev/text-logger-slf4j/$adventureVersion/", +- "https://javadoc.io/doc/org.slf4j/slf4j-api/$slf4jVersion/", ++ // "https://javadoc.io/doc/org.slf4j/slf4j-api/$slf4jVersion/", + "https://logging.apache.org/log4j/2.x/javadoc/log4j-api/", +- "https://javadoc.io/doc/org.apache.maven.resolver/maven-resolver-api/1.7.3", ++ // "https://javadoc.io/doc/org.apache.maven.resolver/maven-resolver-api/1.7.3", + ) + options.tags("apiNote:a:API Note:") + @@ -199,11 +_,11 @@ } diff --git a/purpur-api/paper-patches/files/src/main/java/org/bukkit/entity/Villager.java.patch b/purpur-api/paper-patches/files/src/main/java/org/bukkit/entity/Villager.java.patch index 083a0d057..55d5c2802 100644 --- a/purpur-api/paper-patches/files/src/main/java/org/bukkit/entity/Villager.java.patch +++ b/purpur-api/paper-patches/files/src/main/java/org/bukkit/entity/Villager.java.patch @@ -1,9 +1,9 @@ --- a/src/main/java/org/bukkit/entity/Villager.java +++ b/src/main/java/org/bukkit/entity/Villager.java -@@ -391,4 +_,13 @@ - * reputation regardless of its impact and the player associated. +@@ -408,4 +_,13 @@ + * Demand is still updated even if all events are canceled. */ - public void clearReputations(); + public void restock(); + + // Purpur start + /** diff --git a/purpur-server/minecraft-patches/sources/net/minecraft/server/commands/GiveCommand.java.patch b/purpur-server/minecraft-patches/sources/net/minecraft/server/commands/GiveCommand.java.patch index 557923162..f48a78f28 100644 --- a/purpur-server/minecraft-patches/sources/net/minecraft/server/commands/GiveCommand.java.patch +++ b/purpur-server/minecraft-patches/sources/net/minecraft/server/commands/GiveCommand.java.patch @@ -6,5 +6,5 @@ boolean flag = serverPlayer.getInventory().add(itemStack1); + if (org.purpurmc.purpur.PurpurConfig.disableGiveCommandDrops) continue; // Purpur - add config option for toggling give command dropping if (flag && itemStack1.isEmpty()) { - ItemEntity itemEntity = serverPlayer.drop(itemStack, false); + ItemEntity itemEntity = serverPlayer.drop(itemStack, false, false, false, null); // Paper - do not fire PlayerDropItemEvent for /give command if (itemEntity != null) { diff --git a/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/npc/Villager.java.patch b/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/npc/Villager.java.patch index 71cb36d56..d87abdef5 100644 --- a/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/npc/Villager.java.patch +++ b/purpur-server/minecraft-patches/sources/net/minecraft/world/entity/npc/Villager.java.patch @@ -104,7 +104,7 @@ @@ -504,7 +_,7 @@ - private void updateDemand() { + public void updateDemand() { for (MerchantOffer merchantOffer : this.getOffers()) { - merchantOffer.updateDemand(); + merchantOffer.updateDemand(this.level().purpurConfig.villagerMinimumDemand); // Purpur - Configurable minimum demand for trades diff --git a/purpur-server/minecraft-patches/sources/net/minecraft/world/level/block/SpongeBlock.java.patch b/purpur-server/minecraft-patches/sources/net/minecraft/world/level/block/SpongeBlock.java.patch index ab343ffb3..92a63d004 100644 --- a/purpur-server/minecraft-patches/sources/net/minecraft/world/level/block/SpongeBlock.java.patch +++ b/purpur-server/minecraft-patches/sources/net/minecraft/world/level/block/SpongeBlock.java.patch @@ -19,7 +19,7 @@ + if (!fluidState.is(FluidTags.WATER) && (!level.purpurConfig.spongeAbsorbsLava || !fluidState.is(FluidTags.LAVA)) && (!level.purpurConfig.spongeAbsorbsWaterFromMud || !blockState.is(Blocks.MUD))) { // Purpur - Option for sponges to work on lava and mud return BlockPos.TraversalNodeStatus.SKIP; } else if (blockState.getBlock() instanceof BucketPickup bucketPickup - && !bucketPickup.pickupBlock(null, blockList, blockPos, blockState).isEmpty()) { // CraftBukkit + && !bucketPickup.pickupBlock(null, level, blockPos, blockState).isEmpty()) { @@ -76,6 +_,10 @@ } else { if (blockState.getBlock() instanceof LiquidBlock) { diff --git a/purpur-server/paper-patches/features/0005-API-for-any-mob-to-burn-daylight.patch b/purpur-server/paper-patches/features/0005-API-for-any-mob-to-burn-daylight.patch index 2d98f9323..07071c224 100644 --- a/purpur-server/paper-patches/features/0005-API-for-any-mob-to-burn-daylight.patch +++ b/purpur-server/paper-patches/features/0005-API-for-any-mob-to-burn-daylight.patch @@ -24,10 +24,10 @@ index 2c87953a3b99c5e776fe06271d5cba5cc355bf53..395951c968e95adffa97e1851d104faf Preconditions.checkArgument(entity != null, "Unknown entity"); diff --git a/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java b/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java -index 78846e0abe010997b6a5da04f2be4b5ffba5dd0a..5f30621d717bd0728ddc074072ab7a02c487b253 100644 +index 69d92e708bac7925ff30e403e94200236536b670..fc4fa99a993a017676da2be3cb254399d421bce1 100644 --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java -@@ -1165,4 +1165,16 @@ public class CraftLivingEntity extends CraftEntity implements LivingEntity { +@@ -1167,4 +1167,16 @@ public class CraftLivingEntity extends CraftEntity implements LivingEntity { public CombatTracker getCombatTracker() { return this.getHandle().getCombatTracker().paperCombatTracker; } diff --git a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java.patch b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java.patch index a73b21afb..fa1f1bdc9 100644 --- a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java.patch +++ b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java.patch @@ -1,6 +1,6 @@ --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftLivingEntity.java -@@ -513,7 +_,7 @@ +@@ -514,7 +_,7 @@ net.minecraft.server.level.ServerPlayer nmsKiller = killer == null ? null : ((CraftPlayer) killer).getHandle(); this.getHandle().setLastHurtByMob(nmsKiller); if (nmsKiller != null) { diff --git a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch index 266f13c33..e5121d85f 100644 --- a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch +++ b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch @@ -1,10 +1,9 @@ --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java -@@ -380,4 +_,12 @@ - public void clearReputations() { - getHandle().getGossips().gossips.clear(); +@@ -390,4 +_,11 @@ + public void restock() { + getHandle().restock(); } -+ // Paper end + + // Purpur start - Lobotomize stuck villagers + @Override From aa289e2c6ff801551fb2f585269ccffed3a154fa Mon Sep 17 00:00:00 2001 From: granny Date: Mon, 9 Jun 2025 15:55:26 -0700 Subject: [PATCH 3/7] Updated Upstream (Paper) Upstream has released updates that appear to apply and compile correctly Paper Changes: PaperMC/Paper@95565e0f Add missing attribute serialization updater PaperMC/Paper@519e4224 Fix infinite loop in RegionFile IO --- gradle.properties | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/gradle.properties b/gradle.properties index 055aa3e06..9be207ddf 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,7 +2,7 @@ group = org.purpurmc.purpur version = 1.21.5-R0.1-SNAPSHOT mcVersion = 1.21.5 -paperCommit = 320f25cb04f183c18c16595100897622c88ce073 +paperCommit = 519e4224b1ba73a99c58c8fc53aab003eb6af37a org.gradle.configuration-cache = true org.gradle.caching = true From b1d412fb40e88c4e9b24750efcfb4fd6c6f7d492 Mon Sep 17 00:00:00 2001 From: granny Date: Tue, 10 Jun 2025 17:39:23 -0700 Subject: [PATCH 4/7] Updated Upstream (Paper) Upstream has released updates that appear to apply and compile correctly Paper Changes: PaperMC/Paper@ba7fb23d Finish moving over to Holderable (#12646) --- gradle.properties | 2 +- .../org/bukkit/craftbukkit/entity/CraftVillager.java.patch | 2 +- .../java/org/bukkit/craftbukkit/entity/CraftWolf.java.patch | 5 +++-- 3 files changed, 5 insertions(+), 4 deletions(-) diff --git a/gradle.properties b/gradle.properties index 9be207ddf..54db9641c 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,7 +2,7 @@ group = org.purpurmc.purpur version = 1.21.5-R0.1-SNAPSHOT mcVersion = 1.21.5 -paperCommit = 519e4224b1ba73a99c58c8fc53aab003eb6af37a +paperCommit = ba7fb23ddd2376079951d1e22f9204d1ed691585 org.gradle.configuration-cache = true org.gradle.caching = true diff --git a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch index e5121d85f..88d5d7054 100644 --- a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch +++ b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java.patch @@ -1,6 +1,6 @@ --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftVillager.java -@@ -390,4 +_,11 @@ +@@ -258,4 +_,11 @@ public void restock() { getHandle().restock(); } diff --git a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftWolf.java.patch b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftWolf.java.patch index 4d83946e7..0144ea2a4 100644 --- a/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftWolf.java.patch +++ b/purpur-server/paper-patches/files/src/main/java/org/bukkit/craftbukkit/entity/CraftWolf.java.patch @@ -1,9 +1,10 @@ --- a/src/main/java/org/bukkit/craftbukkit/entity/CraftWolf.java +++ b/src/main/java/org/bukkit/craftbukkit/entity/CraftWolf.java -@@ -228,4 +_,15 @@ - return this.getKey().hashCode(); +@@ -135,4 +_,16 @@ + super(holder); } } ++ + // Purpur start - Configurable chance for wolves to spawn rabid + @Override + public boolean isRabid() { From 293e28a048aff420792c0d0aee709b039ca27d44 Mon Sep 17 00:00:00 2001 From: granny Date: Fri, 13 Jun 2025 19:21:39 -0700 Subject: [PATCH 5/7] use empty registryaccess where context is not needed, closes #1676 --- .../java/org/purpurmc/purpur/entity/PurpurStoredBee.java | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/purpur-server/src/main/java/org/purpurmc/purpur/entity/PurpurStoredBee.java b/purpur-server/src/main/java/org/purpurmc/purpur/entity/PurpurStoredBee.java index 1cd79edbe..800cc8b22 100644 --- a/purpur-server/src/main/java/org/purpurmc/purpur/entity/PurpurStoredBee.java +++ b/purpur-server/src/main/java/org/purpurmc/purpur/entity/PurpurStoredBee.java @@ -2,6 +2,7 @@ package org.purpurmc.purpur.entity; import io.papermc.paper.adventure.PaperAdventure; import net.kyori.adventure.text.Component; +import net.minecraft.core.RegistryAccess; import net.minecraft.nbt.CompoundTag; import net.minecraft.world.level.block.entity.BeehiveBlockEntity; import net.minecraft.world.level.block.entity.BlockEntity; @@ -31,7 +32,7 @@ public class PurpurStoredBee implements StoredEntity { this.blockStorage = blockStorage; CompoundTag customData = handle.occupant.entityData().copyTag(); - net.minecraft.network.chat.Component customNameMinecraft = BlockEntity.parseCustomNameSafe(customData.get("CustomName"), ((CraftWorld) blockStorage.getWorld()).getHandle().registryAccess()); + net.minecraft.network.chat.Component customNameMinecraft = BlockEntity.parseCustomNameSafe(customData.get("CustomName"), RegistryAccess.EMPTY); this.customName = customNameMinecraft == null ? null : PaperAdventure.asAdventure(customNameMinecraft); if (customData.get("BukkitValues") instanceof CompoundTag compoundTag) { @@ -98,7 +99,7 @@ public class PurpurStoredBee implements StoredEntity { if(customName == null) { handle.occupant.entityData().copyTag().remove("CustomName"); } else { - handle.occupant.entityData().copyTag().putString("CustomName", net.minecraft.network.chat.Component.Serializer.toJson(PaperAdventure.asVanilla(customName), ((CraftWorld) blockStorage.getWorld()).getHandle().registryAccess())); + handle.occupant.entityData().copyTag().putString("CustomName", net.minecraft.network.chat.Component.Serializer.toJson(PaperAdventure.asVanilla(customName), RegistryAccess.EMPTY)); } } } From 452bb319db2549a3c2584606943c105b278aa9ba Mon Sep 17 00:00:00 2001 From: granny Date: Fri, 13 Jun 2025 21:53:25 -0700 Subject: [PATCH 6/7] port PaperMC/Paper#12654, closes #1665 --- .../world/inventory/AbstractContainerMenu.java.patch | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/purpur-server/minecraft-patches/sources/net/minecraft/world/inventory/AbstractContainerMenu.java.patch b/purpur-server/minecraft-patches/sources/net/minecraft/world/inventory/AbstractContainerMenu.java.patch index bca7321cd..f1681845d 100644 --- a/purpur-server/minecraft-patches/sources/net/minecraft/world/inventory/AbstractContainerMenu.java.patch +++ b/purpur-server/minecraft-patches/sources/net/minecraft/world/inventory/AbstractContainerMenu.java.patch @@ -8,3 +8,12 @@ // CraftBukkit start public boolean checkReachable = true; public abstract org.bukkit.inventory.InventoryView getBukkitView(); +@@ -552,7 +_,7 @@ + + slot.setChanged(); + // CraftBukkit start - Make sure the client has the right slot contents +- if (player instanceof ServerPlayer serverPlayer && slot.getMaxStackSize() != 64) { ++ if (player instanceof ServerPlayer serverPlayer && slot.getMaxStackSize() != net.minecraft.world.Container.MAX_STACK) { // Purpur - PaperPR#12654 + serverPlayer.connection.send(new net.minecraft.network.protocol.game.ClientboundContainerSetSlotPacket(this.containerId, this.incrementStateId(), slot.index, slot.getItem())); + // Updating a crafting inventory makes the client reset the result slot, have to send it again + if (this.getBukkitView().getType() == org.bukkit.event.inventory.InventoryType.WORKBENCH || this.getBukkitView().getType() == org.bukkit.event.inventory.InventoryType.CRAFTING) { From 849bc79cac217c4ee043f1d9104511354b49a9e0 Mon Sep 17 00:00:00 2001 From: granny Date: Fri, 13 Jun 2025 22:06:35 -0700 Subject: [PATCH 7/7] register test subcommands used for debugging, closes #1675 --- .../gametest/framework/TestCommand.java.patch | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 purpur-server/minecraft-patches/sources/net/minecraft/gametest/framework/TestCommand.java.patch diff --git a/purpur-server/minecraft-patches/sources/net/minecraft/gametest/framework/TestCommand.java.patch b/purpur-server/minecraft-patches/sources/net/minecraft/gametest/framework/TestCommand.java.patch new file mode 100644 index 000000000..f0d6efc60 --- /dev/null +++ b/purpur-server/minecraft-patches/sources/net/minecraft/gametest/framework/TestCommand.java.patch @@ -0,0 +1,11 @@ +--- a/net/minecraft/gametest/framework/TestCommand.java ++++ b/net/minecraft/gametest/framework/TestCommand.java +@@ -455,7 +_,7 @@ + ) + ) + ); +- if (SharedConstants.IS_RUNNING_IN_IDE) { ++ if (org.purpurmc.purpur.PurpurConfig.registerMinecraftDebugCommands || SharedConstants.IS_RUNNING_IN_IDE) { // Purpur - register minecraft debug commands + literalArgumentBuilder = literalArgumentBuilder.then( + Commands.literal("export") + .then(