Hi there,
I have something like:
import std/macros
template someTemplate(body: untyped) =
macro someInnerMacro(innerBody: untyped) {.inject.} =
newCall(ident"echo", newLit(innerBody.repr))
body
proc test[T](x: T) =
someTemplate:
someInnerMacro y
test 1
which fails with:
Error: undeclared identifier: 'y'
this seems to only happen if the proc is generic, the template has an inner template/macro and the body of the template isnt semantically correct.
So this works:
proc test(x: int) =
someTemplate:
someInnerMacro y
and this works:
proc test[T](x: T) =
someTemplate:
someInnerMacro x
so this seems to me like a bug, but maybe Im missing something and this is expected behavior
Generics with macros can cause some very odd issues, simply due to how generics work. What is happening here is that the compiler sees the macro is untyped and attempts to expand it in the declaration resulting in an incorrect behaviour, we can hack around this by giving the template a typed parameter we disregard:
import std/macros
type MyTemplater = distinct void
template someTemplate(_: typedesc[MyTemplater], body: untyped) =
macro someInnerMacro(innerBody: untyped) {.inject.} =
newCall(ident"echo", newLit(innerBody.repr))
body
proc test[T](x: T) =
someTemplate(MyTemplater):
someInnerMacro y
test 1
Here is a nice one:
This doesn't compile
proc foo*(s:openarray): auto =
discard
# Error: invalid type: 'T' in this context: 'proc (s: openArray): untyped'
This compiles:
proc foo*(s:openarray, N: static[int] = 0): auto =
discard