Commit 5963e078 authored by Greg Kroah-Hartman's avatar Greg Kroah-Hartman
Browse files

Merge tag 'thunderbolt-for-v6.12-rc5' of...

Merge tag 'thunderbolt-for-v6.12-rc5' of ssh://gitolite.kernel.org/pub/scm/linux/kernel/git/westeri/thunderbolt into usb-linus

Mika writes:

thunderbolt: Fixes for v6.12-rc5

This includes following USB4/Thunderbolt fixes for v6.12-rc5:

  - Fix KASAN reported stack out-of-bounds read
  - Honor Time Management Unit (TMU) requirements in the domain when
    configuring TMU mode of a newly plugged router.

Both have been in linux-next with no reported issues.

* tag 'thunderbolt-for-v6.12-rc5' of ssh://gitolite.kernel.org/pub/scm/linux/kernel/git/westeri/thunderbolt:
  thunderbolt: Honor TMU requirements in the domain when setting TMU mode
  thunderbolt: Fix KASAN reported stack out-of-bounds read in tb_retimer_scan()
parents 42f7652d 3cea8af2
Loading
Loading
Loading
Loading
+3 −2
Original line number Diff line number Diff line
@@ -516,7 +516,7 @@ int tb_retimer_scan(struct tb_port *port, bool add)
	 */
	tb_retimer_set_inbound_sbtx(port);

	for (i = 1; i <= TB_MAX_RETIMER_INDEX; i++) {
	for (max = 1, i = 1; i <= TB_MAX_RETIMER_INDEX; i++) {
		/*
		 * Last retimer is true only for the last on-board
		 * retimer (the one connected directly to the Type-C
@@ -527,9 +527,10 @@ int tb_retimer_scan(struct tb_port *port, bool add)
			last_idx = i;
		else if (ret < 0)
			break;
	}

		max = i;
	}

	ret = 0;

	/* Add retimers if they do not exist already */
+42 −6
Original line number Diff line number Diff line
@@ -288,6 +288,24 @@ static void tb_increase_tmu_accuracy(struct tb_tunnel *tunnel)
	device_for_each_child(&sw->dev, NULL, tb_increase_switch_tmu_accuracy);
}

static int tb_switch_tmu_hifi_uni_required(struct device *dev, void *not_used)
{
	struct tb_switch *sw = tb_to_switch(dev);

	if (sw && tb_switch_tmu_is_enabled(sw) &&
	    tb_switch_tmu_is_configured(sw, TB_SWITCH_TMU_MODE_HIFI_UNI))
		return 1;

	return device_for_each_child(dev, NULL,
				     tb_switch_tmu_hifi_uni_required);
}

static bool tb_tmu_hifi_uni_required(struct tb *tb)
{
	return device_for_each_child(&tb->dev, NULL,
				     tb_switch_tmu_hifi_uni_required) == 1;
}

static int tb_enable_tmu(struct tb_switch *sw)
{
	int ret;
@@ -302,12 +320,30 @@ static int tb_enable_tmu(struct tb_switch *sw)
	ret = tb_switch_tmu_configure(sw,
			TB_SWITCH_TMU_MODE_MEDRES_ENHANCED_UNI);
	if (ret == -EOPNOTSUPP) {
		if (tb_switch_clx_is_enabled(sw, TB_CL1))
		if (tb_switch_clx_is_enabled(sw, TB_CL1)) {
			/*
			 * Figure out uni-directional HiFi TMU requirements
			 * currently in the domain. If there are no
			 * uni-directional HiFi requirements we can put the TMU
			 * into LowRes mode.
			 *
			 * Deliberately skip bi-directional HiFi links
			 * as these work independently of other links
			 * (and they do not allow any CL states anyway).
			 */
			if (tb_tmu_hifi_uni_required(sw->tb))
				ret = tb_switch_tmu_configure(sw,
					TB_SWITCH_TMU_MODE_LOWRES);
						TB_SWITCH_TMU_MODE_HIFI_UNI);
			else
				ret = tb_switch_tmu_configure(sw,
					TB_SWITCH_TMU_MODE_HIFI_BI);
						TB_SWITCH_TMU_MODE_LOWRES);
		} else {
			ret = tb_switch_tmu_configure(sw, TB_SWITCH_TMU_MODE_HIFI_BI);
		}

		/* If not supported, fallback to bi-directional HiFi */
		if (ret == -EOPNOTSUPP)
			ret = tb_switch_tmu_configure(sw, TB_SWITCH_TMU_MODE_HIFI_BI);
	}
	if (ret)
		return ret;