From nobody Sat Jul 25 19:26:40 2026 Received: from mail-qk1-f172.google.com (mail-qk1-f172.google.com [209.85.222.172]) (using TLSv1.2 with cipher ECDHE-RSA-AES128-GCM-SHA256 (128/128 bits)) (No client certificate requested) by smtp.subspace.kernel.org (Postfix) with ESMTPS id E955A388397 for ; Tue, 14 Jul 2026 13:14:45 +0000 (UTC) Authentication-Results: smtp.subspace.kernel.org; arc=none smtp.client-ip=209.85.222.172 ARC-Seal: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1784034890; cv=none; b=WgD8TqfBBkEd0RO3BDjXksZ2nj58oePAL6sP50d2JOm+4XxGS0uYgp+63FzHG8Uydvpxi1AH16S23nLSNWli+zFkOEYS/kkbx7MpUbZMKtSYQdPd2+2sN6vnmPefjeLW6aJNMFPGRYslUhWSBTaUCHWb3daAbMCFNUdPKPLooPU= ARC-Message-Signature: i=1; a=rsa-sha256; d=subspace.kernel.org; s=arc-20240116; t=1784034890; c=relaxed/simple; bh=3zLr5wC29AQBJyM1LTNCrLPJ/9RCUeECH8DF5+2Hswk=; h=From:To:Cc:Subject:Date:Message-ID:In-Reply-To:References: MIME-Version; b=mQQvqGl089CcRhGh7FoxSdeukfpoCXlZsIO1QM0+Ez8nKQuIDzYbD4o5CMb8MtOLZvFi6+Ytcf9kUDxC4qN7J3gN7phF/aJ3vk9xv+WZDP7lIaMuFcxZ8kHfyll7wAguM0S6SfiUrdqSESJH6Zf0TdCe/6ltVvUFkAb7grEdKsU= ARC-Authentication-Results: i=1; smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com; spf=pass smtp.mailfrom=gmail.com; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b=lRM32T4T; arc=none smtp.client-ip=209.85.222.172 Authentication-Results: smtp.subspace.kernel.org; dmarc=pass (p=none dis=none) header.from=gmail.com Authentication-Results: smtp.subspace.kernel.org; spf=pass smtp.mailfrom=gmail.com Authentication-Results: smtp.subspace.kernel.org; dkim=pass (2048-bit key) header.d=gmail.com header.i=@gmail.com header.b="lRM32T4T" Received: by mail-qk1-f172.google.com with SMTP id af79cd13be357-92e7632b193so99738085a.2 for ; Tue, 14 Jul 2026 06:14:44 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20251104; t=1784034880; x=1784639680; darn=vger.kernel.org; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:from:to:cc:subject:date :message-id:reply-to:content-type; bh=4sdtcAcnvXtBkdPDuwsN8gXcGpdW7yo4L5WrP92J294=; b=lRM32T4TIZ9SJbJZ8fGaIOmzmdUIdYej/wmBsy4YD6lN05WO3NB//hHIFeP5lRJnRv JhHnkSacDyNId3dmdXRDdz5tigLSMVYTDGkIyA30FHOi1GwrVdF+hWRQSL7iHk7E4/qf K/OWz4OcLTSbTzpEvglvr0SEUPBYcce3RtD6pXmHfBz+fkO+oyWz5SwgWOIu3n0PZZG4 VqWJ6cca4q6b9I1ia+u9IIHtj5GskaPfdsH0CAKjl+dXmbr33NQY12q4CYo1sjwpsptm vCfSAnC7BQPrOGG0qKotYk3gea79Om/wD2gJ83ffjNRe6EjssrtjUtUUqHAq8nBFT1Lf QMcw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20251104; t=1784034880; x=1784639680; h=content-transfer-encoding:mime-version:references:in-reply-to :message-id:date:subject:cc:to:from:x-gm-gg:x-gm-message-state:from :to:cc:subject:date:message-id:reply-to:content-type; bh=4sdtcAcnvXtBkdPDuwsN8gXcGpdW7yo4L5WrP92J294=; b=SeL8uegbxs1qaWnTGjs2Rv/TpPpnsjES+4tiw//ogpYVfujWuSkbGdd8yoXQccK3a9 x+Wf1yflxS4K8JRlsJJFh5IByH18avHfAjGWwzztuHHa0YWJEkEQCFl+aBXPV5EzCmiY jqHl50B8HeVNGMAUd02ntZPhXKyZ9fWEc6d7TZCKkB2lARar7Wyq2Nefj1osaHdmjwGs MkjsAjeLERaCkDY1roleTxsNWWhZTi25F/HWp0tTTMw49QOobzVCruR6ArJs/gqrkY11 fqNgFBKIF8sh8do9B+PLb9lAIsfbWa2Ns+IKw24rO62/2ZgnRYCLumPrqhfD5FGNlmkT FBQw== X-Forwarded-Encrypted: i=1; AHgh+Rq7Q/jsiCNQlkbWWzOMOeLTOSD8rfREk/wHhFOLXuhWc6iIjmzm4dk6B876NAyIj3zyt/qm+GxW0tnAHow=@vger.kernel.org X-Gm-Message-State: AOJu0YxMmaE0xK0XOOPfOiHGxMHIyGySN8TzO1dJ7MhsotODEb2hJwxA W7JYsb3A1PEturK31Rfyb4ekmAUnf/37xtgTzDEemJ8foCxfHqAOntrO X-Gm-Gg: AfdE7cn2O3WBFD81qC6M7Ajs1JU05ZG0wB//hH91BFirAAO6AIUdm4rcO9jo3SWAdQH 9cMZFXRK++BT3W3i+A1Sxhd5xQbhwvtzmkk7ZjpQ9KhulXXYKrqTFAtaPW0+px7QR4uG+vGmSr6 qfAyJpUBKOaW2AOYuXAr9jnFMISaXsSmFqGk5EsRcyYiKLXOqwZkx2H0pZC4go4cbW7hpqKkloN B8E7srWQkLaGSLkTCQFQ2/6GQyeWQSvBFKyg6bXIvLI2wwua2BuqzSZK8PB4f2upcxTtHjCS64R 8SoWnnBmIJZZS6qUNjBUJn2y6tv7qQo6K97dMyRY2SDbLtIfWYitxmNJ/Kb26NREhoBr1197lu1 ncDkjah4LoeRDYe+BIPkC2PleGVtNqF2O+DOb4zdVaId4bzukctgT5BkbmmL3XEFhpkuOqWY4Fs M19aYTSknj4KsPGag9b9r3fRd0c5I163nzft/3X5cx8/wJXTRyyvPLWg== X-Received: by 2002:a05:620a:8398:b0:92b:4474:76b with SMTP id af79cd13be357-92ef2c1fa8bmr1220305185a.45.1784034877981; Tue, 14 Jul 2026 06:14:37 -0700 (PDT) Received: from localhost.localdomain ([49.207.223.101]) by smtp.gmail.com with ESMTPSA id af79cd13be357-92ee5bcb074sm1464651785a.21.2026.07.14.06.14.33 (version=TLS1_3 cipher=TLS_CHACHA20_POLY1305_SHA256 bits=256/256); Tue, 14 Jul 2026 06:14:37 -0700 (PDT) From: Biren Pandya To: linusw@kernel.org, jic23@kernel.org, dlechner@baylibre.com, nuno.sa@analog.com, andy@kernel.org, linux-iio@vger.kernel.org, linux-kernel@vger.kernel.org Cc: Biren Pandya Subject: [PATCH v3] iio: gyro: mpu3050: Fix runtime PM leak and refactor trigger state Date: Tue, 14 Jul 2026 18:44:27 +0530 Message-ID: <20260714131426.4257-2-birenpandya@gmail.com> X-Mailer: git-send-email 2.50.1 In-Reply-To: <20260615214504.38979-1-birenpandya@gmail.com> References: <20260615214504.38979-1-birenpandya@gmail.com> Precedence: bulk X-Mailing-List: linux-kernel@vger.kernel.org List-Id: List-Subscribe: List-Unsubscribe: MIME-Version: 1.0 Content-Transfer-Encoding: quoted-printable Content-Type: text/plain; charset="utf-8" mpu3050_drdy_trigger_set_state() calls pm_runtime_get_sync() when the trigger is enabled, but several error paths in the enable branch return directly without dropping the usage counter again. pm_runtime_get_sync() increments the usage counter, so every failed enable leaks a runtime PM reference and the device can no longer autosuspend. The driver state flag hw_irq_trigger is also left set after a failed enable. To fix the error unwind clearly and avoid an asymmetric goto block inside a monolithic function, this patch breaks the trigger state handler into two distinct helpers: mpu3050_drdy_trigger_enable() and mpu3050_drdy_trigger_disable(). The enable helper correctly implements the error unwind path to drop the PM reference and clear the flag. Additionally, pm_runtime_get_sync() is replaced with pm_runtime_resume_and_get() for robust error checking. Fixes: 3904b28efb2c ("iio: gyro: Add driver for the MPU-3050 gyroscope") Signed-off-by: Biren Pandya --- Changes in v3: - Fixed kernel-doc warning for mpu3050_drdy_trigger_set_state(). - Fixed the Fixes tag title to exactly match the target commit. - Link to v2: https://lore.kernel.org/all/20260615214504.38979-1-birenpandy= a@gmail.com/ drivers/iio/gyro/mpu3050-core.c | 166 ++++++++++++++++++-------------- 1 file changed, 92 insertions(+), 74 deletions(-) diff --git a/drivers/iio/gyro/mpu3050-core.c b/drivers/iio/gyro/mpu3050-cor= e.c index d84e04e4b4314..9de126c3b4350 100644 --- a/drivers/iio/gyro/mpu3050-core.c +++ b/drivers/iio/gyro/mpu3050-core.c @@ -945,102 +945,120 @@ static irqreturn_t mpu3050_irq_thread(int irq, void= *p) return IRQ_HANDLED; } =20 -/** - * mpu3050_drdy_trigger_set_state() - set data ready interrupt state - * @trig: trigger instance - * @enable: true if trigger should be enabled, false to disable - */ -static int mpu3050_drdy_trigger_set_state(struct iio_trigger *trig, - bool enable) +static int mpu3050_drdy_trigger_disable(struct iio_trigger *trig) { struct iio_dev *indio_dev =3D iio_trigger_get_drvdata(trig); struct mpu3050 *mpu3050 =3D iio_priv(indio_dev); unsigned int val; int ret; =20 - /* Disabling trigger: disable interrupt and return */ - if (!enable) { - /* Disable all interrupts */ - ret =3D regmap_write(mpu3050->map, - MPU3050_INT_CFG, - 0); - if (ret) - dev_err(mpu3050->dev, "error disabling IRQ\n"); + /* Disable all interrupts */ + ret =3D regmap_write(mpu3050->map, MPU3050_INT_CFG, 0); + if (ret) + dev_err(mpu3050->dev, "error disabling IRQ\n"); =20 - /* Clear IRQ flag */ - ret =3D regmap_read(mpu3050->map, MPU3050_INT_STATUS, &val); - if (ret) - dev_err(mpu3050->dev, "error clearing IRQ status\n"); + /* Clear IRQ flag */ + ret =3D regmap_read(mpu3050->map, MPU3050_INT_STATUS, &val); + if (ret) + dev_err(mpu3050->dev, "error clearing IRQ status\n"); =20 - /* Disable all things in the FIFO and reset it */ - ret =3D regmap_write(mpu3050->map, MPU3050_FIFO_EN, 0); - if (ret) - dev_err(mpu3050->dev, "error disabling FIFO\n"); + /* Disable all things in the FIFO and reset it */ + ret =3D regmap_write(mpu3050->map, MPU3050_FIFO_EN, 0); + if (ret) + dev_err(mpu3050->dev, "error disabling FIFO\n"); =20 - ret =3D regmap_write(mpu3050->map, MPU3050_USR_CTRL, - MPU3050_USR_CTRL_FIFO_RST); - if (ret) - dev_err(mpu3050->dev, "error resetting FIFO\n"); + ret =3D regmap_write(mpu3050->map, MPU3050_USR_CTRL, + MPU3050_USR_CTRL_FIFO_RST); + if (ret) + dev_err(mpu3050->dev, "error resetting FIFO\n"); =20 - pm_runtime_put_autosuspend(mpu3050->dev); - mpu3050->hw_irq_trigger =3D false; + pm_runtime_put_autosuspend(mpu3050->dev); + mpu3050->hw_irq_trigger =3D false; =20 - return 0; - } else { - /* Else we're enabling the trigger from this point */ - pm_runtime_get_sync(mpu3050->dev); - mpu3050->hw_irq_trigger =3D true; + return 0; +} =20 - /* Disable all things in the FIFO */ - ret =3D regmap_write(mpu3050->map, MPU3050_FIFO_EN, 0); - if (ret) - return ret; +static int mpu3050_drdy_trigger_enable(struct iio_trigger *trig) +{ + struct iio_dev *indio_dev =3D iio_trigger_get_drvdata(trig); + struct mpu3050 *mpu3050 =3D iio_priv(indio_dev); + unsigned int val; + int ret; =20 - /* Reset and enable the FIFO */ - ret =3D regmap_set_bits(mpu3050->map, MPU3050_USR_CTRL, - MPU3050_USR_CTRL_FIFO_EN | - MPU3050_USR_CTRL_FIFO_RST); - if (ret) - return ret; + ret =3D pm_runtime_resume_and_get(mpu3050->dev); + if (ret) + return ret; =20 - mpu3050->pending_fifo_footer =3D false; + mpu3050->hw_irq_trigger =3D true; =20 - /* Turn on the FIFO for temp+X+Y+Z */ - ret =3D regmap_write(mpu3050->map, MPU3050_FIFO_EN, - MPU3050_FIFO_EN_TEMP_OUT | - MPU3050_FIFO_EN_GYRO_XOUT | - MPU3050_FIFO_EN_GYRO_YOUT | - MPU3050_FIFO_EN_GYRO_ZOUT | - MPU3050_FIFO_EN_FOOTER); - if (ret) - return ret; + /* Disable all things in the FIFO */ + ret =3D regmap_write(mpu3050->map, MPU3050_FIFO_EN, 0); + if (ret) + goto err_put_autosuspend; =20 - /* Configure the sample engine */ - ret =3D mpu3050_start_sampling(mpu3050); - if (ret) - return ret; + /* Reset and enable the FIFO */ + ret =3D regmap_set_bits(mpu3050->map, MPU3050_USR_CTRL, + MPU3050_USR_CTRL_FIFO_EN | + MPU3050_USR_CTRL_FIFO_RST); + if (ret) + goto err_put_autosuspend; =20 - /* Clear IRQ flag */ - ret =3D regmap_read(mpu3050->map, MPU3050_INT_STATUS, &val); - if (ret) - dev_err(mpu3050->dev, "error clearing IRQ status\n"); + mpu3050->pending_fifo_footer =3D false; =20 - /* Give us interrupts whenever there is new data ready */ - val =3D MPU3050_INT_RAW_RDY_EN; + /* Turn on the FIFO for temp+X+Y+Z */ + ret =3D regmap_write(mpu3050->map, MPU3050_FIFO_EN, + MPU3050_FIFO_EN_TEMP_OUT | + MPU3050_FIFO_EN_GYRO_XOUT | + MPU3050_FIFO_EN_GYRO_YOUT | + MPU3050_FIFO_EN_GYRO_ZOUT | + MPU3050_FIFO_EN_FOOTER); + if (ret) + goto err_put_autosuspend; =20 - if (mpu3050->irq_actl) - val |=3D MPU3050_INT_ACTL; - if (mpu3050->irq_latch) - val |=3D MPU3050_INT_LATCH_EN; - if (mpu3050->irq_opendrain) - val |=3D MPU3050_INT_OPEN; + /* Configure the sample engine */ + ret =3D mpu3050_start_sampling(mpu3050); + if (ret) + goto err_put_autosuspend; =20 - ret =3D regmap_write(mpu3050->map, MPU3050_INT_CFG, val); - if (ret) - return ret; - } + /* Clear IRQ flag */ + ret =3D regmap_read(mpu3050->map, MPU3050_INT_STATUS, &val); + if (ret) + dev_err(mpu3050->dev, "error clearing IRQ status\n"); + + /* Give us interrupts whenever there is new data ready */ + val =3D MPU3050_INT_RAW_RDY_EN; + + if (mpu3050->irq_actl) + val |=3D MPU3050_INT_ACTL; + if (mpu3050->irq_latch) + val |=3D MPU3050_INT_LATCH_EN; + if (mpu3050->irq_opendrain) + val |=3D MPU3050_INT_OPEN; + + ret =3D regmap_write(mpu3050->map, MPU3050_INT_CFG, val); + if (ret) + goto err_put_autosuspend; =20 return 0; + +err_put_autosuspend: + pm_runtime_put_autosuspend(mpu3050->dev); + mpu3050->hw_irq_trigger =3D false; + return ret; +} + +/** + * mpu3050_drdy_trigger_set_state() - set data ready interrupt state + * @trig: trigger instance + * @enable: true if trigger should be enabled, false to disable + */ +static int mpu3050_drdy_trigger_set_state(struct iio_trigger *trig, + bool enable) +{ + if (enable) + return mpu3050_drdy_trigger_enable(trig); + else + return mpu3050_drdy_trigger_disable(trig); } =20 static const struct iio_trigger_ops mpu3050_trigger_ops =3D { --=20 2.50.1 (Apple Git-155)