How to Override the Default C Entrypoint With C Stubs¶
In some cases, it may be necessary to override the default C entry point of an OCaml program. For example, this is the case if you want to let your program handle argument wildcards expansion on Windows.
Let’s consider a trivial “Hello world” program contained in a hello.ml
file:
let () = print_endline "Hello, world!"
The default C entry point is a main
function, originally defined in
runtime/main.c. It
can be overriden by defining a main
function that will at some point call
the OCaml runtime. Let’s write such a minimal example in a main.c
file:
#include <stdio.h>
#define CAML_INTERNALS
#include "caml/misc.h"
#include "caml/mlvalues.h"
#include "caml/sys.h"
#include "caml/callback.h"
/* This is the new entry point */
int main(int argc, char_os **argv)
{
/* Here, we just print a statement */
printf("Doing stuff before calling the OCaml runtime\n");
/* Before calling the OCaml runtime */
caml_main(argv);
caml_do_exit(0);
return 0;
}
The foreign_stubs stanza can be leveraged to
compile and link our OCaml program with the new C entry point defined in
main.c
:
(executable
(name hello)
(foreign_stubs
(language c)
(names main)))
With this dune
file, the whole program can be compiled by merely calling
dune build
. When run, the output shows that it calls the custom entry point
we defined:
$ dune build
$ _build/default/hello.exe
Doing stuff before calling the OCaml runtime
Hello, world!