defmacro __using__(_) do
if !Module.get_attribute(__CALLER__.module, :generated) do
Module.register_attribute(__CALLER__.module, :generated, [])
Module.put_attribute(__CALLER__.module, :generated, true)
quote do
def test, do: IO.puts("test")
end
end
end
You can register attributes, and assign values on the fly. You can also choose what module you register them in. In your case it is the caller's module that you want to avoid double definitions in, so you register and assign value to the attribute in that module. With the code above when module D gets to expand use C (it already ran use B) the attribute will already be on D and you can safely skip A's generated content.