Module C_syntax.Param_guards

Builtin parameter guards: a test seam checking builtin calls pass arguments without narrowing.

val parameter_types : key:Base.string -> Base.string -> (Base.string Base.list, Base.string) Base.Result.t

The parameter types of the function key that a table entry's definition defines, read off its signature, or why there are none to guard: a_macro and not_a_function for an entry that is no function, another reason for a function the guard skips.

val a_macro : Base.string

The reason given for a macro.

val not_a_function : Base.string

The reason given for an entry that names key nowhere as a call or a definition: a type, a constant, a header.

val prelude : param_guard_dialect -> Base.string

The helpers the guards of guard expand to, emitted once before them.

val guard : param_guard_dialect -> key:Base.string -> Base.string Base.list -> Base.string

The macro shadowing key, whose parameters have these types.

val with_guards : ?guard:Base.bool -> ?overrides:(Base.string * Base.string) Base.list -> (Base.unit -> 'a) -> 'a

with_guards ?guard ?overrides f runs f with every kernel prelude of a backend that declares a param_guard_dialect guarding the functions the kernel calls (unless guard is false), and with each (key, definition) of overrides replacing that key's definition in the backend's table -- how a test plants a defect, and shows both that it compiles unguarded and that the guards catch it. A test seam: kernels are never guarded outside it. An override naming a key the table lacks fails the prelude's assembly.

val active : Base.unit -> (Base.bool * (Base.string * Base.string) Base.list) Base.option

Some (guard, overrides) inside with_guards, None outside it.

val note_emitted : Base.int -> Base.unit
val emitted : Base.unit -> Base.int

How many guards the preludes assembled in this process carried: zero where no backend declares a dialect, which is how a test sees that its guards were never emitted.