]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
tpm: tpm_tis: store entire did_vid
authorJim Broadus <jbroadus@gmail.com>
Tue, 26 May 2026 23:22:43 +0000 (16:22 -0700)
committerJarkko Sakkinen <jarkko@kernel.org>
Sun, 21 Jun 2026 01:25:28 +0000 (04:25 +0300)
The entire 32 bit did_vid is read from the device, but only the 16 bit
vendor id portion was stored in the tpm_tis_data structure. Storing the
entire value allows the device id to be used to handle quirks. Printing
the vid and did in the error case also helps identify problem devices.

Signed-off-by: Jim Broadus <jbroadus@gmail.com>
Link: https://lore.kernel.org/r/20260526232245.5409-2-jbroadus@gmail.com
Signed-off-by: Jarkko Sakkinen <jarkko@kernel.org>
drivers/char/tpm/tpm_tis_core.c
drivers/char/tpm/tpm_tis_core.h

index 153a57c7924005ee3c5b32f1520f526b2bf5d7b4..3408b531d3b890053c7f43f54268cc1f0ec2881b 100644 (file)
@@ -799,9 +799,10 @@ out:
 static bool tpm_tis_req_canceled(struct tpm_chip *chip, u8 status)
 {
        struct tpm_tis_data *priv = dev_get_drvdata(&chip->dev);
+       u16 vendor_id = priv->did_vid;
 
        if (!test_bit(TPM_TIS_DEFAULT_CANCELLATION, &priv->flags)) {
-               switch (priv->manufacturer_id) {
+               switch (vendor_id) {
                case TPM_VID_WINBOND:
                        return ((status == TPM_STS_VALID) ||
                                (status == (TPM_STS_VALID | TPM_STS_COMMAND_READY)));
@@ -1122,7 +1123,8 @@ int tpm_tis_core_init(struct device *dev, struct tpm_tis_data *priv, int irq,
                      const struct tpm_tis_phy_ops *phy_ops,
                      acpi_handle acpi_dev_handle)
 {
-       u32 vendor;
+       u16 vendor_id;
+       u16 device_id;
        u32 intfcaps;
        u32 intmask;
        u32 clkrun_val;
@@ -1155,19 +1157,20 @@ int tpm_tis_core_init(struct device *dev, struct tpm_tis_data *priv, int irq,
 
        dev_set_drvdata(&chip->dev, priv);
 
-       rc = tpm_tis_read32(priv, TPM_DID_VID(0), &vendor);
+       rc = tpm_tis_read32(priv, TPM_DID_VID(0), &priv->did_vid);
        if (rc < 0)
                return rc;
 
-       priv->manufacturer_id = vendor;
+       vendor_id = priv->did_vid;
+       device_id = priv->did_vid >> 16;
 
-       if (priv->manufacturer_id == TPM_VID_ATML &&
+       if (vendor_id == TPM_VID_ATML &&
                !(chip->flags & TPM_CHIP_FLAG_TPM2)) {
                priv->timeout_min = TIS_TIMEOUT_MIN_ATML;
                priv->timeout_max = TIS_TIMEOUT_MAX_ATML;
        }
 
-       if (priv->manufacturer_id == TPM_VID_IFX)
+       if (vendor_id == TPM_VID_IFX)
                set_bit(TPM_TIS_STATUS_VALID_RETRY, &priv->flags);
 
        if (is_bsw()) {
@@ -1254,9 +1257,9 @@ int tpm_tis_core_init(struct device *dev, struct tpm_tis_data *priv, int irq,
        if (rc < 0)
                goto out_err;
 
-       dev_info(dev, "%s TPM (device-id 0x%X, rev-id %d)\n",
+       dev_info(dev, "%s TPM (vendor-id 0x%X, device-id 0x%X, rev-id %d)\n",
                 (chip->flags & TPM_CHIP_FLAG_TPM2) ? "2.0" : "1.2",
-                vendor >> 16, rid);
+                vendor_id, device_id, rid);
 
        probe = probe_itpm(chip);
        if (probe < 0) {
@@ -1322,6 +1325,9 @@ int tpm_tis_core_init(struct device *dev, struct tpm_tis_data *priv, int irq,
 
        return 0;
 out_err:
+       dev_err(dev, "TPM vid 0x%X, did 0x%X init failed with error %d\n",
+               vendor_id, device_id, rc);
+
        if (chip->ops->clk_enable != NULL)
                chip->ops->clk_enable(chip, false);
 
index 6c3aa480396b64a9bb11f221f0420aa5e0a80689..f2c77844062a83face086301436ab8a6934eafe5 100644 (file)
@@ -94,7 +94,7 @@ enum tpm_tis_flags {
 
 struct tpm_tis_data {
        struct tpm_chip *chip;
-       u16 manufacturer_id;
+       u32 did_vid;
        struct mutex locality_count_mutex;
        unsigned int locality_count;
        int locality;