mirror of
https://github.com/genodelabs/genode.git
synced 2025-01-18 18:56:29 +00:00
libdrm/iris: use VFS/GPU plugin
Synchronize GPU completion by calling 'read' of the vfs_gpu plugin. This enables pthreads to wait for GPU completions instead of the main EP. issue #4380
This commit is contained in:
parent
b3e12dcece
commit
567b9dfa39
@ -3,3 +3,5 @@ include $(REP_DIR)/lib/mk/libdrm.inc
|
||||
include $(call select_from_repositories,lib/import/import-libdrm.mk)
|
||||
|
||||
SRC_CC := ioctl_iris.cc
|
||||
|
||||
CC_CXX_WARN_STRICT =
|
||||
|
@ -4,6 +4,7 @@ _/src/init
|
||||
_/src/libdrm
|
||||
_/src/libc
|
||||
_/src/vfs
|
||||
_/src/vfs_gpu
|
||||
_/src/expat
|
||||
_/src/zlib
|
||||
_/src/stdcxx
|
||||
|
@ -8,7 +8,7 @@
|
||||
</requires>
|
||||
|
||||
<content>
|
||||
<rom label="egl.lib.so"/>
|
||||
<rom label="egl.lib.so"/>
|
||||
<rom label="expat.lib.so"/>
|
||||
<rom label="gears"/>
|
||||
<rom label="glapi.lib.so"/>
|
||||
@ -20,6 +20,7 @@
|
||||
<rom label="mesa.lib.so"/>
|
||||
<rom label="stdcxx.lib.so"/>
|
||||
<rom label="vfs.lib.so"/>
|
||||
<rom label="vfs_gpu.lib.so"/>
|
||||
<rom label="zlib.lib.so"/>
|
||||
</content>
|
||||
|
||||
@ -27,7 +28,7 @@
|
||||
<libc stdout="/dev/log" stderr="/dev/log" rtc="/dev/rtc" />
|
||||
<vfs>
|
||||
<dir name="dev">
|
||||
<log/> <inline name="rtc">2000-01-01 00:00</inline>
|
||||
<log/> <inline name="rtc">2000-01-01 00:00</inline> <gpu/>
|
||||
</dir>
|
||||
</vfs>
|
||||
<env key="GALLIUM_HUD" value="fps"/>
|
||||
|
@ -18,6 +18,7 @@
|
||||
#include <base/heap.h>
|
||||
#include <base/log.h>
|
||||
#include <base/registry.h>
|
||||
#include <base/shared_object.h>
|
||||
#include <base/sleep.h>
|
||||
|
||||
#include <gpu_session/connection.h>
|
||||
@ -28,11 +29,17 @@ extern "C" {
|
||||
#include <errno.h>
|
||||
#include <drm.h>
|
||||
#include <i915_drm.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#define DRM_NUMBER(req) ((req) & 0xff)
|
||||
}
|
||||
|
||||
namespace Libc {
|
||||
#include <sys/types.h>
|
||||
#include <sys/stat.h>
|
||||
#include <fcntl.h>
|
||||
#include <unistd.h>
|
||||
}
|
||||
|
||||
using Genode::addr_t;
|
||||
using Genode::Attached_dataspace;
|
||||
using Genode::Constructible;
|
||||
@ -251,11 +258,13 @@ class Drm_call
|
||||
using Ram_quota = Genode::Ram_quota;
|
||||
|
||||
Genode::Env &_env;
|
||||
Genode::Heap _heap { _env.ram(), _env.rm() };
|
||||
Gpu::Connection _gpu_session { _env, 3*1024*1024 };
|
||||
Genode::Heap &_heap;
|
||||
Gpu::Connection &_gpu_session;
|
||||
|
||||
Gpu::Info_intel const &_gpu_info {
|
||||
*_gpu_session.attached_info<Gpu::Info_intel>() };
|
||||
size_t _available_gtt_size { _gpu_info.aperture_size };
|
||||
int _wait_fd { 0 };
|
||||
|
||||
using Buffer = Gpu::Buffer;
|
||||
using Buffer_space = Genode::Id_space<Buffer>;
|
||||
@ -669,16 +678,6 @@ class Drm_call
|
||||
}
|
||||
}
|
||||
|
||||
/***************************
|
||||
** execbuffer completion **
|
||||
***************************/
|
||||
|
||||
void _handle_completion() { }
|
||||
|
||||
Genode::Io_signal_handler<Drm_call> _completion_sigh {
|
||||
_env.ep(), *this, &Drm_call::_handle_completion };
|
||||
|
||||
|
||||
/************
|
||||
** ioctls **
|
||||
************/
|
||||
@ -884,6 +883,14 @@ class Drm_call
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int _device_gem_context_destroy(void *arg)
|
||||
{
|
||||
unsigned id = reinterpret_cast<drm_i915_gem_context_destroy *>(arg)->ctx_id;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
int _device_gem_context_set_param(void *arg)
|
||||
{
|
||||
auto * const p = reinterpret_cast<drm_i915_gem_context_param*>(arg);
|
||||
@ -1166,26 +1173,23 @@ class Drm_call
|
||||
}
|
||||
|
||||
switch (cmd) {
|
||||
case DRM_I915_GEM_GET_APERTURE: return _device_gem_get_aperture_size(arg);
|
||||
case DRM_I915_GETPARAM: return _device_getparam(arg);
|
||||
case DRM_I915_GEM_CREATE: return _device_gem_create(arg);
|
||||
case DRM_I915_GEM_MMAP: return _device_gem_mmap(arg);
|
||||
case DRM_I915_GEM_MMAP_GTT: return _device_gem_mmap_gtt(arg);
|
||||
case DRM_I915_GEM_SET_DOMAIN: return _device_gem_set_domain(arg);
|
||||
case DRM_I915_GEM_CONTEXT_CREATE: return _device_gem_context_create(arg);
|
||||
case DRM_I915_GEM_SET_TILING: return _device_gem_set_tiling(arg);
|
||||
case DRM_I915_GEM_SW_FINISH: return _device_gem_sw_finish(arg);
|
||||
case DRM_I915_GEM_EXECBUFFER2: return _device_gem_execbuffer2(arg);
|
||||
case DRM_I915_GEM_BUSY: return _device_gem_busy(arg);
|
||||
case DRM_I915_GEM_MADVISE: return _device_gem_madvise(arg);
|
||||
case DRM_I915_GEM_WAIT: return 0;
|
||||
case DRM_I915_QUERY: return _device_query(arg);
|
||||
case DRM_I915_GEM_GET_APERTURE: return _device_gem_get_aperture_size(arg);
|
||||
case DRM_I915_GETPARAM: return _device_getparam(arg);
|
||||
case DRM_I915_GEM_CREATE: return _device_gem_create(arg);
|
||||
case DRM_I915_GEM_MMAP: return _device_gem_mmap(arg);
|
||||
case DRM_I915_GEM_MMAP_GTT: return _device_gem_mmap_gtt(arg);
|
||||
case DRM_I915_GEM_SET_DOMAIN: return _device_gem_set_domain(arg);
|
||||
case DRM_I915_GEM_CONTEXT_CREATE: return _device_gem_context_create(arg);
|
||||
case DRM_I915_GEM_CONTEXT_DESTROY: return _device_gem_context_destroy(arg);
|
||||
case DRM_I915_GEM_SET_TILING: return _device_gem_set_tiling(arg);
|
||||
case DRM_I915_GEM_SW_FINISH: return _device_gem_sw_finish(arg);
|
||||
case DRM_I915_GEM_EXECBUFFER2: return _device_gem_execbuffer2(arg);
|
||||
case DRM_I915_GEM_BUSY: return _device_gem_busy(arg);
|
||||
case DRM_I915_GEM_MADVISE: return _device_gem_madvise(arg);
|
||||
case DRM_I915_GEM_WAIT: return 0;
|
||||
case DRM_I915_QUERY: return _device_query(arg);
|
||||
case DRM_I915_GEM_CONTEXT_SETPARAM: return _device_gem_context_set_param(arg);
|
||||
case DRM_I915_GEM_CONTEXT_GETPARAM: return _device_gem_context_get_param(arg);
|
||||
case DRM_I915_GEM_CONTEXT_DESTROY:
|
||||
if(verbose_ioctl)
|
||||
Genode::warning("DRM_IOCTL_I915_GEM_CONTEXT_DESTROY not supported");
|
||||
return 0;
|
||||
default:
|
||||
if (verbose_ioctl)
|
||||
Genode::error("Unhandled device specific ioctl:", Genode::Hex(cmd));
|
||||
@ -1365,15 +1369,20 @@ class Drm_call
|
||||
|
||||
public:
|
||||
|
||||
Drm_call(Genode::Env &env)
|
||||
: _env(env)
|
||||
Drm_call(Genode::Env &env, Genode::Heap &heap, Gpu::Connection &gpu_session)
|
||||
: _env(env), _heap(heap), _gpu_session(gpu_session)
|
||||
{
|
||||
/* make handle id 0 unavailable, handled as invalid by iris */
|
||||
drm_syncobj_create reserve_id_0 { };
|
||||
if (_generic_syncobj_create(&reserve_id_0))
|
||||
Genode::warning("syncobject 0 not reserved");
|
||||
|
||||
_gpu_session.completion_sigh(_completion_sigh);
|
||||
_wait_fd = Libc::open("/dev/gpu", 0);
|
||||
if (_wait_fd < 0) {
|
||||
Genode::error("Failed to open '/dev/gpu': ",
|
||||
"try configure '<gpu>' in 'dev' directory of VFS'");
|
||||
throw -1;
|
||||
}
|
||||
}
|
||||
|
||||
int lseek(int fd, off_t offset, int whence)
|
||||
@ -1491,7 +1500,10 @@ class Drm_call
|
||||
if (_gpu_session.complete(seqno)) {
|
||||
break;
|
||||
}
|
||||
_env.ep().wait_and_dispatch_one_io_signal();
|
||||
|
||||
/* wait for completion signal in VFS plugin */
|
||||
char buf;
|
||||
Libc::read(_wait_fd, &buf, 1);
|
||||
}
|
||||
|
||||
/* mark done buffer objects */
|
||||
@ -1511,7 +1523,27 @@ static Genode::Constructible<Drm_call> _call;
|
||||
|
||||
void drm_init(Genode::Env &env)
|
||||
{
|
||||
_call.construct(env);
|
||||
using namespace Genode;
|
||||
|
||||
/*
|
||||
* XXX: lookup Gpu::Connection via 'Gpu::Connection &vfs_gpu_connection()' in
|
||||
* vfs_gpu.lib.so' VFS plugin
|
||||
*/
|
||||
static Heap heap { env.ram(), env.rm() };
|
||||
try {
|
||||
Shared_object object { env, heap, "vfs_gpu.lib.so",
|
||||
Shared_object::BIND_LAZY,
|
||||
Shared_object::DONT_KEEP };
|
||||
|
||||
void *vfs_gpu_connection = object.lookup("_Z18vfs_gpu_connectionv");
|
||||
|
||||
log("libdrm (iris): 'vfs_gpu_connection' found at: ", vfs_gpu_connection);
|
||||
Gpu::Connection &gpu_session = ((Gpu::Connection & (*)())vfs_gpu_connection)();
|
||||
|
||||
_call.construct(env, heap, gpu_session);
|
||||
} catch (Shared_object::Invalid_rom_module) {
|
||||
Genode::error("'vfs_gpu.lib.so' plugin not found");
|
||||
} catch (...) { }
|
||||
}
|
||||
|
||||
|
||||
@ -1524,6 +1556,8 @@ extern "C" void *drm_mmap(void * /* vaddr */, size_t length,
|
||||
int /* prot */, int /* flags */,
|
||||
int /* fd */, off_t offset)
|
||||
{
|
||||
if (_call.constructed() == false) { errno = EIO; return nullptr; }
|
||||
|
||||
/* sanity check if we got a GTT mapped offset */
|
||||
bool const ok = _call->map_buffer_ggtt(offset, length);
|
||||
return ok ? (void *)offset : nullptr;
|
||||
@ -1534,6 +1568,8 @@ extern "C" void *drm_mmap(void * /* vaddr */, size_t length,
|
||||
*/
|
||||
extern "C" int drm_munmap(void *addr, size_t length)
|
||||
{
|
||||
if (_call.constructed() == false) { errno = EIO; return -1; }
|
||||
|
||||
_call->unmap_buffer(addr, length);
|
||||
return 0;
|
||||
}
|
||||
@ -1555,7 +1591,9 @@ extern "C" int drm_lseek(int fd, off_t offset, int whence)
|
||||
|
||||
extern "C" int genode_ioctl(int /* fd */, unsigned long request, void *arg)
|
||||
{
|
||||
if (_call.constructed() == false) { errno = EIO; return -1; }
|
||||
if (verbose_ioctl) { dump_ioctl(request); }
|
||||
|
||||
int const ret = _call->ioctl(request, arg);
|
||||
if (verbose_ioctl) { Genode::log("returned ", ret); }
|
||||
return ret;
|
||||
|
Loading…
Reference in New Issue
Block a user