Issue 2671 - Circular imports and static constructors in templates
Summary: Circular imports and static constructors in templates
Status: RESOLVED WORKSFORME
Alias: None
Product: D
Classification: Unclassified
Component: dmd (show other issues)
Version: D1 (retired)
Hardware: x86 Windows
: P2 critical
Assignee: No Owner
URL:
Keywords: rejects-valid
Depends on:
Blocks:
 
Reported: 2009-02-16 08:04 UTC by Max Samukha
Modified: 2014-03-01 00:36 UTC (History)
3 users (show)

See Also:


Attachments

Note You need to log in before you can comment on or make changes to this issue.
Description Max Samukha 2009-02-16 08:04:33 UTC
Static constructor in a template belongs to the module declaring the template, not the module where the template is instantiated (for template instances that are not mixed-in). The following works and that's cool:

----
module a;
template Foo(int i)
{
  static this()
  {
  }
}

----
module b;
import a;
alias Foo!(1) foo;

----
module c;
import a;
alias Foo!(1) foo;

----

But if we have two separate instances, the example fails with  
'Error: circular initialization dependency with module b'

----
module b;
import a;
alias Foo!(1) foo;

----
module c;
import a;
alias Foo!(2) foo;

----

If there is another way to emulate static constructors in circularly imported modules (not by manually calling an initialization function), please share.
Comment 1 Justin 2009-07-13 15:50:43 UTC
I can confirm this as I ran across it while working on a large project. In my case, I use a template mixin to add a static constructor with some special behavior to various classes sprinkled around various modules. The project builds but gives me an error when I try running:
----------------
Error: circular initialization dependency with module epic.window
----------------

This is a pretty major hitch in my project, so I'd love to see this fixed or at least a workaround.
Comment 2 Walter Bright 2010-03-10 03:12:13 UTC
I cannot reproduce this on either D1.057 or D2.041.
------ a.d -------
module a;
template Foo(int i)
{
  static this()
  {
  }
}

void main() { }
----- b.d --------
module b;
import a;
alias Foo!(1) foo;
----- c.d --------
module c;
import a;
alias Foo!(2) foo;
------------------
dmd -c a
dmd -c b
dmd -c c
dmd a.obj b.obj c.obj
a
------ this works too ----
dmd a b c
a
-----------------------