Commit 8043e222 authored by Linus Torvalds's avatar Linus Torvalds

Merge tag 'tpmdd-v6.5-rc6' of git://git.kernel.org/pub/scm/linux/kernel/git/jarkko/linux-tpmdd

Pull tpm fixes from Jarkko Sakkinen:
 "A few more bug fixes"

* tag 'tpmdd-v6.5-rc6' of git://git.kernel.org/pub/scm/linux/kernel/git/jarkko/linux-tpmdd:
  tpm/tpm_tis: Disable interrupts for Lenovo P620 devices
  tpm: Disable RNG for all AMD fTPMs
  sysctl: set variable key_sysctls storage-class-specifier to static
  tpm/tpm_tis: Disable interrupts for TUXEDO InfinityBook S 15/17 Gen7
parents a027b2ec e117e7ad
...@@ -510,70 +510,6 @@ static int tpm_add_legacy_sysfs(struct tpm_chip *chip) ...@@ -510,70 +510,6 @@ static int tpm_add_legacy_sysfs(struct tpm_chip *chip)
return 0; return 0;
} }
/*
* Some AMD fTPM versions may cause stutter
* https://www.amd.com/en/support/kb/faq/pa-410
*
* Fixes are available in two series of fTPM firmware:
* 6.x.y.z series: 6.0.18.6 +
* 3.x.y.z series: 3.57.y.5 +
*/
#ifdef CONFIG_X86
static bool tpm_amd_is_rng_defective(struct tpm_chip *chip)
{
u32 val1, val2;
u64 version;
int ret;
if (!(chip->flags & TPM_CHIP_FLAG_TPM2))
return false;
ret = tpm_request_locality(chip);
if (ret)
return false;
ret = tpm2_get_tpm_pt(chip, TPM2_PT_MANUFACTURER, &val1, NULL);
if (ret)
goto release;
if (val1 != 0x414D4400U /* AMD */) {
ret = -ENODEV;
goto release;
}
ret = tpm2_get_tpm_pt(chip, TPM2_PT_FIRMWARE_VERSION_1, &val1, NULL);
if (ret)
goto release;
ret = tpm2_get_tpm_pt(chip, TPM2_PT_FIRMWARE_VERSION_2, &val2, NULL);
release:
tpm_relinquish_locality(chip);
if (ret)
return false;
version = ((u64)val1 << 32) | val2;
if ((version >> 48) == 6) {
if (version >= 0x0006000000180006ULL)
return false;
} else if ((version >> 48) == 3) {
if (version >= 0x0003005700000005ULL)
return false;
} else {
return false;
}
dev_warn(&chip->dev,
"AMD fTPM version 0x%llx causes system stutter; hwrng disabled\n",
version);
return true;
}
#else
static inline bool tpm_amd_is_rng_defective(struct tpm_chip *chip)
{
return false;
}
#endif /* CONFIG_X86 */
static int tpm_hwrng_read(struct hwrng *rng, void *data, size_t max, bool wait) static int tpm_hwrng_read(struct hwrng *rng, void *data, size_t max, bool wait)
{ {
struct tpm_chip *chip = container_of(rng, struct tpm_chip, hwrng); struct tpm_chip *chip = container_of(rng, struct tpm_chip, hwrng);
...@@ -588,7 +524,7 @@ static int tpm_hwrng_read(struct hwrng *rng, void *data, size_t max, bool wait) ...@@ -588,7 +524,7 @@ static int tpm_hwrng_read(struct hwrng *rng, void *data, size_t max, bool wait)
static int tpm_add_hwrng(struct tpm_chip *chip) static int tpm_add_hwrng(struct tpm_chip *chip)
{ {
if (!IS_ENABLED(CONFIG_HW_RANDOM_TPM) || tpm_is_firmware_upgrade(chip) || if (!IS_ENABLED(CONFIG_HW_RANDOM_TPM) || tpm_is_firmware_upgrade(chip) ||
tpm_amd_is_rng_defective(chip)) chip->flags & TPM_CHIP_FLAG_HWRNG_DISABLED)
return 0; return 0;
snprintf(chip->hwrng_name, sizeof(chip->hwrng_name), snprintf(chip->hwrng_name, sizeof(chip->hwrng_name),
...@@ -719,7 +655,7 @@ void tpm_chip_unregister(struct tpm_chip *chip) ...@@ -719,7 +655,7 @@ void tpm_chip_unregister(struct tpm_chip *chip)
{ {
tpm_del_legacy_sysfs(chip); tpm_del_legacy_sysfs(chip);
if (IS_ENABLED(CONFIG_HW_RANDOM_TPM) && !tpm_is_firmware_upgrade(chip) && if (IS_ENABLED(CONFIG_HW_RANDOM_TPM) && !tpm_is_firmware_upgrade(chip) &&
!tpm_amd_is_rng_defective(chip)) !(chip->flags & TPM_CHIP_FLAG_HWRNG_DISABLED))
hwrng_unregister(&chip->hwrng); hwrng_unregister(&chip->hwrng);
tpm_bios_log_teardown(chip); tpm_bios_log_teardown(chip);
if (chip->flags & TPM_CHIP_FLAG_TPM2 && !tpm_is_firmware_upgrade(chip)) if (chip->flags & TPM_CHIP_FLAG_TPM2 && !tpm_is_firmware_upgrade(chip))
......
...@@ -463,6 +463,28 @@ static bool crb_req_canceled(struct tpm_chip *chip, u8 status) ...@@ -463,6 +463,28 @@ static bool crb_req_canceled(struct tpm_chip *chip, u8 status)
return (cancel & CRB_CANCEL_INVOKE) == CRB_CANCEL_INVOKE; return (cancel & CRB_CANCEL_INVOKE) == CRB_CANCEL_INVOKE;
} }
static int crb_check_flags(struct tpm_chip *chip)
{
u32 val;
int ret;
ret = crb_request_locality(chip, 0);
if (ret)
return ret;
ret = tpm2_get_tpm_pt(chip, TPM2_PT_MANUFACTURER, &val, NULL);
if (ret)
goto release;
if (val == 0x414D4400U /* AMD */)
chip->flags |= TPM_CHIP_FLAG_HWRNG_DISABLED;
release:
crb_relinquish_locality(chip, 0);
return ret;
}
static const struct tpm_class_ops tpm_crb = { static const struct tpm_class_ops tpm_crb = {
.flags = TPM_OPS_AUTO_STARTUP, .flags = TPM_OPS_AUTO_STARTUP,
.status = crb_status, .status = crb_status,
...@@ -800,6 +822,14 @@ static int crb_acpi_add(struct acpi_device *device) ...@@ -800,6 +822,14 @@ static int crb_acpi_add(struct acpi_device *device)
chip->acpi_dev_handle = device->handle; chip->acpi_dev_handle = device->handle;
chip->flags = TPM_CHIP_FLAG_TPM2; chip->flags = TPM_CHIP_FLAG_TPM2;
rc = tpm_chip_bootstrap(chip);
if (rc)
goto out;
rc = crb_check_flags(chip);
if (rc)
goto out;
rc = tpm_chip_register(chip); rc = tpm_chip_register(chip);
out: out:
......
...@@ -162,6 +162,22 @@ static const struct dmi_system_id tpm_tis_dmi_table[] = { ...@@ -162,6 +162,22 @@ static const struct dmi_system_id tpm_tis_dmi_table[] = {
DMI_MATCH(DMI_PRODUCT_VERSION, "ThinkPad L590"), DMI_MATCH(DMI_PRODUCT_VERSION, "ThinkPad L590"),
}, },
}, },
{
.callback = tpm_tis_disable_irq,
.ident = "ThinkStation P620",
.matches = {
DMI_MATCH(DMI_SYS_VENDOR, "LENOVO"),
DMI_MATCH(DMI_PRODUCT_VERSION, "ThinkStation P620"),
},
},
{
.callback = tpm_tis_disable_irq,
.ident = "TUXEDO InfinityBook S 15/17 Gen7",
.matches = {
DMI_MATCH(DMI_SYS_VENDOR, "TUXEDO"),
DMI_MATCH(DMI_PRODUCT_NAME, "TUXEDO InfinityBook S 15/17 Gen7"),
},
},
{ {
.callback = tpm_tis_disable_irq, .callback = tpm_tis_disable_irq,
.ident = "UPX-TGL", .ident = "UPX-TGL",
......
...@@ -283,6 +283,7 @@ enum tpm_chip_flags { ...@@ -283,6 +283,7 @@ enum tpm_chip_flags {
TPM_CHIP_FLAG_FIRMWARE_POWER_MANAGED = BIT(6), TPM_CHIP_FLAG_FIRMWARE_POWER_MANAGED = BIT(6),
TPM_CHIP_FLAG_FIRMWARE_UPGRADE = BIT(7), TPM_CHIP_FLAG_FIRMWARE_UPGRADE = BIT(7),
TPM_CHIP_FLAG_SUSPENDED = BIT(8), TPM_CHIP_FLAG_SUSPENDED = BIT(8),
TPM_CHIP_FLAG_HWRNG_DISABLED = BIT(9),
}; };
#define to_tpm_chip(d) container_of(d, struct tpm_chip, dev) #define to_tpm_chip(d) container_of(d, struct tpm_chip, dev)
......
...@@ -9,7 +9,7 @@ ...@@ -9,7 +9,7 @@
#include <linux/sysctl.h> #include <linux/sysctl.h>
#include "internal.h" #include "internal.h"
struct ctl_table key_sysctls[] = { static struct ctl_table key_sysctls[] = {
{ {
.procname = "maxkeys", .procname = "maxkeys",
.data = &key_quota_maxkeys, .data = &key_quota_maxkeys,
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment