static void
e1000_diag_test(struct net_device *netdev,
		   struct ethtool_test *eth_test, uint64_t *data)
{
	struct e1000_adapter *adapter = netdev->priv;
	boolean_t if_running = netif_running(netdev);

	if(eth_test->flags == ETH_TEST_FL_OFFLINE) {
		/* Offline tests */

		/* save speed, duplex, autoneg settings */
		uint16_t autoneg_advertised = adapter->hw.autoneg_advertised;
		uint8_t forced_speed_duplex = adapter->hw.forced_speed_duplex;
		uint8_t autoneg = adapter->hw.autoneg;

		/* Link test performed before hardware reset so autoneg doesn't
		 * interfere with test result */
		if(e1000_link_test(adapter, &data[4]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		if(if_running)
			e1000_down(adapter);
		else
			e1000_reset(adapter);

		if(e1000_reg_test(adapter, &data[0]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		e1000_reset(adapter);
		if(e1000_eeprom_test(adapter, &data[1]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		e1000_reset(adapter);
		if(e1000_intr_test(adapter, &data[2]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		e1000_reset(adapter);
		if(e1000_loopback_test(adapter, &data[3]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		/* restore speed, duplex, autoneg settings */
		adapter->hw.autoneg_advertised = autoneg_advertised;
		adapter->hw.forced_speed_duplex = forced_speed_duplex;
		adapter->hw.autoneg = autoneg;

		e1000_reset(adapter);
		if(if_running)
			e1000_up(adapter);
	} else {
		/* Online tests */
		if(e1000_link_test(adapter, &data[4]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		/* Offline tests aren't run; pass by default */
		data[0] = 0;
		data[1] = 0;
		data[2] = 0;
		data[3] = 0;
	}
}
static int
e1000_ethtool_test(struct e1000_adapter *adapter,
		   struct ethtool_test *eth_test, uint64_t *data)
{
	boolean_t if_running = netif_running(adapter->netdev);

	if(eth_test->flags == ETH_TEST_FL_OFFLINE) {
		/* Offline tests */

		/* Link test performed before hardware reset so autoneg doesn't
		 * interfere with test result */
		if(e1000_link_test(adapter, &data[4]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		if(if_running)
			e1000_down(adapter);
		else
			e1000_reset(adapter);

		if(e1000_reg_test(adapter, &data[0]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		e1000_reset(adapter);
		if(e1000_eeprom_test(adapter, &data[1]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		e1000_reset(adapter);
		if(e1000_intr_test(adapter, &data[2]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		e1000_reset(adapter);
		if(e1000_loopback_test(adapter, &data[3]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		e1000_reset(adapter);
		if(if_running)
			e1000_up(adapter);
	} else {
		/* Online tests */
		if(e1000_link_test(adapter, &data[4]))
			eth_test->flags |= ETH_TEST_FL_FAILED;

		/* Offline tests aren't run; pass by default */
		data[0] = 0;
		data[1] = 0;
		data[2] = 0;
		data[3] = 0;
	}
	return 0;
}