SomeRanDev / reflaxe.CPP

An alternative C++ target for Haxe that generates dependent-less, GC-less C++17 code.
MIT License
72 stars 5 forks source link

Custom main() support #36

Open fourst4r opened 1 year ago

fourst4r commented 1 year ago

It would be handy to have the ability to use a custom entrypoint, particularly on Windows.

For applications on Windows there are a few different entrypoints:

int __stdcall WinMain(HINSTANCE, HINSTANCE, PSTR, int) // Graphical ASCII entrypoint
int __stdcall wWinMain(HINSTANCE, HINSTANCE, PWSTR, int) // Graphical UTF-16 entrypoint
int __stdcall DllMain(HINSTANCE, DWORD, LPVOID)  // DLL entrypoint

Which entrypoint is invoked depends on the /SUBSYSTEM specified in the linker options. Currently you can't add any of these because the generated int main() interferes with it. (Also there's no @:callconv yet, but that's a different issue)

SomeRanDev commented 1 year ago

Would @:callconv be the ability to add the content between the type and the name (__stdcall for example)?

SomeRanDev commented 1 year ago

I'm actually not sure how to design a feature for this. Maybe should be able to disable the main function so the user can create their own? (Top level functions can be generated using @:topLevel).

fourst4r commented 1 year ago

Would @:callconv be the ability to add the content between the type and the name (__stdcall for example)?

Yep, that's right, or @:callingConvention if you like.

I'm actually not sure how to design a feature for this. Maybe should be able to disable the main function so the user can create their own? (Top level functions can be generated using @:topLevel).

I was wondering that myself, but that's a good idea honestly.

@:topLevel
@:callingConvention("__stdcall")
function WinMain(instance:HINSTANCE, prevInstance:HINSTANCE, cmdLine:LPSTR, showCmd:Int) {
    ...
}

Would be nice with a define like --define disable-main or something.

Not sure if the Haxe compiler will let you get away with compiling without a main, or with an empty main (are types lazily compiled?)

SomeRanDev commented 1 year ago

You can compile without main, but you have to list out all the types you want to compile in the .hxml. Plus, to have the Haxe and Reflaxe/C++ DCE work, there needs to be a -main. Soooo definitely want to keep the -main argument.

I guess I'll add a -D cxx_no_main_cpp that will disable generating the _main_.cpp.

As a result, you'd need to call your Haxe's "main" function manually, so like:

@:topLevel
@:callingConvention("__stdcall")
function WinMain(instance:HINSTANCE, prevInstance:HINSTANCE, cmdLine:LPSTR, showCmd:Int) {
    // Call directly?
    Main.main();

    // OR... maybe could add an untyped builtin to call the main function?
    untyped __main__();
}
fourst4r commented 1 year ago

Calling Main.main() manually with the define makes perfect sense to me. 😎👍

fourst4r commented 1 year ago

By the way, it cannot be understated how much value you've added to the Haxe ecosystem with Reflaxe, and it's unbelievable how much better Reflaxe.CPP is compared to hxcpp. (Haxe Foundation should be paying you!) I really appreciate your work on these projects 🙏