Value instances and types implementing business logic w/o parsing anything.
In my KSY-spec I need to support different types of data coming from some IoT-devices and in most cases that data is simply distinguished by some byte: E.g. `0` is an unsigned byte of 8 bits, `1` is a binary-coded decimal of 2 digits etc. But in some cases the devices providing the data are known to contain firmware errors influencing how the data is provided, e.g. it might contain wrongly flipped bits. I have things like manufacturer of a device, its firmware revision and some addressing infos available to distinguish the devices from one another and map broken data to internally used data types to handle them specially later.

The problem is that distinguishing the devices with broken firmwares sometimes is not as easy as only checking the manufacturer and firmware revision, but I need to hard-code a list of serial numbers to check against sometimes and those can easily be some dozen or even hundreds of devices. To improve readability of those checks, I'm trying to implement some concept of types not parsing anything at all, because all necessary infos are available already, and instead only provide special checks using value instances.

The end result simply is something like `get_checker_for_bug_xy.is_affected`, where `is_affected` maps to a lot of hard-coded checks. While this is most likely not what KS has been designed for, it's simply possible in my case and with doing so I would benefit of the same KSY being usable in all supported target languages. I already need to support two languages myself and using parsing instances things seem to work:

    # fmt_oms_apl_data:
    instances:
      dummy:
        pos:  _io.pos
        type: fmt_oms_apl_data_date_g_meh(_root, fmt_oms_dll_device_type::heat_meter_outlet.to_i, fmt_oms_dll_device_type::water_meter.to_i)

`fmt_oms_apl_data_date_g_meh` is the checking type designed to not parse anything at all, but simply provide value instances checking things based on the given data. That translates to the following Java:

        private FmtOmsAplDataDateGMeh dummy;
        public FmtOmsAplDataDateGMeh dummy() {
            if (this.dummy != null)
                return this.dummy;
            long _pos = this._io.pos();
            this._io.seek(_io().pos());
            this.dummy = new FmtOmsAplDataDateGMeh(this._io, _root, FmtRecOms.FmtOmsDllDeviceType.HEAT_METER_OUTLET.id(), FmtRecOms.FmtOmsDllDeviceType.WATER_METER.id());
            this._io.seek(_pos);
            return this.dummy;
        }

As I don't need any parsing, I thought of misusing value instances and that doesn't work. The following KSY...

      dummy2:
        value: fmt_oms_apl_data_date_g_meh(_root, fmt_oms_dll_device_type::heat_meter_outlet.to_i, fmt_oms_dll_device_type::water_meter.to_i)

...results in the following exception:

	Exception in thread "main" scala.MatchError: Name(identifier(fmt_oms_apl_data_date_g_meh)) (of class io.kaitai.struct.exprlang.Ast$expr$Name)
		at io.kaitai.struct.translators.TypeDetector.detectTypeRaw(TypeDetector.scala:165)
		at io.kaitai.struct.translators.TypeDetector.detectType(TypeDetector.scala:25)
		at io.kaitai.struct.precompile.ValueTypesDeriver.$anonfun$deriveValueType$2(ValueTypesDeriver.scala:27)
		at io.kaitai.struct.precompile.ValueTypesDeriver.$anonfun$deriveValueType$2$adapted(ValueTypesDeriver.scala:20)
		at scala.collection.immutable.HashMap$HashMap1.foreach(HashMap.scala:231)
		at scala.collection.immutable.HashMap$HashTrieMap.foreach(HashMap.scala:462)
		at io.kaitai.struct.precompile.ValueTypesDeriver.deriveValueType(ValueTypesDeriver.scala:20)
		at io.kaitai.struct.precompile.ValueTypesDeriver.$anonfun$deriveValueType$5(ValueTypesDeriver.scala:50)
		at io.kaitai.struct.precompile.ValueTypesDeriver.$anonfun$deriveValueType$5$adapted(ValueTypesDeriver.scala:48)
		at scala.collection.immutable.HashMap$HashMap1.foreach(HashMap.scala:231)
		at scala.collection.immutable.HashMap$HashTrieMap.foreach(HashMap.scala:462)
		at scala.collection.immutable.HashMap$HashTrieMap.foreach(HashMap.scala:462)
		at io.kaitai.struct.precompile.ValueTypesDeriver.deriveValueType(ValueTypesDeriver.scala:48)
		at io.kaitai.struct.precompile.ValueTypesDeriver.run(ValueTypesDeriver.scala:12)
		at io.kaitai.struct.precompile.SpecsValueTypeDerive.$anonfun$run$2(SpecsValueTypeDerive.scala:15)
		at io.kaitai.struct.precompile.SpecsValueTypeDerive.$anonfun$run$2$adapted(SpecsValueTypeDerive.scala:13)
		at scala.collection.mutable.HashMap.$anonfun$foreach$1(HashMap.scala:138)
		at scala.collection.mutable.HashTable.foreachEntry(HashTable.scala:236)
		at scala.collection.mutable.HashTable.foreachEntry$(HashTable.scala:229)
		at scala.collection.mutable.HashMap.foreachEntry(HashMap.scala:40)
		at scala.collection.mutable.HashMap.foreach(HashMap.scala:138)
		at io.kaitai.struct.precompile.SpecsValueTypeDerive.run(SpecsValueTypeDerive.scala:13)
		at io.kaitai.struct.Main$.precompile(Main.scala:38)
		at io.kaitai.struct.Main$.$anonfun$importAndPrecompile$3(Main.scala:28)
		at io.kaitai.struct.Main$.$anonfun$importAndPrecompile$3$adapted(Main.scala:27)
		at scala.collection.mutable.HashMap.$anonfun$foreach$1(HashMap.scala:138)
		at scala.collection.mutable.HashTable.foreachEntry(HashTable.scala:236)
		at scala.collection.mutable.HashTable.foreachEntry$(HashTable.scala:229)
		at scala.collection.mutable.HashMap.foreachEntry(HashMap.scala:40)
		at scala.collection.mutable.HashMap.foreach(HashMap.scala:138)
		at io.kaitai.struct.Main$.$anonfun$importAndPrecompile$1(Main.scala:27)
		at io.kaitai.struct.Main$.$anonfun$importAndPrecompile$1$adapted(Main.scala:24)
		at scala.util.Success.$anonfun$map$1(Try.scala:251)
		at scala.util.Success.map(Try.scala:209)
		at scala.concurrent.Future.$anonfun$map$1(Future.scala:289)
		at scala.concurrent.impl.Promise.liftedTree1$1(Promise.scala:29)
		at scala.concurrent.impl.Promise.$anonfun$transform$1(Promise.scala:29)
		at scala.concurrent.impl.CallbackRunnable.run(Promise.scala:60)
		at scala.concurrent.impl.ExecutionContextImpl$AdaptedForkJoinTask.exec(ExecutionContextImpl.scala:140)
		at java.util.concurrent.ForkJoinTask.doExec(ForkJoinTask.java:289)
		at java.util.concurrent.ForkJoinPool$WorkQueue.pollAndExecAll(ForkJoinPool.java:1021)
		at java.util.concurrent.ForkJoinPool$WorkQueue.execLocalTasks(ForkJoinPool.java:1046)
		at java.util.concurrent.ForkJoinPool$WorkQueue.runTask(ForkJoinPool.java:1058)
		at java.util.concurrent.ForkJoinPool.runWorker(ForkJoinPool.java:1692)
		at java.util.concurrent.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:157)

Am I doing something wrong with the `value`- instance? If not, do you think my use case is worth supporting? It looks like a classic `value`- instance to me in theory.

In my opinion my use case might even be related to a question I asked in the past already about designs of CTORs of types regarding implicit `_io`, `_root` and stuff compared to explicit `params`:

https://github.com/kaitai-io/kaitai_struct/issues/275#issuecomment-368820503

Using `params`  only, one could get rid of the `_io`-stuff in the checking types and not even parse by accident anymore, because there wouldn't be any data to parse from given using the CTORs.

What do you think?