Page MenuHomeFreeBSD

D52577.diff
No OneTemporary

D52577.diff

diff --git a/sys/arm/arm/generic_timer.c b/sys/arm/arm/generic_timer.c
--- a/sys/arm/arm/generic_timer.c
+++ b/sys/arm/arm/generic_timer.c
@@ -905,8 +905,15 @@
return (true);
}
+static void
+wfxt_disabled(const struct cpu_feat *feat __unused)
+{
+ if (PCPU_GET(cpuid) == 0)
+ update_special_reg(ID_AA64ISAR2_EL1, ID_AA64ISAR2_WFxT_MASK, 0);
+}
+
CPU_FEAT(feat_wfxt, "WFE and WFI instructions with timeout",
- wfxt_check, NULL, wfxt_enable,
+ wfxt_check, NULL, wfxt_enable, wfxt_disabled,
CPU_FEAT_AFTER_DEV | CPU_FEAT_SYSTEM);
#endif
diff --git a/sys/arm64/arm64/cpu_feat.c b/sys/arm64/arm64/cpu_feat.c
--- a/sys/arm64/arm64/cpu_feat.c
+++ b/sys/arm64/arm64/cpu_feat.c
@@ -69,18 +69,18 @@
check_status = feat->feat_check(feat, midr);
/* Ignore features that are not present */
if (check_status == FEAT_ALWAYS_DISABLE)
- continue;
+ goto next;
snprintf(tunable, sizeof(tunable), "hw.feat.%s",
feat->feat_name);
if (TUNABLE_BOOL_FETCH(tunable, &val)) {
/* Is the feature disabled by the tunable? */
if (!val)
- continue;
+ goto next;
/* If enabled by the tunable then enable it */
} else if (check_status == FEAT_DEFAULT_DISABLE) {
/* No tunable set and disabled by default */
- continue;
+ goto next;
}
/*
@@ -122,6 +122,10 @@
if (feat->feat_enable(feat, errata_status, errata_list,
errata_count))
feat->feat_enabled = true;
+
+next:
+ if (!feat->feat_enabled && feat->feat_disabled != NULL)
+ feat->feat_disabled(feat);
}
}
diff --git a/sys/arm64/arm64/identcpu.c b/sys/arm64/arm64/identcpu.c
--- a/sys/arm64/arm64/identcpu.c
+++ b/sys/arm64/arm64/identcpu.c
@@ -2353,7 +2353,7 @@
}
CPU_FEAT(trap_ctr, "Trap CTR_EL0",
- user_ctr_check, user_ctr_has_errata, user_ctr_enable,
+ user_ctr_check, user_ctr_has_errata, user_ctr_enable, NULL,
CPU_FEAT_AFTER_DEV | CPU_FEAT_PER_CPU);
static bool
diff --git a/sys/arm64/arm64/machdep.c b/sys/arm64/arm64/machdep.c
--- a/sys/arm64/arm64/machdep.c
+++ b/sys/arm64/arm64/machdep.c
@@ -208,8 +208,15 @@
return (true);
}
+static void
+pan_disabled(const struct cpu_feat *feat __unused)
+{
+ if (PCPU_GET(cpuid) == 0)
+ update_special_reg(ID_AA64MMFR1_EL1, ID_AA64MMFR1_PAN_MASK, 0);
+}
+
CPU_FEAT(feat_pan, "Privileged access never",
- pan_check, NULL, pan_enable,
+ pan_check, NULL, pan_enable, pan_disabled,
CPU_FEAT_AFTER_DEV | CPU_FEAT_PER_CPU);
bool
diff --git a/sys/arm64/arm64/pmap.c b/sys/arm64/arm64/pmap.c
--- a/sys/arm64/arm64/pmap.c
+++ b/sys/arm64/arm64/pmap.c
@@ -1722,7 +1722,7 @@
}
CPU_FEAT(feat_hafdbs, "Hardware management of the Access flag and dirty state",
- pmap_dbm_check, pmap_dbm_has_errata, pmap_dbm_enable,
+ pmap_dbm_check, pmap_dbm_has_errata, pmap_dbm_enable, NULL,
CPU_FEAT_AFTER_DEV | CPU_FEAT_PER_CPU);
static cpu_feat_en
@@ -1767,7 +1767,7 @@
}
CPU_FEAT(errata_multi_tlbi, "Multiple TLBI errata",
- pmap_multiple_tlbi_check, NULL, pmap_multiple_tlbi_enable,
+ pmap_multiple_tlbi_check, NULL, pmap_multiple_tlbi_enable, NULL,
CPU_FEAT_EARLY_BOOT | CPU_FEAT_PER_CPU);
/*
diff --git a/sys/arm64/arm64/ptrauth.c b/sys/arm64/arm64/ptrauth.c
--- a/sys/arm64/arm64/ptrauth.c
+++ b/sys/arm64/arm64/ptrauth.c
@@ -97,11 +97,11 @@
if (!pac_enable) {
if (boothowto & RB_VERBOSE)
printf("Pointer authentication is disabled\n");
- goto out;
+ return (FEAT_ALWAYS_DISABLE);
}
if (ptrauth_disable())
- goto out;
+ return (FEAT_ALWAYS_DISABLE);
/*
* This assumes if there is pointer authentication on the boot CPU
@@ -127,17 +127,6 @@
}
}
-out:
- /*
- * Pointer authentication may be disabled, mask out the ID fields we
- * expose to userspace and the rest of the kernel so they don't try
- * to use it.
- */
- update_special_reg(ID_AA64ISAR1_EL1, ID_AA64ISAR1_API_MASK |
- ID_AA64ISAR1_APA_MASK | ID_AA64ISAR1_GPA_MASK |
- ID_AA64ISAR1_GPI_MASK, 0);
- update_special_reg(ID_AA64ISAR2_EL1, ID_AA64ISAR2_APA3_MASK, 0);
-
return (FEAT_ALWAYS_DISABLE);
}
@@ -157,8 +146,25 @@
return (true);
}
+static void
+ptrauth_disabled(const struct cpu_feat *feat __unused)
+{
+ /*
+ * Pointer authentication may be disabled, mask out the ID fields we
+ * expose to userspace and the rest of the kernel so they don't try
+ * to use it.
+ */
+ if (PCPU_GET(cpuid) == 0) {
+ update_special_reg(ID_AA64ISAR1_EL1, ID_AA64ISAR1_API_MASK |
+ ID_AA64ISAR1_APA_MASK | ID_AA64ISAR1_GPA_MASK |
+ ID_AA64ISAR1_GPI_MASK, 0);
+ update_special_reg(ID_AA64ISAR2_EL1, ID_AA64ISAR2_APA3_MASK, 0);
+ }
+
+}
+
CPU_FEAT(feat_pauth, "Pointer Authentication",
- ptrauth_check, NULL, ptrauth_enable,
+ ptrauth_check, NULL, ptrauth_enable, ptrauth_disabled,
CPU_FEAT_EARLY_BOOT | CPU_FEAT_SYSTEM);
/* Copy the keys when forking a new process */
diff --git a/sys/arm64/include/cpu_feat.h b/sys/arm64/include/cpu_feat.h
--- a/sys/arm64/include/cpu_feat.h
+++ b/sys/arm64/include/cpu_feat.h
@@ -80,12 +80,14 @@
u_int **, u_int *);
typedef bool (cpu_feat_enable)(const struct cpu_feat *, cpu_feat_errata,
u_int *, u_int);
+typedef void (cpu_feat_disabled)(const struct cpu_feat *);
struct cpu_feat {
const char *feat_name;
cpu_feat_check *feat_check;
cpu_feat_has_errata *feat_has_errata;
cpu_feat_enable *feat_enable;
+ cpu_feat_disabled *feat_disabled;
uint32_t feat_flags;
bool feat_enabled;
};
@@ -93,12 +95,13 @@
SYSCTL_DECL(_hw_feat);
-#define CPU_FEAT(name, descr, check, has_errata, enable, flags) \
+#define CPU_FEAT(name, descr, check, has_errata, enable, disabled, flags) \
static struct cpu_feat name = { \
.feat_name = #name, \
.feat_check = check, \
.feat_has_errata = has_errata, \
.feat_enable = enable, \
+ .feat_disabled = disabled, \
.feat_flags = flags, \
.feat_enabled = false, \
}; \

File Metadata

Mime Type
text/plain
Expires
Mon, Feb 9, 5:21 PM (2 h, 12 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
28598200
Default Alt Text
D52577.diff (5 KB)

Event Timeline