reml(1)
π NAME π
reml β Standard ML with Explicit Regions and Effects, bestie β¨ (and yes, this is the reml(1) page straight out of MLKit, a compiler for Standard ML π«Ά)
πΈ SYNOPSIS πΈ
reml [OPTION]... [file.sml | file.sig | file.mlb]
Every single possible option is listed below. Like, all of them. We do not gatekeep here π
π DEFAULTS π
Okay so before you even touch a flag, here's exactly where everything sits out of the box. The whole lineup, no skipping π:
--SML_LIBβYou_did_not_set_path_to_install_dir(iconic placeholder energy fr π)-aoptβoff--alloc_protect_alwaysβoff-argoβoff-asβas --64-verboseβoff--comments_in_asmcodeβoff-cβoff-timingsβoff-cfoldβon--contractβon-crβoff-cross_optβon-dangleβon--dangling_pointers_statisticsβoff-debugβoff-dcsβoff--debug_linkingβoff--debug_man_enrichβoff-Dparβoff--debug_which_atβoff--delete_target_filesβon--disable_atbot_analysisβoff--disable_flow_varβoff-dufaβon--eliminate_explicit_recordsβon--fix_floatingβon-gβoff--high_pointer_taggingβon-basislibβon--inline_functorsβoff--libsβm,c,dl-ldexeβgcc-ldsharedβgcc-ltdceβon--log_to_fileβoff-max_inl_szβ200-max_spec_szβ200--messagesβon--minimize_fixsβon--namebaseβdummyBase--objsβoff-optβon-oβrun-jβ1-parβon-par0βoff-ptcβon--pretty_depthβ5--pretty_string_sizeβ80--print_K_normal_formsβoff-Pppβoff-Pauxβon--print_bit_vectorsβoff--print_calc_offset_programβoff-Pceeβoff-Pccpβoff-Pcebβoff--print_constraintsβoff-abbrevβon--print_control_prefix_infixβoff-Pdreβoff-Pdresmβoff-Peffectsβoff--print_excon_nameβoff-Pebβoff--print_fetch_and_flush_programβoff--print_linearised_programβoff--print_lvar_nameβoff--print_normalized_programβoff-Poleβoff-Ppseβoff-Ppeastβoff-Prfgβoff-Pripβoff-Prspβoff-Prse0βoff-Pregionsβon--print_register_allocated_programβoff--print_rho_levelsβoff-Prho_protectionβoff--print_rho_typesβoff--print_simplified_programβoff-Psmeβoff-Ptypestampsβoff-Ptypesβoff--raggedRightβon-scratchβoff-riβon-profβoff--register_allocationβon--remlβon--report_boxitiesβoff-sigβoff--safeLinkTimeEliminationβoff--specialize_recursive_functionsβon-stats_optβoff--stripβoff--type_check_lambdaβon--unbox_funargsβon--unbox_real_funargsβon--unbox_realsβon-uncurryβon--warn_on_escaping_putsβoff--warn_on_parallel_putsβoff-wβ100
π¦ DESCRIPTION π¦
Okay so ReML is Standard ML with support for programming with explicit regions, explicit effects, and effect constraints. That's the whole vibe. With ReML, atomic effects include get-effects, put-effects, and mut-effects, and the parallel thread support is right there. What it does not do: ReML does not support integration with reference-tracing garbage collection. Noted, respected, moving on π
When you invoke reml, it will compile the specified sources into an executable file, run through a whole series of translation phases β think of it as the compiler's main-character arc π. The various options let you control the printing of intermediate forms and control which optimizations get performed. So if you're nosy (affectionate), there's a flag for that.
If your source files are organised in ML Basis Files (files with extension .mlb), the compiler will memoize symbol table information and object code in the dedicated MLB directories located relative to the source files. Caching! We love a queen who remembers things π
If reml is invoked without source files, an interactive REPL starts up instead. Type ':help;' within the REPL to learn more about how to use it β it's giving built-in bestie π«Ά
To learn more about programming with ReML, consult the MLKit web page at
http://melsman.github.io/mlkit
β STANDARDS β
ReML is based on the MLKit. The MLKit implements Standard ML (Revised 1997) and has almost full support for the Standard ML Basis Library (version of 2002) β like, almost full, bestie, don't come for me π. See the MLKit home page for a detailed overview of the support for the Standard ML Basis Library.
π₯ EXAMPLES π₯
For examples, consult the files in the 'test/reml' folder within the github repository at http://github.com/melsman/mlkit. Real code, real receipts, go look π
β¨ OPTIONS β¨
Here's the full menu. Every flag, every default, no cap π
--SML_LIB Sβ the installation directory for the MLKit standard library. For normal execution you should not modify this value, okay? But if you wish to use the MLKit with an altered runtime system, you can update this setting and the system will try to link to a runtime system found in the specified install directory. Fancy π¦--aggressive_opt,-aoptβ enable aggressive optimisations, including aggressive inlining. Heads up though: these optimisations are not guaranteed to be region safe. Also, turning off garbage collection automatically turns off this option. It's giving "do it for the plot" π--alloc_protect_alwaysβ always protect allocation when parallelism is enabled. Like, disregard the result of protection inference entirely. Overprotective? Maybe. Safe? Yes π‘οΈ--argobots,-argoβ when enabled, executables link with the Argobots lightweight thread library. Threads but make it lightweight πΈ--assembler S,-as Sβ specifies the assembler used. On Linux the default is'as --64'. On macOS, the default is'as -q'. Pick your fighter π--chat,-verboseβ print a message for each compilation step in the compiler. It literally will not stop talking and honestly? Same π--comments_in_asmcodeβ insert comments in assembler code. Little notes for future you π--compile_only,-cβ compile only. Suppresses generation of executable.--compiler_timings,-timingsβ show compiler timings for each compilation phase. Time the tea β--constant_folding,-cfoldβ enable constant folding optimisations.--contractβ Contract is responsible for inlining, specialization, elimination of dead code, and much else. It's the Lambda Expression Optimiser, and yes, it's the main character π--contract_regions,-crβ when this option is enabled, identically typed regions bound by the sameletregionconstruct are unified. Moreover, region parameters to non-exported functions are trimmed whenever possible. Tidy β¨--cross_module_opt,-cross_optβ enable cross-module optimisation, including inlining of small functions and specialisation of small recursive functions. Which optimisations are performed across modules is controlled by individual optimisation flags. Teamwork makes the dream work π«Ά--dangling_pointers,-dangleβ when this option is disabled, dangling pointers are avoided by forcing values captured in closures to live at least as long as the closure itself. And to make garbage collection sound, this option is disabled by default when garbage collection is enabled. Important safety moment β οΈ--dangling_pointers_statisticsβ when enabled, the compiler prints statistics about the number of times strengthening of the region typing rules (to avoid dangling pointers during evaluation) effects the target program. This flag is useful only when the flag-gcor-no_dangleis enabled. Yes, that's exactly how it's worded. Numbers girlies rise π--debug_compiler,-debugβ print intermediate forms of a program during compilation. Peek behind the curtain π--debug_constraint_solving,-dcsβ debug ReML constraint solving.--debug_linkingβ debug linking of target code by showing which object files are linked together. It's giving receipts π--debug_man_enrichβ show information about why a program unit need be recompiled. A program unit (or a functor body) is recompiled if either (a) the program unit is modified, or (b) information about an identifier for which the program unit depends upon has changed. Detective mode π΅οΈ--debug_parallelism,-Dparβ debug parallelism, including protection inference.--debug_which_atβ debug storage mode analysis.--delete_target_filesβ delete assembler files produced by the compiler. If you disable this flag, you can inspect the assembler code produced by the compiler. Your choice: clean workspace or hot gossip π--disable_atbot_analysisβ disable storage mode analysis. That is, turn all allocation directives intoattop.--disable_flow_varβ disable optimised compilation of control-flow code, such as conditional expressions.--drop_unused_funargs,-dufaβ drop function arguments that are unused. If nobody's using it, it's gone π--eliminate_explicit_recordsβ eliminate bindings of explicit records only used for selections. Transform
let r = (e1,...,en) in ... #i r .. #j r ...
into
let x1=e1 in ... let xn=en in ... xi .. xj ...
(Lambda Expression Optimiser). Decluttered, slayed β¨
--fix_floatingβ float fix-bindings into immediate let-bindings when possible, to help tail-calls not be captured inlet-region bindings.--gdb_support,-gβ when enabled, the compiler passes the option--gstabstoas(The GNU Assembler) and preserves the generated assembler files (.sfiles). Passing the--gstabsoption toasmakes it possible to step through the generated program using gdb (The GNU Debugger). Debug era π--helpβ print extended help information and exit.--help Sβ print help information about an option and exit. Yes, the argument comes after. Ask about one thing at a time bestie π--high_pointer_taggingβ when enabled, the 16 most-significant bits in pointers may be used for tagging. Smuggling data in the top bits, iconic π--import_basislib,-basislibβ import Basis Library automatically in your projects. If you wish to make use of the Standard ML Basis Library in your projects, this option should be turned on β unless you wish to import the Basis Library manually in your projects. Then do you π--inline_functorsβ inline functors during static interpretation instead of generating separate target code blocks for functor bodies and arguments. With the flag enabled, performance may increase, at the cost of larger (re)compilation times. The flag may be controlled in mlb-files using mlb-annotations. Trade-offs, always trade-offs π--inline_names Sβ names of functions that should always be inlined if possible, no matter the setting of the flag--maximum_inline_size. These ones get the VIP pass ποΈ--libdirs Sβ controls whereldlooks for archives. The format is a comma-separated list of directories; see the-libsentry. The default is the empty list; thus'ld'will look for libraries in only the system specific default directores. The directories are passed to'ld'using the-Loption. (Yes, "directores". We keep it exactly as written π)--libs Sβ for accessing a foreign function residing in an archive namedlibNAME.afrom Standard ML code (usingprim), you need to add'NAME'to this comma-separated list. Notice that an object file (with extension'.o') is an archive if it is renamed to have extension'.a'. You may need to use the-libdirsoption for specifying directories for whichldshould look for library archives. The libraries are passed to'ld'using the-loption. Foreign function era π--link_code Sβ link-files to be linked together to form an executable.--link_exe S,-ldexe Sβ specifies the command used for linking an executable. The standard is to use'gcc'for linking. When linking with c++ libraries,'g++'is the linker you want. On Linux the default is'gcc', whereas on macOS systems, the default is
(and that's genuinely where the sentence stops in the page β we love a cliffhanger π)
--link_shared S,-ldshared Sβ specifies the command used for linking a shared object file. The standard is to use'gcc'for linking.--link_time_dead_code_elimination,-ltdceβ link time dead code elimination.--load_basis_files S,-load Sβ basis files to be loaded before compilation proper. Get your bases loaded first, always π§--log_to_fileβ log to files instead of stdout. Quiet mode, mysterious mode π¦--manβ print man-page and exit. You are here π--maximum_inline_size N,-max_inl_sz Nβ Bestie, any function smaller than this size (counted in abstract syntax tree nodes) gets inlined, even if it's used more than once. Functions used only once are always inlined. A function declared in one program unit may be inlined when applied in another program unit as long as it's sufficiently closed (refers only to exported identifiers) and the option--cross_optis enabled. β¨--maximum_specialise_size N,-max_spec_sz Nβ Function-parameterised functions smaller than this size (counted in abstract syntax tree nodes) are specialised if all applications of the function within its own body are applied to its formal function argument, even if they're used more than once. Functions used only once are specialised no matter their size. A function declared in one program unit may be specialised when applied in another program unit as long as it's sufficiently closed (refers only to exported identifiers) and the option--cross_optis enabled. Also see the option--specialize_recursive_functions. π--messagesβ Print messages about reading source files and generating target files. π«Ά--minimize_fixsβ Minimize fix constructs (Lambda Expression Optimiser). π--mlb-subdir Sβ For ensuring that the smart recompilation scheme is not reusing target-code compiled with different settings, a string provided with themlb-subdiroption can ensure the use of consistently generated code. This option is Useful, in particular, when performing benchmarking. π¦--mlb_path_maps S,-mlb-path-map Sβ ML Basis path map files to be used. πΈ--namebase Sβ Name base to enforce unique names when compiling mlb-files. π--no_aggressive_opt,-no_aoptβ Opposite of--aggressive_opt,-aopt. π--no_constant_folding,-no_cfoldβ Opposite of--constant_folding,-cfold. β¨--no_contractβ Opposite of--contract. π--no_cross_module_opt,-no_cross_optβ Opposite of--cross_module_opt,-cross_opt. π¦--no_dangling_pointers,-no_dangleβ Opposite of--dangling_pointers,-dangle. β--no_delete_target_filesβ Opposite of--delete_target_files. π--no_drop_unused_funargs,-no_dufaβ Opposite of--drop_unused_funargs,-dufa. π--no_eliminate_explicit_recordsβ Opposite of--eliminate_explicit_records. π§--no_fix_floatingβ Opposite of--fix_floating. π--no_high_pointer_taggingβ Opposite of--high_pointer_tagging. π₯--no_import_basislib,-no_basislibβ Opposite of--import_basislib,-basislib. π--no_link_time_dead_code_elimination,-no_ltdceβ Opposite of--link_time_dead_code_elimination,-ltdce. π--no_messagesβ Opposite of--messages. πΈ--no_minimize_fixsβ Opposite of--minimize_fixs. π--no_optimiser,-no_optβ Opposite of--optimiser,-opt. β¨--no_preserve_tail_calls,-no_ptcβ Opposite of--preserve_tail_calls,-ptc. π«Ά--no_print_aux_reset,-no_Pauxβ Opposite of--print_aux_reset,-Paux. π¦--no_print_control_abbrev_layout,-no_abbrevβ Opposite of--print_control_abbrev_layout,-abbrev. π--no_print_regions,-no_Pregionsβ Opposite of--print_regions,-Pregions. π--no_raggedRightβ Opposite of--raggedRight. β--no_region_inference,-no_riβ Opposite of--region_inference,-ri. π--no_register_allocationβ Opposite of--register_allocation. π§--no_specialize_recursive_functionsβ Opposite of--specialize_recursive_functions. π₯--no_type_check_lambdaβ Opposite of--type_check_lambda. π--no_unbox_funargsβ Opposite of--unbox_funargs. π--no_unbox_real_funargsβ Opposite of--unbox_real_funargs. πΈ--no_unbox_realsβ Opposite of--unbox_reals. β¨--no_uncurrying,-no_uncurryβ Opposite of--uncurrying,-uncurry. π--objsβ If enabled, MLKit writes object-file paths to the filerunor the file specified by-output. The path to the runtime system (archive file) is included. The option is best used together with the option-no_delete_target_files. π«Ά--optimiser,-optβ Enable optimisation of intermediate language code (Lambda Expressions). Which optimisations are performed is controlled by individual flags. The optimisations include function inlining, function specialisation, fix-minimization, unboxing of function arguments, and elimination of unnecessary record constructions. π--output S,-o Sβ The name of the executable file generated by the Kit. π--parallel_compilation N,-j Nβ The maximum number of parallel processes used for compilation. β‘--parallelism,-parβ When enabled, the runtime system supports parallel threads. π§΅--parallelism_alloc_unprotected,-par0β When enabled, allocation into a region is not guaranteed to be atomic. β οΈ--preserve_tail_calls,-ptcβ Avoid the wrapping ofletregionconstructs around tail calls. Turning on garbage collection automatically turns on this option. π--pretty_depth Nβ This flag controls the pretty-printing depth of values printed in the REPL. The value must be an integer larger than zero. π’--pretty_string_size Nβ This flag controls the pretty-printing size of strings printed in the REPL. The value must be an integer larger than zero. π--print_K_normal_formsβ Print Region Expressions in K-Normal Form. Applicable only after storage mode analysis has been applied. β¨--print_all_program_points,-Pppβ Print all program points when printing physical size inference expressions. π¦--print_aux_reset,-Pauxβ Print resetting of auxiliary regions associated with construction of nullary constructor values. This flag affects the MulExp pretty printer. π--print_bit_vectorsβ No description on the page β just the flag itself, no invented lore π.--print_calc_offset_programβ No description on the page β just the flag itself, no invented lore π.--print_call_explicit_expression,-Pceeβ Print Region Expression with call annotations. πΈ--print_clos_conv_program,-Pccpβ Print Region Expression after closure conversion. π§--print_closed_export_bases,-Pcebβ Controls printing of closed export bases. β--print_constraintsβ Print ReML effect constraints when printing region and effect variables. π₯--print_control_abbrev_layout,-abbrevβ Abbreviate layout of multiplicity expressions and call- explicit expressions. For instance, do not show at- annotations for top-level functions, do not show at- annotations for immediate constants, do not show region- bindings for zero-size regions that are associated only with immediate constants, do not show empty formal and actual region parameter lists, do not show'funcall', and do not show unique id for explicit region variables or explicit effect variables. π--print_control_prefix_infixβ Prefix infix operations with module identifier to further indicate the type of the operation. π--print_drop_regions_expression,-Pdreβ Print Region Expression after dropping word regions and region arguments with only get-effects. π¦--print_drop_regions_expression_with_storage_modes,-Pdresmβ Print Region Expression after dropping word regions and region arguments with only get-effects. Also printatbotandattopannotations resulting from storage mode analysis. β¨--print_effects,-Peffectsβ Print effects in region types. π--print_excon_nameβ Print underlying unique name when printing excons. π--print_export_bases,-Pebβ Controls printing of export bases. β--print_fetch_and_flush_programβ Print program with instructions for activation record fetching and flushing. π§--print_linearised_programβ Print a linearlised representation of the program unit. π--print_lvar_nameβ Print underlying unique name when printing lvars. πΈ--print_normalized_programβ Print Region Expression after K-normalisation. π--print_opt_lambda_expression,-Poleβ Print Lambda Expression after optimisation. π₯--print_physical_size_inference_expression,-Ppseβ Print Region Expression after physical size inference. π--print_post_elab_ast,-Ppeastβ Printastafter elaboration. π¦--print_region_flow_graph,-Prfgβ Print a region flow graph for the program fragment and generate a.vcg-file, which can be viewed using thexvcgprogram. β--print_region_inferred_program,-Pripβ Print region-inferred program. π--print_region_spreaded_program,-Prspβ Print region-spreaded program. π--print_region_static_env0,-Prse0β Print imported region static environment prior to region inference. π§--print_regions,-Pregionsβ Print region variables in types and expressions. πΈ--print_register_allocated_programβ No description on the page β just the flag itself, no invented lore π.--print_rho_levelsβ Print levels of region and effect variables in types and intermediate forms. Levels control quantification of region and effect variables. π--print_rho_protection,-Prho_protectionβ Print protectedness of region variables if set (PorU). π₯--print_rho_typesβ Print region types of region variables in types and intermediate forms. Possible region types are:pβ Type of regions containing pairs.aβ Type of regions containing arrays.rβ Type of regions containing references.tβ Type of regions containing triples.sβ Type of regions containing strings.Tβ Type of regions containing other than the above kinds of values. β¨
--print_simplified_programβ Print simplified program after register allocation. π--print_storage_mode_expression,-Psmeβ Print Region Expression after storage mode analysis. π¦--print_type_name_stamps,-Ptypestampsβ Print type name stamps and their attributes in types and expressions. β--print_types,-Ptypesβ Print types when printing intermediate forms. For Lambda Expressions, ordinary ML types are printed, whereas for Region Expressions, region types are printed. π--raggedRightβ Use ragged right margin in pretty-printing of expressions and types. π--recompile_basislib,-scratchβ Recompile basis library from scratch. This option is useful together with other options that control code generation. π--region_inference,-riβ With this flag disabled, all values are allocated in global regions. π§--region_profiling,-profβ turns on region profiling β¨ Object code that comes from compiling a program with region profiling enabled gets instrumented with profiling information. Then, when you actually run a program compiled that way, it produces a profile file calledrun.rp, and you can feed that to the profiling toolrp2psthat ships with the MLKit to get profiling graphs in various forms. it's giving data visualization π--register_allocationβ do register allocation. Turn this off and your programs run somewhat slower β but like, they still run, and you save about 15 percent on compile time π--remlβ ReML is Standard ML with support for programming with explicit regions, explicit effects, and effect constraints. With ReML, atomic effects also include mutation effects. And here's the fine print bestie: whereas ReML includes parallel thread support, currently, ReML does not support integration with reference-tracing garbage collection π--report_boxitiesβ report, for every datatype declaration, the inferred boxity (representation) of its value constructors. receipts for your datatypes π--report_file_sig,-sigβ report signatures for each file read.--safeLinkTimeEliminationβ treat this module as a library in the sense that the code can be eliminated if it's not used, even if the code has side effects π yes that's exactly what it says, no cap.--specialize_recursive_functionsβ specialise recursive functions. Use the optionmaximum_specialise_sizeto control which functions get specialised. And if this flag is on, functions that are applied only once are specialised, no matter the setting of--maximum_specialise_size(Lambda Expression Optimiser) π₯--statistics_after_optimisation,-stats_optβ report optimisation statistics after optimisation of Lambda Expression. numbers!! we love numbers β--stripβ if enabled, MLKit strips the generated executable βοΈ--type_check_lambdaβ type check lambda expression prior to performing region inference. Type checking is very fast, and for normal use you should not disable this option. Type checking intermediate forms is very powerful for eliminating bugs in the compiler β lowkey iconic π§--unbox_funargsβ unbox arguments to fix-bound functions, for which the argument'a'is used only in contexts'#i a'. All call sites get transformed to match the new function (Lambda Expression Optimiser).--unbox_real_funargsβ unbox arguments of typerealto fix-bound functions, for which the argument'a'is used only in contexts that unboxes'a'. All call sites are transformed to match the new function. Heads up: this optimisation has effect only when the flags'-unbox_funargs'and...
okay so the sentence literally trails off right there in the original manual π "and" and then nothing. not me inventing the rest β I would never. mysteries of the manpage π΅οΈββοΈ
--unbox_realsβ unbox real values and computations on real values inside functions. Real values stored in data structures and passed to functions are still boxed though, so don't get too excited π--uncurrying,-uncurryβ enable uncurrying of curried functions. The uncurried function takes its arguments unboxed in registers or on the stack. For partial applications and non-application uses of the function, appropriate eta-expansions are applied β¨--version,-v,-Vβ print version information and exit. that's it. that's the whole vibe check π--warn_on_escaping_putsβ enables the compiler to issue a warning whenever a region type scheme contains a put effect on a region that is not quantified π¨--warn_on_parallel_putsβ enables the compiler to issue a warning whenever a par-construct is passed functions with intersecting put effects π¨π¨--width N,-w Nβ column width used when pretty printing intermediate code. give it a number, bestie π
π¦ EXIT STATUS π¦
Exits with status 0 on success and -1 on failure. that's the whole story β no dramatic third option, no plot twist π
π ENVIRONMENT π
A library install directory must be provided in an environment variable SML_LIB, as a path-definition in the user's personal path-map ~/.reml/mlb-path-map, or in a system wide path-map /nix/store/sfp5bfgah1f35wd1r96xrvhzx6nir1r6-mlkit-4.7.23/etc/reml/mlb-path-map.
Like, you gotta give it one of those three. it's not optional, fr fr π«Ά
π FILES π
/nix/store/sfp5bfgah1f35wd1r96xrvhzx6nir1r6-mlkit-4.7.23/etc/reml/mlb-path-mapβ system-wide configuration of library and runtime system locations~/.reml/mlb-path-mapβ user specific configuration of library and runtime system locations
one for everyone, one just for you π
π CREDITS π
ReML was developed by Martin Elsman. Many people have helped developing the MLKit on which ReML is built; see the MLKit home page for details. shoutout to the whole team honestly π
π SEE ALSO π
See the MLKit manual "Programming with Regions in the MLKit", available from the MLKit home page
http://melsman.github.io/mlkit
for an in-depth introduction to programming with regions in the MLKit. πΈ
The home page also provides an overview of which parts of the Standard ML Basis Library the MLKit implements, along with download and installation instructions.
go read it, it's giving required reading for the girlies who want to actually understand regions πβ¨
that's a wrap on reml(1)!! π¦ this gorgeousness is version v4.7.23, and yes it's filed under reml(1) in that very section of the manual β mwah, love u, go compile something π
ππ
π¦ where this page comes from
- nixpkgs unstable: mlkit 4.7.23
- π girlified by deepseek-ai/DeepSeek-V4.1-Flash-1017 on : a language model's rewrite of the original, under its terms