diff --git a/src/main/java/li/cil/oc2/api/bus/device/ItemDevice.java b/src/main/java/li/cil/oc2/api/bus/device/ItemDevice.java
new file mode 100644
index 00000000..a1f954e3
--- /dev/null
+++ b/src/main/java/li/cil/oc2/api/bus/device/ItemDevice.java
@@ -0,0 +1,9 @@
+package li.cil.oc2.api.bus.device;
+
+import net.minecraft.nbt.CompoundNBT;
+
+public interface ItemDevice extends Device {
+ void exportToItemStack(CompoundNBT nbt);
+
+ void importFromItemStack(CompoundNBT nbt);
+}
diff --git a/src/main/java/li/cil/oc2/api/bus/device/provider/BlockDeviceProvider.java b/src/main/java/li/cil/oc2/api/bus/device/provider/BlockDeviceProvider.java
new file mode 100644
index 00000000..6a80e7c3
--- /dev/null
+++ b/src/main/java/li/cil/oc2/api/bus/device/provider/BlockDeviceProvider.java
@@ -0,0 +1,51 @@
+package li.cil.oc2.api.bus.device.provider;
+
+import li.cil.oc2.api.bus.device.Device;
+import net.minecraftforge.common.util.LazyOptional;
+import net.minecraftforge.registries.IForgeRegistryEntry;
+
+/**
+ * This is used to query for devices given a block face.
+ *
+ * Implementations may return various device types depending on the query.
+ *
+ * For identical queries and world state, implementations should return the same device.
+ * Failing that, implementations should return instances that are equal to each other
+ * when compared using {@link Object#equals(Object)} and have equal {@link Object#hashCode()}s.
+ *
+ * This allows avoiding unnecessary re-initialization of devices that have not changed since a
+ * previous scan.
+ *
+ * This is also required to avoid device duplication when a device is connected to a
+ * {@link li.cil.oc2.api.bus.DeviceBus} more than once. An example where this can occur are
+ * blocks that expose the same device on all sides having connected cabling adjacent to more
+ * than one face.
+ *
+ * Providers can be registered via the provider registries, much like blocks and items
+ * are registered. For example:
+ *
+ * class YourModInitialization {
+ * static DeferredRegister<BlockDeviceProvider> BLOCK_DEVICE_PROVIDERS = DeferredRegister.create(BlockDeviceProvider.class, "your_mod_id");
+ *
+ * static void initialize() {
+ * BLOCK_DEVICE_PROVIDERS.register("your_block_device_name", YourBlockDeviceProvider::new);
+ *
+ * BLOCK_DEVICE_PROVIDERS.register(FMLJavaModLoadingContext.get().getModEventBus());
+ * }
+ * }
+ *
+ *
+ * @see li.cil.oc2.api.bus.device.rpc.RPCDevice
+ * @see li.cil.oc2.api.bus.device.object.ObjectDevice
+ * @see li.cil.oc2.api.bus.device.vm.VMDevice
+ * @see BlockDeviceQuery
+ */
+public interface BlockDeviceProvider extends IForgeRegistryEntry {
+ /**
+ * Get a device for the specified query.
+ *
+ * @param query the query describing the object to get a {@link Device} for.
+ * @return a device for the specified query, if available.
+ */
+ LazyOptional getDevice(BlockDeviceQuery query);
+}
diff --git a/src/main/java/li/cil/oc2/api/bus/device/provider/BlockDeviceQuery.java b/src/main/java/li/cil/oc2/api/bus/device/provider/BlockDeviceQuery.java
index ac07c509..827f4acf 100644
--- a/src/main/java/li/cil/oc2/api/bus/device/provider/BlockDeviceQuery.java
+++ b/src/main/java/li/cil/oc2/api/bus/device/provider/BlockDeviceQuery.java
@@ -8,8 +8,10 @@ import javax.annotation.Nullable;
/**
* Device query for a block in the world.
+ *
+ * @see BlockDeviceProvider
*/
-public interface BlockDeviceQuery extends DeviceQuery {
+public interface BlockDeviceQuery {
/**
* The world containing the block this query is performed for.
*
diff --git a/src/main/java/li/cil/oc2/api/bus/device/provider/DeviceProvider.java b/src/main/java/li/cil/oc2/api/bus/device/provider/DeviceProvider.java
deleted file mode 100644
index 3e1fcd29..00000000
--- a/src/main/java/li/cil/oc2/api/bus/device/provider/DeviceProvider.java
+++ /dev/null
@@ -1,55 +0,0 @@
-package li.cil.oc2.api.bus.device.provider;
-
-import li.cil.oc2.api.bus.device.Device;
-import li.cil.oc2.api.bus.device.object.ObjectDevice;
-import li.cil.oc2.api.bus.device.rpc.RPCDevice;
-import net.minecraftforge.common.util.LazyOptional;
-import net.minecraftforge.registries.IForgeRegistryEntry;
-
-/**
- * Allows querying for devices given some context.
- *
- * See the specializations of {@link DeviceQuery} for possible queries.
- *
- * - Implementations may handle multiple query types and return various device
- * types depending on the query.
- * -
- * Implementations should return the same device for the same query.
- *
- * Failing that, implementations should return instances that are equal to each
- * other when compared using {@link Object#equals(Object)} and have equal {@link Object#hashCode()}s.
- *
- * This is required to avoid device duplication when a device is connected to a bus more
- * than once (e.g. for blocks when connected cables are adjacent to multiple faces of the
- * block).
- *
- *
- *
- * Providers can be registered via the device provider registry, much like blocks and items
- * are registered. For example:
- *
- * class YourModInitialization {
- * static DeferredRegister<DeviceProvider> PROVIDERS = DeferredRegister.create(DeviceProvider.class, "your_mod_id");
- *
- * static void initialize() {
- * PROVIDERS.register("your_device_name", YourDeviceProvider::new);
- *
- * PROVIDERS.register(FMLJavaModLoadingContext.get().getModEventBus());
- * }
- * }
- *
- *
- * @see RPCDevice
- * @see ObjectDevice
- * @see DeviceQuery
- * @see BlockDeviceQuery
- */
-public interface DeviceProvider extends IForgeRegistryEntry {
- /**
- * Get a device for the specified query.
- *
- * @param query the query describing the object to get a {@link Device} for.
- * @return a device for the specified query, if available.
- */
- LazyOptional getDevice(DeviceQuery query);
-}
diff --git a/src/main/java/li/cil/oc2/api/bus/device/provider/DeviceQuery.java b/src/main/java/li/cil/oc2/api/bus/device/provider/DeviceQuery.java
deleted file mode 100644
index 4de1148e..00000000
--- a/src/main/java/li/cil/oc2/api/bus/device/provider/DeviceQuery.java
+++ /dev/null
@@ -1,10 +0,0 @@
-package li.cil.oc2.api.bus.device.provider;
-
-/**
- * Base interface for all queries to {@link DeviceProvider}s.
- *
- * @see DeviceProvider
- * @see BlockDeviceQuery
- */
-public interface DeviceQuery {
-}
diff --git a/src/main/java/li/cil/oc2/api/bus/device/provider/ItemDeviceProvider.java b/src/main/java/li/cil/oc2/api/bus/device/provider/ItemDeviceProvider.java
new file mode 100644
index 00000000..9a30a4a1
--- /dev/null
+++ b/src/main/java/li/cil/oc2/api/bus/device/provider/ItemDeviceProvider.java
@@ -0,0 +1,48 @@
+package li.cil.oc2.api.bus.device.provider;
+
+import li.cil.oc2.api.bus.device.Device;
+import li.cil.oc2.api.bus.device.ItemDevice;
+import net.minecraftforge.registries.IForgeRegistryEntry;
+
+import java.util.Optional;
+
+/**
+ * This is used to query for devices given an item stack.
+ *
+ * Implementations may return various device types depending on the query.
+ *
+ * For identical queries, implementations should return the same device. Failing that,
+ * implementations should return instances that are equal to each other when compared
+ * using {@link Object#equals(Object)} and have equal {@link Object#hashCode()}s.
+ *
+ * This allows avoiding unnecessary re-initialization of devices that have not changed since a
+ * previous scan.
+ *
+ * Providers can be registered via the provider registries, much like blocks and items
+ * are registered. For example:
+ *
+ * class YourModInitialization {
+ * static DeferredRegister<ItemDeviceProvider> ITEM_DEVICE_PROVIDERS = DeferredRegister.create(ItemDeviceProvider.class, "your_mod_id");
+ *
+ * static void initialize() {
+ * ITEM_DEVICE_PROVIDERS.register("your_item_device_name", YourItemDeviceProvider::new);
+ *
+ * ITEM_DEVICE_PROVIDERS.register(FMLJavaModLoadingContext.get().getModEventBus());
+ * }
+ * }
+ *
+ *
+ * @see li.cil.oc2.api.bus.device.rpc.RPCDevice
+ * @see li.cil.oc2.api.bus.device.object.ObjectDevice
+ * @see li.cil.oc2.api.bus.device.vm.VMDevice
+ * @see ItemDeviceQuery
+ */
+public interface ItemDeviceProvider extends IForgeRegistryEntry {
+ /**
+ * Get a device for the specified query.
+ *
+ * @param query the query describing the object to get a {@link Device} for.
+ * @return a device for the specified query, if available.
+ */
+ Optional getDevice(ItemDeviceQuery query);
+}
diff --git a/src/main/java/li/cil/oc2/api/bus/device/provider/ItemDeviceQuery.java b/src/main/java/li/cil/oc2/api/bus/device/provider/ItemDeviceQuery.java
index 7d083e7c..c29f873d 100644
--- a/src/main/java/li/cil/oc2/api/bus/device/provider/ItemDeviceQuery.java
+++ b/src/main/java/li/cil/oc2/api/bus/device/provider/ItemDeviceQuery.java
@@ -2,6 +2,16 @@ package li.cil.oc2.api.bus.device.provider;
import net.minecraft.item.ItemStack;
-public interface ItemDeviceQuery extends DeviceQuery {
+/**
+ * Device query for an item stack.
+ *
+ * @see ItemDeviceProvider
+ */
+public interface ItemDeviceQuery {
+ /**
+ * The item stack this query is performed for.
+ *
+ * @return the item stack to get a device for.
+ */
ItemStack getItemStack();
}
diff --git a/src/main/java/li/cil/oc2/api/bus/device/rpc/RPCDevice.java b/src/main/java/li/cil/oc2/api/bus/device/rpc/RPCDevice.java
index 81392d61..2cfbbfb3 100644
--- a/src/main/java/li/cil/oc2/api/bus/device/rpc/RPCDevice.java
+++ b/src/main/java/li/cil/oc2/api/bus/device/rpc/RPCDevice.java
@@ -2,7 +2,6 @@ package li.cil.oc2.api.bus.device.rpc;
import li.cil.oc2.api.bus.device.Device;
import li.cil.oc2.api.bus.device.object.ObjectDevice;
-import li.cil.oc2.api.bus.device.provider.DeviceProvider;
import java.util.List;
@@ -20,7 +19,8 @@ import java.util.List;
* the {@link ObjectDevice} class.
*
* @see ObjectDevice
- * @see DeviceProvider
+ * @see li.cil.oc2.api.bus.device.provider.BlockDeviceProvider
+ * @see li.cil.oc2.api.bus.device.provider.ItemDeviceProvider
*/
public interface RPCDevice extends Device {
/**
diff --git a/src/main/java/li/cil/oc2/api/bus/device/vm/VMDevice.java b/src/main/java/li/cil/oc2/api/bus/device/vm/VMDevice.java
index e054b516..41f5c1bf 100644
--- a/src/main/java/li/cil/oc2/api/bus/device/vm/VMDevice.java
+++ b/src/main/java/li/cil/oc2/api/bus/device/vm/VMDevice.java
@@ -17,6 +17,8 @@ import li.cil.sedna.api.device.MemoryMappedDevice;
* for releasing unmanaged resources acquired in {@link #load(VMContext)}.
*
* @see VMDeviceLifecycleListener
+ * @see li.cil.oc2.api.bus.device.provider.BlockDeviceProvider
+ * @see li.cil.oc2.api.bus.device.provider.ItemDeviceProvider
*/
public interface VMDevice extends Device {
/**
diff --git a/src/main/java/li/cil/oc2/common/block/entity/AbstractTileEntity.java b/src/main/java/li/cil/oc2/common/block/entity/AbstractTileEntity.java
index 84118705..8ff44bbf 100644
--- a/src/main/java/li/cil/oc2/common/block/entity/AbstractTileEntity.java
+++ b/src/main/java/li/cil/oc2/common/block/entity/AbstractTileEntity.java
@@ -20,6 +20,8 @@ public abstract class AbstractTileEntity extends TileEntity {
super(tileEntityType);
}
+ ///////////////////////////////////////////////////////////////////
+
@NotNull
@Override
public LazyOptional getCapability(@NotNull final Capability capability, @Nullable final Direction side) {
diff --git a/src/main/java/li/cil/oc2/common/block/entity/BusCableTileEntity.java b/src/main/java/li/cil/oc2/common/block/entity/BusCableTileEntity.java
index c771b306..64dc15bc 100644
--- a/src/main/java/li/cil/oc2/common/block/entity/BusCableTileEntity.java
+++ b/src/main/java/li/cil/oc2/common/block/entity/BusCableTileEntity.java
@@ -27,6 +27,8 @@ public class BusCableTileEntity extends AbstractTileEntity {
setCapabilityIfAbsent(Capabilities.DEVICE_BUS_ELEMENT_CAPABILITY, busElement);
}
+ ///////////////////////////////////////////////////////////////////
+
public void handleNeighborChanged(final BlockPos pos) {
busElement.handleNeighborChanged(pos);
}
diff --git a/src/main/java/li/cil/oc2/common/block/entity/ComputerTileEntity.java b/src/main/java/li/cil/oc2/common/block/entity/ComputerTileEntity.java
index 18e15680..e7d01e50 100644
--- a/src/main/java/li/cil/oc2/common/block/entity/ComputerTileEntity.java
+++ b/src/main/java/li/cil/oc2/common/block/entity/ComputerTileEntity.java
@@ -3,7 +3,6 @@ package li.cil.oc2.common.block.entity;
import it.unimi.dsi.fastutil.bytes.ByteArrayFIFOQueue;
import li.cil.ceres.api.Serialized;
import li.cil.oc2.Constants;
-import li.cil.oc2.api.API;
import li.cil.oc2.api.bus.DeviceBusElement;
import li.cil.oc2.api.bus.device.Device;
import li.cil.oc2.api.bus.device.vm.VMContext;
@@ -20,10 +19,7 @@ import li.cil.oc2.common.network.message.ComputerBusStateMessage;
import li.cil.oc2.common.network.message.ComputerRunStateMessage;
import li.cil.oc2.common.network.message.TerminalBlockOutputMessage;
import li.cil.oc2.common.serialization.NBTSerialization;
-import li.cil.oc2.common.util.HorizontalBlockUtils;
-import li.cil.oc2.common.util.NBTTagIds;
-import li.cil.oc2.common.util.NBTUtils;
-import li.cil.oc2.common.util.ServerScheduler;
+import li.cil.oc2.common.util.*;
import li.cil.oc2.common.vm.Terminal;
import li.cil.oc2.common.vm.VirtualMachine;
import li.cil.oc2.common.vm.VirtualMachineRunner;
@@ -128,9 +124,7 @@ public final class ComputerTileEntity extends AbstractTileEntity implements ITic
itemHandler.setStackInSlot(2, new ItemStack(Items.RAM_8M_ITEM.get()));
final ItemStack hdd = new ItemStack(Items.HDD_ITEM.get());
- final CompoundNBT hddInfo = new CompoundNBT();
- hddInfo.putString(Constants.HDD_BASE_NBT_TAG_NAME, "linux");
- hdd.setTagInfo(API.MOD_ID, hddInfo);
+ ItemStackUtils.getOrCreateModDataTag(hdd).putString(Constants.HDD_BASE_NBT_TAG_NAME, "linux");
itemHandler.setStackInSlot(4, hdd);
}
diff --git a/src/main/java/li/cil/oc2/common/block/entity/RedstoneInterfaceTileEntity.java b/src/main/java/li/cil/oc2/common/block/entity/RedstoneInterfaceTileEntity.java
index 5fdec17d..378cf641 100644
--- a/src/main/java/li/cil/oc2/common/block/entity/RedstoneInterfaceTileEntity.java
+++ b/src/main/java/li/cil/oc2/common/block/entity/RedstoneInterfaceTileEntity.java
@@ -39,6 +39,8 @@ public class RedstoneInterfaceTileEntity extends TileEntity implements NamedDevi
super(TileEntities.REDSTONE_INTERFACE_TILE_ENTITY.get());
}
+ ///////////////////////////////////////////////////////////////////
+
@Override
public CompoundNBT write(CompoundNBT compound) {
compound = super.write(compound);
diff --git a/src/main/java/li/cil/oc2/common/bus/AbstractDeviceBusController.java b/src/main/java/li/cil/oc2/common/bus/AbstractDeviceBusController.java
index 04188fff..b5078c17 100644
--- a/src/main/java/li/cil/oc2/common/bus/AbstractDeviceBusController.java
+++ b/src/main/java/li/cil/oc2/common/bus/AbstractDeviceBusController.java
@@ -42,6 +42,8 @@ public abstract class AbstractDeviceBusController implements DeviceBusController
this.root = root;
}
+ ///////////////////////////////////////////////////////////////////
+
public void dispose() {
for (final DeviceBusElement element : elements) {
element.removeController(this);
diff --git a/src/main/java/li/cil/oc2/common/bus/AbstractGroupingBlockDeviceBusElement.java b/src/main/java/li/cil/oc2/common/bus/AbstractGroupingBlockDeviceBusElement.java
new file mode 100644
index 00000000..8a573ace
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/bus/AbstractGroupingBlockDeviceBusElement.java
@@ -0,0 +1,10 @@
+package li.cil.oc2.common.bus;
+
+import li.cil.oc2.api.bus.device.provider.BlockDeviceProvider;
+import li.cil.oc2.common.bus.device.BlockDeviceInfo;
+
+public abstract class AbstractGroupingBlockDeviceBusElement extends AbstractGroupingDeviceBusElement {
+ public AbstractGroupingBlockDeviceBusElement(final int groupCount) {
+ super(groupCount);
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/AbstractGroupingDeviceBusElement.java b/src/main/java/li/cil/oc2/common/bus/AbstractGroupingDeviceBusElement.java
index cdfab82c..85c684f4 100644
--- a/src/main/java/li/cil/oc2/common/bus/AbstractGroupingDeviceBusElement.java
+++ b/src/main/java/li/cil/oc2/common/bus/AbstractGroupingDeviceBusElement.java
@@ -1,55 +1,58 @@
package li.cil.oc2.common.bus;
import li.cil.oc2.api.bus.device.Device;
-import li.cil.oc2.common.bus.device.DeviceInfo;
+import li.cil.oc2.common.bus.device.AbstractDeviceInfo;
+import li.cil.oc2.common.util.ItemDeviceUtils;
import li.cil.oc2.common.util.NBTTagIds;
import net.minecraft.nbt.CompoundNBT;
import net.minecraft.nbt.ListNBT;
-import net.minecraft.util.ResourceLocation;
import net.minecraftforge.common.util.INBTSerializable;
+import net.minecraftforge.registries.IForgeRegistryEntry;
import java.util.*;
import java.util.stream.Collectors;
-public abstract class AbstractGroupingDeviceBusElement extends AbstractDeviceBusElement implements INBTSerializable {
- private static final String DEVICE_ID_NBT_TAG_NAME = "deviceId";
- private static final String DEVICE_DATA_NBT_TAG_NAME = "deviceData";
+public abstract class AbstractGroupingDeviceBusElement, TDeviceInfo extends AbstractDeviceInfo> extends AbstractDeviceBusElement implements INBTSerializable {
+ private static final String GROUP_ID_NBT_TAG_NAME = "groupId";
+ private static final String GROUP_DATA_NBT_TAG_NAME = "groupData";
///////////////////////////////////////////////////////////////////
protected final int groupCount;
- protected final ArrayList> devicesByGroup;
+ protected final ArrayList> groups;
///////////////////////////////////////////////////////////////////
- protected final UUID[] deviceIds;
- protected final CompoundNBT[] deviceData;
+ protected final UUID[] groupIds;
+ protected final CompoundNBT[] groupData;
///////////////////////////////////////////////////////////////////
protected AbstractGroupingDeviceBusElement(final int groupCount) {
this.groupCount = groupCount;
- this.devicesByGroup = new ArrayList<>(groupCount);
- this.deviceIds = new UUID[groupCount];
- this.deviceData = new CompoundNBT[groupCount];
+ this.groups = new ArrayList<>(groupCount);
+ this.groupIds = new UUID[groupCount];
+ this.groupData = new CompoundNBT[groupCount];
for (int i = 0; i < groupCount; i++) {
- devicesByGroup.add(new HashSet<>());
- deviceIds[i] = UUID.randomUUID();
- deviceData[i] = new CompoundNBT();
+ groups.add(new HashSet<>());
+ groupIds[i] = UUID.randomUUID();
+ groupData[i] = new CompoundNBT();
}
}
+ ///////////////////////////////////////////////////////////////////
+
@Override
public ListNBT serializeNBT() {
- serializeDevices();
-
final ListNBT nbt = new ListNBT();
for (int i = 0; i < groupCount; i++) {
+ serializeDevices(i);
+
final CompoundNBT sideNbt = new CompoundNBT();
- sideNbt.putUniqueId(DEVICE_ID_NBT_TAG_NAME, deviceIds[i]);
- sideNbt.put(DEVICE_DATA_NBT_TAG_NAME, deviceData[i]);
+ sideNbt.putUniqueId(GROUP_ID_NBT_TAG_NAME, groupIds[i]);
+ sideNbt.put(GROUP_DATA_NBT_TAG_NAME, groupData[i]);
nbt.add(sideNbt);
}
@@ -62,11 +65,11 @@ public abstract class AbstractGroupingDeviceBusElement extends AbstractDeviceBus
for (int i = 0; i < count; i++) {
final CompoundNBT sideNbt = nbt.getCompound(i);
- if (sideNbt.hasUniqueId(DEVICE_ID_NBT_TAG_NAME)) {
- deviceIds[i] = sideNbt.getUniqueId(DEVICE_ID_NBT_TAG_NAME);
+ if (sideNbt.hasUniqueId(GROUP_ID_NBT_TAG_NAME)) {
+ groupIds[i] = sideNbt.getUniqueId(GROUP_ID_NBT_TAG_NAME);
}
- if (sideNbt.contains(DEVICE_DATA_NBT_TAG_NAME, NBTTagIds.TAG_COMPOUND)) {
- deviceData[i] = sideNbt.getCompound(DEVICE_DATA_NBT_TAG_NAME);
+ if (sideNbt.contains(GROUP_DATA_NBT_TAG_NAME, NBTTagIds.TAG_COMPOUND)) {
+ groupData[i] = sideNbt.getCompound(GROUP_DATA_NBT_TAG_NAME);
}
}
}
@@ -74,10 +77,10 @@ public abstract class AbstractGroupingDeviceBusElement extends AbstractDeviceBus
@Override
public Optional getDeviceIdentifier(final Device device) {
for (int i = 0; i < groupCount; i++) {
- final HashSet group = devicesByGroup.get(i);
- for (final DeviceInfo deviceInfo : group) {
+ final HashSet group = groups.get(i);
+ for (final TDeviceInfo deviceInfo : group) {
if (Objects.equals(device, deviceInfo.device)) {
- return Optional.of(deviceIds[i]);
+ return Optional.of(groupIds[i]);
}
}
}
@@ -86,29 +89,29 @@ public abstract class AbstractGroupingDeviceBusElement extends AbstractDeviceBus
///////////////////////////////////////////////////////////////////
- protected void setDevicesForGroup(final int index, final HashSet newDevices) {
- final HashSet oldDevices = devicesByGroup.get(index);
+ protected final void setDevicesForGroup(final int index, final Set newDevices) {
+ final HashSet oldDevices = groups.get(index);
if (Objects.equals(newDevices, oldDevices)) {
return;
}
- final HashSet removedDevices = new HashSet<>(oldDevices);
+ final HashSet removedDevices = new HashSet<>(oldDevices);
removedDevices.removeAll(newDevices);
devices.removeAll(removedDevices.stream().map(info -> info.device).collect(Collectors.toList()));
- final HashSet addedDevices = new HashSet<>(newDevices);
+ final HashSet addedDevices = new HashSet<>(newDevices);
addedDevices.removeAll(oldDevices);
devices.addAll(addedDevices.stream().map(info -> info.device).collect(Collectors.toList()));
oldDevices.removeAll(removedDevices);
oldDevices.addAll(newDevices);
- final CompoundNBT devicesNbt = deviceData[index];
- for (final DeviceInfo deviceInfo : removedDevices) {
- getSerializationKey(deviceInfo).ifPresent(devicesNbt::remove);
+ final CompoundNBT devicesNbt = groupData[index];
+ for (final TDeviceInfo deviceInfo : removedDevices) {
+ ItemDeviceUtils.getItemDeviceDataKey(deviceInfo.provider).ifPresent(devicesNbt::remove);
}
- for (final DeviceInfo deviceInfo : addedDevices) {
- getSerializationKey(deviceInfo).ifPresent(key -> {
+ for (final TDeviceInfo deviceInfo : addedDevices) {
+ ItemDeviceUtils.getItemDeviceDataKey(deviceInfo.provider).ifPresent(key -> {
if (devicesNbt.contains(key, NBTTagIds.TAG_COMPOUND)) {
deviceInfo.device.deserializeNBT(devicesNbt.getCompound(key));
}
@@ -120,27 +123,17 @@ public abstract class AbstractGroupingDeviceBusElement extends AbstractDeviceBus
///////////////////////////////////////////////////////////////////
- private void serializeDevices() {
- for (int i = 0; i < groupCount; i++) {
- final CompoundNBT devicesNbt = new CompoundNBT();
- for (final DeviceInfo deviceInfo : devicesByGroup.get(i)) {
- getSerializationKey(deviceInfo).ifPresent(key -> {
- final CompoundNBT deviceNbt = deviceInfo.device.serializeNBT();
- if (!deviceNbt.isEmpty()) {
- devicesNbt.put(key, deviceNbt);
- }
- });
- }
- deviceData[i] = devicesNbt;
- }
- }
-
- private static Optional getSerializationKey(final DeviceInfo info) {
- final ResourceLocation providerName = info.provider.getRegistryName();
- if (providerName == null) {
- return Optional.empty();
+ private void serializeDevices(final int index) {
+ final CompoundNBT devicesNbt = new CompoundNBT();
+ for (final TDeviceInfo deviceInfo : groups.get(index)) {
+ ItemDeviceUtils.getItemDeviceDataKey(deviceInfo.provider).ifPresent(key -> {
+ final CompoundNBT deviceNbt = deviceInfo.device.serializeNBT();
+ if (!deviceNbt.isEmpty()) {
+ devicesNbt.put(key, deviceNbt);
+ }
+ });
}
- return Optional.of(providerName.toString());
+ groupData[index] = devicesNbt;
}
}
diff --git a/src/main/java/li/cil/oc2/common/bus/AbstractGroupingItemDeviceBusElement.java b/src/main/java/li/cil/oc2/common/bus/AbstractGroupingItemDeviceBusElement.java
new file mode 100644
index 00000000..b11ee9c3
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/bus/AbstractGroupingItemDeviceBusElement.java
@@ -0,0 +1,10 @@
+package li.cil.oc2.common.bus;
+
+import li.cil.oc2.api.bus.device.provider.ItemDeviceProvider;
+import li.cil.oc2.common.bus.device.ItemDeviceInfo;
+
+public abstract class AbstractGroupingItemDeviceBusElement extends AbstractGroupingDeviceBusElement {
+ public AbstractGroupingItemDeviceBusElement(final int groupCount) {
+ super(groupCount);
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/ItemHandlerDeviceBusElement.java b/src/main/java/li/cil/oc2/common/bus/ItemHandlerDeviceBusElement.java
index f52016af..4b8b4570 100644
--- a/src/main/java/li/cil/oc2/common/bus/ItemHandlerDeviceBusElement.java
+++ b/src/main/java/li/cil/oc2/common/bus/ItemHandlerDeviceBusElement.java
@@ -1,33 +1,64 @@
package li.cil.oc2.common.bus;
-import li.cil.oc2.common.bus.device.DeviceInfo;
import li.cil.oc2.common.bus.device.Devices;
+import li.cil.oc2.common.bus.device.ItemDeviceInfo;
+import li.cil.oc2.common.util.ItemDeviceUtils;
+import li.cil.oc2.common.util.NBTTagIds;
import net.minecraft.item.ItemStack;
-import net.minecraftforge.common.util.LazyOptional;
-import net.minecraftforge.items.ItemStackHandler;
+import net.minecraft.nbt.CompoundNBT;
+import java.util.Collections;
import java.util.HashSet;
-public class ItemHandlerDeviceBusElement extends AbstractGroupingDeviceBusElement {
- private final ItemStackHandler handler;
+public class ItemHandlerDeviceBusElement extends AbstractGroupingItemDeviceBusElement {
+ public ItemHandlerDeviceBusElement(final int slotCount) {
+ super(slotCount);
+ }
///////////////////////////////////////////////////////////////////
- public ItemHandlerDeviceBusElement(final ItemStackHandler handler) {
- super(handler.getSlots());
- this.handler = handler;
+ public void updateDevices(final int slot, final ItemStack stack) {
+ if (!stack.isEmpty()) {
+ final HashSet newDevices = new HashSet<>(Devices.getDevices(stack));
+ importDeviceDataFromItemStack(stack, newDevices);
+ setDevicesForGroup(slot, newDevices);
+ } else {
+ setDevicesForGroup(slot, Collections.emptySet());
+ }
}
- public void handleSlotChanged(final int slot) {
- final HashSet newDevices = new HashSet<>();
- final ItemStack stack = handler.getStackInSlot(slot);
+ public void handleBeforeItemRemoved(final int slot, final ItemStack stack) {
if (!stack.isEmpty()) {
- for (final LazyOptional info : Devices.getDevices(stack)) {
- info.ifPresent(newDevices::add);
- info.addListener(unused -> handleSlotChanged(slot));
- }
+ exportDeviceDataToItemStack(slot, stack);
+ }
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
+ private void exportDeviceDataToItemStack(final int slot, final ItemStack stack) {
+ final CompoundNBT exportedNbt = new CompoundNBT();
+ for (final ItemDeviceInfo info : groups.get(slot)) {
+ ItemDeviceUtils.getItemDeviceDataKey(info.provider).ifPresent(key -> {
+ final CompoundNBT deviceNbt = new CompoundNBT();
+ info.device.exportToItemStack(deviceNbt);
+ if (!deviceNbt.isEmpty()) {
+ exportedNbt.put(key, deviceNbt);
+ }
+ });
}
- setDevicesForGroup(slot, newDevices);
+ ItemDeviceUtils.setItemDeviceData(stack, exportedNbt);
+ }
+
+ private void importDeviceDataFromItemStack(final ItemStack stack, final HashSet devices) {
+ ItemDeviceUtils.getItemDeviceData(stack).ifPresent(exportedNbt -> {
+ for (final ItemDeviceInfo info : devices) {
+ ItemDeviceUtils.getItemDeviceDataKey(info.provider).ifPresent(key -> {
+ if (exportedNbt.contains(key, NBTTagIds.TAG_COMPOUND)) {
+ info.device.importFromItemStack(exportedNbt.getCompound(key));
+ }
+ });
+ }
+ });
}
}
diff --git a/src/main/java/li/cil/oc2/common/bus/RPCAdapter.java b/src/main/java/li/cil/oc2/common/bus/RPCAdapter.java
index e1360c5a..557cd0ee 100644
--- a/src/main/java/li/cil/oc2/common/bus/RPCAdapter.java
+++ b/src/main/java/li/cil/oc2/common/bus/RPCAdapter.java
@@ -71,6 +71,8 @@ public final class RPCAdapter implements Steppable {
.create();
}
+ ///////////////////////////////////////////////////////////////////
+
public void reset() {
transmitBuffer.clear();
receiveBuffer = null;
diff --git a/src/main/java/li/cil/oc2/common/bus/TileEntityDeviceBusElement.java b/src/main/java/li/cil/oc2/common/bus/TileEntityDeviceBusElement.java
index 8c6b7211..15fc78bd 100644
--- a/src/main/java/li/cil/oc2/common/bus/TileEntityDeviceBusElement.java
+++ b/src/main/java/li/cil/oc2/common/bus/TileEntityDeviceBusElement.java
@@ -2,7 +2,7 @@ package li.cil.oc2.common.bus;
import li.cil.oc2.api.bus.DeviceBus;
import li.cil.oc2.api.bus.DeviceBusElement;
-import li.cil.oc2.common.bus.device.DeviceInfo;
+import li.cil.oc2.common.bus.device.BlockDeviceInfo;
import li.cil.oc2.common.bus.device.Devices;
import li.cil.oc2.common.capabilities.Capabilities;
import li.cil.oc2.common.util.ServerScheduler;
@@ -21,7 +21,7 @@ import java.util.Optional;
import static java.util.Objects.requireNonNull;
-public class TileEntityDeviceBusElement extends AbstractGroupingDeviceBusElement {
+public class TileEntityDeviceBusElement extends AbstractGroupingBlockDeviceBusElement {
private static final int NEIGHBOR_COUNT = 6;
final Direction[] NEIGHBOR_DIRECTIONS = Direction.values();
@@ -36,6 +36,8 @@ public class TileEntityDeviceBusElement extends AbstractGroupingDeviceBusElement
this.tileEntity = tileEntity;
}
+ ///////////////////////////////////////////////////////////////////
+
@Override
public Optional>> getNeighbors() {
final World world = tileEntity.getWorld();
@@ -80,9 +82,9 @@ public class TileEntityDeviceBusElement extends AbstractGroupingDeviceBusElement
final int index = direction.getIndex();
- final HashSet newDevices = new HashSet<>();
+ final HashSet newDevices = new HashSet<>();
if (canConnectToSide(direction)) {
- for (final LazyOptional deviceInfo : Devices.getDevices(world, pos, direction)) {
+ for (final LazyOptional deviceInfo : Devices.getDevices(world, pos, direction)) {
deviceInfo.ifPresent(newDevices::add);
deviceInfo.addListener(unused -> handleNeighborChanged(pos));
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/AbstractDeviceInfo.java b/src/main/java/li/cil/oc2/common/bus/device/AbstractDeviceInfo.java
new file mode 100644
index 00000000..4a42fd40
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/bus/device/AbstractDeviceInfo.java
@@ -0,0 +1,33 @@
+package li.cil.oc2.common.bus.device;
+
+import li.cil.oc2.api.bus.device.Device;
+import net.minecraftforge.registries.IForgeRegistryEntry;
+
+import java.util.Objects;
+
+public abstract class AbstractDeviceInfo, TDevice extends Device> {
+ public final TProvider provider;
+ public final TDevice device;
+
+ ///////////////////////////////////////////////////////////////////
+
+ protected AbstractDeviceInfo(final TProvider provider, final TDevice device) {
+ this.provider = provider;
+ this.device = device;
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
+ @Override
+ public boolean equals(final Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+ final AbstractDeviceInfo, ?> that = (AbstractDeviceInfo, ?>) o;
+ return provider.equals(that.provider) && device.equals(that.device);
+ }
+
+ @Override
+ public int hashCode() {
+ return Objects.hash(provider, device);
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/AbstractHardDiskDriveDevice.java b/src/main/java/li/cil/oc2/common/bus/device/AbstractHardDiskDriveDevice.java
index 90d19ed2..dba26715 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/AbstractHardDiskDriveDevice.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/AbstractHardDiskDriveDevice.java
@@ -1,7 +1,6 @@
package li.cil.oc2.common.bus.device;
import li.cil.oc2.api.bus.device.vm.*;
-import li.cil.oc2.common.bus.device.provider.util.AbstractObjectProxy;
import li.cil.oc2.common.serialization.BlobStorage;
import li.cil.oc2.common.serialization.NBTSerialization;
import li.cil.oc2.common.util.NBTTagIds;
@@ -17,7 +16,7 @@ import java.util.OptionalInt;
import java.util.OptionalLong;
import java.util.UUID;
-public abstract class AbstractHardDiskDriveDevice extends AbstractObjectProxy implements VMDevice, VMDeviceLifecycleListener {
+public abstract class AbstractHardDiskDriveDevice extends AbstractItemDevice implements VMDevice, VMDeviceLifecycleListener {
private static final String DEVICE_NBT_TAG_NAME = "device";
private static final String ADDRESS_NBT_TAG_NAME = "address";
private static final String INTERRUPT_NBT_TAG_NAME = "interrupt";
@@ -45,6 +44,8 @@ public abstract class AbstractHardDiskDriveDevice extends
super(stack);
}
+ ///////////////////////////////////////////////////////////////////
+
@Override
public VMDeviceLoadResult load(final VMContext context) {
if (!allocateDevice(context)) {
@@ -76,6 +77,20 @@ public abstract class AbstractHardDiskDriveDevice extends
}
}
+ @Override
+ public void exportToItemStack(final CompoundNBT nbt) {
+ if (blobHandle != null) {
+ nbt.putUniqueId(BLOB_HANDLE_NBT_TAG_NAME, blobHandle);
+ }
+ }
+
+ @Override
+ public void importFromItemStack(final CompoundNBT nbt) {
+ if (nbt.hasUniqueId(BLOB_HANDLE_NBT_TAG_NAME)) {
+ blobHandle = nbt.getUniqueId(BLOB_HANDLE_NBT_TAG_NAME);
+ }
+ }
+
@Override
public CompoundNBT serializeNBT() {
final CompoundNBT nbt = new CompoundNBT();
diff --git a/src/main/java/li/cil/oc2/common/bus/device/AbstractItemDevice.java b/src/main/java/li/cil/oc2/common/bus/device/AbstractItemDevice.java
new file mode 100644
index 00000000..92a0a8d3
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/bus/device/AbstractItemDevice.java
@@ -0,0 +1,21 @@
+package li.cil.oc2.common.bus.device;
+
+import li.cil.oc2.api.bus.device.ItemDevice;
+import net.minecraft.item.ItemStack;
+import net.minecraft.nbt.CompoundNBT;
+
+public abstract class AbstractItemDevice extends AbstractObjectDevice implements ItemDevice {
+ public AbstractItemDevice(final ItemStack value) {
+ super(value);
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
+ @Override
+ public void exportToItemStack(final CompoundNBT nbt) {
+ }
+
+ @Override
+ public void importFromItemStack(final CompoundNBT nbt) {
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractObjectProxy.java b/src/main/java/li/cil/oc2/common/bus/device/AbstractObjectDevice.java
similarity index 64%
rename from src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractObjectProxy.java
rename to src/main/java/li/cil/oc2/common/bus/device/AbstractObjectDevice.java
index 38c3a704..8a72ca68 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractObjectProxy.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/AbstractObjectDevice.java
@@ -1,22 +1,24 @@
-package li.cil.oc2.common.bus.device.provider.util;
+package li.cil.oc2.common.bus.device;
import javax.annotation.Nullable;
import java.util.Objects;
-public abstract class AbstractObjectProxy {
+public abstract class AbstractObjectDevice {
protected final T value;
///////////////////////////////////////////////////////////////////
- public AbstractObjectProxy(final T value) {
+ public AbstractObjectDevice(final T value) {
this.value = value;
}
+ ///////////////////////////////////////////////////////////////////
+
@Override
public boolean equals(@Nullable final Object o) {
if (this == o) return true;
if (o == null || getClass() != o.getClass()) return false;
- final AbstractObjectProxy> that = (AbstractObjectProxy>) o;
+ final AbstractObjectDevice> that = (AbstractObjectDevice>) o;
return value.equals(that.value);
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/BlockDeviceInfo.java b/src/main/java/li/cil/oc2/common/bus/device/BlockDeviceInfo.java
new file mode 100644
index 00000000..269a4364
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/bus/device/BlockDeviceInfo.java
@@ -0,0 +1,10 @@
+package li.cil.oc2.common.bus.device;
+
+import li.cil.oc2.api.bus.device.Device;
+import li.cil.oc2.api.bus.device.provider.BlockDeviceProvider;
+
+public final class BlockDeviceInfo extends AbstractDeviceInfo {
+ public BlockDeviceInfo(final BlockDeviceProvider blockDeviceProvider, final Device device) {
+ super(blockDeviceProvider, device);
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/DeviceInfo.java b/src/main/java/li/cil/oc2/common/bus/device/DeviceInfo.java
deleted file mode 100644
index 3450df01..00000000
--- a/src/main/java/li/cil/oc2/common/bus/device/DeviceInfo.java
+++ /dev/null
@@ -1,29 +0,0 @@
-package li.cil.oc2.common.bus.device;
-
-import li.cil.oc2.api.bus.device.Device;
-import li.cil.oc2.api.bus.device.provider.DeviceProvider;
-
-import java.util.Objects;
-
-public final class DeviceInfo {
- public final Device device;
- public final DeviceProvider provider;
-
- public DeviceInfo(final Device device, final DeviceProvider provider) {
- this.device = device;
- this.provider = provider;
- }
-
- @Override
- public boolean equals(final Object o) {
- if (this == o) return true;
- if (o == null || getClass() != o.getClass()) return false;
- final DeviceInfo that = (DeviceInfo) o;
- return device.equals(that.device) && provider.equals(that.provider);
- }
-
- @Override
- public int hashCode() {
- return Objects.hash(device, provider);
- }
-}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/Devices.java b/src/main/java/li/cil/oc2/common/bus/device/Devices.java
index 893d6f09..4f077763 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/Devices.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/Devices.java
@@ -1,9 +1,10 @@
package li.cil.oc2.common.bus.device;
import li.cil.oc2.api.bus.device.Device;
+import li.cil.oc2.api.bus.device.ItemDevice;
+import li.cil.oc2.api.bus.device.provider.BlockDeviceProvider;
import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
-import li.cil.oc2.api.bus.device.provider.DeviceProvider;
-import li.cil.oc2.api.bus.device.provider.DeviceQuery;
+import li.cil.oc2.api.bus.device.provider.ItemDeviceProvider;
import li.cil.oc2.api.bus.device.provider.ItemDeviceQuery;
import li.cil.oc2.common.init.Providers;
import net.minecraft.item.ItemStack;
@@ -17,9 +18,10 @@ import net.minecraftforge.registries.IForgeRegistry;
import javax.annotation.Nullable;
import java.util.ArrayList;
import java.util.List;
+import java.util.Optional;
public final class Devices {
- public static List> getDevices(final TileEntity tileEntity, final Direction side) {
+ public static List> getDevices(final TileEntity tileEntity, final Direction side) {
final World world = tileEntity.getWorld();
final BlockPos pos = tileEntity.getPos();
@@ -28,21 +30,23 @@ public final class Devices {
return getDevices(world, pos, side);
}
- public static List> getDevices(final World world, final BlockPos pos, final Direction side) {
+ public static List> getDevices(final World world, final BlockPos pos, final Direction side) {
return getDevices(new BlockQuery(world, pos, side));
}
- public static List> getDevices(final ItemStack stack) {
+ public static List getDevices(final ItemStack stack) {
return getDevices(new ItemQuery(stack));
}
- public static List> getDevices(final DeviceQuery query) {
- final IForgeRegistry providers = Providers.PROVIDERS_REGISTRY.get();
- final ArrayList> devices = new ArrayList<>();
- for (final DeviceProvider provider : providers.getValues()) {
+ ///////////////////////////////////////////////////////////////////
+
+ private static List> getDevices(final BlockQuery query) {
+ final IForgeRegistry registry = Providers.BLOCK_DEVICE_PROVIDER_REGISTRY.get();
+ final ArrayList> devices = new ArrayList<>();
+ for (final BlockDeviceProvider provider : registry.getValues()) {
final LazyOptional device = provider.getDevice(query);
if (device.isPresent()) {
- final LazyOptional info = device.lazyMap(d -> new DeviceInfo(d, provider));
+ final LazyOptional info = device.lazyMap(d -> new BlockDeviceInfo(provider, d));
device.addListener(unused -> info.invalidate());
devices.add(info);
}
@@ -50,6 +54,16 @@ public final class Devices {
return devices;
}
+ private static List getDevices(final ItemQuery query) {
+ final IForgeRegistry registry = Providers.ITEM_DEVICE_PROVIDER_REGISTRY.get();
+ final ArrayList devices = new ArrayList<>();
+ for (final ItemDeviceProvider provider : registry.getValues()) {
+ final Optional device = provider.getDevice(query);
+ device.ifPresent(d -> devices.add(new ItemDeviceInfo(provider, d)));
+ }
+ return devices;
+ }
+
///////////////////////////////////////////////////////////////////
private static class BlockQuery implements BlockDeviceQuery {
diff --git a/src/main/java/li/cil/oc2/common/bus/device/HardDiskDriveDevice.java b/src/main/java/li/cil/oc2/common/bus/device/HardDiskDriveDevice.java
index 4426acaa..9013f784 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/HardDiskDriveDevice.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/HardDiskDriveDevice.java
@@ -11,12 +11,16 @@ public final class HardDiskDriveDevice extends AbstractHardDiskDriveDevice {
+ public ItemDeviceInfo(final ItemDeviceProvider itemDeviceProvider, final ItemDevice device) {
+ super(itemDeviceProvider, device);
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/MemoryDevice.java b/src/main/java/li/cil/oc2/common/bus/device/MemoryDevice.java
index 50b31e3a..62e7c187 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/MemoryDevice.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/MemoryDevice.java
@@ -2,7 +2,6 @@ package li.cil.oc2.common.bus.device;
import li.cil.oc2.Constants;
import li.cil.oc2.api.bus.device.vm.*;
-import li.cil.oc2.common.bus.device.provider.util.AbstractObjectProxy;
import li.cil.oc2.common.serialization.BlobStorage;
import li.cil.oc2.common.util.NBTTagIds;
import li.cil.sedna.api.device.PhysicalMemory;
@@ -15,7 +14,7 @@ import net.minecraft.nbt.CompoundNBT;
import java.util.OptionalLong;
import java.util.UUID;
-public final class MemoryDevice extends AbstractObjectProxy implements VMDevice, VMDeviceLifecycleListener {
+public final class MemoryDevice extends AbstractItemDevice implements VMDevice, VMDeviceLifecycleListener {
private static final String BLOB_HANDLE_NBT_TAG_NAME = "blob";
private static final String ADDRESS_NBT_TAG_NAME = "address";
@@ -37,6 +36,8 @@ public final class MemoryDevice extends AbstractObjectProxy implement
super(value);
}
+ ///////////////////////////////////////////////////////////////////
+
@Override
public VMDeviceLoadResult load(final VMContext context) {
if (!allocateDevice(context)) {
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/BlockDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/BlockDeviceProvider.java
deleted file mode 100644
index 6a516963..00000000
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/BlockDeviceProvider.java
+++ /dev/null
@@ -1,35 +0,0 @@
-package li.cil.oc2.common.bus.device.provider;
-
-import li.cil.oc2.api.bus.device.Device;
-import li.cil.oc2.api.bus.device.object.Callbacks;
-import li.cil.oc2.api.bus.device.object.ObjectDevice;
-import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
-import li.cil.oc2.api.bus.device.provider.DeviceQuery;
-import li.cil.oc2.common.bus.device.provider.util.AbstractDeviceProvider;
-import li.cil.oc2.common.util.WorldUtils;
-import net.minecraft.block.Block;
-import net.minecraft.block.BlockState;
-import net.minecraftforge.common.util.LazyOptional;
-
-public final class BlockDeviceProvider extends AbstractDeviceProvider {
- @Override
- public LazyOptional getDevice(final DeviceQuery query) {
- if (!(query instanceof BlockDeviceQuery)) {
- return LazyOptional.empty();
- }
-
- final BlockDeviceQuery blockQuery = (BlockDeviceQuery) query;
- final BlockState blockState = blockQuery.getWorld().getBlockState(blockQuery.getQueryPosition());
- if (blockState.getBlock().isAir(blockState, blockQuery.getWorld(), blockQuery.getQueryPosition())) {
- return LazyOptional.empty();
- }
-
- final Block block = blockState.getBlock();
- if (!Callbacks.hasMethods(block)) {
- return LazyOptional.empty();
- }
-
- final String typeName = WorldUtils.getBlockName(blockQuery.getWorld(), blockQuery.getQueryPosition());
- return LazyOptional.of(() -> new ObjectDevice(block, typeName));
- }
-}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/BlockStateDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/BlockStateDeviceProvider.java
new file mode 100644
index 00000000..924444fa
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/BlockStateDeviceProvider.java
@@ -0,0 +1,35 @@
+package li.cil.oc2.common.bus.device.provider;
+
+import li.cil.oc2.api.bus.device.Device;
+import li.cil.oc2.api.bus.device.object.Callbacks;
+import li.cil.oc2.api.bus.device.object.ObjectDevice;
+import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
+import li.cil.oc2.common.bus.device.provider.util.AbstractBlockDeviceProvider;
+import li.cil.oc2.common.util.WorldUtils;
+import net.minecraft.block.Block;
+import net.minecraft.block.BlockState;
+import net.minecraft.util.math.BlockPos;
+import net.minecraft.world.World;
+import net.minecraftforge.common.util.LazyOptional;
+
+public final class BlockStateDeviceProvider extends AbstractBlockDeviceProvider {
+ @Override
+ public LazyOptional getDevice(final BlockDeviceQuery query) {
+ final World world = query.getWorld();
+ final BlockPos position = query.getQueryPosition();
+
+ final BlockState blockState = world.getBlockState(position);
+ final Block block = blockState.getBlock();
+
+ if (block.isAir(blockState, world, position)) {
+ return LazyOptional.empty();
+ }
+
+ if (!Callbacks.hasMethods(block)) {
+ return LazyOptional.empty();
+ }
+
+ final String typeName = WorldUtils.getBlockName(world, position);
+ return LazyOptional.of(() -> new ObjectDevice(block, typeName));
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/EnergyStorageDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/EnergyStorageBlockDeviceProvider.java
similarity index 74%
rename from src/main/java/li/cil/oc2/common/bus/device/provider/EnergyStorageDeviceProvider.java
rename to src/main/java/li/cil/oc2/common/bus/device/provider/EnergyStorageBlockDeviceProvider.java
index bbb1d710..2d55ed55 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/EnergyStorageDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/EnergyStorageBlockDeviceProvider.java
@@ -4,31 +4,32 @@ import li.cil.oc2.api.bus.device.Device;
import li.cil.oc2.api.bus.device.object.Callback;
import li.cil.oc2.api.bus.device.object.ObjectDevice;
import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
-import li.cil.oc2.common.bus.device.provider.util.AbstractCapabilityAnyTileEntityDeviceProvider;
-import li.cil.oc2.common.bus.device.provider.util.AbstractObjectProxy;
+import li.cil.oc2.common.bus.device.provider.util.AbstractTileEntityCapabilityDeviceProvider;
+import li.cil.oc2.common.bus.device.AbstractObjectDevice;
import li.cil.oc2.common.capabilities.Capabilities;
+import net.minecraft.tileentity.TileEntity;
import net.minecraftforge.common.util.LazyOptional;
import net.minecraftforge.energy.IEnergyStorage;
-public final class EnergyStorageDeviceProvider extends AbstractCapabilityAnyTileEntityDeviceProvider {
+public final class EnergyStorageBlockDeviceProvider extends AbstractTileEntityCapabilityDeviceProvider {
private static final String ENERGY_STORAGE_TYPE_NAME = "energyStorage";
///////////////////////////////////////////////////////////////////
- public EnergyStorageDeviceProvider() {
+ public EnergyStorageBlockDeviceProvider() {
super(() -> Capabilities.ENERGY_STORAGE_CAPABILITY);
}
///////////////////////////////////////////////////////////////////
@Override
- protected LazyOptional getDevice(final BlockDeviceQuery query, final IEnergyStorage value) {
+ protected LazyOptional getBlockDevice(final BlockDeviceQuery query, final IEnergyStorage value) {
return LazyOptional.of(() -> new ObjectDevice(new EnergyStorageDevice(value), ENERGY_STORAGE_TYPE_NAME));
}
///////////////////////////////////////////////////////////////////
- public static final class EnergyStorageDevice extends AbstractObjectProxy {
+ public static final class EnergyStorageDevice extends AbstractObjectDevice {
public EnergyStorageDevice(final IEnergyStorage energyStorage) {
super(energyStorage);
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/FluidHandlerDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/FluidHandlerBlockDeviceProvider.java
similarity index 74%
rename from src/main/java/li/cil/oc2/common/bus/device/provider/FluidHandlerDeviceProvider.java
rename to src/main/java/li/cil/oc2/common/bus/device/provider/FluidHandlerBlockDeviceProvider.java
index 7a3d7cc7..99128e4f 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/FluidHandlerDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/FluidHandlerBlockDeviceProvider.java
@@ -4,32 +4,33 @@ import li.cil.oc2.api.bus.device.Device;
import li.cil.oc2.api.bus.device.object.Callback;
import li.cil.oc2.api.bus.device.object.ObjectDevice;
import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
-import li.cil.oc2.common.bus.device.provider.util.AbstractCapabilityAnyTileEntityDeviceProvider;
-import li.cil.oc2.common.bus.device.provider.util.AbstractObjectProxy;
+import li.cil.oc2.common.bus.device.provider.util.AbstractTileEntityCapabilityDeviceProvider;
+import li.cil.oc2.common.bus.device.AbstractObjectDevice;
import li.cil.oc2.common.capabilities.Capabilities;
+import net.minecraft.tileentity.TileEntity;
import net.minecraftforge.common.util.LazyOptional;
import net.minecraftforge.fluids.FluidStack;
import net.minecraftforge.fluids.capability.IFluidHandler;
-public final class FluidHandlerDeviceProvider extends AbstractCapabilityAnyTileEntityDeviceProvider {
+public final class FluidHandlerBlockDeviceProvider extends AbstractTileEntityCapabilityDeviceProvider {
private static final String FLUID_HANDLER_TYPE_NAME = "fluidHandler";
///////////////////////////////////////////////////////////////////
- public FluidHandlerDeviceProvider() {
+ public FluidHandlerBlockDeviceProvider() {
super(() -> Capabilities.FLUID_HANDLER_CAPABILITY);
}
///////////////////////////////////////////////////////////////////
@Override
- protected LazyOptional getDevice(final BlockDeviceQuery query, final IFluidHandler value) {
+ protected LazyOptional getBlockDevice(final BlockDeviceQuery query, final IFluidHandler value) {
return LazyOptional.of(() -> new ObjectDevice(new FluidHandlerDevice(value), FLUID_HANDLER_TYPE_NAME));
}
///////////////////////////////////////////////////////////////////
- public static final class FluidHandlerDevice extends AbstractObjectProxy {
+ public static final class FluidHandlerDevice extends AbstractObjectDevice {
public FluidHandlerDevice(final IFluidHandler fluidHandler) {
super(fluidHandler);
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/HardDriveItemDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/HardDriveItemDeviceProvider.java
index fd559f34..aff7228a 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/HardDriveItemDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/HardDriveItemDeviceProvider.java
@@ -2,70 +2,88 @@ package li.cil.oc2.common.bus.device.provider;
import li.cil.oc2.Config;
import li.cil.oc2.Constants;
-import li.cil.oc2.api.API;
-import li.cil.oc2.api.bus.device.Device;
+import li.cil.oc2.api.bus.device.ItemDevice;
import li.cil.oc2.api.bus.device.provider.ItemDeviceQuery;
import li.cil.oc2.common.bus.device.HardDiskDriveDevice;
import li.cil.oc2.common.bus.device.SparseHardDiskDriveDevice;
import li.cil.oc2.common.bus.device.provider.util.AbstractItemDeviceProvider;
import li.cil.oc2.common.init.Items;
+import li.cil.oc2.common.util.ItemStackUtils;
import li.cil.oc2.common.util.NBTTagIds;
import li.cil.sedna.api.device.BlockDevice;
import li.cil.sedna.buildroot.Buildroot;
import li.cil.sedna.device.block.ByteBufferBlockDevice;
import net.minecraft.item.ItemStack;
import net.minecraft.nbt.CompoundNBT;
-import net.minecraftforge.common.util.LazyOptional;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
+import javax.annotation.Nullable;
import java.io.IOException;
import java.util.Objects;
+import java.util.Optional;
public final class HardDriveItemDeviceProvider extends AbstractItemDeviceProvider {
private static final Logger LOGGER = LogManager.getLogger();
///////////////////////////////////////////////////////////////////
+ private static final ByteBufferBlockDevice ROOT_FS;
+
+ static {
+ ByteBufferBlockDevice rootfs;
+ try {
+ rootfs = ByteBufferBlockDevice.createFromStream(Buildroot.getRootFilesystem(), true);
+ } catch (final IOException e) {
+ LOGGER.error(e);
+ rootfs = ByteBufferBlockDevice.create(0, true);
+ }
+ ROOT_FS = rootfs;
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
public HardDriveItemDeviceProvider() {
- super(Items.HDD_ITEM.get());
+ super(Items.HDD_ITEM);
}
///////////////////////////////////////////////////////////////////
@Override
- protected LazyOptional getItemDevice(final ItemDeviceQuery query) {
+ protected Optional getItemDevice(final ItemDeviceQuery query) {
final ItemStack stack = query.getItemStack();
- final CompoundNBT info = stack.getChildTag(API.MOD_ID);
+ final CompoundNBT info = ItemStackUtils.getModDataTag(stack);
if (info == null) {
- return LazyOptional.empty();
+ return Optional.empty();
}
final boolean readonly = info.getBoolean(Constants.HDD_READONLY_NBT_TAG_NAME);
if (info.contains(Constants.HDD_BASE_NBT_TAG_NAME, NBTTagIds.TAG_STRING)) {
final String baseName = info.getString(Constants.HDD_BASE_NBT_TAG_NAME);
- BlockDevice base = null;
-
- // TODO Allow registering additional base file systems?
- if (Objects.equals(baseName, "linux")) {
- try {
- base = ByteBufferBlockDevice.createFromStream(Buildroot.getRootFilesystem(), true);
- } catch (final IOException e) {
- LOGGER.error(e);
- }
- }
+ final BlockDevice base = getBaseBlockDevice(baseName);
if (base != null) {
- final BlockDevice baseForClosure = base;
- return LazyOptional.of(() -> new SparseHardDiskDriveDevice(stack, baseForClosure, readonly));
+ return Optional.of(new SparseHardDiskDriveDevice(stack, base, readonly));
}
} else if (info.contains(Constants.HDD_SIZE_NBT_TAG_NAME, NBTTagIds.TAG_INT)) {
final int size = Math.max(0, Math.min(Config.maxHddSize, info.getInt(Constants.HDD_SIZE_NBT_TAG_NAME)));
- return LazyOptional.of(() -> new HardDiskDriveDevice(stack, size, readonly));
+ return Optional.of(new HardDiskDriveDevice(stack, size, readonly));
}
- return LazyOptional.empty();
+ return Optional.empty();
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
+ @Nullable
+ private static BlockDevice getBaseBlockDevice(final String name) {
+ // TODO Allow registering additional base file systems.
+ if (Objects.equals(name, "linux")) {
+ return ROOT_FS;
+ }
+
+ return null;
}
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/ItemHandlerDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/ItemHandlerBlockDeviceProvider.java
similarity index 74%
rename from src/main/java/li/cil/oc2/common/bus/device/provider/ItemHandlerDeviceProvider.java
rename to src/main/java/li/cil/oc2/common/bus/device/provider/ItemHandlerBlockDeviceProvider.java
index ac9fabde..3bd53f6a 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/ItemHandlerDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/ItemHandlerBlockDeviceProvider.java
@@ -4,32 +4,33 @@ import li.cil.oc2.api.bus.device.Device;
import li.cil.oc2.api.bus.device.object.Callback;
import li.cil.oc2.api.bus.device.object.ObjectDevice;
import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
-import li.cil.oc2.common.bus.device.provider.util.AbstractCapabilityAnyTileEntityDeviceProvider;
-import li.cil.oc2.common.bus.device.provider.util.AbstractObjectProxy;
+import li.cil.oc2.common.bus.device.AbstractObjectDevice;
+import li.cil.oc2.common.bus.device.provider.util.AbstractTileEntityCapabilityDeviceProvider;
import li.cil.oc2.common.capabilities.Capabilities;
import net.minecraft.item.ItemStack;
+import net.minecraft.tileentity.TileEntity;
import net.minecraftforge.common.util.LazyOptional;
import net.minecraftforge.items.IItemHandler;
-public final class ItemHandlerDeviceProvider extends AbstractCapabilityAnyTileEntityDeviceProvider {
+public final class ItemHandlerBlockDeviceProvider extends AbstractTileEntityCapabilityDeviceProvider {
private static final String ITEM_HANDLER_TYPE_NAME = "itemHandler";
///////////////////////////////////////////////////////////////////
- public ItemHandlerDeviceProvider() {
+ public ItemHandlerBlockDeviceProvider() {
super(() -> Capabilities.ITEM_HANDLER_CAPABILITY);
}
///////////////////////////////////////////////////////////////////
@Override
- protected LazyOptional getDevice(final BlockDeviceQuery query, final IItemHandler value) {
+ protected LazyOptional getBlockDevice(final BlockDeviceQuery query, final IItemHandler value) {
return LazyOptional.of(() -> new ObjectDevice(new ItemHandlerDevice(value), ITEM_HANDLER_TYPE_NAME));
}
///////////////////////////////////////////////////////////////////
- public static final class ItemHandlerDevice extends AbstractObjectProxy {
+ public static final class ItemHandlerDevice extends AbstractObjectDevice {
public ItemHandlerDevice(final IItemHandler itemHandler) {
super(itemHandler);
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/MemoryItemDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/MemoryItemDeviceProvider.java
index 63d4ddec..72caa368 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/MemoryItemDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/MemoryItemDeviceProvider.java
@@ -1,21 +1,22 @@
package li.cil.oc2.common.bus.device.provider;
-import li.cil.oc2.api.bus.device.Device;
+import li.cil.oc2.api.bus.device.ItemDevice;
import li.cil.oc2.api.bus.device.provider.ItemDeviceQuery;
import li.cil.oc2.common.bus.device.MemoryDevice;
import li.cil.oc2.common.bus.device.provider.util.AbstractItemDeviceProvider;
import li.cil.oc2.common.init.Items;
-import net.minecraftforge.common.util.LazyOptional;
+
+import java.util.Optional;
public final class MemoryItemDeviceProvider extends AbstractItemDeviceProvider {
public MemoryItemDeviceProvider() {
- super(Items.RAM_8M_ITEM.get());
+ super(Items.RAM_8M_ITEM);
}
///////////////////////////////////////////////////////////////////
@Override
- protected LazyOptional getItemDevice(final ItemDeviceQuery query) {
- return LazyOptional.of(() -> new MemoryDevice(query.getItemStack()));
+ protected Optional getItemDevice(final ItemDeviceQuery query) {
+ return Optional.of(new MemoryDevice(query.getItemStack()));
}
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/TileEntityDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/TileEntityDeviceProvider.java
index cea5d476..825f962c 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/TileEntityDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/TileEntityDeviceProvider.java
@@ -7,15 +7,12 @@ import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
import li.cil.oc2.common.bus.device.provider.util.AbstractTileEntityDeviceProvider;
import li.cil.oc2.common.util.WorldUtils;
import net.minecraft.tileentity.TileEntity;
+import net.minecraft.tileentity.TileEntityType;
import net.minecraftforge.common.util.LazyOptional;
public final class TileEntityDeviceProvider extends AbstractTileEntityDeviceProvider {
- public TileEntityDeviceProvider() {
- super(TileEntity.class);
- }
-
@Override
- public LazyOptional getDevice(final BlockDeviceQuery query, final TileEntity tileEntity) {
+ public LazyOptional getBlockDevice(final BlockDeviceQuery query, final TileEntity tileEntity) {
if (Callbacks.hasMethods(tileEntity)) {
return LazyOptional.of(() -> {
final String typeName = WorldUtils.getBlockName(query.getWorld(), query.getQueryPosition());
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractBlockDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractBlockDeviceProvider.java
new file mode 100644
index 00000000..22fc742a
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractBlockDeviceProvider.java
@@ -0,0 +1,7 @@
+package li.cil.oc2.common.bus.device.provider.util;
+
+import li.cil.oc2.api.bus.device.provider.BlockDeviceProvider;
+import net.minecraftforge.registries.ForgeRegistryEntry;
+
+public abstract class AbstractBlockDeviceProvider extends ForgeRegistryEntry implements BlockDeviceProvider {
+}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractCapabilityAnyTileEntityDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractCapabilityAnyTileEntityDeviceProvider.java
deleted file mode 100644
index bde4254b..00000000
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractCapabilityAnyTileEntityDeviceProvider.java
+++ /dev/null
@@ -1,12 +0,0 @@
-package li.cil.oc2.common.bus.device.provider.util;
-
-import net.minecraft.tileentity.TileEntity;
-import net.minecraftforge.common.capabilities.Capability;
-
-import java.util.function.Supplier;
-
-public abstract class AbstractCapabilityAnyTileEntityDeviceProvider extends AbstractCapabilityTileEntityDeviceProvider {
- public AbstractCapabilityAnyTileEntityDeviceProvider(final Supplier> capabilitySupplier) {
- super(TileEntity.class, capabilitySupplier);
- }
-}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractDeviceProvider.java
deleted file mode 100644
index a9f3c7ac..00000000
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractDeviceProvider.java
+++ /dev/null
@@ -1,7 +0,0 @@
-package li.cil.oc2.common.bus.device.provider.util;
-
-import li.cil.oc2.api.bus.device.provider.DeviceProvider;
-import net.minecraftforge.registries.ForgeRegistryEntry;
-
-public abstract class AbstractDeviceProvider extends ForgeRegistryEntry implements DeviceProvider {
-}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractItemDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractItemDeviceProvider.java
index f30f7aab..b357a7c8 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractItemDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractItemDeviceProvider.java
@@ -1,37 +1,45 @@
package li.cil.oc2.common.bus.device.provider.util;
-import li.cil.oc2.api.bus.device.Device;
-import li.cil.oc2.api.bus.device.provider.DeviceQuery;
+import li.cil.oc2.api.bus.device.ItemDevice;
+import li.cil.oc2.api.bus.device.provider.ItemDeviceProvider;
import li.cil.oc2.api.bus.device.provider.ItemDeviceQuery;
import net.minecraft.item.Item;
import net.minecraft.item.ItemStack;
-import net.minecraftforge.common.util.LazyOptional;
+import net.minecraftforge.fml.RegistryObject;
+import net.minecraftforge.registries.ForgeRegistryEntry;
-public abstract class AbstractItemDeviceProvider extends AbstractDeviceProvider {
- private final Item item;
+import java.util.Optional;
- protected AbstractItemDeviceProvider(final Item item) {
+public abstract class AbstractItemDeviceProvider extends ForgeRegistryEntry implements ItemDeviceProvider {
+ private final RegistryObject- item;
+
+ ///////////////////////////////////////////////////////////////////
+
+ protected AbstractItemDeviceProvider(final RegistryObject
- item) {
this.item = item;
}
- @Override
- public LazyOptional getDevice(final DeviceQuery query) {
- if (!(query instanceof ItemDeviceQuery)) {
- return LazyOptional.empty();
- }
-
- final ItemDeviceQuery itemDeviceQuery = (ItemDeviceQuery) query;
- final ItemStack stack = itemDeviceQuery.getItemStack();
- if (stack.isEmpty()) {
- return LazyOptional.empty();
- }
-
- if (stack.getItem() != item) {
- return LazyOptional.empty();
- }
-
- return getItemDevice(itemDeviceQuery);
+ protected AbstractItemDeviceProvider() {
+ this.item = null;
}
- protected abstract LazyOptional getItemDevice(final ItemDeviceQuery query);
+ ///////////////////////////////////////////////////////////////////
+
+ @Override
+ public final Optional getDevice(final ItemDeviceQuery query) {
+ final ItemStack stack = query.getItemStack();
+ if (stack.isEmpty()) {
+ return Optional.empty();
+ }
+
+ if (item != null && stack.getItem() != item.get()) {
+ return Optional.empty();
+ }
+
+ return getItemDevice(query);
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
+ protected abstract Optional getItemDevice(final ItemDeviceQuery query);
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractCapabilityTileEntityDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractTileEntityCapabilityDeviceProvider.java
similarity index 58%
rename from src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractCapabilityTileEntityDeviceProvider.java
rename to src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractTileEntityCapabilityDeviceProvider.java
index 77cb185c..275d7892 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractCapabilityTileEntityDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractTileEntityCapabilityDeviceProvider.java
@@ -3,23 +3,30 @@ package li.cil.oc2.common.bus.device.provider.util;
import li.cil.oc2.api.bus.device.Device;
import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
import net.minecraft.tileentity.TileEntity;
+import net.minecraft.tileentity.TileEntityType;
import net.minecraftforge.common.capabilities.Capability;
import net.minecraftforge.common.util.LazyOptional;
import java.util.function.Supplier;
-public abstract class AbstractCapabilityTileEntityDeviceProvider extends AbstractTileEntityDeviceProvider {
+public abstract class AbstractTileEntityCapabilityDeviceProvider extends AbstractTileEntityDeviceProvider {
private final Supplier> capabilitySupplier;
///////////////////////////////////////////////////////////////////
- protected AbstractCapabilityTileEntityDeviceProvider(final Class tileEntityType, final Supplier> capabilitySupplier) {
+ protected AbstractTileEntityCapabilityDeviceProvider(final TileEntityType tileEntityType, final Supplier> capabilitySupplier) {
super(tileEntityType);
this.capabilitySupplier = capabilitySupplier;
}
+ protected AbstractTileEntityCapabilityDeviceProvider(final Supplier> capabilitySupplier) {
+ this.capabilitySupplier = capabilitySupplier;
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
@Override
- protected final LazyOptional getDevice(final BlockDeviceQuery blockQuery, final TileEntity tileEntity) {
+ protected final LazyOptional getBlockDevice(final BlockDeviceQuery blockQuery, final TileEntity tileEntity) {
final Capability capability = capabilitySupplier.get();
if (capability == null) throw new IllegalStateException();
final LazyOptional optional = tileEntity.getCapability(capability, blockQuery.getQuerySide());
@@ -28,10 +35,10 @@ public abstract class AbstractCapabilityTileEntityDeviceProvider device = getDevice(blockQuery, value);
+ final LazyOptional device = getBlockDevice(blockQuery, value);
optional.addListener(ignored -> device.invalidate());
return device;
}
- protected abstract LazyOptional getDevice(final BlockDeviceQuery query, final TCapability value);
+ protected abstract LazyOptional getBlockDevice(final BlockDeviceQuery query, final TCapability value);
}
diff --git a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractTileEntityDeviceProvider.java b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractTileEntityDeviceProvider.java
index 262d7401..39d14807 100644
--- a/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractTileEntityDeviceProvider.java
+++ b/src/main/java/li/cil/oc2/common/bus/device/provider/util/AbstractTileEntityDeviceProvider.java
@@ -2,37 +2,42 @@ package li.cil.oc2.common.bus.device.provider.util;
import li.cil.oc2.api.bus.device.Device;
import li.cil.oc2.api.bus.device.provider.BlockDeviceQuery;
-import li.cil.oc2.api.bus.device.provider.DeviceQuery;
import li.cil.oc2.common.util.WorldUtils;
import net.minecraft.tileentity.TileEntity;
+import net.minecraft.tileentity.TileEntityType;
import net.minecraftforge.common.util.LazyOptional;
-public abstract class AbstractTileEntityDeviceProvider extends AbstractDeviceProvider {
- private final Class tileEntityType;
+public abstract class AbstractTileEntityDeviceProvider extends AbstractBlockDeviceProvider {
+ private final TileEntityType tileEntityType;
///////////////////////////////////////////////////////////////////
- protected AbstractTileEntityDeviceProvider(final Class tileEntityType) {
+ protected AbstractTileEntityDeviceProvider(final TileEntityType tileEntityType) {
this.tileEntityType = tileEntityType;
}
- @SuppressWarnings("unchecked")
- @Override
- public LazyOptional getDevice(final DeviceQuery query) {
- if (!(query instanceof BlockDeviceQuery)) {
- return LazyOptional.empty();
- }
-
- final BlockDeviceQuery blockQuery = (BlockDeviceQuery) query;
- final TileEntity tileEntity = WorldUtils.getTileEntityIfChunkExists(blockQuery.getWorld(), blockQuery.getQueryPosition());
- if (!tileEntityType.isInstance(tileEntity)) {
- return LazyOptional.empty();
- }
-
- return getDevice(blockQuery, (T) tileEntity);
+ protected AbstractTileEntityDeviceProvider() {
+ this.tileEntityType = null;
}
///////////////////////////////////////////////////////////////////
- protected abstract LazyOptional getDevice(final BlockDeviceQuery query, final T tileEntity);
+ @SuppressWarnings("unchecked")
+ @Override
+ public final LazyOptional getDevice(final BlockDeviceQuery query) {
+ final TileEntity tileEntity = WorldUtils.getTileEntityIfChunkExists(query.getWorld(), query.getQueryPosition());
+ if (tileEntity == null) {
+ return LazyOptional.empty();
+ }
+
+ if (tileEntityType != null && tileEntity.getType() != tileEntityType) {
+ return LazyOptional.empty();
+ }
+
+ return getBlockDevice(query, (T) tileEntity);
+ }
+
+ ///////////////////////////////////////////////////////////////////
+
+ protected abstract LazyOptional getBlockDevice(final BlockDeviceQuery query, final T tileEntity);
}
diff --git a/src/main/java/li/cil/oc2/common/container/DeviceItemStackHandler.java b/src/main/java/li/cil/oc2/common/container/DeviceItemStackHandler.java
index 4b46b39b..78d22323 100644
--- a/src/main/java/li/cil/oc2/common/container/DeviceItemStackHandler.java
+++ b/src/main/java/li/cil/oc2/common/container/DeviceItemStackHandler.java
@@ -24,9 +24,11 @@ public class DeviceItemStackHandler extends ItemStackHandler {
public DeviceItemStackHandler(final NonNullList stacks) {
super(stacks);
- this.busElement = new ItemHandlerDeviceBusElement(this);
+ this.busElement = new ItemHandlerDeviceBusElement(getSlots());
}
+ ///////////////////////////////////////////////////////////////////
+
public DeviceBusElement getBusElement() {
return busElement;
}
@@ -42,14 +44,19 @@ public class DeviceItemStackHandler extends ItemStackHandler {
public void deserializeNBT(final CompoundNBT nbt) {
super.deserializeNBT(nbt);
busElement.deserializeNBT(nbt.getList(BUS_ELEMENT_NBT_TAG_NAME, NBTTagIds.TAG_COMPOUND));
- for (int i = 0; i < getSlots(); i++) {
- busElement.handleSlotChanged(i);
+ for (int slot = 0; slot < getSlots(); slot++) {
+ busElement.updateDevices(slot, getStackInSlot(slot));
}
}
+ @NotNull
@Override
- public boolean isItemValid(final int slot, @NotNull final ItemStack stack) {
- return super.isItemValid(slot, stack);
+ public ItemStack extractItem(final int slot, final int amount, final boolean simulate) {
+ if (!simulate && amount > 0) {
+ busElement.handleBeforeItemRemoved(slot, getStackInSlot(slot));
+ }
+
+ return super.extractItem(slot, amount, simulate);
}
@Override
@@ -57,11 +64,16 @@ public class DeviceItemStackHandler extends ItemStackHandler {
return 1;
}
+ @Override
+ public boolean isItemValid(final int slot, @NotNull final ItemStack stack) {
+ return super.isItemValid(slot, stack);
+ }
+
///////////////////////////////////////////////////////////////////
@Override
protected void onContentsChanged(final int slot) {
super.onContentsChanged(slot);
- busElement.handleSlotChanged(slot);
+ busElement.updateDevices(slot, getStackInSlot(slot));
}
}
diff --git a/src/main/java/li/cil/oc2/common/init/Providers.java b/src/main/java/li/cil/oc2/common/init/Providers.java
index 79c049f8..ff8ce42c 100644
--- a/src/main/java/li/cil/oc2/common/init/Providers.java
+++ b/src/main/java/li/cil/oc2/common/init/Providers.java
@@ -1,7 +1,8 @@
package li.cil.oc2.common.init;
import li.cil.oc2.api.API;
-import li.cil.oc2.api.bus.device.provider.DeviceProvider;
+import li.cil.oc2.api.bus.device.provider.BlockDeviceProvider;
+import li.cil.oc2.api.bus.device.provider.ItemDeviceProvider;
import li.cil.oc2.common.bus.device.provider.*;
import net.minecraftforge.fml.javafmlmod.FMLJavaModLoadingContext;
import net.minecraftforge.registries.DeferredRegister;
@@ -11,25 +12,28 @@ import net.minecraftforge.registries.RegistryBuilder;
import java.util.function.Supplier;
public final class Providers {
- private static final DeferredRegister PROVIDERS = DeferredRegister.create(DeviceProvider.class, API.MOD_ID);
+ private static final DeferredRegister BLOCK_DEVICE_PROVIDERS = DeferredRegister.create(BlockDeviceProvider.class, API.MOD_ID);
+ private static final DeferredRegister ITEM_DEVICE_PROVIDERS = DeferredRegister.create(ItemDeviceProvider.class, API.MOD_ID);
///////////////////////////////////////////////////////////////////
- public static final Supplier> PROVIDERS_REGISTRY = PROVIDERS.makeRegistry("device_providers", RegistryBuilder::new);
+ public static final Supplier> BLOCK_DEVICE_PROVIDER_REGISTRY = BLOCK_DEVICE_PROVIDERS.makeRegistry("block_device_providers", RegistryBuilder::new);
+ public static final Supplier> ITEM_DEVICE_PROVIDER_REGISTRY = ITEM_DEVICE_PROVIDERS.makeRegistry("item_device_providers", RegistryBuilder::new);
///////////////////////////////////////////////////////////////////
public static void initialize() {
- PROVIDERS.register("block", BlockDeviceProvider::new);
- PROVIDERS.register("tile_entity", TileEntityDeviceProvider::new);
+ BLOCK_DEVICE_PROVIDERS.register("block", BlockStateDeviceProvider::new);
+ BLOCK_DEVICE_PROVIDERS.register("tile_entity", TileEntityDeviceProvider::new);
- PROVIDERS.register("energy_storage", EnergyStorageDeviceProvider::new);
- PROVIDERS.register("fluid_handler", FluidHandlerDeviceProvider::new);
- PROVIDERS.register("item_handler", ItemHandlerDeviceProvider::new);
+ BLOCK_DEVICE_PROVIDERS.register("energy_storage", EnergyStorageBlockDeviceProvider::new);
+ BLOCK_DEVICE_PROVIDERS.register("fluid_handler", FluidHandlerBlockDeviceProvider::new);
+ BLOCK_DEVICE_PROVIDERS.register("item_handler", ItemHandlerBlockDeviceProvider::new);
- PROVIDERS.register("item_memory", MemoryItemDeviceProvider::new);
- PROVIDERS.register("item_hard_drive", HardDriveItemDeviceProvider::new);
+ ITEM_DEVICE_PROVIDERS.register("item_memory", MemoryItemDeviceProvider::new);
+ ITEM_DEVICE_PROVIDERS.register("item_hard_drive", HardDriveItemDeviceProvider::new);
- PROVIDERS.register(FMLJavaModLoadingContext.get().getModEventBus());
+ BLOCK_DEVICE_PROVIDERS.register(FMLJavaModLoadingContext.get().getModEventBus());
+ ITEM_DEVICE_PROVIDERS.register(FMLJavaModLoadingContext.get().getModEventBus());
}
}
diff --git a/src/main/java/li/cil/oc2/common/network/Network.java b/src/main/java/li/cil/oc2/common/network/Network.java
index 43e5ebf3..119a1d54 100644
--- a/src/main/java/li/cil/oc2/common/network/Network.java
+++ b/src/main/java/li/cil/oc2/common/network/Network.java
@@ -22,6 +22,8 @@ public final class Network {
PROTOCOL_VERSION::equals
);
+ ///////////////////////////////////////////////////////////////////
+
private static int nextPacketId = 1;
///////////////////////////////////////////////////////////////////
diff --git a/src/main/java/li/cil/oc2/common/network/message/AbstractTerminalBlockMessage.java b/src/main/java/li/cil/oc2/common/network/message/AbstractTerminalBlockMessage.java
index 429b273b..5f7cd72d 100644
--- a/src/main/java/li/cil/oc2/common/network/message/AbstractTerminalBlockMessage.java
+++ b/src/main/java/li/cil/oc2/common/network/message/AbstractTerminalBlockMessage.java
@@ -21,6 +21,8 @@ public abstract class AbstractTerminalBlockMessage {
fromBytes(buffer);
}
+ ///////////////////////////////////////////////////////////////////
+
public void fromBytes(final PacketBuffer buffer) {
pos = buffer.readBlockPos();
data = buffer.readByteArray();
diff --git a/src/main/java/li/cil/oc2/common/network/message/ComputerBusStateMessage.java b/src/main/java/li/cil/oc2/common/network/message/ComputerBusStateMessage.java
index 52ea2282..54e0aa14 100644
--- a/src/main/java/li/cil/oc2/common/network/message/ComputerBusStateMessage.java
+++ b/src/main/java/li/cil/oc2/common/network/message/ComputerBusStateMessage.java
@@ -24,6 +24,8 @@ public class ComputerBusStateMessage {
fromBytes(buffer);
}
+ ///////////////////////////////////////////////////////////////////
+
public static boolean handleMessage(final ComputerBusStateMessage message, final Supplier context) {
context.get().enqueueWork(() -> MessageUtils.withClientTileEntityAt(message.pos, ComputerTileEntity.class,
(tileEntity) -> tileEntity.setBusStateClient(message.busState)));
diff --git a/src/main/java/li/cil/oc2/common/network/message/ComputerRunStateMessage.java b/src/main/java/li/cil/oc2/common/network/message/ComputerRunStateMessage.java
index fbd77f74..47fe6129 100644
--- a/src/main/java/li/cil/oc2/common/network/message/ComputerRunStateMessage.java
+++ b/src/main/java/li/cil/oc2/common/network/message/ComputerRunStateMessage.java
@@ -23,6 +23,8 @@ public class ComputerRunStateMessage {
fromBytes(buffer);
}
+ ///////////////////////////////////////////////////////////////////
+
public static boolean handleMessage(final ComputerRunStateMessage message, final Supplier context) {
context.get().enqueueWork(() -> MessageUtils.withClientTileEntityAt(message.pos, ComputerTileEntity.class,
(tileEntity) -> tileEntity.setRunStateClient(message.runState)));
diff --git a/src/main/java/li/cil/oc2/common/network/message/TerminalBlockInputMessage.java b/src/main/java/li/cil/oc2/common/network/message/TerminalBlockInputMessage.java
index 3f155a1f..7ffa8948 100644
--- a/src/main/java/li/cil/oc2/common/network/message/TerminalBlockInputMessage.java
+++ b/src/main/java/li/cil/oc2/common/network/message/TerminalBlockInputMessage.java
@@ -17,6 +17,8 @@ public final class TerminalBlockInputMessage extends AbstractTerminalBlockMessag
super(buffer);
}
+ ///////////////////////////////////////////////////////////////////
+
public static boolean handleMessage(final AbstractTerminalBlockMessage message, final Supplier context) {
context.get().enqueueWork(() -> MessageUtils.withServerTileEntityAt(context, message.pos, ComputerTileEntity.class,
(tileEntity) -> tileEntity.getTerminal().putInput(ByteBuffer.wrap(message.data))));
diff --git a/src/main/java/li/cil/oc2/common/network/message/TerminalBlockOutputMessage.java b/src/main/java/li/cil/oc2/common/network/message/TerminalBlockOutputMessage.java
index 6612e163..73477cdd 100644
--- a/src/main/java/li/cil/oc2/common/network/message/TerminalBlockOutputMessage.java
+++ b/src/main/java/li/cil/oc2/common/network/message/TerminalBlockOutputMessage.java
@@ -17,6 +17,8 @@ public final class TerminalBlockOutputMessage extends AbstractTerminalBlockMessa
super(buffer);
}
+ ///////////////////////////////////////////////////////////////////
+
public static boolean handleMessage(final AbstractTerminalBlockMessage message, final Supplier context) {
context.get().enqueueWork(() -> MessageUtils.withClientTileEntityAt(message.pos, ComputerTileEntity.class,
tileEntity -> tileEntity.getTerminal().putOutput(ByteBuffer.wrap(message.data))));
diff --git a/src/main/java/li/cil/oc2/common/util/HorizontalBlockUtils.java b/src/main/java/li/cil/oc2/common/util/HorizontalBlockUtils.java
index 496d625b..64676f72 100644
--- a/src/main/java/li/cil/oc2/common/util/HorizontalBlockUtils.java
+++ b/src/main/java/li/cil/oc2/common/util/HorizontalBlockUtils.java
@@ -9,6 +9,8 @@ import javax.annotation.Nullable;
public final class HorizontalBlockUtils {
public static final int HORIZONTAL_DIRECTION_COUNT = 4;
+ ///////////////////////////////////////////////////////////////////
+
@Nullable
public static Direction toLocal(final BlockState blockState, @Nullable final Direction direction) {
if (direction == null) {
diff --git a/src/main/java/li/cil/oc2/common/util/ItemDeviceUtils.java b/src/main/java/li/cil/oc2/common/util/ItemDeviceUtils.java
new file mode 100644
index 00000000..7dcf0a55
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/util/ItemDeviceUtils.java
@@ -0,0 +1,49 @@
+package li.cil.oc2.common.util;
+
+import net.minecraft.item.ItemStack;
+import net.minecraft.nbt.CompoundNBT;
+import net.minecraft.util.ResourceLocation;
+import net.minecraftforge.registries.IForgeRegistryEntry;
+
+import javax.annotation.Nullable;
+import java.util.Optional;
+
+public final class ItemDeviceUtils {
+ private static final String ITEM_DEVICE_DATA_NBT_TAG_NAME = "item_device";
+
+ ///////////////////////////////////////////////////////////////////
+
+ public static Optional getItemDeviceData(final ItemStack stack) {
+ if (stack.isEmpty()) {
+ return Optional.empty();
+ }
+
+ final CompoundNBT nbt = ItemStackUtils.getModDataTag(stack);
+ if (nbt == null) {
+ return Optional.empty();
+ }
+
+ return Optional.of(nbt.getCompound(ITEM_DEVICE_DATA_NBT_TAG_NAME));
+ }
+
+ public static void setItemDeviceData(final ItemStack stack, final CompoundNBT data) {
+ if (data.isEmpty()) {
+ return;
+ }
+
+ ItemStackUtils.getOrCreateModDataTag(stack).put(ITEM_DEVICE_DATA_NBT_TAG_NAME, data);
+ }
+
+ public static Optional getItemDeviceDataKey(@Nullable final IForgeRegistryEntry> provider) {
+ if (provider == null) {
+ return Optional.empty();
+ }
+
+ final ResourceLocation providerName = provider.getRegistryName();
+ if (providerName == null) {
+ return Optional.empty();
+ }
+
+ return Optional.of(providerName.toString());
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/util/ItemStackUtils.java b/src/main/java/li/cil/oc2/common/util/ItemStackUtils.java
new file mode 100644
index 00000000..b4aa5c70
--- /dev/null
+++ b/src/main/java/li/cil/oc2/common/util/ItemStackUtils.java
@@ -0,0 +1,26 @@
+package li.cil.oc2.common.util;
+
+import li.cil.oc2.api.API;
+import net.minecraft.item.ItemStack;
+import net.minecraft.nbt.CompoundNBT;
+
+import javax.annotation.Nullable;
+
+public final class ItemStackUtils {
+ @Nullable
+ public static CompoundNBT getModDataTag(final ItemStack stack) {
+ if (stack.isEmpty()) {
+ return null;
+ }
+
+ return stack.getChildTag(API.MOD_ID);
+ }
+
+ public static CompoundNBT getOrCreateModDataTag(final ItemStack stack) {
+ if (stack.isEmpty()) {
+ throw new IllegalArgumentException();
+ }
+
+ return stack.getOrCreateChildTag(API.MOD_ID);
+ }
+}
diff --git a/src/main/java/li/cil/oc2/common/vm/ManagedInterruptAllocator.java b/src/main/java/li/cil/oc2/common/vm/ManagedInterruptAllocator.java
index 970441f7..473c522c 100644
--- a/src/main/java/li/cil/oc2/common/vm/ManagedInterruptAllocator.java
+++ b/src/main/java/li/cil/oc2/common/vm/ManagedInterruptAllocator.java
@@ -23,6 +23,8 @@ public final class ManagedInterruptAllocator implements InterruptAllocator {
this.interruptCount = interruptCount;
}
+ ///////////////////////////////////////////////////////////////////
+
public void freeze() {
isFrozen = true;
}
diff --git a/src/main/java/li/cil/oc2/common/vm/ManagedInterruptController.java b/src/main/java/li/cil/oc2/common/vm/ManagedInterruptController.java
index 1c9e3972..2845a3fa 100644
--- a/src/main/java/li/cil/oc2/common/vm/ManagedInterruptController.java
+++ b/src/main/java/li/cil/oc2/common/vm/ManagedInterruptController.java
@@ -15,6 +15,8 @@ public final class ManagedInterruptController implements InterruptController {
this.allocator = allocator;
}
+ ///////////////////////////////////////////////////////////////////
+
public void invalidate() {
isValid = false;
interruptController.lowerInterrupts(raisedInterrupts);
diff --git a/src/main/java/li/cil/oc2/common/vm/ManagedMemoryAllocator.java b/src/main/java/li/cil/oc2/common/vm/ManagedMemoryAllocator.java
index d7c7ae06..bbb1c221 100644
--- a/src/main/java/li/cil/oc2/common/vm/ManagedMemoryAllocator.java
+++ b/src/main/java/li/cil/oc2/common/vm/ManagedMemoryAllocator.java
@@ -9,6 +9,8 @@ public final class ManagedMemoryAllocator implements MemoryAllocator {
private final ArrayList claimedMemory = new ArrayList<>();
private boolean isFrozen;
+ ///////////////////////////////////////////////////////////////////
+
public void freeze() {
isFrozen = true;
}
diff --git a/src/main/java/li/cil/oc2/common/vm/ManagedMemoryMap.java b/src/main/java/li/cil/oc2/common/vm/ManagedMemoryMap.java
index b9a5e453..baad095f 100644
--- a/src/main/java/li/cil/oc2/common/vm/ManagedMemoryMap.java
+++ b/src/main/java/li/cil/oc2/common/vm/ManagedMemoryMap.java
@@ -18,6 +18,8 @@ final class ManagedMemoryMap implements MemoryMap {
this.memoryMap = memoryMap;
}
+ ///////////////////////////////////////////////////////////////////
+
@Override
public OptionalLong findFreeRange(final long start, final long end, final int size) {
return memoryMap.findFreeRange(start, end, size);
diff --git a/src/main/java/li/cil/oc2/common/vm/ManagedMemoryRangeAllocator.java b/src/main/java/li/cil/oc2/common/vm/ManagedMemoryRangeAllocator.java
index 65df3d00..b285d022 100644
--- a/src/main/java/li/cil/oc2/common/vm/ManagedMemoryRangeAllocator.java
+++ b/src/main/java/li/cil/oc2/common/vm/ManagedMemoryRangeAllocator.java
@@ -14,10 +14,14 @@ public final class ManagedMemoryRangeAllocator implements MemoryRangeAllocator {
private final ArrayList managedDevices = new ArrayList<>();
private boolean isFrozen;
+ ///////////////////////////////////////////////////////////////////
+
public ManagedMemoryRangeAllocator(final Board board) {
this.board = board;
}
+ ///////////////////////////////////////////////////////////////////
+
public void freeze() {
isFrozen = true;
}
diff --git a/src/main/java/li/cil/oc2/common/vm/ManagedVMContext.java b/src/main/java/li/cil/oc2/common/vm/ManagedVMContext.java
index a23dc072..6646e854 100644
--- a/src/main/java/li/cil/oc2/common/vm/ManagedVMContext.java
+++ b/src/main/java/li/cil/oc2/common/vm/ManagedVMContext.java
@@ -27,6 +27,8 @@ public final class ManagedVMContext implements VMContext {
this.memoryAllocator = new ManagedMemoryAllocator();
}
+ ///////////////////////////////////////////////////////////////////
+
public void freeze() {
memoryRangeAllocator.freeze();
interruptAllocator.freeze();
diff --git a/src/main/java/li/cil/oc2/common/vm/Terminal.java b/src/main/java/li/cil/oc2/common/vm/Terminal.java
index 1e138569..9ce6d1c2 100644
--- a/src/main/java/li/cil/oc2/common/vm/Terminal.java
+++ b/src/main/java/li/cil/oc2/common/vm/Terminal.java
@@ -57,12 +57,16 @@ public final class Terminal {
private static final byte DEFAULT_COLORS = COLOR_WHITE << COLOR_FOREGROUND_SHIFT;
private static final byte DEFAULT_STYLE = 0;
+ ///////////////////////////////////////////////////////////////////
+
public enum State { // Must be public for serialization.
NORMAL, // Currently reading characters normally.
ESCAPE, // Last character was ESC, figure out what kind next.
SEQUENCE, // Know what sequence we have, now parsing it.
}
+ ///////////////////////////////////////////////////////////////////
+
private final ByteArrayFIFOQueue input = new ByteArrayFIFOQueue(32);
private final byte[] buffer = new byte[WIDTH * HEIGHT];
private final byte[] colors = new byte[WIDTH * HEIGHT];
@@ -85,10 +89,14 @@ public final class Terminal {
private transient Object renderer;
private transient boolean displayOnly; // Set on client to not send responses to status requests.
+ ///////////////////////////////////////////////////////////////////
+
public Terminal() {
clear();
}
+ ///////////////////////////////////////////////////////////////////
+
public void setDisplayOnly(final boolean value) {
displayOnly = value;
}
@@ -331,6 +339,8 @@ public final class Terminal {
}
}
+ ///////////////////////////////////////////////////////////////////
+
private void selectStyle(final int sgr) {
switch (sgr) {
case 0: { // Reset / Normal
@@ -476,6 +486,8 @@ public final class Terminal {
dirty.set(-1);
}
+ ///////////////////////////////////////////////////////////////////
+
@OnlyIn(Dist.CLIENT)
private static final class Renderer {
private static final ResourceLocation LOCATION_FONT_TEXTURE = new ResourceLocation(API.MOD_ID, "textures/font/terminus.png");
@@ -506,15 +518,21 @@ public final class Terminal {
0x777777, // White
};
+ ///////////////////////////////////////////////////////////////
+
private final Terminal terminal;
private final Object[] lines = new Object[HEIGHT]; // Cached vertex buffers for rendering, untyped for server.
private Object lastMatrix; // Untyped for server.
+ ///////////////////////////////////////////////////////////////
+
public Renderer(final Terminal terminal) {
this.terminal = terminal;
}
+ ///////////////////////////////////////////////////////////////
+
public void render(final AtomicInteger dirty, final MatrixStack stack) {
validateLineCache(dirty, stack);
renderBuffer();
@@ -524,6 +542,8 @@ public final class Terminal {
}
}
+ ///////////////////////////////////////////////////////////////
+
private void renderBuffer() {
GlStateManager.depthMask(false);
Minecraft.getInstance().getTextureManager().bindTexture(LOCATION_FONT_TEXTURE);
diff --git a/src/main/java/li/cil/oc2/common/vm/VirtualMachine.java b/src/main/java/li/cil/oc2/common/vm/VirtualMachine.java
index 944c90aa..3c06a234 100644
--- a/src/main/java/li/cil/oc2/common/vm/VirtualMachine.java
+++ b/src/main/java/li/cil/oc2/common/vm/VirtualMachine.java
@@ -7,22 +7,12 @@ import li.cil.oc2.api.bus.device.vm.MemoryRangeAllocator;
import li.cil.oc2.api.bus.device.vm.VMContext;
import li.cil.oc2.common.bus.RPCAdapter;
import li.cil.sedna.api.device.InterruptController;
-import li.cil.sedna.buildroot.Buildroot;
-import li.cil.sedna.device.block.ByteBufferBlockDevice;
import li.cil.sedna.device.rtc.GoldfishRTC;
import li.cil.sedna.device.serial.UART16550A;
import li.cil.sedna.device.virtio.VirtIOConsoleDevice;
import li.cil.sedna.riscv.R5Board;
-import org.apache.logging.log4j.LogManager;
-import org.apache.logging.log4j.Logger;
-
-import java.io.IOException;
public final class VirtualMachine {
- private static final Logger LOGGER = LogManager.getLogger();
-
- ///////////////////////////////////////////////////////////////////
-
// We report a clock rate to the VM such that for the VM it looks as though
// passes as much faster as MC time passes faster than real time.
public static final int REPORTED_CPU_FREQUENCY = 700_000;
@@ -32,19 +22,6 @@ public final class VirtualMachine {
private static final int RTC_INTERRUPT = 0x2;
private static final int RPC_INTERRUPT = 0x3;
- private static final ByteBufferBlockDevice ROOT_FS;
-
- static {
- ByteBufferBlockDevice rootfs;
- try {
- rootfs = ByteBufferBlockDevice.createFromStream(Buildroot.getRootFilesystem(), true);
- } catch (final IOException e) {
- LOGGER.error(e);
- rootfs = ByteBufferBlockDevice.create(0, true);
- }
- ROOT_FS = rootfs;
- }
-
///////////////////////////////////////////////////////////////////
public final MinecraftRealTimeCounter rtc = new MinecraftRealTimeCounter();
@@ -92,6 +69,8 @@ public final class VirtualMachine {
board.setStandardOutputDevice(uart);
}
+ ///////////////////////////////////////////////////////////////////
+
public void reset() {
board.reset();
rpcAdapter.reset();
diff --git a/src/main/java/li/cil/oc2/common/vm/VirtualMachineDeviceBusAdapter.java b/src/main/java/li/cil/oc2/common/vm/VirtualMachineDeviceBusAdapter.java
index bf865370..107ac587 100644
--- a/src/main/java/li/cil/oc2/common/vm/VirtualMachineDeviceBusAdapter.java
+++ b/src/main/java/li/cil/oc2/common/vm/VirtualMachineDeviceBusAdapter.java
@@ -33,6 +33,8 @@ public final class VirtualMachineDeviceBusAdapter {
this.claimedInterrupts.set(0);
}
+ ///////////////////////////////////////////////////////////////////
+
public VMContext getGlobalContext() {
return globalContext;
}
diff --git a/src/main/java/li/cil/oc2/common/vm/VirtualMachineRunner.java b/src/main/java/li/cil/oc2/common/vm/VirtualMachineRunner.java
index d468ca49..929801e5 100644
--- a/src/main/java/li/cil/oc2/common/vm/VirtualMachineRunner.java
+++ b/src/main/java/li/cil/oc2/common/vm/VirtualMachineRunner.java
@@ -36,6 +36,8 @@ public class VirtualMachineRunner implements Runnable {
this.board = board;
}
+ ///////////////////////////////////////////////////////////////////
+
public void tick() {
cycleLimit += getCyclesPerTick();
if (timeQuotaInMillis.addAndGet(TIMESLICE_IN_MS) > 0 && lastSchedule == null || lastSchedule.isDone() || lastSchedule.isCancelled()) {