To make sure the messages in my message-queue are type-safe, I have to record the message type in each message.
This is how I went about it: proc idOfType*(T: typedesc): MsgTypeID {.inline.} = let tid = 0 # Accesses "type register here" ... MsgTypeID(tid) proc sendMsg*[T](q: QueueID, m: ptr Msg[T]): void {.inline.} = let typeidOfT {.global.} = idOfType(T) m.mybase.mytypeid = typeidOfT fillAndSendMsg[T](q, m, true) It looked like it worked, but then today I realised I was using a single type in the test messages, so I added a second type to my test, and then it failed. To get it to work again, I have to change the code to this: proc idOfType*(T: typedesc): MsgTypeID {.inline.} = let tid = 0 # Accesses "type register here" ... MsgTypeID(tid) proc sendMsg*[T](q: QueueID, m: ptr Msg[T]): void {.inline.} = let typeidOfT = idOfType(T) m.mybase.mytypeid = typeidOfT fillAndSendMsg[T](q, m, true) I was under the impressing that since sendMsg() is generic, the compiler would generate one typeidOfT _per type T_. Since my test is now failing with two types, I assume the compiler generates a single typeidOfT for all sendMsg() "instantiations". Is there a way to work around that? It's rather expensive to compute the ID of a type (it involves locks and creating shared heap objects), so I don't want to do that for each message, but rather only once for each type. I've also tried the following, which doesn't compile: proc sendMsg*[T](q: QueueID, m: ptr Msg[T]): void {.inline.} = static: let typeidOfT {.global.} = idOfType(T) m.mybase.mytypeid = typeidOfT fillAndSendMsg[T](q, m, true) proc sendMsg*[T](q: QueueID, m: ptr Msg[T]): void {.inline.} = static: const typeidOfT {.global.} = idOfType(T) m.mybase.mytypeid = typeidOfT fillAndSendMsg[T](q, m, true)