All of lore.kernel.org
 help / color / mirror / Atom feed
* [RFC] P9 ldmx support
@ 2016-04-11 18:57 Jack Miller
  2016-04-11 18:57 ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller
                   ` (3 more replies)
  0 siblings, 4 replies; 16+ messages in thread
From: Jack Miller @ 2016-04-11 18:57 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: michaele, michael.neuling

All -

These are patches based on next to support the forthcoming ldmx instruction
through the existing P8 EBB infrastructure. Obviously it doesn't actually
*work* without some other patches and a P9 system, but with the context
switch change to FSCR it makes sense to get this upstream for testing ASAP.

The first patch context switches FSCR per thread so that the second patch can
lazily enable this feature (FSCR.LM) with a facility unavailable exception
and context switch two new ldmx registers (LMRR / LMSER) per thread as well.
Third patch is a couple of basic tests.

Any comments welcome.

- Jack

^ permalink raw reply	[flat|nested] 16+ messages in thread

* [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-11 18:57 [RFC] P9 ldmx support Jack Miller
@ 2016-04-11 18:57 ` Jack Miller
  2016-04-12 23:42   ` [1/3] " Michael Ellerman
  2016-04-13 10:51   ` [PATCH 1/3] " Anton Blanchard
  2016-04-11 18:57 ` [PATCH 2/3] powerpc: Load Monitor Register Support Jack Miller
                   ` (2 subsequent siblings)
  3 siblings, 2 replies; 16+ messages in thread
From: Jack Miller @ 2016-04-11 18:57 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: michaele, michael.neuling

Previously we just saved the FSCR, but only restored it in some
settings, and never copied it thread to thread. This patch always
restores the FSCR and formalizes new threads inheriting its setting so
that later we can manipulate FSCR bits in start_thread.

Signed-off-by: Jack Miller <jack@codezen.org>
---
 arch/powerpc/kernel/process.c | 7 +++++++
 1 file changed, 7 insertions(+)

diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index b8500b4..0c7e797 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -1043,6 +1043,10 @@ static inline void restore_sprs(struct thread_struct *old_thread,
 
 		if (old_thread->tar != new_thread->tar)
 			mtspr(SPRN_TAR, new_thread->tar);
+
+		if (old_thread->fscr != new_thread->fscr)
+			mtspr(SPRN_FSCR, new_thread->fscr);
+
 	}
 #endif
 }
@@ -1478,6 +1482,9 @@ int copy_thread(unsigned long clone_flags, unsigned long usp,
 	}
 	if (cpu_has_feature(CPU_FTR_HAS_PPR))
 		p->thread.ppr = INIT_PPR;
+
+	if (cpu_has_feature(CPU_FTR_ARCH_207S))
+		p->thread.fscr = mfspr(SPRN_FSCR);
 #endif
 	kregs->nip = ppc_function_entry(f);
 	return 0;
-- 
2.8.0

^ permalink raw reply related	[flat|nested] 16+ messages in thread

* [PATCH 2/3] powerpc: Load Monitor Register Support
  2016-04-11 18:57 [RFC] P9 ldmx support Jack Miller
  2016-04-11 18:57 ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller
@ 2016-04-11 18:57 ` Jack Miller
  2016-04-12  5:40   ` Segher Boessenkool
  2016-04-11 18:57 ` [PATCH 3/3] powerpc: Load Monitor Register Tests Jack Miller
  2016-04-12  1:05 ` [RFC] P9 ldmx support Michael Neuling
  3 siblings, 1 reply; 16+ messages in thread
From: Jack Miller @ 2016-04-11 18:57 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: michaele, michael.neuling

This enables new registers, LMRR and LMSER, that can trigger an EBB in
userspace code when a monitored load (via the new ldmx instruction)
loads memory from a monitored space. This facility is controlled by a
new FSCR bit, LM.

This patch disables the control bit on CPU setup and enables that bit
when a facility unavailable exception is taken for using it. On context
switch, this bit is then used to determine whether the two relevant
registers are saved and restored. This is done lazily for performance
reasons.

Signed-off-by: Jack Miller <jack@codezen.org>
---
 arch/powerpc/include/asm/processor.h  |  2 ++
 arch/powerpc/include/asm/reg.h        |  5 +++++
 arch/powerpc/kernel/cpu_setup_power.S |  1 +
 arch/powerpc/kernel/process.c         | 19 +++++++++++++++++++
 arch/powerpc/kernel/traps.c           |  4 ++++
 5 files changed, 31 insertions(+)

diff --git a/arch/powerpc/include/asm/processor.h b/arch/powerpc/include/asm/processor.h
index 009fab1..2bb822b 100644
--- a/arch/powerpc/include/asm/processor.h
+++ b/arch/powerpc/include/asm/processor.h
@@ -314,6 +314,8 @@ struct thread_struct {
 	unsigned long	mmcr2;
 	unsigned 	mmcr0;
 	unsigned 	used_ebb;
+	unsigned long	lmrr;
+	unsigned long	lmser;
 #endif
 };
 
diff --git a/arch/powerpc/include/asm/reg.h b/arch/powerpc/include/asm/reg.h
index 7972c9f..ab98ca4 100644
--- a/arch/powerpc/include/asm/reg.h
+++ b/arch/powerpc/include/asm/reg.h
@@ -282,6 +282,8 @@
 #define SPRN_HRMOR	0x139	/* Real mode offset register */
 #define SPRN_HSRR0	0x13A	/* Hypervisor Save/Restore 0 */
 #define SPRN_HSRR1	0x13B	/* Hypervisor Save/Restore 1 */
+#define SPRN_LMRR	0x32D	/* Load Monitor Region Register */
+#define SPRN_LMSER	0x32E	/* Load Monitor Section Enable Register */
 #define SPRN_IC		0x350	/* Virtual Instruction Count */
 #define SPRN_VTB	0x351	/* Virtual Time Base */
 #define SPRN_LDBAR	0x352	/* LD Base Address Register */
@@ -291,6 +293,7 @@
 #define SPRN_PMCR	0x374	/* Power Management Control Register */
 
 /* HFSCR and FSCR bit numbers are the same */
+#define FSCR_LM_LG	11	/* Enable Load Monitor Registers */
 #define FSCR_TAR_LG	8	/* Enable Target Address Register */
 #define FSCR_EBB_LG	7	/* Enable Event Based Branching */
 #define FSCR_TM_LG	5	/* Enable Transactional Memory */
@@ -300,10 +303,12 @@
 #define FSCR_VECVSX_LG	1	/* Enable VMX/VSX  */
 #define FSCR_FP_LG	0	/* Enable Floating Point */
 #define SPRN_FSCR	0x099	/* Facility Status & Control Register */
+#define   FSCR_LM	__MASK(FSCR_LM_LG)
 #define   FSCR_TAR	__MASK(FSCR_TAR_LG)
 #define   FSCR_EBB	__MASK(FSCR_EBB_LG)
 #define   FSCR_DSCR	__MASK(FSCR_DSCR_LG)
 #define SPRN_HFSCR	0xbe	/* HV=1 Facility Status & Control Register */
+#define   HFSCR_LM	__MASK(FSCR_LM_LG)
 #define   HFSCR_TAR	__MASK(FSCR_TAR_LG)
 #define   HFSCR_EBB	__MASK(FSCR_EBB_LG)
 #define   HFSCR_TM	__MASK(FSCR_TM_LG)
diff --git a/arch/powerpc/kernel/cpu_setup_power.S b/arch/powerpc/kernel/cpu_setup_power.S
index 584e119..0474856 100644
--- a/arch/powerpc/kernel/cpu_setup_power.S
+++ b/arch/powerpc/kernel/cpu_setup_power.S
@@ -157,6 +157,7 @@ __init_LPCR:
 
 __init_FSCR:
 	mfspr	r3,SPRN_FSCR
+	andi.   r3,r3,(~FSCR_LM)@L
 	ori	r3,r3,FSCR_TAR|FSCR_DSCR|FSCR_EBB
 	mtspr	SPRN_FSCR,r3
 	blr
diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index 0c7e797..e39af31 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -1005,6 +1005,14 @@ static inline void save_sprs(struct thread_struct *t)
 		 */
 		t->tar = mfspr(SPRN_TAR);
 	}
+
+	if (cpu_has_feature(CPU_FTR_ARCH_300)) {
+		/* Conditionally save Load Monitor registers, if enabled */
+		if (t->fscr & FSCR_LM) {
+			t->lmrr = mfspr(SPRN_LMRR);
+			t->lmser = mfspr(SPRN_LMSER);
+		}
+	}
 #endif
 }
 
@@ -1046,7 +1054,16 @@ static inline void restore_sprs(struct thread_struct *old_thread,
 
 		if (old_thread->fscr != new_thread->fscr)
 			mtspr(SPRN_FSCR, new_thread->fscr);
+	}
 
+	if (cpu_has_feature(CPU_FTR_ARCH_300)) {
+		/* Conditionally restore Load Monitor registers, if enabled */
+		if (new_thread->fscr & FSCR_LM) {
+			if (old_thread->lmrr != new_thread->lmrr);
+				mtspr(SPRN_LMRR, new_thread->lmrr);
+			if (old_thread->lmser != new_thread->lmser);
+				mtspr(SPRN_LMSER, new_thread->lmser);
+		}
 	}
 #endif
 }
@@ -1573,6 +1590,8 @@ void start_thread(struct pt_regs *regs, unsigned long start, unsigned long sp)
 		regs->gpr[2] = 0;
 		regs->msr = MSR_USER32;
 	}
+
+	current->thread.fscr &= ~FSCR_LM;
 #endif
 #ifdef CONFIG_VSX
 	current->thread.used_vsr = 0;
diff --git a/arch/powerpc/kernel/traps.c b/arch/powerpc/kernel/traps.c
index 9229ba6..93ff3ac 100644
--- a/arch/powerpc/kernel/traps.c
+++ b/arch/powerpc/kernel/traps.c
@@ -1376,6 +1376,7 @@ void facility_unavailable_exception(struct pt_regs *regs)
 		[FSCR_TM_LG] = "TM",
 		[FSCR_EBB_LG] = "EBB",
 		[FSCR_TAR_LG] = "TAR",
+		[FSCR_LM_LG] = "LM",
 	};
 	char *facility = "unknown";
 	u64 value;
@@ -1432,6 +1433,9 @@ void facility_unavailable_exception(struct pt_regs *regs)
 			emulate_single_step(regs);
 		}
 		return;
+	} else if ((status == FSCR_LM_LG) && cpu_has_feature(CPU_FTR_ARCH_300)) {
+		mtspr(SPRN_FSCR, value | FSCR_LM);
+		return;
 	}
 
 	if ((status < ARRAY_SIZE(facility_strings)) &&
-- 
2.8.0

^ permalink raw reply related	[flat|nested] 16+ messages in thread

* [PATCH 3/3] powerpc: Load Monitor Register Tests
  2016-04-11 18:57 [RFC] P9 ldmx support Jack Miller
  2016-04-11 18:57 ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller
  2016-04-11 18:57 ` [PATCH 2/3] powerpc: Load Monitor Register Support Jack Miller
@ 2016-04-11 18:57 ` Jack Miller
  2016-04-15 10:34   ` Madhavan Srinivasan
  2016-04-12  1:05 ` [RFC] P9 ldmx support Michael Neuling
  3 siblings, 1 reply; 16+ messages in thread
From: Jack Miller @ 2016-04-11 18:57 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: michaele, michael.neuling

Adds two tests. One is a simple test to ensure that the new registers
LMRR and LMSER are properly maintained. The other actually uses the
existing EBB test infrastructure to test that LMRR and LMSER behave as
documented.

Signed-off-by: Jack Miller <jack@codezen.org>
---
 tools/testing/selftests/powerpc/pmu/ebb/Makefile   |   2 +-
 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c  | 144 +++++++++++++++++++++
 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h  |  39 ++++++
 .../selftests/powerpc/pmu/ebb/ebb_lmr_regs.c       |  38 ++++++
 tools/testing/selftests/powerpc/pmu/ebb/reg.h      |   5 +
 5 files changed, 227 insertions(+), 1 deletion(-)
 create mode 100644 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c
 create mode 100644 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h
 create mode 100644 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c

diff --git a/tools/testing/selftests/powerpc/pmu/ebb/Makefile b/tools/testing/selftests/powerpc/pmu/ebb/Makefile
index 8d2279c4..6b0453e 100644
--- a/tools/testing/selftests/powerpc/pmu/ebb/Makefile
+++ b/tools/testing/selftests/powerpc/pmu/ebb/Makefile
@@ -14,7 +14,7 @@ TEST_PROGS := reg_access_test event_attributes_test cycles_test	\
 	 fork_cleanup_test ebb_on_child_test			\
 	 ebb_on_willing_child_test back_to_back_ebbs_test	\
 	 lost_exception_test no_handler_test			\
-	 cycles_with_mmcr2_test
+	 cycles_with_mmcr2_test ebb_lmr ebb_lmr_regs
 
 all: $(TEST_PROGS)
 
diff --git a/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c
new file mode 100644
index 0000000..266062b7
--- /dev/null
+++ b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c
@@ -0,0 +1,144 @@
+/*
+ * Copyright 2016, Jack Miller, IBM Corp.
+ * Licensed under GPLv2.
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+
+#include "ebb.h"
+#include "ebb_lmr.h"
+
+#define SIZE		(32 * 1024 * 1024)	/* 32M */
+#define LM_SIZE		0	/* Smallest encoding, 32M */
+
+#define SECTIONS	64	/* 1 per bit in LMSER */
+#define SECTION_SIZE	(SIZE / SECTIONS)
+#define SECTION_LONGS   (SECTION_SIZE / sizeof(long))
+
+static unsigned long *test_mem;
+
+static int lmr_count = 0;
+
+void ebb_lmr_handler(void)
+{
+	lmr_count++;
+}
+
+void ldmx_full_section(unsigned long *mem, int section)
+{
+	unsigned long *ptr;
+	int i;
+
+	for (i = 0; i < SECTION_LONGS; i++) {
+		ptr = &mem[(SECTION_LONGS * section) + i];
+		ldmx((unsigned long) &ptr);
+		ebb_lmr_reset();
+	}
+}
+
+unsigned long section_masks[] = {
+	0x8000000000000000,
+	0xFF00000000000000,
+	0x0000000F70000000,
+	0x8000000000000001,
+	0xF0F0F0F0F0F0F0F0,
+	0x0F0F0F0F0F0F0F0F,
+	0x0
+};
+
+int ebb_lmr_section_test(unsigned long *mem)
+{
+	unsigned long *mask = section_masks;
+	int i;
+
+	for (; *mask; mask++) {
+		mtspr(SPRN_LMSER, *mask);
+		printf("Testing mask 0x%016lx\n", mfspr(SPRN_LMSER));
+
+		for (i = 0; i < 64; i++) {
+			lmr_count = 0;
+			ldmx_full_section(mem, i);
+			if (*mask & (1UL << (63 - i)))
+				FAIL_IF(lmr_count != SECTION_LONGS);
+			else
+				FAIL_IF(lmr_count);
+		}
+	}
+
+	return 0;
+}
+
+int ebb_lmr(void)
+{
+	int i;
+
+	SKIP_IF(!ebb_is_supported());
+	SKIP_IF(!lmr_is_supported());
+
+	setup_ebb_handler(ebb_lmr_handler);
+
+	ebb_global_enable();
+
+	FAIL_IF(posix_memalign((void **)&test_mem, SIZE, SIZE) != 0);
+
+	mtspr(SPRN_LMSER, 0);
+
+	FAIL_IF(mfspr(SPRN_LMSER) != 0);
+
+	mtspr(SPRN_LMRR, ((unsigned long)test_mem | LM_SIZE));
+
+	FAIL_IF(mfspr(SPRN_LMRR) != ((unsigned long)test_mem | LM_SIZE));
+
+	/* Read every single byte to ensure we get no false positives */
+	for (i = 0; i < SECTIONS; i++)
+		ldmx_full_section(test_mem, i);
+
+	FAIL_IF(lmr_count != 0);
+
+	/* Turn on the first section */
+
+	mtspr(SPRN_LMSER, (1UL << 63));
+	FAIL_IF(mfspr(SPRN_LMSER) != (1UL << 63));
+
+	/* Enable LM (BESCR) */
+
+	mtspr(SPRN_BESCR, mfspr(SPRN_BESCR) | BESCR_LME);
+	FAIL_IF(!(mfspr(SPRN_BESCR) & BESCR_LME));
+
+	ldmx((unsigned long)&test_mem);
+
+	FAIL_IF(lmr_count != 1);	// exactly one exception
+	FAIL_IF(mfspr(SPRN_BESCR) & BESCR_LME);	// LM now disabled
+	FAIL_IF(!(mfspr(SPRN_BESCR) & BESCR_LMEO));	// occurred bit set
+
+	printf("Simple LMR EBB OK\n");
+
+	/* This shouldn't cause an EBB since it's been disabled */
+	ldmx((unsigned long)&test_mem);
+	FAIL_IF(lmr_count != 1);
+
+	printf("LMR disable on EBB OK\n");
+
+	ebb_lmr_reset();
+
+	/* This should cause an EBB or reset is broken */
+	ldmx((unsigned long)&test_mem);
+	FAIL_IF(lmr_count != 2);
+
+	printf("LMR reset EBB OK\n");
+
+	ebb_lmr_reset();
+
+	return ebb_lmr_section_test(test_mem);
+}
+
+int main(void)
+{
+	int ret = test_harness(ebb_lmr, "ebb_lmr");
+
+	if (test_mem)
+		free(test_mem);
+
+	return ret;
+}
diff --git a/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h
new file mode 100644
index 0000000..7911756
--- /dev/null
+++ b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h
@@ -0,0 +1,39 @@
+#ifndef _SELFTESTS_POWERPC_PMU_EBB_LMR_H
+#define _SELFTESTS_POWERPC_PMU_EBB_LMR_H
+
+#include "reg.h"
+
+#ifndef PPC_FEATURE2_ARCH_3_00
+#define PPC_FEATURE2_ARCH_3_00 0x00800000
+#endif
+
+#define lmr_is_supported() have_hwcap2(PPC_FEATURE2_ARCH_3_00)
+
+static inline void ebb_lmr_reset(void)
+{
+	unsigned long bescr = mfspr(SPRN_BESCR);
+	bescr &= ~(BESCR_LMEO);
+	bescr |= BESCR_LME;
+	mtspr(SPRN_BESCR, bescr);
+}
+
+#define LDMX(t, a, b)\
+    (0x7c00026a |\
+    ((t & 0x1f) << 21) |\
+    ((a & 0x1f) << 16) |\
+    ((b & 0x1f) << 11))
+
+static inline unsigned long ldmx(unsigned long address)
+{
+	unsigned long ret;
+
+	asm volatile ("mr 9, %1\r\n"
+		      ".long " __stringify(LDMX(9, 0, 9)) "\r\n"
+		      "mr %0, 9\r\n":"=r"(ret)
+		      :"r"(address)
+		      :"r9");
+
+	return ret;
+}
+
+#endif
diff --git a/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c
new file mode 100644
index 0000000..d2a4898
--- /dev/null
+++ b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c
@@ -0,0 +1,38 @@
+/*
+ * Copyright 2016, Jack Miller, IBM Corp.
+ * Licensed under GPLv2.
+ */
+
+#include <stdlib.h>
+#include <stdio.h>
+#include <unistd.h>
+
+#include "ebb.h"
+#include "ebb_lmr.h"
+
+#define CHECKS 10000
+
+int ebb_lmr_regs(void)
+{
+	int i;
+
+	SKIP_IF(!ebb_is_supported());
+	SKIP_IF(!lmr_is_supported());
+
+	ebb_global_enable();
+
+	for (i = 0; i < CHECKS; i++) {
+		mtspr(SPRN_LMRR, i << 25);	// skip size and rsvd bits
+		mtspr(SPRN_LMSER, i);
+
+		FAIL_IF(mfspr(SPRN_LMRR) != (i << 25));
+		FAIL_IF(mfspr(SPRN_LMSER) != i);
+	}
+
+	return 0;
+}
+
+int main(void)
+{
+	return test_harness(ebb_lmr_regs, "ebb_lmr_regs");
+}
diff --git a/tools/testing/selftests/powerpc/pmu/ebb/reg.h b/tools/testing/selftests/powerpc/pmu/ebb/reg.h
index 5921b0d..0659a7b 100644
--- a/tools/testing/selftests/powerpc/pmu/ebb/reg.h
+++ b/tools/testing/selftests/powerpc/pmu/ebb/reg.h
@@ -34,6 +34,11 @@
 
 #define BESCR_PMEO     0x1     /* PMU Event-based exception Occurred */
 #define BESCR_PME      (0x1ul << 32) /* PMU Event-based exception Enable */
+#define BESCR_LME      (0x1ul << 34) /* Load Monitor Enable */
+#define BESCR_LMEO     (0x1ul << 2)  /* Load Monitor Exception Occurred */
+
+#define SPRN_LMRR      813     /* Load Monitor Region Register */
+#define SPRN_LMSER     814     /* Load Monitor Section Enable Register */
 
 #define SPRN_PMC1      771
 #define SPRN_PMC2      772
-- 
2.8.0

^ permalink raw reply related	[flat|nested] 16+ messages in thread

* Re: [RFC] P9 ldmx support
  2016-04-11 18:57 [RFC] P9 ldmx support Jack Miller
                   ` (2 preceding siblings ...)
  2016-04-11 18:57 ` [PATCH 3/3] powerpc: Load Monitor Register Tests Jack Miller
@ 2016-04-12  1:05 ` Michael Neuling
  3 siblings, 0 replies; 16+ messages in thread
From: Michael Neuling @ 2016-04-12  1:05 UTC (permalink / raw)
  To: Jack Miller, linuxppc-dev


> Re: [RFC] P9 ldmx support

These are good to go and don't need to be marked as RFC.

FWIW, we've been testing these internally and they've been solid.

> These are patches based on next to support the forthcoming ldmx
> instruction through the existing P8 EBB infrastructure. Obviously it
> doesn't actually *work* without some other patches and a P9 system,
> but with the context switch change to FSCR it makes sense to get
> this upstream for testing ASAP.

Yep.

Thanks,
Mikey

> The first patch context switches FSCR per thread so that the second patch=
 can
> lazily enable this feature (FSCR.LM) with a facility unavailable exceptio=
n
> and context switch two new ldmx registers (LMRR / LMSER) per thread as we=
ll.
> Third patch is a couple of basic tests.

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 2/3] powerpc: Load Monitor Register Support
  2016-04-11 18:57 ` [PATCH 2/3] powerpc: Load Monitor Register Support Jack Miller
@ 2016-04-12  5:40   ` Segher Boessenkool
  2016-04-13 17:39     ` Jack Miller
  0 siblings, 1 reply; 16+ messages in thread
From: Segher Boessenkool @ 2016-04-12  5:40 UTC (permalink / raw)
  To: Jack Miller; +Cc: linuxppc-dev, michael.neuling, michaele

Hi,

On Mon, Apr 11, 2016 at 01:57:44PM -0500, Jack Miller wrote:
>  __init_FSCR:
>  	mfspr	r3,SPRN_FSCR
> +	andi.   r3,r3,(~FSCR_LM)@L
>  	ori	r3,r3,FSCR_TAR|FSCR_DSCR|FSCR_EBB
>  	mtspr	SPRN_FSCR,r3
>  	blr

This clears the top 48 bits as well.  Shouldn't matter currently; but
more robust (and easier to read, if you know the idiom) is

	ori	r3,r3,FSCR_LM|FSCR_TAR|FSCR_DSCR|FSCR_EBB
	xori	r3,r3,FSCR_LM


Segher

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [1/3] powerpc: Complete FSCR context switch
  2016-04-11 18:57 ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller
@ 2016-04-12 23:42   ` Michael Ellerman
  2016-04-13 10:51   ` [PATCH 1/3] " Anton Blanchard
  1 sibling, 0 replies; 16+ messages in thread
From: Michael Ellerman @ 2016-04-12 23:42 UTC (permalink / raw)
  To: Jack Miller, linuxppc-dev; +Cc: michael.neuling

On Mon, 2016-11-04 at 18:57:43 UTC, Jack Miller wrote:
> Previously we just saved the FSCR, but only restored it in some
> settings, and never copied it thread to thread. This patch always
> restores the FSCR and formalizes new threads inheriting its setting so
> that later we can manipulate FSCR bits in start_thread.

This seems like it's a bug in the current code?

cheers

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-11 18:57 ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller
  2016-04-12 23:42   ` [1/3] " Michael Ellerman
@ 2016-04-13 10:51   ` Anton Blanchard
  2016-04-13 17:52     ` Jack Miller
  1 sibling, 1 reply; 16+ messages in thread
From: Anton Blanchard @ 2016-04-13 10:51 UTC (permalink / raw)
  To: Jack Miller; +Cc: linuxppc-dev, michael.neuling, michaele

Hi Jack,

> Previously we just saved the FSCR, but only restored it in some
> settings, and never copied it thread to thread. This patch always
> restores the FSCR and formalizes new threads inheriting its setting so
> that later we can manipulate FSCR bits in start_thread.

Will this break the existing FSCR_DSCR bit handling?

         if (cpu_has_feature(CPU_FTR_DSCR)) {
                u64 dscr = get_paca()->dscr_default;
                u64 fscr = old_thread->fscr & ~FSCR_DSCR;

                if (new_thread->dscr_inherit) {
                        dscr = new_thread->dscr;
                        fscr |= FSCR_DSCR;
                }

                if (old_thread->dscr != dscr)
                        mtspr(SPRN_DSCR, dscr);

                if (old_thread->fscr != fscr)
                        mtspr(SPRN_FSCR, fscr);
        }

If not, we should modify the above so we don't write the FSCR twice.

Anton

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 2/3] powerpc: Load Monitor Register Support
  2016-04-12  5:40   ` Segher Boessenkool
@ 2016-04-13 17:39     ` Jack Miller
  0 siblings, 0 replies; 16+ messages in thread
From: Jack Miller @ 2016-04-13 17:39 UTC (permalink / raw)
  To: Segher Boessenkool; +Cc: linuxppc-dev, michael.neuling, michaele

Thanks, yeah, that's more readable and more correct. I'll change it in
the next spin.

- Jack

On Tue, Apr 12, 2016 at 12:40 AM, Segher Boessenkool
<segher@kernel.crashing.org> wrote:
> Hi,
>
> On Mon, Apr 11, 2016 at 01:57:44PM -0500, Jack Miller wrote:
>>  __init_FSCR:
>>       mfspr   r3,SPRN_FSCR
>> +     andi.   r3,r3,(~FSCR_LM)@L
>>       ori     r3,r3,FSCR_TAR|FSCR_DSCR|FSCR_EBB
>>       mtspr   SPRN_FSCR,r3
>>       blr
>
> This clears the top 48 bits as well.  Shouldn't matter currently; but
> more robust (and easier to read, if you know the idiom) is
>
>         ori     r3,r3,FSCR_LM|FSCR_TAR|FSCR_DSCR|FSCR_EBB
>         xori    r3,r3,FSCR_LM
>
>
> Segher

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-13 10:51   ` [PATCH 1/3] " Anton Blanchard
@ 2016-04-13 17:52     ` Jack Miller
  2016-04-13 23:49       ` Michael Neuling
  0 siblings, 1 reply; 16+ messages in thread
From: Jack Miller @ 2016-04-13 17:52 UTC (permalink / raw)
  To: Anton Blanchard; +Cc: Jack Miller, linuxppc-dev, michael.neuling, michaele

Hi Anton.

On Wed, Apr 13, 2016 at 5:51 AM, Anton Blanchard <anton@samba.org> wrote:
> Hi Jack,
>
>> Previously we just saved the FSCR, but only restored it in some
>> settings, and never copied it thread to thread. This patch always
>> restores the FSCR and formalizes new threads inheriting its setting so
>> that later we can manipulate FSCR bits in start_thread.
>
> Will this break the existing FSCR_DSCR bit handling?
>
>          if (cpu_has_feature(CPU_FTR_DSCR)) {
>                 u64 dscr = get_paca()->dscr_default;
>                 u64 fscr = old_thread->fscr & ~FSCR_DSCR;
>
>                 if (new_thread->dscr_inherit) {
>                         dscr = new_thread->dscr;
>                         fscr |= FSCR_DSCR;
>                 }
>
>                 if (old_thread->dscr != dscr)
>                         mtspr(SPRN_DSCR, dscr);
>
>                 if (old_thread->fscr != fscr)
>                         mtspr(SPRN_FSCR, fscr);
>         }
>
> If not, we should modify the above so we don't write the FSCR twice.

I think this code is just partially redundant. I think it's trying to
predict the right FSCR value based on this dscr_inherit flag. Now that
we fully switch it, we could skip setting FSCR here, and just set DSCR
if FSCR.DSCR is set (similar to what my patches do with FSCR.LM). In
fact, we might be able to just entirely get rid of the dscr_inherit
flag, but I'd have to look harder at that.

Right now the FSCR switch is conditional on FTR_ARCH_207S which is
more exclusive than FTR_DSCR, but I guess the actual FSCR register is
universal to PPC64 like the fscr field in the thread struct? If so, I
can just move the FSCR save/restore out of the 207 conditional.

Anyway, I'll clean this up a bit, add the little asm tweak from
Segher, and put another spin on the list.

- Jack

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-13 17:52     ` Jack Miller
@ 2016-04-13 23:49       ` Michael Neuling
  2016-04-14 18:39         ` Jack Miller
  0 siblings, 1 reply; 16+ messages in thread
From: Michael Neuling @ 2016-04-13 23:49 UTC (permalink / raw)
  To: Jack Miller, Anton Blanchard; +Cc: linuxppc-dev, michael

On Wed, 2016-04-13 at 12:52 -0500, Jack Miller wrote:

> Hi Anton.
>=20
> On Wed, Apr 13, 2016 at 5:51 AM, Anton Blanchard <anton@samba.org> wrote:

> > Hi Jack,
> >=20

> > > Previously we just saved the FSCR, but only restored it in some
> > > settings, and never copied it thread to thread. This patch always
> > > restores the FSCR and formalizes new threads inheriting its setting s=
o
> > > that later we can manipulate FSCR bits in start_thread.
> >=20
> > Will this break the existing FSCR_DSCR bit handling?
> >=20
> >          if (cpu_has_feature(CPU_FTR_DSCR)) {
> >                 u64 dscr =3D get_paca()->dscr_default;
> >                 u64 fscr =3D old_thread->fscr & ~FSCR_DSCR;
> >=20
> >                 if (new_thread->dscr_inherit) {
> >                         dscr =3D new_thread->dscr;
> >                         fscr |=3D FSCR_DSCR;
> >                 }
> >=20
> >                 if (old_thread->dscr !=3D dscr)
> >                         mtspr(SPRN_DSCR, dscr);
> >=20
> >                 if (old_thread->fscr !=3D fscr)
> >                         mtspr(SPRN_FSCR, fscr);
> >         }
> >=20
> > If not, we should modify the above so we don't write the FSCR twice.
>=20
> I think this code is just partially redundant. I think it's trying to
> predict the right FSCR value based on this dscr_inherit flag. Now that
> we fully switch it, we could skip setting FSCR here, and just set DSCR
> if FSCR.DSCR is set (similar to what my patches do with FSCR.LM). In
> fact, we might be able to just entirely get rid of the dscr_inherit
> flag, but I'd have to look harder at that.

I'm not sure that works on processes before power8.

There DSCR SPR number 0x11 will always trap and emulate from userspace
(see arch/powerpc/kernel/traps.c:emulate_instruction()).  That is not
controlled by FSCR and should work on POWER7 where FSCR is not
present.  We need to set the inherit bit there too.

DSCR SPR number 0x3 is controlled by fscr, but it's only avaliable on
POWER8.

> Right now the FSCR switch is conditional on FTR_ARCH_207S which is
> more exclusive than FTR_DSCR, but I guess the actual FSCR register is
> universal to PPC64 like the fscr field in the thread struct? If so, I
> can just move the FSCR save/restore out of the 207 conditional.

FSCR was only introduced in power8, so it needs to be 207 conditional

Mikey

>=20
> Anyway, I'll clean this up a bit, add the little asm tweak from
> Segher, and put another spin on the list.
>=20
> - Jack
>=20

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-13 23:49       ` Michael Neuling
@ 2016-04-14 18:39         ` Jack Miller
  2016-04-14 23:11           ` Michael Neuling
  0 siblings, 1 reply; 16+ messages in thread
From: Jack Miller @ 2016-04-14 18:39 UTC (permalink / raw)
  To: Michael Neuling; +Cc: Jack Miller, Anton Blanchard, linuxppc-dev, michael

> I'm not sure that works on processes before power8.
>
> There DSCR SPR number 0x11 will always trap and emulate from userspace
> (see arch/powerpc/kernel/traps.c:emulate_instruction()).  That is not
> controlled by FSCR and should work on POWER7 where FSCR is not
> present.  We need to set the inherit bit there too.
>
> DSCR SPR number 0x3 is controlled by fscr, but it's only avaliable on
> POWER8.
>
>> Right now the FSCR switch is conditional on FTR_ARCH_207S which is
>> more exclusive than FTR_DSCR, but I guess the actual FSCR register is
>> universal to PPC64 like the fscr field in the thread struct? If so, I
>> can just move the FSCR save/restore out of the 207 conditional.
>
> FSCR was only introduced in power8, so it needs to be 207 conditional
>

So on P6/P7 (which have FTR_DSCR) set we're potentially mtspr'ing to a
non-existent register? Yuck. Can at least strip that logic out thanks
to the full context switch, I think, even if dscr_inherit actually has
a use.

- Jack

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-14 18:39         ` Jack Miller
@ 2016-04-14 23:11           ` Michael Neuling
  0 siblings, 0 replies; 16+ messages in thread
From: Michael Neuling @ 2016-04-14 23:11 UTC (permalink / raw)
  To: Jack Miller; +Cc: Anton Blanchard, linuxppc-dev, michael

On Thu, 2016-04-14 at 13:39 -0500, Jack Miller wrote:


> > I'm not sure that works on processes before power8.
> >=20
> > There DSCR SPR number 0x11 will always trap and emulate from userspace
> > (see arch/powerpc/kernel/traps.c:emulate_instruction()).  That is not
> > controlled by FSCR and should work on POWER7 where FSCR is not
> > present.  We need to set the inherit bit there too.
> >=20
> > DSCR SPR number 0x3 is controlled by fscr, but it's only avaliable on
> > POWER8.
> >=20

> > > Right now the FSCR switch is conditional on FTR_ARCH_207S which is
> > > more exclusive than FTR_DSCR, but I guess the actual FSCR register is
> > > universal to PPC64 like the fscr field in the thread struct? If so, I
> > > can just move the FSCR save/restore out of the 207 conditional.
> >=20
> > FSCR was only introduced in power8, so it needs to be 207 conditional
> >=20
>=20
> So on P6/P7 (which have FTR_DSCR) set we're potentially mtspr'ing to a
> non-existent register? Yuck. Can at least strip that logic out thanks
> to the full context switch, I think, even if dscr_inherit actually has
> a use.

Yeah, welcome to DSCR... it's horrible. :-(

It's not actually non-existent.  It's just OS only privileged.

Not that that makes much difference, as we still trap and emulate (and
set the inherent bit).

Mikey

^ permalink raw reply	[flat|nested] 16+ messages in thread

* Re: [PATCH 3/3] powerpc: Load Monitor Register Tests
  2016-04-11 18:57 ` [PATCH 3/3] powerpc: Load Monitor Register Tests Jack Miller
@ 2016-04-15 10:34   ` Madhavan Srinivasan
  0 siblings, 0 replies; 16+ messages in thread
From: Madhavan Srinivasan @ 2016-04-15 10:34 UTC (permalink / raw)
  To: Jack Miller, linuxppc-dev; +Cc: michael.neuling, michaele



On Tuesday 12 April 2016 12:27 AM, Jack Miller wrote:
> Adds two tests. One is a simple test to ensure that the new registers
> LMRR and LMSER are properly maintained. The other actually uses the
> existing EBB test infrastructure to test that LMRR and LMSER behave as
> documented.
>
> Signed-off-by: Jack Miller <jack@codezen.org>
> ---
>  tools/testing/selftests/powerpc/pmu/ebb/Makefile   |   2 +-
>  tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c  | 144 +++++++++++++++++++++
>  tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h  |  39 ++++++
>  .../selftests/powerpc/pmu/ebb/ebb_lmr_regs.c       |  38 ++++++
>  tools/testing/selftests/powerpc/pmu/ebb/reg.h      |   5 +
>  5 files changed, 227 insertions(+), 1 deletion(-)
>  create mode 100644 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c
>  create mode 100644 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h
>  create mode 100644 tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c
>
> diff --git a/tools/testing/selftests/powerpc/pmu/ebb/Makefile b/tools/testing/selftests/powerpc/pmu/ebb/Makefile
> index 8d2279c4..6b0453e 100644
> --- a/tools/testing/selftests/powerpc/pmu/ebb/Makefile
> +++ b/tools/testing/selftests/powerpc/pmu/ebb/Makefile
> @@ -14,7 +14,7 @@ TEST_PROGS := reg_access_test event_attributes_test cycles_test	\
>  	 fork_cleanup_test ebb_on_child_test			\
>  	 ebb_on_willing_child_test back_to_back_ebbs_test	\
>  	 lost_exception_test no_handler_test			\
> -	 cycles_with_mmcr2_test
> +	 cycles_with_mmcr2_test ebb_lmr ebb_lmr_regs
>  
>  all: $(TEST_PROGS)
>  
> diff --git a/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c
> new file mode 100644
> index 0000000..266062b7
> --- /dev/null
> +++ b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.c
> @@ -0,0 +1,144 @@
> +/*
> + * Copyright 2016, Jack Miller, IBM Corp.
> + * Licensed under GPLv2.
> + */
> +
> +#include <stdlib.h>
> +#include <stdio.h>
> +
> +#include "ebb.h"
> +#include "ebb_lmr.h"
> +
> +#define SIZE		(32 * 1024 * 1024)	/* 32M */
> +#define LM_SIZE		0	/* Smallest encoding, 32M */
> +
> +#define SECTIONS	64	/* 1 per bit in LMSER */
> +#define SECTION_SIZE	(SIZE / SECTIONS)
> +#define SECTION_LONGS   (SECTION_SIZE / sizeof(long))
> +
> +static unsigned long *test_mem;
> +
> +static int lmr_count = 0;
> +
> +void ebb_lmr_handler(void)
> +{
> +	lmr_count++;
> +}
> +
> +void ldmx_full_section(unsigned long *mem, int section)
> +{
> +	unsigned long *ptr;
> +	int i;
> +
> +	for (i = 0; i < SECTION_LONGS; i++) {
> +		ptr = &mem[(SECTION_LONGS * section) + i];
> +		ldmx((unsigned long) &ptr);
> +		ebb_lmr_reset();
> +	}
> +}
> +
> +unsigned long section_masks[] = {
> +	0x8000000000000000,
> +	0xFF00000000000000,
> +	0x0000000F70000000,
> +	0x8000000000000001,
> +	0xF0F0F0F0F0F0F0F0,
> +	0x0F0F0F0F0F0F0F0F,
> +	0x0
> +};
> +
> +int ebb_lmr_section_test(unsigned long *mem)
> +{
> +	unsigned long *mask = section_masks;
> +	int i;
> +
> +	for (; *mask; mask++) {
> +		mtspr(SPRN_LMSER, *mask);
> +		printf("Testing mask 0x%016lx\n", mfspr(SPRN_LMSER));
> +
> +		for (i = 0; i < 64; i++) {
> +			lmr_count = 0;
> +			ldmx_full_section(mem, i);
> +			if (*mask & (1UL << (63 - i)))
> +				FAIL_IF(lmr_count != SECTION_LONGS);
> +			else
> +				FAIL_IF(lmr_count);
> +		}
> +	}
> +
> +	return 0;
> +}
> +
> +int ebb_lmr(void)
> +{
> +	int i;
> +
> +	SKIP_IF(!ebb_is_supported());
> +	SKIP_IF(!lmr_is_supported());
> +
> +	setup_ebb_handler(ebb_lmr_handler);
> +
> +	ebb_global_enable();
> +
> +	FAIL_IF(posix_memalign((void **)&test_mem, SIZE, SIZE) != 0);
> +
> +	mtspr(SPRN_LMSER, 0);
> +
> +	FAIL_IF(mfspr(SPRN_LMSER) != 0);
> +
> +	mtspr(SPRN_LMRR, ((unsigned long)test_mem | LM_SIZE));
> +
> +	FAIL_IF(mfspr(SPRN_LMRR) != ((unsigned long)test_mem | LM_SIZE));
> +
> +	/* Read every single byte to ensure we get no false positives */
> +	for (i = 0; i < SECTIONS; i++)
> +		ldmx_full_section(test_mem, i);
> +
> +	FAIL_IF(lmr_count != 0);

Another possible addition is to have EBB enabled with LMSER
set to zero?


> +
> +	/* Turn on the first section */
> +
> +	mtspr(SPRN_LMSER, (1UL << 63));
> +	FAIL_IF(mfspr(SPRN_LMSER) != (1UL << 63));
> +
> +	/* Enable LM (BESCR) */
> +
> +	mtspr(SPRN_BESCR, mfspr(SPRN_BESCR) | BESCR_LME);
> +	FAIL_IF(!(mfspr(SPRN_BESCR) & BESCR_LME));
> +
> +	ldmx((unsigned long)&test_mem);
> +
> +	FAIL_IF(lmr_count != 1);	// exactly one exception
> +	FAIL_IF(mfspr(SPRN_BESCR) & BESCR_LME);	// LM now disabled
> +	FAIL_IF(!(mfspr(SPRN_BESCR) & BESCR_LMEO));	// occurred bit set
> +
> +	printf("Simple LMR EBB OK\n");
> +
> +	/* This shouldn't cause an EBB since it's been disabled */
> +	ldmx((unsigned long)&test_mem);
> +	FAIL_IF(lmr_count != 1);
> +
> +	printf("LMR disable on EBB OK\n");
> +
> +	ebb_lmr_reset();
> +
> +	/* This should cause an EBB or reset is broken */
> +	ldmx((unsigned long)&test_mem);
> +	FAIL_IF(lmr_count != 2);
> +
> +	printf("LMR reset EBB OK\n");
> +
> +	ebb_lmr_reset();
> +
> +	return ebb_lmr_section_test(test_mem);
> +}
> +
> +int main(void)
> +{
> +	int ret = test_harness(ebb_lmr, "ebb_lmr");
> +
> +	if (test_mem)
> +		free(test_mem);
> +
> +	return ret;
> +}
> diff --git a/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h
> new file mode 100644
> index 0000000..7911756
> --- /dev/null
> +++ b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr.h
> @@ -0,0 +1,39 @@
> +#ifndef _SELFTESTS_POWERPC_PMU_EBB_LMR_H
> +#define _SELFTESTS_POWERPC_PMU_EBB_LMR_H
> +
> +#include "reg.h"
> +
> +#ifndef PPC_FEATURE2_ARCH_3_00
> +#define PPC_FEATURE2_ARCH_3_00 0x00800000
> +#endif
> +
> +#define lmr_is_supported() have_hwcap2(PPC_FEATURE2_ARCH_3_00)
> +
> +static inline void ebb_lmr_reset(void)
> +{
> +	unsigned long bescr = mfspr(SPRN_BESCR);
> +	bescr &= ~(BESCR_LMEO);
> +	bescr |= BESCR_LME;
> +	mtspr(SPRN_BESCR, bescr);
> +}
> +
> +#define LDMX(t, a, b)\
> +    (0x7c00026a |\
> +    ((t & 0x1f) << 21) |\
> +    ((a & 0x1f) << 16) |\
> +    ((b & 0x1f) << 11))
> +
> +static inline unsigned long ldmx(unsigned long address)
> +{
> +	unsigned long ret;
> +
> +	asm volatile ("mr 9, %1\r\n"
> +		      ".long " __stringify(LDMX(9, 0, 9)) "\r\n"
> +		      "mr %0, 9\r\n":"=r"(ret)
> +		      :"r"(address)
> +		      :"r9");
> +
> +	return ret;
> +}
> +
> +#endif
> diff --git a/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c
> new file mode 100644
> index 0000000..d2a4898
> --- /dev/null
> +++ b/tools/testing/selftests/powerpc/pmu/ebb/ebb_lmr_regs.c
> @@ -0,0 +1,38 @@
> +/*
> + * Copyright 2016, Jack Miller, IBM Corp.
> + * Licensed under GPLv2.
> + */
> +
> +#include <stdlib.h>
> +#include <stdio.h>
> +#include <unistd.h>
> +
> +#include "ebb.h"
> +#include "ebb_lmr.h"
> +
> +#define CHECKS 10000
> +
> +int ebb_lmr_regs(void)
> +{
> +	int i;
> +
> +	SKIP_IF(!ebb_is_supported());
> +	SKIP_IF(!lmr_is_supported());
> +
> +	ebb_global_enable();
> +
> +	for (i = 0; i < CHECKS; i++) {
> +		mtspr(SPRN_LMRR, i << 25);	// skip size and rsvd bits
> +		mtspr(SPRN_LMSER, i);
> +
> +		FAIL_IF(mfspr(SPRN_LMRR) != (i << 25));
> +		FAIL_IF(mfspr(SPRN_LMSER) != i);
> +	}
> +
> +	return 0;
> +}
> +
> +int main(void)
> +{
> +	return test_harness(ebb_lmr_regs, "ebb_lmr_regs");
> +}
> diff --git a/tools/testing/selftests/powerpc/pmu/ebb/reg.h b/tools/testing/selftests/powerpc/pmu/ebb/reg.h
> index 5921b0d..0659a7b 100644
> --- a/tools/testing/selftests/powerpc/pmu/ebb/reg.h
> +++ b/tools/testing/selftests/powerpc/pmu/ebb/reg.h
> @@ -34,6 +34,11 @@
>  
>  #define BESCR_PMEO     0x1     /* PMU Event-based exception Occurred */
>  #define BESCR_PME      (0x1ul << 32) /* PMU Event-based exception Enable */
> +#define BESCR_LME      (0x1ul << 34) /* Load Monitor Enable */
> +#define BESCR_LMEO     (0x1ul << 2)  /* Load Monitor Exception Occurred */
> +
> +#define SPRN_LMRR      813     /* Load Monitor Region Register */
> +#define SPRN_LMSER     814     /* Load Monitor Section Enable Register */
>  
>  #define SPRN_PMC1      771
>  #define SPRN_PMC2      772

^ permalink raw reply	[flat|nested] 16+ messages in thread

* [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-18 21:08 ` [v3] P9 ldmx support Jack Miller
@ 2016-04-18 21:08   ` Jack Miller
  0 siblings, 0 replies; 16+ messages in thread
From: Jack Miller @ 2016-04-18 21:08 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: mpe, mikey, anton

Previously we just saved the FSCR, but only restored it in some
settings, and never copied it thread to thread. This patch always
restores the FSCR and formalizes new threads inheriting its setting so
that later we can manipulate FSCR bits in start_thread.

Signed-off-by: Jack Miller <jack@codezen.org>
---
 arch/powerpc/kernel/process.c | 14 +++++++-------
 1 file changed, 7 insertions(+), 7 deletions(-)

diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index b8500b4..00bf6f5 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -1019,18 +1019,12 @@ static inline void restore_sprs(struct thread_struct *old_thread,
 #ifdef CONFIG_PPC_BOOK3S_64
 	if (cpu_has_feature(CPU_FTR_DSCR)) {
 		u64 dscr = get_paca()->dscr_default;
-		u64 fscr = old_thread->fscr & ~FSCR_DSCR;
 
-		if (new_thread->dscr_inherit) {
+		if (new_thread->dscr_inherit)
 			dscr = new_thread->dscr;
-			fscr |= FSCR_DSCR;
-		}
 
 		if (old_thread->dscr != dscr)
 			mtspr(SPRN_DSCR, dscr);
-
-		if (old_thread->fscr != fscr)
-			mtspr(SPRN_FSCR, fscr);
 	}
 
 	if (cpu_has_feature(CPU_FTR_ARCH_207S)) {
@@ -1041,6 +1035,9 @@ static inline void restore_sprs(struct thread_struct *old_thread,
 		if (old_thread->ebbrr != new_thread->ebbrr)
 			mtspr(SPRN_EBBRR, new_thread->ebbrr);
 
+		if (old_thread->fscr != new_thread->fscr)
+			mtspr(SPRN_FSCR, new_thread->fscr);
+
 		if (old_thread->tar != new_thread->tar)
 			mtspr(SPRN_TAR, new_thread->tar);
 	}
@@ -1478,6 +1475,9 @@ int copy_thread(unsigned long clone_flags, unsigned long usp,
 	}
 	if (cpu_has_feature(CPU_FTR_HAS_PPR))
 		p->thread.ppr = INIT_PPR;
+
+	if (cpu_has_feature(CPU_FTR_ARCH_207S))
+		p->thread.fscr = mfspr(SPRN_FSCR);
 #endif
 	kregs->nip = ppc_function_entry(f);
 	return 0;
-- 
2.8.0

^ permalink raw reply related	[flat|nested] 16+ messages in thread

* [PATCH 1/3] powerpc: Complete FSCR context switch
  2016-04-18 19:07 [v2] " Jack Miller
@ 2016-04-18 19:08 ` Jack Miller
  0 siblings, 0 replies; 16+ messages in thread
From: Jack Miller @ 2016-04-18 19:08 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: mpe, mikey, anton

Previously we just saved the FSCR, but only restored it in some
settings, and never copied it thread to thread. This patch always
restores the FSCR and formalizes new threads inheriting its setting so
that later we can manipulate FSCR bits in start_thread.

Signed-off-by: Jack Miller <jack@codezen.org>
---
 arch/powerpc/kernel/process.c | 14 +++++++-------
 1 file changed, 7 insertions(+), 7 deletions(-)

diff --git a/arch/powerpc/kernel/process.c b/arch/powerpc/kernel/process.c
index b8500b4..00bf6f5 100644
--- a/arch/powerpc/kernel/process.c
+++ b/arch/powerpc/kernel/process.c
@@ -1019,18 +1019,12 @@ static inline void restore_sprs(struct thread_struct *old_thread,
 #ifdef CONFIG_PPC_BOOK3S_64
 	if (cpu_has_feature(CPU_FTR_DSCR)) {
 		u64 dscr = get_paca()->dscr_default;
-		u64 fscr = old_thread->fscr & ~FSCR_DSCR;
 
-		if (new_thread->dscr_inherit) {
+		if (new_thread->dscr_inherit)
 			dscr = new_thread->dscr;
-			fscr |= FSCR_DSCR;
-		}
 
 		if (old_thread->dscr != dscr)
 			mtspr(SPRN_DSCR, dscr);
-
-		if (old_thread->fscr != fscr)
-			mtspr(SPRN_FSCR, fscr);
 	}
 
 	if (cpu_has_feature(CPU_FTR_ARCH_207S)) {
@@ -1041,6 +1035,9 @@ static inline void restore_sprs(struct thread_struct *old_thread,
 		if (old_thread->ebbrr != new_thread->ebbrr)
 			mtspr(SPRN_EBBRR, new_thread->ebbrr);
 
+		if (old_thread->fscr != new_thread->fscr)
+			mtspr(SPRN_FSCR, new_thread->fscr);
+
 		if (old_thread->tar != new_thread->tar)
 			mtspr(SPRN_TAR, new_thread->tar);
 	}
@@ -1478,6 +1475,9 @@ int copy_thread(unsigned long clone_flags, unsigned long usp,
 	}
 	if (cpu_has_feature(CPU_FTR_HAS_PPR))
 		p->thread.ppr = INIT_PPR;
+
+	if (cpu_has_feature(CPU_FTR_ARCH_207S))
+		p->thread.fscr = mfspr(SPRN_FSCR);
 #endif
 	kregs->nip = ppc_function_entry(f);
 	return 0;
-- 
2.8.0

^ permalink raw reply related	[flat|nested] 16+ messages in thread

end of thread, other threads:[~2016-04-18 21:09 UTC | newest]

Thread overview: 16+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2016-04-11 18:57 [RFC] P9 ldmx support Jack Miller
2016-04-11 18:57 ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller
2016-04-12 23:42   ` [1/3] " Michael Ellerman
2016-04-13 10:51   ` [PATCH 1/3] " Anton Blanchard
2016-04-13 17:52     ` Jack Miller
2016-04-13 23:49       ` Michael Neuling
2016-04-14 18:39         ` Jack Miller
2016-04-14 23:11           ` Michael Neuling
2016-04-11 18:57 ` [PATCH 2/3] powerpc: Load Monitor Register Support Jack Miller
2016-04-12  5:40   ` Segher Boessenkool
2016-04-13 17:39     ` Jack Miller
2016-04-11 18:57 ` [PATCH 3/3] powerpc: Load Monitor Register Tests Jack Miller
2016-04-15 10:34   ` Madhavan Srinivasan
2016-04-12  1:05 ` [RFC] P9 ldmx support Michael Neuling
2016-04-18 19:07 [v2] " Jack Miller
2016-04-18 19:08 ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller
2016-04-18 20:47 [PATCH 2/3] powerpc: Load Monitor Register Support kbuild test robot
2016-04-18 21:08 ` [v3] P9 ldmx support Jack Miller
2016-04-18 21:08   ` [PATCH 1/3] powerpc: Complete FSCR context switch Jack Miller

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.