Question regarding OCaml build artifacts

I’m using jbuilder but I think this applies to any build systems (even ocamlopt): I’ve created a simple native project (a hello world with opium), and jbuilder generated these files:

$ ls _build/default
hello_world.cmi
hello_world.cmo
hello_world.cmt
hello_world.cmx
hello_world.depends.ocamldep-output
hello_world.exe
hello_world.ml
hello_world.o
hello_world.requires.sexp

Are all these files actually necessary for running hello_world.exe? If not, which are? If I, say, want to create a docker container for running the program (assuming I’m also building in a same image so no need to cross-compile), can I just copy the hello_world.exe and execute it? Does it already include the dependencies (like in this case, opium)?

I’ve read Chapter 23 of RWO but I’m still not sure… I’ve tried moving the .exe to another directory and executing it, it runs, but since it’s still on the same machine there might be some file resolving going on that I don’t know of.

Note that I’m coming from an interpreted (JavaScript) and a VM-based (Java and Elixir) worlds, so I have little knowledge about native compilation. Help is much appreciated.

2 Likes

The executable is usable entirely on its own. Those files are used as part of the compilation, but are not needed after.

3 Likes

I see. That clears things up. Thanks @Yaron_Minsky!

I just realized we can’t mark post as solution in this forum. Might be great to integrate the Discourse Solved plugin :smile:

2 Likes

I realize through your question that we don’t have a good documentation of what the various file extensions are. Namely:

  • the reference manual has a ocamlc overview that details extensions associated to byecode compilation (.ml{,i}, .cm{i,o,a} and C stubs (.c, .o, .so) and an ocamlopt overview that details native-related extensions (.cmx{,a}), but it was not updated with the more recent .cmt{,i} files – they are documented when the relevant options are documented, but not in the overview.

  • the ocamlbuild manual has a basic target documentation that also includes some of this information, but it includes some ocamlbuild-specific files (.mllib, etc.) and does not detail .cmt* either (they are intermediate artifacts/products, rarely targets in themselves).

We should update the reference manual with information on .cmt* files, and I guess it would be nice for Jbuilder’s documentation to have information about its specicifc extensions (the ocamldep output handling and .requires.sexp in your example).

Thanks!

P.S.: I created a Mantis issue MPR#7584 to track the feature request. It is marked as a “junior job” so it will show up in the list of easy tasks for new contributors.

4 Likes

If you are targeting something minimal like a Docker container, keep in mind that you would also need any .so files the .exe may need while running. That could be achieved by installing the relevant system packages into the run image or by scraping the linked .so files from the build image and including them manually in the run image.

1 Like