QuinnAddon · module handoff

Speedmine for QuinnAddon

THM-Addons' packet miner, ported to Yarn mappings and QuinnAddon's conventions, with nine defects of the original fixed.

Source
THM 26.2
Lines in
1,507
Lines out
1,413
Fixes
9
Mixins
3
Compiled
clean

What was done

What you get

FileWhat it is
port-only/
Speedmine.java
The original behaviour, only reshaped so it builds inside QuinnAddon. Keep it as the reference point.
fixed/
Speedmine.java
The same module with nine defects fixed. This is the one to ship.
changes.diff249 lines. Exactly what differs between the two, so the fixes can be reviewed on their own.
mixin/ClientPlayerInteraction
ManagerAccessor.java
Required. Puts the client's prediction sequence number on the dig packets.
mixin/ClientWorld
Accessor.java
Required. Lets a packet-triggered rebreak record what the server really has, so a rejected rebreak rolls back to the block and not to air.
mixin/PlayerMove
C2SPacketAccessor.java
Needed only by the Air Miner group.

Builds

Built here from the source on this site, against Minecraft 1.21.11, Yarn 1.21.11+build.3 and meteor-client:1.21.11-SNAPSHOT. The hashes are there so you can tell the file did not change on the way to you; they say nothing about what is inside it, which is why the source is on the same page.

FileWhat it is
QuinnAddon-Test
-0.1.0.jar
For the tester. Speedmine, Inventory Cleaner and Auto Accept, nothing else. Its own mod id (quinnaddon-test) and package, so it can sit beside the real QuinnAddon without colliding.
quinnaddon-test
-source.zip
The whole project that jar was built from, Gradle files included.
QuinnAddon-v0.4.0
-with-speedmine.jar
QuinnAddon at tag v0.4.0 with Speedmine and the two modules merged in — proof the merge builds. Not a release; that is yours to cut. Its own version string reads 0.2.3, for the reason in the next section.
SHA256SUMS.txtHashes for the three files above.

If you are the tester: take the first jar, put it in mods beside Meteor, and do not run the normal QuinnAddon at the same time — they share the Speedmine module even though the ids differ. Nothing here has been run in-game, so anything you see is new information. The part most worth hammering is speedmine, and the rebreaks in particular: turn on debug-rebreak and it reports confirmed rebreaks per second beside the module name, which is a number worth writing down and comparing against whatever you normally use. Worth saying out loud: breaking is the dangerous half of a packet miner, so test it somewhere you can afford to lose what you are standing on.

Inventory Cleaner and Auto Accept

Neither of these was asked for. They are Rei's, added on his own initiative because he wanted them in the test build. Speedmine does not depend on either, so they can be dropped without touching anything else — say so and they come out.

Both arrived as finished code. Neither compiled here, and both had something worth fixing before a tester runs them. The originals are on the source page beside the fixed ones.

Still not covered: the offhand is outside the range Inventory Cleaner walks, and Auto Accept's chat check is a heuristic — a server with an unusual chat format could still get through it, which is what the player-list check is there to catch.

The code itself

Both versions, the diff between them and the two mixins are on their own page, in full, with a raw link beside each for copying.

Open the source →

Credit and licence

The THM file ships with this header, and it is a condition of use, not a courtesy:

Copyright (c) THM Addons contributors. Credit the devs, keep the link.
By using this code you agree to the license terms and to keep your repo public.

So the port keeps a header pointing back at Magnus-Krill/THM-Addons, and the module description credits them. QuinnAddon is already public, so the rest is satisfied. Please don't strip that header. Credit also to mushek, named in the original, and to BlackOut, whose AutoMine the target picker follows.

Install

Four files in, two files get a line each. Take Speedmine from fixed/, not port-only/ — same class name, so only one of them can sit in the repo at a time.

src/main/java/com/example/addon/
  modules/Speedmine.java
  mixin/ClientPlayerInteractionManagerAccessor.java
  mixin/ClientWorldAccessor.java
  mixin/PlayerMoveC2SPacketAccessor.java

// addon-template.mixins.json
"client": [
    "BetterTabPlusMixin",
    "ClientPlayerInteractionManagerAccessor",
    "ClientWorldAccessor",
    "PlayerMoveC2SPacketAccessor"
],

// QuinnAddon.java
modules.add(new Speedmine());

Two of the three mixins are required: vanilla's sendSequencedPacket is private and ClientWorld.getPendingUpdateManager() is package-private, and the miner needs both to put a sequence number on a dig packet and to keep rebreak rollbacks honest. PlayerMoveC2SPacketAccessor is only for the Air Miner — drop that settings group and you can leave it out.

Why it isn't a copy-paste

THM builds against Mojang mappings; QuinnAddon uses Yarn. Every Minecraft type and method differs, so not one line compiles as-is. On top of that, THM leans on its own support classes, none of which exist here. Each one had to be replaced — this is true even of port-only.

THMQuinnAddon
Mojang mappingsYarn — mc.level → mc.world, ServerboundPlayerActionPacket → PlayerActionC2SPacket
InventoryManagera local server-slot tracker over UpdateSelectedSlotC2SPacket
RangeUtilsisInRange() / closestFace(), in the file
RenderUtilsTHMRender3DEvent.renderer.box()
hand-written
mining formula
BlockUtils.getBreakDelta(slot, state) — Meteor already had it
ClientLevel mixinMeteor's BlockUpdateEvent
sequenced-packet
accessor
same idea, our own invoker on ClientPlayerInteractionManager
PaketLimiter,
ThmMembers, THMSystem
dropped — THM-only
fromTag() migrationdropped — no legacy Speedmine settings to migrate

One of those is worth a second look. THM wrote the vanilla mining formula out by hand, in two places that had drifted apart; Meteor ships the same calculation, so the port is shorter and can't disagree with itself. The world-update mixin also disappeared, since Meteor fires BlockUpdateEvent for exactly that.

One behavioural difference to watch. THM pauses mining through its InventoryManager priority system, so eating and other modules can hold the inventory. QuinnAddon has no shared arbiter, so this port falls back to mc.player.isUsingItem(). If AutoTotemPlus and Speedmine start fighting over the hotbar slot, that's where a shared lock belongs.

Where this differs from THM

All 35 settings are here; none dropped, none added. These are the behavioural differences, and each one exists because QuinnAddon does not have the system THM leans on. Worth knowing before you compare the two side by side.

The nine fixes

  1. A declined click did nothing at all

    The break event was cancelled before deciding whether to mine the block. With multitask off and an item in use, left-clicking a block neither packet-mined it nor fell back to vanilla mining. handleBlockClick now reports whether it took the block, and the event is cancelled only then.

  2. requestBreak could stall the whole module

    It only checked for air. An unbreakable block passed in by another module produced a context with zero progress that the removal check never cleared, so the primary slot stayed occupied forever. It now validates the block, and any context making no progress for 3s is dropped. The original's unused startMs field looks like this timeout was planned and forgotten — it is used now.

  3. One queue insert stored a mutable BlockPos

    Three of the four inserts called immutable(); one didn't. Harmless with today's callers, and silent corruption the day a MutableBlockPos reaches it.

  4. A replaced block kept being mined as the old one

    The context holds the BlockState it started on while the removal check reads the live world, so swapping the target block left it mining with the old hardness and firing the old block's break particles.

  5. Surround ring sat one block too high

    Math.round on the enemy's Y, so standing on a slab, snow layer or soul sand shifted the whole ring up. Floored now.

  6. Dead players were still targeted

    isSpectator was checked, isAlive was not, so the picker kept digging around a corpse for the whole death animation.

  7. The tool search could never return "no tool"

    It started at -1, which an empty hand already beats, making every no-tool branch dead code. Ties also went to the lowest hotbar index, so it swapped away from an equally good tool already in hand. It now starts from the selected slot, which also means fewer slot packets.

  8. One timeout, written twice

    The rebreak deadline existed as 2000 ms in one place and 2_000_000_000 ns in another. One constant now, the other derived.

  9. Outline ignored rebreak-mode Off

    Every other rebreak check tested the mode; the "last broken block" outline didn't, so it drew with rebreaks disabled.

Left alone on purpose

Build check

Both files compile against Minecraft 1.21.11, Yarn 1.21.11+build.3 and meteor-client:1.21.11-SNAPSHOT. gradlew build runs clean through compileJava, jar and remapJar, and the produced jar carries Speedmine.class and both accessors.

One real problem surfaced on the way, and it is the reason the second mixin exists: PendingUpdateManager lives in net.minecraft.client.network, not client.world, and ClientWorld.getPendingUpdateManager() is package-private. The first attempt reached for it directly and could not. Everything else that looked mapping-risky — PlayerEntity.isGliding(), PlayerMoveC2SPacket.Full(...), PlayerInventory.getSelectedSlot() — was right first time.

What this does not cover: nothing has been run in-game. The mixins compile and are listed in the config, but whether they apply at runtime, and how the miner behaves against a live anticheat, is still for you to test.

On the insta rebreak question

The idea post asked whether this is on FutureClient / Mio speedmine level, specifically at insta rebreak. Having read the whole file: the rebreak path is the most worked-on part of it.

Whether it actually matches those clients is measured, not read, and none of this has been run in-game. But the answer is one setting away: turn on debug-rebreak, run the others the same way, and compare.

Worth doing in QuinnAddon

Three things I ran into while porting. None of them block this module; the first will bite eventually.