svn commit: r220866 - head/sys/dev/iwn

Bernhard Schmidt bschmidt at FreeBSD.org
Tue Apr 19 19:47:42 UTC 2011


Author: bschmidt
Date: Tue Apr 19 19:47:41 2011
New Revision: 220866
URL: http://svn.freebsd.org/changeset/base/220866

Log:
  Pull some features out of the firmware:
  - If a ENH_SENS TLV section exit the firmware is capable of doing
    enhanced sensitivity calibration.
  - Newer devices/firmwares have more calibration commands therefore
    hardcoding the noise gain/reset commands no longer works. It is
    supposed to use the next index after the newest calibration type
    support. Read the command index of the TLV section if available.

Modified:
  head/sys/dev/iwn/if_iwn.c
  head/sys/dev/iwn/if_iwnreg.h
  head/sys/dev/iwn/if_iwnvar.h

Modified: head/sys/dev/iwn/if_iwn.c
==============================================================================
--- head/sys/dev/iwn/if_iwn.c	Tue Apr 19 19:26:27 2011	(r220865)
+++ head/sys/dev/iwn/if_iwn.c	Tue Apr 19 19:47:41 2011	(r220866)
@@ -772,6 +772,8 @@ iwn5000_attach(struct iwn_softc *sc, uin
 	sc->fw_data_maxsz = IWN5000_FW_DATA_MAXSZ;
 	sc->fwsz = IWN5000_FWSZ;
 	sc->sched_txfact_addr = IWN5000_SCHED_TXFACT;
+	sc->reset_noise_gain = IWN5000_PHY_CALIB_RESET_NOISE_GAIN;
+	sc->noise_gain = IWN5000_PHY_CALIB_NOISE_GAIN;
 
 	switch (sc->hw_type) {
 	case IWN_HW_REV_TYPE_5100:
@@ -4367,7 +4369,7 @@ iwn5000_init_gains(struct iwn_softc *sc)
 	struct iwn_phy_calib cmd;
 
 	memset(&cmd, 0, sizeof cmd);
-	cmd.code = IWN5000_PHY_CALIB_RESET_NOISE_GAIN;
+	cmd.code = sc->reset_noise_gain;
 	cmd.ngroups = 1;
 	cmd.isvalid = 1;
 	DPRINTF(sc, IWN_DEBUG_CALIBRATE,
@@ -4419,7 +4421,7 @@ iwn5000_set_gains(struct iwn_softc *sc)
 	div = (sc->hw_type == IWN_HW_REV_TYPE_6050) ? 20 : 30;
 
 	memset(&cmd, 0, sizeof cmd);
-	cmd.code = IWN5000_PHY_CALIB_NOISE_GAIN;
+	cmd.code = sc->noise_gain;
 	cmd.ngroups = 1;
 	cmd.isvalid = 1;
 	/* Get first available RX antenna as referential. */
@@ -5900,7 +5902,7 @@ iwn_read_firmware_tlv(struct iwn_softc *
 	const struct iwn_fw_tlv *tlv;
 	const uint8_t *ptr, *end;
 	uint64_t altmask;
-	uint32_t len;
+	uint32_t len, tmp;
 
 	if (fw->size < sizeof (*hdr)) {
 		device_printf(sc->sc_dev, "%s: firmware too short: %zu bytes\n",
@@ -5965,6 +5967,17 @@ iwn_read_firmware_tlv(struct iwn_softc *
 			fw->boot.text = ptr;
 			fw->boot.textsz = len;
 			break;
+		case IWN_FW_TLV_ENH_SENS:
+			if (!len)
+				sc->sc_flags |= IWN_FLAG_ENH_SENS;
+			break;
+		case IWN_FW_TLV_PHY_CALIB:
+			tmp = htole32(*ptr);
+			if (tmp < 253) {
+				sc->reset_noise_gain = tmp;
+				sc->noise_gain = tmp + 1;
+			}
+			break;
 		default:
 			DPRINTF(sc, IWN_DEBUG_RESET,
 			    "TLV type %d not handled\n", le16toh(tlv->type));

Modified: head/sys/dev/iwn/if_iwnreg.h
==============================================================================
--- head/sys/dev/iwn/if_iwnreg.h	Tue Apr 19 19:26:27 2011	(r220865)
+++ head/sys/dev/iwn/if_iwnreg.h	Tue Apr 19 19:47:41 2011	(r220866)
@@ -1322,6 +1322,8 @@ struct iwn_fw_tlv {
 #define IWN_FW_TLV_INIT_DATA		4
 #define IWN_FW_TLV_BOOT_TEXT		5
 #define IWN_FW_TLV_PBREQ_MAXLEN		6
+#define IWN_FW_TLV_ENH_SENS		14
+#define IWN_FW_TLV_PHY_CALIB		15
 
 	uint16_t	alt;
 	uint32_t	len;

Modified: head/sys/dev/iwn/if_iwnvar.h
==============================================================================
--- head/sys/dev/iwn/if_iwnvar.h	Tue Apr 19 19:26:27 2011	(r220865)
+++ head/sys/dev/iwn/if_iwnvar.h	Tue Apr 19 19:47:41 2011	(r220866)
@@ -222,6 +222,8 @@ struct iwn_softc {
 	uint32_t		fw_data_maxsz;
 	uint32_t		fwsz;
 	bus_size_t		sched_txfact_addr;
+	uint32_t		reset_noise_gain;
+	uint32_t		noise_gain;
 
 	/* TX scheduler rings. */
 	struct iwn_dma_info	sched_dma;


More information about the svn-src-head mailing list