Nim
                                
                                 Nim copied to clipboard
                                
                                    Nim copied to clipboard
                            
                            
                            
                        getImpl for closure iterator works unreliably
import macros
macro getClosureEnvType(iter: typed): untyped =
  # Returns type of closure iterator environment object
  # Here we expect the last argument of the iterator
  # to be the environment, which works _sometimes_
  let im = getImpl(iter)
  result = getType(im.params[^1])
  result = result[^1]
iterator foo() {.closure.} =
  # This is our iterator we want to get the type of environment of
  echo "hi"
# The following two lines look unrelated but commenting either of those
# will result in compilation failure :/
var p = foo
iterator dummy_iter() {.closure.} = discard
# The following line compiles only if both above two lines are present :/
type FooEnv = getClosureEnvType(foo)
$ nim -v
Nim Compiler Version 1.7.1 [Linux: amd64]
Compiled at 2022-05-22
Copyright (c) 2006-2022 by Andreas Rumpf
git hash: 63cca93ea9bcab3c1fea39ff3789fd3a656d2db2
active boot switches: -d:release
getImplTransformed seems to work.
import macros
macro getClosureEnvType(iter: typed): untyped =
  # Returns type of closure iterator environment object
  # Here we expect the last argument of the iterator
  # to be the environment, which works _sometimes_
  let im = getImplTransformed(iter)
  # echo im.treeRepr
  result = getType(im.params[^1])
  result = result[^1]
iterator foo*() {.closure.} =
  # This is our iterator we want to get the type of environment of
  echo "hi"
type FooEnv = getClosureEnvType(foo)
@xflywind indeed, thanks for the tip!
However it stops working as soon as the code is wrapped into a proc :(
import macros
macro getClosureEnvType(iter: typed): untyped =
  # Returns type of closure iterator environment object
  # Here we expect the last argument of the iterator
  # to be the environment, which works _sometimes_
  let im = getImplTransformed(iter)
  result = getType(im.params[^1])
  result = result[^1]
proc test() =
  iterator foo() {.closure.} =
    # This is our iterator we want to get the type of environment of
    echo "hi"
  # The following causes compilation failure
  type FooEnv = getClosureEnvType(foo)