InteractionChain class

Пакет: com.hypixel.hytale.server.core.entity

Файл: com/hypixel/hytale/server/core/entity/InteractionChain.java

implements: ChainSyncStorage

Поля (54)

МодификаторыТипИмя
final HytaleLogger LOGGER
ForkedChainId baseForkedChainId
InteractionChainData chainData
InteractionState clientState
ForkedChainId forkedChainId
return
final Long2ObjectMap<InteractionChain.TempChain> tempForkedChainData
final List<InteractionSyncData> tempSyncData
InteractionChain.CallState var1
long var1
InteractionEntry var1
InteractionEntry var1
int var10
RootInteraction var11
ObjectIterator var12
Entry var13
InteractionChain.TempChain var14
int var15
InteractionChain var16
long var2
var2
InteractionEntry var2
int var2
int var2
long var3
var3
long var3
var3
InteractionCooldown var3
InteractionEntry var3
var3
int var3
long var4
String var4
var4
InteractionEntry var4
ForkedChainId var4
var4
ForkedChainId var4
var4
long var5
long var5
CooldownHandler.Cooldown var5
int var5
InteractionChain var5
InteractionChain.TempChain var5
InteractionChain.TempChain var6
InteractionChain var7
var7
InteractionChain.TempChain var7
InteractionEntry var8
InteractionEntry var8
int var9
RootInteraction var9

Методы (107)

МодификаторыВозвратСигнатура
private record CallStaterecord CallState(RootInteraction rootInteraction, int operationCounter)
abstract throw new IllegalArgumentExceptionthrow new IllegalArgumentException("Trying to access removed interaction entry")
TempChain TempChain()
public void clearInteractionSyncDatapublic void clearInteractionSyncData(int var1)
public boolean consumeFirstRunboolean consumeFirstRun()
public void copyTempFromvoid copyTempFrom(@Nonnull InteractionChain.TempChain var1)
public void flagDesyncvoid flagDesync()
abstract for for(int var4 = Math.max(var5, 0)
static long forkedIdToIndexlong forkedIdToIndex(@Nonnull ForkedChainId var0)
public ForkedChainId getBaseForkedChainIdForkedChainId getBaseForkedChainId()
public ForkedChainId getBaseForkedChainIdpublic ForkedChainId getBaseForkedChainId()
public InteractionType getBaseTypeInteractionType getBaseType()
public int getCallDepthint getCallDepth()
public InteractionChainData getChainDataInteractionChainData getChainData()
public InteractionChainData getChainDatapublic InteractionChainData getChainData()
public int getChainIdint getChainId()
public int getClientOperationIndexint getClientOperationIndex()
public InteractionState getClientStatepublic InteractionState getClientState()
public InteractionContext getContextInteractionContext getContext()
public InteractionState getFinalStateInteractionState getFinalState()
public InteractionChain getForkedChainInteractionChain getForkedChain(@Nonnull ForkedChainId var1)
public ForkedChainId getForkedChainIdForkedChainId getForkedChainId()
public InteractionEntry getInteractionpublic InteractionEntry getInteraction(int var1)
public int getOperationCounterint getOperationCounter()
public int getOperationIndexint getOperationIndex()
public InteractionChain.TempChain getOrCreateTempForkedChainpublic InteractionChain.TempChain getOrCreateTempForkedChain(@Nonnull ForkedChainId var1)
public RootInteraction getRootInteractionRootInteraction getRootInteraction()
public InteractionState getServerStateInteractionState getServerState()
public int getSimulatedCallDepthint getSimulatedCallDepth()
public int getSimulatedOperationCounterint getSimulatedOperationCounter()
public RootInteraction getSimulatedRootInteractionRootInteraction getSimulatedRootInteraction()
public float getTimeInSecondsfloat getTimeInSeconds()
public float getTimeShiftfloat getTimeShift()
public long getTimestamplong getTimestamp()
public InteractionType getTypeInteractionType getType()
public long getWaitingForClientFinishedlong getWaitingForClientFinished()
public long getWaitingForServerFinishedlong getWaitingForServerFinished()
public boolean hasSentInitialboolean hasSentInitial()
if if(var5 != NULL_FORK_ID)
if if(var7 == null && var1.subIndex < 0 && var2 != null)
if if(var8 == null)
if if(var7 != null)
if if(var1.subIndex < 0)
if if(var4 != NULL_FORK_ID)
if if(var2 != null)
if if(var5 != NULL_FORK_ID)
if if(var7 != null)
if if(var14.baseForkedChainId != null)
if if(var16 != null)
if if(var16 == var2)
if if(var2)
if if(this.timestamp == 0L)
if if(!this.completed)
if if(this.onCompletion != null)
if if(var2)
if if(var3 != null && var3.cooldownId != null)
if if(var5 != null)
if if(this.serverState == InteractionState.NotFinished)
if if(this.clientState == InteractionState.NotFinished)
if if(var2 < 0)
if if(var3 == null)
if if(var3 != 0)
if if(var1 >= 0)
if if(var1 != 0)
if if(this.tempSyncDataOffset == var1)
if if(var5 != null)
if if(var6 == null)
public boolean isDesyncedboolean isDesynced()
public boolean isFirstRunboolean isFirstRun()
public boolean isPredictedboolean isPredicted()
public boolean isSyncDataOutOfOrderpublic boolean isSyncDataOutOfOrder(int var1)
public void nextOperationIndexvoid nextOperationIndex()
void onCompletionvoid onCompletion(CooldownHandler var1, boolean var2)
public void popRootvoid popRoot()
public void pushRootvoid pushRoot(RootInteraction var1, boolean var2)
public void putForkedChainvoid putForkedChain(@Nonnull ForkedChainId var1, @Nonnull InteractionChain var2)
public void putInteractionSyncDatapublic void putInteractionSyncData(int var1, InteractionSyncData var2)
public void removeInteractionEntryvoid removeInteractionEntry(@Nonnull InteractionManager var1, int var2)
public boolean requiresClientboolean requiresClient()
public void setBaseForkedChainIdpublic void setBaseForkedChainId(ForkedChainId var1)
public void setBaseTypevoid setBaseType(InteractionType var1)
public void setChainDatapublic void setChainData(InteractionChainData var1)
public void setChainIdvoid setChainId(int var1)
public void setClientStatepublic void setClientState(InteractionState var1)
public void setFinalStatevoid setFinalState(InteractionState var1)
public void setFirstRunvoid setFirstRun(boolean var1)
public void setForkedChainIdpublic void setForkedChainId(ForkedChainId var1)
public void setOnCompletionvoid setOnCompletion(Runnable var1)
public void setOperationCountervoid setOperationCounter(int var1)
public void setPreTickedvoid setPreTicked(boolean var1)
void setPredictedvoid setPredicted(boolean var1)
public void setSentInitialvoid setSentInitial(boolean var1)
public void setServerStatevoid setServerState(InteractionState var1)
public void setSimulatedOperationCountervoid setSimulatedOperationCounter(int var1)
public void setTimeShiftvoid setTimeShift(float var1)
public void setTimestampvoid setTimestamp(long var1)
public void setWaitingForClientFinishedvoid setWaitingForClientFinished(long var1)
public void setWaitingForServerFinishedvoid setWaitingForServerFinished(long var1)
public void syncForkpublic void syncFork(@Nonnull Ref<EntityStore> var1, @Nonnull InteractionManager var2, @Nonnull SyncInteractionChain var3)
abstract this this(null, null, var1, var2, var3, var4, var5, var6)
public String toStringpublic String toString()
void updateServerStatevoid updateServerState()
void updateSimulatedStatevoid updateSimulatedState()
public void updateSyncPositionpublic void updateSyncPosition(int var1)
public boolean wasPreTickedboolean wasPreTicked()
while while(var4.forkedId != null)
while while(var4.forkedId != null)

Исходный код

Показать/скрыть
class="kw">package com.hypixel.hytale.server.core.entity;

class="kw">import com.hypixel.hytale.component.Ref;
class="kw">import com.hypixel.hytale.logger.HytaleLogger;
class="kw">import com.hypixel.hytale.protocol.ForkedChainId;
class="kw">import com.hypixel.hytale.protocol.InteractionChainData;
class="kw">import com.hypixel.hytale.protocol.InteractionCooldown;
class="kw">import com.hypixel.hytale.protocol.InteractionState;
class="kw">import com.hypixel.hytale.protocol.InteractionSyncData;
class="kw">import com.hypixel.hytale.protocol.InteractionType;
class="kw">import com.hypixel.hytale.protocol.packets.interaction.SyncInteractionChain;
class="kw">import com.hypixel.hytale.server.core.modules.interaction.interaction.CooldownHandler;
class="kw">import com.hypixel.hytale.server.core.modules.interaction.interaction.config.Interaction;
class="kw">import com.hypixel.hytale.server.core.modules.interaction.interaction.config.RootInteraction;
class="kw">import com.hypixel.hytale.server.core.universe.world.storage.EntityStore;
class="kw">import it.unimi.dsi.fastutil.longs.Long2LongMap;
class="kw">import it.unimi.dsi.fastutil.longs.Long2LongOpenHashMap;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectMap;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectMaps;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectOpenHashMap;
class="kw">import it.unimi.dsi.fastutil.longs.Long2ObjectMap.Entry;
class="kw">import it.unimi.dsi.fastutil.objects.ObjectArrayList;
class="kw">import it.unimi.dsi.fastutil.objects.ObjectIterator;
class="kw">import java.util.List;
class="kw">import java.util.logging.Level;
class="kw">import javax.annotation.Nonnull;
class="kw">import javax.annotation.Nullable;

class="kw">public class InteractionChain class="kw">implements ChainSyncStorage {
   class="kw">private class="kw">static class="kw">final HytaleLogger LOGGER = HytaleLogger.forEnclosingClass();
   class="kw">private class="kw">static class="kw">final long NULL_FORK_ID = forkedIdToIndex(new ForkedChainId(-1, Integer.MAX_VALUE, null));
   class="kw">private class="kw">static class="kw">final int FORK_MAP_INITIAL_CAPACITY = 2;
   class="kw">private class="kw">final InteractionType type;
   class="kw">private InteractionType baseType;
   class="kw">private class="kw">final InteractionChainData chainData;
   class="kw">private int chainId;
   class="kw">private class="kw">final ForkedChainId forkedChainId;
   class="kw">private class="kw">final ForkedChainId baseForkedChainId;
   class="kw">private boolean predicted;
   class="kw">private class="kw">final InteractionContext context;
   @Nonnull
   class="kw">private class="kw">final Long2ObjectMap<InteractionChain> forkedChains = new Long2ObjectOpenHashMap(2);
   @Nonnull
   class="kw">private class="kw">final Long2ObjectMap<InteractionChain.TempChain> tempForkedChainData = new Long2ObjectOpenHashMap(2);
   @Nonnull
   class="kw">private class="kw">final Long2LongMap forkedChainsMap = new Long2LongOpenHashMap(2);
   @Nonnull
   class="kw">private class="kw">final List<InteractionChain> newForks = new ObjectArrayList();
   @Nonnull
   class="kw">private class="kw">final RootInteraction initialRootInteraction;
   class="kw">private RootInteraction rootInteraction;
   class="kw">private int operationCounter = 0;
   @Nonnull
   class="kw">private class="kw">final List<InteractionChain.CallState> callStack = new ObjectArrayList();
   class="kw">private int simulatedCallStack = 0;
   class="kw">private class="kw">final boolean requiresClient;
   class="kw">private int simulatedOperationCounter = 0;
   class="kw">private RootInteraction simulatedRootInteraction;
   class="kw">private int operationIndex = 0;
   class="kw">private int operationIndexOffset = 0;
   class="kw">private int clientOperationIndex = 0;
   @Nonnull
   class="kw">private class="kw">final List<InteractionEntry> interactions = new ObjectArrayList();
   @Nonnull
   class="kw">private class="kw">final List<InteractionSyncData> tempSyncData = new ObjectArrayList();
   class="kw">private int tempSyncDataOffset = 0;
   class="kw">private long timestamp = System.nanoTime();
   class="kw">private long waitingForServerFinished;
   class="kw">private long waitingForClientFinished;
   class="kw">private InteractionState clientState = InteractionState.NotFinished;
   class="kw">private InteractionState serverState = InteractionState.NotFinished;
   class="kw">private InteractionState finalState = InteractionState.Finished;
   @Nullable
   class="kw">private Runnable onCompletion;
   class="kw">private boolean sentInitial;
   class="kw">private boolean desynced;
   class="kw">private float timeShift;
   class="kw">private boolean firstRun = true;
   class="kw">private boolean isFirstRun = true;
   class="kw">private boolean completed = false;
   class="kw">private boolean preTicked;
   boolean skipChainOnClick;

   class="kw">public InteractionChain(
      InteractionType var1, InteractionContext var2, InteractionChainData var3, @Nonnull RootInteraction var4, @Nullable Runnable var5, boolean var6
   ) {
      this(null, null, var1, var2, var3, var4, var5, var6);
   }

   class="kw">public InteractionChain(
      ForkedChainId var1,
      ForkedChainId var2,
      InteractionType var3,
      InteractionContext var4,
      InteractionChainData var5,
      @Nonnull RootInteraction var6,
      @Nullable Runnable var7,
      boolean var8
   ) {
      this.type = this.baseType = var3;
      this.context = var4;
      this.chainData = var5;
      this.forkedChainId = var1;
      this.baseForkedChainId = var2;
      this.onCompletion = var7;
      this.initialRootInteraction = this.rootInteraction = this.simulatedRootInteraction = var6;
      this.requiresClient = var8 || var6.needsRemoteSync();
      this.forkedChainsMap.defaultReturnValue(NULL_FORK_ID);
   }

   class="kw">public InteractionType getType() {
      class="kw">return this.type;
   }

   class="kw">public int getChainId() {
      class="kw">return this.chainId;
   }

   class="kw">public ForkedChainId getForkedChainId() {
      class="kw">return this.forkedChainId;
   }

   class="kw">public ForkedChainId getBaseForkedChainId() {
      class="kw">return this.baseForkedChainId;
   }

   @Nonnull
   class="kw">public RootInteraction getInitialRootInteraction() {
      class="kw">return this.initialRootInteraction;
   }

   class="kw">public boolean isPredicted() {
      class="kw">return this.predicted;
   }

   class="kw">public InteractionContext getContext() {
      class="kw">return this.context;
   }

   class="kw">public InteractionChainData getChainData() {
      class="kw">return this.chainData;
   }

   class="kw">public InteractionState getServerState() {
      class="kw">return this.serverState;
   }

   class="kw">public boolean requiresClient() {
      class="kw">return this.requiresClient;
   }

   class="kw">public RootInteraction getRootInteraction() {
      class="kw">return this.rootInteraction;
   }

   class="kw">public RootInteraction getSimulatedRootInteraction() {
      class="kw">return this.simulatedRootInteraction;
   }

   class="kw">public int getOperationCounter() {
      class="kw">return this.operationCounter;
   }

   class="kw">public void setOperationCounter(int var1) {
      this.operationCounter = var1;
   }

   class="kw">public int getSimulatedOperationCounter() {
      class="kw">return this.simulatedOperationCounter;
   }

   class="kw">public void setSimulatedOperationCounter(int var1) {
      this.simulatedOperationCounter = var1;
   }

   class="kw">public boolean wasPreTicked() {
      class="kw">return this.preTicked;
   }

   class="kw">public void setPreTicked(boolean var1) {
      this.preTicked = var1;
   }

   class="kw">public int getOperationIndex() {
      class="kw">return this.operationIndex;
   }

   class="kw">public void nextOperationIndex() {
      this.operationIndex++;
      this.clientOperationIndex++;
   }

   class="kw">public int getClientOperationIndex() {
      class="kw">return this.clientOperationIndex;
   }

   @Nullable
   class="kw">public InteractionChain findForkedChain(@Nonnull ForkedChainId var1, @Nullable InteractionChainData var2) {
      long var3 = forkedIdToIndex(var1);
      long var5 = this.forkedChainsMap.get(var3);
      if (var5 != NULL_FORK_ID) {
         var3 = var5;
      }

      InteractionChain var7 = (InteractionChain)this.forkedChains.get(var3);
      if (var7 == null && var1.subIndex < 0 && var2 != null) {
         InteractionEntry var8 = this.getInteraction(var1.entryIndex);
         if (var8 == null) {
            class="kw">return null;
         }

         int var9 = var8.getServerState().rootInteraction;
         int var10 = var8.getServerState().operationCounter;
         RootInteraction var11 = RootInteraction.getAssetMap().getAsset(var9);
         if (var11.getOperation(var10).getInnerOperation() class="kw">instanceof Interaction var13) {
            this.context.initEntry(this, var8, null);
            var7 = var13.mapForkChain(this.context, var2);
            this.context.deinitEntry(this, var8, null);
            if (var7 != null) {
               this.forkedChainsMap.put(var3, forkedIdToIndex(var7.getBaseForkedChainId()));
            }

            class="kw">return var7;
         } else {
            class="kw">return null;
         }
      } else {
         class="kw">return var7;
      }
   }

   class="kw">public InteractionChain getForkedChain(@Nonnull ForkedChainId var1) {
      long var2 = forkedIdToIndex(var1);
      if (var1.subIndex < 0) {
         long var4 = this.forkedChainsMap.get(var2);
         if (var4 != NULL_FORK_ID) {
            var2 = var4;
         }
      }

      class="kw">return (InteractionChain)this.forkedChains.get(var2);
   }

   class="kw">public void putForkedChain(@Nonnull ForkedChainId var1, @Nonnull InteractionChain var2) {
      this.newForks.add(var2);
      this.forkedChains.put(forkedIdToIndex(var1), var2);
   }

   @Nullable
   class="kw">public InteractionChain.TempChain getTempForkedChain(@Nonnull ForkedChainId var1) {
      InteractionEntry var2 = this.getInteraction(var1.entryIndex);
      if (var2 != null) {
         if (var1.subIndex < var2.getNextForkId()) {
            class="kw">return null;
         }
      } else if (var1.entryIndex < this.operationIndexOffset) {
         class="kw">return null;
      }

      class="kw">return (InteractionChain.TempChain)this.tempForkedChainData.computeIfAbsent(forkedIdToIndex(var1), var0 -> new InteractionChain.TempChain());
   }

   @Nullable
   InteractionChain.TempChain removeTempForkedChain(@Nonnull ForkedChainId var1, InteractionChain var2) {
      long var3 = forkedIdToIndex(var1);
      long var5 = this.forkedChainsMap.get(var3);
      if (var5 != NULL_FORK_ID) {
         var3 = var5;
      }

      InteractionChain.TempChain var7 = (InteractionChain.TempChain)this.tempForkedChainData.remove(var3);
      if (var7 != null) {
         class="kw">return var7;
      }

      InteractionEntry var8 = this.context.getEntry();
      RootInteraction var9 = RootInteraction.getAssetMap().getAsset(var8.getState().rootInteraction);
      if (var9.getOperation(var8.getState().operationCounter).getInnerOperation() class="kw">instanceof Interaction var11) {
         ObjectIterator var12 = Long2ObjectMaps.fastIterator(this.getTempForkedChainData());

         while (var12.hasNext()) {
            Entry var13 = (Entry<InteractionChain.TempChain>)var12.next();
            InteractionChain.TempChain var14 = (InteractionChain.TempChain)var13.getValue();
            if (var14.baseForkedChainId != null) {
               int var15 = var14.baseForkedChainId.entryIndex;
               if (var15 == var8.getIndex()) {
                  InteractionChain var16 = var11.mapForkChain(this.getContext(), var14.chainData);
                  if (var16 != null) {
                     this.forkedChainsMap.put(forkedIdToIndex(var14.baseForkedChainId), forkedIdToIndex(var16.getBaseForkedChainId()));
                  }

                  if (var16 == var2) {
                     var12.remove();
                     class="kw">return var14;
                  }
               }
            }
         }
      }

      class="kw">return null;
   }

   class="kw">public boolean hasSentInitial() {
      class="kw">return this.sentInitial;
   }

   class="kw">public void setSentInitial(boolean var1) {
      this.sentInitial = var1;
   }

   class="kw">public float getTimeShift() {
      class="kw">return this.timeShift;
   }

   class="kw">public void setTimeShift(float var1) {
      this.timeShift = var1;
   }

   class="kw">public boolean consumeFirstRun() {
      this.isFirstRun = this.firstRun;
      this.firstRun = false;
      class="kw">return this.isFirstRun;
   }

   class="kw">public boolean isFirstRun() {
      class="kw">return this.isFirstRun;
   }

   class="kw">public void setFirstRun(boolean var1) {
      this.isFirstRun = var1;
   }

   class="kw">public int getCallDepth() {
      class="kw">return this.callStack.size();
   }

   class="kw">public int getSimulatedCallDepth() {
      class="kw">return this.simulatedCallStack;
   }

   class="kw">public void pushRoot(RootInteraction var1, boolean var2) {
      if (var2) {
         this.simulatedRootInteraction = var1;
         this.simulatedOperationCounter = 0;
         this.simulatedCallStack++;
      } else {
         this.callStack.add(new InteractionChain.CallState(this.rootInteraction, this.operationCounter));
         this.operationCounter = 0;
         this.rootInteraction = var1;
      }
   }

   class="kw">public void popRoot() {
      InteractionChain.CallState var1 = this.callStack.removeLast();
      this.rootInteraction = var1.rootInteraction;
      this.operationCounter = var1.operationCounter + 1;
      this.simulatedRootInteraction = this.rootInteraction;
      this.simulatedOperationCounter = this.operationCounter;
      this.simulatedCallStack--;
   }

   class="kw">public float getTimeInSeconds() {
      if (this.timestamp == 0L) {
         class="kw">return 0.0F;
      }

      long var1 = System.nanoTime() - this.timestamp;
      class="kw">return (float)var1 / 1.0E9F;
   }

   class="kw">public void setOnCompletion(Runnable var1) {
      this.onCompletion = var1;
   }

   void onCompletion(CooldownHandler var1, boolean var2) {
      if (!this.completed) {
         this.completed = true;
         if (this.onCompletion != null) {
            this.onCompletion.run();
            this.onCompletion = null;
         }

         if (var2) {
            InteractionCooldown var3 = this.initialRootInteraction.getCooldown();
            String var4 = this.initialRootInteraction.getId();
            if (var3 != null && var3.cooldownId != null) {
               var4 = var3.cooldownId;
            }

            CooldownHandler.Cooldown var5 = var1.getCooldown(var4);
            if (var5 != null) {
               var5.tick(0.016666668F);
            }
         }
      }
   }

   void updateServerState() {
      if (this.serverState == InteractionState.NotFinished) {
         if (this.operationCounter >= this.rootInteraction.getOperationMax()) {
            this.serverState = this.finalState;
         } else {
            InteractionEntry var1 = this.getOrCreateInteractionEntry(this.operationIndex);

            this.serverState = class="kw">switch (var1.getServerState().state) {
               case NotFinished, Finished -> InteractionState.NotFinished;
               class="kw">default -> InteractionState.Failed;
            };
         }
      }
   }

   void updateSimulatedState() {
      if (this.clientState == InteractionState.NotFinished) {
         if (this.simulatedOperationCounter >= this.rootInteraction.getOperationMax()) {
            this.clientState = this.finalState;
         } else {
            InteractionEntry var1 = this.getOrCreateInteractionEntry(this.clientOperationIndex);

            this.clientState = class="kw">switch (var1.getSimulationState().state) {
               case NotFinished, Finished -> InteractionState.NotFinished;
               class="kw">default -> InteractionState.Failed;
            };
         }
      }
   }

   @Override
   class="kw">public InteractionState getClientState() {
      class="kw">return this.clientState;
   }

   @Override
   class="kw">public void setClientState(InteractionState var1) {
      this.clientState = var1;
   }

   @Nonnull
   class="kw">public InteractionEntry getOrCreateInteractionEntry(int var1) {
      int var2 = var1 - this.operationIndexOffset;
      if (var2 < 0) {
         throw new IllegalArgumentException("Trying to access removed interaction entry");
      }

      InteractionEntry var3 = var2 < this.interactions.size() ? this.interactions.get(var2) : null;
      if (var3 == null) {
         if (var2 != this.interactions.size()) {
            throw new IllegalArgumentException("Trying to add interaction entry at a weird location: " + var2 + " " + this.interactions.size());
         }

         var3 = new InteractionEntry(var1, this.operationCounter, RootInteraction.getRootInteractionIdOrUnknown(this.rootInteraction.getId()));
         this.interactions.add(var3);
      }

      class="kw">return var3;
   }

   @Nullable
   @Override
   class="kw">public InteractionEntry getInteraction(int var1) {
      var1 -= this.operationIndexOffset;
      class="kw">return var1 >= 0 && var1 < this.interactions.size() ? this.interactions.get(var1) : null;
   }

   class="kw">public void removeInteractionEntry(@Nonnull InteractionManager var1, int var2) {
      int var3 = var2 - this.operationIndexOffset;
      if (var3 != 0) {
         this.flagDesync();
      } else {
         InteractionEntry var4 = this.interactions.remove(var3);
         this.operationIndexOffset++;
         this.tempForkedChainData.values().removeIf(var3x -> {
            if (var3x.baseForkedChainId.entryIndex != var4.getIndex()) {
               class="kw">return false;
            }

            var1.sendCancelPacket(this.getChainId(), var3x.forkedChainId);
            class="kw">return true;
         });
      }
   }

   @Override
   class="kw">public void putInteractionSyncData(int var1, InteractionSyncData var2) {
      var1 -= this.tempSyncDataOffset;
      if (var1 >= 0) {
         if (var1 < this.tempSyncData.size()) {
            this.tempSyncData.set(var1, var2);
         } else if (var1 == this.tempSyncData.size()) {
            this.tempSyncData.add(var2);
         } else {
            LOGGER.at(Level.WARNING).log("Temp sync data sent out of order: %d %d", var1, this.tempSyncData.size());
         }
      }
   }

   @Override
   class="kw">public void clearInteractionSyncData(int var1) {
      int var2 = var1 - this.tempSyncDataOffset;
      if (!this.tempSyncData.isEmpty()) {
         for (int var3 = this.tempSyncData.size() - 1; var3 >= var2 && var3 >= 0; var3--) {
            this.tempSyncData.remove(var3);
         }
      }

      int var5 = var1 - this.operationIndexOffset;

      for (int var4 = Math.max(var5, 0); var4 < this.interactions.size(); var4++) {
         this.interactions.get(var4).setClientState(null);
      }
   }

   @Nullable
   class="kw">public InteractionSyncData removeInteractionSyncData(int var1) {
      var1 -= this.tempSyncDataOffset;
      if (var1 != 0) {
         class="kw">return null;
      }

      if (this.tempSyncData.isEmpty()) {
         class="kw">return null;
      }

      if (this.tempSyncData.get(var1) == null) {
         class="kw">return null;
      }

      this.tempSyncDataOffset++;
      class="kw">return this.tempSyncData.remove(var1);
   }

   @Override
   class="kw">public void updateSyncPosition(int var1) {
      if (this.tempSyncDataOffset == var1) {
         this.tempSyncDataOffset = var1 + 1;
      } else if (var1 > this.tempSyncDataOffset) {
         throw new IllegalArgumentException("Temp sync data sent out of order: " + var1 + " " + this.tempSyncData.size());
      }
   }

   @Override
   class="kw">public boolean isSyncDataOutOfOrder(int var1) {
      class="kw">return var1 > this.tempSyncDataOffset + this.tempSyncData.size();
   }

   @Override
   class="kw">public void syncFork(@Nonnull Ref<EntityStore> var1, @Nonnull InteractionManager var2, @Nonnull SyncInteractionChain var3) {
      ForkedChainId var4 = var3.forkedId;

      while (var4.forkedId != null) {
         var4 = var4.forkedId;
      }

      InteractionChain var5 = this.findForkedChain(var4, var3.data);
      if (var5 != null) {
         var2.sync(var1, var5, var3);
      } else {
         InteractionChain.TempChain var6 = this.getTempForkedChain(var4);
         if (var6 == null) {
            class="kw">return;
         }

         var6.setForkedChainId(var3.forkedId);
         var6.setBaseForkedChainId(var4);
         var6.setChainData(var3.data);
         var2.sync(var1, var6, var3);
      }
   }

   class="kw">public void copyTempFrom(@Nonnull InteractionChain.TempChain var1) {
      this.setClientState(var1.clientState);
      this.tempSyncData.addAll(var1.tempSyncData);
      this.getTempForkedChainData().putAll(var1.tempForkedChainData);
   }

   class="kw">private class="kw">static long forkedIdToIndex(@Nonnull ForkedChainId var0) {
      class="kw">return (long)var0.entryIndex << 32 | var0.subIndex & 4294967295L;
   }

   class="kw">public void setChainId(int var1) {
      this.chainId = var1;
   }

   class="kw">public InteractionType getBaseType() {
      class="kw">return this.baseType;
   }

   class="kw">public void setBaseType(InteractionType var1) {
      this.baseType = var1;
   }

   @Nonnull
   class="kw">public Long2ObjectMap<InteractionChain> getForkedChains() {
      class="kw">return this.forkedChains;
   }

   @Nonnull
   class="kw">public Long2ObjectMap<InteractionChain.TempChain> getTempForkedChainData() {
      class="kw">return this.tempForkedChainData;
   }

   class="kw">public long getTimestamp() {
      class="kw">return this.timestamp;
   }

   class="kw">public void setTimestamp(long var1) {
      this.timestamp = var1;
   }

   class="kw">public long getWaitingForServerFinished() {
      class="kw">return this.waitingForServerFinished;
   }

   class="kw">public void setWaitingForServerFinished(long var1) {
      this.waitingForServerFinished = var1;
   }

   class="kw">public long getWaitingForClientFinished() {
      class="kw">return this.waitingForClientFinished;
   }

   class="kw">public void setWaitingForClientFinished(long var1) {
      this.waitingForClientFinished = var1;
   }

   class="kw">public void setServerState(InteractionState var1) {
      this.serverState = var1;
   }

   class="kw">public InteractionState getFinalState() {
      class="kw">return this.finalState;
   }

   class="kw">public void setFinalState(InteractionState var1) {
      this.finalState = var1;
   }

   void setPredicted(boolean var1) {
      this.predicted = var1;
   }

   class="kw">public void flagDesync() {
      this.desynced = true;
      this.forkedChains.forEach((var0, var1) -> var1.flagDesync());
   }

   class="kw">public boolean isDesynced() {
      class="kw">return this.desynced;
   }

   @Nonnull
   class="kw">public List<InteractionChain> getNewForks() {
      class="kw">return this.newForks;
   }

   @Nonnull
   @Override
   class="kw">public String toString() {
      class="kw">return "InteractionChain{type="
         + this.type
         + ", chainData="
         + this.chainData
         + ", chainId="
         + this.chainId
         + ", forkedChainId="
         + this.forkedChainId
         + ", predicted="
         + this.predicted
         + ", context="
         + this.context
         + ", forkedChains="
         + this.forkedChains
         + ", tempForkedChainData="
         + this.tempForkedChainData
         + ", initialRootInteraction="
         + this.initialRootInteraction
         + ", rootInteraction="
         + this.rootInteraction
         + ", operationCounter="
         + this.operationCounter
         + ", callStack="
         + this.callStack
         + ", simulatedCallStack="
         + this.simulatedCallStack
         + ", requiresClient="
         + this.requiresClient
         + ", simulatedOperationCounter="
         + this.simulatedOperationCounter
         + ", simulatedRootInteraction="
         + this.simulatedRootInteraction
         + ", operationIndex="
         + this.operationIndex
         + ", operationIndexOffset="
         + this.operationIndexOffset
         + ", clientOperationIndex="
         + this.clientOperationIndex
         + ", interactions="
         + this.interactions
         + ", tempSyncData="
         + this.tempSyncData
         + ", tempSyncDataOffset="
         + this.tempSyncDataOffset
         + ", timestamp="
         + this.timestamp
         + ", waitingForServerFinished="
         + this.waitingForServerFinished
         + ", waitingForClientFinished="
         + this.waitingForClientFinished
         + ", clientState="
         + this.clientState
         + ", serverState="
         + this.serverState
         + ", onCompletion="
         + this.onCompletion
         + ", sentInitial="
         + this.sentInitial
         + ", desynced="
         + this.desynced
         + ", timeShift="
         + this.timeShift
         + ", firstRun="
         + this.firstRun
         + ", skipChainOnClick="
         + this.skipChainOnClick
         + "}";
   }

   class="kw">private record CallState(RootInteraction rootInteraction, int operationCounter) {
      class="kw">private CallState {
      }
   }

   class="kw">static class TempChain class="kw">implements ChainSyncStorage {
      class="kw">final Long2ObjectMap<InteractionChain.TempChain> tempForkedChainData = new Long2ObjectOpenHashMap();
      class="kw">final List<InteractionSyncData> tempSyncData = new ObjectArrayList();
      ForkedChainId forkedChainId;
      InteractionState clientState = InteractionState.NotFinished;
      ForkedChainId baseForkedChainId;
      InteractionChainData chainData;

      TempChain() {
      }

      @Nonnull
      class="kw">public InteractionChain.TempChain getOrCreateTempForkedChain(@Nonnull ForkedChainId var1) {
         class="kw">return (InteractionChain.TempChain)this.tempForkedChainData
            .computeIfAbsent(InteractionChain.forkedIdToIndex(var1), var0 -> new InteractionChain.TempChain());
      }

      @Override
      class="kw">public InteractionState getClientState() {
         class="kw">return this.clientState;
      }

      @Override
      class="kw">public void setClientState(InteractionState var1) {
         this.clientState = var1;
      }

      @Nullable
      @Override
      class="kw">public InteractionEntry getInteraction(int var1) {
         class="kw">return null;
      }

      @Override
      class="kw">public void putInteractionSyncData(int var1, InteractionSyncData var2) {
         if (var1 < this.tempSyncData.size()) {
            this.tempSyncData.set(var1, var2);
         } else {
            if (var1 != this.tempSyncData.size()) {
               throw new IllegalArgumentException("Temp sync data sent out of order: " + var1 + " " + this.tempSyncData.size());
            }

            this.tempSyncData.add(var2);
         }
      }

      @Override
      class="kw">public void updateSyncPosition(int var1) {
      }

      @Override
      class="kw">public boolean isSyncDataOutOfOrder(int var1) {
         class="kw">return var1 > this.tempSyncData.size();
      }

      @Override
      class="kw">public void syncFork(@Nonnull Ref<EntityStore> var1, @Nonnull InteractionManager var2, @Nonnull SyncInteractionChain var3) {
         ForkedChainId var4 = var3.forkedId;

         while (var4.forkedId != null) {
            var4 = var4.forkedId;
         }

         InteractionChain.TempChain var5 = this.getOrCreateTempForkedChain(var4);
         var5.setForkedChainId(var3.forkedId);
         var5.setBaseForkedChainId(var4);
         var5.setChainData(var3.data);
         var2.sync(var1, var5, var3);
      }

      @Override
      class="kw">public void clearInteractionSyncData(int var1) {
         for (int var2 = this.tempSyncData.size() - 1; var2 >= var1; var2--) {
            this.tempSyncData.remove(var2);
         }
      }

      class="kw">public InteractionChainData getChainData() {
         class="kw">return this.chainData;
      }

      class="kw">public void setChainData(InteractionChainData var1) {
         this.chainData = var1;
      }

      class="kw">public ForkedChainId getBaseForkedChainId() {
         class="kw">return this.baseForkedChainId;
      }

      class="kw">public void setBaseForkedChainId(ForkedChainId var1) {
         this.baseForkedChainId = var1;
      }

      class="kw">public void setForkedChainId(ForkedChainId var1) {
         this.forkedChainId = var1;
      }

      @Nonnull
      @Override
      class="kw">public String toString() {
         class="kw">return "TempChain{tempForkedChainData=" + this.tempForkedChainData + ", tempSyncData=" + this.tempSyncData + ", clientState=" + this.clientState + "}";
      }
   }
}