Crate wolfram_library_link

Source
Expand description

A safe and ergonomic wrapper around Wolfram LibraryLink.

Wolfram LibraryLink is an interface for dynamic libraries that can be dynamically loaded by the Wolfram Language. This crate provides idiomatic Rust bindings around the lower-level LibraryLink C interface.

Features:

  • Call Rust functions from Wolfram code.
  • Pass data efficiently between Rust and Wolfram code using native data types like NumericArray and Image.
  • Pass arbitrary expressions between Rust and Wolfram code using Expr and the #[export(wstp)] macro.
  • Generate asynchronous events handled by the Wolfram Language, using an AsyncTaskObject background thread.

Wolfram LibraryLink provides a powerful way to connect external code to the Wolfram Language, enabling high-speed and memory-efficient execution. It does this by allowing dynamic libraries to be directly loaded into the Wolfram Language kernel so that functions in the libraries can be immediately called from the Wolfram Language.

    — Wolfram LibraryLink User Guide

§Library function types

The Wolfram LibraryLink interface supports two different types of library function:

  • Native functions
  • WSTP functions

The two function types differ in how their arguments and return value are passed between the Wolfram Language and the compiled library function.

Native functions pass their values using efficient native data types, like machine sized integers, floating point numbers, C strings, or NumericArrays. Calling a native function is efficient, but they are unable to pass more complicated values (like general Wolfram Language expressions).

WSTP functions pass their values using WSTP Link objects. A Link object can be used to pass arbitrary Wolfram Language expressions to or from the library function. However, WSTP links are less efficient for passing basic numeric arguments.

§Examples

Example programs: In addition to the basic example programs show below, the wolfram-library-link repository contains example programs demonstrating the major features of this crate.

Quick Start: The LibraryLink for Rust Quick Start is a complete tutorial covering how to create a new Rust library, compile it, and call into it from the Wolfram Language.

§Native functions

Rust functions can be exported for use from the Wolfram Language using the #[export] macro:

use wolfram_library_link::export;

#[export]
fn square(x: i64) -> i64 {
    x * x
}

Then, after building the Rust code into a dynamic library, the function can be loaded into the Wolfram Language using LibraryFunctionLoad:

square = LibraryFunctionLoad["<library name>", "square", {Integer}, Integer];

After being loaded, a library function can be called like any other Wolfram Language function:

square[5]   (* Returns 25 *)

§WSTP Functions

Rust WSTP functions can be exported for use from the Wolfram Language using the #[export(wstp)] macro:

use wolfram_library_link::{export, wstp::Link};

#[export(wstp)]
fn square(link: &mut Link) {
    // WSTP function arguments are passed as a List expression: {...}
    let arg_count = link.test_head("System`List").unwrap();

    // Get that the argument list contains a single element.
    if arg_count != 1 {
        panic!("square: expected one argument")
    }

    // Check that the argument is an integer, and get it's value.
    let x: i64 = link.get_i64().expect("expected Integer argument");

    // Write the return value.
    link.put_i64(x * x).unwrap();
}

§Documentation

See the docs module for a complete list of available long-form documentation.


§Additional Features

§Non-primitive native types

Native functions support passing primitive types like bool, i64, f64, and strings. Additionally, they also support a small number of non-primitive types that can be used to efficiently pass more complicated data structures between the Wolfram Langauge and compiled code, without requiring the full generality of using a WSTP function.

The set of currently supported non-primitive native types includes:

§Cooperative computation abort handling

The Wolfram Language supports the ability for the user to abort an in-progress computation, without ending the process and losing their current state. This is accomplished by code that checks if an abort has been triggered — and if so, performs an early return — which is placed at important points in the Wolfram Language kernel evaluation process.

User libraries can cooperatively include abort checking logic in their library using the aborted() function. This enables LibraryLink libraries to provide the same user experience as built in Wolfram Language functions. LibraryLink libraries that may perform long computations are especially encouraged to do abort checking within loops that may run for a long time.

use wolfram_library_link as wll;

if wll::aborted() {
    // The user aborted this computation, so it doesn't matter what we return.
    panic!("Wolfram abort");
}

Note: The Wolfram Language ‘abort’ command is not at all related to the C/Rust abort() function. The abort() function is typically used when an unrecoverable error occurs, at a point determined by the programmer. The Wolfram ‘abort’ command can be issued by the user at any point, and is commonly used to end long-running computations the user no longer wishes to wait for.

§Show backtrace when a panic occurs

WSTP functions will automatically catch any Rust panics that occur in the wrapped code, and return a Failure object with the panic message and source file/line number. The failure can optionally include a backtrace showing the location of the panic.

This is configured by the "LIBRARY_LINK_RUST_BACKTRACE" environment variable. Enable it by evaluating:

SetEnvironment["LIBRARY_LINK_RUST_BACKTRACE" -> "True"]

Now the error shown when a panic occurs will include a backtrace.

The error message may include more information if the "nightly" feature of wolfram-library-link is enabled.

Re-exports§

pub use wolfram_library_link_sys as sys;
pub use wstp;

Modules§

docs
Documentation articles about the usage of wolfram-library-link.
expr
Efficient and ergonomic representation of Wolfram expressions in Rust.
managed
Managed expressions.
rtl
Lazy bindings to Wolfram Runtime Library (RTL) functions.

Macros§

generate_loader
Generate and export a “loader” function, which returns an Association containing the names and loaded forms of all functions exported by this library.

Structs§

AsyncTaskObject
Handle to a Wolfram Language AsynchronousTaskObjectWL instance.
DataStore
Storage for heterogenous expression-like data.
DataStoreNode
Element borrowed from the linked list of nodes that make up a DataStore.
Image
Native Wolfram ImageWL or Image3DWL.
Nodes
Iterator over the DataStoreNodes stored in a DataStore.
NumericArray
Native Wolfram NumericArrayWL.
UninitImage
Represents an allocated Image whose image data has not yet been initialized.
UninitNumericArray
Represents an allocated NumericArray whose elements have not yet been initialized.
WolframLibraryData

Enums§

ColorSpace
Color space used by an Image.
DataStoreNodeValue
Value of a DataStoreNode.
ImageType
Type of data stored in an Image.
NumericArrayConvertMethod
Conversion method used by NumericArray::convert_to().
NumericArrayDataType
The type of the data being stored in a NumericArray.
NumericArrayKind
Data array borrowed from a NumericArray.
Pixel
Position of a pixel position in an Image.

Traits§

FromArg
Trait implemented for types that can be passed via an MArgument.
ImageData
Trait implemented for types that can logically be stored in an Image.
IntoArg
Trait implemented for types that can be returned via an MArgument.
NativeFunction
Trait implemented for any function whose parameters and return type are native LibraryLink MArgument types.
NumericArrayType
Trait implemented for types that can be stored in a NumericArray.
WstpFunction
Trait implemented for any function whose parameters and return type can be passed over a WSTP Link.

Functions§

aborted
Returns true if the user has requested that the current evaluation be aborted.
evaluate
Evaluate expr by calling back into the Wolfram Kernel.
exported_library_functions_association
Returns an Association containing the names and LibraryFunctionLoad calls for every function in this library marked with #[export(..)].
get_library_data
Get the WolframLibraryData instance recorded by the last call to initialize().
initialize
Initialize static data for the current Wolfram library.
try_evaluate
Attempt to evaluate expr, returning an error if a WSTP transport error occurred or evaluation failed.

Attribute Macros§

export
Export the specified functions as native LibraryLink functions.
init
Designate an initialization function to run when this library is loaded via Wolfram LibraryLink.