API Reference

SDK-REF-009 v1.0

Complete C API reference for libquac100. All functions are declared in <quac100/quac100.h>. Thread safety, memory ownership, and FIPS applicability are noted for each function. Functions marked [FIPS] are available in FIPS 140-3 mode; those marked [Permissive] are restricted to permissive mode only.

Overview #

The libquac100 API is organized into functional groups. All functions return quac_status_t unless otherwise noted. Output buffers are always caller-allocated. The API is fully re-entrant and thread-safe — multiple threads can share a single quac_device_t handle without external locking.

GroupHeaderFunctionsDescription
Corequac100.h12Init, shutdown, device open/close, versioning
KEMquac100_kem.h8Key encapsulation: keygen, encaps, decaps, hybrid
Signaturequac100_sig.h8Digital signatures: keygen, sign, verify, hybrid
Randomquac100_rand.h6QRNG, DRBG, seed management
Key Mgmtquac100_keymgmt.h14Persistent keys, wrapping, lifecycle
Asyncquac100_async.h16Async submission, batch, callbacks, queue mgmt
Diagnosticsquac100_diag.h10Device info, health, POST, audit, temperature

Conventions #

Return Values

All functions return quac_status_t (int32_t). A return value of QUAC_OK (0) indicates success. Negative values indicate errors. Use quac_strerror() to convert error codes to human-readable strings.

Memory Ownership

The caller owns all input and output buffers. The SDK never allocates memory on behalf of the caller. Output buffers must be large enough to hold the result — use the quac_*_output_size() helper functions to query required sizes. Input buffers can be freed or reused immediately after the synchronous call returns.

Thread Safety

All functions are safe to call concurrently from multiple threads on the same quac_device_t handle. The SDK uses internal lock-free ring buffers for hardware communication. No external synchronization is required.

Naming Convention

Functions follow the pattern quac_{group}_{action}. Types follow quac_{group}_{noun}_t. Constants follow QUAC_{GROUP}_{NAME}.

Initialization & Device #

quac_init

quac_status_t quac_init(void);

Initialize the QuantaCore SDK. Must be called once before any other SDK function. Loads the kernel driver interface, initializes internal thread pools, and performs library self-checks. [FIPS] Thread-safe (uses internal once-initialization).

quac_init_ex

quac_status_t quac_init_ex(const quac_init_config_t *config);

Extended initialization with configuration options. Allows setting log level, log callback, memory allocator overrides, and thread pool sizes. Pass NULL for defaults (equivalent to quac_init()). [FIPS]

FieldTypeDefaultDescription
log_levelquac_log_level_tQUAC_LOG_WARNMinimum log severity
log_callbackquac_log_cb_tNULL (stderr)Custom log handler
allocquac_allocator_t*NULL (malloc/free)Custom memory allocator
async_threadsuint32_t4Completion callback thread pool size

quac_shutdown

quac_status_t quac_shutdown(void);

Shut down the SDK and release all resources. All device handles must be closed before calling. Waits for pending async operations to complete (up to 5 seconds). [FIPS]

quac_open

quac_device_t *quac_open(uint32_t device_index);

Open a QUAC 100 device by index (0-based). Returns a device handle on success, NULL on failure. Call quac_get_last_error() to retrieve the error code. The returned handle is thread-safe. [FIPS]

quac_open_ex

quac_device_t *quac_open_ex(uint32_t device_index, const quac_device_config_t *config);

Extended device open with configuration. Allows setting queue depth, interrupt coalescing, DMA preferences, NUMA affinity, and callback thread configuration. [FIPS]

quac_close

quac_status_t quac_close(quac_device_t *dev);

Close a device handle. Zeroizes all ephemeral session keys, waits for in-flight async operations, and releases kernel resources. The handle is invalid after this call. [FIPS]

quac_enumerate

quac_status_t quac_enumerate(quac_device_info_t *devices, size_t max_devices, size_t *n_found);

Enumerate all QUAC 100 devices in the system. Populates the devices array with device index, PCIe BDF address, serial number, firmware version, and operational status. Does not require quac_open(). [FIPS]

quac_get_version

const char *quac_get_version(void);

Return the SDK version string (e.g., "1.2.0"). Does not require initialization. [FIPS]

quac_get_version_numeric

uint32_t quac_get_version_numeric(void);

Return the SDK version as a packed integer: (major << 16) | (minor << 8) | patch. Useful for compile-time version checks. [FIPS]

KEM Functions #

quac_kem_keygen

quac_status_t quac_kem_keygen(quac_device_t *dev, quac_kem_alg_t alg, quac_kem_keypair_t *kp);

Generate a KEM key pair. The private key and public key are written to kp. Key material is generated using hardware QRNG. [FIPS] for ML-KEM-512/768/1024.

AlgorithmConstantPK SizeSK Size
ML-KEM-512QUAC_KEM_ML_KEM_512800 bytes1,632 bytes
ML-KEM-768QUAC_KEM_ML_KEM_7681,184 bytes2,400 bytes
ML-KEM-1024QUAC_KEM_ML_KEM_10241,568 bytes3,168 bytes

quac_kem_encaps

quac_status_t quac_kem_encaps(quac_device_t *dev, quac_kem_alg_t alg,
    const uint8_t *pk, size_t pk_len,
    uint8_t *ct, size_t *ct_len,
    uint8_t *ss, size_t *ss_len);

Encapsulate a shared secret using the recipient's public key. Writes ciphertext to ct and shared secret to ss. The shared secret is always 32 bytes for all ML-KEM parameter sets. [FIPS]

quac_kem_decaps

quac_status_t quac_kem_decaps(quac_device_t *dev, quac_kem_alg_t alg,
    const uint8_t *sk, size_t sk_len,
    const uint8_t *ct, size_t ct_len,
    uint8_t *ss, size_t *ss_len);

Decapsulate a shared secret using the private key and ciphertext. Implements implicit rejection — if decapsulation fails, a deterministic but unpredictable shared secret is returned (no error code distinguishes valid from invalid ciphertext). [FIPS]

quac_kem_output_size

quac_status_t quac_kem_output_size(quac_kem_alg_t alg,
    size_t *ct_size, size_t *ss_size);

Query the ciphertext and shared secret sizes for a given KEM algorithm. Use to allocate output buffers before calling quac_kem_encaps(). [FIPS]

quac_kem_hybrid_encaps

quac_status_t quac_kem_hybrid_encaps(quac_device_t *dev,
    quac_kem_alg_t pq_alg, const uint8_t *pq_pk, size_t pq_pk_len,
    quac_kem_classical_t classical_alg, const uint8_t *classical_pk, size_t classical_pk_len,
    quac_hybrid_mode_t mode,
    uint8_t *ct, size_t *ct_len,
    uint8_t *ss, size_t *ss_len);

Perform hybrid KEM encapsulation combining a post-quantum and classical algorithm. The shared secret is derived by concatenating and hashing both component secrets using HKDF-SHA3-256. Supported classical algorithms: QUAC_KEM_X25519, QUAC_KEM_X448, QUAC_KEM_ECDH_P256, QUAC_KEM_ECDH_P384. [FIPS]

quac_kem_hybrid_decaps

quac_status_t quac_kem_hybrid_decaps(quac_device_t *dev,
    quac_kem_alg_t pq_alg, const uint8_t *pq_sk, size_t pq_sk_len,
    quac_kem_classical_t classical_alg, const uint8_t *classical_sk, size_t classical_sk_len,
    quac_hybrid_mode_t mode,
    const uint8_t *ct, size_t ct_len,
    uint8_t *ss, size_t *ss_len);

Hybrid KEM decapsulation. Counterpart to quac_kem_hybrid_encaps(). [FIPS]

Signature Functions #

quac_sig_keygen

quac_status_t quac_sig_keygen(quac_device_t *dev, quac_sig_alg_t alg, quac_sig_keypair_t *kp);

Generate a signature key pair. [FIPS] for ML-DSA and SLH-DSA parameter sets.

AlgorithmConstantPK SizeSK SizeSig Size
ML-DSA-44QUAC_SIG_ML_DSA_441,312 B2,560 B2,420 B
ML-DSA-65QUAC_SIG_ML_DSA_651,952 B4,032 B3,309 B
ML-DSA-87QUAC_SIG_ML_DSA_872,592 B4,896 B4,627 B
SLH-DSA-128sQUAC_SIG_SLH_DSA_128S32 B64 B7,856 B
SLH-DSA-128fQUAC_SIG_SLH_DSA_128F32 B64 B17,088 B
SLH-DSA-192sQUAC_SIG_SLH_DSA_192S48 B96 B16,224 B
SLH-DSA-256sQUAC_SIG_SLH_DSA_256S64 B128 B29,792 B

quac_sign

quac_status_t quac_sign(quac_device_t *dev, quac_sig_alg_t alg,
    const uint8_t *sk, size_t sk_len,
    const uint8_t *msg, size_t msg_len,
    uint8_t *sig, size_t *sig_len);

Sign a message. The signature is written to sig and the actual length to *sig_len. For ML-DSA, signing is randomized (nonce generated from QRNG). For SLH-DSA, signing is deterministic. [FIPS]

quac_verify

quac_status_t quac_verify(quac_device_t *dev, quac_sig_alg_t alg,
    const uint8_t *pk, size_t pk_len,
    const uint8_t *msg, size_t msg_len,
    const uint8_t *sig, size_t sig_len);

Verify a signature. Returns QUAC_OK if the signature is valid, QUAC_ERR_VERIFY_FAILED if invalid. The function is constant-time — the return time does not depend on whether the signature is valid. [FIPS]

quac_sign_hybrid

quac_status_t quac_sign_hybrid(quac_device_t *dev,
    quac_sig_alg_t pq_alg, const uint8_t *pq_sk, size_t pq_sk_len,
    quac_sig_classical_t classical_alg, const uint8_t *classical_sk, size_t classical_sk_len,
    quac_hybrid_mode_t mode,
    const uint8_t *msg, size_t msg_len,
    uint8_t *sig, size_t *sig_len);

Create a hybrid signature combining PQ and classical algorithms. The output format concatenates both signatures with a type header. [FIPS]

quac_verify_hybrid

quac_status_t quac_verify_hybrid(quac_device_t *dev,
    quac_sig_alg_t pq_alg, const uint8_t *pq_pk, size_t pq_pk_len,
    quac_sig_classical_t classical_alg, const uint8_t *classical_pk, size_t classical_pk_len,
    quac_hybrid_mode_t mode,
    const uint8_t *msg, size_t msg_len,
    const uint8_t *sig, size_t sig_len);

Verify a hybrid signature. In QUAC_HYBRID_BOTH mode, both signatures must be valid. In QUAC_HYBRID_EITHER, at least one must be valid. [FIPS]

quac_sig_output_size

quac_status_t quac_sig_output_size(quac_sig_alg_t alg, size_t *sig_size);

Query the maximum signature size for a given algorithm. [FIPS]

Random Generation #

quac_random

quac_status_t quac_random(quac_device_t *dev, uint8_t *buf, size_t len);

Generate cryptographically secure random bytes using the hardware QRNG source passed through the SP 800-90A CTR_DRBG. This is the recommended function for all general-purpose random number generation. [FIPS]

quac_random_raw

quac_status_t quac_random_raw(quac_device_t *dev, uint8_t *buf, size_t len);

Generate raw quantum random bytes directly from the QRNG entropy source, bypassing the DRBG. Output passes SP 800-90B continuous health tests. Maximum 1 MB per call. [Permissive] — raw QRNG output is not FIPS-approved without DRBG conditioning.

quac_random_seed

quac_status_t quac_random_seed(quac_device_t *dev, const uint8_t *additional_input, size_t len);

Provide additional entropy input to the DRBG. This is mixed with the QRNG seed, not used as the sole seed source. Useful for incorporating application-specific entropy. [FIPS]

quac_random_reseed

quac_status_t quac_random_reseed(quac_device_t *dev);

Force an immediate DRBG reseed from the QRNG source. The DRBG automatically reseeds every 2^48 generate calls; this function triggers an early reseed. [FIPS]

quac_random_health

quac_status_t quac_random_health(quac_device_t *dev, quac_rng_health_t *health);

Query the health status of the QRNG entropy source and DRBG. Returns entropy rate estimate, continuous health test results, and reseed counter. [FIPS]

FieldTypeDescription
entropy_rate_bpsdoubleEstimated entropy rate in bits per sample
health_test_passedboolSP 800-90B continuous health test status
repetition_count_okboolRepetition count test status
adaptive_proportion_okboolAdaptive proportion test status
drbg_reseed_counteruint64_tNumber of generate calls since last reseed
total_bytes_generateduint64_tTotal random bytes generated since power-on

Key Management #

quac_key_generate

quac_status_t quac_key_generate(quac_device_t *dev, const quac_key_attrs_t *attrs, quac_key_handle_t *handle);

Generate a persistent key stored within the hardware cryptographic boundary. The key is identified by the returned handle and optionally by the label set in attrs. [FIPS]

quac_key_import

quac_status_t quac_key_import(quac_device_t *dev, const quac_key_attrs_t *attrs,
    const uint8_t *key_data, size_t key_len, quac_key_handle_t *handle);

Import a key from external material. In FIPS mode, only wrapped (encrypted) key data is accepted. In permissive mode, plaintext keys can be imported. [FIPS] (wrapped only)

quac_key_find

quac_status_t quac_key_find(quac_device_t *dev, const char *label, quac_key_handle_t *handle);

Find a persistent key by its label. Returns QUAC_ERR_NOT_FOUND if no key with the given label exists. [FIPS]

quac_key_get_info

quac_status_t quac_key_get_info(quac_key_handle_t handle, quac_key_info_t *info);

Query metadata about a key: algorithm, usage flags, lifecycle state, creation time, expiration, and label. Does not expose key material. [FIPS]

quac_key_get_state

quac_status_t quac_key_get_state(quac_key_handle_t handle, quac_key_state_t *state);

Query the lifecycle state of a key. [FIPS]

quac_key_activate / quac_key_deactivate / quac_key_suspend

quac_status_t quac_key_activate(quac_key_handle_t handle);
quac_status_t quac_key_deactivate(quac_key_handle_t handle);
quac_status_t quac_key_suspend(quac_key_handle_t handle);

Transition a key through lifecycle states. Invalid transitions return QUAC_ERR_INVALID_STATE. [FIPS]

quac_key_destroy

quac_status_t quac_key_destroy(quac_key_handle_t handle);

Permanently destroy a key. Key material is zeroized using 3-pass overwrite with verification. The handle is invalid after this call. [FIPS]

quac_key_wrap / quac_key_unwrap

quac_status_t quac_key_wrap(quac_key_handle_t key, quac_key_handle_t wrapping_key,
    quac_wrap_alg_t alg, uint8_t *out, size_t out_cap, size_t *out_len);
quac_status_t quac_key_unwrap(quac_device_t *dev, quac_key_handle_t wrapping_key,
    quac_wrap_alg_t alg, const uint8_t *data, size_t data_len,
    const quac_key_attrs_t *attrs, quac_key_handle_t *handle);

Wrap (export) or unwrap (import) a key using AES Key Wrap with Padding (AES-KWP). The wrapping key must be stored in hardware. [FIPS]

quac_key_enumerate

quac_status_t quac_key_enumerate(quac_device_t *dev,
    quac_key_handle_t *handles, size_t max_handles, size_t *n_found);

List all persistent keys stored on the device. [FIPS]

quac_key_get_public

quac_status_t quac_key_get_public(quac_key_handle_t handle,
    uint8_t *pk, size_t pk_cap, size_t *pk_len);

Extract the public key component from a persistent key pair. Public key extraction is always permitted regardless of the key's extractable attribute. [FIPS]

Async & Batch Functions #

quac_async_submit

quac_status_t quac_async_submit(quac_device_t *dev, const quac_async_desc_t *desc, quac_job_t *job);

Submit an asynchronous operation. Returns immediately. The job handle is written to *job. [FIPS]

quac_async_poll

quac_job_status_t quac_async_poll(quac_job_t job);

Non-blocking status check. Returns QUAC_JOB_PENDING, QUAC_JOB_COMPLETED, QUAC_JOB_FAILED, or QUAC_JOB_CANCELLED. [FIPS]

quac_async_wait / quac_async_wait_any

quac_status_t quac_async_wait(quac_job_t job, uint32_t timeout_ms);
quac_status_t quac_async_wait_any(quac_job_t *jobs, size_t n_jobs, size_t *completed_idx, uint32_t timeout_ms);

Block until a job (or any of several jobs) completes. timeout_ms = 0 means infinite wait. Returns QUAC_ERR_TIMEOUT if timeout expires. [FIPS]

quac_async_cancel

quac_status_t quac_async_cancel(quac_job_t job);

Cancel a pending job. Returns QUAC_ERR_IN_PROGRESS if already executing on hardware. [FIPS]

quac_async_release

quac_status_t quac_async_release(quac_job_t job);

Release a job handle after retrieving its result. Must be called for every completed job. [FIPS]

quac_async_get_event_fd

int quac_async_get_event_fd(quac_device_t *dev);

Get a file descriptor that becomes readable when completions are available. Suitable for epoll/kqueue/io_uring integration. [FIPS]

quac_async_reap

quac_status_t quac_async_reap(quac_device_t *dev, quac_job_t *completed, size_t max, size_t *n_completed);

Harvest completed jobs after the event FD signals. Non-blocking. [FIPS]

quac_batch_submit / quac_batch_submit_ex

quac_status_t quac_batch_submit(quac_device_t *dev, const quac_batch_desc_t *descs, size_t n, quac_batch_t *batch);
quac_status_t quac_batch_submit_ex(quac_device_t *dev, const quac_batch_desc_t *descs, size_t n,
    const quac_batch_opts_t *opts, quac_batch_t *batch);

Submit a batch of operations. The extended version accepts options for ordering, atomicity, progress callbacks, and DMA coalescing. [FIPS]

quac_batch_wait / quac_batch_release

quac_status_t quac_batch_wait(quac_batch_t batch, uint32_t timeout_ms);
quac_status_t quac_batch_release(quac_batch_t batch);

Wait for all operations in a batch to complete, then release the batch handle. [FIPS]

Diagnostics & Info #

quac_get_device_info

quac_status_t quac_get_device_info(quac_device_t *dev, quac_device_info_t *info);

Query comprehensive device information: model, serial number, firmware version, PCIe link status, temperature, power consumption, uptime, and total operations count. [FIPS]

quac_get_fips_status

quac_status_t quac_get_fips_status(quac_device_t *dev, quac_fips_status_t *status);

Query FIPS 140-3 operational mode, self-test status, certificate number, and security policy version. [FIPS]

quac_get_temperature

quac_status_t quac_get_temperature(quac_device_t *dev, quac_temp_info_t *temp);

Read current, minimum, maximum, and threshold temperatures from on-chip sensors. [FIPS]

quac_get_performance_counters

quac_status_t quac_get_performance_counters(quac_device_t *dev, quac_perf_counters_t *counters);

Read hardware performance counters: total operations by type, average latency per algorithm, queue utilization, DMA transfer statistics, and PCIe bandwidth usage. [FIPS]

quac_strerror

const char *quac_strerror(quac_status_t status);

Convert an error code to a human-readable string. Thread-safe (returns pointer to static string). [FIPS]

quac_zeroize

void quac_zeroize(void *ptr, size_t len);

Securely zero memory with a compiler barrier to prevent optimization. Use for host-side sensitive data after use. [FIPS]

Error Codes #

CodeConstantDescription
0QUAC_OKOperation completed successfully
-1QUAC_ERR_INVALID_PARAMInvalid parameter (NULL pointer, bad length, unknown algorithm)
-2QUAC_ERR_DEVICE_NOT_FOUNDNo QUAC 100 device at specified index
-3QUAC_ERR_DEVICE_BUSYDevice is in use by another process exclusively
-4QUAC_ERR_NOT_INITIALIZEDSDK not initialized (call quac_init first)
-5QUAC_ERR_BUFFER_TOO_SMALLOutput buffer insufficient (use *_output_size to query)
-6QUAC_ERR_VERIFY_FAILEDSignature verification failed
-7QUAC_ERR_KEY_NOT_FOUNDNo key with the specified handle or label
-8QUAC_ERR_INVALID_STATEKey lifecycle state does not permit this operation
-9QUAC_ERR_FIPS_NOT_APPROVEDOperation not permitted in FIPS mode
-10QUAC_ERR_QUEUE_FULLHardware command queue is full (async)
-11QUAC_ERR_TIMEOUTOperation timed out
-12QUAC_ERR_IN_PROGRESSOperation already executing (cannot cancel)
-13QUAC_ERR_HW_FAULTHardware fault detected (check tamper status)
-14QUAC_ERR_SELF_TEST_FAILEDPOST or conditional self-test failed
-15QUAC_ERR_RNG_HEALTHQRNG health test failure
-16QUAC_ERR_STORAGE_FULLKey storage capacity exhausted
-17QUAC_ERR_PERMISSIONInsufficient permissions (driver, key usage)
-18QUAC_ERR_DRIVERKernel driver communication error
-19QUAC_ERR_FIRMWAREFirmware error (check device logs)
-20QUAC_ERR_INTERNALInternal SDK error (bug — report to support)

Next Steps #

For SDK packages and pre-built binaries, visit the Downloads page. For support tiers and licensing options, see Support & Licensing.