SML# Document Version 4.0.0
16 The SML# Structure

16.2 Programs in the separate compilation mode

A program in the separate compilation mode is a set of source files and their interface files. The contents of a source file, denoted here as ⟨source⟩, are given below.

⟨source⟩ ::= (⟨interfaceFileSpec⟩)?  ⟨sourceProgram⟩
⟨interfaceFileSpec⟩ ::= _interface  "⟨filePath⟩"
⟨sourceProgram⟩ ::=
 | ⟨decl⟩  ⟨sourceProgram⟩
 | ⟨topdecl⟩  ⟨sourceProgram⟩

If there is no interface file specification ⟨interfaceFileSpec⟩ in a source file and there is a file of the same name S.smi as that of the source file S.sml (except for its suffix) in the same directory, then that file is implicitly specified as the interface file of the source file. ⟨filePath⟩ is a relative path. Regardless of OS, / (slash) is used for directory separator.

The contents of an interface file, ⟨interface⟩, consist of ⟨requireList⟩ that specifies the set of interface file paths required for the source file, and ⟨provideList⟩ that specifies the set of declarations the source file provides to the other compilation units.

⟨interface⟩ ::= ⟨requireList⟩  ⟨provideList⟩
⟨requireList⟩ ::=
 | _require  (local)?  ⟨interfaceName⟩  ⟨requireList⟩  (init)?
 | _require  (local)?  ⟨sigFilePath⟩  ⟨requireList⟩  (init)?
⟨interfaceName⟩ ::= ⟨smiFilePath⟩
 | ⟨librarySmiFilePath⟩
⟨provideList⟩ ::=
 | ⟨provide⟩  ⟨provideList⟩
⟨provide⟩ ::= ⟨provideInfix⟩
 | ⟨provideVal⟩
 | ⟨provideType⟩
 | ⟨provideDatatype⟩
 | ⟨provideException⟩
 | ⟨provideStr⟩
 | ⟨provideFun⟩

⟨requireList⟩ specifies interface file names (file path or library name) of source files or signature file paths referenced by the source file. local directive in a _require declaration indicates that the specified interface file is only used inside of the source file and does not referenced in ⟨provideList⟩. init is an annotation indicating that the program corresponding to the specified interface must be executed and precede the program that _requires it. ⟨provideList⟩ specifies the set of declarations the source file provides to the other compilation units.

⟨smiFilePath⟩, ⟨sigFilePath⟩, and ⟨librarySmiFilePath⟩ are file paths relative to the file in which _require is written. Regardless of OS, / (slash) is used for directory separators. If a path does not begins with . (period) and the specified file does not exist, the compiler searches for the file from the load path given in the command line.

SML# provides the following interface libraries.

library smi file name contents
basis.smi Standard ML Basis Library
ml-yacc-lib.smi yacc and lex tools
smlformat-lib.smi SMLFormat formatter generator
smlnj-lib.smi Standard ML of New Jersey library
ffi.smi C FFI support library
thread.smi Multithread library
reify.smi Dynamic typing library
smlunit-lib.smi SMLUnit tool

The following summarizes ⟨provide⟩ specifications corresponding to declarations.

  • •

    Correspondence between core declarations and their interfaces

    declaration (⟨decl⟩) corresponding provide (⟨provide⟩)
    ⟨infixDecl⟩ ⟨provideInfix⟩
    ⟨valDecl⟩ ⟨provideVal⟩
    ⟨valRecDecl⟩ ⟨provideVal⟩
    ⟨funDecl⟩ ⟨provideVal⟩
    ⟨datatypeDecl⟩ ⟨provideData⟩
    ⟨typeDecl⟩ ⟨provideType⟩
    ⟨exceptionDecl⟩ ⟨provideException⟩
    ⟨localDecl⟩
  • •

    Correspondence between module delcarations and their interfaces

    declaration (⟨topdecl⟩) corresponding provide (⟨provide⟩)
    ⟨strDecl⟩ ⟨provideStr⟩
    ⟨sigDecl⟩
    ⟨functorDecl⟩ ⟨provideFun⟩
    ⟨localTopdecl⟩

    Signature files are directly referenced in the interface through _require ⟨sigFilePath⟩.

We show simple examples below.

  • •

    Example 1 (Using the Standard ML Basis Library)

    file code
    hello.sml val _ = print "Welcome to SML#\n"
    hello.smi _require "basis.smi"

    Compilation and execution

    $ smlsharp hello.sml
    $ ./a.out
    Welcome to SML# $

  • •

    Example 3 (separate compilation)

    file code
    hello.sml val _ = puts "Welcome to SML#"
    hello.smi _require "puts.smi"
    puts.sml val puts = _import "puts" : string -> int
    puts.smi val puts : string -> int

    Compilation and execution

    $ smlsharp -c hello.sml
    $ smlsharp -c puts.sml
    $ smlsharp -o hello hello.smi
    $ ./hello
    Welcome to SML# $