Native Ada runner API¶
For authors writing a workflow runner in Ada 2012. The Ada SDK is a thin
Interfaces.C binding over the native C SDK in native/c/. It does not
reimplement the bridge protocol: every verb reaches
$HTTK_WORKFLOW_PYTHON -m httk.workflow._shell_bridge, while only
--describe is native. The C library owns registration, dispatch, and process
exit status, so Ada runners publish the same protocol bytes as C, Bash,
Fortran, and Python runners.
The package is httk_workflow.ads plus httk_workflow.adb under
native/ada/. It uses only Ada 2012 standard packages and GNAT’s normal
compiler/runtime. Build the C source separately, then link it through
gnatmake:
cc -std=c99 -c .../native/c/httk_workflow.c -o httk_workflow_c.o
gnatmake -gnat2012 -gnatwa -gnatwe -I.../native/ada \
-o runner runner.adb -largs httk_workflow_c.o
Registration and dispatch¶
Httk_Workflow_Runner takes a workflow name, an array of
Unbounded_String step names, and an array of Step_Handler values. A handler
is a library-level C-convention function returning Interfaces.C.int:
function Step_Prepare return Interfaces.C.int with Convention => C;
function Step_Prepare return Interfaces.C.int is
begin
if Httk_Workflow_Advance ("run") /= 0 then null; end if;
return 0;
end Step_Prepare;
Handlers must be declared at library level. A nested handler’s 'Access would
require a GNAT stack trampoline and an executable stack, so nested handlers are
not supported.
The C struct contains an int (*)(void), so handlers must return an integer;
procedures are undefined behavior. Httk_Workflow_Main forwards the Ada
command line to httk_workflow_main, which dispatches the registered handler
and owns the final status. Call Httk_Workflow_Exit with that status because
Ada’s normal program termination would otherwise return zero.
Every ending has the C semantics:
Handler ending |
Result |
|---|---|
publishes and returns |
the published outcome |
returns |
|
requested step is absent |
|
returns nonzero |
|
The last row inherits the C layer’s breadcrumb label, CError. There is no
AdaError: dispatch and abnormal-handler classification happen in the C
library.
Httk_Workflow_Describe prints the native description. Passing --describe
to Httk_Workflow_Main, or setting HTTK_WORKFLOW_DESCRIBE=1, produces the
same bytes as the Bash SDK for the same workflow and steps.
Ada-to-C mapping¶
The public package keeps the C names and groups, with Ada strings copied into
Interfaces.C.Strings.chars_ptr values for each call:
Ada |
C |
|---|---|
|
|
|
|
|
|
|
corresponding |
|
|
|
corresponding |
|
corresponding transactional/child C functions |
|
|
|
corresponding outcome C functions |
|
corresponding C functions |
|
|
|
|
Tail arguments use String_List, an array of Unbounded_String; No_Arguments
passes a C NULL array. Httk_Workflow_Parameter, Setting, and Environment
have overloads with and without a fallback. Httk_Workflow_Exit is the Ada
counterpart of returning from a C main.
Strings, ownership, and absent reads¶
Input String values are copied to temporary NUL-terminated C strings and
released after the call. C string results are returned as freshly malloc’d
strings under the C contract. The binding copies each result into an Ada
Unbounded_String and releases the original with libc free, exactly once.
Read procedures return both Present : Boolean and Status : C.int:
Value : Ada.Strings.Unbounded.Unbounded_String;
Present : Boolean;
Status : Interfaces.C.int;
Httk_Workflow_State_Get ("energy", Value, Present, Status);
An allocated empty C string means Present = True and Status = 0. A NULL
answer means Present = False; status 1 is a legitimate absent answer and
status 2 is a refused call. Thus absent and present-empty values do not
collapse. The same rule applies to operation ids, child keys, declarations,
context values, calculated values, and other C string returns.
The status constants are HTTK_WORKFLOW_OK (0),
HTTK_WORKFLOW_ABSENT (1), and HTTK_WORKFLOW_REFUSED (2).
Httk_Workflow_Run instead returns the supervised program classification:
0, 22 for a nonzero program exit, 124 for timeout, and 125 for a
checker or diagnostic stop.
The relaxation example¶
examples/relax_ada/relax.adb registers the library-level handlers from
relax_steps.ads/relax_steps.adb and declares httk.vasp.relax-ada with
prepare, run, and publish steps. It stages files/POSCAR, resolves
vasp.command, invokes Httk_Workflow_Run, records the completion state, and
stages VASP outputs into transactional data. It is driven by the same mock VASP
flow as the other native SDK examples:
cd examples/relax_ada
make
./relax --describe
The Makefile uses cc -std=c99 for the C object and
gnatmake -gnat2012 -gnatwa -gnatwe for Ada, with no executable-stack linker
flag.