tricu

A lazy functional language based on Tree Calculus
Log | Files | Refs | README | LICENSE

README.md (3432B)


Native PHP binding

64-bit PHP with the FFI extension uses the Haskell embedding ABI. The Nix package selects that runtime and extension:

nix build .#tricu-php .#tricu-php-tests --no-link
PHP=$(nix path-info .#tricu-php)
"$PHP/bin/tricu-php" run test/fixtures/id.arboricx id hello
"$PHP/bin/tricu-php" run test/fixtures/false.arboricx false --format bool

Require $PHP/share/tricu-php/src/ffi.php, then use Arboricx\Library:

$ctx = (new Arboricx\Library())->context();
try {
    $number = $ctx->number('18446744073709551615');
    echo $ctx->toNumber($number); // exact decimal string
} finally {
    $ctx->close();
}

Library($path) selects a library explicitly. Default discovery checks TRICU_LIB and the installed library beside the PHP sources. The header comes from the installed package or the repository's Haskell interface. A selected process uses one runtime-library path. Keep the complete native runtime closure; Nix retains it automatically.

Handles are opaque FFI\CData uint64 scalars. Pass them back to context methods; PHP integer casts are unnecessary. number accepts nonnegative PHP integers or canonical decimal uint64 strings. toNumber always returns an exact decimal string, including small numbers. This preserves unsigned values beyond PHP's signed integer range. PHP strings carry both byte buffers (bytes/toBytes) and strict UTF-8 text (string/toString), preserving embedded NULs.

loadBundle($bytes, $exportName) verifies a bundle and selects an explicit export. apply suspends application; reduce demands only the outer constructor. kind returns 0/1/2 for Leaf/Stem/Fork, and child returns an owned handle. toBool checks the canonical boolean shapes. runIO returns an array with outcome, value, and cleanup: outcome 0/1/2 means completed/failed/cancelled, and both payload handles are owned. Task reasons stay opaque until observed; ordinary error Results may be completion values. Boundary failures throw Arboricx\TricuError with numeric status and diagnostic text.

Release intermediate handles in long-lived contexts. Explicit close releases all remaining roots and is idempotent. Destruction also releases abandoned contexts. Returned byte/text buffers are copied to PHP strings and freed in finally. Native calls are synchronous. IO uses OS process authority; use trusted programs or supervised processes with resource limits.

The Linux library is pinned in memory across dlclose, matching GHC's process lifetime even when PHP releases a request-scoped FFI object. Checks cover CLI execution and repeated uploads/errors in one PHP built-in server process. Initialize GHC in the process that executes the bundle; after a fork, use a fresh executable process for embedding.

The public/ example runs pure uploaded bundles with an explicit export and result format. Requests select pure bundle execution. Run this example under external process supervision with execution and memory limits for uploaded computations.

The CLI requires run BUNDLE EXPORT, accepts text arguments, and supports --io and --format string|number|bool|bytes (default string; bytes render as hex). -- ends option parsing. Terminal task failure/cancellation exits nonzero with its reason left opaque. Fuel/collection helpers, implicit export selection, heuristic decoding, and the old inspect CLI are retired here.