Thread overview
undefined reference to `_D15TypeInfo_Struct6__vtblZ'
Dec 23, 2013
Mike
Dec 23, 2013
Johannes Pfau
Dec 23, 2013
Mike
Dec 23, 2013
Mike
December 23, 2013
Thanks for all the help lately.  I'm sorry to be flooding this list with so many questions, but I'm making good progress, and still running into some things I don't quite understand.

I'm getting the following linker error as soon as I add a struct to my code.

undefined reference to `_D15TypeInfo_Struct6__vtblZ'

I'm guessing this is because GDC is not generating the vtbl for my TypeInfo_Struct class.

Is this because I'm missing something in my runtime implementation, or could this be a code generation bug?

I ran objdump on my object file, and this symbmol did not appear.

I'm using GDC 4.8 arm-none-eabi:

(compile) arm-none-eabi-gdc -mthumb -mcpu=cortex-m4 -fno-emit-moduleinfo -ffunction-sections -fdata-sections -c   start.d -o start.o

(link) arm-none-eabi-ld -T link.ld start.o -o start.elf


I've reduce my code quite a bit to the following, just to make the problem reproducible:

*********
start.d
*********
alias void function() ISR;
extern(C) immutable ISR[1] ISRVectorTable =
[
    &OnReset
];

void OnReset()
{
  while(true)
  { }
}

**********
object.d
**********
module object;

alias uint               size_t;
alias immutable(char)[]  string;

class Object
{}

class TypeInfo
{}

class TypeInfo_Struct : TypeInfo
{
    string name;
    void[] m_init;      // initializer; init.ptr == null if 0 initialize

    @safe pure nothrow
    {
	size_t   function(in void*)           xtoHash;
	bool     function(in void*, in void*) xopEquals;
	int      function(in void*, in void*) xopCmp;
	char[]   function(in void*)           xtoString;

	enum StructFlags : uint
	{
	    hasPointers = 0x1,
	}
	StructFlags m_flags;
    }
    void function(void*)                    xdtor;
    void function(void*)                    xpostblit;

    uint m_align;
    immutable(void)* m_RTInfo;                // data for precise GC
}

***************
Linker Script
***************
MEMORY
{
  CCRAM    (rxw) : ORIGIN = 0x10000000, LENGTH =   64k
  SRAM     (rxw) : ORIGIN = 0x20000000, LENGTH =  128k
  FLASH    (rx)  : ORIGIN = 0x08000000, LENGTH = 1024k
}

_stackStart = ORIGIN(CCRAM) + LENGTH(CCRAM);

SECTIONS
{
    /* Don't need exception stuff right now */
    /DISCARD/ :
    {
	*(.ARM.extab*)
	*(.ARM.exidx*)
    }

    .text :
    {
	LONG(_stackStart);            /* Initial stack pointer */
	KEEP(*(*.ISRVectorTable))     /* Interrupt vector table */
	
	. = ALIGN(4);
	/* the code */
	*(.text)
	*(.text*)
	
	/* for "hello\r\n" string constant */
	. = ALIGN(4);
	*(.rodata)
	*(.rodata*)

	. = ALIGN(4);
	dataRomStart = .;
    } >FLASH

    .data : AT (dataRomStart)
    {
	. = ALIGN(4);
	dataRamStart = .;
	
	. = ALIGN(4);
	*(.data)
	*(.data*)

	. = ALIGN(4);
	dataRamEnd = .;
    } >SRAM

    .bss :
    {
	. = ALIGN(4);
        bssStart = .;

        *(.bss)
        *(.bss*)

	. = ALIGN(4);
	bssEnd = .;
    } >SRAM
}
December 23, 2013
Am Mon, 23 Dec 2013 12:03:09 +0000
schrieb "Mike" <none@none.com>:

> Thanks for all the help lately.  I'm sorry to be flooding this list with so many questions, but I'm making good progress, and still running into some things I don't quite understand.
> 
> I'm getting the following linker error as soon as I add a struct to my code.
> 
> undefined reference to `_D15TypeInfo_Struct6__vtblZ'
> 

It looks like you didn't compile object.d? The vtblZ symbols are only generated when you compile a .d file and then you have to link in the resulting object file, importing alone is not enough.

So something like
arm-eabi-gdc object.d -o object.o
link object.o start.o -o start

December 23, 2013
On Monday, 23 December 2013 at 12:57:33 UTC, Johannes Pfau wrote:
> Am Mon, 23 Dec 2013 12:03:09 +0000
> schrieb "Mike" <none@none.com>:
>
>> Thanks for all the help lately.  I'm sorry to be flooding this list with so many questions, but I'm making good progress, and still running into some things I don't quite understand.
>> 
>> I'm getting the following linker error as soon as I add a struct to my code.
>> 
>> undefined reference to `_D15TypeInfo_Struct6__vtblZ'
>> 
>
> It looks like you didn't compile object.d? The vtblZ symbols are only
> generated when you compile a .d file and then you have to link in the
> resulting object file, importing alone is not enough.
>
> So something like
> arm-eabi-gdc object.d -o object.o
> link object.o start.o -o start

Thanks johannes.  I already tried just as you suggested, but when I tried it, I ended up with multiple definitions as shown below.  This is why I assumed it was compiled automatically

start.o:(.rodata._D6Object6__initZ+0x0): multiple definition of `_D6Object6__initZ'
object.o:(.rodata._D6Object6__initZ+0x0): first defined here
start.o:(.rodata._D6Object6__vtblZ+0x0): multiple definition of `_D6Object6__vtblZ'
object.o:(.rodata._D6Object6__vtblZ+0x0): first defined here
start.o:(.data._D6Object7__ClassZ+0x0): multiple definition of `_D6Object7__ClassZ'
object.o:(.data._D6Object7__ClassZ+0x0): first defined here
start.o:(.rodata._D14TypeInfo_Class6__vtblZ+0x0): multiple definition of `_D14TypeInfo_Class6__vtblZ'
object.o:(.rodata._D14TypeInfo_Class6__vtblZ+0x0): first defined here


So I'm quite confused.  Do I need and object.di file instead? Is there something to naming "object_.d" (trailing underscore) instead of "object.d"?
December 23, 2013
On Monday, 23 December 2013 at 13:19:21 UTC, Mike wrote:
> On Monday, 23 December 2013 at 12:57:33 UTC, Johannes Pfau wrote:
>> Am Mon, 23 Dec 2013 12:03:09 +0000
>> schrieb "Mike" <none@none.com>:
>>
>>> Thanks for all the help lately.  I'm sorry to be flooding this list with so many questions, but I'm making good progress, and still running into some things I don't quite understand.
>>> 
>>> I'm getting the following linker error as soon as I add a struct to my code.
>>> 
>>> undefined reference to `_D15TypeInfo_Struct6__vtblZ'
>>> 
>>
>> It looks like you didn't compile object.d? The vtblZ symbols are only
>> generated when you compile a .d file and then you have to link in the
>> resulting object file, importing alone is not enough.
>>
>> So something like
>> arm-eabi-gdc object.d -o object.o
>> link object.o start.o -o start
>
> Thanks johannes.  I already tried just as you suggested, but when I tried it, I ended up with multiple definitions as shown below.  This is why I assumed it was compiled automatically
>
> start.o:(.rodata._D6Object6__initZ+0x0): multiple definition of `_D6Object6__initZ'
> object.o:(.rodata._D6Object6__initZ+0x0): first defined here
> start.o:(.rodata._D6Object6__vtblZ+0x0): multiple definition of `_D6Object6__vtblZ'
> object.o:(.rodata._D6Object6__vtblZ+0x0): first defined here
> start.o:(.data._D6Object7__ClassZ+0x0): multiple definition of `_D6Object7__ClassZ'
> object.o:(.data._D6Object7__ClassZ+0x0): first defined here
> start.o:(.rodata._D14TypeInfo_Class6__vtblZ+0x0): multiple definition of `_D14TypeInfo_Class6__vtblZ'
> object.o:(.rodata._D14TypeInfo_Class6__vtblZ+0x0): first defined here
>
>
> So I'm quite confused.  Do I need and object.di file instead? Is there something to naming "object_.d" (trailing underscore) instead of "object.d"?

Cancel that.  I had a makefile typo.  My mistake.  You are correct.