Read the solver’s output
In this release the Solver prints JSON to the terminal. A human-readable format is planned. Until it lands, this page tells you which fields to read and gives one-liners that reduce the output to a short summary.
The fields that matter
Every successful run prints one JSON object with these fields:
result.outcomeis the answer itself. Itsshapefield says how to read the rest:"attainable_set"(fromevaluate, and fromcheck --predicate): the values the expression can take, in the two listings described below."approximated"(from a model with behavior that can run forever): the same two listings, computed within the explored depth. See Explore state machine reachability."assertions"(fromcheckwithout--predicate): a list of assertions, each with itsnameand its ownoutcomein one of the two shapes above. An assertion’s outcome lists which oftrueandfalsethe assertion can take.
attainableandunattainableare the two listings in every outcome. Each hasvalues,exhaustiveand, when the Solver gave up, areason:attainable.valueslists every value known to be possible, each with awitness(the values of the model’s features that produce it). On a model with behavior over time, a value carries atraceinstead (the run that reaches it, snapshot by snapshot).unattainable.valueslists every value known to be impossible. For a boolean expression this is how “must be true” reads: an assertion that holds in every allowed situation hasfalseinunattainable.values.exhaustivesays whether a listing is complete."true"means no other value belongs in it."false"means the listing is not complete, for example because--max-valuescut it off or because the values cannot all be listed."undetermined"means the method does not settle completeness, such as the bounded depth of a state machine exploration."unknown"means the Solver gave up (for example, at a--solver-limitor--timeout, see Check that requirements hold), or the answer depends on part of the model it could not analyze, andreasonsays which.
result.determinationsays whether the model pins the answer down.determinedmeans the model has a single answer.undeterminedmeans the answer varies with values the model leaves open.inconsistentmeans the model allows no situation at all, so there is no value to list.unknownmeans the Solver could not decide enough to say.result.causesnames what kept the answer from being a single determined value. Anunanalyzableentry carries thereasonsa part of the model could not be analyzed (see Handle unsupported syntax). Anunknownentry New in v1.0.0 names open values whose effect on the answer the Solver could not decide, with thereason, for example{"unknown": {"names": ["Battery::battery.cellB.voltage"], "reason": "solver limit exhausted: the check exceeded --solver-limit 1"}}.warningslists the parts of the model the Solver had to skip, with reasons.alt_semanticsappears when you pass--alt-semantics, and records every active override with its description. See Add assumptions.fail_when(fromcheck) echoes the--fail-whenmode that decided the exit code. See Check that requirements hold.exit_codeis also the process exit code: 0 for an answer that passes, 1 for acheckthat fails its--fail-whenmode, 2 for a model or query that could not be loaded.
A few fields appear only in specific outputs:
A witness of a sum over a collection can carry a
partitionsfield, listing for eachcollectionhow its members are grouped (members in one group are the same individual).A witness can carry an
orderfield, listing the snapshots of a feature written more than once in the order they occur.A witness of a requirement can carry an
unwritten_membersentry, naming an openrequireorassumeside whose unwritten members take the listed value.An outcome on a model with behavior over time carries
integral, which says whether every listed value is an integer.
Changed in version 1.0.0: Before 1.0.0, a check assertion carried a status (satisfied, violated or
unanalyzable) with a counterexample or a reason, and check --predicate used a
"predicate" shape with a single status. An attainable set listed its values in
values (or proven, for a state machine) and had no unattainable listing. A
former satisfied is now false in unattainable.values. A former violated is
false in attainable.values, and its witness replaces the counterexample. A former
unanalyzable is an exhaustive of "unknown" with a reason.
Getting a short summary with jq
jq is a widely used command-line tool for slicing JSON. On
Windows, install it with winget install jqlang.jq. On macOS, use brew install jq. On Linux, it is in every major package manager.
On Windows, set PYTHONUTF8 before piping the output into another program,
so that the program receives UTF-8 text. In PowerShell, run
$env:PYTHONUTF8 = "1". In Command Prompt, run set PYTHONUTF8=1. The
setting lasts until you close that window.
The attainable truth values of each assertion, one line per assertion (works on any
check run without --predicate):
syside solver check -i pump.sysml | jq -r \
'.result.outcome.assertions[]
| "\(.name): \(.outcome.attainable.values | map(.value) | join(","))"'
Pump::flowOk: true
Pump::pressureOk: false,true
An assertion that lists false can fail.
The witness of every assertion that can fail:
syside solver check -i pump.sysml | jq -r \
'.result.outcome.assertions[] | .name as $n
| .outcome.attainable.values[] | select(.value == "false")
| .witness.values[] | "\($n): \(.[0]) = \(.[1])"'
Pump::pressureOk: Pump::pump.pressure = 11
Just the values from an evaluate run:
syside solver evaluate -i battery.sysml \
--expr "Battery::battery.totalVoltage" | jq -r \
'.result.outcome.attainable.values[].value'
-9
-8
-7
-6
-5
-4
-3
-2
-1
0
Without jq: PowerShell
Windows PowerShell can parse JSON with no extra installation. Run
$env:PYTHONUTF8 = "1" first:
syside solver check -i pump.sysml | ConvertFrom-Json |
ForEach-Object { $_.result.outcome.assertions } |
Select-Object name, @{ Name = "attainable"; Expression = {
($_.outcome.attainable.values | ForEach-Object { $_.value }) -join "," } }
name attainable
---- ----------
Pump::flowOk true
Pump::pressureOk false,true
Keeping the full output
The JSON is a complete record of the run. For an audit trail, redirect it to a file and summarize from there:
syside solver check -i pump.sysml > check-result.json