mirror of
https://github.com/genodelabs/genode.git
synced 2024-12-23 15:32:25 +00:00
gpu: introduce information dataspace
The current info implementation (as RPC) is limited in a few ways: * The amount of data that may be transferred is constrained by the underlying base platform * Most information never changes during run time but is copied nonetheless * The information differs depending on the used GPU device and in its current implementation only contains Intel GPU specific details With this commit the 'info' RPC call is replaced with the 'info_dataspace' call that transfers the capability for the dataspace containing the information only. This is complemented by a client local 'attached_info' call that allows for getting typed access to the information. The layout of the information is moved to its own and GPU-specific header file, e.g., 'gpu/info_intel.h' Issue #4265.
This commit is contained in:
parent
cfb170c719
commit
e37792ce94
@ -21,6 +21,7 @@
|
|||||||
#include <base/sleep.h>
|
#include <base/sleep.h>
|
||||||
|
|
||||||
#include <gpu_session/connection.h>
|
#include <gpu_session/connection.h>
|
||||||
|
#include <gpu/info_intel.h>
|
||||||
#include <util/retry.h>
|
#include <util/retry.h>
|
||||||
|
|
||||||
extern "C" {
|
extern "C" {
|
||||||
@ -223,7 +224,8 @@ class Drm_call
|
|||||||
Genode::Env &_env;
|
Genode::Env &_env;
|
||||||
Genode::Heap _heap { _env.ram(), _env.rm() };
|
Genode::Heap _heap { _env.ram(), _env.rm() };
|
||||||
Gpu::Connection _gpu_session { _env };
|
Gpu::Connection _gpu_session { _env };
|
||||||
Gpu::Info _gpu_info { _gpu_session.info() };
|
Gpu::Info_intel const &_gpu_info {
|
||||||
|
*_gpu_session.attached_info<Gpu::Info_intel>() };
|
||||||
size_t _available_gtt_size { _gpu_info.aperture_size };
|
size_t _available_gtt_size { _gpu_info.aperture_size };
|
||||||
bool _complete { false };
|
bool _complete { false };
|
||||||
|
|
||||||
@ -1144,12 +1146,11 @@ class Drm_call
|
|||||||
while (_complete == false)
|
while (_complete == false)
|
||||||
_env.ep().wait_and_dispatch_one_io_signal();
|
_env.ep().wait_and_dispatch_one_io_signal();
|
||||||
|
|
||||||
/* make done buffer objects */
|
/* mark done buffer objects */
|
||||||
Gpu::Info gpu_info { _gpu_session.info() };
|
|
||||||
|
|
||||||
_buffer_space.for_each<Buffer>([&] (Buffer &h) {
|
_buffer_space.for_each<Buffer>([&] (Buffer &h) {
|
||||||
if (!h.busy) return;
|
if (!h.busy) return;
|
||||||
if (h.seqno.value > gpu_info.last_completed.value) return;
|
if (h.seqno.value > _gpu_info.last_completed.value) return;
|
||||||
h.busy = false;
|
h.busy = false;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
66
repos/os/include/gpu/info_intel.h
Normal file
66
repos/os/include/gpu/info_intel.h
Normal file
@ -0,0 +1,66 @@
|
|||||||
|
/*
|
||||||
|
* \brief Gpu session interface.
|
||||||
|
* \author Josef Soentgen
|
||||||
|
* \date 2021-09-23
|
||||||
|
*/
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2021 Genode Labs GmbH
|
||||||
|
*
|
||||||
|
* This file is part of the Genode OS framework, which is distributed
|
||||||
|
* under the terms of the GNU Affero General Public License version 3.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef _INCLUDE__GPU_INFO_INTEL_H_
|
||||||
|
#define _INCLUDE__GPU_INFO_INTEL_H_
|
||||||
|
|
||||||
|
#include <gpu_session/gpu_session.h>
|
||||||
|
|
||||||
|
namespace Gpu {
|
||||||
|
|
||||||
|
struct Info_intel;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Gpu information
|
||||||
|
*
|
||||||
|
* Used to query information in the DRM backend
|
||||||
|
*/
|
||||||
|
struct Gpu::Info_intel
|
||||||
|
{
|
||||||
|
using Chip_id = Genode::uint16_t;
|
||||||
|
using Features = Genode::uint32_t;
|
||||||
|
using size_t = Genode::size_t;
|
||||||
|
using Context_id = Genode::uint32_t;
|
||||||
|
|
||||||
|
Chip_id chip_id;
|
||||||
|
Features features;
|
||||||
|
size_t aperture_size;
|
||||||
|
Context_id ctx_id;
|
||||||
|
|
||||||
|
Sequence_number last_completed;
|
||||||
|
|
||||||
|
struct Revision { Genode::uint8_t value; } revision;
|
||||||
|
struct Slice_mask { unsigned value; } slice_mask;
|
||||||
|
struct Subslice_mask { unsigned value; } subslice_mask;
|
||||||
|
struct Eu_total { unsigned value; } eus;
|
||||||
|
struct Subslices { unsigned value; } subslices;
|
||||||
|
|
||||||
|
Info_intel(Chip_id chip_id, Features features, size_t aperture_size,
|
||||||
|
Context_id ctx_id, Sequence_number last,
|
||||||
|
Revision rev, Slice_mask s_mask, Subslice_mask ss_mask,
|
||||||
|
Eu_total eu, Subslices subslice)
|
||||||
|
:
|
||||||
|
chip_id(chip_id), features(features),
|
||||||
|
aperture_size(aperture_size), ctx_id(ctx_id),
|
||||||
|
last_completed(last),
|
||||||
|
revision(rev),
|
||||||
|
slice_mask(s_mask),
|
||||||
|
subslice_mask(ss_mask),
|
||||||
|
eus(eu),
|
||||||
|
subslices(subslice)
|
||||||
|
{ }
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif /* _INCLUDE__GPU_INFO_INTEL_H_ */
|
@ -37,8 +37,8 @@ class Gpu::Session_client : public Genode::Rpc_client<Session>
|
|||||||
** Session interface **
|
** Session interface **
|
||||||
***********************/
|
***********************/
|
||||||
|
|
||||||
Info info() const override {
|
Genode::Dataspace_capability info_dataspace() const override {
|
||||||
return call<Rpc_info>(); }
|
return call<Rpc_info_dataspace>(); }
|
||||||
|
|
||||||
Gpu::Sequence_number exec_buffer(Buffer_id id,
|
Gpu::Sequence_number exec_buffer(Buffer_id id,
|
||||||
Genode::size_t size) override {
|
Genode::size_t size) override {
|
||||||
|
@ -5,7 +5,7 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Copyright (C) 2017 Genode Labs GmbH
|
* Copyright (C) 2017-2021 Genode Labs GmbH
|
||||||
*
|
*
|
||||||
* This file is part of the Genode OS framework, which is distributed
|
* This file is part of the Genode OS framework, which is distributed
|
||||||
* under the terms of the GNU Affero General Public License version 3.
|
* under the terms of the GNU Affero General Public License version 3.
|
||||||
@ -17,11 +17,19 @@
|
|||||||
#include <gpu_session/client.h>
|
#include <gpu_session/client.h>
|
||||||
#include <base/connection.h>
|
#include <base/connection.h>
|
||||||
#include <base/allocator.h>
|
#include <base/allocator.h>
|
||||||
|
#include <base/attached_dataspace.h>
|
||||||
|
|
||||||
namespace Gpu { struct Connection; }
|
namespace Gpu { struct Connection; }
|
||||||
|
|
||||||
struct Gpu::Connection : Genode::Connection<Session>, Session_client
|
struct Gpu::Connection : Genode::Connection<Session>, Session_client
|
||||||
{
|
{
|
||||||
|
/**
|
||||||
|
* Attached GPU information dataspace
|
||||||
|
*
|
||||||
|
* \noapi
|
||||||
|
*/
|
||||||
|
Genode::Attached_dataspace _info_dataspace;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Issue session request
|
* Issue session request
|
||||||
*
|
*
|
||||||
@ -45,8 +53,20 @@ struct Gpu::Connection : Genode::Connection<Session>, Session_client
|
|||||||
const char *label = "")
|
const char *label = "")
|
||||||
:
|
:
|
||||||
Genode::Connection<Session>(env, _session(env.parent(), label, quota)),
|
Genode::Connection<Session>(env, _session(env.parent(), label, quota)),
|
||||||
Session_client(cap())
|
Session_client(cap()),
|
||||||
|
_info_dataspace(env.rm(), info_dataspace())
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get typed pointer to the information dataspace
|
||||||
|
*
|
||||||
|
* \return typed pointer
|
||||||
|
*/
|
||||||
|
template <typename T>
|
||||||
|
T const *attached_info() const
|
||||||
|
{
|
||||||
|
return _info_dataspace.local_addr<T>();
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* _INCLUDE__GPU_SESSION__CONNECTION_H_ */
|
#endif /* _INCLUDE__GPU_SESSION__CONNECTION_H_ */
|
||||||
|
@ -25,7 +25,6 @@ namespace Gpu {
|
|||||||
using Buffer_id = Genode::Id_space<Buffer>::Id;
|
using Buffer_id = Genode::Id_space<Buffer>::Id;
|
||||||
|
|
||||||
struct Sequence_number;
|
struct Sequence_number;
|
||||||
struct Info;
|
|
||||||
struct Session;
|
struct Session;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -38,48 +37,6 @@ struct Gpu::Sequence_number
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
/*
|
|
||||||
* Gpu information
|
|
||||||
*
|
|
||||||
* Used to query information in the DRM backend
|
|
||||||
*/
|
|
||||||
struct Gpu::Info
|
|
||||||
{
|
|
||||||
using Chip_id = Genode::uint16_t;
|
|
||||||
using Features = Genode::uint32_t;
|
|
||||||
using size_t = Genode::size_t;
|
|
||||||
using Context_id = Genode::uint32_t;
|
|
||||||
|
|
||||||
Chip_id chip_id;
|
|
||||||
Features features;
|
|
||||||
size_t aperture_size;
|
|
||||||
Context_id ctx_id;
|
|
||||||
|
|
||||||
Sequence_number last_completed;
|
|
||||||
|
|
||||||
struct Revision { Genode::uint8_t value; } revision;
|
|
||||||
struct Slice_mask { unsigned value; } slice_mask;
|
|
||||||
struct Subslice_mask { unsigned value; } subslice_mask;
|
|
||||||
struct Eu_total { unsigned value; } eus;
|
|
||||||
struct Subslices { unsigned value; } subslices;
|
|
||||||
|
|
||||||
Info(Chip_id chip_id, Features features, size_t aperture_size,
|
|
||||||
Context_id ctx_id, Sequence_number last,
|
|
||||||
Revision rev, Slice_mask s_mask, Subslice_mask ss_mask,
|
|
||||||
Eu_total eu, Subslices subslice)
|
|
||||||
:
|
|
||||||
chip_id(chip_id), features(features),
|
|
||||||
aperture_size(aperture_size), ctx_id(ctx_id),
|
|
||||||
last_completed(last),
|
|
||||||
revision(rev),
|
|
||||||
slice_mask(s_mask),
|
|
||||||
subslice_mask(ss_mask),
|
|
||||||
eus(eu),
|
|
||||||
subslices(subslice)
|
|
||||||
{ }
|
|
||||||
};
|
|
||||||
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Gpu session interface
|
* Gpu session interface
|
||||||
*/
|
*/
|
||||||
@ -102,9 +59,9 @@ struct Gpu::Session : public Genode::Session
|
|||||||
***********************/
|
***********************/
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Query GPU information
|
* Get GPU information dataspace
|
||||||
*/
|
*/
|
||||||
virtual Info info() const = 0;
|
virtual Genode::Dataspace_capability info_dataspace() const = 0;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute commands from given buffer
|
* Execute commands from given buffer
|
||||||
@ -194,7 +151,7 @@ struct Gpu::Session : public Genode::Session
|
|||||||
** RPC interface **
|
** RPC interface **
|
||||||
*******************/
|
*******************/
|
||||||
|
|
||||||
GENODE_RPC(Rpc_info, Info, info);
|
GENODE_RPC(Rpc_info_dataspace, Genode::Dataspace_capability, info_dataspace);
|
||||||
GENODE_RPC_THROW(Rpc_exec_buffer, Gpu::Sequence_number, exec_buffer,
|
GENODE_RPC_THROW(Rpc_exec_buffer, Gpu::Sequence_number, exec_buffer,
|
||||||
GENODE_TYPE_LIST(Invalid_state),
|
GENODE_TYPE_LIST(Invalid_state),
|
||||||
Gpu::Buffer_id, Genode::size_t);
|
Gpu::Buffer_id, Genode::size_t);
|
||||||
@ -217,7 +174,7 @@ struct Gpu::Session : public Genode::Session
|
|||||||
GENODE_RPC(Rpc_set_tiling, bool, set_tiling,
|
GENODE_RPC(Rpc_set_tiling, bool, set_tiling,
|
||||||
Gpu::Buffer_id, unsigned);
|
Gpu::Buffer_id, unsigned);
|
||||||
|
|
||||||
GENODE_RPC_INTERFACE(Rpc_info, Rpc_exec_buffer,
|
GENODE_RPC_INTERFACE(Rpc_info_dataspace, Rpc_exec_buffer,
|
||||||
Rpc_completion_sigh, Rpc_alloc_buffer,
|
Rpc_completion_sigh, Rpc_alloc_buffer,
|
||||||
Rpc_free_buffer, Rpc_map_buffer, Rpc_unmap_buffer,
|
Rpc_free_buffer, Rpc_map_buffer, Rpc_unmap_buffer,
|
||||||
Rpc_map_buffer_ppgtt, Rpc_unmap_buffer_ppgtt,
|
Rpc_map_buffer_ppgtt, Rpc_unmap_buffer_ppgtt,
|
||||||
|
@ -1,2 +1,2 @@
|
|||||||
MIRRORED_FROM_REP_DIR := include/gpu_session
|
MIRRORED_FROM_REP_DIR := include/gpu_session include/gpu
|
||||||
include $(REP_DIR)/recipes/api/session.inc
|
include $(REP_DIR)/recipes/api/session.inc
|
||||||
|
@ -13,6 +13,7 @@
|
|||||||
|
|
||||||
/* Genode includes */
|
/* Genode includes */
|
||||||
#include <base/attached_rom_dataspace.h>
|
#include <base/attached_rom_dataspace.h>
|
||||||
|
#include <base/attached_ram_dataspace.h>
|
||||||
#include <base/component.h>
|
#include <base/component.h>
|
||||||
#include <base/heap.h>
|
#include <base/heap.h>
|
||||||
#include <base/log.h>
|
#include <base/log.h>
|
||||||
@ -22,6 +23,7 @@
|
|||||||
#include <base/session_object.h>
|
#include <base/session_object.h>
|
||||||
#include <dataspace/client.h>
|
#include <dataspace/client.h>
|
||||||
#include <gpu_session/gpu_session.h>
|
#include <gpu_session/gpu_session.h>
|
||||||
|
#include <gpu/info_intel.h>
|
||||||
#include <io_mem_session/connection.h>
|
#include <io_mem_session/connection.h>
|
||||||
#include <irq_session/connection.h>
|
#include <irq_session/connection.h>
|
||||||
#include <platform_device/client.h>
|
#include <platform_device/client.h>
|
||||||
@ -112,12 +114,12 @@ struct Igd::Device
|
|||||||
} _pci_backend_alloc { _resources.platform() };
|
} _pci_backend_alloc { _resources.platform() };
|
||||||
|
|
||||||
|
|
||||||
Device_info _info { };
|
Device_info _info { };
|
||||||
Gpu::Info::Revision _revision { };
|
Gpu::Info_intel::Revision _revision { };
|
||||||
Gpu::Info::Slice_mask _slice_mask { };
|
Gpu::Info_intel::Slice_mask _slice_mask { };
|
||||||
Gpu::Info::Subslice_mask _subslice_mask { };
|
Gpu::Info_intel::Subslice_mask _subslice_mask { };
|
||||||
Gpu::Info::Eu_total _eus { };
|
Gpu::Info_intel::Eu_total _eus { };
|
||||||
Gpu::Info::Subslices _subslices { };
|
Gpu::Info_intel::Subslices _subslices { };
|
||||||
|
|
||||||
void _pci_info(String<64> const &descr) const
|
void _pci_info(String<64> const &descr) const
|
||||||
{
|
{
|
||||||
@ -533,6 +535,8 @@ struct Igd::Device
|
|||||||
enum {
|
enum {
|
||||||
APERTURE_SIZE = 32u << 20,
|
APERTURE_SIZE = 32u << 20,
|
||||||
MAX_FENCES = 16,
|
MAX_FENCES = 16,
|
||||||
|
|
||||||
|
INFO_SIZE = 4096,
|
||||||
};
|
};
|
||||||
|
|
||||||
Device &_device;
|
Device &_device;
|
||||||
@ -541,7 +545,10 @@ struct Igd::Device
|
|||||||
Engine<Rcs_context> rcs;
|
Engine<Rcs_context> rcs;
|
||||||
uint32_t active_fences { 0 };
|
uint32_t active_fences { 0 };
|
||||||
uint64_t _current_seqno { 0 };
|
uint64_t _current_seqno { 0 };
|
||||||
uint64_t _completed_seqno { 0 };
|
|
||||||
|
Genode::Attached_ram_dataspace _info_dataspace;
|
||||||
|
Gpu::Info_intel &_info {
|
||||||
|
*_info_dataspace.local_addr<Gpu::Info_intel>() };
|
||||||
|
|
||||||
uint32_t _id_alloc()
|
uint32_t _id_alloc()
|
||||||
{
|
{
|
||||||
@ -551,13 +558,24 @@ struct Igd::Device
|
|||||||
return v << 8;
|
return v << 8;
|
||||||
}
|
}
|
||||||
|
|
||||||
Vgpu(Device &device, Allocator &alloc)
|
Vgpu(Device &device, Allocator &alloc,
|
||||||
|
Ram_allocator &ram, Region_map &rm)
|
||||||
:
|
:
|
||||||
_device(device),
|
_device(device),
|
||||||
_id(_id_alloc()),
|
_id(_id_alloc()),
|
||||||
rcs(_device, _id + Rcs_context::HW_ID, alloc)
|
rcs(_device, _id + Rcs_context::HW_ID, alloc),
|
||||||
|
_info_dataspace(ram, rm, INFO_SIZE)
|
||||||
{
|
{
|
||||||
_device.vgpu_created();
|
_device.vgpu_created();
|
||||||
|
|
||||||
|
_info = Gpu::Info_intel(_device.id(), _device.features(),
|
||||||
|
APERTURE_SIZE,
|
||||||
|
_id, Gpu::Sequence_number { .value = 0 },
|
||||||
|
_device._revision,
|
||||||
|
_device._slice_mask,
|
||||||
|
_device._subslice_mask,
|
||||||
|
_device._eus,
|
||||||
|
_device._subslices);
|
||||||
}
|
}
|
||||||
|
|
||||||
~Vgpu()
|
~Vgpu()
|
||||||
@ -565,6 +583,11 @@ struct Igd::Device
|
|||||||
_device.vgpu_released();
|
_device.vgpu_released();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Genode::Dataspace_capability info_dataspace() const
|
||||||
|
{
|
||||||
|
return _info_dataspace.cap();
|
||||||
|
}
|
||||||
|
|
||||||
uint32_t id() const { return _id; }
|
uint32_t id() const { return _id; }
|
||||||
|
|
||||||
void completion_sigh(Genode::Signal_context_capability sigh) {
|
void completion_sigh(Genode::Signal_context_capability sigh) {
|
||||||
@ -575,12 +598,12 @@ struct Igd::Device
|
|||||||
|
|
||||||
uint64_t current_seqno() const { return _current_seqno; }
|
uint64_t current_seqno() const { return _current_seqno; }
|
||||||
|
|
||||||
uint64_t completed_seqno() const { return _completed_seqno; }
|
uint64_t completed_seqno() const { return _info.last_completed.value; }
|
||||||
|
|
||||||
void user_complete()
|
void user_complete()
|
||||||
{
|
{
|
||||||
/* remember last completed seqno for info object */
|
_info.last_completed =
|
||||||
_completed_seqno = _device.seqno();
|
Gpu::Sequence_number { .value = _device.seqno() };
|
||||||
}
|
}
|
||||||
|
|
||||||
bool setup_ring_buffer(Gpu::addr_t const buffer_addr)
|
bool setup_ring_buffer(Gpu::addr_t const buffer_addr)
|
||||||
@ -1150,7 +1173,7 @@ struct Igd::Device
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
_eus = Gpu::Info::Eu_total { eu_total };
|
_eus = Gpu::Info_intel::Eu_total { eu_total };
|
||||||
}
|
}
|
||||||
|
|
||||||
/*********************
|
/*********************
|
||||||
@ -1540,7 +1563,7 @@ class Gpu::Session_component : public Genode::Session_object<Gpu::Session>
|
|||||||
_rm(rm),
|
_rm(rm),
|
||||||
_ram(ram, _ram_quota_guard(), _cap_quota_guard()),
|
_ram(ram, _ram_quota_guard(), _cap_quota_guard()),
|
||||||
_device(device),
|
_device(device),
|
||||||
_vgpu(_device, _heap)
|
_vgpu(_device, _heap, ram, rm)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
~Session_component()
|
~Session_component()
|
||||||
@ -1561,16 +1584,9 @@ class Gpu::Session_component : public Genode::Session_object<Gpu::Session>
|
|||||||
** Gpu session interface **
|
** Gpu session interface **
|
||||||
***************************/
|
***************************/
|
||||||
|
|
||||||
Info info() const override
|
Genode::Dataspace_capability info_dataspace() const override
|
||||||
{
|
{
|
||||||
Genode::size_t const aperture_size = Igd::Device::Vgpu::APERTURE_SIZE;
|
return _vgpu.info_dataspace();
|
||||||
return Info(_device.id(), _device.features(), aperture_size,
|
|
||||||
_vgpu.id(), { .value = _vgpu.completed_seqno() },
|
|
||||||
_device._revision,
|
|
||||||
_device._slice_mask,
|
|
||||||
_device._subslice_mask,
|
|
||||||
_device._eus,
|
|
||||||
_device._subslices);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Gpu::Sequence_number exec_buffer(Buffer_id id,
|
Gpu::Sequence_number exec_buffer(Buffer_id id,
|
||||||
|
Loading…
Reference in New Issue
Block a user