diff options
| -rw-r--r-- | Documentation/accelerators/ocxl.rst | 5 | ||||
| -rw-r--r-- | arch/powerpc/boot/Makefile | 3 | ||||
| -rw-r--r-- | arch/powerpc/include/asm/book3s/64/mmu.h | 3 | ||||
| -rw-r--r-- | arch/powerpc/include/asm/book3s/64/tlbflush-radix.h | 3 | ||||
| -rw-r--r-- | arch/powerpc/include/asm/cputable.h | 4 | ||||
| -rw-r--r-- | arch/powerpc/include/asm/mmu_context.h | 18 | ||||
| -rw-r--r-- | arch/powerpc/kernel/dt_cpu_ftrs.c | 7 | ||||
| -rw-r--r-- | arch/powerpc/kernel/exceptions-64s.S | 2 | ||||
| -rw-r--r-- | arch/powerpc/kernel/irq.c | 8 | ||||
| -rw-r--r-- | arch/powerpc/kernel/prom_init.c | 1 | ||||
| -rw-r--r-- | arch/powerpc/kvm/book3s_64_mmu_radix.c | 3 | ||||
| -rw-r--r-- | arch/powerpc/kvm/book3s_hv_rm_mmu.c | 11 | ||||
| -rw-r--r-- | arch/powerpc/mm/hash_native_64.c | 16 | ||||
| -rw-r--r-- | arch/powerpc/mm/mmu_context_book3s64.c | 1 | ||||
| -rw-r--r-- | arch/powerpc/mm/pgtable_64.c | 1 | ||||
| -rw-r--r-- | arch/powerpc/mm/tlb-radix.c | 169 | ||||
| -rw-r--r-- | drivers/misc/ocxl/file.c | 27 | ||||
| -rw-r--r-- | include/uapi/misc/ocxl.h | 17 | ||||
| -rw-r--r-- | tools/testing/selftests/powerpc/mm/subpage_prot.c | 14 | ||||
| -rw-r--r-- | tools/testing/selftests/powerpc/tm/Makefile | 2 | ||||
| -rw-r--r-- | tools/testing/selftests/powerpc/tm/tm-trap.c | 2 |
21 files changed, 223 insertions, 94 deletions
diff --git a/Documentation/accelerators/ocxl.rst b/Documentation/accelerators/ocxl.rst index 4f7af841d935..ddcc58d01cfb 100644 --- a/Documentation/accelerators/ocxl.rst +++ b/Documentation/accelerators/ocxl.rst | |||
| @@ -152,6 +152,11 @@ OCXL_IOCTL_IRQ_SET_FD: | |||
| 152 | Associate an event fd to an AFU interrupt so that the user process | 152 | Associate an event fd to an AFU interrupt so that the user process |
| 153 | can be notified when the AFU sends an interrupt. | 153 | can be notified when the AFU sends an interrupt. |
| 154 | 154 | ||
| 155 | OCXL_IOCTL_GET_METADATA: | ||
| 156 | |||
| 157 | Obtains configuration information from the card, such at the size of | ||
| 158 | MMIO areas, the AFU version, and the PASID for the current context. | ||
| 159 | |||
| 155 | 160 | ||
| 156 | mmap | 161 | mmap |
| 157 | ---- | 162 | ---- |
diff --git a/arch/powerpc/boot/Makefile b/arch/powerpc/boot/Makefile index ef6549e57157..26d5d2a5b8e9 100644 --- a/arch/powerpc/boot/Makefile +++ b/arch/powerpc/boot/Makefile | |||
| @@ -101,7 +101,8 @@ $(addprefix $(obj)/,$(zlib-y)): \ | |||
| 101 | libfdt := fdt.c fdt_ro.c fdt_wip.c fdt_sw.c fdt_rw.c fdt_strerror.c | 101 | libfdt := fdt.c fdt_ro.c fdt_wip.c fdt_sw.c fdt_rw.c fdt_strerror.c |
| 102 | libfdtheader := fdt.h libfdt.h libfdt_internal.h | 102 | libfdtheader := fdt.h libfdt.h libfdt_internal.h |
| 103 | 103 | ||
| 104 | $(addprefix $(obj)/,$(libfdt) libfdt-wrapper.o simpleboot.o epapr.o opal.o): \ | 104 | $(addprefix $(obj)/,$(libfdt) libfdt-wrapper.o simpleboot.o epapr.o opal.o \ |
| 105 | treeboot-akebono.o treeboot-currituck.o treeboot-iss4xx.o): \ | ||
| 105 | $(addprefix $(obj)/,$(libfdtheader)) | 106 | $(addprefix $(obj)/,$(libfdtheader)) |
| 106 | 107 | ||
| 107 | src-wlib-y := string.S crt0.S stdio.c decompress.c main.c \ | 108 | src-wlib-y := string.S crt0.S stdio.c decompress.c main.c \ |
diff --git a/arch/powerpc/include/asm/book3s/64/mmu.h b/arch/powerpc/include/asm/book3s/64/mmu.h index 777778579305..c8c836e8ad1b 100644 --- a/arch/powerpc/include/asm/book3s/64/mmu.h +++ b/arch/powerpc/include/asm/book3s/64/mmu.h | |||
| @@ -97,6 +97,9 @@ typedef struct { | |||
| 97 | /* Number of bits in the mm_cpumask */ | 97 | /* Number of bits in the mm_cpumask */ |
| 98 | atomic_t active_cpus; | 98 | atomic_t active_cpus; |
| 99 | 99 | ||
| 100 | /* Number of users of the external (Nest) MMU */ | ||
| 101 | atomic_t copros; | ||
| 102 | |||
| 100 | /* NPU NMMU context */ | 103 | /* NPU NMMU context */ |
| 101 | struct npu_context *npu_context; | 104 | struct npu_context *npu_context; |
| 102 | 105 | ||
diff --git a/arch/powerpc/include/asm/book3s/64/tlbflush-radix.h b/arch/powerpc/include/asm/book3s/64/tlbflush-radix.h index 8eea90f80e45..19b45ba6caf9 100644 --- a/arch/powerpc/include/asm/book3s/64/tlbflush-radix.h +++ b/arch/powerpc/include/asm/book3s/64/tlbflush-radix.h | |||
| @@ -47,9 +47,6 @@ extern void radix__flush_tlb_page_psize(struct mm_struct *mm, unsigned long vmad | |||
| 47 | #endif | 47 | #endif |
| 48 | extern void radix__flush_tlb_pwc(struct mmu_gather *tlb, unsigned long addr); | 48 | extern void radix__flush_tlb_pwc(struct mmu_gather *tlb, unsigned long addr); |
| 49 | extern void radix__flush_tlb_collapsed_pmd(struct mm_struct *mm, unsigned long addr); | 49 | extern void radix__flush_tlb_collapsed_pmd(struct mm_struct *mm, unsigned long addr); |
| 50 | extern void radix__flush_tlb_lpid_va(unsigned long lpid, unsigned long gpa, | ||
| 51 | unsigned long page_size); | ||
| 52 | extern void radix__flush_tlb_lpid(unsigned long lpid); | ||
| 53 | extern void radix__flush_tlb_all(void); | 50 | extern void radix__flush_tlb_all(void); |
| 54 | extern void radix__flush_tlb_pte_p9_dd1(unsigned long old_pte, struct mm_struct *mm, | 51 | extern void radix__flush_tlb_pte_p9_dd1(unsigned long old_pte, struct mm_struct *mm, |
| 55 | unsigned long address); | 52 | unsigned long address); |
diff --git a/arch/powerpc/include/asm/cputable.h b/arch/powerpc/include/asm/cputable.h index 734ff976b82f..66eba1e0007b 100644 --- a/arch/powerpc/include/asm/cputable.h +++ b/arch/powerpc/include/asm/cputable.h | |||
| @@ -215,6 +215,7 @@ static inline void cpu_feature_keys_init(void) { } | |||
| 215 | #define CPU_FTR_POWER9_DD2_1 LONG_ASM_CONST(0x0000080000000000) | 215 | #define CPU_FTR_POWER9_DD2_1 LONG_ASM_CONST(0x0000080000000000) |
| 216 | #define CPU_FTR_P9_TM_HV_ASSIST LONG_ASM_CONST(0x0000100000000000) | 216 | #define CPU_FTR_P9_TM_HV_ASSIST LONG_ASM_CONST(0x0000100000000000) |
| 217 | #define CPU_FTR_P9_TM_XER_SO_BUG LONG_ASM_CONST(0x0000200000000000) | 217 | #define CPU_FTR_P9_TM_XER_SO_BUG LONG_ASM_CONST(0x0000200000000000) |
| 218 | #define CPU_FTR_P9_TLBIE_BUG LONG_ASM_CONST(0x0000400000000000) | ||
| 218 | 219 | ||
| 219 | #ifndef __ASSEMBLY__ | 220 | #ifndef __ASSEMBLY__ |
| 220 | 221 | ||
| @@ -465,7 +466,8 @@ static inline void cpu_feature_keys_init(void) { } | |||
| 465 | CPU_FTR_STCX_CHECKS_ADDRESS | CPU_FTR_POPCNTB | CPU_FTR_POPCNTD | \ | 466 | CPU_FTR_STCX_CHECKS_ADDRESS | CPU_FTR_POPCNTB | CPU_FTR_POPCNTD | \ |
| 466 | CPU_FTR_CFAR | CPU_FTR_HVMODE | CPU_FTR_VMX_COPY | \ | 467 | CPU_FTR_CFAR | CPU_FTR_HVMODE | CPU_FTR_VMX_COPY | \ |
| 467 | CPU_FTR_DBELL | CPU_FTR_HAS_PPR | CPU_FTR_ARCH_207S | \ | 468 | CPU_FTR_DBELL | CPU_FTR_HAS_PPR | CPU_FTR_ARCH_207S | \ |
| 468 | CPU_FTR_TM_COMP | CPU_FTR_ARCH_300 | CPU_FTR_PKEY) | 469 | CPU_FTR_TM_COMP | CPU_FTR_ARCH_300 | CPU_FTR_PKEY | \ |
| 470 | CPU_FTR_P9_TLBIE_BUG) | ||
| 469 | #define CPU_FTRS_POWER9_DD1 ((CPU_FTRS_POWER9 | CPU_FTR_POWER9_DD1) & \ | 471 | #define CPU_FTRS_POWER9_DD1 ((CPU_FTRS_POWER9 | CPU_FTR_POWER9_DD1) & \ |
| 470 | (~CPU_FTR_SAO)) | 472 | (~CPU_FTR_SAO)) |
| 471 | #define CPU_FTRS_POWER9_DD2_0 CPU_FTRS_POWER9 | 473 | #define CPU_FTRS_POWER9_DD2_0 CPU_FTRS_POWER9 |
diff --git a/arch/powerpc/include/asm/mmu_context.h b/arch/powerpc/include/asm/mmu_context.h index 051b3d63afe3..3a15b6db9501 100644 --- a/arch/powerpc/include/asm/mmu_context.h +++ b/arch/powerpc/include/asm/mmu_context.h | |||
| @@ -92,15 +92,23 @@ static inline void dec_mm_active_cpus(struct mm_struct *mm) | |||
| 92 | static inline void mm_context_add_copro(struct mm_struct *mm) | 92 | static inline void mm_context_add_copro(struct mm_struct *mm) |
| 93 | { | 93 | { |
| 94 | /* | 94 | /* |
| 95 | * On hash, should only be called once over the lifetime of | 95 | * If any copro is in use, increment the active CPU count |
| 96 | * the context, as we can't decrement the active cpus count | 96 | * in order to force TLB invalidations to be global as to |
| 97 | * and flush properly for the time being. | 97 | * propagate to the Nest MMU. |
| 98 | */ | 98 | */ |
| 99 | inc_mm_active_cpus(mm); | 99 | if (atomic_inc_return(&mm->context.copros) == 1) |
| 100 | inc_mm_active_cpus(mm); | ||
| 100 | } | 101 | } |
| 101 | 102 | ||
| 102 | static inline void mm_context_remove_copro(struct mm_struct *mm) | 103 | static inline void mm_context_remove_copro(struct mm_struct *mm) |
| 103 | { | 104 | { |
| 105 | int c; | ||
| 106 | |||
| 107 | c = atomic_dec_if_positive(&mm->context.copros); | ||
| 108 | |||
| 109 | /* Detect imbalance between add and remove */ | ||
| 110 | WARN_ON(c < 0); | ||
| 111 | |||
| 104 | /* | 112 | /* |
| 105 | * Need to broadcast a global flush of the full mm before | 113 | * Need to broadcast a global flush of the full mm before |
| 106 | * decrementing active_cpus count, as the next TLBI may be | 114 | * decrementing active_cpus count, as the next TLBI may be |
| @@ -111,7 +119,7 @@ static inline void mm_context_remove_copro(struct mm_struct *mm) | |||
| 111 | * for the time being. Invalidations will remain global if | 119 | * for the time being. Invalidations will remain global if |
| 112 | * used on hash. | 120 | * used on hash. |
| 113 | */ | 121 | */ |
| 114 | if (radix_enabled()) { | 122 | if (c == 0 && radix_enabled()) { |
| 115 | flush_all_mm(mm); | 123 | flush_all_mm(mm); |
| 116 | dec_mm_active_cpus(mm); | 124 | dec_mm_active_cpus(mm); |
| 117 | } | 125 | } |
diff --git a/arch/powerpc/kernel/dt_cpu_ftrs.c b/arch/powerpc/kernel/dt_cpu_ftrs.c index 0af2c5dc5162..4313ff07edca 100644 --- a/arch/powerpc/kernel/dt_cpu_ftrs.c +++ b/arch/powerpc/kernel/dt_cpu_ftrs.c | |||
| @@ -714,8 +714,10 @@ static __init void cpufeatures_cpu_quirks(void) | |||
| 714 | cur_cpu_spec->cpu_features |= CPU_FTR_P9_TM_HV_ASSIST | | 714 | cur_cpu_spec->cpu_features |= CPU_FTR_P9_TM_HV_ASSIST | |
| 715 | CPU_FTR_P9_TM_XER_SO_BUG; | 715 | CPU_FTR_P9_TM_XER_SO_BUG; |
| 716 | 716 | ||
| 717 | if ((version & 0xffff0000) == 0x004e0000) | 717 | if ((version & 0xffff0000) == 0x004e0000) { |
| 718 | cur_cpu_spec->cpu_features &= ~(CPU_FTR_DAWR); | 718 | cur_cpu_spec->cpu_features &= ~(CPU_FTR_DAWR); |
| 719 | cur_cpu_spec->cpu_features |= CPU_FTR_P9_TLBIE_BUG; | ||
| 720 | } | ||
| 719 | } | 721 | } |
| 720 | 722 | ||
| 721 | static void __init cpufeatures_setup_finished(void) | 723 | static void __init cpufeatures_setup_finished(void) |
| @@ -727,6 +729,9 @@ static void __init cpufeatures_setup_finished(void) | |||
| 727 | cur_cpu_spec->cpu_features |= CPU_FTR_HVMODE; | 729 | cur_cpu_spec->cpu_features |= CPU_FTR_HVMODE; |
| 728 | } | 730 | } |
| 729 | 731 | ||
| 732 | /* Make sure powerpc_base_platform is non-NULL */ | ||
| 733 | powerpc_base_platform = cur_cpu_spec->platform; | ||
| 734 | |||
| 730 | system_registers.lpcr = mfspr(SPRN_LPCR); | 735 | system_registers.lpcr = mfspr(SPRN_LPCR); |
| 731 | system_registers.hfscr = mfspr(SPRN_HFSCR); | 736 | system_registers.hfscr = mfspr(SPRN_HFSCR); |
| 732 | system_registers.fscr = mfspr(SPRN_FSCR); | 737 | system_registers.fscr = mfspr(SPRN_FSCR); |
diff --git a/arch/powerpc/kernel/exceptions-64s.S b/arch/powerpc/kernel/exceptions-64s.S index a19fbaa8e873..6bee20c43feb 100644 --- a/arch/powerpc/kernel/exceptions-64s.S +++ b/arch/powerpc/kernel/exceptions-64s.S | |||
| @@ -706,7 +706,7 @@ EXC_COMMON_BEGIN(bad_addr_slb) | |||
| 706 | ld r3, PACA_EXSLB+EX_DAR(r13) | 706 | ld r3, PACA_EXSLB+EX_DAR(r13) |
| 707 | std r3, _DAR(r1) | 707 | std r3, _DAR(r1) |
| 708 | beq cr6, 2f | 708 | beq cr6, 2f |
| 709 | li r10, 0x480 /* fix trap number for I-SLB miss */ | 709 | li r10, 0x481 /* fix trap number for I-SLB miss */ |
| 710 | std r10, _TRAP(r1) | 710 | std r10, _TRAP(r1) |
| 711 | 2: bl save_nvgprs | 711 | 2: bl save_nvgprs |
| 712 | addi r3, r1, STACK_FRAME_OVERHEAD | 712 | addi r3, r1, STACK_FRAME_OVERHEAD |
diff --git a/arch/powerpc/kernel/irq.c b/arch/powerpc/kernel/irq.c index f88038847790..061aa0f47bb1 100644 --- a/arch/powerpc/kernel/irq.c +++ b/arch/powerpc/kernel/irq.c | |||
| @@ -476,6 +476,14 @@ void force_external_irq_replay(void) | |||
| 476 | */ | 476 | */ |
| 477 | WARN_ON(!arch_irqs_disabled()); | 477 | WARN_ON(!arch_irqs_disabled()); |
| 478 | 478 | ||
| 479 | /* | ||
| 480 | * Interrupts must always be hard disabled before irq_happened is | ||
| 481 | * modified (to prevent lost update in case of interrupt between | ||
| 482 | * load and store). | ||
| 483 | */ | ||
| 484 | __hard_irq_disable(); | ||
| 485 | local_paca->irq_happened |= PACA_IRQ_HARD_DIS; | ||
| 486 | |||
| 479 | /* Indicate in the PACA that we have an interrupt to replay */ | 487 | /* Indicate in the PACA that we have an interrupt to replay */ |
| 480 | local_paca->irq_happened |= PACA_IRQ_EE; | 488 | local_paca->irq_happened |= PACA_IRQ_EE; |
| 481 | } | 489 | } |
diff --git a/arch/powerpc/kernel/prom_init.c b/arch/powerpc/kernel/prom_init.c index 8ca3f4c915e3..0323e073341d 100644 --- a/arch/powerpc/kernel/prom_init.c +++ b/arch/powerpc/kernel/prom_init.c | |||
| @@ -874,7 +874,6 @@ struct ibm_arch_vec __cacheline_aligned ibm_architecture_vec = { | |||
| 874 | .mmu = 0, | 874 | .mmu = 0, |
| 875 | .hash_ext = 0, | 875 | .hash_ext = 0, |
| 876 | .radix_ext = 0, | 876 | .radix_ext = 0, |
| 877 | .byte22 = 0, | ||
| 878 | }, | 877 | }, |
| 879 | 878 | ||
| 880 | /* option vector 6: IBM PAPR hints */ | 879 | /* option vector 6: IBM PAPR hints */ |
diff --git a/arch/powerpc/kvm/book3s_64_mmu_radix.c b/arch/powerpc/kvm/book3s_64_mmu_radix.c index 0c854816e653..0837b9738d76 100644 --- a/arch/powerpc/kvm/book3s_64_mmu_radix.c +++ b/arch/powerpc/kvm/book3s_64_mmu_radix.c | |||
| @@ -157,6 +157,9 @@ static void kvmppc_radix_tlbie_page(struct kvm *kvm, unsigned long addr, | |||
| 157 | asm volatile("ptesync": : :"memory"); | 157 | asm volatile("ptesync": : :"memory"); |
| 158 | asm volatile(PPC_TLBIE_5(%0, %1, 0, 0, 1) | 158 | asm volatile(PPC_TLBIE_5(%0, %1, 0, 0, 1) |
| 159 | : : "r" (addr), "r" (kvm->arch.lpid) : "memory"); | 159 | : : "r" (addr), "r" (kvm->arch.lpid) : "memory"); |
| 160 | if (cpu_has_feature(CPU_FTR_P9_TLBIE_BUG)) | ||
| 161 | asm volatile(PPC_TLBIE_5(%0, %1, 0, 0, 1) | ||
| 162 | : : "r" (addr), "r" (kvm->arch.lpid) : "memory"); | ||
| 160 | asm volatile("ptesync": : :"memory"); | 163 | asm volatile("ptesync": : :"memory"); |
| 161 | } | 164 | } |
| 162 | 165 | ||
diff --git a/arch/powerpc/kvm/book3s_hv_rm_mmu.c b/arch/powerpc/kvm/book3s_hv_rm_mmu.c index 8888e625a999..e1c083fbe434 100644 --- a/arch/powerpc/kvm/book3s_hv_rm_mmu.c +++ b/arch/powerpc/kvm/book3s_hv_rm_mmu.c | |||
| @@ -473,6 +473,17 @@ static void do_tlbies(struct kvm *kvm, unsigned long *rbvalues, | |||
| 473 | trace_tlbie(kvm->arch.lpid, 0, rbvalues[i], | 473 | trace_tlbie(kvm->arch.lpid, 0, rbvalues[i], |
| 474 | kvm->arch.lpid, 0, 0, 0); | 474 | kvm->arch.lpid, 0, 0, 0); |
| 475 | } | 475 | } |
| 476 | |||
| 477 | if (cpu_has_feature(CPU_FTR_P9_TLBIE_BUG)) { | ||
| 478 | /* | ||
| 479 | * Need the extra ptesync to make sure we don't | ||
| 480 | * re-order the tlbie | ||
| 481 | */ | ||
| 482 | asm volatile("ptesync": : :"memory"); | ||
| 483 | asm volatile(PPC_TLBIE_5(%0,%1,0,0,0) : : | ||
| 484 | "r" (rbvalues[0]), "r" (kvm->arch.lpid)); | ||
| 485 | } | ||
| 486 | |||
| 476 | asm volatile("eieio; tlbsync; ptesync" : : : "memory"); | 487 | asm volatile("eieio; tlbsync; ptesync" : : : "memory"); |
| 477 | kvm->arch.tlbie_lock = 0; | 488 | kvm->arch.tlbie_lock = 0; |
| 478 | } else { | 489 | } else { |
diff --git a/arch/powerpc/mm/hash_native_64.c b/arch/powerpc/mm/hash_native_64.c index 993842f1ed60..1d049c78c82a 100644 --- a/arch/powerpc/mm/hash_native_64.c +++ b/arch/powerpc/mm/hash_native_64.c | |||
| @@ -201,6 +201,15 @@ static inline unsigned long ___tlbie(unsigned long vpn, int psize, | |||
| 201 | return va; | 201 | return va; |
| 202 | } | 202 | } |
| 203 | 203 | ||
| 204 | static inline void fixup_tlbie(unsigned long vpn, int psize, int apsize, int ssize) | ||
| 205 | { | ||
| 206 | if (cpu_has_feature(CPU_FTR_P9_TLBIE_BUG)) { | ||
| 207 | /* Need the extra ptesync to ensure we don't reorder tlbie*/ | ||
| 208 | asm volatile("ptesync": : :"memory"); | ||
| 209 | ___tlbie(vpn, psize, apsize, ssize); | ||
| 210 | } | ||
| 211 | } | ||
| 212 | |||
| 204 | static inline void __tlbie(unsigned long vpn, int psize, int apsize, int ssize) | 213 | static inline void __tlbie(unsigned long vpn, int psize, int apsize, int ssize) |
| 205 | { | 214 | { |
| 206 | unsigned long rb; | 215 | unsigned long rb; |
| @@ -278,6 +287,7 @@ static inline void tlbie(unsigned long vpn, int psize, int apsize, | |||
| 278 | asm volatile("ptesync": : :"memory"); | 287 | asm volatile("ptesync": : :"memory"); |
| 279 | } else { | 288 | } else { |
| 280 | __tlbie(vpn, psize, apsize, ssize); | 289 | __tlbie(vpn, psize, apsize, ssize); |
| 290 | fixup_tlbie(vpn, psize, apsize, ssize); | ||
| 281 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | 291 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); |
| 282 | } | 292 | } |
| 283 | if (lock_tlbie && !use_local) | 293 | if (lock_tlbie && !use_local) |
| @@ -771,7 +781,7 @@ static void native_hpte_clear(void) | |||
| 771 | */ | 781 | */ |
| 772 | static void native_flush_hash_range(unsigned long number, int local) | 782 | static void native_flush_hash_range(unsigned long number, int local) |
| 773 | { | 783 | { |
| 774 | unsigned long vpn; | 784 | unsigned long vpn = 0; |
| 775 | unsigned long hash, index, hidx, shift, slot; | 785 | unsigned long hash, index, hidx, shift, slot; |
| 776 | struct hash_pte *hptep; | 786 | struct hash_pte *hptep; |
| 777 | unsigned long hpte_v; | 787 | unsigned long hpte_v; |
| @@ -843,6 +853,10 @@ static void native_flush_hash_range(unsigned long number, int local) | |||
| 843 | __tlbie(vpn, psize, psize, ssize); | 853 | __tlbie(vpn, psize, psize, ssize); |
| 844 | } pte_iterate_hashed_end(); | 854 | } pte_iterate_hashed_end(); |
| 845 | } | 855 | } |
| 856 | /* | ||
| 857 | * Just do one more with the last used values. | ||
| 858 | */ | ||
| 859 | fixup_tlbie(vpn, psize, psize, ssize); | ||
| 846 | asm volatile("eieio; tlbsync; ptesync":::"memory"); | 860 | asm volatile("eieio; tlbsync; ptesync":::"memory"); |
| 847 | 861 | ||
| 848 | if (lock_tlbie) | 862 | if (lock_tlbie) |
diff --git a/arch/powerpc/mm/mmu_context_book3s64.c b/arch/powerpc/mm/mmu_context_book3s64.c index 80acad52b006..422be81bf69f 100644 --- a/arch/powerpc/mm/mmu_context_book3s64.c +++ b/arch/powerpc/mm/mmu_context_book3s64.c | |||
| @@ -166,6 +166,7 @@ int init_new_context(struct task_struct *tsk, struct mm_struct *mm) | |||
| 166 | mm_iommu_init(mm); | 166 | mm_iommu_init(mm); |
| 167 | #endif | 167 | #endif |
| 168 | atomic_set(&mm->context.active_cpus, 0); | 168 | atomic_set(&mm->context.active_cpus, 0); |
| 169 | atomic_set(&mm->context.copros, 0); | ||
| 169 | 170 | ||
| 170 | return 0; | 171 | return 0; |
| 171 | } | 172 | } |
diff --git a/arch/powerpc/mm/pgtable_64.c b/arch/powerpc/mm/pgtable_64.c index 28c980eb4422..adf469f312f2 100644 --- a/arch/powerpc/mm/pgtable_64.c +++ b/arch/powerpc/mm/pgtable_64.c | |||
| @@ -481,6 +481,7 @@ void mmu_partition_table_set_entry(unsigned int lpid, unsigned long dw0, | |||
| 481 | "r" (TLBIEL_INVAL_SET_LPID), "r" (lpid)); | 481 | "r" (TLBIEL_INVAL_SET_LPID), "r" (lpid)); |
| 482 | trace_tlbie(lpid, 0, TLBIEL_INVAL_SET_LPID, lpid, 2, 0, 0); | 482 | trace_tlbie(lpid, 0, TLBIEL_INVAL_SET_LPID, lpid, 2, 0, 0); |
| 483 | } | 483 | } |
| 484 | /* do we need fixup here ?*/ | ||
| 484 | asm volatile("eieio; tlbsync; ptesync" : : : "memory"); | 485 | asm volatile("eieio; tlbsync; ptesync" : : : "memory"); |
| 485 | } | 486 | } |
| 486 | EXPORT_SYMBOL_GPL(mmu_partition_table_set_entry); | 487 | EXPORT_SYMBOL_GPL(mmu_partition_table_set_entry); |
diff --git a/arch/powerpc/mm/tlb-radix.c b/arch/powerpc/mm/tlb-radix.c index 001c1f6458b6..291eab4ed7cd 100644 --- a/arch/powerpc/mm/tlb-radix.c +++ b/arch/powerpc/mm/tlb-radix.c | |||
| @@ -119,6 +119,49 @@ static inline void __tlbie_pid(unsigned long pid, unsigned long ric) | |||
| 119 | trace_tlbie(0, 0, rb, rs, ric, prs, r); | 119 | trace_tlbie(0, 0, rb, rs, ric, prs, r); |
| 120 | } | 120 | } |
| 121 | 121 | ||
| 122 | static inline void __tlbiel_va(unsigned long va, unsigned long pid, | ||
| 123 | unsigned long ap, unsigned long ric) | ||
| 124 | { | ||
| 125 | unsigned long rb,rs,prs,r; | ||
| 126 | |||
| 127 | rb = va & ~(PPC_BITMASK(52, 63)); | ||
| 128 | rb |= ap << PPC_BITLSHIFT(58); | ||
| 129 | rs = pid << PPC_BITLSHIFT(31); | ||
| 130 | prs = 1; /* process scoped */ | ||
| 131 | r = 1; /* radix format */ | ||
| 132 | |||
| 133 | asm volatile(PPC_TLBIEL(%0, %4, %3, %2, %1) | ||
| 134 | : : "r"(rb), "i"(r), "i"(prs), "i"(ric), "r"(rs) : "memory"); | ||
| 135 | trace_tlbie(0, 1, rb, rs, ric, prs, r); | ||
| 136 | } | ||
| 137 | |||
| 138 | static inline void __tlbie_va(unsigned long va, unsigned long pid, | ||
| 139 | unsigned long ap, unsigned long ric) | ||
| 140 | { | ||
| 141 | unsigned long rb,rs,prs,r; | ||
| 142 | |||
| 143 | rb = va & ~(PPC_BITMASK(52, 63)); | ||
| 144 | rb |= ap << PPC_BITLSHIFT(58); | ||
| 145 | rs = pid << PPC_BITLSHIFT(31); | ||
| 146 | prs = 1; /* process scoped */ | ||
| 147 | r = 1; /* radix format */ | ||
| 148 | |||
| 149 | asm volatile(PPC_TLBIE_5(%0, %4, %3, %2, %1) | ||
| 150 | : : "r"(rb), "i"(r), "i"(prs), "i"(ric), "r"(rs) : "memory"); | ||
| 151 | trace_tlbie(0, 0, rb, rs, ric, prs, r); | ||
| 152 | } | ||
| 153 | |||
| 154 | static inline void fixup_tlbie(void) | ||
| 155 | { | ||
| 156 | unsigned long pid = 0; | ||
| 157 | unsigned long va = ((1UL << 52) - 1); | ||
| 158 | |||
| 159 | if (cpu_has_feature(CPU_FTR_P9_TLBIE_BUG)) { | ||
| 160 | asm volatile("ptesync": : :"memory"); | ||
| 161 | __tlbie_va(va, pid, mmu_get_ap(MMU_PAGE_64K), RIC_FLUSH_TLB); | ||
| 162 | } | ||
| 163 | } | ||
| 164 | |||
| 122 | /* | 165 | /* |
| 123 | * We use 128 set in radix mode and 256 set in hpt mode. | 166 | * We use 128 set in radix mode and 256 set in hpt mode. |
| 124 | */ | 167 | */ |
| @@ -151,24 +194,25 @@ static inline void _tlbiel_pid(unsigned long pid, unsigned long ric) | |||
| 151 | static inline void _tlbie_pid(unsigned long pid, unsigned long ric) | 194 | static inline void _tlbie_pid(unsigned long pid, unsigned long ric) |
| 152 | { | 195 | { |
| 153 | asm volatile("ptesync": : :"memory"); | 196 | asm volatile("ptesync": : :"memory"); |
| 154 | __tlbie_pid(pid, ric); | ||
| 155 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | ||
| 156 | } | ||
| 157 | 197 | ||
| 158 | static inline void __tlbiel_va(unsigned long va, unsigned long pid, | 198 | /* |
| 159 | unsigned long ap, unsigned long ric) | 199 | * Workaround the fact that the "ric" argument to __tlbie_pid |
| 160 | { | 200 | * must be a compile-time contraint to match the "i" constraint |
| 161 | unsigned long rb,rs,prs,r; | 201 | * in the asm statement. |
| 162 | 202 | */ | |
| 163 | rb = va & ~(PPC_BITMASK(52, 63)); | 203 | switch (ric) { |
| 164 | rb |= ap << PPC_BITLSHIFT(58); | 204 | case RIC_FLUSH_TLB: |
| 165 | rs = pid << PPC_BITLSHIFT(31); | 205 | __tlbie_pid(pid, RIC_FLUSH_TLB); |
| 166 | prs = 1; /* process scoped */ | 206 | break; |
| 167 | r = 1; /* radix format */ | 207 | case RIC_FLUSH_PWC: |
| 168 | 208 | __tlbie_pid(pid, RIC_FLUSH_PWC); | |
| 169 | asm volatile(PPC_TLBIEL(%0, %4, %3, %2, %1) | 209 | break; |
| 170 | : : "r"(rb), "i"(r), "i"(prs), "i"(ric), "r"(rs) : "memory"); | 210 | case RIC_FLUSH_ALL: |
| 171 | trace_tlbie(0, 1, rb, rs, ric, prs, r); | 211 | default: |
| 212 | __tlbie_pid(pid, RIC_FLUSH_ALL); | ||
| 213 | } | ||
| 214 | fixup_tlbie(); | ||
| 215 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | ||
| 172 | } | 216 | } |
| 173 | 217 | ||
| 174 | static inline void __tlbiel_va_range(unsigned long start, unsigned long end, | 218 | static inline void __tlbiel_va_range(unsigned long start, unsigned long end, |
| @@ -203,22 +247,6 @@ static inline void _tlbiel_va_range(unsigned long start, unsigned long end, | |||
| 203 | asm volatile("ptesync": : :"memory"); | 247 | asm volatile("ptesync": : :"memory"); |
| 204 | } | 248 | } |
| 205 | 249 | ||
| 206 | static inline void __tlbie_va(unsigned long va, unsigned long pid, | ||
| 207 | unsigned long ap, unsigned long ric) | ||
| 208 | { | ||
| 209 | unsigned long rb,rs,prs,r; | ||
| 210 | |||
| 211 | rb = va & ~(PPC_BITMASK(52, 63)); | ||
| 212 | rb |= ap << PPC_BITLSHIFT(58); | ||
| 213 | rs = pid << PPC_BITLSHIFT(31); | ||
| 214 | prs = 1; /* process scoped */ | ||
| 215 | r = 1; /* radix format */ | ||
| 216 | |||
| 217 | asm volatile(PPC_TLBIE_5(%0, %4, %3, %2, %1) | ||
| 218 | : : "r"(rb), "i"(r), "i"(prs), "i"(ric), "r"(rs) : "memory"); | ||
| 219 | trace_tlbie(0, 0, rb, rs, ric, prs, r); | ||
| 220 | } | ||
| 221 | |||
| 222 | static inline void __tlbie_va_range(unsigned long start, unsigned long end, | 250 | static inline void __tlbie_va_range(unsigned long start, unsigned long end, |
| 223 | unsigned long pid, unsigned long page_size, | 251 | unsigned long pid, unsigned long page_size, |
| 224 | unsigned long psize) | 252 | unsigned long psize) |
| @@ -237,6 +265,7 @@ static inline void _tlbie_va(unsigned long va, unsigned long pid, | |||
| 237 | 265 | ||
| 238 | asm volatile("ptesync": : :"memory"); | 266 | asm volatile("ptesync": : :"memory"); |
| 239 | __tlbie_va(va, pid, ap, ric); | 267 | __tlbie_va(va, pid, ap, ric); |
| 268 | fixup_tlbie(); | ||
| 240 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | 269 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); |
| 241 | } | 270 | } |
| 242 | 271 | ||
| @@ -248,6 +277,7 @@ static inline void _tlbie_va_range(unsigned long start, unsigned long end, | |||
| 248 | if (also_pwc) | 277 | if (also_pwc) |
| 249 | __tlbie_pid(pid, RIC_FLUSH_PWC); | 278 | __tlbie_pid(pid, RIC_FLUSH_PWC); |
| 250 | __tlbie_va_range(start, end, pid, page_size, psize); | 279 | __tlbie_va_range(start, end, pid, page_size, psize); |
| 280 | fixup_tlbie(); | ||
| 251 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | 281 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); |
| 252 | } | 282 | } |
| 253 | 283 | ||
| @@ -311,6 +341,16 @@ void radix__local_flush_tlb_page(struct vm_area_struct *vma, unsigned long vmadd | |||
| 311 | } | 341 | } |
| 312 | EXPORT_SYMBOL(radix__local_flush_tlb_page); | 342 | EXPORT_SYMBOL(radix__local_flush_tlb_page); |
| 313 | 343 | ||
| 344 | static bool mm_needs_flush_escalation(struct mm_struct *mm) | ||
| 345 | { | ||
| 346 | /* | ||
| 347 | * P9 nest MMU has issues with the page walk cache | ||
| 348 | * caching PTEs and not flushing them properly when | ||
| 349 | * RIC = 0 for a PID/LPID invalidate | ||
| 350 | */ | ||
| 351 | return atomic_read(&mm->context.copros) != 0; | ||
| 352 | } | ||
| 353 | |||
| 314 | #ifdef CONFIG_SMP | 354 | #ifdef CONFIG_SMP |
| 315 | void radix__flush_tlb_mm(struct mm_struct *mm) | 355 | void radix__flush_tlb_mm(struct mm_struct *mm) |
| 316 | { | 356 | { |
| @@ -321,9 +361,12 @@ void radix__flush_tlb_mm(struct mm_struct *mm) | |||
| 321 | return; | 361 | return; |
| 322 | 362 | ||
| 323 | preempt_disable(); | 363 | preempt_disable(); |
| 324 | if (!mm_is_thread_local(mm)) | 364 | if (!mm_is_thread_local(mm)) { |
| 325 | _tlbie_pid(pid, RIC_FLUSH_TLB); | 365 | if (mm_needs_flush_escalation(mm)) |
| 326 | else | 366 | _tlbie_pid(pid, RIC_FLUSH_ALL); |
| 367 | else | ||
| 368 | _tlbie_pid(pid, RIC_FLUSH_TLB); | ||
| 369 | } else | ||
| 327 | _tlbiel_pid(pid, RIC_FLUSH_TLB); | 370 | _tlbiel_pid(pid, RIC_FLUSH_TLB); |
| 328 | preempt_enable(); | 371 | preempt_enable(); |
| 329 | } | 372 | } |
| @@ -435,10 +478,14 @@ void radix__flush_tlb_range(struct vm_area_struct *vma, unsigned long start, | |||
| 435 | } | 478 | } |
| 436 | 479 | ||
| 437 | if (full) { | 480 | if (full) { |
| 438 | if (local) | 481 | if (local) { |
| 439 | _tlbiel_pid(pid, RIC_FLUSH_TLB); | 482 | _tlbiel_pid(pid, RIC_FLUSH_TLB); |
| 440 | else | 483 | } else { |
| 441 | _tlbie_pid(pid, RIC_FLUSH_TLB); | 484 | if (mm_needs_flush_escalation(mm)) |
| 485 | _tlbie_pid(pid, RIC_FLUSH_ALL); | ||
| 486 | else | ||
| 487 | _tlbie_pid(pid, RIC_FLUSH_TLB); | ||
| 488 | } | ||
| 442 | } else { | 489 | } else { |
| 443 | bool hflush = false; | 490 | bool hflush = false; |
| 444 | unsigned long hstart, hend; | 491 | unsigned long hstart, hend; |
| @@ -465,6 +512,7 @@ void radix__flush_tlb_range(struct vm_area_struct *vma, unsigned long start, | |||
| 465 | if (hflush) | 512 | if (hflush) |
| 466 | __tlbie_va_range(hstart, hend, pid, | 513 | __tlbie_va_range(hstart, hend, pid, |
| 467 | HPAGE_PMD_SIZE, MMU_PAGE_2M); | 514 | HPAGE_PMD_SIZE, MMU_PAGE_2M); |
| 515 | fixup_tlbie(); | ||
| 468 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | 516 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); |
| 469 | } | 517 | } |
| 470 | } | 518 | } |
| @@ -548,6 +596,9 @@ static inline void __radix__flush_tlb_range_psize(struct mm_struct *mm, | |||
| 548 | } | 596 | } |
| 549 | 597 | ||
| 550 | if (full) { | 598 | if (full) { |
| 599 | if (!local && mm_needs_flush_escalation(mm)) | ||
| 600 | also_pwc = true; | ||
| 601 | |||
| 551 | if (local) | 602 | if (local) |
| 552 | _tlbiel_pid(pid, also_pwc ? RIC_FLUSH_ALL : RIC_FLUSH_TLB); | 603 | _tlbiel_pid(pid, also_pwc ? RIC_FLUSH_ALL : RIC_FLUSH_TLB); |
| 553 | else | 604 | else |
| @@ -603,46 +654,6 @@ void radix__flush_tlb_collapsed_pmd(struct mm_struct *mm, unsigned long addr) | |||
| 603 | } | 654 | } |
| 604 | #endif /* CONFIG_TRANSPARENT_HUGEPAGE */ | 655 | #endif /* CONFIG_TRANSPARENT_HUGEPAGE */ |
| 605 | 656 | ||
| 606 | void radix__flush_tlb_lpid_va(unsigned long lpid, unsigned long gpa, | ||
| 607 | unsigned long page_size) | ||
| 608 | { | ||
| 609 | unsigned long rb,rs,prs,r; | ||
| 610 | unsigned long ap; | ||
| 611 | unsigned long ric = RIC_FLUSH_TLB; | ||
| 612 | |||
| 613 | ap = mmu_get_ap(radix_get_mmu_psize(page_size)); | ||
| 614 | rb = gpa & ~(PPC_BITMASK(52, 63)); | ||
| 615 | rb |= ap << PPC_BITLSHIFT(58); | ||
| 616 | rs = lpid & ((1UL << 32) - 1); | ||
| 617 | prs = 0; /* process scoped */ | ||
| 618 | r = 1; /* radix format */ | ||
| 619 | |||
| 620 | asm volatile("ptesync": : :"memory"); | ||
| 621 | asm volatile(PPC_TLBIE_5(%0, %4, %3, %2, %1) | ||
| 622 | : : "r"(rb), "i"(r), "i"(prs), "i"(ric), "r"(rs) : "memory"); | ||
| 623 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | ||
| 624 | trace_tlbie(lpid, 0, rb, rs, ric, prs, r); | ||
| 625 | } | ||
| 626 | EXPORT_SYMBOL(radix__flush_tlb_lpid_va); | ||
| 627 | |||
| 628 | void radix__flush_tlb_lpid(unsigned long lpid) | ||
| 629 | { | ||
| 630 | unsigned long rb,rs,prs,r; | ||
| 631 | unsigned long ric = RIC_FLUSH_ALL; | ||
| 632 | |||
| 633 | rb = 0x2 << PPC_BITLSHIFT(53); /* IS = 2 */ | ||
| 634 | rs = lpid & ((1UL << 32) - 1); | ||
| 635 | prs = 0; /* partition scoped */ | ||
| 636 | r = 1; /* radix format */ | ||
| 637 | |||
| 638 | asm volatile("ptesync": : :"memory"); | ||
| 639 | asm volatile(PPC_TLBIE_5(%0, %4, %3, %2, %1) | ||
| 640 | : : "r"(rb), "i"(r), "i"(prs), "i"(ric), "r"(rs) : "memory"); | ||
| 641 | asm volatile("eieio; tlbsync; ptesync": : :"memory"); | ||
| 642 | trace_tlbie(lpid, 0, rb, rs, ric, prs, r); | ||
| 643 | } | ||
| 644 | EXPORT_SYMBOL(radix__flush_tlb_lpid); | ||
| 645 | |||
| 646 | void radix__flush_pmd_tlb_range(struct vm_area_struct *vma, | 657 | void radix__flush_pmd_tlb_range(struct vm_area_struct *vma, |
| 647 | unsigned long start, unsigned long end) | 658 | unsigned long start, unsigned long end) |
| 648 | { | 659 | { |
diff --git a/drivers/misc/ocxl/file.c b/drivers/misc/ocxl/file.c index 337462e1569f..038509e5d031 100644 --- a/drivers/misc/ocxl/file.c +++ b/drivers/misc/ocxl/file.c | |||
| @@ -102,10 +102,32 @@ static long afu_ioctl_attach(struct ocxl_context *ctx, | |||
| 102 | return rc; | 102 | return rc; |
| 103 | } | 103 | } |
| 104 | 104 | ||
| 105 | static long afu_ioctl_get_metadata(struct ocxl_context *ctx, | ||
| 106 | struct ocxl_ioctl_metadata __user *uarg) | ||
| 107 | { | ||
| 108 | struct ocxl_ioctl_metadata arg; | ||
| 109 | |||
| 110 | memset(&arg, 0, sizeof(arg)); | ||
| 111 | |||
| 112 | arg.version = 0; | ||
| 113 | |||
| 114 | arg.afu_version_major = ctx->afu->config.version_major; | ||
| 115 | arg.afu_version_minor = ctx->afu->config.version_minor; | ||
| 116 | arg.pasid = ctx->pasid; | ||
| 117 | arg.pp_mmio_size = ctx->afu->config.pp_mmio_stride; | ||
| 118 | arg.global_mmio_size = ctx->afu->config.global_mmio_size; | ||
| 119 | |||
| 120 | if (copy_to_user(uarg, &arg, sizeof(arg))) | ||
| 121 | return -EFAULT; | ||
| 122 | |||
| 123 | return 0; | ||
| 124 | } | ||
| 125 | |||
| 105 | #define CMD_STR(x) (x == OCXL_IOCTL_ATTACH ? "ATTACH" : \ | 126 | #define CMD_STR(x) (x == OCXL_IOCTL_ATTACH ? "ATTACH" : \ |
| 106 | x == OCXL_IOCTL_IRQ_ALLOC ? "IRQ_ALLOC" : \ | 127 | x == OCXL_IOCTL_IRQ_ALLOC ? "IRQ_ALLOC" : \ |
| 107 | x == OCXL_IOCTL_IRQ_FREE ? "IRQ_FREE" : \ | 128 | x == OCXL_IOCTL_IRQ_FREE ? "IRQ_FREE" : \ |
| 108 | x == OCXL_IOCTL_IRQ_SET_FD ? "IRQ_SET_FD" : \ | 129 | x == OCXL_IOCTL_IRQ_SET_FD ? "IRQ_SET_FD" : \ |
| 130 | x == OCXL_IOCTL_GET_METADATA ? "GET_METADATA" : \ | ||
| 109 | "UNKNOWN") | 131 | "UNKNOWN") |
| 110 | 132 | ||
| 111 | static long afu_ioctl(struct file *file, unsigned int cmd, | 133 | static long afu_ioctl(struct file *file, unsigned int cmd, |
| @@ -159,6 +181,11 @@ static long afu_ioctl(struct file *file, unsigned int cmd, | |||
| 159 | irq_fd.eventfd); | 181 | irq_fd.eventfd); |
| 160 | break; | 182 | break; |
| 161 | 183 | ||
| 184 | case OCXL_IOCTL_GET_METADATA: | ||
| 185 | rc = afu_ioctl_get_metadata(ctx, | ||
| 186 | (struct ocxl_ioctl_metadata __user *) args); | ||
| 187 | break; | ||
| 188 | |||
| 162 | default: | 189 | default: |
| 163 | rc = -EINVAL; | 190 | rc = -EINVAL; |
| 164 | } | 191 | } |
diff --git a/include/uapi/misc/ocxl.h b/include/uapi/misc/ocxl.h index 4b0b0b756f3e..0af83d80fb3e 100644 --- a/include/uapi/misc/ocxl.h +++ b/include/uapi/misc/ocxl.h | |||
| @@ -32,6 +32,22 @@ struct ocxl_ioctl_attach { | |||
| 32 | __u64 reserved3; | 32 | __u64 reserved3; |
| 33 | }; | 33 | }; |
| 34 | 34 | ||
| 35 | struct ocxl_ioctl_metadata { | ||
| 36 | __u16 version; // struct version, always backwards compatible | ||
| 37 | |||
| 38 | // Version 0 fields | ||
| 39 | __u8 afu_version_major; | ||
| 40 | __u8 afu_version_minor; | ||
| 41 | __u32 pasid; // PASID assigned to the current context | ||
| 42 | |||
| 43 | __u64 pp_mmio_size; // Per PASID MMIO size | ||
| 44 | __u64 global_mmio_size; | ||
| 45 | |||
| 46 | // End version 0 fields | ||
| 47 | |||
| 48 | __u64 reserved[13]; // Total of 16*u64 | ||
| 49 | }; | ||
| 50 | |||
| 35 | struct ocxl_ioctl_irq_fd { | 51 | struct ocxl_ioctl_irq_fd { |
| 36 | __u64 irq_offset; | 52 | __u64 irq_offset; |
| 37 | __s32 eventfd; | 53 | __s32 eventfd; |
| @@ -45,5 +61,6 @@ struct ocxl_ioctl_irq_fd { | |||
| 45 | #define OCXL_IOCTL_IRQ_ALLOC _IOR(OCXL_MAGIC, 0x11, __u64) | 61 | #define OCXL_IOCTL_IRQ_ALLOC _IOR(OCXL_MAGIC, 0x11, __u64) |
| 46 | #define OCXL_IOCTL_IRQ_FREE _IOW(OCXL_MAGIC, 0x12, __u64) | 62 | #define OCXL_IOCTL_IRQ_FREE _IOW(OCXL_MAGIC, 0x12, __u64) |
| 47 | #define OCXL_IOCTL_IRQ_SET_FD _IOW(OCXL_MAGIC, 0x13, struct ocxl_ioctl_irq_fd) | 63 | #define OCXL_IOCTL_IRQ_SET_FD _IOW(OCXL_MAGIC, 0x13, struct ocxl_ioctl_irq_fd) |
| 64 | #define OCXL_IOCTL_GET_METADATA _IOR(OCXL_MAGIC, 0x14, struct ocxl_ioctl_metadata) | ||
| 48 | 65 | ||
| 49 | #endif /* _UAPI_MISC_OCXL_H */ | 66 | #endif /* _UAPI_MISC_OCXL_H */ |
diff --git a/tools/testing/selftests/powerpc/mm/subpage_prot.c b/tools/testing/selftests/powerpc/mm/subpage_prot.c index 35ade7406dcd..3ae77ba93208 100644 --- a/tools/testing/selftests/powerpc/mm/subpage_prot.c +++ b/tools/testing/selftests/powerpc/mm/subpage_prot.c | |||
| @@ -135,6 +135,16 @@ static int run_test(void *addr, unsigned long size) | |||
| 135 | return 0; | 135 | return 0; |
| 136 | } | 136 | } |
| 137 | 137 | ||
| 138 | static int syscall_available(void) | ||
| 139 | { | ||
| 140 | int rc; | ||
| 141 | |||
| 142 | errno = 0; | ||
| 143 | rc = syscall(__NR_subpage_prot, 0, 0, 0); | ||
| 144 | |||
| 145 | return rc == 0 || (errno != ENOENT && errno != ENOSYS); | ||
| 146 | } | ||
| 147 | |||
| 138 | int test_anon(void) | 148 | int test_anon(void) |
| 139 | { | 149 | { |
| 140 | unsigned long align; | 150 | unsigned long align; |
| @@ -145,6 +155,8 @@ int test_anon(void) | |||
| 145 | void *mallocblock; | 155 | void *mallocblock; |
| 146 | unsigned long mallocsize; | 156 | unsigned long mallocsize; |
| 147 | 157 | ||
| 158 | SKIP_IF(!syscall_available()); | ||
| 159 | |||
| 148 | if (getpagesize() != 0x10000) { | 160 | if (getpagesize() != 0x10000) { |
| 149 | fprintf(stderr, "Kernel page size must be 64K!\n"); | 161 | fprintf(stderr, "Kernel page size must be 64K!\n"); |
| 150 | return 1; | 162 | return 1; |
| @@ -180,6 +192,8 @@ int test_file(void) | |||
| 180 | off_t filesize; | 192 | off_t filesize; |
| 181 | int fd; | 193 | int fd; |
| 182 | 194 | ||
| 195 | SKIP_IF(!syscall_available()); | ||
| 196 | |||
| 183 | fd = open(file_name, O_RDWR); | 197 | fd = open(file_name, O_RDWR); |
| 184 | if (fd == -1) { | 198 | if (fd == -1) { |
| 185 | perror("failed to open file"); | 199 | perror("failed to open file"); |
diff --git a/tools/testing/selftests/powerpc/tm/Makefile b/tools/testing/selftests/powerpc/tm/Makefile index 1c9e5d0a0491..c0e45d2dde25 100644 --- a/tools/testing/selftests/powerpc/tm/Makefile +++ b/tools/testing/selftests/powerpc/tm/Makefile | |||
| @@ -16,7 +16,7 @@ $(OUTPUT)/tm-syscall: tm-syscall-asm.S | |||
| 16 | $(OUTPUT)/tm-syscall: CFLAGS += -I../../../../../usr/include | 16 | $(OUTPUT)/tm-syscall: CFLAGS += -I../../../../../usr/include |
| 17 | $(OUTPUT)/tm-tmspr: CFLAGS += -pthread | 17 | $(OUTPUT)/tm-tmspr: CFLAGS += -pthread |
| 18 | $(OUTPUT)/tm-vmx-unavail: CFLAGS += -pthread -m64 | 18 | $(OUTPUT)/tm-vmx-unavail: CFLAGS += -pthread -m64 |
| 19 | $(OUTPUT)/tm-resched-dscr: ../pmu/lib.o | 19 | $(OUTPUT)/tm-resched-dscr: ../pmu/lib.c |
| 20 | $(OUTPUT)/tm-unavailable: CFLAGS += -O0 -pthread -m64 -Wno-error=uninitialized -mvsx | 20 | $(OUTPUT)/tm-unavailable: CFLAGS += -O0 -pthread -m64 -Wno-error=uninitialized -mvsx |
| 21 | $(OUTPUT)/tm-trap: CFLAGS += -O0 -pthread -m64 | 21 | $(OUTPUT)/tm-trap: CFLAGS += -O0 -pthread -m64 |
| 22 | 22 | ||
diff --git a/tools/testing/selftests/powerpc/tm/tm-trap.c b/tools/testing/selftests/powerpc/tm/tm-trap.c index 5d92c23ee6cb..179d592f0073 100644 --- a/tools/testing/selftests/powerpc/tm/tm-trap.c +++ b/tools/testing/selftests/powerpc/tm/tm-trap.c | |||
| @@ -255,6 +255,8 @@ int tm_trap_test(void) | |||
| 255 | 255 | ||
| 256 | struct sigaction trap_sa; | 256 | struct sigaction trap_sa; |
| 257 | 257 | ||
| 258 | SKIP_IF(!have_htm()); | ||
| 259 | |||
| 258 | trap_sa.sa_flags = SA_SIGINFO; | 260 | trap_sa.sa_flags = SA_SIGINFO; |
| 259 | trap_sa.sa_sigaction = trap_signal_handler; | 261 | trap_sa.sa_sigaction = trap_signal_handler; |
| 260 | sigaction(SIGTRAP, &trap_sa, NULL); | 262 | sigaction(SIGTRAP, &trap_sa, NULL); |
