Commit Graph

390 Commits

Author SHA1 Message Date
Louis Gesbert
dc1b725e9b Reformat 2024-06-21 12:23:01 +02:00
Louis Gesbert
0e05c75028 Internal typing: print the faulty program when debug is enabled
Since the typing error happened on generated code, it's hard to debug without
printing it.
2024-06-21 12:23:01 +02:00
Louis Gesbert
70c01749b2 Fix regression on internal typing errors reported as user errors 2024-06-21 12:23:01 +02:00
Louis Gesbert
712fc1e279 Support closure calls across modules
First I was disappointed that we couldn't convert closure environment properly
because of their opaque nature (native/interpreted conversion is based on the
Catala types) ; but after more thought it's actually unnecessary to convert them
at all since we are guaranteed that they can't be consumed outside of their
realm.
2024-06-21 12:23:01 +02:00
Louis Gesbert
8881fee37f Allow catala ocaml --closure-conversion
it's probably not useful per se, but will be handy for debugging
2024-06-21 12:23:01 +02:00
Louis Gesbert
09bdc3b4da Printer: print closures as functions
This avoids differences in test results depending on wether closure conversion
is enabled or not: the functional values within structure are a different type
internally but with this patch they are printed the same.
2024-06-21 12:23:01 +02:00
Louis Gesbert
21cea5c968 Closure conversion fix
Support for manipulating toplevel functions as values was buggy, because the
recursion after eta-expansion would fall into the pattern for a `let..in` and
not do the expected transformation.

The patch explicitely builds the closure in that case, avoiding such issues with
recursion.
2024-06-21 12:23:01 +02:00
Louis Gesbert
23b196aace Types printer: use commas rather than * for tuples 2024-06-21 12:16:49 +02:00
vbot
441dd54ec3
Refactor suggestions 2024-06-20 15:59:54 +02:00
vbot
e7beb0daad
Fix typing error message consistency 2024-06-19 14:52:31 +02:00
vbot
b2449f7b4c
Add multiple typing errors using delayed errors 2024-06-19 14:52:31 +02:00
Louis Gesbert
035dff35a3 Preserve and propagate types through closure conversion
some of the types (in particular, in hoisted closures) could not be
reconstructed afterwards. This properly propagates the types, including to
closure deconstruction time, giving additional insurance; and allowing
monomorphisation not to choke on the result.
2024-05-30 17:00:07 +02:00
Louis Gesbert
db87409125 Replace module hashes for external modules
NOTE: This is a temporary solution

A future approach could be to have Catala generate a module loader (with the
proper hash), relieving the user implementation from having to do the
registration.
2024-05-28 11:43:50 +02:00
Louis Gesbert
f04e889173 Pass the "external module" info along passes 2024-05-28 11:43:50 +02:00
Louis Gesbert
709b51beb6 Fix hashing of submodule references 2024-05-28 11:43:50 +02:00
Louis Gesbert
403156b36e Computation and checking of module hashes
This includes a few separate changes:

- pass visibility information of declarations (depending on wether the
  declaration was in a ```catala-metadata block or not)

- add reasonable hash computation functions to discriminate the interfaces. In
  particular:
  * Uids have a `hash` function that depends on their string, but not on their
    actual uid (which is not stable between runs of the compiler) ; the existing
    `hash` function and its uses have been renamed to `id`.
  * The `Hash` module provides the tools to properly combine hashes, etc. While
    we rely on `Hashtbl.hash` for the atoms, we take care not to use it on any
    recursive structure (it relies on a bounded traversal).

- insert the hashes in the artefacts, and properly check and report those (for
  OCaml)

**Remains to do**:

- Record and check the hashes in the other backends

- Provide a way to get stable inline-test outputs in the presence of module
  hashes

- Provide a way to write external modules that don't break at every Catala
  update.
2024-05-28 11:43:50 +02:00
Louis Gesbert
5f289307a0 Runtime value printer: use <object> on non-printable entitites 2024-05-15 10:24:18 +02:00
Louis Gesbert
affa45c115 Unify traces between interpreter and runtime
This is a first step into unifying trace handling. This patch only affects the
interpreter, by delegating trace recording to the already existing runtime
functions.

At end of interpretation, it recovers the registered trace from the runtime, and
prints it.

NOTE: there are some limitations due to this approach, as runtime values going
through this interface have to be converted to the "runtime embedded" type. In
particular, functions can no longer be printed (which makes full sense if we
want it to happen in the same way in compiled code) ; some information, like
types, is lost, but it didn't appear to be used.

Also, a specific printer had to be added for runtime values (but it's very
simple so that shouldn't be a problem).

@denismerigoux I'd like your input on how well this goes for your use-cases.

Further work should probably be cleanup and unification of the runtime logging
interfaces ; there is already code for re-structuring the traces, printing to
JSON, etc. which could be common to runtime and interpreter.
2024-05-06 22:16:54 +02:00
Louis Gesbert
c864f658c8 Cleaner message printing
Aerates the printing of messages, removes extraneous noise, and more clearly
attaches the various information tied to a given message.
2024-05-03 12:21:34 +02:00
Louis Gesbert
facce68b25 Make refactored runtime error messages clearer
mostly reverting to the ones the interpreter was printing ; for the case of
divisions, we choose to point to the denominator instead of the operator as it's
where the only possible error (division by zero) comes from.
2024-05-02 16:30:47 +02:00
Louis Gesbert
4d412027d0 Remove direct dependency towards dates_calc from the compiler
The dependency should only go through the `Runtime` module
2024-05-02 16:30:46 +02:00
Louis Gesbert
a8635f0e61 Simplify unthunking function ; cleanup warnings in 'make testuite' 2024-04-30 17:56:06 +02:00
Louis Gesbert
cee8e57d02 More precise positions for operators throughout 2024-04-30 16:35:08 +02:00
Louis Gesbert
50d686f089 Pass exception positions to the HandleDefault operators
This puts runtime exception info on par with what we had in the interpreter, and
repairs the regression on the interpreter which no longer had them.
2024-04-29 16:09:38 +02:00
Louis Gesbert
959bcb9ccd Remove obsolete "except" type from the interpreter 2024-04-29 13:42:40 +02:00
Louis Gesbert
9d07015864 Unify runtime error handling
- Clearly distinguish Exceptions from Errors. The only catchable exception
  available in our AST is `EmptyError`, so the corresponding nodes are made less
  generic, and a node `FatalError` is added

- Runtime errors are defined as a specific type in the OCaml runtime, with a
  carrier exception and printing functions. These are used throughout, and
  consistently by the interpreter. They always carry a position, that can be
  converted to be printed with the fancy compiler location printer, or in a
  simpler way from the backends.

- All operators that might be subject to an error take a position as argument,
  in order to print an informative message without relying on backtraces from
  the backend
2024-04-26 18:31:26 +02:00
Louis Gesbert
97d007f1e7 Rename EmptyError to Empty
It's not an error! It happens in the normal control flow :)

This is to distinguish from the other runtime exceptions which are actually
fatal errors.
2024-04-25 14:39:15 +02:00
Louis Gesbert
78200953f3
Improvements around external modules and error handling (#605) 2024-04-16 23:13:46 +02:00
Louis Gesbert
1de18f0e04 Preserve the capitalisation of module filenames
Module names must be capitalised (start with a capital letter), and the name of
the file on disk must match ; however, matching up to capitalisation is allowed,
i.e. the file on disk can start with a lowercase letter.

A mismatch between Clerk assuming generated module artifacts would match the
capitalised module name, and `catala depends` matching the names of files on
disk (because it would otherwise mean treating dependencies differently
depending on if they originate from modules or not) was causing "file not found"
errors later on in the compilation chain.

This patch enforces that the capitalisation of the original file name on
disk (which is always known) takes precedence in Clerk, matching the behaviour
of `catala depends` and fixing the issue. It's also actually a small
simplification in Clerk code.
2024-04-15 23:00:56 +02:00
Louis Gesbert
20288bcb26 Protect the interpreter against exceptions from custom code 2024-04-15 14:13:33 +02:00
Louis Gesbert
5d432d6bb9 OCaml runtime: register fallback exception printers
This was a pending TODO: now the Catala program compiled into OCaml should
return better messages and a little more information about uncaught exceptions.

Note that this also concerns, at the moment, compiled modules called from the
Catala interpreter: in this case, it's already better than nothing, but what we
need is proper interoperation between the runtime exceptions and the interpreter
handling (`EmptyError` should already be handled properly since it is critical
to the computation flow, but "error" exceptions are left uncaught and will kill
the interpreter).

This may be part of a bigger task on unifying the output of the runtime and
toplevel, which also concerns computation traces.

Note 2: All runtime exceptions don't have a position available, which is quite
unfortunate when your program hits an error. With `OCAMLRUNPARAM=b` and if
compiled with `-g` (which should normally be the case), you can get an OCaml
backtrace but that's not very friendly. Ideas for improvement:
- The runtime could force-enable backtrace recording (`Printexc.record_backtrace
  true`) to supersede the need for `OCAMLRUNPARAM`. We can also record our own
  handler to print the file position and/or backtrace in the way we see fit
- The printer of OCaml code in Catala could insert line directives so that the
  positions in the backtrace actually trace automatically back to the Catala
  code
- If we don't want to leverage any OCaml machinery in this way, the compiler
  should add position information to any operator that might fail (e.g.
  divisions, date comparisons, etc.).
Note that running in trace mode might already help pinpoint the location of the
error ?
2024-04-15 14:13:33 +02:00
Louis Gesbert
eded54d2b5 Support for direct tuple member access
As discussed in #549

NOTE: This implements only the direct tuple member access (syntax `foo.N` with N a
number)

- It seems more efficient to wait for the general pattern-matching rewrite to
  handle pattern-matching on tuples
- Until then we keep the (now obsolete) `let (x, y) = pair in x` syntax, to
  leave time for updates, but we won't be documenting it
2024-04-13 09:37:03 +02:00
Louis Gesbert
a61ae7979f
Support for structure updates
Closes #592

A new node is added in `desugared`, and translated into an exploded structure
literal during translation to `scopelang`. The main reason to put it there is
that it needs to be after disambiguation, since that is used to discover the
type of the structure that is being updated.
2024-04-12 17:17:48 +02:00
Louis Gesbert
b78cd9c29a
Improve message formatting throughout
Ensuring messages don't print overlong lines still requires some manual work:
- if they don't contain any `Format` directives (`%` or `@`), use `"%a"
  Format.pp_print_text` to turn word-wrapping on.
- otherwise replace spaces with `@ ` to mark possible cutting points, as soon
  that it's possible the line will get over 80 chars (most often, this means
  starting before the first `%a`)
2024-04-12 17:07:36 +02:00
Louis Gesbert
def10e7f98 Message: further simplification 2024-04-10 19:26:23 +02:00
Louis Gesbert
98fc97a241 Rewriting message calls to use the new intf 2024-04-10 19:26:23 +02:00
Louis Gesbert
75bf768264 Reformat 2024-04-04 10:56:56 +02:00
Louis Gesbert
0ec04c4925 Branch cleanup and test outputs update
Lots of tests have a new warning because they were calling subscopes without
using their outputs. A better solution could be to mark these subscopes as
`output`, now that it's possible !
2024-04-04 10:55:21 +02:00
Louis Gesbert
cde9a66295 Output scopes and subscope variable rework done 2024-04-04 10:24:18 +02:00
Louis Gesbert
852bebd357 Completely remove subscope input vars (use local vars) 2024-04-04 10:24:18 +02:00
Louis Gesbert
f151a9a794 Wip: handling subscope calls as normal definitions
- for the moment we still have specific vars for subscope inputs (in scopelang)
- this causes trouble with default-embedding of scope calls
2024-04-04 10:24:18 +02:00
Louis Gesbert
4eeb8221f4 Fix var bindings in desugared->scopelang 2024-04-04 10:24:18 +02:00
Louis Gesbert
7951661981 Turn subscope-vars into scope vars
They are to become citizens of the same class if we want to allow
output-subscopes (without unnecessary complications like deconstructing and
reconstructing the same structure). And it's reasonable to assume that they
share the same namespace.

With this we should shortly collapse the (internal) ambiguity between

- `subscope.subvar`: access to a variable within a subscope
- `subscope.subfield`: access to a field of the output structure contained in a
  subscope variable

With the subscope a variable, these should now become strictly equivalent, so
the plan is that the first could be removed.
2024-04-04 10:24:18 +02:00
Louis Gesbert
619cafebb8 Reformat 2024-03-20 14:41:06 +01:00
Louis Gesbert
4cec981f62 Move global options of Cli to their own module
This resolves a dependency cycle that would forbid `Cli` from using the modue
`File`, which was annoying.
2024-03-19 15:18:35 +01:00
Louis Gesbert
1ea77201ff Lcalc interpreter: fix passing of context arguments 2024-02-26 14:56:43 +01:00
Louis Gesbert
07b71656e7 Native/interpreter interface: handle option types 2024-02-26 14:56:43 +01:00
Louis Gesbert
ba9fc85b84 Make exception output consistent across the interpreters 2024-02-26 14:56:43 +01:00
Louis Gesbert
97ae62384e Add externals to scalc, working test with Python backend 2024-02-26 14:56:43 +01:00
Louis Gesbert
e0928677b1 Small ocaml/js output rehaul
Print to json directly rather than depend on yojson and a ppx.

Note: this should be tested with the website in order to validate that the Json
output is 1-to-1.
(a second step could be to simplify this output, now that it's manual)
2024-02-21 11:28:56 +01:00