Unverified Commit 37473397 authored by Douglas Anderson's avatar Douglas Anderson Committed by Mark Brown
Browse files

regulator: core: Make regulator_lock_two() logic easier to follow



The regulator_lock_two() function could be made clearer in the case of
lock contention by having a local variable for each of the held and
contended locks. Let's do that. At the same time, let's use the swap()
function instead of open coding it.

This change is expected to be a no-op and simply improves code
clarity.

Suggested-by: default avatarStephen Boyd <swboyd@chromium.org>
Link: https://lore.kernel.org/r/CAE-0n53Eb1BeDPmjBycXUaQAF4ppiAM6UDWje_jiB9GAmR8MMw@mail.gmail.com


Signed-off-by: default avatarDouglas Anderson <dianders@chromium.org>
Link: https://lore.kernel.org/r/20230413173359.1.I1ae92b25689bd6579952e6d458b79f5f8054a0c9@changeid


Signed-off-by: default avatarMark Brown <broonie@kernel.org>
parent 902f8c98
Loading
Loading
Loading
Loading
+12 −19
Original line number Diff line number Diff line
@@ -219,7 +219,7 @@ static void regulator_lock_two(struct regulator_dev *rdev1,
			       struct regulator_dev *rdev2,
			       struct ww_acquire_ctx *ww_ctx)
{
	struct regulator_dev *tmp;
	struct regulator_dev *held, *contended;
	int ret;

	ww_acquire_init(ww_ctx, &regulator_ww_class);
@@ -233,25 +233,18 @@ static void regulator_lock_two(struct regulator_dev *rdev1,
		goto exit;
	}

	held = rdev1;
	contended = rdev2;
	while (true) {
		/*
		 * Start of loop: rdev1 was locked and rdev2 was contended.
		 * Need to unlock rdev1, slowly lock rdev2, then try rdev1
		 * again.
		 */
		regulator_unlock(rdev1);
		regulator_unlock(held);

		ww_mutex_lock_slow(&rdev2->mutex, ww_ctx);
		rdev2->ref_cnt++;
		rdev2->mutex_owner = current;
		ret = regulator_lock_nested(rdev1, ww_ctx);
		ww_mutex_lock_slow(&contended->mutex, ww_ctx);
		contended->ref_cnt++;
		contended->mutex_owner = current;
		swap(held, contended);
		ret = regulator_lock_nested(contended, ww_ctx);

		if (ret == -EDEADLOCK) {
			/* More contention; swap which needs to be slow */
			tmp = rdev1;
			rdev1 = rdev2;
			rdev2 = tmp;
		} else {
		if (ret != -EDEADLOCK) {
			WARN_ON(ret);
			break;
		}