* [PATCH v0 0/4] ppc64le: dynamic ftrace and kgraft support
@ 2015-03-19 20:35 Torsten Duwe
2015-03-19 20:45 ` [PATCH v0 1/4] ppc64le: dynamic ftrace Torsten Duwe
` (3 more replies)
0 siblings, 4 replies; 5+ messages in thread
From: Torsten Duwe @ 2015-03-19 20:35 UTC (permalink / raw)
To: ppc-dev; +Cc: Linux Kernel Mailing List
Here's an initial version of dynamic ftrace for ABIv2 (ppc64le),
the code maturity is somewhere between proof of concept and pre-alpha.
I have split it into 4 parts, for ftrace and kgraft, a configuration
enablement and the actual code, respectively.
Please have a look and tell me whether this is the way to go.
Torsten
^ permalink raw reply [flat|nested] 5+ messages in thread
* Re: [PATCH v0 1/4] ppc64le: dynamic ftrace
2015-03-19 20:35 [PATCH v0 0/4] ppc64le: dynamic ftrace and kgraft support Torsten Duwe
@ 2015-03-19 20:45 ` Torsten Duwe
2015-03-19 20:48 ` [PATCH v0 2/4] ppc64le: dynamic ftrace configuration options Torsten Duwe
` (2 subsequent siblings)
3 siblings, 0 replies; 5+ messages in thread
From: Torsten Duwe @ 2015-03-19 20:45 UTC (permalink / raw)
To: ppc-dev; +Cc: Linux Kernel Mailing List
I'm pretty sure not everything is ifdef'd properly,
and the FIXME needs to be solved in order to disable
ftracing again. Built upon some original code by
Vojtech Pavlik.
diff --git a/arch/powerpc/include/asm/ftrace.h b/arch/powerpc/include/asm/ftrace.h
index e366187..a69d47e 100644
--- a/arch/powerpc/include/asm/ftrace.h
+++ b/arch/powerpc/include/asm/ftrace.h
@@ -46,6 +46,8 @@
extern void _mcount(void);
#ifdef CONFIG_DYNAMIC_FTRACE
+# define FTRACE_ADDR ((unsigned long)ftrace_caller+8)
+# define FTRACE_REGS_ADDR FTRACE_ADDR
static inline unsigned long ftrace_call_adjust(unsigned long addr)
{
/* reloction of mcount call site is the same as the address */
@@ -57,6 +58,9 @@ struct dyn_arch_ftrace {
#endif /* CONFIG_DYNAMIC_FTRACE */
#endif /* __ASSEMBLY__ */
+#ifdef CONFIG_DYNAMIC_FTRACE
+#define ARCH_SUPPORTS_FTRACE_OPS 1
+#endif
#endif
#if defined(CONFIG_FTRACE_SYSCALLS) && defined(CONFIG_PPC64) && !defined(__ASSEMBLY__)
diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S
index 5bbd1bc..9caf9af 100644
--- a/arch/powerpc/kernel/entry_64.S
+++ b/arch/powerpc/kernel/entry_64.S
@@ -1159,32 +1170,107 @@ _GLOBAL(enter_prom)
#ifdef CONFIG_FUNCTION_TRACER
#ifdef CONFIG_DYNAMIC_FTRACE
-_GLOBAL(mcount)
+
+#define TOCSAVE 24
+
_GLOBAL(_mcount)
- blr
+ nop // REQUIRED for ftrace, to calculate local/global entry diff
+.localentry _mcount,.-_mcount
+ mflr r0
+ mtctr r0
+
+ LOAD_REG_ADDR_PIC(r12,ftrace_trace_function)
+ ld r12,0(r12)
+ LOAD_REG_ADDR_PIC(r0,ftrace_stub)
+ cmpd r0,r12
+ ld r0,LRSAVE(r1)
+ bne- 2f
+
+ mtlr r0
+ bctr
+
+2: /* here we have (*ftrace_trace_function)() in r12,
+ "selfpc" in CTR
+ and "frompc" in r0 */
+
+ mtlr r0
+ bctr
+
+_GLOBAL(ftrace_caller)
+ mr r0,r2 // global (module) call: save module TOC
+ b 1f
+.localentry ftrace_caller,.-ftrace_caller
+ mr r0,r2 // local call: callee's TOC == our TOC
+ b 2f
+
+1: addis r2,r12,(.TOC.-0b)@ha
+ addi r2,r2,(.TOC.-0b)@l
+
+2: // Here we have our proper TOC ptr in R2,
+ // and the one we need to restore on return in r0.
+
+ ld r12, 16(r1) // get caller's adress
+
+ stdu r1,-SWITCH_FRAME_SIZE(r1)
+
+ std r12, _LINK(r1)
+ SAVE_8GPRS(0,r1)
+ std r0,TOCSAVE(r1)
+ SAVE_8GPRS(8,r1)
+ SAVE_8GPRS(16,r1)
+ SAVE_8GPRS(24,r1)
+
+
+ LOAD_REG_IMMEDIATE(r3,function_trace_op)
+ ld r5,0(r3)
+
+ mflr r3
+ std r3, _NIP(r1)
+ std r3, 16(r1)
+ subi r3, r3, MCOUNT_INSN_SIZE
+ mfmsr r4
+ std r4, _MSR(r1)
+ mfctr r4
+ std r4, _CTR(r1)
+ mfxer r4
+ std r4, _XER(r1)
+ mr r4, r12
+ addi r6, r1 ,STACK_FRAME_OVERHEAD
-_GLOBAL_TOC(ftrace_caller)
- /* Taken from output of objdump from lib64/glibc */
- mflr r3
- ld r11, 0(r1)
- stdu r1, -112(r1)
- std r3, 128(r1)
- ld r4, 16(r11)
- subi r3, r3, MCOUNT_INSN_SIZE
.globl ftrace_call
ftrace_call:
bl ftrace_stub
nop
+
+ ld r3, _NIP(r1)
+ mtlr r3
+
+ REST_8GPRS(0,r1)
+ REST_8GPRS(8,r1)
+ REST_8GPRS(16,r1)
+ REST_8GPRS(24,r1)
+
+ addi r1, r1, SWITCH_FRAME_SIZE
+
+ ld r12, 16(r1) // get caller's adress
+ mr r2,r0 // restore callee's TOC
+ mflr r0 // move this LR to CTR
+ mtctr r0
+ mr r0,r12 // restore callee's lr at _mcount site
+ mtlr r0
+ bctr // jump after _mcount site
+
#ifdef CONFIG_FUNCTION_GRAPH_TRACER
.globl ftrace_graph_call
ftrace_graph_call:
b ftrace_graph_stub
_GLOBAL(ftrace_graph_stub)
#endif
- ld r0, 128(r1)
- mtlr r0
- addi r1, r1, 112
+
_GLOBAL(ftrace_stub)
+ nop
+ nop
+.localentry ftrace_stub,.-ftrace_stub
blr
#else
_GLOBAL_TOC(_mcount)
@@ -1218,20 +1304,17 @@ _GLOBAL(ftrace_stub)
#ifdef CONFIG_FUNCTION_GRAPH_TRACER
_GLOBAL(ftrace_graph_caller)
/* load r4 with local address */
- ld r4, 128(r1)
+ ld r4, LRSAVE+SWITCH_FRAME_SIZE(r1)
subi r4, r4, MCOUNT_INSN_SIZE
/* get the parent address */
- ld r11, 112(r1)
- addi r3, r11, 16
+ ld r11, SWITCH_FRAME_SIZE(r1)
+ addi r3, r11, LRSAVE
bl prepare_ftrace_return
nop
- ld r0, 128(r1)
- mtlr r0
- addi r1, r1, 112
- blr
+ b ftrace_graph_stub
_GLOBAL(return_to_handler)
/* need to save return values */
diff --git a/arch/powerpc/kernel/ftrace.c b/arch/powerpc/kernel/ftrace.c
index 390311c..4fe16fb 100644
--- a/arch/powerpc/kernel/ftrace.c
+++ b/arch/powerpc/kernel/ftrace.c
@@ -61,8 +61,11 @@ ftrace_modify_code(unsigned long ip, unsigned int old, unsigned int new)
return -EFAULT;
/* Make sure it is what we expect it to be */
- if (replaced != old)
+ if (replaced != old) {
+ printk(KERN_ERR "%p: replaced (%#x) != old (%#x)",
+ (void *)ip, replaced, old);
return -EINVAL;
+ }
/* replace the text with the new text */
if (patch_instruction((unsigned int *)ip, new))
@@ -106,14 +109,16 @@ static int
__ftrace_make_nop(struct module *mod,
struct dyn_ftrace *rec, unsigned long addr)
{
- unsigned int op;
+ unsigned int op, op0, op1, pop;
unsigned long entry, ptr;
unsigned long ip = rec->ip;
void *tramp;
/* read where this goes */
- if (probe_kernel_read(&op, (void *)ip, sizeof(int)))
+ if (probe_kernel_read(&op, (void *)ip, sizeof(int))) {
+ printk(KERN_ERR "Fetching opcode failed.\n");
return -EFAULT;
+ }
/* Make sure that that this is still a 24bit jump */
if (!is_bl_op(op)) {
@@ -158,10 +163,42 @@ __ftrace_make_nop(struct module *mod,
*
* Use a b +8 to jump over the load.
*/
- op = 0x48000008; /* b +8 */
- if (patch_instruction((unsigned int *)ip, op))
+ pop = 0x48000008; /* b +8 */
+
+ /*
+ * Check what is in the next instruction. We can see ld r2,40(r1), but
+ * on first pass after boot we will see mflr r0.
+ */
+ if (probe_kernel_read(&op, (void *)(ip+4), MCOUNT_INSN_SIZE)) {
+ printk(KERN_ERR "Fetching op failed.\n");
+ return -EFAULT;
+ }
+
+ if (op != 0xe8410028) { /* ld r2,STACK_OFFSET(r1) */
+
+ if (probe_kernel_read(&op0, (void *)(ip-8), MCOUNT_INSN_SIZE)) {
+ printk(KERN_ERR "Fetching op0 failed.\n");
+ return -EFAULT;
+ }
+
+ if (probe_kernel_read(&op1, (void *)(ip-4), MCOUNT_INSN_SIZE)) {
+ printk(KERN_ERR "Fetching op1 failed.\n");
+ return -EFAULT;
+ }
+
+ if (op0 != 0x7c0802a6 && op1 != 0xf8010010) { /* mflr r0 ; std r0,LRSAVE(r1) */
+ printk(KERN_ERR "Unexpected instructions around bl when enabling dynamic ftrace! (%08x,%08x,bl,%08x)\n", op0, op1, op);
+ return -EINVAL;
+ }
+
+ pop = PPC_INST_NOP; /* When using -mkernel_profile there is no load to jump over */
+ }
+
+ if (patch_instruction((unsigned int *)ip, pop)) {
+ printk(KERN_ERR "Patching NOP failed.\n");
return -EPERM;
+ }
return 0;
}
@@ -251,7 +288,7 @@ int ftrace_make_nop(struct module *mod,
*/
if (test_24bit_addr(ip, addr)) {
/* within range */
- old = ftrace_call_replace(ip, addr, 1);
+ old = ftrace_call_replace(ip, addr + 4, 1); /* FIXME */
new = PPC_INST_NOP;
return ftrace_modify_code(ip, old, new);
}
@@ -287,6 +324,13 @@ int ftrace_make_nop(struct module *mod,
#ifdef CONFIG_MODULES
#ifdef CONFIG_PPC64
+#ifdef CONFIG_DYNAMIC_FTRACE_WITH_REGS
+int ftrace_modify_call(struct dyn_ftrace *rec, unsigned long old_addr,
+ unsigned long addr)
+{
+ return ftrace_make_call(rec, addr);
+}
+#endif
static int
__ftrace_make_call(struct dyn_ftrace *rec, unsigned long addr)
{
@@ -306,11 +350,18 @@ __ftrace_make_call(struct dyn_ftrace *rec, unsigned long addr)
* The load offset is different depending on the ABI. For simplicity
* just mask it out when doing the compare.
*/
+#if 0 // -pg, no -mprofile-kernel
if ((op[0] != 0x48000008) || ((op[1] & 0xffff0000) != 0xe8410000)) {
- pr_err("Unexpected call sequence: %x %x\n", op[0], op[1]);
+ pr_err("Unexpected call sequence at %p: %x %x\n", ip, op[0], op[1]);
return -EINVAL;
}
-
+#else
+ /* look for patched "NOP" on ppc64 with -mprofile-kernel */
+ if ((op[0] != 0x60000000) ) {
+ pr_err("Unexpected call at %p: %x\n", ip, op[0]);
+ return -EINVAL;
+ }
+#endif
/* If we never set up a trampoline to ftrace_caller, then bail */
if (!rec->arch.mod->arch.tramp) {
pr_err("No ftrace trampoline\n");
@@ -330,7 +381,7 @@ __ftrace_make_call(struct dyn_ftrace *rec, unsigned long addr)
return 0;
}
-#else
+#else /* !CONFIG_PPC64: */
static int
__ftrace_make_call(struct dyn_ftrace *rec, unsigned long addr)
{
diff --git a/arch/powerpc/kernel/module_64.c b/arch/powerpc/kernel/module_64.c
index d807ee6..05b88d3 100644
--- a/arch/powerpc/kernel/module_64.c
+++ b/arch/powerpc/kernel/module_64.c
@@ -140,12 +140,22 @@ static u32 ppc64_stub_insns[] = {
0x4e800420 /* bctr */
};
+/* In case of _mcount calls or dynamic ftracing, Do not save the
+ current callee's TOC (in R2) again into the original caller's stack
+ frame during this trampoline hop. The stack frame already holds
+ that of the original caller. _mcount and ftrace_caller will take
+ care of this TOC value themselves.
+*/
+#define SQUASH_TOC_SAVE_INSN(trampoline_addr) \
+ ((struct ppc64_stub_entry*)(trampoline_addr))-> \
+ jump[2] = PPC_INST_NOP;
+
#ifdef CONFIG_DYNAMIC_FTRACE
static u32 ppc64_stub_mask[] = {
0xffff0000,
0xffff0000,
- 0xffffffff,
+ 0x00000000,
0xffffffff,
#if !defined(_CALL_ELF) || _CALL_ELF != 2
0xffffffff,
@@ -172,6 +182,9 @@ bool is_module_trampoline(u32 *p)
if ((insna & mask) != (insnb & mask))
return false;
}
+ if (insns[2] != ppc64_stub_insns[2] &&
+ insns[2] != PPC_INST_NOP )
+ return false;
return true;
}
@@ -477,6 +490,14 @@ static unsigned long stub_for_addr(Elf64_Shdr *sechdrs,
static int restore_r2(u32 *instruction, struct module *me)
{
if (*instruction != PPC_INST_NOP) {
+
+ /* -mprofile_kernel sequence starting with mflr r0; std r0, LRSAVE(r1) */
+ if (instruction[-3] == 0x7c0802a6 && instruction[-2] == 0xf8010010) {
+ /* Nothing to be done here, it's a _mcount call location
+ and r2 will have to be restored in the _mcount function */
+ return 2;
+ };
+
printk("%s: Expect noop after relocate, got %08x\n",
me->name, *instruction);
return 0;
@@ -492,7 +513,7 @@ int apply_relocate_add(Elf64_Shdr *sechdrs,
unsigned int relsec,
struct module *me)
{
- unsigned int i;
+ unsigned int i, r2;
Elf64_Rela *rela = (void *)sechdrs[relsec].sh_addr;
Elf64_Sym *sym;
unsigned long *location;
@@ -605,8 +626,11 @@ int apply_relocate_add(Elf64_Shdr *sechdrs,
value = stub_for_addr(sechdrs, value, me);
if (!value)
return -ENOENT;
- if (!restore_r2((u32 *)location + 1, me))
+ if (!(r2 = restore_r2((u32 *)location + 1, me)))
return -ENOEXEC;
+ /* Squash the TOC saver for profiler calls */
+ if (!strcmp("_mcount", strtab+sym->st_name))
+ SQUASH_TOC_SAVE_INSN(value);
} else
value += local_entry_offset(sym);
@@ -667,6 +691,9 @@ int apply_relocate_add(Elf64_Shdr *sechdrs,
me->arch.tramp = stub_for_addr(sechdrs,
(unsigned long)ftrace_caller,
me);
+ /* ftrace_caller will take care of the TOC;
+ do not clobber original caller's value. */
+ SQUASH_TOC_SAVE_INSN(me->arch.tramp);
#endif
return 0;
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH v0 2/4] ppc64le: dynamic ftrace configuration options
2015-03-19 20:35 [PATCH v0 0/4] ppc64le: dynamic ftrace and kgraft support Torsten Duwe
2015-03-19 20:45 ` [PATCH v0 1/4] ppc64le: dynamic ftrace Torsten Duwe
@ 2015-03-19 20:48 ` Torsten Duwe
2015-03-19 20:51 ` [PATCH v0 3/4] ppc64le: kgraft support Torsten Duwe
2015-03-19 20:54 ` [PATCH v0 4/4] ppc64le: kgraft config options Torsten Duwe
3 siblings, 0 replies; 5+ messages in thread
From: Torsten Duwe @ 2015-03-19 20:48 UTC (permalink / raw)
To: ppc-dev; +Cc: Linux Kernel Mailing List
Switch on -mprofile-kernel, and remove it again
from directories involved in exception handling.
This needs to be done more fine grained, of course.
diff --git a/Makefile b/Makefile
index 1a60bdd..72644e6 100644
--- a/Makefile
+++ b/Makefile
@@ -732,7 +732,10 @@ ifdef CONFIG_FUNCTION_TRACER
ifdef CONFIG_HAVE_FENTRY
CC_USING_FENTRY := $(call cc-option, -mfentry -DCC_USING_FENTRY)
endif
-KBUILD_CFLAGS += -pg $(CC_USING_FENTRY)
+ifdef CONFIG_HAVE_MPROFILE_KERNEL
+CC_USING_MPROFILE_KERNEL := $(call cc-option, -mprofile-kernel -DCC_USING_MPROFILE_KERNEL)
+endif
+KBUILD_CFLAGS += -pg $(CC_USING_FENTRY) $(CC_USING_MPROFILE_KERNEL)
KBUILD_AFLAGS += $(CC_USING_FENTRY)
ifdef CONFIG_DYNAMIC_FTRACE
ifdef CONFIG_HAVE_C_RECORDMCOUNT
diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig
index 4bc7b62..d82d7c8 100644
--- a/arch/powerpc/Kconfig
+++ b/arch/powerpc/Kconfig
@@ -93,8 +93,10 @@ config PPC
select OF_RESERVED_MEM
select HAVE_FTRACE_MCOUNT_RECORD
select HAVE_DYNAMIC_FTRACE
+ select HAVE_DYNAMIC_FTRACE_WITH_REGS
select HAVE_FUNCTION_TRACER
select HAVE_FUNCTION_GRAPH_TRACER
+ select HAVE_MPROFILE_KERNEL
select SYSCTL_EXCEPTION_TRACE
select ARCH_WANT_OPTIONAL_GPIOLIB
select VIRT_TO_BUS if !PPC64
diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile
index 670c312..688e6f9 100644
--- a/arch/powerpc/kernel/Makefile
+++ b/arch/powerpc/kernel/Makefile
@@ -17,14 +17,14 @@ endif
ifdef CONFIG_FUNCTION_TRACER
# Do not trace early boot code
-CFLAGS_REMOVE_cputable.o = -pg -mno-sched-epilog
-CFLAGS_REMOVE_prom_init.o = -pg -mno-sched-epilog
-CFLAGS_REMOVE_btext.o = -pg -mno-sched-epilog
-CFLAGS_REMOVE_prom.o = -pg -mno-sched-epilog
+CFLAGS_REMOVE_cputable.o = -pg -mno-sched-epilog -mprofile-kernel
+CFLAGS_REMOVE_prom_init.o = -pg -mno-sched-epilog -mprofile-kernel
+CFLAGS_REMOVE_btext.o = -pg -mno-sched-epilog -mprofile-kernel
+CFLAGS_REMOVE_prom.o = -pg -mno-sched-epilog -mprofile-kernel
# do not trace tracer code
-CFLAGS_REMOVE_ftrace.o = -pg -mno-sched-epilog
+CFLAGS_REMOVE_ftrace.o = -pg -mno-sched-epilog -mprofile-kernel
# timers used by tracing
-CFLAGS_REMOVE_time.o = -pg -mno-sched-epilog
+CFLAGS_REMOVE_time.o = -pg -mno-sched-epilog -mprofile-kernel
endif
obj-y := cputable.o ptrace.o syscalls.o \
diff --git a/kernel/Makefile b/kernel/Makefile
index 8af7403..3c8821d 100644
--- a/kernel/Makefile
+++ b/kernel/Makefile
@@ -13,8 +13,9 @@ obj-y = fork.o exec_domain.o panic.o \
ifdef CONFIG_FUNCTION_TRACER
# Do not trace debug files and internal ftrace files
-CFLAGS_REMOVE_cgroup-debug.o = -pg
-CFLAGS_REMOVE_irq_work.o = -pg
+CFLAGS_REMOVE_cgroup-debug.o = -pg -mprofile-kernel
+CFLAGS_REMOVE_irq_work.o = -pg -mprofile-kernel
+CFLAGS_REMOVE_extable.o = -pg -mprofile-kernel
endif
# cond_syscall is currently not LTO compatible
diff --git a/kernel/locking/Makefile b/kernel/locking/Makefile
index 8541bfd..1cc57c8 100644
--- a/kernel/locking/Makefile
+++ b/kernel/locking/Makefile
@@ -2,10 +2,10 @@
obj-y += mutex.o semaphore.o rwsem.o mcs_spinlock.o
ifdef CONFIG_FUNCTION_TRACER
-CFLAGS_REMOVE_lockdep.o = -pg
-CFLAGS_REMOVE_lockdep_proc.o = -pg
-CFLAGS_REMOVE_mutex-debug.o = -pg
-CFLAGS_REMOVE_rtmutex-debug.o = -pg
+CFLAGS_REMOVE_lockdep.o = -pg -mprofile-kernel
+CFLAGS_REMOVE_lockdep_proc.o = -pg -mprofile-kernel
+CFLAGS_REMOVE_mutex-debug.o = -pg -mprofile-kernel
+CFLAGS_REMOVE_rtmutex-debug.o = -pg -mprofile-kernel
endif
obj-$(CONFIG_DEBUG_MUTEXES) += mutex-debug.o
diff --git a/kernel/trace/Kconfig b/kernel/trace/Kconfig
index a5da09c..dd53f3d 100644
--- a/kernel/trace/Kconfig
+++ b/kernel/trace/Kconfig
@@ -52,6 +52,11 @@ config HAVE_FENTRY
help
Arch supports the gcc options -pg with -mfentry
+config HAVE_MPROFILE_KERNEL
+ bool
+ help
+ Arch supports the gcc options -pg with -mprofile-kernel
+
config HAVE_C_RECORDMCOUNT
bool
help
diff --git a/arch/powerpc/lib/Makefile b/arch/powerpc/lib/Makefile
index 59fa2de..b2f5029 100644
--- a/arch/powerpc/lib/Makefile
+++ b/arch/powerpc/lib/Makefile
@@ -6,8 +6,8 @@ subdir-ccflags-$(CONFIG_PPC_WERROR) := -Werror
ccflags-$(CONFIG_PPC64) := $(NO_MINIMAL_TOC)
-CFLAGS_REMOVE_code-patching.o = -pg
-CFLAGS_REMOVE_feature-fixups.o = -pg
+CFLAGS_REMOVE_code-patching.o = -pg -mprofile-kernel
+CFLAGS_REMOVE_feature-fixups.o = -pg -mprofile-kernel
obj-y := string.o alloc.o \
crtsavres.o
diff --git a/arch/powerpc/mm/Makefile b/arch/powerpc/mm/Makefile
index d0130ff..22633af 100644
--- a/arch/powerpc/mm/Makefile
+++ b/arch/powerpc/mm/Makefile
@@ -6,6 +6,11 @@ subdir-ccflags-$(CONFIG_PPC_WERROR) := -Werror
ccflags-$(CONFIG_PPC64) := $(NO_MINIMAL_TOC)
+# needed for do_page_fault in fault.c :
+KBUILD_CFLAGS := $(filter-out -mprofile-kernel, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -pg, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -DCC_USING_MPROFILE_KERNEL, $(KBUILD_CFLAGS))
+
obj-y := fault.o mem.o pgtable.o gup.o mmap.o \
init_$(CONFIG_WORD_SIZE).o \
pgtable_$(CONFIG_WORD_SIZE).o
diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile
index 688e6f9..1f08a53 100644
--- a/arch/powerpc/kernel/Makefile
+++ b/arch/powerpc/kernel/Makefile
@@ -26,6 +26,9 @@ CFLAGS_REMOVE_ftrace.o = -pg -mno-sched-epilog -mprofile-kernel
# timers used by tracing
CFLAGS_REMOVE_time.o = -pg -mno-sched-epilog -mprofile-kernel
endif
+KBUILD_CFLAGS := $(filter-out -mprofile-kernel, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -pg, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -DCC_USING_MPROFILE_KERNEL, $(KBUILD_CFLAGS))
obj-y := cputable.o ptrace.o syscalls.o \
irq.o align.o signal_32.o pmc.o vdso.o \
diff --git a/kernel/Makefile b/kernel/Makefile
index f2f8537..f84c784 100644
--- a/kernel/Makefile
+++ b/kernel/Makefile
@@ -17,6 +17,9 @@ CFLAGS_REMOVE_cgroup-debug.o = -pg -mprofile-kernel
CFLAGS_REMOVE_irq_work.o = -pg -mprofile-kernel
CFLAGS_REMOVE_extable.o = -pg -mprofile-kernel
endif
+KBUILD_CFLAGS := $(filter-out -mprofile-kernel, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -pg, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -DCC_USING_MPROFILE_KERNEL, $(KBUILD_CFLAGS))
# cond_syscall is currently not LTO compatible
CFLAGS_sys_ni.o = $(DISABLE_LTO)
diff --git a/lib/Makefile b/lib/Makefile
index d6b4bc4..186cf9b 100644
--- a/lib/Makefile
+++ b/lib/Makefile
@@ -6,6 +6,9 @@ ifdef CONFIG_FUNCTION_TRACER
ORIG_CFLAGS := $(KBUILD_CFLAGS)
KBUILD_CFLAGS = $(subst -pg,,$(ORIG_CFLAGS))
endif
+KBUILD_CFLAGS := $(filter-out -mprofile-kernel, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -pg, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -DCC_USING_MPROFILE_KERNEL, $(KBUILD_CFLAGS))
lib-y := ctype.o string.o vsprintf.o cmdline.o \
rbtree.o radix-tree.o dump_stack.o timerqueue.o\
diff --git a/mm/Makefile b/mm/Makefile
index 632ae77..07be08f 100644
--- a/mm/Makefile
+++ b/mm/Makefile
@@ -20,6 +20,10 @@ obj-y := filemap.o mempool.o oom_kill.o fadvise.o \
interval_tree.o list_lru.o workingset.o \
iov_iter.o $(mmu-y)
+KBUILD_CFLAGS := $(filter-out -mprofile-kernel, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -pg, $(KBUILD_CFLAGS))
+KBUILD_CFLAGS := $(filter-out -DCC_USING_MPROFILE_KERNEL, $(KBUILD_CFLAGS))
+
obj-y += init-mm.o
ifdef CONFIG_NO_BOOTMEM
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH v0 3/4] ppc64le: kgraft support
2015-03-19 20:35 [PATCH v0 0/4] ppc64le: dynamic ftrace and kgraft support Torsten Duwe
2015-03-19 20:45 ` [PATCH v0 1/4] ppc64le: dynamic ftrace Torsten Duwe
2015-03-19 20:48 ` [PATCH v0 2/4] ppc64le: dynamic ftrace configuration options Torsten Duwe
@ 2015-03-19 20:51 ` Torsten Duwe
2015-03-19 20:54 ` [PATCH v0 4/4] ppc64le: kgraft config options Torsten Duwe
3 siblings, 0 replies; 5+ messages in thread
From: Torsten Duwe @ 2015-03-19 20:51 UTC (permalink / raw)
To: ppc-dev; +Cc: Linux Kernel Mailing List
The kgraft hooks for ppc64. Just massaged a bit to
get them to compile and not interfere.
Feel free to test them if you're daring ;)
diff --git a/arch/powerpc/include/asm/kgraft.h b/arch/powerpc/include/asm/kgraft.h
new file mode 100644
index 0000000..7f8600d
--- /dev/null
+++ b/arch/powerpc/include/asm/kgraft.h
@@ -0,0 +1,33 @@
+/*
+ * kGraft Online Kernel Patching
+ *
+ * Copyright (c) 2013-2014 SUSE
+ * Authors: Jiri Kosina
+ * Vojtech Pavlik
+ * Jiri Slaby
+ */
+
+/*
+ * This program is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License as published by the Free
+ * Software Foundation; either version 2 of the License, or (at your option)
+ * any later version.
+ */
+
+#ifndef ASM_KGR_H
+#define ASM_KGR_H
+
+#include <asm/ptrace.h>
+#include <linux/stacktrace.h>
+
+static inline void kgr_set_regs_ip(struct pt_regs *regs, unsigned long ip)
+{
+ regs->link = ip;
+}
+
+static inline bool kgr_needs_lazy_migration(struct task_struct *p)
+{
+ return true;
+}
+
+#endif
diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h
index b034ecd..aa6a084 100644
--- a/arch/powerpc/include/asm/thread_info.h
+++ b/arch/powerpc/include/asm/thread_info.h
@@ -92,6 +92,7 @@ static inline struct thread_info *current_thread_info(void)
TIF_NEED_RESCHED */
#define TIF_32BIT 4 /* 32 bit binary */
#define TIF_RESTORE_TM 5 /* need to restore TM FP/VEC/VSX */
+#define TIF_KGR_IN_PROGRESS 6 /* kGraft patching in progress */
#define TIF_SYSCALL_AUDIT 7 /* syscall auditing active */
#define TIF_SINGLESTEP 8 /* singlestepping active */
#define TIF_NOHZ 9 /* in adaptive nohz mode */
@@ -115,8 +117,10 @@ static inline struct thread_info *current_thread_info(void)
#define _TIF_POLLING_NRFLAG (1<<TIF_POLLING_NRFLAG)
#define _TIF_32BIT (1<<TIF_32BIT)
#define _TIF_RESTORE_TM (1<<TIF_RESTORE_TM)
+#define _TIF_KGR_IN_PROGRESS (1<<TIF_KGR_IN_PROGRESS)
#define _TIF_SYSCALL_AUDIT (1<<TIF_SYSCALL_AUDIT)
#define _TIF_SINGLESTEP (1<<TIF_SINGLESTEP)
+#define _TIF_NOHZ (1<<TIF_NOHZ)
#define _TIF_SECCOMP (1<<TIF_SECCOMP)
#define _TIF_RESTOREALL (1<<TIF_RESTOREALL)
#define _TIF_NOERROR (1<<TIF_NOERROR)
@@ -124,7 +128,7 @@ static inline struct thread_info *current_thread_info(void)
#define _TIF_UPROBE (1<<TIF_UPROBE)
#define _TIF_SYSCALL_TRACEPOINT (1<<TIF_SYSCALL_TRACEPOINT)
#define _TIF_EMULATE_STACK_STORE (1<<TIF_EMULATE_STACK_STORE)
-#define _TIF_NOHZ (1<<TIF_NOHZ)
+
#define _TIF_SYSCALL_T_OR_A (_TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT | \
_TIF_SECCOMP | _TIF_SYSCALL_TRACEPOINT | \
_TIF_NOHZ)
@@ -132,7 +136,8 @@ static inline struct thread_info *current_thread_info(void)
#define _TIF_USER_WORK_MASK (_TIF_SIGPENDING | _TIF_NEED_RESCHED | \
_TIF_NOTIFY_RESUME | _TIF_UPROBE | \
_TIF_RESTORE_TM)
-#define _TIF_PERSYSCALL_MASK (_TIF_RESTOREALL|_TIF_NOERROR)
+
+#define _TIF_PERSYSCALL_MASK (_TIF_RESTOREALL|_TIF_NOERROR|_TIF_KGR_IN_PROGRESS)
/* Bits in local_flags */
/* Don't move TLF_NAPPING without adjusting the code in entry_32.S */
diff --git a/arch/powerpc/kernel/entry_64.S b/arch/powerpc/kernel/entry_64.S
index 5bbd1bc..569acd4 100644
--- a/arch/powerpc/kernel/entry_64.S
+++ b/arch/powerpc/kernel/entry_64.S
@@ -151,8 +151,8 @@ END_FW_FTR_SECTION_IFSET(FW_FEATURE_SPLPAR)
#endif
CURRENT_THREAD_INFO(r11, r1)
ld r10,TI_FLAGS(r11)
- andi. r11,r10,_TIF_SYSCALL_T_OR_A
- bne syscall_dotrace
+ andi. r10,r10,(_TIF_SYSCALL_T_OR_A|_TIF_KGR_IN_PROGRESS)
+ bne- syscall_precall
.Lsyscall_dotrace_cont:
cmpldi 0,r0,NR_syscalls
bge- syscall_enosys
@@ -245,6 +245,17 @@ syscall_error:
neg r3,r3
std r5,_CCR(r1)
b .Lsyscall_error_cont
+
+syscall_precall:
+ andi. r10,r10,(_TIF_KGR_IN_PROGRESS)
+ beq+ syscall_dotrace
+
+ addi r11,r11,TI_FLAGS
+1: ldarx r12,0,r11
+ andc r12,r12,r10
+ stdcx. r12,0,r11
+ bne- 1b
+ subi r11,r11,TI_FLAGS
/* Traced system call support */
syscall_dotrace:
^ permalink raw reply related [flat|nested] 5+ messages in thread
* [PATCH v0 4/4] ppc64le: kgraft config options
2015-03-19 20:35 [PATCH v0 0/4] ppc64le: dynamic ftrace and kgraft support Torsten Duwe
` (2 preceding siblings ...)
2015-03-19 20:51 ` [PATCH v0 3/4] ppc64le: kgraft support Torsten Duwe
@ 2015-03-19 20:54 ` Torsten Duwe
3 siblings, 0 replies; 5+ messages in thread
From: Torsten Duwe @ 2015-03-19 20:54 UTC (permalink / raw)
To: ppc-dev; +Cc: Linux Kernel Mailing List
Enable kgraft on ppc, fairly trivial.
diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig
index 4bc7b62..d82d7c8 100644
--- a/arch/powerpc/Kconfig
+++ b/arch/powerpc/Kconfig
@@ -102,6 +104,7 @@ config PPC
select HAVE_IOREMAP_PROT
select HAVE_EFFICIENT_UNALIGNED_ACCESS if !CPU_LITTLE_ENDIAN
select HAVE_KPROBES
+ select HAVE_KGRAFT
select HAVE_ARCH_KGDB
select HAVE_KRETPROBES
select HAVE_ARCH_TRACEHOOK
@@ -291,6 +294,8 @@ source "init/Kconfig"
source "kernel/Kconfig.freezer"
+source "kernel/Kconfig.kgraft"
+
source "arch/powerpc/sysdev/Kconfig"
source "arch/powerpc/platforms/Kconfig"
^ permalink raw reply related [flat|nested] 5+ messages in thread
end of thread, other threads:[~2015-03-19 20:54 UTC | newest]
Thread overview: 5+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-03-19 20:35 [PATCH v0 0/4] ppc64le: dynamic ftrace and kgraft support Torsten Duwe
2015-03-19 20:45 ` [PATCH v0 1/4] ppc64le: dynamic ftrace Torsten Duwe
2015-03-19 20:48 ` [PATCH v0 2/4] ppc64le: dynamic ftrace configuration options Torsten Duwe
2015-03-19 20:51 ` [PATCH v0 3/4] ppc64le: kgraft support Torsten Duwe
2015-03-19 20:54 ` [PATCH v0 4/4] ppc64le: kgraft config options Torsten Duwe
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).