tflite-c-rs 0.0.1

Safe Rust wrapper for the TensorFlow Lite C API via runtime dynamic loading (libloading) — no build-time TFLite link required.
Documentation
//! Error type returned by fallible operations in this crate.

use std::ffi::NulError;
use std::path::PathBuf;

use thiserror::Error;

use crate::ffi::{TfLiteStatus, TfLiteType};

/// Errors that can arise while loading the TensorFlow Lite shared library,
/// building an interpreter, or operating on tensors.
#[derive(Debug, Error)]
pub enum Error {
    /// None of the candidate shared-library paths could be opened.
    ///
    /// The `paths` list records every probe attempt in order. The `source`
    /// contains the last underlying `libloading` failure, which is usually
    /// the most informative.
    #[error("could not load TensorFlow Lite shared library (tried {paths:?})")]
    LoadFailed {
        /// Underlying loader error from the last attempted path.
        #[source]
        source: libloading::Error,
        /// All candidate paths that were probed, in the order they were tried.
        paths: Vec<String>,
    },

    /// The shared library opened but a required exported symbol was missing.
    #[error("symbol `{name}` not found in TensorFlow Lite shared library")]
    SymbolNotFound {
        /// Name of the missing symbol (matches the upstream C identifier).
        name: &'static str,
        /// Underlying loader error.
        #[source]
        source: libloading::Error,
    },

    /// `TfLiteModelCreateFromFile` returned NULL for the given path.
    #[error("failed to load model from {path:?}")]
    ModelLoadFailed {
        /// Filesystem path passed to the loader.
        path: PathBuf,
    },

    /// A filesystem path could not be expressed as a C string (non-UTF-8 or
    /// embedded NUL byte).
    #[error("path could not be passed to the C API: {0}")]
    InvalidPath(#[source] NulError),

    /// A delegate option key/value pair contained an embedded NUL byte.
    #[error("delegate option key or value contained an embedded NUL byte: {0}")]
    InvalidOption(#[source] NulError),

    /// `TfLiteInterpreterCreate` returned NULL.
    #[error("failed to create TensorFlow Lite interpreter")]
    InterpreterCreateFailed,

    /// `TfLiteInterpreterAllocateTensors` returned a non-Ok status.
    #[error("interpreter failed to allocate tensors")]
    AllocateTensorsFailed,

    /// `TfLiteInterpreterInvoke` returned a non-Ok status.
    #[error("interpreter invocation failed with status {status:?}")]
    InvokeFailed {
        /// Raw status code returned by the C API.
        status: TfLiteStatus,
    },

    /// Tensor index was out of bounds for the interpreter.
    #[error("tensor index {index} out of bounds (count is {count})")]
    TensorIndexOutOfBounds {
        /// The requested tensor index.
        index: usize,
        /// The number of tensors available.
        count: usize,
    },

    /// The tensor's actual element type did not match the typed accessor.
    #[error("tensor dtype mismatch: expected {expected:?}, got {actual:?}")]
    DtypeMismatch {
        /// The element type the caller requested.
        expected: TfLiteType,
        /// The element type the tensor actually has.
        actual: TfLiteType,
    },

    /// A tensor handle returned by the C API was unexpectedly NULL.
    #[error("tensor handle was NULL")]
    NullTensor,

    /// A tensor's data pointer was unexpectedly NULL.
    #[error("tensor data pointer was NULL")]
    NullData,

    /// `TfLiteExternalDelegateCreate` returned NULL.
    #[error("failed to create external delegate")]
    DelegateCreateFailed,

    /// The C API rejected an external-delegate option (non-Ok status).
    #[error("setting external delegate option failed with status {status:?}")]
    DelegateOptionRejected {
        /// Raw status returned by the C API.
        status: TfLiteStatus,
    },

    /// The loaded TFLite library does not export the `TfLiteExternalDelegate*`
    /// symbol group, so this crate cannot construct an [`crate::ExternalDelegate`].
    ///
    /// These symbols live in TFLite's experimental C header and are routinely
    /// omitted from prebuilt shared objects. The core load → invoke path
    /// remains fully functional — only external-delegate construction is
    /// blocked.
    #[error("loaded TFLite library does not export the TfLiteExternalDelegate* symbol group")]
    ExternalDelegateApiUnavailable,
}

/// Convenience alias for `Result<T, tflite_c::Error>`.
pub type Result<T> = std::result::Result<T, Error>;