nngn
Loading...
Searching...
No Matches
compute Directory Reference

Compute back ends.

More...

Directory dependency graph for compute:
master/src/compute

Files

file  compute.cpp
 
file  compute.h [code]
 
file  lua_compute.cpp
 
file  opencl.cpp
 
file  opencl.h [code]
 
file  pseudo.cpp
 

Detailed Description

Compute back ends.

Compute back ends for task execution in heterogeneous compute devices.

The following area of the screenshots page shows some of the compute capabilities:

https://bbguimaraes.com/nngn/screenshots/compute.html

Lua

The compute back end is exposed to Lua via the nngn.compute variable. Compiling a program and executing a kernel is done similarly to the C++ API:

prog = nngn.compute:create_prog(io.open("prog.cl"):read("a"))
nngn.compute:execute(prog, "fn", Compute.BLOCKING, {256, 256}, {16, 16}, {
Compute.FLOAT, 3.1415,
Compute.BYTEV, {0, 1, 2, 3},
})
Definition: audio.cpp:7

Compute.BLOCKING makes the execution synchronous. Kernels can also be executed concurrently (requires a device with an out-of-order queue) and synchronized using events:

events = {}
-- Last two arguments are wait list and output events.
nngn.compute:execute(prog, "k0", 0, {1}, {1}, {}, nil, events)
-- Reuse output.
nngn.compute:execute(prog, "k1", 0, {1}, {1}, {}, nil, events)
-- Wait for all previous events, reuse output.
nngn.compute:execute(prog, "k2", 0, {1}, {1}, {}, events, events)
-- Wait for all previous events and release them.
nngn.compute:wait(events)
nngn.compute:release_events(events)
release
Definition: input.lua:46
auto wait(const Compute &c, std::vector< const void * > events)
Definition: lua_compute.cpp:466
bool release_events(const Compute &c, std::vector< const void * > events)
Definition: lua_compute.cpp:477
bool execute(Compute &c, lua_Integer program, const char *func, Compute::ExecFlag flags, nngn::lua::table_view global_size, nngn::lua::table_view local_size, nngn::lua::table_view data, std::optional< nngn::lua::value_view > wait_opt, std::optional< nngn::lua::table_view > events_opt)
Definition: lua_compute.cpp:591
constexpr struct nngn::lua::nil_type nil

Separate tables can be used to construct more complex task graphs.

Buffers

To create and populate a device buffer:

b = assert(nngn.compute:create_buffer(Compute.READ_WRITE, size))
v = Compute.create_vector(size)
Compute.fill_rnd_vector(v)
assert(nngn.compute:write_buffer(b, v))
create_buffer
Definition: img_common.lua:37
assert
Definition: debug.lua:3
v[1]
Definition: math.lua:19

Common operations on buffers are creation:

rw = Compute.READ_WRITE
assert(nngn.compute:create_buffer(rw, Compute.FLOATV, size))
-- From existing data.
assert(nngn.compute:create_buffer(
rw, Compute.FLOATV, size,
Compute.create_vector(1024)))
data
Definition: house0.lua:10

write:

assert(nngn.compute:write_buffer(b, offset, n, Compute.FLOATV, v))
n
Definition: dump_lights.lua:5

and read:

assert(nngn.compute:read_buffer(b, Compute.FLOATV, n, v))
read_buffer
Definition: img_common.lua:35

Compute back ends for task execution in heterogeneous compute devices.

The following area of the screenshots page shows some of the compute capabilities:

https://bbguimaraes.com/nngn/screenshots/compute.html

Lua

The compute back end is exposed to Lua via the nngn.compute variable. Compiling a program and executing a kernel is done similarly to the C++ API:

prog = nngn.compute:create_prog(io.open("prog.cl"):read("a"))
nngn.compute:execute(prog, "fn", Compute.BLOCKING, {256, 256}, {16, 16}, {
Compute.FLOAT, 3.1415,
Compute.BYTEV, {0, 1, 2, 3},
})

Compute.BLOCKING makes the execution synchronous. Kernels can also be executed concurrently (requires a device with an out-of-order queue) and synchronized using events:

events = {}
-- Last two arguments are wait list and output events.
nngn.compute:execute(prog, "k0", 0, {1}, {1}, {}, nil, events)
-- Reuse output.
nngn.compute:execute(prog, "k1", 0, {1}, {1}, {}, nil, events)
-- Wait for all previous events, reuse output.
nngn.compute:execute(prog, "k2", 0, {1}, {1}, {}, events, events)
-- Wait for all previous events and release them.
nngn.compute:wait(events)
nngn.compute:release_events(events)

Separate tables can be used to construct more complex task graphs.

Buffers

To create and populate a device buffer:

b = assert(nngn.compute:create_buffer(Compute.READ_WRITE, size))
v = Compute.create_vector(size)
Compute.fill_rnd_vector(v)
assert(nngn.compute:write_buffer(b, v))

Common operations on buffers are creation:

rw = Compute.READ_WRITE
assert(nngn.compute:create_buffer(rw, Compute.FLOATV, size))
-- From existing data.
assert(nngn.compute:create_buffer(
rw, Compute.FLOATV, size,
Compute.create_vector(1024)))

write:

assert(nngn.compute:write_buffer(b, offset, n, Compute.FLOATV, v))

and read:

assert(nngn.compute:read_buffer(b, Compute.FLOATV, n, v))