Refactor DGPU support code into drivers/system76/dgpu

Change-Id: Id29d6ade82b7212a3a68f6f3c27769e17d3fdcdc
This commit is contained in:
Jeremy Soller
2020-07-20 10:02:45 -06:00
parent 65600cdec6
commit 9e729e44a8
41 changed files with 200 additions and 1234 deletions

View File

@@ -0,0 +1,5 @@
config DRIVERS_SYSTEM76_DGPU
bool
default n
help
System76 switchable graphics support

View File

@@ -0,0 +1,3 @@
# SPDX-License-Identifier: GPL-2.0-only
ramstage-$(CONFIG_DRIVERS_SYSTEM76_DGPU) += ramstage.c

View File

@@ -1,33 +1,34 @@
// From https://review.coreboot.org/c/coreboot/+/28380
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2017-2018 Patrick Rudolph <siro@das-labor.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; version 2 of
* the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* Nvidia Optimus support methods.
*
* Methods defined here are known to work on Lenovo's Sandy Bridge
* and Ivy Bridge series, which have GPIO21 pulled low on installed dGPU and
* GPIO17 to detect dGPU "PowerGood". They use the same PMH7 functions to
* enable dGPU power and handle dGPU reset.
*/
/* SPDX-License-Identifier: GPL-2.0-only */
#define DGPU_RST_N GPP_F22
#define DGPU_PWR_EN GPP_F23
#define DGPU_GC6 GPP_K21
Device (\_SB.PCI0.PEGP) {
Name (_ADR, 0x00010000)
Device (\_SB.PCI0.PEGP.DEV0)
{
PowerResource (PWRR, 0, 0) {
Name (_STA, 1)
Method (_ON) {
Debug = "PEGP.PWRR._ON"
If (_STA != 1) {
\_SB.PCI0.PEGP.DEV0._ON ()
_STA = 1
}
}
Method (_OFF) {
Debug = "PEGP.PWRR._OFF"
If (_STA != 0) {
\_SB.PCI0.PEGP.DEV0._OFF ()
_STA = 0
}
}
}
Name (_PR0, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR2, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR3, Package () { \_SB.PCI0.PEGP.PWRR })
}
Device (\_SB.PCI0.PEGP.DEV0) {
Name(_ADR, 0x00000000)
Name (_STA, 0xF)
Name (LTRE, 0)
@@ -35,8 +36,7 @@ Device (\_SB.PCI0.PEGP.DEV0)
// Memory mapped PCI express registers
// Not sure what this stuff is, but it is used to get into GC6
OperationRegion (RPCX, SystemMemory, 0xE0008000, 0x1000)
Field (RPCX, ByteAcc, NoLock, Preserve)
{
Field (RPCX, ByteAcc, NoLock, Preserve) {
PVID, 16,
PDID, 16,
CMDR, 8,
@@ -85,8 +85,7 @@ Device (\_SB.PCI0.PEGP.DEV0)
LREV, 1
}
Method (_ON)
{
Method (_ON) {
Debug = "PEGP.DEV0._ON"
If (_STA != 0xF) {
@@ -143,8 +142,7 @@ Device (\_SB.PCI0.PEGP.DEV0)
}
}
Method (_OFF)
{
Method (_OFF) {
Debug = "PEGP.DEV0._OFF"
If (_STA != 0x5) {

View File

@@ -0,0 +1,23 @@
/* SPDX-License-Identifier: GPL-2.0-only */
//TODO: do not require this to be included in mainboard bootblock.c
#include <console/console.h>
#include <delay.h>
#include <gpio.h>
static void dgpu_power_enable(int onoff) {
printk(BIOS_DEBUG, "system76: DGPU power %d\n", onoff);
if (onoff) {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 1);
mdelay(4);
gpio_set(DGPU_RST_N, 1);
} else {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 0);
}
mdelay(50);
}

View File

@@ -0,0 +1,81 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootstate.h>
#include <console/console.h>
#include <device/pci.h>
static void dgpu_read_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_read_resources %s\n", dev_path(dev));
pci_dev_read_resources(dev);
int bar;
// Find all BARs on DGPU, mark them above 4g if prefetchable
for (bar = PCI_BASE_ADDRESS_0; bar <= PCI_BASE_ADDRESS_5; bar += 4) {
printk(BIOS_INFO, " BAR at 0x%02x\n", bar);
struct resource *res;
res = probe_resource(dev, bar);
if (res) {
if (res->flags & IORESOURCE_PREFETCH) {
printk(BIOS_INFO, " marked above 4g\n");
res->flags |= IORESOURCE_ABOVE_4G;
} else {
printk(BIOS_INFO, " not prefetch\n");
}
} else {
printk(BIOS_INFO, " not found\n");
}
}
}
static void dgpu_enable_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_enable_resources %s\n", dev_path(dev));
dev->subsystem_vendor = CONFIG_SUBSYSTEM_VENDOR_ID;
dev->subsystem_device = CONFIG_SUBSYSTEM_DEVICE_ID;
printk(BIOS_INFO, " subsystem <- %04x/%04x\n", dev->subsystem_vendor, dev->subsystem_device);
pci_write_config32(dev, 0x40, ((dev->subsystem_device & 0xffff) << 16) | (dev->subsystem_vendor & 0xffff));
pci_dev_enable_resources(dev);
}
static struct device_operations dgpu_pci_ops_dev = {
.read_resources = dgpu_read_resources,
.set_resources = pci_dev_set_resources,
.enable_resources = dgpu_enable_resources,
#if CONFIG(HAVE_ACPI_TABLES)
.write_acpi_tables = pci_rom_write_acpi_tables,
.acpi_fill_ssdt = pci_rom_ssdt,
#endif
.init = pci_dev_init,
.ops_pci = &pci_dev_ops_pci,
};
static void dgpu_above_4g(void *unused) {
struct device *pdev;
// Find PEG0
pdev = pcidev_on_root(1, 0);
if (!pdev) {
printk(BIOS_ERR, "system76: failed to find PEG0\n");
return;
}
printk(BIOS_INFO, "system76: PEG0 at %p, %04x:%04x\n", pdev, pdev->vendor, pdev->device);
int fn;
for (fn = 0; fn < 8; fn++) {
struct device *dev;
// Find DGPU functions
dev = pcidev_path_behind(pdev->link_list, PCI_DEVFN(0, fn));
if (dev) {
printk(BIOS_INFO, "system76: DGPU fn %d at %p, %04x:%04x\n", fn, dev, dev->vendor, dev->device);
dev->ops = &dgpu_pci_ops_dev;
} else {
printk(BIOS_ERR, "system76: failed to find DGPU fn %d\n", fn);
}
}
}
BOOT_STATE_INIT_ENTRY(BS_DEV_RESOURCES, BS_ON_ENTRY, dgpu_above_4g, NULL);

View File

@@ -5,6 +5,7 @@ config BOARD_SPECIFIC_OPTIONS
select BOARD_ROMSIZE_KB_16384
select DRIVERS_I2C_HID
select DRIVERS_I2C_TAS5825M
select DRIVERS_SYSTEM76_DGPU
select EC_SYSTEM76_EC
select HAVE_ACPI_RESUME
select HAVE_ACPI_TABLES

View File

@@ -1,5 +1,8 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include "../gpio.h"
#include <drivers/system76/dgpu/acpi/dgpu.asl>
#define EC_GPE_SCI 0x03 /* GPP_K3 */
#define EC_GPE_SWI 0x06 /* GPP_K6 */
#define EC_COLOR_KEYBOARD 1
@@ -7,10 +10,6 @@
Scope (\_SB) {
#include "sleep.asl"
Scope (PCI0) {
#include "pegp.asl"
#include "dgpu.asl"
}
}
Scope (\_GPE) {

View File

@@ -1,34 +0,0 @@
// From https://review.coreboot.org/c/coreboot/+/40625
/* SPDX-License-Identifier: GPL-2.0-only */
Device (PEGP)
{
Name (_ADR, 0x00010000)
PowerResource (PWRR, 0, 0)
{
Name (_STA, 1)
Method (_ON)
{
Debug = "PEGP.PWRR._ON"
If (_STA != 1) {
\_SB.PCI0.PEGP.DEV0._ON ()
_STA = 1
}
}
Method (_OFF)
{
Debug = "PEGP.PWRR._OFF"
If (_STA != 0) {
\_SB.PCI0.PEGP.DEV0._OFF ()
_STA = 0
}
}
}
Name (_PR0, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR2, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR3, Package () { \_SB.PCI0.PEGP.PWRR })
}

View File

@@ -1,29 +1,11 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootblock_common.h>
#include <console/console.h>
#include <delay.h>
#include <gpio.h>
#include "gpio.h"
#include <drivers/system76/dgpu/bootblock.c>
static void dgpu_power_enable(int onoff) {
printk(BIOS_DEBUG, "system76: DGPU power %d\n", onoff);
if (onoff) {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 1);
mdelay(4);
gpio_set(DGPU_RST_N, 1);
} else {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 0);
}
mdelay(50);
}
void bootblock_mainboard_init(void)
{
void bootblock_mainboard_init(void) {
gpio_configure_pads(early_gpio_table, ARRAY_SIZE(early_gpio_table));
dgpu_power_enable(1);
}

View File

@@ -14,16 +14,14 @@ DefinitionBlock(
#include <soc/intel/common/block/acpi/acpi/globalnvs.asl>
#include <cpu/intel/common/acpi/cpu.asl>
Device (\_SB.PCI0)
{
Device (\_SB.PCI0) {
#include <soc/intel/common/block/acpi/acpi/northbridge.asl>
#include <soc/intel/cannonlake/acpi/southbridge.asl>
}
#include <southbridge/intel/common/acpi/sleepstates.asl>
Scope (\_SB.PCI0.LPCB)
{
Scope (\_SB.PCI0.LPCB) {
#include <drivers/pc80/pc/ps2_controller.asl>
}

View File

@@ -3,14 +3,15 @@
#ifndef MAINBOARD_GPIO_H
#define MAINBOARD_GPIO_H
#include <soc/gpe.h>
#include <soc/gpio.h>
#define DGPU_RST_N GPP_F22
#define DGPU_PWR_EN GPP_F23
#define DGPU_GC6 GPP_K21
#ifndef __ACPI__
#include <soc/gpe.h>
#include <soc/gpio.h>
/* Pad configuration in romstage. */
static const struct pad_config early_gpio_table[] = {
PAD_CFG_TERM_GPO(GPP_F22, 0, NONE, DEEP), // DGPU_RST_N

View File

@@ -1,90 +1,10 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootstate.h>
#include <console/console.h>
#include <device/pci.h>
#include <soc/ramstage.h>
#include "gpio.h"
void mainboard_silicon_init_params(FSP_S_CONFIG *params)
{
void mainboard_silicon_init_params(FSP_S_CONFIG *params) {
/* Configure pads prior to SiliconInit() in case there's any
* dependencies during hardware initialization. */
cnl_configure_pads(gpio_table, ARRAY_SIZE(gpio_table));
}
static void dgpu_read_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_read_resources %s\n", dev_path(dev));
pci_dev_read_resources(dev);
int bar;
// Find all BARs on DGPU, mark them above 4g if prefetchable
for (bar = PCI_BASE_ADDRESS_0; bar <= PCI_BASE_ADDRESS_5; bar += 4) {
printk(BIOS_INFO, " BAR at 0x%02x\n", bar);
struct resource *res;
res = probe_resource(dev, bar);
if (res) {
if (res->flags & IORESOURCE_PREFETCH) {
printk(BIOS_INFO, " marked above 4g\n");
res->flags |= IORESOURCE_ABOVE_4G;
} else {
printk(BIOS_INFO, " not prefetch\n");
}
} else {
printk(BIOS_INFO, " not found\n");
}
}
}
static void dgpu_enable_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_enable_resources %s\n", dev_path(dev));
dev->subsystem_vendor = CONFIG_SUBSYSTEM_VENDOR_ID;
dev->subsystem_device = CONFIG_SUBSYSTEM_DEVICE_ID;
printk(BIOS_INFO, " subsystem <- %04x/%04x\n", dev->subsystem_vendor, dev->subsystem_device);
pci_write_config32(dev, 0x40, ((dev->subsystem_device & 0xffff) << 16) | (dev->subsystem_vendor & 0xffff));
pci_dev_enable_resources(dev);
}
static struct device_operations dgpu_pci_ops_dev = {
.read_resources = dgpu_read_resources,
.set_resources = pci_dev_set_resources,
.enable_resources = dgpu_enable_resources,
#if CONFIG(HAVE_ACPI_TABLES)
.write_acpi_tables = pci_rom_write_acpi_tables,
.acpi_fill_ssdt = pci_rom_ssdt,
#endif
.init = pci_dev_init,
.ops_pci = &pci_dev_ops_pci,
};
static void dgpu_above_4g(void *unused) {
struct device *pdev;
// Find PEG0
pdev = pcidev_on_root(1, 0);
if (!pdev) {
printk(BIOS_ERR, "system76: failed to find PEG0\n");
return;
}
printk(BIOS_INFO, "system76: PEG0 at %p, %04x:%04x\n", pdev, pdev->vendor, pdev->device);
int fn;
for (fn = 0; fn < 8; fn++) {
struct device *dev;
// Find DGPU functions
dev = pcidev_path_behind(pdev->link_list, PCI_DEVFN(0, fn));
if (dev) {
printk(BIOS_INFO, "system76: DGPU fn %d at %p, %04x:%04x\n", fn, dev, dev->vendor, dev->device);
dev->ops = &dgpu_pci_ops_dev;
} else {
printk(BIOS_ERR, "system76: failed to find DGPU fn %d\n", fn);
}
}
}
BOOT_STATE_INIT_ENTRY(BS_DEV_RESOURCES, BS_ON_ENTRY, dgpu_above_4g, NULL);

View File

@@ -78,8 +78,7 @@ static const struct cnl_mb_cfg memcfg = {
.ect = 0,
};
void mainboard_memory_init_params(FSPM_UPD *memupd)
{
void mainboard_memory_init_params(FSPM_UPD *memupd) {
// Allow memory clocks higher than 2933 MHz
memupd->FspmConfig.SaOcSupport = 1;
// Set primary display to internal graphics

View File

@@ -4,6 +4,7 @@ config BOARD_SPECIFIC_OPTIONS
def_bool y
select BOARD_ROMSIZE_KB_16384
select DRIVERS_I2C_HID
select DRIVERS_SYSTEM76_DGPU
select EC_SYSTEM76_EC
select HAVE_ACPI_RESUME
select HAVE_ACPI_TABLES

View File

@@ -1,203 +0,0 @@
// From https://review.coreboot.org/c/coreboot/+/28380
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2017-2018 Patrick Rudolph <siro@das-labor.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; version 2 of
* the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* Nvidia Optimus support methods.
*
* Methods defined here are known to work on Lenovo's Sandy Bridge
* and Ivy Bridge series, which have GPIO21 pulled low on installed dGPU and
* GPIO17 to detect dGPU "PowerGood". They use the same PMH7 functions to
* enable dGPU power and handle dGPU reset.
*/
#define DGPU_RST_N GPP_F22
#define DGPU_PWR_EN GPP_F23
#define DGPU_GC6 GPP_K21
Device (\_SB.PCI0.PEGP.DEV0)
{
Name(_ADR, 0x00000000)
Name (_STA, 0xF)
Name (LTRE, 0)
// Memory mapped PCI express registers
// Not sure what this stuff is, but it is used to get into GC6
OperationRegion (RPCX, SystemMemory, 0xE0008000, 0x1000)
Field (RPCX, ByteAcc, NoLock, Preserve)
{
PVID, 16,
PDID, 16,
CMDR, 8,
Offset (0x19),
PRBN, 8,
Offset (0x84),
D0ST, 2,
Offset (0xAA),
CEDR, 1,
Offset (0xAC),
, 4,
CMLW, 6,
Offset (0xB0),
ASPM, 2,
, 2,
P0LD, 1,
RTLK, 1,
Offset (0xC9),
, 2,
LREN, 1,
Offset (0x11A),
, 1,
VCNP, 1,
Offset (0x214),
Offset (0x216),
P0LS, 4,
Offset (0x248),
, 7,
Q0L2, 1,
Q0L0, 1,
Offset (0x504),
Offset (0x506),
PCFG, 2,
Offset (0x508),
TREN, 1,
Offset (0xC20),
, 4,
P0AP, 2,
Offset (0xC38),
, 3,
P0RM, 1,
Offset (0xC74),
P0LT, 4,
Offset (0xD0C),
, 20,
LREV, 1
}
Method (_ON)
{
Debug = "PEGP.DEV0._ON"
If (_STA != 0xF) {
Debug = " If DGPU_PWR_EN low"
If (! GTXS (DGPU_PWR_EN)) {
Debug = " DGPU_PWR_EN high"
STXS (DGPU_PWR_EN)
Debug = " Sleep 16"
Sleep (16)
}
Debug = " DGPU_RST_N high"
STXS(DGPU_RST_N)
Debug = " Sleep 10"
Sleep (10)
Debug = " Q0L0 = 1"
Q0L0 = 1
Debug = " Sleep 16"
Sleep (16)
Debug = " While Q0L0"
Local0 = 0
While (Q0L0) {
If ((Local0 > 4)) {
Debug = " While Q0L0 timeout"
Break
}
Sleep (16)
Local0++
}
Debug = " P0RM = 0"
P0RM = 0
Debug = " P0AP = 0"
P0AP = 0
Debug = Concatenate(" LREN = ", ToHexString(LTRE))
LREN = LTRE
Debug = " CEDR = 1"
CEDR = 1
Debug = " CMDR |= 7"
CMDR |= 7
Debug = " _STA = 0xF"
_STA = 0xF
}
}
Method (_OFF)
{
Debug = "PEGP.DEV0._OFF"
If (_STA != 0x5) {
Debug = Concatenate(" LTRE = ", ToHexString(LREN))
LTRE = LREN
Debug = " Q0L2 = 1"
Q0L2 = 1
Debug = " Sleep 16"
Sleep (16)
Debug = " While Q0L2"
Local0 = Zero
While (Q0L2) {
If ((Local0 > 4)) {
Debug = " While Q0L2 timeout"
Break
}
Sleep (16)
Local0++
}
Debug = " P0RM = 1"
P0RM = 1
Debug = " P0AP = 3"
P0AP = 3
Debug = " Sleep 10"
Sleep (10)
Debug = " DGPU_RST_N low"
CTXS(DGPU_RST_N)
Debug = " While DGPU_GC6 low"
Local0 = Zero
While (! GRXS(DGPU_GC6)) {
If ((Local0 > 4)) {
Debug = " While DGPU_GC6 low timeout"
Debug = " DGPU_PWR_EN low"
CTXS (DGPU_PWR_EN)
Break
}
Sleep (16)
Local0++
}
Debug = " _STA = 0x5"
_STA = 0x5
}
}
}

View File

@@ -1,5 +1,8 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include "../gpio.h"
#include <drivers/system76/dgpu/acpi/dgpu.asl>
#define EC_GPE_SCI 0x03 /* GPP_K3 */
#define EC_GPE_SWI 0x06 /* GPP_K6 */
#define EC_COLOR_KEYBOARD 1
@@ -9,8 +12,6 @@ Scope (\_SB) {
#include "sleep.asl"
Scope (PCI0) {
#include "backlight.asl"
#include "pegp.asl"
#include "dgpu.asl"
}
}

View File

@@ -1,34 +0,0 @@
// From https://review.coreboot.org/c/coreboot/+/40625
/* SPDX-License-Identifier: GPL-2.0-only */
Device (PEGP)
{
Name (_ADR, 0x00010000)
PowerResource (PWRR, 0, 0)
{
Name (_STA, 1)
Method (_ON)
{
Debug = "PEGP.PWRR._ON"
If (_STA != 1) {
\_SB.PCI0.PEGP.DEV0._ON ()
_STA = 1
}
}
Method (_OFF)
{
Debug = "PEGP.PWRR._OFF"
If (_STA != 0) {
\_SB.PCI0.PEGP.DEV0._OFF ()
_STA = 0
}
}
}
Name (_PR0, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR2, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR3, Package () { \_SB.PCI0.PEGP.PWRR })
}

View File

@@ -1,29 +1,11 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootblock_common.h>
#include <console/console.h>
#include <delay.h>
#include <gpio.h>
#include "gpio.h"
#include <drivers/system76/dgpu/bootblock.c>
static void dgpu_power_enable(int onoff) {
printk(BIOS_DEBUG, "system76: DGPU power %d\n", onoff);
if (onoff) {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 1);
mdelay(4);
gpio_set(DGPU_RST_N, 1);
} else {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 0);
}
mdelay(50);
}
void bootblock_mainboard_init(void)
{
void bootblock_mainboard_init(void) {
gpio_configure_pads(early_gpio_table, ARRAY_SIZE(early_gpio_table));
dgpu_power_enable(1);
}

View File

@@ -14,16 +14,14 @@ DefinitionBlock(
#include <soc/intel/common/block/acpi/acpi/globalnvs.asl>
#include <cpu/intel/common/acpi/cpu.asl>
Device (\_SB.PCI0)
{
Device (\_SB.PCI0) {
#include <soc/intel/common/block/acpi/acpi/northbridge.asl>
#include <soc/intel/cannonlake/acpi/southbridge.asl>
}
#include <southbridge/intel/common/acpi/sleepstates.asl>
Scope (\_SB.PCI0.LPCB)
{
Scope (\_SB.PCI0.LPCB) {
#include <drivers/pc80/pc/ps2_controller.asl>
}

View File

@@ -1,90 +1,10 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootstate.h>
#include <console/console.h>
#include <device/pci.h>
#include <soc/ramstage.h>
#include "gpio.h"
void mainboard_silicon_init_params(FSP_S_CONFIG *params)
{
void mainboard_silicon_init_params(FSP_S_CONFIG *params) {
/* Configure pads prior to SiliconInit() in case there's any
* dependencies during hardware initialization. */
cnl_configure_pads(gpio_table, ARRAY_SIZE(gpio_table));
}
static void dgpu_read_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_read_resources %s\n", dev_path(dev));
pci_dev_read_resources(dev);
int bar;
// Find all BARs on DGPU, mark them above 4g if prefetchable
for (bar = PCI_BASE_ADDRESS_0; bar <= PCI_BASE_ADDRESS_5; bar += 4) {
printk(BIOS_INFO, " BAR at 0x%02x\n", bar);
struct resource *res;
res = probe_resource(dev, bar);
if (res) {
if (res->flags & IORESOURCE_PREFETCH) {
printk(BIOS_INFO, " marked above 4g\n");
res->flags |= IORESOURCE_ABOVE_4G;
} else {
printk(BIOS_INFO, " not prefetch\n");
}
} else {
printk(BIOS_INFO, " not found\n");
}
}
}
static void dgpu_enable_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_enable_resources %s\n", dev_path(dev));
dev->subsystem_vendor = CONFIG_SUBSYSTEM_VENDOR_ID;
dev->subsystem_device = CONFIG_SUBSYSTEM_DEVICE_ID;
printk(BIOS_INFO, " subsystem <- %04x/%04x\n", dev->subsystem_vendor, dev->subsystem_device);
pci_write_config32(dev, 0x40, ((dev->subsystem_device & 0xffff) << 16) | (dev->subsystem_vendor & 0xffff));
pci_dev_enable_resources(dev);
}
static struct device_operations dgpu_pci_ops_dev = {
.read_resources = dgpu_read_resources,
.set_resources = pci_dev_set_resources,
.enable_resources = dgpu_enable_resources,
#if CONFIG(HAVE_ACPI_TABLES)
.write_acpi_tables = pci_rom_write_acpi_tables,
.acpi_fill_ssdt = pci_rom_ssdt,
#endif
.init = pci_dev_init,
.ops_pci = &pci_dev_ops_pci,
};
static void dgpu_above_4g(void *unused) {
struct device *pdev;
// Find PEG0
pdev = pcidev_on_root(1, 0);
if (!pdev) {
printk(BIOS_ERR, "system76: failed to find PEG0\n");
return;
}
printk(BIOS_INFO, "system76: PEG0 at %p, %04x:%04x\n", pdev, pdev->vendor, pdev->device);
int fn;
for (fn = 0; fn < 8; fn++) {
struct device *dev;
// Find DGPU functions
dev = pcidev_path_behind(pdev->link_list, PCI_DEVFN(0, fn));
if (dev) {
printk(BIOS_INFO, "system76: DGPU fn %d at %p, %04x:%04x\n", fn, dev, dev->vendor, dev->device);
dev->ops = &dgpu_pci_ops_dev;
} else {
printk(BIOS_ERR, "system76: failed to find DGPU fn %d\n", fn);
}
}
}
BOOT_STATE_INIT_ENTRY(BS_DEV_RESOURCES, BS_ON_ENTRY, dgpu_above_4g, NULL);

View File

@@ -78,8 +78,7 @@ static const struct cnl_mb_cfg memcfg = {
.ect = 0,
};
void mainboard_memory_init_params(FSPM_UPD *memupd)
{
void mainboard_memory_init_params(FSPM_UPD *memupd) {
// Set primary display to internal graphics
memupd->FspmConfig.PrimaryDisplay = 0;
cannonlake_memcfg_init(&memupd->FspmConfig, &memcfg);

View File

@@ -4,6 +4,7 @@ config BOARD_SPECIFIC_OPTIONS
def_bool y
select BOARD_ROMSIZE_KB_16384
select DRIVERS_I2C_HID
select DRIVERS_SYSTEM76_DGPU
select EC_SYSTEM76_EC
select HAVE_ACPI_RESUME
select HAVE_ACPI_TABLES

View File

@@ -2,10 +2,8 @@
#include <drivers/intel/gma/acpi/gma.asl>
Scope (GFX0)
{
Name (BRIG, Package (22)
{
Scope (GFX0) {
Name (BRIG, Package (22) {
40, /* default AC */
40, /* default Battery */
5,

View File

@@ -1,203 +0,0 @@
// From https://review.coreboot.org/c/coreboot/+/28380
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2017-2018 Patrick Rudolph <siro@das-labor.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; version 2 of
* the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* Nvidia Optimus support methods.
*
* Methods defined here are known to work on Lenovo's Sandy Bridge
* and Ivy Bridge series, which have GPIO21 pulled low on installed dGPU and
* GPIO17 to detect dGPU "PowerGood". They use the same PMH7 functions to
* enable dGPU power and handle dGPU reset.
*/
#define DGPU_RST_N GPP_F22
#define DGPU_PWR_EN GPP_F23
#define DGPU_GC6 GPP_K21
Device (\_SB.PCI0.PEGP.DEV0)
{
Name(_ADR, 0x00000000)
Name (_STA, 0xF)
Name (LTRE, 0)
// Memory mapped PCI express registers
// Not sure what this stuff is, but it is used to get into GC6
OperationRegion (RPCX, SystemMemory, 0xE0008000, 0x1000)
Field (RPCX, ByteAcc, NoLock, Preserve)
{
PVID, 16,
PDID, 16,
CMDR, 8,
Offset (0x19),
PRBN, 8,
Offset (0x84),
D0ST, 2,
Offset (0xAA),
CEDR, 1,
Offset (0xAC),
, 4,
CMLW, 6,
Offset (0xB0),
ASPM, 2,
, 2,
P0LD, 1,
RTLK, 1,
Offset (0xC9),
, 2,
LREN, 1,
Offset (0x11A),
, 1,
VCNP, 1,
Offset (0x214),
Offset (0x216),
P0LS, 4,
Offset (0x248),
, 7,
Q0L2, 1,
Q0L0, 1,
Offset (0x504),
Offset (0x506),
PCFG, 2,
Offset (0x508),
TREN, 1,
Offset (0xC20),
, 4,
P0AP, 2,
Offset (0xC38),
, 3,
P0RM, 1,
Offset (0xC74),
P0LT, 4,
Offset (0xD0C),
, 20,
LREV, 1
}
Method (_ON)
{
Debug = "PEGP.DEV0._ON"
If (_STA != 0xF) {
Debug = " If DGPU_PWR_EN low"
If (! GTXS (DGPU_PWR_EN)) {
Debug = " DGPU_PWR_EN high"
STXS (DGPU_PWR_EN)
Debug = " Sleep 16"
Sleep (16)
}
Debug = " DGPU_RST_N high"
STXS(DGPU_RST_N)
Debug = " Sleep 10"
Sleep (10)
Debug = " Q0L0 = 1"
Q0L0 = 1
Debug = " Sleep 16"
Sleep (16)
Debug = " While Q0L0"
Local0 = 0
While (Q0L0) {
If ((Local0 > 4)) {
Debug = " While Q0L0 timeout"
Break
}
Sleep (16)
Local0++
}
Debug = " P0RM = 0"
P0RM = 0
Debug = " P0AP = 0"
P0AP = 0
Debug = Concatenate(" LREN = ", ToHexString(LTRE))
LREN = LTRE
Debug = " CEDR = 1"
CEDR = 1
Debug = " CMDR |= 7"
CMDR |= 7
Debug = " _STA = 0xF"
_STA = 0xF
}
}
Method (_OFF)
{
Debug = "PEGP.DEV0._OFF"
If (_STA != 0x5) {
Debug = Concatenate(" LTRE = ", ToHexString(LREN))
LTRE = LREN
Debug = " Q0L2 = 1"
Q0L2 = 1
Debug = " Sleep 16"
Sleep (16)
Debug = " While Q0L2"
Local0 = Zero
While (Q0L2) {
If ((Local0 > 4)) {
Debug = " While Q0L2 timeout"
Break
}
Sleep (16)
Local0++
}
Debug = " P0RM = 1"
P0RM = 1
Debug = " P0AP = 3"
P0AP = 3
Debug = " Sleep 10"
Sleep (10)
Debug = " DGPU_RST_N low"
CTXS(DGPU_RST_N)
Debug = " While DGPU_GC6 low"
Local0 = Zero
While (! GRXS(DGPU_GC6)) {
If ((Local0 > 4)) {
Debug = " While DGPU_GC6 low timeout"
Debug = " DGPU_PWR_EN low"
CTXS (DGPU_PWR_EN)
Break
}
Sleep (16)
Local0++
}
Debug = " _STA = 0x5"
_STA = 0x5
}
}
}

View File

@@ -1,5 +1,8 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include "../gpio.h"
#include <drivers/system76/dgpu/acpi/dgpu.asl>
#define EC_GPE_SCI 0x03 /* GPP_K3 */
#define EC_GPE_SWI 0x06 /* GPP_K6 */
#define EC_COLOR_KEYBOARD 1
@@ -9,8 +12,6 @@ Scope (\_SB) {
#include "sleep.asl"
Scope (PCI0) {
#include "backlight.asl"
#include "pegp.asl"
#include "dgpu.asl"
}
}

View File

@@ -1,34 +0,0 @@
// From https://review.coreboot.org/c/coreboot/+/40625
/* SPDX-License-Identifier: GPL-2.0-only */
Device (PEGP)
{
Name (_ADR, 0x00010000)
PowerResource (PWRR, 0, 0)
{
Name (_STA, 1)
Method (_ON)
{
Debug = "PEGP.PWRR._ON"
If (_STA != 1) {
\_SB.PCI0.PEGP.DEV0._ON ()
_STA = 1
}
}
Method (_OFF)
{
Debug = "PEGP.PWRR._OFF"
If (_STA != 0) {
\_SB.PCI0.PEGP.DEV0._OFF ()
_STA = 0
}
}
}
Name (_PR0, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR2, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR3, Package () { \_SB.PCI0.PEGP.PWRR })
}

View File

@@ -1,29 +1,11 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootblock_common.h>
#include <console/console.h>
#include <delay.h>
#include <gpio.h>
#include "gpio.h"
#include <drivers/system76/dgpu/bootblock.c>
static void dgpu_power_enable(int onoff) {
printk(BIOS_DEBUG, "system76: DGPU power %d\n", onoff);
if (onoff) {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 1);
mdelay(4);
gpio_set(DGPU_RST_N, 1);
} else {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 0);
}
mdelay(50);
}
void bootblock_mainboard_init(void)
{
void bootblock_mainboard_init(void) {
gpio_configure_pads(early_gpio_table, ARRAY_SIZE(early_gpio_table));
dgpu_power_enable(1);
}

View File

@@ -14,16 +14,14 @@ DefinitionBlock(
#include <soc/intel/common/block/acpi/acpi/globalnvs.asl>
#include <cpu/intel/common/acpi/cpu.asl>
Device (\_SB.PCI0)
{
Device (\_SB.PCI0) {
#include <soc/intel/common/block/acpi/acpi/northbridge.asl>
#include <soc/intel/cannonlake/acpi/southbridge.asl>
}
#include <southbridge/intel/common/acpi/sleepstates.asl>
Scope (\_SB.PCI0.LPCB)
{
Scope (\_SB.PCI0.LPCB) {
#include <drivers/pc80/pc/ps2_controller.asl>
}

View File

@@ -3,14 +3,15 @@
#ifndef MAINBOARD_GPIO_H
#define MAINBOARD_GPIO_H
#include <soc/gpe.h>
#include <soc/gpio.h>
#define DGPU_RST_N GPP_F22
#define DGPU_PWR_EN GPP_F23
#define DGPU_GC6 GPP_K21
#ifndef __ACPI__
#include <soc/gpe.h>
#include <soc/gpio.h>
/* Pad configuration in romstage. */
static const struct pad_config early_gpio_table[] = {
PAD_CFG_GPI(GPP_C20, NONE, DEEP),

View File

@@ -1,90 +1,10 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootstate.h>
#include <console/console.h>
#include <device/pci.h>
#include <soc/ramstage.h>
#include "gpio.h"
void mainboard_silicon_init_params(FSP_S_CONFIG *params)
{
void mainboard_silicon_init_params(FSP_S_CONFIG *params) {
/* Configure pads prior to SiliconInit() in case there's any
* dependencies during hardware initialization. */
cnl_configure_pads(gpio_table, ARRAY_SIZE(gpio_table));
}
static void dgpu_read_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_read_resources %s\n", dev_path(dev));
pci_dev_read_resources(dev);
int bar;
// Find all BARs on DGPU, mark them above 4g if prefetchable
for (bar = PCI_BASE_ADDRESS_0; bar <= PCI_BASE_ADDRESS_5; bar += 4) {
printk(BIOS_INFO, " BAR at 0x%02x\n", bar);
struct resource *res;
res = probe_resource(dev, bar);
if (res) {
if (res->flags & IORESOURCE_PREFETCH) {
printk(BIOS_INFO, " marked above 4g\n");
res->flags |= IORESOURCE_ABOVE_4G;
} else {
printk(BIOS_INFO, " not prefetch\n");
}
} else {
printk(BIOS_INFO, " not found\n");
}
}
}
static void dgpu_enable_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_enable_resources %s\n", dev_path(dev));
dev->subsystem_vendor = CONFIG_SUBSYSTEM_VENDOR_ID;
dev->subsystem_device = CONFIG_SUBSYSTEM_DEVICE_ID;
printk(BIOS_INFO, " subsystem <- %04x/%04x\n", dev->subsystem_vendor, dev->subsystem_device);
pci_write_config32(dev, 0x40, ((dev->subsystem_device & 0xffff) << 16) | (dev->subsystem_vendor & 0xffff));
pci_dev_enable_resources(dev);
}
static struct device_operations dgpu_pci_ops_dev = {
.read_resources = dgpu_read_resources,
.set_resources = pci_dev_set_resources,
.enable_resources = dgpu_enable_resources,
#if CONFIG(HAVE_ACPI_TABLES)
.write_acpi_tables = pci_rom_write_acpi_tables,
.acpi_fill_ssdt = pci_rom_ssdt,
#endif
.init = pci_dev_init,
.ops_pci = &pci_dev_ops_pci,
};
static void dgpu_above_4g(void *unused) {
struct device *pdev;
// Find PEG0
pdev = pcidev_on_root(1, 0);
if (!pdev) {
printk(BIOS_ERR, "system76: failed to find PEG0\n");
return;
}
printk(BIOS_INFO, "system76: PEG0 at %p, %04x:%04x\n", pdev, pdev->vendor, pdev->device);
int fn;
for (fn = 0; fn < 8; fn++) {
struct device *dev;
// Find DGPU functions
dev = pcidev_path_behind(pdev->link_list, PCI_DEVFN(0, fn));
if (dev) {
printk(BIOS_INFO, "system76: DGPU fn %d at %p, %04x:%04x\n", fn, dev, dev->vendor, dev->device);
dev->ops = &dgpu_pci_ops_dev;
} else {
printk(BIOS_ERR, "system76: failed to find DGPU fn %d\n", fn);
}
}
}
BOOT_STATE_INIT_ENTRY(BS_DEV_RESOURCES, BS_ON_ENTRY, dgpu_above_4g, NULL);

View File

@@ -78,8 +78,7 @@ static const struct cnl_mb_cfg memcfg = {
.ect = 0,
};
void mainboard_memory_init_params(FSPM_UPD *memupd)
{
void mainboard_memory_init_params(FSPM_UPD *memupd) {
// Set primary display to internal graphics
memupd->FspmConfig.PrimaryDisplay = 0;
cannonlake_memcfg_init(&memupd->FspmConfig, &memcfg);

View File

@@ -5,6 +5,7 @@ config BOARD_SPECIFIC_OPTIONS
select BOARD_ROMSIZE_KB_16384
select DRIVERS_I2C_HID
select DRIVERS_I2C_TAS5825M
select DRIVERS_SYSTEM76_DGPU
select EC_SYSTEM76_EC
select HAVE_ACPI_RESUME
select HAVE_ACPI_TABLES

View File

@@ -2,10 +2,8 @@
#include <drivers/intel/gma/acpi/gma.asl>
Scope (GFX0)
{
Name (BRIG, Package (22)
{
Scope (GFX0) {
Name (BRIG, Package (22) {
40, /* default AC */
40, /* default Battery */
5,

View File

@@ -1,203 +0,0 @@
// From https://review.coreboot.org/c/coreboot/+/28380
/*
* This file is part of the coreboot project.
*
* Copyright (C) 2017-2018 Patrick Rudolph <siro@das-labor.org>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
* published by the Free Software Foundation; version 2 of
* the License.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* Nvidia Optimus support methods.
*
* Methods defined here are known to work on Lenovo's Sandy Bridge
* and Ivy Bridge series, which have GPIO21 pulled low on installed dGPU and
* GPIO17 to detect dGPU "PowerGood". They use the same PMH7 functions to
* enable dGPU power and handle dGPU reset.
*/
#define DGPU_RST_N GPP_F22
#define DGPU_PWR_EN GPP_F23
#define DGPU_GC6 GPP_K21
Device (\_SB.PCI0.PEGP.DEV0)
{
Name(_ADR, 0x00000000)
Name (_STA, 0xF)
Name (LTRE, 0)
// Memory mapped PCI express registers
// Not sure what this stuff is, but it is used to get into GC6
OperationRegion (RPCX, SystemMemory, 0xE0008000, 0x1000)
Field (RPCX, ByteAcc, NoLock, Preserve)
{
PVID, 16,
PDID, 16,
CMDR, 8,
Offset (0x19),
PRBN, 8,
Offset (0x84),
D0ST, 2,
Offset (0xAA),
CEDR, 1,
Offset (0xAC),
, 4,
CMLW, 6,
Offset (0xB0),
ASPM, 2,
, 2,
P0LD, 1,
RTLK, 1,
Offset (0xC9),
, 2,
LREN, 1,
Offset (0x11A),
, 1,
VCNP, 1,
Offset (0x214),
Offset (0x216),
P0LS, 4,
Offset (0x248),
, 7,
Q0L2, 1,
Q0L0, 1,
Offset (0x504),
Offset (0x506),
PCFG, 2,
Offset (0x508),
TREN, 1,
Offset (0xC20),
, 4,
P0AP, 2,
Offset (0xC38),
, 3,
P0RM, 1,
Offset (0xC74),
P0LT, 4,
Offset (0xD0C),
, 20,
LREV, 1
}
Method (_ON)
{
Debug = "PEGP.DEV0._ON"
If (_STA != 0xF) {
Debug = " If DGPU_PWR_EN low"
If (! GTXS (DGPU_PWR_EN)) {
Debug = " DGPU_PWR_EN high"
STXS (DGPU_PWR_EN)
Debug = " Sleep 16"
Sleep (16)
}
Debug = " DGPU_RST_N high"
STXS(DGPU_RST_N)
Debug = " Sleep 10"
Sleep (10)
Debug = " Q0L0 = 1"
Q0L0 = 1
Debug = " Sleep 16"
Sleep (16)
Debug = " While Q0L0"
Local0 = 0
While (Q0L0) {
If ((Local0 > 4)) {
Debug = " While Q0L0 timeout"
Break
}
Sleep (16)
Local0++
}
Debug = " P0RM = 0"
P0RM = 0
Debug = " P0AP = 0"
P0AP = 0
Debug = Concatenate(" LREN = ", ToHexString(LTRE))
LREN = LTRE
Debug = " CEDR = 1"
CEDR = 1
Debug = " CMDR |= 7"
CMDR |= 7
Debug = " _STA = 0xF"
_STA = 0xF
}
}
Method (_OFF)
{
Debug = "PEGP.DEV0._OFF"
If (_STA != 0x5) {
Debug = Concatenate(" LTRE = ", ToHexString(LREN))
LTRE = LREN
Debug = " Q0L2 = 1"
Q0L2 = 1
Debug = " Sleep 16"
Sleep (16)
Debug = " While Q0L2"
Local0 = Zero
While (Q0L2) {
If ((Local0 > 4)) {
Debug = " While Q0L2 timeout"
Break
}
Sleep (16)
Local0++
}
Debug = " P0RM = 1"
P0RM = 1
Debug = " P0AP = 3"
P0AP = 3
Debug = " Sleep 10"
Sleep (10)
Debug = " DGPU_RST_N low"
CTXS(DGPU_RST_N)
Debug = " While DGPU_GC6 low"
Local0 = Zero
While (! GRXS(DGPU_GC6)) {
If ((Local0 > 4)) {
Debug = " While DGPU_GC6 low timeout"
Debug = " DGPU_PWR_EN low"
CTXS (DGPU_PWR_EN)
Break
}
Sleep (16)
Local0++
}
Debug = " _STA = 0x5"
_STA = 0x5
}
}
}

View File

@@ -1,5 +1,8 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include "../gpio.h"
#include <drivers/system76/dgpu/acpi/dgpu.asl>
#define EC_GPE_SCI 0x03 /* GPP_K3 */
#define EC_GPE_SWI 0x06 /* GPP_K6 */
#define EC_COLOR_KEYBOARD 1
@@ -9,8 +12,6 @@ Scope (\_SB) {
#include "sleep.asl"
Scope (PCI0) {
#include "backlight.asl"
#include "pegp.asl"
#include "dgpu.asl"
}
}

View File

@@ -1,34 +0,0 @@
// From https://review.coreboot.org/c/coreboot/+/40625
/* SPDX-License-Identifier: GPL-2.0-only */
Device (PEGP)
{
Name (_ADR, 0x00010000)
PowerResource (PWRR, 0, 0)
{
Name (_STA, 1)
Method (_ON)
{
Debug = "PEGP.PWRR._ON"
If (_STA != 1) {
\_SB.PCI0.PEGP.DEV0._ON ()
_STA = 1
}
}
Method (_OFF)
{
Debug = "PEGP.PWRR._OFF"
If (_STA != 0) {
\_SB.PCI0.PEGP.DEV0._OFF ()
_STA = 0
}
}
}
Name (_PR0, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR2, Package () { \_SB.PCI0.PEGP.PWRR })
Name (_PR3, Package () { \_SB.PCI0.PEGP.PWRR })
}

View File

@@ -1,29 +1,11 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootblock_common.h>
#include <console/console.h>
#include <delay.h>
#include <gpio.h>
#include "gpio.h"
#include <drivers/system76/dgpu/bootblock.c>
static void dgpu_power_enable(int onoff) {
printk(BIOS_DEBUG, "system76: DGPU power %d\n", onoff);
if (onoff) {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 1);
mdelay(4);
gpio_set(DGPU_RST_N, 1);
} else {
gpio_set(DGPU_RST_N, 0);
mdelay(4);
gpio_set(DGPU_PWR_EN, 0);
}
mdelay(50);
}
void bootblock_mainboard_init(void)
{
void bootblock_mainboard_init(void) {
gpio_configure_pads(early_gpio_table, ARRAY_SIZE(early_gpio_table));
dgpu_power_enable(1);
}

View File

@@ -14,16 +14,14 @@ DefinitionBlock(
#include <soc/intel/common/block/acpi/acpi/globalnvs.asl>
#include <cpu/intel/common/acpi/cpu.asl>
Device (\_SB.PCI0)
{
Device (\_SB.PCI0) {
#include <soc/intel/common/block/acpi/acpi/northbridge.asl>
#include <soc/intel/cannonlake/acpi/southbridge.asl>
}
#include <southbridge/intel/common/acpi/sleepstates.asl>
Scope (\_SB.PCI0.LPCB)
{
Scope (\_SB.PCI0.LPCB) {
#include <drivers/pc80/pc/ps2_controller.asl>
}

View File

@@ -3,14 +3,15 @@
#ifndef MAINBOARD_GPIO_H
#define MAINBOARD_GPIO_H
#include <soc/gpe.h>
#include <soc/gpio.h>
#define DGPU_RST_N GPP_F22
#define DGPU_PWR_EN GPP_F23
#define DGPU_GC6 GPP_K21
#ifndef __ACPI__
#include <soc/gpe.h>
#include <soc/gpio.h>
/* Pad configuration in romstage. */
static const struct pad_config early_gpio_table[] = {
PAD_CFG_TERM_GPO(GPP_C14, 1, NONE, RSMRST), // M.2_PLT_RST_CNTRL1#

View File

@@ -1,90 +1,10 @@
/* SPDX-License-Identifier: GPL-2.0-only */
#include <bootstate.h>
#include <console/console.h>
#include <device/pci.h>
#include <soc/ramstage.h>
#include "gpio.h"
void mainboard_silicon_init_params(FSP_S_CONFIG *params)
{
void mainboard_silicon_init_params(FSP_S_CONFIG *params) {
/* Configure pads prior to SiliconInit() in case there's any
* dependencies during hardware initialization. */
cnl_configure_pads(gpio_table, ARRAY_SIZE(gpio_table));
}
static void dgpu_read_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_read_resources %s\n", dev_path(dev));
pci_dev_read_resources(dev);
int bar;
// Find all BARs on DGPU, mark them above 4g if prefetchable
for (bar = PCI_BASE_ADDRESS_0; bar <= PCI_BASE_ADDRESS_5; bar += 4) {
printk(BIOS_INFO, " BAR at 0x%02x\n", bar);
struct resource *res;
res = probe_resource(dev, bar);
if (res) {
if (res->flags & IORESOURCE_PREFETCH) {
printk(BIOS_INFO, " marked above 4g\n");
res->flags |= IORESOURCE_ABOVE_4G;
} else {
printk(BIOS_INFO, " not prefetch\n");
}
} else {
printk(BIOS_INFO, " not found\n");
}
}
}
static void dgpu_enable_resources(struct device *dev) {
printk(BIOS_INFO, "system76: dgpu_enable_resources %s\n", dev_path(dev));
dev->subsystem_vendor = CONFIG_SUBSYSTEM_VENDOR_ID;
dev->subsystem_device = CONFIG_SUBSYSTEM_DEVICE_ID;
printk(BIOS_INFO, " subsystem <- %04x/%04x\n", dev->subsystem_vendor, dev->subsystem_device);
pci_write_config32(dev, 0x40, ((dev->subsystem_device & 0xffff) << 16) | (dev->subsystem_vendor & 0xffff));
pci_dev_enable_resources(dev);
}
static struct device_operations dgpu_pci_ops_dev = {
.read_resources = dgpu_read_resources,
.set_resources = pci_dev_set_resources,
.enable_resources = dgpu_enable_resources,
#if CONFIG(HAVE_ACPI_TABLES)
.write_acpi_tables = pci_rom_write_acpi_tables,
.acpi_fill_ssdt = pci_rom_ssdt,
#endif
.init = pci_dev_init,
.ops_pci = &pci_dev_ops_pci,
};
static void dgpu_above_4g(void *unused) {
struct device *pdev;
// Find PEG0
pdev = pcidev_on_root(1, 0);
if (!pdev) {
printk(BIOS_ERR, "system76: failed to find PEG0\n");
return;
}
printk(BIOS_INFO, "system76: PEG0 at %p, %04x:%04x\n", pdev, pdev->vendor, pdev->device);
int fn;
for (fn = 0; fn < 8; fn++) {
struct device *dev;
// Find DGPU functions
dev = pcidev_path_behind(pdev->link_list, PCI_DEVFN(0, fn));
if (dev) {
printk(BIOS_INFO, "system76: DGPU fn %d at %p, %04x:%04x\n", fn, dev, dev->vendor, dev->device);
dev->ops = &dgpu_pci_ops_dev;
} else {
printk(BIOS_ERR, "system76: failed to find DGPU fn %d\n", fn);
}
}
}
BOOT_STATE_INIT_ENTRY(BS_DEV_RESOURCES, BS_ON_ENTRY, dgpu_above_4g, NULL);

View File

@@ -78,8 +78,7 @@ static const struct cnl_mb_cfg memcfg = {
.ect = 0,
};
void mainboard_memory_init_params(FSPM_UPD *memupd)
{
void mainboard_memory_init_params(FSPM_UPD *memupd) {
// Allow memory clocks higher than 2933 MHz
memupd->FspmConfig.SaOcSupport = 1;
// Set primary display to internal graphics