Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit da1f607e authored by Mario Limonciello's avatar Mario Limonciello Committed by Darren Hart (VMware)
Browse files

platform/x86: dell-smbios-smm: test for WSMT



WSMT is as an attestation to the OS that the platform won't
modify memory outside of pre-defined areas.

If a platform has WSMT enabled in BIOS setup, SMM calls through
dcdbas will fail.  The only way to access platform data in these
instances is through the WMI SMBIOS calling interface.

Signed-off-by: default avatarMario Limonciello <mario.limonciello@dell.com>
Reviewed-by: default avatarEdward O'Callaghan <quasisec@google.com>
Signed-off-by: default avatarDarren Hart (VMware) <dvhart@infradead.org>
parent 1a258e67
Loading
Loading
Loading
Loading
+33 −0
Original line number Diff line number Diff line
@@ -102,6 +102,32 @@ int dell_smbios_smm_call(struct calling_interface_buffer *input)
	return 0;
}

/* When enabled this indicates that SMM won't work */
static bool test_wsmt_enabled(void)
{
	struct calling_interface_token *wsmt;

	/* if token doesn't exist, SMM will work */
	wsmt = dell_smbios_find_token(WSMT_EN_TOKEN);
	if (!wsmt)
		return false;

	/* If token exists, try to access over SMM but set a dummy return.
	 * - If WSMT disabled it will be overwritten by SMM
	 * - If WSMT enabled then dummy value will remain
	 */
	buffer->cmd_class = CLASS_TOKEN_READ;
	buffer->cmd_select = SELECT_TOKEN_STD;
	memset(buffer, 0, sizeof(struct calling_interface_buffer));
	buffer->input[0] = wsmt->location;
	buffer->output[0] = 99;
	dell_smbios_smm_call(buffer);
	if (buffer->output[0] == 99)
		return true;

	return false;
}

static int __init dell_smbios_smm_init(void)
{
	int ret;
@@ -115,6 +141,12 @@ static int __init dell_smbios_smm_init(void)

	dmi_walk(find_cmd_address, NULL);

	if (test_wsmt_enabled()) {
		pr_debug("Disabling due to WSMT enabled\n");
		ret = -ENODEV;
		goto fail_wsmt;
	}

	platform_device = platform_device_alloc("dell-smbios", 1);
	if (!platform_device) {
		ret = -ENOMEM;
@@ -138,6 +170,7 @@ static int __init dell_smbios_smm_init(void)
fail_platform_device_add:
	platform_device_put(platform_device);

fail_wsmt:
fail_platform_device_alloc:
	free_page((unsigned long)buffer);
	return ret;
+2 −0
Original line number Diff line number Diff line
@@ -44,6 +44,8 @@
#define KBD_LED_AUTO_100_TOKEN	0x02F6
#define GLOBAL_MIC_MUTE_ENABLE	0x0364
#define GLOBAL_MIC_MUTE_DISABLE	0x0365
#define WSMT_EN_TOKEN		0x04EC
#define WSMT_DIS_TOKEN		0x04ED

struct notifier_block;