drivers/intel/gma: Hook up libgfxinit

Add `libgfxinit` as another option for native graphics initialization.
For that, the function gma_gfxinit() (see drivers/intel/gma/i915.h) has
to be called by the respective northbridge/soc code.

A mainboard port needs to select `CONFIG_MAINBOARD_HAS_LIBGFXINIT` and
implement the Ada package `GMA.Mainboard` with a single function `ports`
that returns a list of ports to be probed for displays.

v2: Update 3rdparty/libgfxinit to its latest master commit to make
    things buildable within coreboot.

v3: Another update to 3rdparty/libgfxinit. Including support to select
    the I2C port for VGA.

Change-Id: I4c7be3745f32853797d3f3689396dde07d4ca950
Signed-off-by: Nico Huber <nico.huber@secunet.com>
Reviewed-on: https://review.coreboot.org/16952
Tested-by: build bot (Jenkins)
Reviewed-by: Paul Menzel <paulepanter@users.sourceforge.net>
Reviewed-by: Ronald G. Minnich <rminnich@gmail.com>
This commit is contained in:
Nico Huber 2016-10-05 17:47:32 +02:00 committed by Nico Huber
parent c83239eabc
commit 542e9488bd
7 changed files with 256 additions and 2 deletions

2
3rdparty/libgfxinit vendored

@ -1 +1 @@
Subproject commit 83693c8d7d87f5cebe120abdf25951c9e212b319
Subproject commit 6a3566773f3b52550ebf0d042154958a2403bb40

View File

@ -24,7 +24,7 @@ config MAINBOARD_HAS_NATIVE_VGA_INIT
# FIXME Ugly hack to allow Z9s driver native framebuffer configuration
config NATIVE_VGA_INIT_USE_EDID
bool
default n if DRIVERS_XGI_Z9S
default n if DRIVERS_XGI_Z9S || MAINBOARD_USE_LIBGFXINIT
default y if !DRIVERS_XGI_Z9S
config MAINBOARD_HAS_NATIVE_VGA_INIT_TEXTMODECFG
@ -42,6 +42,23 @@ config MAINBOARD_DO_NATIVE_VGA_INIT
If unsure, say N.
config MAINBOARD_HAS_LIBGFXINIT
def_bool n
select MAINBOARD_HAS_NATIVE_VGA_INIT
help
Selected by mainboards that implement support for `libgfxinit`.
Usually this requires a list of ports to be probed for displays.
config MAINBOARD_USE_LIBGFXINIT
bool "Use libgfxinit for native graphics initialization"
depends on MAINBOARD_DO_NATIVE_VGA_INIT
depends on MAINBOARD_HAS_LIBGFXINIT
select RAMSTAGE_LIBHWBASE
default n
help
Use the SPARK library `libgfxinit` for the native graphics
initialization. This requires an Ada toolchain.
# TODO: Explain differences (if any) for onboard cards.
config VGA_ROM_RUN
bool "Run VGA Option ROMs"

View File

@ -36,3 +36,54 @@ config INTEL_INT15
config INTEL_GMA_ACPI
bool
default n
config GFX_GMA_CPU
string
default "Skylake" if SOC_INTEL_SKYLAKE
default "Broadwell" if SOC_INTEL_BROADWELL
default "Haswell" if NORTHBRIDGE_INTEL_HASWELL
default "Ivybridge" if NORTHBRIDGE_INTEL_IVYBRIDGE
default "Sandybridge" if NORTHBRIDGE_INTEL_SANDYBRIDGE
default "Ironlake" if NORTHBRIDGE_INTEL_NEHALEM
config GFX_GMA_CPU_VARIANT
string
default "ULT" if (SOC_INTEL_SKYLAKE && !SKYLAKE_SOC_PCH_H) || SOC_INTEL_BROADWELL || NORTHBRIDGE_INTEL_HASWELL
default "Normal"
config GFX_GMA_INTERNAL_IS_EDP
bool
default n if GFX_GMA_INTERNAL_IS_LVDS
default y
config GFX_GMA_INTERNAL_IS_LVDS
bool
default n
config GFX_GMA_INTERNAL_PORT
string
default "DP" if GFX_GMA_INTERNAL_IS_EDP
default "LVDS"
config GFX_GMA_ANALOG_I2C_HDMI_B
bool
default n
config GFX_GMA_ANALOG_I2C_HDMI_C
bool
default n
config GFX_GMA_ANALOG_I2C_HDMI_D
bool
default n
config GFX_GMA_ANALOG_I2C_PORT
string
default "PCH_HDMI_B" if GFX_GMA_ANALOG_I2C_HDMI_B
default "PCH_HDMI_C" if GFX_GMA_ANALOG_I2C_HDMI_C
default "PCH_HDMI_D" if GFX_GMA_ANALOG_I2C_HDMI_D
default "PCH_DAC"
help
Boards with a DVI-I connector share the I2C pins for both analog and
digital displays. In that case, the EDID for a VGA display has to be
read over the I2C interface of the coupled digital port.

View File

@ -20,3 +20,26 @@ ifeq ($(CONFIG_VGA_ROM_RUN),y)
ramstage-$(CONFIG_INTEL_INT15) += int15.c
endif
ramstage-$(CONFIG_INTEL_GMA_ACPI) += acpi.c
ifeq ($(CONFIG_MAINBOARD_USE_LIBGFXINIT),y)
$(call add-special-class,gfxinit)
gfxinit-handler = $(eval ramstage-srcs += $(1)$(2))
$(call add-special-class,gfxinit-gen)
gfxinit-gen-handler = \
$(eval additional-dirs += $(dir $(2))) \
$(eval ramstage-srcs += $(2)) \
$(eval ramstage-ads-deps += $(2)) \
$(eval ramstage-adb-deps += $(2)) \
$(eval $(2): $(obj)/config.h)
CONFIG_GFX_GMA_DEFAULT_MMIO := 0 # dummy, will be overwritten at runtime
subdirs-y += ../../../../3rdparty/libgfxinit
ramstage-y += gma.ads
ramstage-y += gma.adb
endif # CONFIG_MAINBOARD_USE_LIBGFXINIT

View File

@ -0,0 +1,117 @@
with HW.GFX;
with HW.GFX.Framebuffer_Filler;
with HW.GFX.GMA;
use HW.GFX;
use HW.GFX.GMA;
with GMA.Mainboard;
package body GMA
is
vbe_valid : boolean := false;
linear_fb_addr : word64;
fb : Framebuffer_Type;
function vbe_mode_info_valid return Interfaces.C.int
is
begin
return (if vbe_valid then 1 else 0);
end vbe_mode_info_valid;
procedure fill_lb_framebuffer (framebuffer : out lb_framebuffer)
is
use type word32;
begin
framebuffer :=
(tag => 0,
size => 0,
physical_address => linear_fb_addr,
x_resolution => word32 (fb.Width),
y_resolution => word32 (fb.Height),
bytes_per_line => 4 * word32 (fb.Stride),
bits_per_pixel => 32,
reserved_mask_pos => 24,
reserved_mask_size => 8,
red_mask_pos => 16,
red_mask_size => 8,
green_mask_pos => 8,
green_mask_size => 8,
blue_mask_pos => 0,
blue_mask_size => 8);
end fill_lb_framebuffer;
----------------------------------------------------------------------------
procedure gfxinit
(mmio_base : in word64;
linear_fb : in word64;
phys_fb : in word32;
lightup_ok : out Interfaces.C.int)
is
use type pos32;
ports : Port_List;
configs : Configs_Type;
success : boolean;
stride : Width_Type;
max_h : pos16 := 1;
max_v : pos16 := 1;
begin
lightup_ok := 0;
HW.GFX.GMA.Initialize
(MMIO_Base => mmio_base,
Success => success);
if success then
ports := Mainboard.ports;
HW.GFX.GMA.Scan_Ports (configs, ports);
if configs (Primary).Port /= Disabled then
for i in Config_Index loop
exit when configs (i).Port = Disabled;
max_h := pos16'max (max_h, configs (i).Mode.H_Visible);
max_v := pos16'max (max_v, configs (i).Mode.V_Visible);
end loop;
stride := ((Width_Type (max_h) + 63) / 64) * 64;
for i in Config_Index loop
exit when configs (i).Port = Disabled;
configs (i).Framebuffer :=
(Width => Width_Type (configs (i).Mode.H_Visible),
Height => Height_Type (configs (i).Mode.V_Visible),
BPC => 8,
Stride => stride,
Offset => 0);
end loop;
HW.GFX.GMA.Dump_Configs (configs);
fb :=
(Width => Width_Type (max_h),
Height => Height_Type (max_v),
BPC => 8,
Stride => stride,
Offset => 0);
HW.GFX.GMA.Setup_Default_GTT (fb, phys_fb);
HW.GFX.Framebuffer_Filler.Fill (linear_fb, fb);
HW.GFX.GMA.Update_Outputs (configs);
linear_fb_addr := linear_fb;
vbe_valid := true;
lightup_ok := 1;
end if;
end if;
end gfxinit;
end GMA;

View File

@ -0,0 +1,43 @@
with Interfaces.C;
with HW;
use HW;
package GMA
is
procedure gfxinit
(mmio_base : in word64;
linear_fb : in word64;
phys_fb : in word32;
lightup_ok : out Interfaces.C.int);
pragma Export (C, gfxinit, "gma_gfxinit");
----------------------------------------------------------------------------
function vbe_mode_info_valid return Interfaces.C.int;
pragma Export (C, vbe_mode_info_valid, "vbe_mode_info_valid");
type lb_framebuffer is record
tag : word32;
size : word32;
physical_address : word64;
x_resolution : word32;
y_resolution : word32;
bytes_per_line : word32;
bits_per_pixel : word8;
red_mask_pos : word8;
red_mask_size : word8;
green_mask_pos : word8;
green_mask_size : word8;
blue_mask_pos : word8;
blue_mask_size : word8;
reserved_mask_pos : word8;
reserved_mask_size : word8;
end record;
procedure fill_lb_framebuffer (framebuffer : out lb_framebuffer);
pragma Export (C, fill_lb_framebuffer, "fill_lb_framebuffer");
end GMA;

View File

@ -309,4 +309,7 @@ void
generate_fake_intel_oprom(const struct i915_gpu_controller_info *conf,
struct device *dev, const char *idstr);
/* interface to libgfxinit (gma.adb) */
void gma_gfxinit(u64 mmio_base, u64 linear_fb, u32 phys_fb, int *success);
#endif