-
-
Notifications
You must be signed in to change notification settings - Fork 1.6k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Add Crystal.main #4998
Add Crystal.main #4998
Conversation
This makes it possible to invoke `__crystal_main` from inside types and modules.
src/crystal/main.cr
Outdated
# - Invokes the given *block* | ||
# - Handles unhandled exceptions | ||
# - Invokes `at_exit` handlers | ||
# - Flushes STDOUT and STDERR |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please, enclose STDOUT and STDERR in backticks `` to link 'em to docs.
src/crystal/main.cr
Outdated
end | ||
|
||
# Executes the main user code. This normally is executed | ||
# after initializing the GC and executing `at_exit` handlers. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
[...] and before executing
at_exit
handlers.
?
src/crystal/main.cr
Outdated
# in Crystal (like `new` for classes) can be used. | ||
def self.main(argc : Int32, argv : UInt8**) | ||
main do | ||
_crystal_main(argc, argv) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't be here main_user_code(argc, argv)
instead?
This makes it simpler to redefine main with custom logic.
Looks great! One minor thing: sometimes we don't want a main, for example Android applications are shared objects, loaded from Java (JNI). |
@ysbaddaden Was that possible before this PR? |
# Executes the main user code. This normally is executed | ||
# after initializing the GC and before executing `at_exit` handlers. | ||
# | ||
# You should never invoke this method unless you need to |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Would it be possible to raise early if this is executed twice? Seems like a bit of an edge case but might be worth protecting. This could be another PR though.
# | ||
# ``` | ||
# fun main(argc : Int32, argv : UInt8**) : Int32 | ||
# LibFoo.init_foo_and_invoke_main(argc, argv, ->Crystal.main) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Shouldn't ->Crystal.main
be ->Crystal.main(Int32, UInt8**)
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If it's a lib call the compiler figures out the argument types.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Didn't know that, cushtie!
@asterite no, it wasn't possible, but since it's touching main declarations, it could have been an opportunity to allow to skip generating a default main function. Anyway, no big deal. |
Can we also provide MSDN page for envp: https://msdn.microsoft.com/en-us/library/k104fy6h.aspx |
@david50407 envp parameter is widely accepted, yet not standardised, see discussion on SO. btw, wouldn't it be redundant with access to |
@asterite This is awesome, and is exactly what I was trying to accomplish myself, but couldn't figure out. This is really nice! |
Fixes #4793
Closes #4793
Please read the doc comments in the commit.
As an example, to implement what is needed in #4793 one can now write:
This is a breaking change because the macro
redefine_main
is removed.One more thing: I exposemain
to Crystal as__crystal_c_main
. This makes it possible to have a user-defined method namedmain
, so kinda fixes what's described in #4761. Next, the compiler should disallow funs and methods with the same names, but I'll send that in a separate PR.^ I decided it's better for now to expose it as
main
, because otherwise to redefine it one would need to use the same cryptic name. I'll later change the compiler to never exposefun main
to Crystal code because it never needs to be invoked.There's one
TODO
there that is fixed by the first commit in this PR. We can get rid of it after releasing the next version.I also removed the single usage of
redefine_main
, which maybe was needed before, but removing it I got the SDL samples to work (they didn't work anymore).