Skip to content

API System

Lu-Fi edited this page Nov 1, 2026 · 7 revisions

API reference: System

The System module starts and stops the library, connects modules into a pipeline with bind calls, hands out timestamps and gives access to a few system facilities. Every program calls IMP_System_Init once before it creates FrameSource channels, encoder channels, OSD or IVS groups, and IMP_System_Exit at the end.

Pipeline cells: a cell (IMPCell) names one output of one module: device (DEV_ID_FS, DEV_ID_ENC, DEV_ID_OSD, DEV_ID_IVS, ...), group (or channel) and output index. IMP_System_Bind(src, dst) connects the output of src to the input of dst, for example FrameSource channel 0 to encoder group 0. OpenIMP records the bind; the consumer (the encoder, the IVS group) pulls frames from the source when it starts, so bind before the consumer starts. At most 16 binds exist at a time.

Extensions in this module (OpenIMP only): OpenIMP_* functions that belong to FrameSource, such as the fallback test frame, are described on the FrameSource page and in Beyond the Vendor.

Status columns: T10 T20 T21 T23 T30 T31 T40 T41. As of 2026-11-01. Part of the API reference.

Contents

Status symbols are those of the feature matrix (API coverage tables):

  • ✅ works, device-tested
  • ✅+ works, device-tested, better than the vendor
  • ✅rt API round trip on device, no visible effect expected
  • ✅r works: called by the streamer on fleet cameras of this SoC that passed the fleet soak
  • ✅○ vendor no-op, OpenIMP matches that
  • 🔧h implemented, host tests only (no camera run yet)
  • 🔧a really connected per static audit, no device test tracked
  • 🔧+ API round trip in QEMU, no camera
  • ⚠c value only stored and read back, nothing applied
  • ⚠s returns 0 without any effect
  • ❌e exported but fails or has a known defect
  • ❌ not exported by OpenIMP
  • · function does not exist on this SoC (not in that SoC's vendor API; not a gap)
  • ? state not determined
  • 📋 no OpenIMP build for this SoC yet (planned)

Start and stop

IMP_System_Init

int IMP_System_Init(void);

Initialises the library, starts the system clock at zero and prepares the FrameSource, IVS, OSD, encoder and framebuffer parts.

Returns: 0 on success and when already initialised; negative when one of the parts fails (those already started are shut down again).

Call it once, before any other module call.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest agg63 2026-10-31 .31
  • T20: apitest agg63 2026-10-31 .107
  • T21: apitest agg63 2026-10-31 .24
  • T23: apitest agg62 2026-10-31 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest agg61 2026-10-31 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest agg61 2026-10-31 .34

Used by: prudynt, raptor, timps.

IMP_System_Exit

int IMP_System_Exit(void);

Shuts the parts down in the reverse order.

Returns: 0, also when not initialised.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest agg63 2026-10-31 .31
  • T20: apitest agg63 2026-10-31 .107
  • T21: apitest agg63 2026-10-31 .24
  • T23: apitest agg62 2026-10-31 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest agg61 2026-10-31 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest agg61 2026-10-31 .34

Used by: prudynt, raptor, timps.

Binding modules

IMP_System_Bind

int IMP_System_Bind(IMPCell *srcCell, IMPCell *dstCell);

Connects the output cell src to the input cell dst.

Parameters

  • src: Source cell.
  • dst: Destination cell.

Returns: 0 on success and when the same bind already exists; -1 for a NULL cell or when all bind slots are used.

Typical binds are FrameSource -> encoder, FrameSource -> IVS, FrameSource -> OSD -> encoder. For an OSD group in the middle use IMP_OSD_AttachToGroup.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest agg63 2026-10-31 .31
  • T20: apitest agg63 2026-10-31 .107
  • T21: apitest agg63 2026-10-31 .24
  • T23: apitest rc3gaps2 2026-10-27 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: prudynt, raptor, timps.

See also: IMP_System_UnBind, IMP_System_GetBindbyDest

IMP_System_UnBind

int IMP_System_UnBind(IMPCell *srcCell, IMPCell *dstCell);

Removes a bind.

Returns: 0 on success; -1 for a NULL cell or when no such bind exists.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest agg63 2026-10-31 .31
  • T20: apitest agg63 2026-10-31 .107
  • T21: apitest agg63 2026-10-31 .24
  • T23: apitest agg47 2026-10-26 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: prudynt, raptor, timps.

IMP_System_GetBindbyDest

int IMP_System_GetBindbyDest(IMPCell *dstCell, IMPCell *srcCell);

Finds the source cell that feeds a destination cell.

Parameters

  • dst: Destination cell.
  • src: Receives the source cell.

Returns: 0 on success; -1 for a NULL pointer or when nothing is bound to dst.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest agg63 2026-10-31 .31
  • T20: apitest agg63 2026-10-31 .107
  • T21: apitest agg63 2026-10-31 .24
  • T23: apitest agg47 2026-10-26 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: raptor.

Time and identification

IMP_System_GetVersion

int IMP_System_GetVersion(IMPVersion *pstVersion);

Writes the version text of the library into a buffer.

Parameters

  • version: Buffer of at least 64 bytes; it is zeroed and the text is copied in.

Returns: -1 for NULL.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest rc3gaps2 2026-10-27 .31
  • T20: apitest rc3gaps2 2026-10-27 .107
  • T21: apitest rc3gaps2 2026-10-27 .24
  • T23: apitest rc3gaps2 2026-10-27 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: prudynt, raptor, timps.

Difference from the vendor library: The text is OpenIMP's own, for example libimp.so T31 openimp; the vendor library returns its release number.

IMP_System_GetCPUInfo

const char *IMP_System_GetCPUInfo(void);

Returns the name of the SoC variant, for example T31X, T41NQ or T40-XP.

Returns: A pointer to a constant string, never NULL.

The variant is read from the SoC when possible; otherwise a default of the family is returned.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest rc3gaps2 2026-10-27 .31
  • T20: apitest rc3gaps2 2026-10-27 .107
  • T21: apitest rc3gaps2 2026-10-27 .24
  • T23: apitest rc3gaps2 2026-10-27 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: prudynt, raptor.

IMP_System_GetTimeStamp

uint64_t IMP_System_GetTimeStamp(void);

Returns the system time in microseconds since System_Init (or since the last RebaseTimeStamp), taken from a monotonic clock.

Returns: The time, or -1 when the clock cannot be read.

FrameSource frame timestamps are on this timeline.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest rc3gaps2 2026-10-27 .31
  • T20: apitest rc3gaps2 2026-10-27 .107
  • T21: apitest rc3gaps2 2026-10-27 .24
  • T23: apitest rc3gaps2 2026-10-27 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: raptor, timps.

IMP_System_RebaseTimeStamp

int IMP_System_RebaseTimeStamp(uint64_t basets);

Moves the system timeline so that the current moment has the given value.

Parameters

  • timestamp: New "now" in microseconds.

Returns: 0, or -1 when the clock cannot be read.

Use it to align the timeline with an external clock (for example the first RTP timestamp).

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest rc3gaps2 2026-10-27 .31
  • T20: apitest rc3gaps2 2026-10-27 .107
  • T21: apitest rc3gaps2 2026-10-27 .24
  • T23: apitest rc3gaps2 2026-10-27 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: prudynt, raptor.

Register access

Direct access to hardware registers by physical address through /dev/mem. For debugging and bring-up, not for streamers.

IMP_System_ReadReg32

uint32_t IMP_System_ReadReg32(uint32_t addr);

Reads a 32-bit hardware register at a physical address.

Parameters

  • addr: Physical address, must be 4-byte aligned.

Returns: The register value; 0 when the address is not aligned or /dev/mem cannot be used (a failure cannot be told from a register that reads 0).

The access maps one page of /dev/mem per call. It was tested by reading and writing a scratch register of the UART.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest rc3gaps2 2026-10-27 .31
  • T20: apitest rc3gaps2 2026-10-27 .107
  • T21: apitest rc3gaps2 2026-10-27 .24
  • T23: apitest rc3gaps2 2026-10-27 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: raptor.

IMP_System_WriteReg32

void IMP_System_WriteReg32(uint32_t addr, uint32_t val);

Writes a 32-bit hardware register at a physical address.

Parameters

  • addr: Physical address, 4-byte aligned.
  • value: Value to write.

Returns: no value.

Writing the wrong register can hang the SoC.

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ 🔧+ ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest rc3gaps2 2026-10-27 .31
  • T20: apitest rc3gaps2 2026-10-27 .107
  • T21: apitest rc3gaps2 2026-10-27 .24
  • T23: apitest rc3gaps2 2026-10-27 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Used by: raptor.

Memory pools

A pool reserves a block of media memory under an id; channels bound to it with IMP_FrameSource_SetPool or IMP_Encoder_SetPool take their buffers from it. T41 carves a real contiguous pool out of the rmem arena. On the other SoCs OpenIMP allocates every channel from its single rmem arena anyway, so a requested pool is validated and recorded by name but reserves nothing (reserving memory that nothing draws from would only shrink the arena).

IMP_System_MemPoolRequest

int IMP_System_MemPoolRequest(int poolId, size_t size, const char *name);

Requests a memory pool under an id.

Parameters

  • poolId: Pool number, 0 to 31 on T31, T40 and T41.
  • size: Bytes, above 0.
  • name: Label for diagnostics.

Returns: 0 on success; -1 for an invalid id, a size of 0, a size above 2 GiB (T41), when the id is already requested (T31, T40, T41) or when the memory is not available (T41).

SoC: only in the vendor API of T23, T31, T40, T41

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T23: apitest rc3gaps2 2026-10-27 .30
  • T31: apitest rc3gaps2 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest rc3gaps2 2026-10-27 .34

Difference from the vendor library: T41 reserves a real block in rmem, as the vendor library does. T23, T31 and T40 only record the request. See Beyond the Vendor: Behaviour that differs from the vendor (better or deviating on purpose).

IMP_System_MemPoolFree

int IMP_System_MemPoolFree(int poolId);

Releases a pool.

Returns: -1 for an invalid or not requested pool. On T41 also -1 while a buffer of the pool is still allocated; the channels bound to the pool are unbound and may be bound again with IMP_FrameSource_SetPool.

SoC: only in the vendor API of T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · · · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T31: apitest rc3gaps2 2026-10-27 .26

Difference from the vendor library: Beyond the vendor on T41: the vendor library keeps a pool until the program exits, OpenIMP lets the application release it. See Beyond the Vendor: Behaviour that differs from the vendor (better or deviating on purpose).

IMP_MemPool_InitPool

int IMP_MemPool_InitPool(int pool_id, uint32_t size, int flags);  /* T21, T23, T30, T31 */
int IMP_MemPool_InitPool(int pool_id, uint32_t size, const char *name);  /* T40, T41 */

Low-level pool creation; not in the public header. On T41 it is the call behind System_MemPoolRequest.

Returns: 0 on success; -1 for an invalid id, a size of 0, a pool that is already in use, or when the memory is not available.

T21, T23, T30 and T31: ids 0 to 15, one DMA block of the given size, flags is ignored. T40 and T41: ids 0 to 31, size up to 2 GiB, the block is carved out of rmem as one contiguous range and registered under the id with its name. On T40 the System call only records the request and does not use this function. Use System_MemPoolRequest.

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

IMP_MemPool_GetById

int IMP_MemPool_GetById(int pool_id, void *info_out);  /* T21, T23, T30, T31 */
void *IMP_MemPool_GetById(int pool_id);  /* T40, T41 */

Looks up a pool by id. Not in the public header.

Returns: T21, T23, T30, T31: 0 and an IMPDMABufferInfo (name, physical and virtual address, size, id) in info_out; -1 for an invalid id, a NULL pointer or a pool that is not in use. T40, T41: a non-NULL pointer when the pool exists, otherwise NULL.

On T41 FrameSource checks it before it binds a channel to the pool.

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

IMP_MemPool_Release

int IMP_MemPool_Release(int pool_id);

Low-level release of a pool. Use System_MemPoolFree where it exists.

Returns: 0 on success and for a pool that is not in use; -1 for an invalid id.

Only on T21, T23, T30 and T31 (ids 0 to 15); it frees the DMA block. T40 and T41 release pools through System_MemPoolFree.

SoC: T21, T23, T30 and T31.

T10 T20 T21 T23 T30 T31 T40 T41
· · · · · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T31: apitest agg61 2026-10-31 .26

IMP_PoolAlloc

uintptr_t IMP_PoolAlloc(int pool_id, void *info, intptr_t size, char *tag);

Allocates a buffer from the pool pool_id made with MemPool_InitPool. Not in the public header.

Returns: Descriptor form (info is a descriptor): 0 and the virtual and physical address in the descriptor, -1 on failure. Size form: the virtual address, 0 on failure.

Free with PoolFree. The T31 vendor library takes the same four arguments and allocates through the pool object.

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

IMP_PoolFree

void IMP_PoolFree(void *ptr);

Gives a pool buffer back. Not in the public header.

Returns: 0 on success, non-zero on error (mostly -1; T40 and T41 return their own error codes for some failures).

No return value.

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

IMP_PoolAlloc_Dump

int IMP_PoolAlloc_Dump(void);

Prints the pools and the buffers allocated from them to the log. Debug aid.

Returns: 0.0

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

IMP_PoolAlloc_Set_Attr

int IMP_PoolAlloc_Set_Attr(uint32_t alignment, uint32_t cache_policy);

Stores the alignment and cache policy for later pool allocations.

Returns: 0.0

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: The T31 vendor function is an empty stub that returns 0 and stores nothing. OpenIMP stores the values and PoolAlloc_Get_Attr reads them back; the allocator itself does not use them (extra, documented).

IMP_PoolAlloc_Get_Attr

int IMP_PoolAlloc_Get_Attr(uint32_t *alignment, uint32_t *cache_policy);

Reads back the values stored by PoolAlloc_Set_Attr (default 4096 and 0).

Returns: 0.0

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: The T31 vendor function returns 0 and leaves both outputs untouched. OpenIMP fills them (extra, documented).

IMP_PoolFlushCache

int IMP_PoolFlushCache(void *ptr, uint32_t size);

Writes the data cache of a pool buffer back to memory.

Returns: 0; -1 for a NULL pointer or a size of 0.

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: The T31 vendor function is an empty stub that returns 0. OpenIMP flushes the range through the memory driver (extra, documented).

IMP_PoolPhys_to_Virt

void *IMP_PoolPhys_to_Virt(uint32_t phys);

Converts a physical address inside a pool buffer to the virtual address.

Returns: The address, NULL when it is not inside a live buffer.

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: The T31 vendor function always returns 0. OpenIMP converts (extra, documented).

IMP_PoolVirt_to_Phys

uint32_t IMP_PoolVirt_to_Phys(void *virt);

Converts a virtual address inside a pool buffer to the physical address.

Returns: The address, 0 when it is not inside a live buffer.

SoC: only in the vendor API of T23, T31

T10 T20 T21 T23 T30 T31 T40 T41
· · · ✅ · ✅ · ·

Tested (tool, date, camera, what was checked):

  • T23: apitest agg62 2026-10-31 .30
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: The T31 vendor function always returns 0. OpenIMP converts (extra, documented).

IMP_Phys_to_Virt

void *IMP_Phys_to_Virt(uint32_t phys);

Converts a physical address inside an IMP_Alloc buffer to the virtual address (offsets inside the buffer work). Not in the public header.

Returns: The address, NULL when it is not inside a live buffer.

SoC: not in the vendor API of T40, T41

T10 T20 T21 T23 T30 T31 T40 T41
🔧+ 🔧+ 🔧+ ✅ 🔧+ ✅ · ·

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T23: apitest agg62 2026-10-31 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: T10, T20, T21: the vendor function forwards to the allocator, which converts any address inside its whole memory region linearly (0 outside it). OpenIMP converts inside live buffers only, so an address in the region but outside every buffer gives NULL (stricter).

IMP_Virt_to_Phys

uint32_t IMP_Virt_to_Phys(void *virt);

Converts a virtual address inside an IMP_Alloc buffer to the physical address. Not in the public header.

Returns: The address, 0 when it is not inside a live buffer.

SoC: not in the vendor API of T40, T41

T10 T20 T21 T23 T30 T31 T40 T41
🔧+ 🔧+ 🔧+ ✅ 🔧+ ✅ · ·

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T23: apitest agg62 2026-10-31 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: T10, T20, T21: the vendor function converts any address inside the allocator region (0 outside); OpenIMP only inside live buffers.

IMP_Sp_Alloc

uintptr_t IMP_Sp_Alloc(int size, char *tag);   /* T23 form, used on the other SoCs too */
int IMP_Sp_Alloc(IMPDMABufferInfo *info, uintptr_t phys);   /* T10, T20, T21 */

T23: allocates a physically contiguous buffer, like IMP_Alloc, and returns its virtual address. T10, T20 and T21: takes one more reference on a live buffer and fills the descriptor. Not in the public header.

Returns: T23: the virtual address, 0 on failure. T10, T20, T21: 0 and the descriptor filled; -1 for a NULL descriptor, a physical address of 0 or an address that is not a live buffer.

T10, T20, T21: phys is the physical address of a buffer from IMP_Alloc (exact start address, as the vendor allocator compares it). Every Sp_Alloc needs one more IMP_Free; the buffer is released by the last one. Disassembly of the T20/T10 3.12.0 and T21 1.0.33 libraries: the vendor function is the reference-count increment of the allocator (counter at +16 of the allocation record, initial value 1, free decrements and releases at 0).

SoC: not in the vendor API of T40, T41

T10 T20 T21 T23 T30 T31 T40 T41
🔧+ 🔧+ 🔧+ ✅ 🔧+ ✅ · ·

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera)
  • T23: apitest agg62 2026-10-31 .30
  • T30: apitest t30audit 2026-10-31 QEMU (no camera)
  • T31: apitest agg61 2026-10-31 .26

Difference from the vendor library: The T31 vendor function also takes a descriptor plus a second non-NULL argument and returns 0 or -1, so it very likely is the same reference call; the OpenIMP call form on T31 still follows the T23 library and is not tested on a T31 camera.

Logging

IMP_Log_Get/Set_Option

int IMP_Log_Get_Option(void);
void IMP_Log_Set_Option(int option);

Reads or sets which fields (file, line, function, ...) the library prints in front of a log message.

Parameters

  • option: Bit mask of the IMP_LOG_OP_* flags; IMP_LOG_OP_NONE gives the terse vendor line.

Returns: Get returns the mask, Set has no return value.

OpenIMP prints warnings and errors to stderr always, informational and debug messages only when OPENIMP_DEBUG_TRACE is set. Syslog output is enabled with OPENIMP_LOG_SYSLOG=1. The default mask is the full one.

SoC: not in the vendor API of T30

T10 T20 T21 T23 T30 T31 T40 T41
✅ ✅ ✅ ✅ · ✅ ✅ ✅

Tested (tool, date, camera, what was checked):

  • T10: apitest agg47-cases 2026-10-26 .31
  • T20: apitest agg47-cases 2026-10-26 .107
  • T21: apitest agg47-cases 2026-10-26 .24
  • T23: apitest agg47-cases 2026-10-26 .30
  • T31: apitest next+ko/libimp swap 2026-10-27 .26
  • T40: apitest agg65e 2026-11-01 .184
  • T41: apitest next+ko/libimp swap 2026-10-27 .34

Difference from the vendor library: The vendor library starts with no fields and prints everything it has; OpenIMP is quiet by default so a camera is not flooded.

Decoder (T23)

A JPEG decoder on channel 0, implemented by OpenIMP on T23 only (the T40 and T41 vendor libraries export it too; OpenIMP does not). It decodes JPEG pictures into NV12, NV21 or YUV420P. The vendor library decodes on the VPU; OpenIMP decodes in its own software decoder (baseline JPEG, gray or YCbCr, 4:4:4, 4:2:2, 4:4:0 or 4:2:0, restart intervals; progressive and arithmetic-coded files are refused) in the calling thread. A build with the OEM helper process (OPENIMP_T23_HELIX_BRIDGE=1) uses the helper's VPU decoder instead and falls back to the software decoder when the helper cannot be started. The picture is always 4:2:0 with the width and height of the file (no alignment padding), the colour planes taken straight from the file's Cb and Cr.

IMP_Decoder_CreateChn

/* IMP_Decoder_CreateChn: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Creates the decoder channel 0 (software decoder, or the OEM helper when built in).

Parameters

  • chn: Channel, only 0.
  • attr: Decoder attribute; the type must be JPEG, the maximum size non-zero, the pixel format NV12, NV21 or YUV420P.

Returns: -1 for another channel, another payload type or pixel format, a zero size, an existing channel or when the worker cannot be started.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

IMP_Decoder_DestroyChn

/* IMP_Decoder_DestroyChn: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Destroys the channel (stops the helper when one is used) and releases all frames.

Returns: -1 for another channel or a channel that does not exist.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

IMP_Decoder_StartRecvPic

/* IMP_Decoder_StartRecvPic: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Marks the channel as receiving.

Returns: -1 for another channel or a channel that does not exist.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

IMP_Decoder_StopRecvPic

/* IMP_Decoder_StopRecvPic: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Marks the channel as not receiving and wakes any waiting caller.

Returns: -1 for another channel or a channel that does not exist.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

IMP_Decoder_SendStreamTimeout

/* IMP_Decoder_SendStreamTimeout: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Decodes one JPEG picture. It waits up to the timeout for a free picture buffer, decodes and queues the picture.

Parameters

  • stream: JPEG data (p_payload, i_payload) and a timestamp that is passed on to the picture.
  • timeout_ms: Maximum wait in milliseconds for a buffer and for the decode.

Returns: -1 for another channel, an empty or NULL stream, no free buffer within the timeout, a file that is not a baseline JPEG, damaged or truncated, or a picture larger than the channel's maximum size.

Number of pictures that can be held at once is the nrKeepStream of the channel attribute (at least 1). Give every picture back with ReleaseFrame.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

IMP_Decoder_PollingFrame

/* IMP_Decoder_PollingFrame: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Waits until a decoded picture is ready.

Returns: 0 when ready; -1 on timeout, for another channel or when the channel does not exist.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

IMP_Decoder_GetFrame

/* IMP_Decoder_GetFrame: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Hands out the oldest decoded picture (a pointer to its frame info with address and size).

Returns: -1 when none is ready, for another channel, NULL or when the channel does not exist.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

IMP_Decoder_ReleaseFrame

/* IMP_Decoder_ReleaseFrame: exported by libimp; declared in the vendor SDK header, not in the OpenIMP include directory */

Gives a picture back so the buffer can be reused.

Returns: -1 for another channel, NULL, or a frame that was not handed out.

SoC: Implemented by OpenIMP on T23. T10, T20 and T21 export the call as a stub that returns -1 with errno ENOTSUP (no JPEG decoder in OpenIMP there); T30 to T41 do not export it.

T10 T20 T21 T23 T30 T31 T40 T41
❌e ❌e ❌e ❌e ❌ · · ❌e

Tested (tool, date, camera, what was checked):

  • T10: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T20: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T21: apitest t2xbl 2026-10-31 QEMU (no camera): exported as a stub by design, all eight calls return -1 with errno ENOTSUP (no JPEG decoder in OpenIMP on this SoC)
  • T40: vendor libimp T40 1.3.1 (uclibc and glibc libimp.so, libimp.a): no IMP_Decoder_* symbol exported (nm -D, strings); the names only exist in the SDK header imp_decoder.h, so the stock library answers a program with an unresolved symbol (checked 2026-10-31, #66)
  • T41: QEMU T41 2026-10-31 case dec 8/8

System utilities (SU)

SU_Base_SetWkupMode

int SU_Base_SetWkupMode(int mode);

Selects how the RTC wake-up behaves (mode 1 or 2). T41 only.

Returns: 0 when the RTC accepted the request, -1 (with errno) for a mode other than 1 or 2 (EINVAL, nothing is touched), a missing /dev/rtc0, or an RTC driver that does not know the request.

The request is the one of the vendor libsysutils: a three-word block {0, 0x2c, mode code} sent to /dev/rtc0. The call changes the wake-up configuration, so test it only on purpose.

SoC: only in the vendor API of T41

T10 T20 T21 T23 T30 T31 T40 T41
· · · · · · · 🔧h

Tested (tool, date, camera, what was checked):

  • T41: host test tests/core/su_base_wkup_test.c; QEMU T41 2026-10-31 mode 0 refusal

Difference from the vendor library: The board's libsysutils writes the mode number into /sys/power/state, which the kernel rejects; OpenIMP sends the vendor request instead. The symbol is in libimp.so, so it wins only where libimp is resolved first.

SU_Base_Get/SetTime

int SU_Base_GetTime(SUTime *time);
int SU_Base_SetTime(SUTime *time);

Reads or sets the battery-backed RTC (/dev/rtc0). Month is 1 to 12 and the year is the full year.

Returns: 0, -1 when the RTC node cannot be opened or the ioctl fails (a board without an RTC driver).

SoC: T40 (ported from the vendor libsysutils into libimp; other SoCs use the vendor libsysutils.so).

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Base_Get/SetAlarm

int SU_Base_GetAlarm(SUTime *time);
int SU_Base_SetAlarm(SUTime *time);

Reads or sets the RTC alarm time.

Returns: 0, -1 on a missing RTC or a failing ioctl.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Base_EnableAlarm

int SU_Base_EnableAlarm(void);

Switches the RTC alarm interrupt on. Refused with -1 unless the alarm time lies after the current time.

Returns: 0 on success, non-zero on error (mostly -1; T40 and T41 return their own error codes for some failures).

An armed alarm can wake or power the camera on boards that wire it up.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Base_DisableAlarm

int SU_Base_DisableAlarm(void);

Switches the RTC alarm interrupt off.

Returns: 0 on success, non-zero on error (mostly -1; T40 and T41 return their own error codes for some failures).

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Base_PollingAlarm

int SU_Base_PollingAlarm(uint32_t timeoutMsec);

Waits up to timeoutMsec for the RTC alarm.

Returns: 0, also after the timeout (the vendor only logs it); -1 when the RTC node cannot be opened.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Base_Reboot

int SU_Base_Reboot(void);

Syncs and sends SIGTERM to init (reboot on busybox init). Returns 0.

Returns: 0 on success, non-zero on error (mostly -1; T40 and T41 return their own error codes for some failures).

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Base_Suspend

int SU_Base_Suspend(void);

Writes mem to /sys/power/state.

Returns: 0, -1 when the node cannot be opened or written.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_ADC_Init

int SU_ADC_Init(void);

Opens the six ADC channel nodes /dev/ingenic_adc_aux_0 to _5.

Returns: 0, -1 when one node is missing (the board has no ADC driver).

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
· · · · · · 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)
  • T41: disassembly of libsysutils 1.2.5 and apitest su area, QEMU T41 2026-10-31 (N/A: no node)

SU_ADC_Exit

int SU_ADC_Exit(void);

Closes the channel nodes.

Returns: 0 on success, non-zero on error (mostly -1; T40 and T41 return their own error codes for some failures).

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_ADC_EnableChn

int SU_ADC_EnableChn(uint32_t chn_num);

Switches an ADC channel on (0 to 5).

Returns: 0, -1 for a channel above 5, before SU_ADC_Init or on an ioctl error.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_ADC_DisableChn

int SU_ADC_DisableChn(uint32_t chn_num);

Switches an ADC channel off.

Returns: 0 on success, non-zero on error (mostly -1; T40 and T41 return their own error codes for some failures).

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_ADC_GetChnValue

int SU_ADC_GetChnValue(uint32_t chn_num, int *value);

Reads the current value of an ADC channel.

Returns: 0, -1 for a bad channel, NULL pointer or a failing read.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Key_ReadEvent

int SU_Key_ReadEvent(int evfd, int *keyCode, SUKeyEvent *event);

Blocks until a key event arrives on the handle of SU_Key_OpenEvent; returns the key code (low 8 bits of the input code) and pressed / released.

Returns: 0, -1 on a read error.

Key press events of the gpio_keys input device only.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Key_EnableEvent

int SU_Key_EnableEvent(int keyCode);

Takes a hardware key out of the disabled_keys list of the gpio_keys driver again.

Returns: 0, -1 when the gpio_keys sysfs nodes are missing.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_Key_DisableEvent

int SU_Key_DisableEvent(int keyCode);

Masks a hardware key in the gpio_keys driver (disabled_keys).

Returns: 0, -1 when the gpio_keys sysfs nodes are missing.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_LED_Command

int SU_LED_Command(int ledNum, SULedCmd cmd);

Drives the LED on GPIO ledNum through sysfs (export, active_low 0, direction out, value). LED_GPIO_UNEXPORT writes 0 and releases the GPIO.

Returns: 0, -1 when one of the sysfs nodes cannot be opened.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a 🔧h 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: host test tests/core/su_sysutils_test.c (fake ioctl and temp files, 2026-10-31); ported from the vendor libsysutils 1.3.1 disassembly; no camera run yet (the Eufy .184 may have no RTC / ADC / gpio_keys / LED, apitest reports N/A there)

SU_CIPHER_Init

int SU_CIPHER_Init(void);

Hardware AES engine of the vendor library. Not provided: the open stack has no AES/DES kernel driver.

Returns: -1 with errno ENOTSUP; the same for SU_CIPHER_Exit, CreateHandle, DestroyHandle, ConfigHandle, Encrypt, Decrypt, DES_Init, DES_Exit and DES_Test.

The vendor library answers -1 as well on a kernel without /dev/aes and /dev/jz-des. Software AES/DES would be an extra beyond the vendor and is not offered.

SoC: T40.

T10 T20 T21 T23 T30 T31 T40 T41
🔧a 🔧a 🔧a 🔧a 🔧a 🔧a ❌e 🔧a

Tested (tool, date, camera, what was checked):

  • T30: static audit 2026-10-31 (OpenIMP claude/t30-audit)
  • T40: apitest area su in QEMU T40 2026-10-31: -1 / ENOTSUP PASS for all 10 calls

SU_Base_Shutdown

int SU_Base_Shutdown(void);

Syncs the file systems and tells the init process to reboot (or power off).

Returns: 0 when the signal reached init, -1 (with errno) when it could not be sent.

The call returns before the shutdown has finished. The environment variable OPENIMP_SU_SHUTDOWN selects what init is asked to do: unset or reboot sends SIGTERM (reboot on busybox init), poweroff sends SIGUSR2 (power off), vendor sends SIGCHLD like the vendor library.

T10 T20 T21 T23 T30 T31 T40 T41
🔧h 🔧h 🔧h 🔧h 🔧h 🔧h 🔧h 🔧h

Difference from the vendor library: The vendor library only sends SIGCHLD, which busybox init ignores, so on such a system the camera keeps running. OpenIMP's default sends the signal busybox acts on.

Clone this wiki locally