May 23, 2015 Re: What happens when you launch a D application ? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Suliman | > > Could you explain what mean "C main inside the runtime". I thought that is only one main is possible. And why it's named "*ะก* main" D is not C-translated language. > > Same question is about _Dmain -- what is it? > > If I will call this() before main? What it will be? Will it run before main? > This is a great question; one which I've tried to answer through my own investigation. So, I'll add what I've learned. Every D program is started as if it were a C program. This is easiest to see with the GNU toolchain. Try to compile a blank test.c file gcc test.c /usr/lib/gcc/x86_64-unknown-linux-gnu/4.9.2/../../../../lib/crt1.o: In function `_start': (.text+0x20): undefined reference to `main' Now try to compile a blank test.d file gdc test.d /usr/lib/gcc/x86_64-unknown-linux-gnu/4.9.2/../../../../lib/crt1.o: In function `_start': (.text+0x20): undefined reference to `main' {...and a bunch of other errors} So, you can see that both C and D programs need to define an unmangled `main` symbol. We call this symbol "C main". DMD and LDC seem to add "C main" automatically, while GDC defines it in the D runtime: https://github.com/D-Programming-GDC/GDC/blob/master/libphobos/libdruntime/__entrypoint.di#L60 "C main" then calls `_d_run_main`, and passes in a pointer to `_DMain`. `_DMain` is actually a phony alias to your D program's `void main()`, so you won't find it implemented anywhere. Your D program's `void main()` is D-mangled, so it is distinguishable from "C main". We call this symbol "D main" https://github.com/D-Programming-GDC/GDC/blob/master/libphobos/libdruntime/__entrypoint.di#L62 https://github.com/D-Programming-GDC/GDC/blob/master/libphobos/libdruntime/rt/dmain2.d#L235 _d_run_main calls `rt_init()` which does all of the D runtime initialization... https://github.com/D-Programming-GDC/GDC/blob/master/libphobos/libdruntime/rt/dmain2.d#L410 ... and then calls `_DMain` (but it was passed into `_d_run_main as` `mainFunc`: https://github.com/D-Programming-GDC/GDC/blob/master/libphobos/libdruntime/rt/dmain2.d#L411 So in summary it looks like this (At least in Linux): * Operating system calls `_start` which is defined in the C Runtime (crt1.o). * _start calls the unmangled `main` which we will call "C main". This function is automatically added by DMD and LDC, but defined in GDC's D runtime. * "C main" calls `_d_run_main` passing in a pointer to the symbol `_DMain`. `_DMain` is actually your D program's `void main()` function. It is D-mangled, so the linker can distinguish it from "C main" * `_d_run_main` then calls `rt_init()` to initialize the runtime, and then calls `_DMain`. I believe the module constructors and the static constructors are called in D runtime's rt_init function: https://github.com/D-Programming-GDC/GDC/blob/master/libphobos/libdruntime/rt/dmain2.d#L152 I'm still studying how exactly that works, though. I think they are linked into ModuleInfo. I hope this is helpful. If you want to know more about how the operating system calls C main (at least in a Linux environment), see these links: http://dbp-consulting.com/tutorials/debugging/linuxProgramStartup.html https://gcc.gnu.org/onlinedocs/gccint/Initialization.html Mike |
May 23, 2015 Re: What happens when you launch a D application ? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Mike | >Every D program is started as if it were a C program.
Why is so necessary?
What about C++ and other languages? Does they have more then one main?
Why it's more than one main is needed? Why D apps can't start with single main?
|
May 23, 2015 Re: What happens when you launch a D application ? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Suliman | On 23/05/2015 10:57 p.m., Suliman wrote: >> Every D program is started as if it were a C program. > Why is so necessary? > > What about C++ and other languages? Does they have more then one main? Depends on the implementation. I believe Visual C++ does. But it is used like D's to allow it to initialize the runtime. https://msdn.microsoft.com/en-us/library/bb918180.aspx > Why it's more than one main is needed? Why D apps can't start with > single main? Oh but they can. But I guess you'll want things like the GC, module constructors ext oh and some globally initialized memory. |
May 23, 2015 Re: What happens when you launch a D application ? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Suliman | On Saturday, 23 May 2015 at 10:57:22 UTC, Suliman wrote: >>Every D program is started as if it were a C program. > Why is so necessary? It's not actually necessary. You could implement the `_start` function in your D program. Here's a D program without any C runtime, D runtime, or main. long __d_sys_write(long arg1, in void* arg2, long arg3) { ulong result; asm { "syscall" : "=a" result : "a" 1, "D" arg1, "S" arg2, "m" arg2, "d" arg3 : "memory", "cc", "rcx", "r11"; } return result; } extern(C) void __d_sys_exit(long arg1) { asm { "syscall" : : "a" 60, "D" arg1, : "memory", "cc", "rcx", "r11"; } } extern(C) void _start() { // you could put this in a main function and // call main() from here. auto text = "Hello, World!\n"; __d_sys_write(1, text.ptr, text.length); __d_sys_exit(0); } Compile with: gdc -fno-emit-moduleinfo -nostartfiles test.d This produces a 733 byte "Hello World" binary. -fno-emit-moduleinfo will prevent the compiler from generating a lot of auxiliary code that's not needed for this program. -nostartfiles will prevent the C runtime from being linked in. This is a nice little experiment, but once you start trying to use structs, classes, arrays, exceptions, or any other feature of D, you will need more and more of the D runtime. There may also be some things generated by GDC that get called implicitly by the C runtime's initialization procedures (e.g. _init, _fini, etc..) but I'm not that knowledgeable about the compiler's codegen. > > What about C++ and other languages? Does they have more then one main? C++ is a superset of C, so in my experience, C++ only needs C main. However, C++ has static constructors that get called by some of the initialization procedures in the C runtime before actually calling main. I wonder if C++ free functions mangled in C++...I'm not sure. > > Why it's more than one main is needed? Why D apps can't start with single main? I don't think the current implementation is necessary. There are probably many different ways to implement D program initialization. I don't see why D runtime couldn't just implement _start, omit the C runtime altogether, and do everything in D, but I trust the compiler implementers have their reasons. If you're interested in digging deeper, you'll probably have to ask questions on D.GNU to get the attention of the compiler implementers. Mike |
May 23, 2015 Re: What happens when you launch a D application ? | ||||
---|---|---|---|---|
| ||||
Posted in reply to Suliman | On Saturday, 23 May 2015 at 10:57:22 UTC, Suliman wrote:
>>Every D program is started as if it were a C program.
> Why is so necessary?
>
> What about C++ and other languages? Does they have more then one main?
>
> Why it's more than one main is needed? Why D apps can't start with single main?
You could have obtained answer long time ago by using debugger and looking into sources of druntime at github.
|
Copyright © 1999-2021 by the D Language Foundation