mirror of
https://github.com/mmueller41/genode.git
synced 2026-01-21 12:32:56 +01:00
intel_fb: request copy of Intel opregion
acpica and the Intel display driver tries to use the Intel Opregion simultaneously on Genode, which is not supported nor wanted for IO_MEM region as which it is handled. Attempts to remove the access to the region was not successful, since some SSDT table contains ACPI AML code which is executed regularly and read/write the Opregion. The patch adds support to read in a copy of the Intel Opregion done by the acpi_drv component. The copy was sufficient to make the Intel display driver working to find and lookup the Intel VBT (video bios table) information to setup all connectors on a Fujitsu U7411 docking station. Fixes #4531
This commit is contained in:
committed by
Christian Helmuth
parent
c2d9fbca9b
commit
88118b133a
@@ -68,6 +68,9 @@ append config {
|
||||
<route>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<service name="Platform"> <child name="platform_drv" label="intel_fb_drv"/> </service>
|
||||
<service name="ROM" label="intel_fb_drv -> intel_opregion">
|
||||
<child name="acpi_report_rom" label="intel_fb_drv -> intel_opregion"/>
|
||||
</service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
<config prio_levels="2">
|
||||
|
||||
@@ -215,6 +215,9 @@ void intel_gt_init_early(struct intel_gt * gt, struct drm_i915_private * i915)
|
||||
init_llist_head(>->watchdog.list);
|
||||
|
||||
lx_emul_trace(__func__);
|
||||
|
||||
/* disable panel self refresh (required for FUJITSU S937/S938) */
|
||||
i915->params.enable_psr = 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -242,7 +245,7 @@ void * memremap(resource_size_t offset, size_t size, unsigned long flags)
|
||||
{
|
||||
lx_emul_trace(__func__);
|
||||
|
||||
return NULL;
|
||||
return intel_io_mem_map(offset, size);
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -39,6 +39,7 @@ unsigned int lx_emul_io_port_inl(unsigned short port);
|
||||
|
||||
void *emul_alloc_shmem_file_buffer(unsigned long);
|
||||
|
||||
void * intel_io_mem_map(unsigned long offset, unsigned long size);
|
||||
|
||||
#include "lx_i915.h"
|
||||
|
||||
|
||||
70
repos/pc/src/drivers/framebuffer/intel/pc/opregion_io_mem.cc
Normal file
70
repos/pc/src/drivers/framebuffer/intel/pc/opregion_io_mem.cc
Normal file
@@ -0,0 +1,70 @@
|
||||
/*
|
||||
* \brief Linux emulation environment specific to this driver - Intel opregion
|
||||
* \author Alexander Boettcher
|
||||
* \date 2022-01-21
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2022 Genode Labs GmbH
|
||||
*
|
||||
* This file is distributed under the terms of the GNU General Public License
|
||||
* version 2.
|
||||
*/
|
||||
|
||||
|
||||
#include <base/log.h>
|
||||
#include <lx_kit/env.h>
|
||||
#include <base/attached_io_mem_dataspace.h>
|
||||
#include <base/attached_rom_dataspace.h>
|
||||
|
||||
#include <region_map/client.h>
|
||||
#include <rm_session/connection.h>
|
||||
#include <rom_session/connection.h>
|
||||
|
||||
|
||||
extern "C" void * intel_io_mem_map(unsigned long const phys,
|
||||
unsigned long const size)
|
||||
{
|
||||
using namespace Genode;
|
||||
|
||||
static Constructible<Attached_rom_dataspace> rom_opregion { };
|
||||
static addr_t opregion_start = 0;
|
||||
static addr_t opregion_size = 0;
|
||||
|
||||
if (!rom_opregion.constructed()) {
|
||||
try {
|
||||
rom_opregion.construct(Lx_kit::env().env, "intel_opregion");
|
||||
|
||||
Dataspace_client ds_client(rom_opregion->cap());
|
||||
|
||||
auto mem_local = rom_opregion->local_addr<char>();
|
||||
opregion_start = *(addr_t*)(mem_local + ds_client.size() - sizeof(addr_t) * 2);
|
||||
opregion_size = *(addr_t*)(mem_local + ds_client.size() - sizeof(addr_t));
|
||||
|
||||
if (opregion_size > ds_client.size())
|
||||
opregion_size = ds_client.size();
|
||||
} catch (...) {
|
||||
error("Intel opregion ROM lookup failed");
|
||||
if (rom_opregion.constructed())
|
||||
rom_opregion.destruct();
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
if ((opregion_start <= phys) &&
|
||||
(phys + size <= opregion_start + opregion_size)) {
|
||||
|
||||
try {
|
||||
auto ptr = ((addr_t)rom_opregion->local_addr<void>())
|
||||
+ (phys - opregion_start) + (phys & 0xffful);
|
||||
return (void *)ptr;
|
||||
} catch (...) {
|
||||
error("Intel opregion lookup failed");
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
|
||||
warning("Unknown memremap range ", Hex_range(phys, size));
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
@@ -11,6 +11,7 @@ INC_DIR += $(REL_PRG_DIR)/shadow
|
||||
SRC_CC += main.cc
|
||||
SRC_CC += misc.cc
|
||||
SRC_CC += emul.cc
|
||||
SRC_CC += opregion_io_mem.cc
|
||||
SRC_C += dummies.c
|
||||
SRC_C += lx_emul.c
|
||||
SRC_C += $(notdir $(wildcard $(REL_PRG_DIR)/generated_dummies.c))
|
||||
|
||||
Reference in New Issue
Block a user