nb/intel/haswell: Handle boards that do not support IGD

Processor graphics is disabled on, for example, the C222 and C224
chipsets.

The change to resource assignment in northbridge.c prevents the following
warning that occurs when the IGD is disabled:

> skipping PCI: 00:00.0@3 fixed resource, size=0!

Tested on a Supermicro X10SLM+-F, which has the IGD disabled by the
chipset. The graphics memory is reclaimed and no issues were observed.

Also tested on an ASRock H81M-HDS. This board has an IGD, but no
regressions were observed.

Change-Id: I86d4aef50b6588f08b86c9758a4b95ccd65e9a96
Signed-off-by: Tristan Corrick <tristan@corrick.kiwi>
Reviewed-on: https://review.coreboot.org/c/30271
Tested-by: build bot (Jenkins) <no-reply@coreboot.org>
Reviewed-by: Arthur Heymans <arthur@aheymans.xyz>
Reviewed-by: Angel Pons <th3fanbus@gmail.com>
diff --git a/src/northbridge/intel/haswell/early_init.c b/src/northbridge/intel/haswell/early_init.c
index 861873e..e31bb0e 100644
--- a/src/northbridge/intel/haswell/early_init.c
+++ b/src/northbridge/intel/haswell/early_init.c
@@ -47,28 +47,41 @@
 
 static void haswell_setup_graphics(void)
 {
-	u32 reg32;
-	u16 reg16;
+	bool igd_enabled;
+	u16 ggc;
 	u8 reg8;
 
 	printk(BIOS_DEBUG, "Initializing Graphics...\n");
 
-	/* Setup IGD memory by setting GGC[7:3] = 1 for 32MB */
-	reg16 = pci_read_config16(PCI_DEV(0,0,0), GGC);
-	reg16 &= ~0x00f8;
-	reg16 |= 1 << 3;
-	/* Program GTT memory by setting GGC[9:8] = 2MB */
-	reg16 &= ~0x0300;
-	reg16 |= 2 << 8;
-	/* Enable VGA decode */
-	reg16 &= ~0x0002;
-	pci_write_config16(PCI_DEV(0,0,0), GGC, reg16);
+	igd_enabled = !!(pci_read_config32(PCI_DEV(0, 0, 0), DEVEN)
+			 & DEVEN_D2EN);
+
+	ggc = pci_read_config16(PCI_DEV(0, 0, 0), GGC);
+	ggc &= ~0x3f8;
+	if (igd_enabled) {
+		ggc |= GGC_GTT_2MB | GGC_IGD_MEM_IN_32MB_UNITS(1);
+		ggc &= ~GGC_DISABLE_VGA_IO_DECODE;
+	} else {
+		ggc |= GGC_GTT_0MB | GGC_IGD_MEM_IN_32MB_UNITS(0) |
+		       GGC_DISABLE_VGA_IO_DECODE;
+	}
+	pci_write_config16(PCI_DEV(0, 0, 0), GGC, ggc);
+
+	if (!igd_enabled) {
+		printk(BIOS_DEBUG, "IGD is disabled.\n");
+		return;
+	}
 
 	/* Enable 256MB aperture */
 	reg8 = pci_read_config8(PCI_DEV(0, 2, 0), MSAC);
 	reg8 &= ~0x06;
 	reg8 |= 0x02;
 	pci_write_config8(PCI_DEV(0, 2, 0), MSAC, reg8);
+}
+
+static void haswell_setup_misc(void)
+{
+	u32 reg32;
 
 	/* Erratum workarounds */
 	reg32 = MCHBAR32(0x5f00);
@@ -128,4 +141,6 @@
 	haswell_setup_iommu();
 
 	haswell_setup_graphics();
+
+	haswell_setup_misc();
 }
diff --git a/src/northbridge/intel/haswell/haswell.h b/src/northbridge/intel/haswell/haswell.h
index 33818ee..bc2fc60 100644
--- a/src/northbridge/intel/haswell/haswell.h
+++ b/src/northbridge/intel/haswell/haswell.h
@@ -54,6 +54,11 @@
 #define DMIBAR		0x68
 
 #define GGC		0x50			/* GMCH Graphics Control */
+#define  GGC_DISABLE_VGA_IO_DECODE	(1 << 1)
+#define  GGC_IGD_MEM_IN_32MB_UNITS(x)	(((x) & 0x1f) << 3)
+#define  GGC_GTT_0MB		(0 << 8)
+#define  GGC_GTT_1MB		(1 << 8)
+#define  GGC_GTT_2MB		(2 << 8)
 
 #define DEVEN		0x54			/* Device Enable */
 #define  DEVEN_D7EN	(1 << 14)
diff --git a/src/northbridge/intel/haswell/northbridge.c b/src/northbridge/intel/haswell/northbridge.c
index a803e98..fcdb683 100644
--- a/src/northbridge/intel/haswell/northbridge.c
+++ b/src/northbridge/intel/haswell/northbridge.c
@@ -371,13 +371,15 @@
 			  IORESOURCE_STORED | IORESOURCE_RESERVE |
 			  IORESOURCE_ASSIGNED | IORESOURCE_CACHEABLE;
 
-	/* BGSM -> TOLUD */
-	resource = new_resource(dev, index++);
-	resource->base = mc_values[BGSM_REG];
-	resource->size = mc_values[TOLUD_REG] - resource->base;
-	resource->flags = IORESOURCE_MEM | IORESOURCE_FIXED |
-			  IORESOURCE_STORED | IORESOURCE_RESERVE |
-			  IORESOURCE_ASSIGNED;
+	/* BGSM -> TOLUD. If the IGD is disabled, BGSM can equal TOLUD */
+	if (mc_values[BGSM_REG] != mc_values[TOLUD_REG]) {
+		resource = new_resource(dev, index++);
+		resource->base = mc_values[BGSM_REG];
+		resource->size = mc_values[TOLUD_REG] - resource->base;
+		resource->flags = IORESOURCE_MEM | IORESOURCE_FIXED |
+				  IORESOURCE_STORED | IORESOURCE_RESERVE |
+				  IORESOURCE_ASSIGNED;
+	}
 
 	/* 4GiB -> TOUUD */
 	base_k = 4096 * 1024; /* 4GiB */