Mekanism

Mekanism

129M Downloads

Fusion reactor produces infinite heat under certain conditions

dabaer opened this issue ยท 7 comments

commented

Issue description

When connecting a Fusion reactor to a Thermoelectric boiler via Quantum Entangloperters and Thermodynamic conductors, it is possible to create a feedback loop of heat. I assume the YottaKelvin values shown in the UI are the equivalent of Infinity due to there not being any infinite heat sources (and the UI therefore not supporting such display) like there are with energy.

We stumbled across this by accident while attempting to increase the heat going into a boiler to power Industrial Turbines. We did quite a bit of testing and have been able to slightly narrow down this easily reproducible condition inside of the ATM9 Modpack. Basically when connected a certain way, the Fusion reactor will pulse between negative and positive heat values while exponentially increasing (and decreasing) in temperature, until it reaches the infinity-like value. This heat loop infects the reactor, boiler and quantum entangloporter network permanently (or for at least an hour in our testing), or until each complete multiblock is destroyed, or network deleted.

The reactor continues to output heat and power, though interestingly it stops consuming fuel when in this state. In certain conditions, when disconnected from the boiler, the reactor is also able to get stuck in a negative infinity-like state for heat.

Additionally, we only tested this on a server, as well as in the Overworld (Savannah Biome) and the ATM Mining dimension.

javaw_CoBB8f7F8S
javaw_HTpkPDrpV6

Steps to reproduce

  1. Build a Fusion reactor with ports on all available faces.
  2. Run the reactor at max burn (unsure if this is required, we only tested it at 98 mb/t) with Deuterium and Tritium
  3. Build a Thermoelectric Boiler (initially observed with a max size boiler, and later tested on 7x7) with 5 valves that face 5 ports directly on the reactor. For some reason this requires exactly 5 facing ports, we could not reproduce this with less than 5.
  4. Connect Thermodynamic conductors on all of the ports on all but one side of the reactor, and connected together.
  5. Entangloporters on the 5 remaining reactor ports, connected to the same network, with heat input/output set on all faces.
  6. An Entangloporter in this same configuration connected to another valve on the boiler (unsure if this is required)
  7. The aforementioned conductors connected to one of the Entangloporters (also unsure if this is required)

Minecraft version

1.20.1 (Latest)

(Neo)Forge version

47.1.3

Mekanism version

10.4.2 (Latest)

Other relevant versions

AllTheMods9 version 0.2.10

If a (crash)log is relevant for this issue, link it here: (It's almost always relevant)

No response

commented

Impressive, tried to reproduce it in 10.4.2 with only mek and a few mods and it was a success, the reactor goes between negative and positive 64-bit limit continuously. Although once the reactor glitches, it is broken forever, producing continuous infinite energy.

commented

Upon further investigating, turns out there are a few factors that causes this bug. There is a bug where case heat constantly goes between negative and positive values and there is the problem of Quantum Entangloporters sending heat to each other causing a massive loop where the heat goes up to 64-bit limit. Quantum Entangloporters sending heat to each other isn't a big problem but the reactor's case heat constantly flickering makes the Quantum Entangloporter's heat transfer very broken. I am not sure if thermodynamic conductors play a role in this bug, but they probably do.

commented

Just want to mention, it happened to me too a few months(maybe more) ago.

commented

Take heat from a new Quantum Entangloperter connected to a network of two Quantum Entangloperters that transfer heat from fusion reactor to a boiler can cause the new one transfer negative heat (can be under 0K). This can probably related to the same problem.

commented

Probably related to the strange negative heat problem (about how Quantum Entangloperter transfer heat?) and some overflow?

commented

default double simulateAdjacent() {
double adjacentTransfer = 0;
for (Direction side : EnumUtils.DIRECTIONS) {
IHeatHandler sink = getAdjacent(side);
if (sink != null) {
double heatCapacity = getTotalHeatCapacity(side);
double invConduction = sink.getTotalInverseConduction() + getTotalInverseConductionCoefficient(side);
double tempToTransfer = (getTotalTemperature(side) - getAmbientTemperature(side)) / invConduction;
//TODO - 1.18: Try and figure out how to do this properly/I believe the below is correct
// but it seems to nerf the heat system quite a bit so needs more review than being able
// to be done just before a release is made
/*double temp = getTotalTemperature(side);
double sinkTemp = sink.getTotalTemperature();
if (temp <= sinkTemp) {
//If our temperature is lower than the sink, we skip calculating what the adjacent loss to the sink
// is as if the sink is able to have heat transferred away from it (which is a bit of a weird concept
// in relation to thermodynamics, but makes some sense with our implementation), it will be handled by
// the sink when the sink simulates adjacent heat transfers. This also prevents us from having heat
// transfers effectively happen "twice" per tick rather than just once
// Note: We also skip if our temp is equal to the sink's temperature so that we can short circuit
// past the following logic
continue;
}
double heatCapacity = getTotalHeatCapacity(side);
double sinkHeatCapacity = sink.getTotalHeatCapacity();
//Calculate the target temperature using calorimetry
double finalTemp = (temp * heatCapacity + sinkTemp * sinkHeatCapacity) / (heatCapacity + sinkHeatCapacity);
double invConduction = sink.getTotalInverseConduction() + getTotalInverseConductionCoefficient(side);
double tempToTransfer = (temp - finalTemp) / invConduction;*/
double heatToTransfer = tempToTransfer * heatCapacity;
handleHeat(-heatToTransfer, side);
//Note: Our sinks in mek are "lazy" but they will update the next tick if needed
sink.handleHeat(heatToTransfer);
adjacentTransfer = incrementAdjacentTransfer(adjacentTransfer, tempToTransfer, side);
}
}
return adjacentTransfer;
}

I haven't learned how real world heat transfer, but this seems cause multiple heat transfer in one tick(Quantum Entangloperters and ports of fusion reactor). Transfer more heat than the container have seems also possible, since new heat was applied next tick but transfers are using heat for current tick(which might already used and cause negative heat/pulse between negative and positive heat values).
A possible solution might be manage all heat transfers and tick once after or before next tick. The tile entities still tick but only increase the area of surface (which can be used in heat transfer formula) of the specific "transfer" or add the transfer to the pending transfer set.
Steps:

  • tick tile entities to summarize all transfers
    • find all adjacent containers and add the cooler ones to the adjacent transfer map
      • map<pair<high-temp(itself),low-temp>,area>
      • If repeated, increase area by 1.
    • find all environment (such as lava, water, and air(for biome and probably weather?)) and add all those to the environment transfer map.
      • map<pair<container(itself),environment-type>,area>
        environment-type can be just temp(double value) because environment can't be change
      • If repeated, increase area by 1.
    • find all internal visual containers (coolant of reactors or burning the fuel) and add all those to the visual transfer set
      • set<pair<container(itself),visual-container>>.
      • visual-container includes structure or tile entity instance and container type
      • Area can be provided by visual container from constant(fusion) or structure info(fission and boiler).
      • There can also be maximum cool-down(water amount in boiler) and constant heat-up(fuel rate fission)
  • At the end of tick, do all transfer, process once for each container
    • do a snapshot for all heat containers
    • for each heat container, do internal heat-up
    • for each heat container, do adjacent transfer
    • for each heat container, do internal cool-down
    • for each heat container, do environment cool-down
    • for each heat container, do environment heat-up
commented

After a long time I decided to return to this issue and did some extensive testing, and narrowed the requirements down to a fusion reactor with any temp value over 300K in both plasma and casing, lots of ports, and a way to extract heat from the reactor all at once (5 boilers on 5 sides). This is what causes the issue. Turns out there is a delay in the internal code and more factors that caused this. @thiakil pushed some fixes on a new branch and this bug no longer occurs. If anyone is curious about what is the scenario while the bug is occuring, let me know. I can explain it here. It is just a little complicated and long to type.