1 /* SPDX-License-Identifier: GPL-2.0 */ 2 #ifndef _ASM_POWERPC_SECTIONS_H 3 #define _ASM_POWERPC_SECTIONS_H 4 #ifdef __KERNEL__ 5 6 #include <linux/elf.h> 7 #include <linux/uaccess.h> 8 9 #include <asm-generic/sections.h> 10 11 extern char __head_end[]; 12 extern char __srwx_boundary[]; 13 14 #ifdef __powerpc64__ 15 16 extern char __start_interrupts[]; 17 extern char __end_interrupts[]; 18 19 extern char __prom_init_toc_start[]; 20 extern char __prom_init_toc_end[]; 21 22 #ifdef CONFIG_PPC_POWERNV 23 extern char start_real_trampolines[]; 24 extern char end_real_trampolines[]; 25 extern char start_virt_trampolines[]; 26 extern char end_virt_trampolines[]; 27 #endif 28 29 /* 30 * This assumes the kernel is never compiled -mcmodel=small or 31 * the total .toc is always less than 64k. 32 */ kernel_toc_addr(void)33static inline unsigned long kernel_toc_addr(void) 34 { 35 unsigned long toc_ptr; 36 37 asm volatile("mr %0, 2" : "=r" (toc_ptr)); 38 return toc_ptr; 39 } 40 overlaps_interrupt_vector_text(unsigned long start,unsigned long end)41static inline int overlaps_interrupt_vector_text(unsigned long start, 42 unsigned long end) 43 { 44 unsigned long real_start, real_end; 45 real_start = __start_interrupts - _stext; 46 real_end = __end_interrupts - _stext; 47 48 return start < (unsigned long)__va(real_end) && 49 (unsigned long)__va(real_start) < end; 50 } 51 overlaps_kernel_text(unsigned long start,unsigned long end)52static inline int overlaps_kernel_text(unsigned long start, unsigned long end) 53 { 54 return start < (unsigned long)__init_end && 55 (unsigned long)_stext < end; 56 } 57 58 #ifdef PPC64_ELF_ABI_v1 59 60 #define HAVE_DEREFERENCE_FUNCTION_DESCRIPTOR 1 61 62 #undef dereference_function_descriptor dereference_function_descriptor(void * ptr)63static inline void *dereference_function_descriptor(void *ptr) 64 { 65 struct ppc64_opd_entry *desc = ptr; 66 void *p; 67 68 if (!get_kernel_nofault(p, (void *)&desc->funcaddr)) 69 ptr = p; 70 return ptr; 71 } 72 73 #undef dereference_kernel_function_descriptor dereference_kernel_function_descriptor(void * ptr)74static inline void *dereference_kernel_function_descriptor(void *ptr) 75 { 76 if (ptr < (void *)__start_opd || ptr >= (void *)__end_opd) 77 return ptr; 78 79 return dereference_function_descriptor(ptr); 80 } 81 #endif /* PPC64_ELF_ABI_v1 */ 82 83 #endif 84 85 #endif /* __KERNEL__ */ 86 #endif /* _ASM_POWERPC_SECTIONS_H */ 87