Skip to content

1. Cases and quantities ​

A test answers yes or no. A numerical code needs more: which numbers it computes, so that a change can be judged by what it does to them. This track gives quad a declared case — a program run with given arguments, and the numbers to read from what it prints — and then builds on it: references, shadow builds, error assessment, differential runs, benchmarks, and a gate that runs everything.

The case program integrates sin(x) over [0, pi] (exactly 2) with both rules and n intervals, the first argument:

fortran
!< The integral of sin(x) over [0, pi], exact value 2, with n intervals (the first argument, default 16).
program area
!< The integral of sin(x) over [0, pi], exact value 2, with n intervals (the first argument, default 16).
use quad_rules, only : R8P, trapezoid, simpson
use integrands, only : sine
implicit none
real(R8P), parameter :: pi = acos(-1._R8P) !< Pi.
character(len=32)    :: arg                !< The first argument.
integer              :: n                  !< Number of intervals.

n = 16
if (command_argument_count() > 0) then
   call get_command_argument(1, arg)
   read(arg, *) n
endif
print '(A, I0)', 'n = ', n
print '(A, ES24.17)', 'trapezoid = ', trapezoid(sine, 0._R8P, pi, n)
print '(A, ES24.17)', 'simpson = ', simpson(sine, 0._R8P, pi, n)
endprogram area

The case, in the fobos:

ini
[case:area]
description = sin(x) over [0, pi] with 16 intervals, both rules
target      = src/area.F90
mode        = release
args        = 16
quantities  = stdout

quantities = stdout reads every name = number line the program prints; a quantity can also be a regular expression, a column of a file, a JSON key, an HDF5 dataset, a record of an unformatted file or the exit status (see cases and quantities).

console
$ fobis case list
area                 src/area.F90  [quantities: *]
console
$ fobis case run
Running case area...
  ok (exit 0, 0.00 s) in .fobis/runs/area/default
    n = 16
    trapezoid = 1.9935703437723395
    simpson = 2.0000165910479359

The case is built with its mode (here release) and run in a fresh directory of its own, where the program's output is kept:

console
$ ls .fobis/runs/area/default
stderr.txt
stdout.txt

.fobis/ holds what FoBiS produces for verification (runs, shadow builds, variants): the chapter adds it to .gitignore.

Provenance ​

A number means little without what produced it. fobis provenance prints what a result produced now would depend on: the commit and whether the tree is dirty (an untracked source counts, an untracked output does not), the pinned dependencies, the mode's compiler, its version and flags, the loaded environment modules:

console
$ fobis provenance --mode release | sed "/^machine:/,\$d"
fobis: 3.9.8
date: 2026-10-14T08:39:21+00:00
git:
  commit: b15eb6be644457b2e64c9cc90d3fb60599820baa
  branch: master
  dirty: False
dependencies:
  penf: 4cb9d326c08f109ed5126d83c27e8e70c98b7eaa
mode: release
compiler:
  name: gnu
  binary: -
  cflags: -O3 -funroll-loops -c
  lflags: -
  preproc: -
  command: gfortran
  version: GNU Fortran (Ubuntu 13.4.0-6ubuntu1~24~ppa1) 13.4.0
  path: ~/.local/bin/gfortran
environment:
  modules: -
  omp_num_threads: -

The output stops before the machine: section, which names the host, the CPU model and cores and the GPUs. The compiler's version and the commit are those of the machine that recorded this page: yours will differ.

Every result of the next chapters carries this record, and every comparison reports what changed in it.

What you learned

[case:NAME], quantities, fobis case list and case run, run directories, fobis provenance. Reference: cases, quantities and provenance.

Next: 2. References.