Unverified Commit cb27ca36 authored by openeuler-ci-bot's avatar openeuler-ci-bot Committed by Gitee
Browse files

!7368 bugfix from mainline

Merge Pull Request from: @ci-robot 
 
PR sync from: Yang Yingliang <yangyingliang@huawei.com>
https://mailweb.openeuler.org/hyperkitty/list/kernel@openeuler.org/message/O633VS72US4NDEDV7V3VRCV5X5LYR3Q2/ 
Josh Poimboeuf (3):
  x86/srso: Set CPUID feature bits independently of bug or mitigation
    status
  x86/srso: Don't probe microcode in a guest
  x86/srso: Fix vulnerability reporting for missing microcode


-- 
2.25.1
 
https://gitee.com/openeuler/kernel/issues/I9NZ3E 
 
Link:https://gitee.com/openeuler/kernel/pulls/7368

 

Reviewed-by: default avatarXie XiuQi <xiexiuqi@huawei.com>
Signed-off-by: default avatarJialin Zhang <zhangjialin11@huawei.com>
parents 2e196c2f ae070226
Loading
Loading
Loading
Loading
+13 −6
Original line number Diff line number Diff line
@@ -44,12 +44,19 @@ The possible values in this file are:

 - 'Not affected'               The processor is not vulnerable

 - 'Vulnerable'                 The processor is vulnerable and no mitigations have been applied.
 - 'Vulnerable: no microcode'   The processor is vulnerable, no
                                microcode extending IBPB functionality
                                to address the vulnerability has been
                                applied.

 - 'Mitigation: microcode'      Extended IBPB functionality microcode
 - 'Vulnerable: Safe RET, no microcode'
                                The "Safe RET" mitigation (see below) has
                                been applied to protect the kernel, but the
                                IBPB-extending microcode has not been applied.
                                User space tasks may still be vulnerable.

 - 'Vulnerable: Microcode, no safe RET'
                                Extended IBPB functionality microcode
                                patch has been applied. It does not
                                address User->Kernel and Guest->Host
                                transitions protection but it does
@@ -58,9 +65,9 @@ The possible values in this file are:

                                (spec_rstack_overflow=microcode)

 - 'Mitigation: safe RET'       Software-only mitigation. It complements
                                the extended IBPB microcode patch
                                functionality by addressing User->Kernel
 - 'Mitigation: Safe RET'       Combined microcode/software mitigation.
                                It complements the extended IBPB microcode
                                patch functionality by addressing User->Kernel
                                and Guest->Host transitions protection.

                                Selected by default or by
@@ -112,7 +119,7 @@ an indrect branch prediction barrier after having applied the required
microcode patch for one's system. This mitigation comes also at
a performance cost.

Mitigation: safe RET
Mitigation: Safe RET
--------------------

The mitigation works by ensuring all RET instructions speculate to
+0 −2
Original line number Diff line number Diff line
@@ -839,12 +839,10 @@ extern u16 get_llc_id(unsigned int cpu);
extern u16 amd_get_nb_id(int cpu);
extern u32 amd_get_nodes_per_socket(void);
extern void amd_clear_divider(void);
extern bool cpu_has_ibpb_brtype_microcode(void);
#else
static inline u16 amd_get_nb_id(int cpu)		{ return 0; }
static inline u32 amd_get_nodes_per_socket(void)	{ return 0; }
static inline void amd_clear_divider(void)		{ }
static inline bool cpu_has_ibpb_brtype_microcode(void)	{ return false; }
#endif

static inline uint32_t hypervisor_cpuid_base(const char *sig, uint32_t leaves)
+9 −19
Original line number Diff line number Diff line
@@ -783,6 +783,15 @@ static void early_init_amd(struct cpuinfo_x86 *c)

	if (cpu_has(c, X86_FEATURE_TOPOEXT))
		smp_num_siblings = ((cpuid_ebx(0x8000001e) >> 8) & 0xff) + 1;

	if (!cpu_has(c, X86_FEATURE_HYPERVISOR) && !cpu_has(c, X86_FEATURE_IBPB_BRTYPE)) {
		if (c->x86 == 0x17 && boot_cpu_has(X86_FEATURE_AMD_IBPB))
			setup_force_cpu_cap(X86_FEATURE_IBPB_BRTYPE);
		else if (c->x86 >= 0x19 && !wrmsrl_safe(MSR_IA32_PRED_CMD, PRED_CMD_SBPB)) {
			setup_force_cpu_cap(X86_FEATURE_IBPB_BRTYPE);
			setup_force_cpu_cap(X86_FEATURE_SBPB);
		}
	}
}

static void init_amd_k8(struct cpuinfo_x86 *c)
@@ -1326,25 +1335,6 @@ void set_dr_addr_mask(unsigned long mask, int dr)
	}
}

bool cpu_has_ibpb_brtype_microcode(void)
{
	switch (boot_cpu_data.x86) {
	/* Zen1/2 IBPB flushes branch type predictions too. */
	case 0x17:
		return boot_cpu_has(X86_FEATURE_AMD_IBPB);
	case 0x19:
		/* Poke the MSR bit on Zen3/4 to check its presence. */
		if (!wrmsrl_safe(MSR_IA32_PRED_CMD, PRED_CMD_SBPB)) {
			setup_force_cpu_cap(X86_FEATURE_SBPB);
			return true;
		} else {
			return false;
		}
	default:
		return false;
	}
}

static void zenbleed_check_cpu(void *unused)
{
	struct cpuinfo_x86 *c = &cpu_data(smp_processor_id());
+23 −26
Original line number Diff line number Diff line
@@ -2251,6 +2251,8 @@ early_param("l1tf", l1tf_cmdline);

enum srso_mitigation {
	SRSO_MITIGATION_NONE,
	SRSO_MITIGATION_UCODE_NEEDED,
	SRSO_MITIGATION_SAFE_RET_UCODE_NEEDED,
	SRSO_MITIGATION_MICROCODE,
	SRSO_MITIGATION_SAFE_RET,
	SRSO_MITIGATION_IBPB,
@@ -2267,8 +2269,10 @@ enum srso_mitigation_cmd {

static const char * const srso_strings[] = {
	[SRSO_MITIGATION_NONE]			= "Vulnerable",
	[SRSO_MITIGATION_MICROCODE]      = "Mitigation: microcode",
	[SRSO_MITIGATION_SAFE_RET]	 = "Mitigation: safe RET",
	[SRSO_MITIGATION_UCODE_NEEDED]		= "Vulnerable: No microcode",
	[SRSO_MITIGATION_SAFE_RET_UCODE_NEEDED]	= "Vulnerable: Safe RET, no microcode",
	[SRSO_MITIGATION_MICROCODE]		= "Vulnerable: Microcode, no safe RET",
	[SRSO_MITIGATION_SAFE_RET]		= "Mitigation: Safe RET",
	[SRSO_MITIGATION_IBPB]			= "Mitigation: IBPB",
	[SRSO_MITIGATION_IBPB_ON_VMEXIT]	= "Mitigation: IBPB on VMEXIT only"
};
@@ -2302,26 +2306,12 @@ early_param("spec_rstack_overflow", srso_parse_cmdline);

static void __init srso_select_mitigation(void)
{
	bool has_microcode;
	bool has_microcode = boot_cpu_has(X86_FEATURE_IBPB_BRTYPE);

	if (!boot_cpu_has_bug(X86_BUG_SRSO) || cpu_mitigations_off())
		goto pred_cmd;

	/*
	 * The first check is for the kernel running as a guest in order
	 * for guests to verify whether IBPB is a viable mitigation.
	 */
	has_microcode = boot_cpu_has(X86_FEATURE_IBPB_BRTYPE) || cpu_has_ibpb_brtype_microcode();
	if (!has_microcode) {
		pr_warn("IBPB-extending microcode not applied!\n");
		pr_warn(SRSO_NOTICE);
	} else {
		/*
		 * Enable the synthetic (even if in a real CPUID leaf)
		 * flags for guests.
		 */
		setup_force_cpu_cap(X86_FEATURE_IBPB_BRTYPE);

	if (has_microcode) {
		/*
		 * Zen1/2 with SMT off aren't vulnerable after the right
		 * IBPB microcode has been applied.
@@ -2338,6 +2328,12 @@ static void __init srso_select_mitigation(void)
			srso_mitigation = SRSO_MITIGATION_IBPB;
			goto pred_cmd;
		}
	} else {
		pr_warn("IBPB-extending microcode not applied!\n");
		pr_warn(SRSO_NOTICE);

		/* may be overwritten by SRSO_CMD_SAFE_RET below */
		srso_mitigation = SRSO_MITIGATION_UCODE_NEEDED;
	}

	switch (srso_cmd) {
@@ -2367,7 +2363,10 @@ static void __init srso_select_mitigation(void)
				setup_force_cpu_cap(X86_FEATURE_SRSO);
				x86_return_thunk = srso_return_thunk;
			}
			if (has_microcode)
				srso_mitigation = SRSO_MITIGATION_SAFE_RET;
			else
				srso_mitigation = SRSO_MITIGATION_SAFE_RET_UCODE_NEEDED;
		} else {
			pr_err("WARNING: kernel not compiled with CPU_SRSO.\n");
			goto pred_cmd;
@@ -2402,7 +2401,7 @@ static void __init srso_select_mitigation(void)
		break;
	}

	pr_info("%s%s\n", srso_strings[srso_mitigation], (has_microcode ? "" : ", no microcode"));
	pr_info("%s\n", srso_strings[srso_mitigation]);

pred_cmd:
	if ((!boot_cpu_has_bug(X86_BUG_SRSO) || srso_cmd == SRSO_CMD_OFF) &&
@@ -2619,9 +2618,7 @@ static ssize_t srso_show_state(char *buf)
	if (boot_cpu_has(X86_FEATURE_SRSO_NO))
		return sysfs_emit(buf, "Mitigation: SMT disabled\n");

	return sysfs_emit(buf, "%s%s\n",
			  srso_strings[srso_mitigation],
			  boot_cpu_has(X86_FEATURE_IBPB_BRTYPE) ? "" : ", no microcode");
	return sysfs_emit(buf, "%s\n", srso_strings[srso_mitigation]);
}

static ssize_t cpu_show_common(struct device *dev, struct device_attribute *attr,