Should betterC modules and programs be able to use the modules under core.stdc? I certainly expected they should, or at least for many modules.
The specific issue I ran in to was with varargs routines, and making use of core.stdc.stdarg, where I had to link with phobos.
$ cat stdarg1.d
import core.stdc.stdarg;
pragma(printf)
public extern(C) int wrap_printf(scope const char* f, ...) {
import core.stdc.stdio;
va_list ap;
va_start(ap, f);
auto rc = vprintf(f, ap);
va_end(ap);
return rc;
}
extern(C) void main() {
wrap_printf("Foo\n");
}
$ dmd -betterC stdarg1.d
/usr/bin/ld: stdarg1.o: in function `wrap_printf':
stdarg1.d:(.text.wrap_printf[wrap_printf]+0xce): undefined reference to `_D4core4stdc6stdarg6va_endFNbNiPSQBf8internal6vararg8sysv_x6413__va_list_tagZv'
collect2: error: ld returned 1 exit status
Error: undefined reference to `nothrow @nogc void core.stdc.stdarg.va_end(core.internal.vararg.sysv_x64.__va_list_tag*)`
referenced from `wrap_printf`
perhaps `.d` files need to be added on the command line, or use `-i` to compile imports
Error: linker exited with status 1
cc stdarg1.o -o stdarg1 -m64 -Xlinker --export-dynamic -L/usr/lib/x86_64-linux-gnu -lpthread -lm -lrt -ldl
Yet I can make it link, and work using:
$ dmd -c -betterC stdarg1.d
$ dmd -of=stdarg1 stdarg1.o
$ ./stdarg1
Foo
I tried to work around this via the following, and various variations, however I ran a different issue.
$ cat stdarg2.d
pragma(printf)
public extern(C) int wrap_printf(scope const char* f, ...) {
import stdarg2c;
extern(C) int vprintf(scope const char*, va_list);
va_list ap;
va_start(ap, f);
auto rc = vprintf(f, ap);
va_end(ap);
return rc;
}
extern(C) void main() {
wrap_printf("Foo2\n");
}
$ cat stdarg2c.c
#include <stdarg.h>
$ dmd -betterC stdarg2.d
stdarg2.d(2): Error: `__va_list_tag` is not defined, perhaps `import core.stdc.stdarg;` ?
Actually importing core.stdc.stdarg as it suggests simply brings back the original issue.