<p>Patrick Rudolph has uploaded this change for <strong>review</strong>.</p><p><a href="https://review.coreboot.org/20794">View Change</a></p><pre style="font-family: monospace,monospace; white-space: pre-wrap;">drvs/lenovo/hybrid_graphics: Switch to new hybrid driver<br><br>Get rid of old hybrid graphics driver and use the new one.<br>Disable IGD and PEG in early romstage and remove the PCI based driver.<br>Add GPIO configuration in devicetree.<br><br>Needs test on all devices.<br><br>Change-Id: Ibf18b75e8afe2568de8498b39a608dac8db3ba73<br>Signed-off-by: Patrick Rudolph <siro@das-labor.org><br>---<br>M src/drivers/lenovo/Kconfig<br>M src/drivers/lenovo/Makefile.inc<br>D src/drivers/lenovo/hybrid_graphics.c<br>M src/mainboard/lenovo/t420/devicetree.cb<br>M src/mainboard/lenovo/t420/romstage.c<br>M src/mainboard/lenovo/t420s/devicetree.cb<br>M src/mainboard/lenovo/t420s/romstage.c<br>M src/mainboard/lenovo/t430/devicetree.cb<br>M src/mainboard/lenovo/t430/romstage.c<br>M src/mainboard/lenovo/t520/devicetree.cb<br>M src/mainboard/lenovo/t520/romstage.c<br>M src/mainboard/lenovo/t530/devicetree.cb<br>M src/mainboard/lenovo/t530/romstage.c<br>13 files changed, 220 insertions(+), 131 deletions(-)<br><br></pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">git pull ssh://review.coreboot.org:29418/coreboot refs/changes/94/20794/1</pre><pre style="font-family: monospace,monospace; white-space: pre-wrap;">diff --git a/src/drivers/lenovo/Kconfig b/src/drivers/lenovo/Kconfig<br>index 38b86da..f20f3b2 100644<br>--- a/src/drivers/lenovo/Kconfig<br>+++ b/src/drivers/lenovo/Kconfig<br>@@ -27,15 +27,3 @@<br> endchoice<br> <br> endif<br>-<br>-config DRIVERS_LENOVO_HYBRID_GRAPHICS<br>- bool<br>- default n<br>-<br>-config HYBRID_GRAPHICS_GPIO_NUM<br>- depends on DRIVERS_LENOVO_HYBRID_GRAPHICS<br>- int<br>- default 52<br>- help<br>- Set a default GPIO that sets the panel LVDS signal routing to<br>- integrated or discrete GPU.<br>diff --git a/src/drivers/lenovo/Makefile.inc b/src/drivers/lenovo/Makefile.inc<br>index 66f8594..c50db5b 100644<br>--- a/src/drivers/lenovo/Makefile.inc<br>+++ b/src/drivers/lenovo/Makefile.inc<br>@@ -1,2 +1 @@<br> ramstage-$(CONFIG_DRIVERS_LENOVO_WACOM) += wacom.c<br>-ramstage-$(CONFIG_DRIVERS_LENOVO_HYBRID_GRAPHICS) += hybrid_graphics.c<br>diff --git a/src/drivers/lenovo/hybrid_graphics.c b/src/drivers/lenovo/hybrid_graphics.c<br>deleted file mode 100644<br>index 802823a..0000000<br>--- a/src/drivers/lenovo/hybrid_graphics.c<br>+++ /dev/null<br>@@ -1,114 +0,0 @@<br>-/*<br>- * This file is part of the coreboot project.<br>- *<br>- * Copyright (C) 2015-2016 Patrick Rudolph<br>- * Copyright (C) 2015 Timothy Pearson <tpearson@raptorengineeringinc.com>, Raptor Engineering<br>- *<br>- * This program is free software; you can redistribute it and/or modify<br>- * it under the terms of the GNU General Public License as published by<br>- * the Free Software Foundation; version 2 of the License.<br>- *<br>- * This program is distributed in the hope that it will be useful,<br>- * but WITHOUT ANY WARRANTY; without even the implied warranty of<br>- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the<br>- * GNU General Public License for more details.<br>- */<br>-<br>-#include <types.h><br>-#include <string.h><br>-#include <option.h><br>-#include <device/device.h><br>-#include <device/pci_def.h><br>-#include <device/pci_ops.h><br>-#include <device/pci_ids.h><br>-#include <device/pci.h><br>-#include <console/console.h><br>-#include <southbridge/intel/common/gpio.h><br>-<br>-/* Hybrid graphics allows to connect LVDS interface to either iGPU<br>- * or dGPU depending on GPIO level.<br>- * Nvidia is calling this functionality "muxed Optimus".<br>- * Some devices, like T430s, only support "muxless Optimus" where the<br>- * Intel GPU is always connected to the panel.<br>- * As it is only linked on lenovo and only executed if the GPU exists<br>- * we know for sure that the dGPU is there and connected to first PEG slot.<br>- *<br>- * Note: Once native gfx init is done for AMD or Nvida graphic<br>- * cards, merge this code.<br>- */<br>-<br>-#define HYBRID_GRAPHICS_INTEGRATED 0<br>-#define HYBRID_GRAPHICS_DISCRETE 1<br>-<br>-static void hybrid_graphics_disable_peg(struct device *dev)<br>-{<br>- struct device *peg_dev;<br>-<br>- /* connect LVDS interface to iGPU */<br>- set_gpio(CONFIG_HYBRID_GRAPHICS_GPIO_NUM, GPIO_LEVEL_HIGH);<br>- printk(BIOS_DEBUG, "Hybrid graphics: Switching panel to integrated GPU.\n");<br>- dev->enabled = 0;<br>-<br>- /* Disable PEG10 */<br>- peg_dev = dev_find_slot(0, PCI_DEVFN(1, 0));<br>- if (peg_dev)<br>- peg_dev->enabled = 0;<br>-<br>- printk(BIOS_DEBUG, "Hybrid graphics: Disabled PEG10.\n");<br>-}<br>-<br>-/* Called before VGA enable bits are set and only if dGPU<br>- * is present. Enable/disable VGA devices here. */<br>-static void hybrid_graphics_enable_peg(struct device *dev)<br>-{<br>- u8 hybrid_graphics_mode;<br>-<br>- hybrid_graphics_mode = HYBRID_GRAPHICS_INTEGRATED;<br>- get_option(&hybrid_graphics_mode, "hybrid_graphics_mode");<br>-<br>- if (hybrid_graphics_mode == HYBRID_GRAPHICS_DISCRETE) {<br>- /* connect LVDS interface to dGPU */<br>- set_gpio(CONFIG_HYBRID_GRAPHICS_GPIO_NUM, GPIO_LEVEL_LOW);<br>- printk(BIOS_DEBUG, "Hybrid graphics: Switching panel to discrete GPU.\n");<br>- dev->enabled = 1;<br>-<br>- /* Disable IGD */<br>- dev = dev_find_slot(0, PCI_DEVFN(2, 0));<br>- if (dev && dev->ops->disable)<br>- dev->ops->disable(dev);<br>- dev->enabled = 0;<br>-<br>- printk(BIOS_DEBUG, "Hybrid graphics: Disabled IGD.\n");<br>- } else<br>- hybrid_graphics_disable_peg(dev);<br>-}<br>-<br>-static struct pci_operations pci_dev_ops_pci = {<br>- .set_subsystem = pci_dev_set_subsystem,<br>-};<br>-<br>-struct device_operations hybrid_graphics_ops = {<br>- .read_resources = pci_dev_read_resources,<br>- .set_resources = pci_dev_set_resources,<br>- .enable_resources = pci_dev_enable_resources,<br>- .init = pci_dev_init,<br>- .scan_bus = 0,<br>- .enable = hybrid_graphics_enable_peg,<br>- .disable = hybrid_graphics_disable_peg,<br>- .ops_pci = &pci_dev_ops_pci,<br>-};<br>-<br>-static const unsigned short pci_device_ids_nvidia[] = {<br>- 0x0ffc, /* Nvidia NVS Quadro K1000m Lenovo W530 */<br>- 0x0def, /* NVidia NVS 5400m Lenovo T430/T530 */<br>- 0x0dfc, /* NVidia NVS 5200m Lenovo T430s */<br>- 0x1056, /* NVidia NVS 4200m Lenovo T420/T520 */<br>- 0x1057, /* NVidia NVS 4200m Lenovo T420/T520 */<br>- 0x0a6c, /* NVidia NVS 3100m Lenovo T410/T510 */<br>- 0 };<br>-<br>-static const struct pci_driver hybrid_peg_nvidia __pci_driver = {<br>- .ops = &hybrid_graphics_ops,<br>- .vendor = PCI_VENDOR_ID_NVIDIA,<br>- .devices = pci_device_ids_nvidia,<br>-};<br>diff --git a/src/mainboard/lenovo/t420/devicetree.cb b/src/mainboard/lenovo/t420/devicetree.cb<br>index deb62b7..7d41204 100644<br>--- a/src/mainboard/lenovo/t420/devicetree.cb<br>+++ b/src/mainboard/lenovo/t420/devicetree.cb<br>@@ -162,6 +162,17 @@<br> register "eventd_enable" = "0xff"<br> register "evente_enable" = "0x0d"<br> end<br>+ chip drivers/lenovo/hybrid_graphics<br>+ device pnp ff.f on end # dummy<br>+<br>+ register "detect_gpio" = "21"<br>+<br>+ register "has_panel_hybrid_gpio" = "1"<br>+ register "panel_hybrid_gpio" = "52"<br>+ register "panel_integrated_lvl" = "1"<br>+<br>+ register "has_backlight_gpio" = "0"<br>+ end<br> end # LPC Controller<br> device pci 1f.2 on<br> subsystemid 0x17aa 0x21ce<br>diff --git a/src/mainboard/lenovo/t420/romstage.c b/src/mainboard/lenovo/t420/romstage.c<br>index 94b8d62..f08ca03 100644<br>--- a/src/mainboard/lenovo/t420/romstage.c<br>+++ b/src/mainboard/lenovo/t420/romstage.c<br>@@ -18,6 +18,37 @@<br> #include <arch/io.h><br> #include <northbridge/intel/sandybridge/raminit_native.h><br> #include <southbridge/intel/bd82x6x/pch.h><br>+#include <drivers/lenovo/hybrid_graphics/hybrid_graphics.h><br>+#include <northbridge/intel/sandybridge/sandybridge.h><br>+#include <device/device.h><br>+#include <device/pci.h><br>+<br>+static void hybrid_graphics_init(void)<br>+{<br>+ struct device *dev;<br>+ bool peg, igd;<br>+ u32 reg32;<br>+<br>+ early_hybrid_graphics(&igd, &peg);<br>+<br>+ dev = dev_find_slot(0, PCI_DEVFN(0, 0));<br>+ if (!dev)<br>+ return;<br>+<br>+ /* Hide disabled devices */<br>+ reg32 = pci_read_config32(dev, DEVEN);<br>+ reg32 &= ~(DEVEN_PEG10 | DEVEN_IGD);<br>+<br>+ if (peg)<br>+ reg32 |= DEVEN_PEG10;<br>+<br>+ if (igd)<br>+ reg32 |= DEVEN_IGD;<br>+<br>+ pci_write_config32(dev, DEVEN, reg32);<br>+<br>+ /* TODO: Toggle GPU power */<br>+}<br> <br> void pch_enable_lpc(void)<br> {<br>@@ -65,6 +96,7 @@<br> <br> void mainboard_early_init(int s3resume)<br> {<br>+ hybrid_graphics_init();<br> }<br> <br> void mainboard_config_superio(void)<br>diff --git a/src/mainboard/lenovo/t420s/devicetree.cb b/src/mainboard/lenovo/t420s/devicetree.cb<br>index 3224322..b0ed992 100644<br>--- a/src/mainboard/lenovo/t420s/devicetree.cb<br>+++ b/src/mainboard/lenovo/t420s/devicetree.cb<br>@@ -154,6 +154,17 @@<br> register "eventd_enable" = "0xff"<br> register "evente_enable" = "0x0d"<br> end<br>+ chip drivers/lenovo/hybrid_graphics<br>+ device pnp ff.f on end # dummy<br>+<br>+ register "detect_gpio" = "21"<br>+<br>+ register "has_panel_hybrid_gpio" = "1"<br>+ register "panel_hybrid_gpio" = "52"<br>+ register "panel_integrated_lvl" = "1"<br>+<br>+ register "has_backlight_gpio" = "0"<br>+ end<br> end # LPC Controller<br> device pci 1f.2 on<br> subsystemid 0x17aa 0x21d2<br>diff --git a/src/mainboard/lenovo/t420s/romstage.c b/src/mainboard/lenovo/t420s/romstage.c<br>index d7f1c23..207abc6 100644<br>--- a/src/mainboard/lenovo/t420s/romstage.c<br>+++ b/src/mainboard/lenovo/t420s/romstage.c<br>@@ -17,10 +17,40 @@<br> <br> #include <arch/byteorder.h><br> #include <arch/io.h><br>-#include <device/pci_def.h><br> #include <console/console.h><br> #include <northbridge/intel/sandybridge/raminit_native.h><br> #include <southbridge/intel/bd82x6x/pch.h><br>+#include <drivers/lenovo/hybrid_graphics/hybrid_graphics.h><br>+#include <northbridge/intel/sandybridge/sandybridge.h><br>+#include <device/device.h><br>+#include <device/pci.h><br>+<br>+static void hybrid_graphics_init(void)<br>+{<br>+ struct device *dev;<br>+ bool peg, igd;<br>+ u32 reg32;<br>+<br>+ early_hybrid_graphics(&igd, &peg);<br>+<br>+ dev = dev_find_slot(0, PCI_DEVFN(0, 0));<br>+ if (!dev)<br>+ return;<br>+<br>+ /* Hide disabled devices */<br>+ reg32 = pci_read_config32(dev, DEVEN);<br>+ reg32 &= ~(DEVEN_PEG10 | DEVEN_IGD);<br>+<br>+ if (peg)<br>+ reg32 |= DEVEN_PEG10;<br>+<br>+ if (igd)<br>+ reg32 |= DEVEN_IGD;<br>+<br>+ pci_write_config32(dev, DEVEN, reg32);<br>+<br>+ /* TODO: Toggle GPU power */<br>+}<br> <br> void pch_enable_lpc(void)<br> {<br>@@ -65,7 +95,9 @@<br> read_spd(&spd[2], 0x51, id_only);<br> }<br> <br>-void mainboard_early_init(int s3resume) {<br>+void mainboard_early_init(int s3resume)<br>+{<br>+ hybrid_graphics_init();<br> }<br> <br> void mainboard_config_superio(void)<br>diff --git a/src/mainboard/lenovo/t430/devicetree.cb b/src/mainboard/lenovo/t430/devicetree.cb<br>index 0a121b7..d43c0c9 100644<br>--- a/src/mainboard/lenovo/t430/devicetree.cb<br>+++ b/src/mainboard/lenovo/t430/devicetree.cb<br>@@ -150,6 +150,17 @@<br> register "eventd_enable" = "0xff"<br> register "evente_enable" = "0x0d"<br> end<br>+ chip drivers/lenovo/hybrid_graphics<br>+ device pnp ff.f on end # dummy<br>+<br>+ register "detect_gpio" = "21"<br>+<br>+ register "has_panel_hybrid_gpio" = "1"<br>+ register "panel_hybrid_gpio" = "52"<br>+ register "panel_integrated_lvl" = "1"<br>+<br>+ register "has_backlight_gpio" = "0"<br>+ end<br> end<br> device pci 1f.2 on # SATA Controller 1<br> subsystemid 0x17aa 0x21f3<br>diff --git a/src/mainboard/lenovo/t430/romstage.c b/src/mainboard/lenovo/t430/romstage.c<br>index eb2d29e..c1be93c 100644<br>--- a/src/mainboard/lenovo/t430/romstage.c<br>+++ b/src/mainboard/lenovo/t430/romstage.c<br>@@ -18,6 +18,37 @@<br> #include <northbridge/intel/sandybridge/raminit_native.h><br> #include <southbridge/intel/bd82x6x/pch.h><br> #include <ec/lenovo/pmh7/pmh7.h><br>+#include <drivers/lenovo/hybrid_graphics/hybrid_graphics.h><br>+#include <northbridge/intel/sandybridge/sandybridge.h><br>+#include <device/device.h><br>+#include <device/pci.h><br>+<br>+static void hybrid_graphics_init(void)<br>+{<br>+ struct device *dev;<br>+ bool peg, igd;<br>+ u32 reg32;<br>+<br>+ early_hybrid_graphics(&igd, &peg);<br>+<br>+ dev = dev_find_slot(0, PCI_DEVFN(0, 0));<br>+ if (!dev)<br>+ return;<br>+<br>+ /* Hide disabled devices */<br>+ reg32 = pci_read_config32(dev, DEVEN);<br>+ reg32 &= ~(DEVEN_PEG10 | DEVEN_IGD);<br>+<br>+ if (peg)<br>+ reg32 |= DEVEN_PEG10;<br>+<br>+ if (igd)<br>+ reg32 |= DEVEN_IGD;<br>+<br>+ pci_write_config32(dev, DEVEN, reg32);<br>+<br>+ /* TODO: Toggle GPU power */<br>+}<br> <br> void pch_enable_lpc(void)<br> {<br>@@ -57,6 +88,7 @@<br> <br> void mainboard_early_init(int s3resume)<br> {<br>+ hybrid_graphics_init();<br> }<br> <br> void mainboard_config_superio(void)<br>diff --git a/src/mainboard/lenovo/t520/devicetree.cb b/src/mainboard/lenovo/t520/devicetree.cb<br>index 0065799..11f7b51 100644<br>--- a/src/mainboard/lenovo/t520/devicetree.cb<br>+++ b/src/mainboard/lenovo/t520/devicetree.cb<br>@@ -133,6 +133,17 @@<br> register "eventd_enable" = "0xff"<br> register "evente_enable" = "0x0d"<br> end<br>+ chip drivers/lenovo/hybrid_graphics<br>+ device pnp ff.f on end # dummy<br>+<br>+ register "detect_gpio" = "21"<br>+<br>+ register "has_panel_hybrid_gpio" = "1"<br>+ register "panel_hybrid_gpio" = "52"<br>+ register "panel_integrated_lvl" = "1"<br>+<br>+ register "has_backlight_gpio" = "0"<br>+ end<br> end # LPC bridge<br> device pci 1f.2 on end # SATA Controller 1<br> device pci 1f.3 on # SMBUS controller<br>diff --git a/src/mainboard/lenovo/t520/romstage.c b/src/mainboard/lenovo/t520/romstage.c<br>index f84bc0d..154423e 100644<br>--- a/src/mainboard/lenovo/t520/romstage.c<br>+++ b/src/mainboard/lenovo/t520/romstage.c<br>@@ -35,6 +35,36 @@<br> #include <arch/cpu.h><br> #include <cpu/x86/msr.h><br> #include <cbfs.h><br>+#include <drivers/lenovo/hybrid_graphics/hybrid_graphics.h><br>+#include <device/device.h><br>+#include <device/pci.h><br>+<br>+static void hybrid_graphics_init(void)<br>+{<br>+ struct device *dev;<br>+ bool peg, igd;<br>+ u32 reg32;<br>+<br>+ early_hybrid_graphics(&igd, &peg);<br>+<br>+ dev = dev_find_slot(0, PCI_DEVFN(0, 0));<br>+ if (!dev)<br>+ return;<br>+<br>+ /* Hide disabled devices */<br>+ reg32 = pci_read_config32(dev, DEVEN);<br>+ reg32 &= ~(DEVEN_PEG10 | DEVEN_IGD);<br>+<br>+ if (peg)<br>+ reg32 |= DEVEN_PEG10;<br>+<br>+ if (igd)<br>+ reg32 |= DEVEN_IGD;<br>+<br>+ pci_write_config32(dev, DEVEN, reg32);<br>+<br>+ /* TODO: Toggle GPU power */<br>+}<br> <br> void pch_enable_lpc(void)<br> {<br>@@ -79,7 +109,9 @@<br> read_spd (&spd[2], 0x51, id_only);<br> }<br> <br>-void mainboard_early_init(int s3resume) {<br>+void mainboard_early_init(int s3resume)<br>+{<br>+ hybrid_graphics_init();<br> }<br> <br> void mainboard_config_superio(void)<br>diff --git a/src/mainboard/lenovo/t530/devicetree.cb b/src/mainboard/lenovo/t530/devicetree.cb<br>index 2047a78..1ba060b 100644<br>--- a/src/mainboard/lenovo/t530/devicetree.cb<br>+++ b/src/mainboard/lenovo/t530/devicetree.cb<br>@@ -140,6 +140,17 @@<br> register "eventd_enable" = "0xff"<br> register "evente_enable" = "0x0d"<br> end<br>+ chip drivers/lenovo/hybrid_graphics<br>+ device pnp ff.f on end # dummy<br>+<br>+ register "detect_gpio" = "21"<br>+<br>+ register "has_panel_hybrid_gpio" = "1"<br>+ register "panel_hybrid_gpio" = "52"<br>+ register "panel_integrated_lvl" = "1"<br>+<br>+ register "has_backlight_gpio" = "0"<br>+ end<br> end # LPC bridge<br> device pci 1f.2 on end # SATA Controller 1<br> device pci 1f.3 on<br>diff --git a/src/mainboard/lenovo/t530/romstage.c b/src/mainboard/lenovo/t530/romstage.c<br>index c454ec7..d1b7ec1 100644<br>--- a/src/mainboard/lenovo/t530/romstage.c<br>+++ b/src/mainboard/lenovo/t530/romstage.c<br>@@ -22,6 +22,37 @@<br> #include <console/console.h><br> #include <northbridge/intel/sandybridge/raminit_native.h><br> #include <southbridge/intel/bd82x6x/pch.h><br>+#include <northbridge/intel/sandybridge/sandybridge.h><br>+#include <drivers/lenovo/hybrid_graphics/hybrid_graphics.h><br>+#include <device/device.h><br>+#include <device/pci.h><br>+<br>+static void hybrid_graphics_init(void)<br>+{<br>+ struct device *dev;<br>+ bool peg, igd;<br>+ u32 reg32;<br>+<br>+ early_hybrid_graphics(&igd, &peg);<br>+<br>+ dev = dev_find_slot(0, PCI_DEVFN(0, 0));<br>+ if (!dev)<br>+ return;<br>+<br>+ /* Hide disabled devices */<br>+ reg32 = pci_read_config32(dev, DEVEN);<br>+ reg32 &= ~(DEVEN_PEG10 | DEVEN_IGD);<br>+<br>+ if (peg)<br>+ reg32 |= DEVEN_PEG10;<br>+<br>+ if (igd)<br>+ reg32 |= DEVEN_IGD;<br>+<br>+ pci_write_config32(dev, DEVEN, reg32);<br>+<br>+ /* TODO: Toggle GPU power */<br>+}<br> <br> void pch_enable_lpc(void)<br> {<br>@@ -66,7 +97,9 @@<br> read_spd (&spd[2], 0x51, id_only);<br> }<br> <br>-void mainboard_early_init(int s3resume) {<br>+void mainboard_early_init(int s3resume)<br>+{<br>+ hybrid_graphics_init();<br> }<br> <br> void mainboard_config_superio(void)<br></pre><p>To view, visit <a href="https://review.coreboot.org/20794">change 20794</a>. To unsubscribe, visit <a href="https://review.coreboot.org/settings">settings</a>.</p><div itemscope itemtype="http://schema.org/EmailMessage"><div itemscope itemprop="action" itemtype="http://schema.org/ViewAction"><link itemprop="url" href="https://review.coreboot.org/20794"/><meta itemprop="name" content="View Change"/></div></div>
<div style="display:none"> Gerrit-Project: coreboot </div>
<div style="display:none"> Gerrit-Branch: master </div>
<div style="display:none"> Gerrit-MessageType: newchange </div>
<div style="display:none"> Gerrit-Change-Id: Ibf18b75e8afe2568de8498b39a608dac8db3ba73 </div>
<div style="display:none"> Gerrit-Change-Number: 20794 </div>
<div style="display:none"> Gerrit-PatchSet: 1 </div>
<div style="display:none"> Gerrit-Owner: Patrick Rudolph <siro@das-labor.org> </div>