www.digitalmars.com         C & C++   DMDScript  

digitalmars.D.bugs - [Issue 311] New: Object files missing certain template instantiations

reply d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=311

           Summary: Object files missing certain template instantiations
           Product: D
           Version: 0.165
          Platform: PC
        OS/Version: Linux
            Status: NEW
          Keywords: link-failure
          Severity: major
          Priority: P2
         Component: DMD
        AssignedTo: bugzilla digitalmars.com
        ReportedBy: oskar.linde gmail.com


This is a very old infamous linking error that only appears when compiling the
modules separately on DMD, and always on GDC (that only supports one module at
a time compilation).

The smallest example I have found that triggers the bug is a three module
import chain a->b->c, where b instantiates a template in c, and the template in
c instantiates another template in c. The code for this other template never
gets written to any object file.

The workaround is to add an import c; in a.

---------- a.d ---------
import b;
//import c;

void main() { func(); }
---------- b.d ---------
import c;

void func()() { C(); }
---------- c.d ---------
void C(T=int)() { C!(double)(); }
------------------------

$ dmd -c a.d
$ dmd -c b.d
$ dmd -c c.d
$ dmd a.o b.o c.o
a.o: In function `_D1c8__T1CTiZ1CFZv':
a.d:(.gnu.linkonce.t_D1c8__T1CTiZ1CFZv+0x4): undefined reference to
`_D1c8__T1CTdZ1CFZv'

$ gdc a.d b.d c.d
/tmp/ccWsXe5T.o: In function `_D1c8__T1CTiZ1CFZv':
a.d:(.gnu.linkonce.t._D1c8__T1CTiZ1CFZv[_D1c8__T1CTiZ1CFZv]+0x7): undefined
reference to `_D1c8__T1CTdZ1CFZv'

$ dmd a.d b.d c.d
No error

Uncommenting the import c; in a.d makes the error go away.

I've not had the chance to verify this on any other platform than Linux.
DMD version 0.165 and GDC 0.17 was used.

/Oskar


-- 
Aug 26 2006
next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=311


deewiant gmail.com changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
         OS/Version|Linux                       |All




------- Comment #1 from deewiant gmail.com  2006-08-26 06:07 -------
Verified to occur on Windows as well.


-- 
Aug 26 2006
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=311


bugzilla digitalmars.com changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|NEW                         |RESOLVED
         Resolution|                            |FIXED




------- Comment #2 from bugzilla digitalmars.com  2006-09-19 15:27 -------
Fixed in DMC 0.167.


-- 
Sep 19 2006
prev sibling next sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=311


kirklin.mcdonald gmail.com changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|RESOLVED                    |REOPENED
         Resolution|FIXED                       |




------- Comment #3 from kirklin.mcdonald gmail.com  2006-10-08 17:57 -------
Though DMD 0.167 did fix the case in the original bug report, this bug can
still manifest in more complex cases.

In the following example, we have a small "library" consisting of four modules,
and a piece of "client" code that imports the library and uses it.

The library has a diamond-shaped layout: "lib" imports a and b, which both
import "back".

[test.d]
import lib;

void main() {
    func_a("Hello".dup");
    func_b(34);
}

[lib.d]
public import a;
public import b;

[a.d]
private import std.stdio;
private import back;

void func_a(T) (T t) {
    writef("func_a: ");
    backend_func(t);
}

[b.d]
private import std.stdio;
private import back;

void func_b(T) (T t) {
    writef("func_b: ");
    backend_func(t);
}

[back.d]
private import std.stdio;

void backend_func(T) (T t) {
    writefln(t);
}

When compiled on Windows with DMD 0.169, we get:

dmd -c test.d
dmd -c a.d
dmd -c b.d
dmd -c back.d
dmd -c lib.d
dmd test.obj a.obj b.obj back.obj lib.obj

OPTLINK (R) for Win32 Release 7.50B1 Copyright (C) Digital Mars 1989 - 2001 All Rights Reserved test.obj(test) Error 42: Symbol Undefined __arguments_Aa test.obj(test) Error 42: Symbol Undefined __arguments_i --- errorlevel 2 Roughly equivalent (though more verbose) errors occur on Linux. The code works fine on either platform when compiled all at once: $ dmd test a b back lib gcc test.o a.o b.o back.o lib.o -o test -m32 -lphobos -lpthread -lm $ ./test func_a: Hello func_b: 34 It is interesting to compare sizes of the object files generated by the two methods. This is on Linux with DMD 0.169: Compiled all at once: Size Name 2420 a.o 2408 b.o 2248 back.o 1204 lib.o 2828 test.o Compiled one by one: Size Name 1716 a.o 1716 b.o 1700 back.o 1204 lib.o 3496 test.o --
Oct 08 2006
prev sibling parent d-bugmail puremagic.com writes:
http://d.puremagic.com/issues/show_bug.cgi?id=311


bugzilla digitalmars.com changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|REOPENED                    |RESOLVED
         Resolution|                            |FIXED




------- Comment #4 from bugzilla digitalmars.com  2006-11-25 03:26 -------
Fixed DMD 0.175


-- 
Nov 25 2006