Module Spoc_core.Vector

include module type of struct include Vector_types end
include sig ... end
type (!'a, !'b) scalar_kind =
  1. | Float32 : (float, Stdlib.Bigarray.float32_elt) scalar_kind
  2. | Float64 : (float, Stdlib.Bigarray.float64_elt) scalar_kind
  3. | Int32 : (int32, Stdlib.Bigarray.int32_elt) scalar_kind
  4. | Int64 : (int64, Stdlib.Bigarray.int64_elt) scalar_kind
  5. | Char : (char, Stdlib.Bigarray.int8_unsigned_elt) scalar_kind
  6. | Complex32 : (Stdlib.Complex.t, Stdlib.Bigarray.complex32_elt) scalar_kind
type !'a custom_type = 'a Spoc_core_base.Make(Ctypes_ops).custom_type = {
  1. elem_size : int;
  2. type_id : 'a Sarek_ir_types.Type_id.t;
  3. vector_type_id : ('a, unit) t Sarek_ir_types.Type_id.t;
  4. get : Ctypes_ops.handle -> int -> 'a;
  5. set : Ctypes_ops.handle -> int -> 'a -> unit;
  6. name : string;
}
and (!'c, !'d) kind = ('c, 'd) Spoc_core_base.Make(Ctypes_ops).kind =
  1. | Scalar : ('a, 'b) scalar_kind -> ('a, 'b) kind
  2. | Custom : 'a0 custom_type -> ('a0, unit) kind
and (!'c, !'d) host_storage = ('c, 'd) Spoc_core_base.Make(Ctypes_ops).host_storage =
  1. | Bigarray_storage : ('a, 'b, Stdlib.Bigarray.c_layout) Stdlib.Bigarray.Array1.t -> ('a, 'b) host_storage
  2. | Custom_storage : {
    1. ptr : Ctypes_ops.handle;
    2. custom : 'a0 custom_type;
    3. length : int;
    } -> ('a0, unit) host_storage
and (!'a, !'b) t = ('a, 'b) Spoc_core_base.Make(Ctypes_ops).t = {
  1. host : ('a, 'b) host_storage;
  2. device_buffers : (int, Ctypes_ops.device_buf) Stdlib.Hashtbl.t;
  3. length : int;
  4. kind : ('a, 'b) kind;
  5. mutable location : location;
  6. mutable auto_sync : bool;
  7. id : int;
}
val to_bigarray_kind : ('a, 'b) scalar_kind -> ('a, 'b) Stdlib.Bigarray.kind
val bigarray_elem_size : ('a, 'b) Stdlib.Bigarray.kind -> int
val scalar_elem_size : ('a, 'b) scalar_kind -> int
val elem_size : ('a, 'b) kind -> int
val scalar_kind_name : ('a, 'b) scalar_kind -> string
val kind_name : ('a, 'b) kind -> string
val float32_type_id : float Sarek_ir_types.Type_id.t
val float64_type_id : float Sarek_ir_types.Type_id.t
val int32_type_id : int32 Sarek_ir_types.Type_id.t
val int64_type_id : int64 Sarek_ir_types.Type_id.t
val char_type_id : char Sarek_ir_types.Type_id.t
val complex32_type_id : Stdlib.Complex.t Sarek_ir_types.Type_id.t
val scalar_type_id : ('a, 'b) scalar_kind -> 'a Sarek_ir_types.Type_id.t
val type_id : ('a, 'b) kind -> 'a Sarek_ir_types.Type_id.t
val float32_vector_type_id : (float, Stdlib.Bigarray.float32_elt) t Sarek_ir_types.Type_id.t
val float64_vector_type_id : (float, Stdlib.Bigarray.float64_elt) t Sarek_ir_types.Type_id.t
val int32_vector_type_id : (int32, Stdlib.Bigarray.int32_elt) t Sarek_ir_types.Type_id.t
val int64_vector_type_id : (int64, Stdlib.Bigarray.int64_elt) t Sarek_ir_types.Type_id.t
val char_vector_type_id : (char, Stdlib.Bigarray.int8_unsigned_elt) t Sarek_ir_types.Type_id.t
val complex32_vector_type_id : (Stdlib.Complex.t, Stdlib.Bigarray.complex32_elt) t Sarek_ir_types.Type_id.t
val vector_type_id : ('a, 'b) kind -> ('a, 'b) t Sarek_ir_types.Type_id.t
val create_scalar : ('a, 'b) scalar_kind -> ?dev:Ctypes_ops.device_t -> int -> ('a, 'b) t
val create : ('a, 'b) kind -> ?dev:Ctypes_ops.device_t -> int -> ('a, 'b) t
val create_custom : 'a custom_type -> ?dev:Ctypes_ops.device_t -> int -> ('a, unit) t
val of_bigarray : ('a, 'b) scalar_kind -> ('a, 'b, Stdlib.Bigarray.c_layout) Stdlib.Bigarray.Array1.t -> ('a, 'b) t
val of_raw_handle : 'a custom_type -> nativeint -> int -> ('a, unit) t
val has_buffer : ('a, 'b) t -> Ctypes_ops.device_t -> bool
val get_buffer : ('a, 'b) t -> Ctypes_ops.device_t -> Ctypes_ops.device_buf option
type sub_meta = Spoc_core_base.Make(Ctypes_ops).sub_meta = {
  1. parent_id : int;
  2. start : int;
  3. ok_range : int;
  4. ko_range : int;
  5. depth : int;
}
val is_sub : ('a, 'b) t -> bool
val get_sub_meta : ('a, 'b) t -> sub_meta option
val depth : ('a, 'b) t -> int
val parent_id : ('a, 'b) t -> int option
val sub_start : ('a, 'b) t -> int option
val sub_ok_range : ('a, 'b) t -> int option
val sub_ko_range : ('a, 'b) t -> int option
val copy_host_only : ('a, 'b) t -> ('a, 'b) t
val sub_vector_host : ('a, 'b) t -> start:int -> len:int -> ('a, 'b) t
val partition_host : ('a, 'b) t -> Ctypes_ops.device_t array -> ('a, 'b) t array
val of_list : ('a, 'b) kind -> 'a list -> ('a, 'b) t
val of_array : ('a, 'b) kind -> 'a array -> ('a, 'b) t
val host_handle : ('a, 'b) t -> Ctypes_ops.handle
val host_raw : ('a, 'b) t -> nativeint
module type DEVICE_BUFFER = Vector_types.DEVICE_BUFFER

Re-export DEVICE_BUFFER module type for backward compatibility

type device_buffer = (module DEVICE_BUFFER)

Device buffer type alias

module Custom_helpers = Vector_types.Custom_helpers

Helper functions for custom type implementations. These wrap Ctypes operations to provide simpler APIs for PPX-generated code.

val of_ctypes_ptr : 'a custom_type -> unit Ctypes.ptr -> int -> ('a, unit) t

Wrap an existing ctypes pointer as a custom-storage vector (shares memory).

Accessors

val length : ('a, 'b) t -> int
val kind : ('a, 'b) t -> ('a, 'b) kind
val location : ('a, 'b) t -> location
val id : ('a, 'b) t -> int
val device : ('a, 'b) t -> Device.t option

Get device if vector has GPU data

Raw Data Access

val to_bigarray : 'a 'b. ('a, 'b) t -> ('a, 'b, Stdlib.Bigarray.c_layout) Stdlib.Bigarray.Array1.t

Get underlying Bigarray (only for scalar vectors)

Sync and host pointer helpers (delegated)

type sync_callback = Vector_transfer.sync_callback = {
  1. sync : 'a 'b. ('a, 'b) t -> bool;
}
val to_ctypes_ptr : ('a, 'b) Vector_types.t -> unit Ctypes.ptr
val host_ptr : ('a, 'b) Vector_types.t -> nativeint
val register_sync_callback : Vector_transfer.sync_callback -> unit
val ensure_cpu_sync : ('a, 'b) Vector_types.t -> unit

Element Access

val get : 'a 'b. ('a, 'b) t -> int -> 'a

Get element (works for both storage types). Auto-syncs from GPU if location is Stale_CPU and auto_sync is enabled.

val set : 'a 'b. ('a, 'b) t -> int -> 'a -> unit

Set element (works for both storage types)

val (.%[]) : ('a, 'b) t -> int -> 'a

Indexing operators

val (.%[]<-) : ('a, 'b) t -> int -> 'a -> unit

Unsafe Access (no bounds check)

val unsafe_get : 'a 'b. ('a, 'b) t -> int -> 'a
val unsafe_set : 'a 'b. ('a, 'b) t -> int -> 'a -> unit
val kernel_set : 'a 'b. ('a, 'b) t -> int -> 'a -> unit

Kernel-safe set: no bounds check, no location update. Use this in parallel kernel execution where:

  • Bounds are guaranteed by kernel logic
  • Location tracking is not needed (data stays on same device)
  • Multiple threads may write to different indices concurrently

Auto-sync Control

val set_auto_sync : ('a, 'b) t -> bool -> unit
val auto_sync : ('a, 'b) t -> bool

Location Queries

val is_on_cpu : ('a, 'b) t -> bool
val is_on_gpu : ('a, 'b) t -> bool
val is_synced : ('a, 'b) t -> bool
val needs_gpu_update : ('a, 'b) t -> bool
val needs_cpu_update : ('a, 'b) t -> bool

Device Buffer Management

has_buffer and get_buffer are provided by Vector_types via the functor.

Pretty Printing

val location_to_string : location -> string
val to_string : ('a, 'b) t -> string

Convenience Constructors for Scalar Types

val float32 : (float, Stdlib.Bigarray.float32_elt) kind
val float64 : (float, Stdlib.Bigarray.float64_elt) kind
val int32 : (int32, Stdlib.Bigarray.int32_elt) kind
val int64 : (int64, Stdlib.Bigarray.int64_elt) kind
val char : (char, Stdlib.Bigarray.int8_unsigned_elt) kind
val complex32 : (Stdlib.Complex.t, Stdlib.Bigarray.complex32_elt) kind
val create_float32 : ?dev:Ctypes_ops.device_t -> int -> (float, Stdlib.Bigarray.float32_elt) t
val create_float64 : ?dev:Ctypes_ops.device_t -> int -> (float, Stdlib.Bigarray.float64_elt) t
val create_int32 : ?dev:Ctypes_ops.device_t -> int -> (int32, Stdlib.Bigarray.int32_elt) t
val create_int64 : ?dev:Ctypes_ops.device_t -> int -> (int64, Stdlib.Bigarray.int64_elt) t

Initialization Helpers

val fill : 'a 'b. ('a, 'b) t -> 'a -> unit

Fill vector with a value

val init : 'a 'b. ('a, 'b) kind -> int -> (int -> 'a) -> ('a, 'b) t

Initialize with a function

val copy : 'a 'b. ('a, 'b) t -> ('a, 'b) t

Copy vector (CPU data only, auto-syncs source if needed)

Subvector Support

val sub_vector : ('a, 'b) t -> start:int -> len:int -> ?ok_range:int -> ?ko_range:int -> unit -> ('a, 'b) t

Create a subvector that shares CPU memory with parent.

  • parameter vec

    Parent vector

  • parameter start

    Starting index in parent

  • parameter len

    Length of subvector

  • parameter ok_range

    Elements safe to read (default: len)

  • parameter ko_range

    Elements to avoid writing (default: 0)

Multi-GPU Helpers

val partition : ('a, 'b) t -> Device.t array -> ('a, 'b) t array

Partition a vector across multiple devices. Creates subvectors, one per device, that together cover the full vector.

val gather : ('a, 'b) t array -> unit

Gather subvectors back to parent (sync all to CPU). Assumes subvectors were created by partition and don't overlap.

Phase 6: Vector Utilities

Iteration

val iter : 'a 'b. ('a -> unit) -> ('a, 'b) t -> unit

Iterate over all elements (CPU-side, auto-syncs if needed)

val iteri : 'a 'b. (int -> 'a -> unit) -> ('a, 'b) t -> unit

Iterate with index

Mapping

val map : 'a 'b 'c 'd. ('a -> 'c) -> ('c, 'd) kind -> ('a, 'b) t -> ('c, 'd) t

Map function over vector, creating new vector with given kind

val mapi : 'a 'b 'c 'd. (int -> 'a -> 'c) -> ('c, 'd) kind -> ('a, 'b) t -> ('c, 'd) t

Map with index

val map_inplace : 'a 'b. ('a -> 'a) -> ('a, 'b) t -> unit

In-place map (same type)

Folding

val fold_left : 'a 'b 'acc. ('acc -> 'a -> 'acc) -> 'acc -> ('a, 'b) t -> 'acc

Fold left

val fold_right : 'a 'b 'acc. ('a -> 'acc -> 'acc) -> ('a, 'b) t -> 'acc -> 'acc

Fold right

Predicates

val for_all : 'a 'b. ('a -> bool) -> ('a, 'b) t -> bool

Check if all elements satisfy predicate

val exists : 'a 'b. ('a -> bool) -> ('a, 'b) t -> bool

Check if any element satisfies predicate

val find : 'a 'b. ('a -> bool) -> ('a, 'b) t -> 'a option

Find first element satisfying predicate

val find_index : 'a 'b. ('a -> bool) -> ('a, 'b) t -> int option

Find index of first element satisfying predicate

Aggregation

val sum : zero:'a -> add:('a -> 'a -> 'a) -> ('a, 'b) t -> 'a

Sum elements (requires + operation via fold)

val min_elt : compare:('a -> 'a -> int) -> ('a, 'b) t -> 'a option

Find minimum element

val max_elt : compare:('a -> 'a -> int) -> ('a, 'b) t -> 'a option

Find maximum element

Conversion

val to_list : 'a 'b. ('a, 'b) t -> 'a list

Convert to OCaml list

val to_array : 'a 'b. ('a, 'b) t -> 'a array

Convert to OCaml array

Blitting

val blit : 'a 'b. src:('a, 'b) t -> src_off:int -> dst:('a, 'b) t -> dst_off:int -> len:int -> unit

Copy elements from one vector to another