I would like to use deriveAutoReg but my type requires a KnownFoo superclass constraint e.g.:
data MsgConfig = MsgConfig
{ _msgChannelWidth :: Nat
}
type family MsgChannelWidth (cfg :: MsgConfig) :: Nat where
MsgChannelWidth ('MsgConfig x) = x
type KnownMsgConfig cfg = KnownNat (MsgChannelWidth cfg)
data Message (cfg :: MsgConfig) = Status
{ _msg_channel :: Unsigned (MsgChannelWidth cfg)
, _msg_data :: Vec 60 (Unsigned 8)
, _msg_chksum :: Unsigned 4
}
deriving (Bundle, Generic)
deriving instance (KnownMsgConfig cfg) => BitPack (Message cfg)
deriving instance (KnownMsgConfig cfg) => Eq (Message cfg)
deriving instance (KnownMsgConfig cfg) => NFDataX (Message cfg)
deriving instance (KnownMsgConfig cfg) => Show (Message cfg)
deriving instance (KnownMsgConfig cfg) => ShowX (Message cfg)
makeLenses ''Message
deriveAutoReg ''Message
As expected, I get an error:
• No instance for ‘KnownNat (MsgChannelWidth cfg)’
arising from the superclasses of an instance declaration
• In the instance declaration for ‘AutoReg (Message cfg)’
|
597 | deriveAutoReg ''Message
| ^^^^^^^^^^^^^^^^^^^^^^^
My guess is that since this is a macro there is no simple way of adding the superclass constraint.
I’m not [yet] familiar enough with template haskell to alter the macro implementation so until that time comes, is there an easy way to achieve what I want here?
For context, my goal is that when Message ends up in a register (well, autoReg), I get a register for each field instead of a single large register. My real type has ~45 fields and I suspect the resulting ~1200 bit register is worsening synthesis results compared to the functionally equivalent original verilog implementation.