Module Backend.Memory

GPU memory allocation and transfer

type 'a buffer
val alloc : Device.t -> int -> ('a, 'b) Stdlib.Bigarray.kind -> 'a buffer
val alloc_custom : Device.t -> size:int -> elem_size:int -> 'a buffer

Allocate buffer for custom types with explicit element size in bytes

val alloc_zero_copy : Device.t -> ('a, 'b, Stdlib.Bigarray.c_layout) Stdlib.Bigarray.Array1.t -> ('a, 'b) Stdlib.Bigarray.kind -> 'a buffer option

A buffer that IS the host array, for backends whose device memory is host memory (Native, Interpreter: is_zero_copy is true, no transfer and no synchronisation). Used for every vector by default, so it must preserve copy semantics: backends with device memory of their own, OpenCL CPU devices included, return None.

val alloc_host_ptr : Device.t -> ('a, 'b, Stdlib.Bigarray.c_layout) Stdlib.Bigarray.Array1.t -> ('a, 'b) Stdlib.Bigarray.kind -> ('a buffer, Spoc_framework.Framework_sig.host_ptr_refusal) Stdlib.result

Explicit opt-in: a device buffer created over the host array's memory (OpenCL CL_MEM_USE_HOST_PTR). Never used implicitly. The caller keeps the array alive and in place for the buffer's lifetime. Host access goes through host_to_device/device_to_host (or the _ptr variants) on the same array, which synchronise (map/unmap) instead of copying. Native and Interpreter return their alloc_zero_copy buffer.

val free : 'a buffer -> unit

Synchronous Transfers

val host_to_device : src:('a, 'b, Stdlib.Bigarray.c_layout) Stdlib.Bigarray.Array1.t -> dst:'a buffer -> unit
val device_to_host : src:'a buffer -> dst:('a, 'b, Stdlib.Bigarray.c_layout) Stdlib.Bigarray.Array1.t -> unit
val host_ptr_to_device : src_ptr:nativeint -> byte_size:int -> dst:'a buffer -> unit

Transfer from raw pointer to device (for custom types). src_ptr is a raw machine address (as produced by raw_address_of_ptr); a nativeint is NOT a GC root, so the CALLER must keep the pointed-to allocation live across this call. Transfers are synchronous today (a live source on the caller's stack suffices); an async backend (e.g. the worker+SAB readback planned for the jsoo path) must root the source explicitly.

val device_to_host_ptr : src:'a buffer -> dst_ptr:nativeint -> byte_size:int -> unit

Transfer from device to raw pointer (for custom types). Same keep-alive contract as host_ptr_to_device: the caller owns dst_ptr's liveness.

val device_to_device : src:'a buffer -> dst:'a buffer -> unit

Buffer Info

val size : 'a buffer -> int
val device_ptr : 'a buffer -> nativeint
val is_zero_copy : 'a buffer -> bool

Check if buffer uses zero-copy (no transfers needed)