9950 Need support for Intel I219 v6-v9
Reviewed by: Jason King <jason.king@joyent.com>
Reviewed by: Garrett D'Amore <garrett@damore.org>
Approved by: Garrett D'Amore <garrett@damore.org>
diff --git a/usr/src/pkg/manifests/driver-network-e1000g.mf b/usr/src/pkg/manifests/driver-network-e1000g.mf
index 727cb7a..1037302 100644
--- a/usr/src/pkg/manifests/driver-network-e1000g.mf
+++ b/usr/src/pkg/manifests/driver-network-e1000g.mf
@@ -147,9 +147,17 @@
     alias=pci8086,15b7 \
     alias=pci8086,15b8 \
     alias=pci8086,15b9 \
+    alias=pci8086,15bb \
+    alias=pci8086,15bc \
+    alias=pci8086,15bd \
+    alias=pci8086,15be \
     alias=pci8086,15d6 \
     alias=pci8086,15d7 \
     alias=pci8086,15d8 \
+    alias=pci8086,15df \
+    alias=pci8086,15e0 \
+    alias=pci8086,15e1 \
+    alias=pci8086,15e2 \
     alias=pci8086,15e3 \
     alias=pci8086,294c \
     alias=pci8086,f0fe \
@@ -215,9 +223,17 @@
     alias=pciex8086,15b7 \
     alias=pciex8086,15b8 \
     alias=pciex8086,15b9 \
+    alias=pciex8086,15bb \
+    alias=pciex8086,15bc \
+    alias=pciex8086,15bd \
+    alias=pciex8086,15be \
     alias=pciex8086,15d6 \
     alias=pciex8086,15d7 \
     alias=pciex8086,15d8 \
+    alias=pciex8086,15df \
+    alias=pciex8086,15e0 \
+    alias=pciex8086,15e1 \
+    alias=pciex8086,15e2 \
     alias=pciex8086,15e3 \
     alias=pciex8086,294c \
     alias=pciex8086,f0fe
diff --git a/usr/src/uts/common/io/e1000api/README.illumos b/usr/src/uts/common/io/e1000api/README.illumos
index b4335b1..37cecd0 100644
--- a/usr/src/uts/common/io/e1000api/README.illumos
+++ b/usr/src/uts/common/io/e1000api/README.illumos
@@ -45,6 +45,12 @@
 needs to be done in terms of changed interfaces and expectations for the
 drivers.
 
+# Support for Ice Lake and Cannon Lake
+
+Due to several changes that have been made to the core e1000 code in
+FreeBSD that's specific to changes for iflib, a whole sale update was
+not done and instead support was manually merged based on Intel.
+
 # e1000_defines.h
 
 In e1000_defines.h we add the following three definitions which are not
diff --git a/usr/src/uts/common/io/e1000api/e1000_api.c b/usr/src/uts/common/io/e1000api/e1000_api.c
index 52e2609..45dbbfc 100644
--- a/usr/src/uts/common/io/e1000api/e1000_api.c
+++ b/usr/src/uts/common/io/e1000api/e1000_api.c
@@ -310,6 +310,16 @@
 	case E1000_DEV_ID_PCH_SPT_I219_V5:
 		mac->type = e1000_pch_spt;
 		break;
+	case E1000_DEV_ID_PCH_CNP_I219_LM6:
+	case E1000_DEV_ID_PCH_CNP_I219_V6:
+	case E1000_DEV_ID_PCH_CNP_I219_LM7:
+	case E1000_DEV_ID_PCH_CNP_I219_V7:
+	case E1000_DEV_ID_PCH_ICP_I219_LM8:
+	case E1000_DEV_ID_PCH_ICP_I219_V8:
+	case E1000_DEV_ID_PCH_ICP_I219_LM9:
+	case E1000_DEV_ID_PCH_ICP_I219_V9:
+		mac->type = e1000_pch_cnp;
+		break;
 	case E1000_DEV_ID_82575EB_COPPER:
 	case E1000_DEV_ID_82575EB_FIBER_SERDES:
 	case E1000_DEV_ID_82575GB_QUAD_COPPER:
@@ -461,6 +471,7 @@
 	case e1000_pch2lan:
 	case e1000_pch_lpt:
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		e1000_init_function_pointers_ich8lan(hw);
 		break;
 	case e1000_82575:
diff --git a/usr/src/uts/common/io/e1000api/e1000_hw.h b/usr/src/uts/common/io/e1000api/e1000_hw.h
index 98931b7..ff9f1ff 100644
--- a/usr/src/uts/common/io/e1000api/e1000_hw.h
+++ b/usr/src/uts/common/io/e1000api/e1000_hw.h
@@ -146,6 +146,14 @@
 #define E1000_DEV_ID_PCH_SPT_I219_V4		0x15D8
 #define E1000_DEV_ID_PCH_SPT_I219_LM5		0x15E3
 #define E1000_DEV_ID_PCH_SPT_I219_V5		0x15D6
+#define E1000_DEV_ID_PCH_CNP_I219_LM6		0x15BD
+#define E1000_DEV_ID_PCH_CNP_I219_V6		0x15BE
+#define E1000_DEV_ID_PCH_CNP_I219_LM7		0x15BB
+#define E1000_DEV_ID_PCH_CNP_I219_V7		0x15BC
+#define E1000_DEV_ID_PCH_ICP_I219_LM8		0x15DF
+#define E1000_DEV_ID_PCH_ICP_I219_V8		0x15E0
+#define E1000_DEV_ID_PCH_ICP_I219_LM9		0x15E1
+#define E1000_DEV_ID_PCH_ICP_I219_V9		0x15E2
 #define E1000_DEV_ID_82576			0x10C9
 #define E1000_DEV_ID_82576_FIBER		0x10E6
 #define E1000_DEV_ID_82576_SERDES		0x10E7
@@ -205,6 +213,13 @@
 #define E1000_ALT_MAC_ADDRESS_OFFSET_LAN2	6
 #define E1000_ALT_MAC_ADDRESS_OFFSET_LAN3	9
 
+/*
+ * This enumeration represents all of the different kinds of MAC chips that are
+ * used by both the e1000g and igb drivers. The ordering here is important as
+ * certain classes of MACs are very similar, but have minor differences and so
+ * are compared based on the ordering here. Changing the order here should not
+ * be done arbitrarily.
+ */
 enum e1000_mac_type {
 	e1000_undefined = 0,
 	e1000_82542,
@@ -225,6 +240,13 @@
 	e1000_82574,
 	e1000_82583,
 	e1000_80003es2lan,
+	/*
+	 * The following MACs all share the ich8 style of hardware and are
+	 * implemented in ich8, though some are a little more different than
+	 * others. The pch_lpt, pch_spt, and pch_cnp family are a bit more
+	 * different than the others and just have slight variants in behavior
+	 * between them. They are ordered based on release.
+	 */
 	e1000_ich8lan,
 	e1000_ich9lan,
 	e1000_ich10lan,
@@ -232,6 +254,12 @@
 	e1000_pch2lan,
 	e1000_pch_lpt,
 	e1000_pch_spt,
+	e1000_pch_cnp,
+	/*
+	 * After this point all MACs are used by the igb(7D) driver as opposed
+	 * to e1000g(7D). If a new MAC is specific to e1000g series of devices,
+	 * then it should be added above this.
+	 */
 	e1000_82575,
 	e1000_82576,
 	e1000_82580,
diff --git a/usr/src/uts/common/io/e1000api/e1000_ich8lan.c b/usr/src/uts/common/io/e1000api/e1000_ich8lan.c
index a08aed6..966e176 100644
--- a/usr/src/uts/common/io/e1000api/e1000_ich8lan.c
+++ b/usr/src/uts/common/io/e1000api/e1000_ich8lan.c
@@ -243,8 +243,7 @@
 	if (ret_val)
 		return FALSE;
 out:
-	if ((hw->mac.type == e1000_pch_lpt) ||
-	    (hw->mac.type == e1000_pch_spt)) {
+	if (hw->mac.type >= e1000_pch_lpt) {
 		/* Only unforce SMBus if ME is not active */
 		if (!(E1000_READ_REG(hw, E1000_FWSM) &
 		    E1000_ICH_FWSM_FW_VALID)) {
@@ -345,6 +344,7 @@
 	switch (hw->mac.type) {
 	case e1000_pch_lpt:
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		if (e1000_phy_is_accessible_pchlan(hw))
 			break;
 
@@ -493,6 +493,7 @@
 		case e1000_pch2lan:
 		case e1000_pch_lpt:
 		case e1000_pch_spt:
+		case e1000_pch_cnp:
 			/* In case the PHY needs to be in mdio slow mode,
 			 * set slow mode and try to get the PHY id again.
 			 */
@@ -641,7 +642,7 @@
 
 	nvm->type = e1000_nvm_flash_sw;
 
-	if (hw->mac.type == e1000_pch_spt) {
+	if (hw->mac.type >= e1000_pch_spt) {
 		/* in SPT, gfpreg doesn't exist. NVM size is taken from the
 		 * STRAP register. This is because in SPT the GbE Flash region
 		 * is no longer accessed through the flash registers. Instead,
@@ -701,7 +702,7 @@
 	/* Function Pointers */
 	nvm->ops.acquire	= e1000_acquire_nvm_ich8lan;
 	nvm->ops.release	= e1000_release_nvm_ich8lan;
-	if (hw->mac.type == e1000_pch_spt) {
+	if (hw->mac.type >= e1000_pch_spt) {
 		nvm->ops.read	= e1000_read_nvm_spt;
 		nvm->ops.update	= e1000_update_nvm_checksum_spt;
 	} else {
@@ -794,6 +795,7 @@
 		/* fall-through */
 	case e1000_pch_lpt:
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		/* multicast address update for pch2 */
 		mac->ops.update_mc_addr_list =
 			e1000_update_mc_addr_list_pch2lan;
@@ -815,8 +817,7 @@
 		break;
 	}
 
-	if ((mac->type == e1000_pch_lpt) ||
-	    (mac->type == e1000_pch_spt)) {
+	if (mac->type >= e1000_pch_lpt) {
 		mac->rar_entry_count = E1000_PCH_LPT_RAR_ENTRIES;
 		mac->ops.rar_set = e1000_rar_set_pch_lpt;
 		mac->ops.setup_physical_interface = e1000_setup_copper_link_pch_lpt;
@@ -1576,9 +1577,7 @@
 	 * aggressive resulting in many collisions. To avoid this, increase
 	 * the IPG and reduce Rx latency in the PHY.
 	 */
-	if (((hw->mac.type == e1000_pch2lan) ||
-	     (hw->mac.type == e1000_pch_lpt) ||
-	     (hw->mac.type == e1000_pch_spt)) && link) {
+	if ((hw->mac.type >= e1000_pch2lan) && link) {
 		u16 speed, duplex;
 
 		e1000_get_speed_and_duplex_copper_generic(hw, &speed, &duplex);
@@ -1589,7 +1588,7 @@
 			tipg_reg |= 0xFF;
 			/* Reduce Rx latency in analog PHY */
 			emi_val = 0;
-		} else if (hw->mac.type == e1000_pch_spt &&
+		} else if (hw->mac.type >= e1000_pch_spt &&
 			   duplex == FULL_DUPLEX && speed != SPEED_1000) {
 			tipg_reg |= 0xC;
 			emi_val = 1;
@@ -1611,8 +1610,7 @@
 			emi_addr = I217_RX_CONFIG;
 		ret_val = e1000_write_emi_reg_locked(hw, emi_addr, emi_val);
 
-		if (hw->mac.type == e1000_pch_lpt ||
-		    hw->mac.type == e1000_pch_spt) {
+		if (hw->mac.type >= e1000_pch_lpt) {
 			u16 phy_reg;
 
 			hw->phy.ops.read_reg_locked(hw, I217_PLL_CLOCK_GATE_REG,
@@ -1641,7 +1639,7 @@
 		if (ret_val)
 			return ret_val;
 
-		if (hw->mac.type == e1000_pch_spt) {
+		if (hw->mac.type >= e1000_pch_spt) {
 			u16 data;
 			u16 ptr_gap;
 
@@ -1690,8 +1688,7 @@
 	 * on power up.
 	 * Set the Beacon Duration for I217 to 8 usec
 	 */
-	if ((hw->mac.type == e1000_pch_lpt) ||
-	    (hw->mac.type == e1000_pch_spt)) {
+	if (hw->mac.type >= e1000_pch_lpt) {
 		u32 mac_reg;
 
 		mac_reg = E1000_READ_REG(hw, E1000_FEXTNVM4);
@@ -1709,8 +1706,7 @@
 		if (ret_val)
 			return ret_val;
 	}
-	if ((hw->mac.type == e1000_pch_lpt) ||
-	    (hw->mac.type == e1000_pch_spt)) {
+	if (hw->mac.type >= e1000_pch_lpt) {
 		/* Set platform power management values for
 		 * Latency Tolerance Reporting (LTR)
 		 * Optimized Buffer Flush/Fill (OBFF)
@@ -1723,7 +1719,7 @@
 	/* Clear link partner's EEE ability */
 	hw->dev_spec.ich8lan.eee_lp_ability = 0;
 
-	/* FEXTNVM6 K1-off workaround */
+	/* FEXTNVM6 K1-off workaround - for SPT only */
 	if (hw->mac.type == e1000_pch_spt) {
 		u32 pcieanacfg = E1000_READ_REG(hw, E1000_PCIEANACFG);
 		u32 fextnvm6 = E1000_READ_REG(hw, E1000_FEXTNVM6);
@@ -1831,6 +1827,7 @@
 	case e1000_pch2lan:
 	case e1000_pch_lpt:
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		hw->phy.ops.init_params = e1000_init_phy_params_pchlan;
 		break;
 	default:
@@ -2295,6 +2292,7 @@
 	case e1000_pch2lan:
 	case e1000_pch_lpt:
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		sw_cfg_mask = E1000_FEXTNVM_SW_CONFIG_ICH8M;
 		break;
 	default:
@@ -3412,6 +3410,7 @@
 
 	switch (hw->mac.type) {
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		bank1_offset = nvm->flash_bank_size;
 		act_offset = E1000_ICH_NVM_SIG_WORD;
 
@@ -3671,7 +3670,7 @@
 	/* Clear FCERR and DAEL in hw status by writing 1 */
 	hsfsts.hsf_status.flcerr = 1;
 	hsfsts.hsf_status.dael = 1;
-	if (hw->mac.type == e1000_pch_spt)
+	if (hw->mac.type >= e1000_pch_spt)
 		E1000_WRITE_FLASH_REG(hw, ICH_FLASH_HSFSTS,
 				      hsfsts.regval & 0xFFFF);
 	else
@@ -3691,7 +3690,7 @@
 		 * Begin by setting Flash Cycle Done.
 		 */
 		hsfsts.hsf_status.flcdone = 1;
-		if (hw->mac.type == e1000_pch_spt)
+		if (hw->mac.type >= e1000_pch_spt)
 			E1000_WRITE_FLASH_REG(hw, ICH_FLASH_HSFSTS,
 					      hsfsts.regval & 0xFFFF);
 		else
@@ -3718,7 +3717,7 @@
 			 * now set the Flash Cycle Done.
 			 */
 			hsfsts.hsf_status.flcdone = 1;
-			if (hw->mac.type == e1000_pch_spt)
+			if (hw->mac.type >= e1000_pch_spt)
 				E1000_WRITE_FLASH_REG(hw, ICH_FLASH_HSFSTS,
 						      hsfsts.regval & 0xFFFF);
 			else
@@ -3748,13 +3747,13 @@
 	DEBUGFUNC("e1000_flash_cycle_ich8lan");
 
 	/* Start a cycle by writing 1 in Flash Cycle Go in Hw Flash Control */
-	if (hw->mac.type == e1000_pch_spt)
+	if (hw->mac.type >= e1000_pch_spt)
 		hsflctl.regval = E1000_READ_FLASH_REG(hw, ICH_FLASH_HSFSTS)>>16;
 	else
 		hsflctl.regval = E1000_READ_FLASH_REG16(hw, ICH_FLASH_HSFCTL);
 	hsflctl.hsf_ctrl.flcgo = 1;
 
-	if (hw->mac.type == e1000_pch_spt)
+	if (hw->mac.type >= e1000_pch_spt)
 		E1000_WRITE_FLASH_REG(hw, ICH_FLASH_HSFSTS,
 				      hsflctl.regval << 16);
 	else
@@ -3837,7 +3836,7 @@
 	/* In SPT, only 32 bits access is supported,
 	 * so this function should not be called.
 	 */
-	if (hw->mac.type == e1000_pch_spt)
+	if (hw->mac.type >= e1000_pch_spt)
 		return -E1000_ERR_NVM;
 	else
 		ret_val = e1000_read_flash_data_ich8lan(hw, offset, 1, &word);
@@ -3945,9 +3944,8 @@
 
 	DEBUGFUNC("e1000_read_flash_data_ich8lan");
 
-		if (offset > ICH_FLASH_LINEAR_ADDR_MASK ||
-		    hw->mac.type != e1000_pch_spt)
-			return -E1000_ERR_NVM;
+	if (offset > ICH_FLASH_LINEAR_ADDR_MASK && hw->mac.type < e1000_pch_spt)
+		return -E1000_ERR_NVM;
 	flash_linear_addr = ((ICH_FLASH_LINEAR_ADDR_MASK & offset) +
 			     hw->nvm.flash_base_addr);
 
@@ -4387,6 +4385,7 @@
 	switch (hw->mac.type) {
 	case e1000_pch_lpt:
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		word = NVM_COMPAT;
 		valid_csum_mask = NVM_COMPAT_VALID_CSUM;
 		break;
@@ -4434,7 +4433,7 @@
 
 	DEBUGFUNC("e1000_write_ich8_data");
 
-	if (hw->mac.type == e1000_pch_spt) {
+	if (hw->mac.type >= e1000_pch_spt) {
 		if (size != 4 || offset > ICH_FLASH_LINEAR_ADDR_MASK)
 			return -E1000_ERR_NVM;
 	} else {
@@ -4454,9 +4453,9 @@
 		/* In SPT, This register is in Lan memory space, not
 		 * flash.  Therefore, only 32 bit access is supported
 		 */
-		if (hw->mac.type == e1000_pch_spt)
+		if (hw->mac.type >= e1000_pch_spt)
 			hsflctl.regval =
-			    E1000_READ_FLASH_REG(hw, ICH_FLASH_HSFSTS)>>16;
+			    E1000_READ_FLASH_REG(hw, ICH_FLASH_HSFSTS) >> 16;
 		else
 			hsflctl.regval =
 			    E1000_READ_FLASH_REG16(hw, ICH_FLASH_HSFCTL);
@@ -4468,7 +4467,7 @@
 		 * not flash.  Therefore, only 32 bit access is
 		 * supported
 		 */
-		if (hw->mac.type == e1000_pch_spt)
+		if (hw->mac.type >= e1000_pch_spt)
 			E1000_WRITE_FLASH_REG(hw, ICH_FLASH_HSFSTS,
 					      hsflctl.regval << 16);
 		else
@@ -4530,7 +4529,7 @@
 
 	DEBUGFUNC("e1000_write_flash_data32_ich8lan");
 
-	if (hw->mac.type == e1000_pch_spt) {
+	if (hw->mac.type >= e1000_pch_spt) {
 		if (offset > ICH_FLASH_LINEAR_ADDR_MASK)
 			return -E1000_ERR_NVM;
 	}
@@ -4546,7 +4545,7 @@
 		/* In SPT, This register is in Lan memory space, not
 		 * flash.  Therefore, only 32 bit access is supported
 		 */
-		if (hw->mac.type == e1000_pch_spt)
+		if (hw->mac.type >= e1000_pch_spt)
 			hsflctl.regval = E1000_READ_FLASH_REG(hw,
 							      ICH_FLASH_HSFSTS)
 					 >> 16;
@@ -4561,7 +4560,7 @@
 		 * not flash.  Therefore, only 32 bit access is
 		 * supported
 		 */
-		if (hw->mac.type == e1000_pch_spt)
+		if (hw->mac.type >= e1000_pch_spt)
 			E1000_WRITE_FLASH_REG(hw, ICH_FLASH_HSFSTS,
 					      hsflctl.regval << 16);
 		else
@@ -4763,7 +4762,7 @@
 			/* Write a value 11 (block Erase) in Flash
 			 * Cycle field in hw flash control
 			 */
-			if (hw->mac.type == e1000_pch_spt)
+			if (hw->mac.type >= e1000_pch_spt)
 				hsflctl.regval =
 				    E1000_READ_FLASH_REG(hw,
 							 ICH_FLASH_HSFSTS)>>16;
@@ -4773,7 +4772,7 @@
 							   ICH_FLASH_HSFCTL);
 
 			hsflctl.hsf_ctrl.flcycle = ICH_CYCLE_ERASE;
-			if (hw->mac.type == e1000_pch_spt)
+			if (hw->mac.type >= e1000_pch_spt)
 				E1000_WRITE_FLASH_REG(hw, ICH_FLASH_HSFSTS,
 						      hsflctl.regval << 16);
 			else
@@ -5211,8 +5210,7 @@
 	E1000_WRITE_REG(hw, E1000_RFCTL, reg);
 
 	/* Enable ECC on Lynxpoint */
-	if ((hw->mac.type == e1000_pch_lpt) ||
-	    (hw->mac.type == e1000_pch_spt)) {
+	if (hw->mac.type >= e1000_pch_lpt) {
 		reg = E1000_READ_REG(hw, E1000_PBECCSTS);
 		reg |= E1000_PBECCSTS_ECC_ENABLE;
 		E1000_WRITE_REG(hw, E1000_PBECCSTS, reg);
@@ -5645,7 +5643,7 @@
 		    (device_id == E1000_DEV_ID_PCH_LPTLP_I218_V) ||
 		    (device_id == E1000_DEV_ID_PCH_I218_LM3) ||
 		    (device_id == E1000_DEV_ID_PCH_I218_V3) ||
-		    (hw->mac.type == e1000_pch_spt)) {
+		    (hw->mac.type >= e1000_pch_spt)) {
 			u32 fextnvm6 = E1000_READ_REG(hw, E1000_FEXTNVM6);
 
 			E1000_WRITE_REG(hw, E1000_FEXTNVM6,
diff --git a/usr/src/uts/common/io/e1000g/e1000g_main.c b/usr/src/uts/common/io/e1000g/e1000g_main.c
index de4ebc2..a2bdebc 100644
--- a/usr/src/uts/common/io/e1000g/e1000g_main.c
+++ b/usr/src/uts/common/io/e1000g/e1000g_main.c
@@ -25,7 +25,7 @@
 /*
  * Copyright 2012 DEY Storage Systems, Inc.  All rights reserved.
  * Copyright 2013 Nexenta Systems, Inc.  All rights reserved.
- * Copyright (c) 2017, Joyent, Inc.
+ * Copyright (c) 2018, Joyent, Inc.
  */
 
 /*
@@ -711,6 +711,7 @@
 		}
 		break;
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		/*
 		 * On the SPT, the device flash is actually in BAR0, not a
 		 * separate BAR. Therefore we end up setting the
@@ -780,7 +781,7 @@
 regs_map_fail:
 	if (osdep->reg_handle != NULL)
 		ddi_regs_map_free(&osdep->reg_handle);
-	if (osdep->ich_flash_handle != NULL && hw->mac.type != e1000_pch_spt)
+	if (osdep->ich_flash_handle != NULL && hw->mac.type < e1000_pch_spt)
 		ddi_regs_map_free(&osdep->ich_flash_handle);
 	return (DDI_FAILURE);
 }
@@ -909,6 +910,7 @@
 	case e1000_pch2lan:
 	case e1000_pch_lpt:
 	case e1000_pch_spt:
+	case e1000_pch_cnp:
 		Adapter->max_mtu = MAXIMUM_MTU_9K;
 		break;
 	/* types with a special limit */
@@ -1147,7 +1149,7 @@
 		if (Adapter->osdep.reg_handle != NULL)
 			ddi_regs_map_free(&Adapter->osdep.reg_handle);
 		if (Adapter->osdep.ich_flash_handle != NULL &&
-		    Adapter->shared.mac.type != e1000_pch_spt)
+		    Adapter->shared.mac.type < e1000_pch_spt)
 			ddi_regs_map_free(&Adapter->osdep.ich_flash_handle);
 		if (Adapter->osdep.io_reg_handle != NULL)
 			ddi_regs_map_free(&Adapter->osdep.io_reg_handle);
@@ -1486,6 +1488,8 @@
 		pba = E1000_PBA_26K;
 	} else if (hw->mac.type == e1000_pch_spt) {
 		pba = E1000_PBA_26K;
+	} else if (hw->mac.type == e1000_pch_cnp) {
+		pba = E1000_PBA_26K;
 	} else {
 		/*
 		 * Total FIFO is 40K
@@ -1712,10 +1716,10 @@
 	case e1000_media_type_copper:
 		if (hw->mac.get_link_status) {
 			/*
-			 * SPT devices need a bit of extra time before we ask
-			 * them.
+			 * SPT and newer devices need a bit of extra time before
+			 * we ask them.
 			 */
-			if (hw->mac.type == e1000_pch_spt)
+			if (hw->mac.type >= e1000_pch_spt)
 				msec_delay(50);
 			(void) e1000_check_for_link(hw);
 			if ((E1000_READ_REG(hw, E1000_STATUS) &
@@ -2076,7 +2080,7 @@
 	 * rings are flushed before we do anything else. This must be done
 	 * before we release DMA resources.
 	 */
-	if (Adapter->shared.mac.type == e1000_pch_spt)
+	if (Adapter->shared.mac.type >= e1000_pch_spt)
 		e1000g_flush_desc_rings(Adapter);
 
 	if (global) {
@@ -2536,8 +2540,7 @@
 		 * additional registers are available. If the value is 2-7, only
 		 * that number are available.
 		 */
-		if (hw->mac.type == e1000_pch_lpt ||
-		    hw->mac.type == e1000_pch_spt) {
+		if (hw->mac.type >= e1000_pch_lpt) {
 			uint32_t locked, rar;
 
 			locked = E1000_READ_REG(hw, E1000_FWSM) &