linux-i2c.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
From: "Uwe Kleine-König" <u.kleine-koenig@pengutronix.de>
To: Tudor Ambarus <tudor.ambarus@microchip.com>
Cc: Alexandre Belloni <alexandre.belloni@bootlin.com>,
	Nicolas Ferre <nicolas.ferre@microchip.com>,
	linux-crypto@vger.kernel.org, kernel@pengutronix.de,
	Claudiu Beznea <claudiu.beznea@microchip.com>,
	linux-arm-kernel@lists.infradead.org, linux-i2c@vger.kernel.org,
	Ard Biesheuvel <ard.biesheuvel@linaro.org>
Subject: Re: Bug in atmel-ecc driver
Date: Tue, 17 May 2022 12:24:32 +0200	[thread overview]
Message-ID: <20220517102432.pljcsjkar3oswdnl@pengutronix.de> (raw)
In-Reply-To: <20220513135954.exewihnibnhdckkn@pengutronix.de>

[-- Attachment #1: Type: text/plain, Size: 2890 bytes --]

Hello,

[added Ard to Cc as he last touched that driver]

On Fri, May 13, 2022 at 03:59:54PM +0200, Uwe Kleine-König wrote:
> TL;DR: when a device bound to the drivers/crypto/atmel-ecc.c driver is
> unbound while tfm_count isn't zero, this probably results in a
> use-after-free.
> 
> The .remove function has:
> 
> 	if (atomic_read(&i2c_priv->tfm_count)) {
>                 dev_err(&client->dev, "Device is busy\n");
>                 return -EBUSY;
>         }
> 
> before actually calling the cleanup stuff. If this branch is hit the
> result is likely:
> 
>  - "Device is busy" from drivers/crypto/atmel-ecc.c
>  - "remove failed (EBUSY), will be ignored" from the i2c core
>  - the devm cleanup callbacks are called, including the one kfreeing
>    *i2c_priv
>  - at a later time atmel_ecc_i2c_client_free() is called which does
>    atomic_dec(&i2c_priv->tfm_count);
>  - *boom*
> 
> I think to fix that you need to call get_device for the i2c device
> before increasing tfm_count (and a matching put_device when decreasing
> it). Having said that the architecture of this driver looks strange to
> me, so there might be nicer fixes (probably with more effort).

I tried to understand the architecture a bit, what I found is
irritating. So the atmel-ecc driver provides a static struct kpp_alg
atmel_ecdh_nist_p256 which embeds a struct crypto_alg (.base). During
.probe() it calls crypto_register_kpp on that global kpp_alg. That is,
if there are two or more devices bound to this driver, the same kpp_alg
structure is registered repeatedly.  This involves (among others)

 - refcount_set(&atmel_ecdh_nist_p256.base.cra_refcount)
   in crypto_check_alg()
 - INIT_LIST_HEAD(&atmel_ecdh_nist_p256.base.cra_users)
   in __crypto_register_alg()

and then a check about registering the same alg twice which makes the
call crypto_register_alg() return -EEXIST. So if a second device is
bound, it probably corrupts the first device and then fails to probe.

So there can always be (at most) only one bound device which somehow
makes the whole logic in atmel_ecdh_init_tfm ->
atmel_ecc_i2c_client_alloc to select the least used(?) i2c client among
all the bound devices ridiculous.

Is there someone still caring for this driver? Does this justify 

diff --git a/drivers/crypto/Kconfig b/drivers/crypto/Kconfig
index 7b2d138bc83e..b3242fba82aa 100644
--- a/drivers/crypto/Kconfig
+++ b/drivers/crypto/Kconfig
@@ -573,6 +573,7 @@ config CRYPTO_DEV_ATMEL_I2C
 
 config CRYPTO_DEV_ATMEL_ECC
 	tristate "Support for Microchip / Atmel ECC hw accelerator"
+	depends on BROKEN
 	depends on I2C
 	select CRYPTO_DEV_ATMEL_I2C
 	select CRYPTO_ECDH

?

Best regards
Uwe

-- 
Pengutronix e.K.                           | Uwe Kleine-König            |
Industrial Linux Solutions                 | https://www.pengutronix.de/ |

[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 488 bytes --]

  reply	other threads:[~2022-05-17 10:27 UTC|newest]

Thread overview: 12+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2022-05-13 13:59 Bug in atmel-ecc driver Uwe Kleine-König
2022-05-17 10:24 ` Uwe Kleine-König [this message]
2022-05-17 13:11   ` Tudor.Ambarus
2022-05-17 14:33     ` Uwe Kleine-König
2022-05-18 10:07       ` Tudor.Ambarus
2022-05-18 21:36         ` Uwe Kleine-König
2022-05-20 17:21         ` [PATCH] crypto: atmel-ecc - Remove duplicated error reporting in .remove() Uwe Kleine-König
2022-06-07  6:48           ` Uwe Kleine-König
2022-06-08  4:33           ` Tudor.Ambarus
2022-06-08  7:04             ` Uwe Kleine-König
2022-06-08  8:35               ` Tudor.Ambarus
2022-06-10  9:14           ` Herbert Xu

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20220517102432.pljcsjkar3oswdnl@pengutronix.de \
    --to=u.kleine-koenig@pengutronix.de \
    --cc=alexandre.belloni@bootlin.com \
    --cc=ard.biesheuvel@linaro.org \
    --cc=claudiu.beznea@microchip.com \
    --cc=kernel@pengutronix.de \
    --cc=linux-arm-kernel@lists.infradead.org \
    --cc=linux-crypto@vger.kernel.org \
    --cc=linux-i2c@vger.kernel.org \
    --cc=nicolas.ferre@microchip.com \
    --cc=tudor.ambarus@microchip.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).