Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
L
linux
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Commits
Issue Boards
Open sidebar
Kirill Smelkov
linux
Commits
98580960
Commit
98580960
authored
Nov 16, 2008
by
Ingo Molnar
Browse files
Options
Browse Files
Download
Plain Diff
Merge branch 'tracing/ftrace' into tracing/function-return-tracer
parents
c91add5f
1c80025a
Changes
18
Hide whitespace changes
Inline
Side-by-side
Showing
18 changed files
with
284 additions
and
164 deletions
+284
-164
arch/x86/include/asm/ftrace.h
arch/x86/include/asm/ftrace.h
+8
-0
arch/x86/kernel/ftrace.c
arch/x86/kernel/ftrace.c
+26
-3
include/linux/ftrace.h
include/linux/ftrace.h
+41
-12
kernel/module.c
kernel/module.c
+1
-1
kernel/trace/ftrace.c
kernel/trace/ftrace.c
+109
-115
kernel/trace/trace.c
kernel/trace/trace.c
+14
-9
kernel/trace/trace.h
kernel/trace/trace.h
+2
-1
kernel/trace/trace_boot.c
kernel/trace/trace_boot.c
+2
-1
kernel/trace/trace_branch.c
kernel/trace/trace_branch.c
+2
-1
kernel/trace/trace_functions.c
kernel/trace/trace_functions.c
+2
-1
kernel/trace/trace_functions_return.c
kernel/trace/trace_functions_return.c
+2
-1
kernel/trace/trace_irqsoff.c
kernel/trace/trace_irqsoff.c
+6
-3
kernel/trace/trace_mmiotrace.c
kernel/trace/trace_mmiotrace.c
+2
-1
kernel/trace/trace_nop.c
kernel/trace/trace_nop.c
+2
-1
kernel/trace/trace_sched_switch.c
kernel/trace/trace_sched_switch.c
+2
-1
kernel/trace/trace_sched_wakeup.c
kernel/trace/trace_sched_wakeup.c
+2
-1
kernel/trace/trace_selftest.c
kernel/trace/trace_selftest.c
+59
-11
kernel/trace/trace_sysprof.c
kernel/trace/trace_sysprof.c
+2
-1
No files found.
arch/x86/include/asm/ftrace.h
View file @
98580960
...
...
@@ -17,6 +17,14 @@ static inline unsigned long ftrace_call_adjust(unsigned long addr)
*/
return
addr
-
1
;
}
#ifdef CONFIG_DYNAMIC_FTRACE
struct
dyn_arch_ftrace
{
/* No extra data needed for x86 */
};
#endif
/* CONFIG_DYNAMIC_FTRACE */
#endif
/* __ASSEMBLY__ */
#endif
/* CONFIG_FUNCTION_TRACER */
...
...
arch/x86/kernel/ftrace.c
View file @
98580960
...
...
@@ -166,7 +166,7 @@ static int ftrace_calc_offset(long ip, long addr)
return
(
int
)(
addr
-
ip
);
}
unsigned
char
*
ftrace_call_replace
(
unsigned
long
ip
,
unsigned
long
addr
)
static
unsigned
char
*
ftrace_call_replace
(
unsigned
long
ip
,
unsigned
long
addr
)
{
static
union
ftrace_code_union
calc
;
...
...
@@ -311,12 +311,12 @@ do_ftrace_mod_code(unsigned long ip, void *new_code)
static
unsigned
char
ftrace_nop
[
MCOUNT_INSN_SIZE
];
unsigned
char
*
ftrace_nop_replace
(
void
)
static
unsigned
char
*
ftrace_nop_replace
(
void
)
{
return
ftrace_nop
;
}
int
static
int
ftrace_modify_code
(
unsigned
long
ip
,
unsigned
char
*
old_code
,
unsigned
char
*
new_code
)
{
...
...
@@ -349,6 +349,29 @@ ftrace_modify_code(unsigned long ip, unsigned char *old_code,
return
0
;
}
int
ftrace_make_nop
(
struct
module
*
mod
,
struct
dyn_ftrace
*
rec
,
unsigned
long
addr
)
{
unsigned
char
*
new
,
*
old
;
unsigned
long
ip
=
rec
->
ip
;
old
=
ftrace_call_replace
(
ip
,
addr
);
new
=
ftrace_nop_replace
();
return
ftrace_modify_code
(
rec
->
ip
,
old
,
new
);
}
int
ftrace_make_call
(
struct
dyn_ftrace
*
rec
,
unsigned
long
addr
)
{
unsigned
char
*
new
,
*
old
;
unsigned
long
ip
=
rec
->
ip
;
old
=
ftrace_nop_replace
();
new
=
ftrace_call_replace
(
ip
,
addr
);
return
ftrace_modify_code
(
rec
->
ip
,
old
,
new
);
}
int
ftrace_update_ftrace_func
(
ftrace_func_t
func
)
{
unsigned
long
ip
=
(
unsigned
long
)(
&
ftrace_call
);
...
...
include/linux/ftrace.h
View file @
98580960
...
...
@@ -74,6 +74,9 @@ static inline void ftrace_start(void) { }
#endif
/* CONFIG_FUNCTION_TRACER */
#ifdef CONFIG_DYNAMIC_FTRACE
/* asm/ftrace.h must be defined for archs supporting dynamic ftrace */
#include <asm/ftrace.h>
enum
{
FTRACE_FL_FREE
=
(
1
<<
0
),
FTRACE_FL_FAILED
=
(
1
<<
1
),
...
...
@@ -88,6 +91,7 @@ struct dyn_ftrace {
struct
list_head
list
;
unsigned
long
ip
;
/* address of mcount call-site */
unsigned
long
flags
;
struct
dyn_arch_ftrace
arch
;
};
int
ftrace_force_update
(
void
);
...
...
@@ -95,22 +99,40 @@ void ftrace_set_filter(unsigned char *buf, int len, int reset);
/* defined in arch */
extern
int
ftrace_ip_converted
(
unsigned
long
ip
);
extern
unsigned
char
*
ftrace_nop_replace
(
void
);
extern
unsigned
char
*
ftrace_call_replace
(
unsigned
long
ip
,
unsigned
long
addr
);
extern
int
ftrace_dyn_arch_init
(
void
*
data
);
extern
int
ftrace_update_ftrace_func
(
ftrace_func_t
func
);
extern
void
ftrace_caller
(
void
);
extern
void
ftrace_call
(
void
);
extern
void
mcount_call
(
void
);
/* May be defined in arch */
extern
int
ftrace_arch_read_dyn_info
(
char
*
buf
,
int
size
);
/**
* ftrace_make_nop - convert code into top
* @mod: module structure if called by module load initialization
* @rec: the mcount call site record
* @addr: the address that the call site should be calling
*
* This is a very sensitive operation and great care needs
* to be taken by the arch. The operation should carefully
* read the location, check to see if what is read is indeed
* what we expect it to be, and then on success of the compare,
* it should write to the location.
*
* The code segment at @rec->ip should be a caller to @addr
*
* Return must be:
* 0 on success
* -EFAULT on error reading the location
* -EINVAL on a failed compare of the contents
* -EPERM on error writing to the location
* Any other value will be considered a failure.
*/
extern
int
ftrace_make_nop
(
struct
module
*
mod
,
struct
dyn_ftrace
*
rec
,
unsigned
long
addr
);
/**
* ftrace_modify_code - modify code segment
* @ip: the address of the code segment
* @old_code: the contents of what is expected to be there
* @new_code: the code to patch in
* ftrace_make_call - convert a nop call site into a call to addr
* @rec: the mcount call site record
* @addr: the address that the call site should call
*
* This is a very sensitive operation and great care needs
* to be taken by the arch. The operation should carefully
...
...
@@ -118,6 +140,8 @@ extern int ftrace_arch_read_dyn_info(char *buf, int size);
* what we expect it to be, and then on success of the compare,
* it should write to the location.
*
* The code segment at @rec->ip should be a nop
*
* Return must be:
* 0 on success
* -EFAULT on error reading the location
...
...
@@ -125,8 +149,11 @@ extern int ftrace_arch_read_dyn_info(char *buf, int size);
* -EPERM on error writing to the location
* Any other value will be considered a failure.
*/
extern
int
ftrace_modify_code
(
unsigned
long
ip
,
unsigned
char
*
old_code
,
unsigned
char
*
new_code
);
extern
int
ftrace_make_call
(
struct
dyn_ftrace
*
rec
,
unsigned
long
addr
);
/* May be defined in arch */
extern
int
ftrace_arch_read_dyn_info
(
char
*
buf
,
int
size
);
extern
int
skip_trace
(
unsigned
long
ip
);
...
...
@@ -259,11 +286,13 @@ static inline void ftrace_dump(void) { }
#ifdef CONFIG_FTRACE_MCOUNT_RECORD
extern
void
ftrace_init
(
void
);
extern
void
ftrace_init_module
(
unsigned
long
*
start
,
unsigned
long
*
end
);
extern
void
ftrace_init_module
(
struct
module
*
mod
,
unsigned
long
*
start
,
unsigned
long
*
end
);
#else
static
inline
void
ftrace_init
(
void
)
{
}
static
inline
void
ftrace_init_module
(
unsigned
long
*
start
,
unsigned
long
*
end
)
{
}
ftrace_init_module
(
struct
module
*
mod
,
unsigned
long
*
start
,
unsigned
long
*
end
)
{
}
#endif
...
...
kernel/module.c
View file @
98580960
...
...
@@ -2201,7 +2201,7 @@ static noinline struct module *load_module(void __user *umod,
/* sechdrs[0].sh_size is always zero */
mseg
=
section_objs
(
hdr
,
sechdrs
,
secstrings
,
"__mcount_loc"
,
sizeof
(
*
mseg
),
&
num_mcount
);
ftrace_init_module
(
mseg
,
mseg
+
num_mcount
);
ftrace_init_module
(
m
od
,
m
seg
,
mseg
+
num_mcount
);
err
=
module_finalize
(
hdr
,
sechdrs
,
mod
);
if
(
err
<
0
)
...
...
kernel/trace/ftrace.c
View file @
98580960
...
...
@@ -334,7 +334,7 @@ ftrace_record_ip(unsigned long ip)
{
struct
dyn_ftrace
*
rec
;
if
(
!
ftrace_enabled
||
ftrace_disabled
)
if
(
ftrace_disabled
)
return
NULL
;
rec
=
ftrace_alloc_dyn_node
(
ip
);
...
...
@@ -348,107 +348,129 @@ ftrace_record_ip(unsigned long ip)
return
rec
;
}
static
void
print_ip_ins
(
const
char
*
fmt
,
unsigned
char
*
p
)
{
int
i
;
printk
(
KERN_CONT
"%s"
,
fmt
);
for
(
i
=
0
;
i
<
MCOUNT_INSN_SIZE
;
i
++
)
printk
(
KERN_CONT
"%s%02x"
,
i
?
":"
:
""
,
p
[
i
]);
}
static
void
ftrace_bug
(
int
failed
,
unsigned
long
ip
)
{
switch
(
failed
)
{
case
-
EFAULT
:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace faulted on modifying "
);
print_ip_sym
(
ip
);
break
;
case
-
EINVAL
:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace failed to modify "
);
print_ip_sym
(
ip
);
print_ip_ins
(
" actual: "
,
(
unsigned
char
*
)
ip
);
printk
(
KERN_CONT
"
\n
"
);
break
;
case
-
EPERM
:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace faulted on writing "
);
print_ip_sym
(
ip
);
break
;
default:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace faulted on unknown error "
);
print_ip_sym
(
ip
);
}
}
#define FTRACE_ADDR ((long)(ftrace_caller))
static
int
__ftrace_replace_code
(
struct
dyn_ftrace
*
rec
,
unsigned
char
*
old
,
unsigned
char
*
new
,
int
enable
)
__ftrace_replace_code
(
struct
dyn_ftrace
*
rec
,
int
enable
)
{
unsigned
long
ip
,
fl
;
ip
=
rec
->
ip
;
if
(
ftrace_filtered
&&
enable
)
{
/*
* If this record is not to be traced and
* it is not enabled then do nothing.
*
* If this record is not to be traced and
* it is enabled then disabled it.
*
*/
if
(
rec
->
flags
&
FTRACE_FL_NOTRACE
)
{
if
(
rec
->
flags
&
FTRACE_FL_ENABLED
)
rec
->
flags
&=
~
FTRACE_FL_ENABLED
;
else
return
0
;
}
else
if
(
ftrace_filtered
&&
enable
)
{
/*
* If filtering is on:
*
* If this record is set to be filtered and
* is enabled then do nothing.
*
* If this record is set to be filtered and
* it is not enabled, enable it.
*
* If this record is not set to be filtered
* and it is not enabled do nothing.
*
* If this record is set not to trace then
* do nothing.
*
* If this record is set not to trace and
* it is enabled then disable it.
*
* If this record is not set to be filtered and
* it is enabled, disable it.
* Filtering is on:
*/
fl
=
rec
->
flags
&
(
FTRACE_FL_FILTER
|
FTRACE_FL_NOTRACE
|
FTRACE_FL_ENABLED
);
fl
=
rec
->
flags
&
(
FTRACE_FL_FILTER
|
FTRACE_FL_ENABLED
);
if
((
fl
==
(
FTRACE_FL_FILTER
|
FTRACE_FL_ENABLED
))
||
(
fl
==
(
FTRACE_FL_FILTER
|
FTRACE_FL_NOTRACE
))
||
!
fl
||
(
fl
==
FTRACE_FL_NOTRACE
))
/* Record is filtered and enabled, do nothing */
if
(
fl
==
(
FTRACE_FL_FILTER
|
FTRACE_FL_ENABLED
))
return
0
;
/*
* If it is enabled disable it,
* otherwise enable it!
*/
if
(
fl
&
FTRACE_FL_ENABLED
)
{
/* swap new and old */
new
=
old
;
old
=
ftrace_call_replace
(
ip
,
FTRACE_ADDR
);
/* Record is not filtered and is not enabled do nothing */
if
(
!
fl
)
return
0
;
/* Record is not filtered but enabled, disable it */
if
(
fl
==
FTRACE_FL_ENABLED
)
rec
->
flags
&=
~
FTRACE_FL_ENABLED
;
}
else
{
new
=
ftrace_call_replace
(
ip
,
FTRACE_ADDR
);
else
/* Otherwise record is filtered but not enabled, enable it */
rec
->
flags
|=
FTRACE_FL_ENABLED
;
}
}
else
{
/* Disable or not filtered */
if
(
enable
)
{
/*
* If this record is set not to trace and is
* not enabled, do nothing.
*/
fl
=
rec
->
flags
&
(
FTRACE_FL_NOTRACE
|
FTRACE_FL_ENABLED
);
if
(
fl
==
FTRACE_FL_NOTRACE
)
return
0
;
new
=
ftrace_call_replace
(
ip
,
FTRACE_ADDR
);
}
else
old
=
ftrace_call_replace
(
ip
,
FTRACE_ADDR
);
if
(
enable
)
{
/* if record is enabled, do nothing */
if
(
rec
->
flags
&
FTRACE_FL_ENABLED
)
return
0
;
rec
->
flags
|=
FTRACE_FL_ENABLED
;
}
else
{
/* if record is not enabled do nothing */
if
(
!
(
rec
->
flags
&
FTRACE_FL_ENABLED
))
return
0
;
rec
->
flags
&=
~
FTRACE_FL_ENABLED
;
}
}
return
ftrace_modify_code
(
ip
,
old
,
new
);
if
(
rec
->
flags
&
FTRACE_FL_ENABLED
)
return
ftrace_make_call
(
rec
,
FTRACE_ADDR
);
else
return
ftrace_make_nop
(
NULL
,
rec
,
FTRACE_ADDR
);
}
static
void
ftrace_replace_code
(
int
enable
)
{
int
i
,
failed
;
unsigned
char
*
new
=
NULL
,
*
old
=
NULL
;
struct
dyn_ftrace
*
rec
;
struct
ftrace_page
*
pg
;
if
(
enable
)
old
=
ftrace_nop_replace
();
else
new
=
ftrace_nop_replace
();
for
(
pg
=
ftrace_pages_start
;
pg
;
pg
=
pg
->
next
)
{
for
(
i
=
0
;
i
<
pg
->
index
;
i
++
)
{
rec
=
&
pg
->
records
[
i
];
/* don't modify code that has already faulted */
if
(
rec
->
flags
&
FTRACE_FL_FAILED
)
/*
* Skip over free records and records that have
* failed.
*/
if
(
rec
->
flags
&
FTRACE_FL_FREE
||
rec
->
flags
&
FTRACE_FL_FAILED
)
continue
;
/* ignore updates to this record's mcount site */
...
...
@@ -459,68 +481,30 @@ static void ftrace_replace_code(int enable)
unfreeze_record
(
rec
);
}
failed
=
__ftrace_replace_code
(
rec
,
old
,
new
,
enable
);
failed
=
__ftrace_replace_code
(
rec
,
enable
);
if
(
failed
&&
(
rec
->
flags
&
FTRACE_FL_CONVERTED
))
{
rec
->
flags
|=
FTRACE_FL_FAILED
;
if
((
system_state
==
SYSTEM_BOOTING
)
||
!
core_kernel_text
(
rec
->
ip
))
{
ftrace_free_rec
(
rec
);
}
}
else
ftrace_bug
(
failed
,
rec
->
ip
);
}
}
}
}
static
void
print_ip_ins
(
const
char
*
fmt
,
unsigned
char
*
p
)
{
int
i
;
printk
(
KERN_CONT
"%s"
,
fmt
);
for
(
i
=
0
;
i
<
MCOUNT_INSN_SIZE
;
i
++
)
printk
(
KERN_CONT
"%s%02x"
,
i
?
":"
:
""
,
p
[
i
]);
}
static
int
ftrace_code_disable
(
struct
dyn_ftrace
*
rec
)
ftrace_code_disable
(
struct
module
*
mod
,
struct
dyn_ftrace
*
rec
)
{
unsigned
long
ip
;
unsigned
char
*
nop
,
*
call
;
int
ret
;
ip
=
rec
->
ip
;
nop
=
ftrace_nop_replace
();
call
=
ftrace_call_replace
(
ip
,
mcount_addr
);
ret
=
ftrace_modify_code
(
ip
,
call
,
nop
);
ret
=
ftrace_make_nop
(
mod
,
rec
,
mcount_addr
);
if
(
ret
)
{
switch
(
ret
)
{
case
-
EFAULT
:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace faulted on modifying "
);
print_ip_sym
(
ip
);
break
;
case
-
EINVAL
:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace failed to modify "
);
print_ip_sym
(
ip
);
print_ip_ins
(
" expected: "
,
call
);
print_ip_ins
(
" actual: "
,
(
unsigned
char
*
)
ip
);
print_ip_ins
(
" replace: "
,
nop
);
printk
(
KERN_CONT
"
\n
"
);
break
;
case
-
EPERM
:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace faulted on writing "
);
print_ip_sym
(
ip
);
break
;
default:
FTRACE_WARN_ON_ONCE
(
1
);
pr_info
(
"ftrace faulted on unknown error "
);
print_ip_sym
(
ip
);
}
ftrace_bug
(
ret
,
ip
);
rec
->
flags
|=
FTRACE_FL_FAILED
;
return
0
;
}
...
...
@@ -560,8 +544,7 @@ static void ftrace_startup(void)
mutex_lock
(
&
ftrace_start_lock
);
ftrace_start_up
++
;
if
(
ftrace_start_up
==
1
)
command
|=
FTRACE_ENABLE_CALLS
;
command
|=
FTRACE_ENABLE_CALLS
;
if
(
saved_ftrace_func
!=
ftrace_trace_function
)
{
saved_ftrace_func
=
ftrace_trace_function
;
...
...
@@ -639,7 +622,7 @@ static cycle_t ftrace_update_time;
static
unsigned
long
ftrace_update_cnt
;
unsigned
long
ftrace_update_tot_cnt
;
static
int
ftrace_update_code
(
voi
d
)
static
int
ftrace_update_code
(
struct
module
*
mo
d
)
{
struct
dyn_ftrace
*
p
,
*
t
;
cycle_t
start
,
stop
;
...
...
@@ -656,7 +639,7 @@ static int ftrace_update_code(void)
list_del_init
(
&
p
->
list
);
/* convert record (i.e, patch mcount-call with NOP) */
if
(
ftrace_code_disable
(
p
))
{
if
(
ftrace_code_disable
(
mod
,
p
))
{
p
->
flags
|=
FTRACE_FL_CONVERTED
;
ftrace_update_cnt
++
;
}
else
...
...
@@ -1211,7 +1194,7 @@ ftrace_regex_release(struct inode *inode, struct file *file, int enable)
mutex_lock
(
&
ftrace_sysctl_lock
);
mutex_lock
(
&
ftrace_start_lock
);
if
(
iter
->
filtered
&&
ftrace_start_up
&&
ftrace_enabled
)
if
(
ftrace_start_up
&&
ftrace_enabled
)
ftrace_run_update_code
(
FTRACE_ENABLE_CALLS
);
mutex_unlock
(
&
ftrace_start_lock
);
mutex_unlock
(
&
ftrace_sysctl_lock
);
...
...
@@ -1298,7 +1281,8 @@ static __init int ftrace_init_debugfs(void)
fs_initcall
(
ftrace_init_debugfs
);
static
int
ftrace_convert_nops
(
unsigned
long
*
start
,
static
int
ftrace_convert_nops
(
struct
module
*
mod
,
unsigned
long
*
start
,
unsigned
long
*
end
)
{
unsigned
long
*
p
;
...
...
@@ -1309,23 +1293,32 @@ static int ftrace_convert_nops(unsigned long *start,
p
=
start
;
while
(
p
<
end
)
{
addr
=
ftrace_call_adjust
(
*
p
++
);
/*
* Some architecture linkers will pad between
* the different mcount_loc sections of different
* object files to satisfy alignments.
* Skip any NULL pointers.
*/
if
(
!
addr
)
continue
;
ftrace_record_ip
(
addr
);
}
/* disable interrupts to prevent kstop machine */
local_irq_save
(
flags
);
ftrace_update_code
();
ftrace_update_code
(
mod
);
local_irq_restore
(
flags
);
mutex_unlock
(
&
ftrace_start_lock
);
return
0
;
}
void
ftrace_init_module
(
unsigned
long
*
start
,
unsigned
long
*
end
)
void
ftrace_init_module
(
struct
module
*
mod
,
unsigned
long
*
start
,
unsigned
long
*
end
)
{
if
(
ftrace_disabled
||
start
==
end
)
return
;
ftrace_convert_nops
(
start
,
end
);
ftrace_convert_nops
(
mod
,
start
,
end
);
}
extern
unsigned
long
__start_mcount_loc
[];
...
...
@@ -1355,7 +1348,8 @@ void __init ftrace_init(void)
last_ftrace_enabled
=
ftrace_enabled
=
1
;
ret
=
ftrace_convert_nops
(
__start_mcount_loc
,
ret
=
ftrace_convert_nops
(
NULL
,
__start_mcount_loc
,
__stop_mcount_loc
);
return
;
...
...
kernel/trace/trace.c
View file @
98580960
...
...
@@ -1051,7 +1051,7 @@ function_trace_call(unsigned long ip, unsigned long parent_ip)
* Need to use raw, since this must be called before the
* recursive protection is performed.
*/
raw_
local_irq_save
(
flags
);
local_irq_save
(
flags
);
cpu
=
raw_smp_processor_id
();
data
=
tr
->
data
[
cpu
];
disabled
=
atomic_inc_return
(
&
data
->
disabled
);
...
...
@@ -1062,7 +1062,7 @@ function_trace_call(unsigned long ip, unsigned long parent_ip)
}
atomic_dec
(
&
data
->
disabled
);
raw_
local_irq_restore
(
flags
);
local_irq_restore
(
flags
);
}
#ifdef CONFIG_FUNCTION_RET_TRACER
...
...
@@ -2638,8 +2638,11 @@ static int tracing_set_tracer(char *buf)
current_trace
->
reset
(
tr
);
current_trace
=
t
;
if
(
t
->
init
)
t
->
init
(
tr
);
if
(
t
->
init
)
{
ret
=
t
->
init
(
tr
);
if
(
ret
)
goto
out
;
}
trace_branch_enable
(
tr
);
out:
...
...
@@ -2655,6 +2658,9 @@ tracing_set_trace_write(struct file *filp, const char __user *ubuf,
char
buf
[
max_tracer_type_len
+
1
];
int
i
;
size_t
ret
;
int
err
;
ret
=
cnt
;
if
(
cnt
>
max_tracer_type_len
)
cnt
=
max_tracer_type_len
;
...
...
@@ -2668,12 +2674,11 @@ tracing_set_trace_write(struct file *filp, const char __user *ubuf,
for
(
i
=
cnt
-
1
;
i
>
0
&&
isspace
(
buf
[
i
]);
i
--
)
buf
[
i
]
=
0
;
ret
=
tracing_set_tracer
(
buf
);
if
(
!
ret
)
ret
=
cnt
;
err
=
tracing_set_tracer
(
buf
);
if
(
err
)
ret
urn
err
;
if
(
ret
>
0
)
filp
->
f_pos
+=
ret
;
filp
->
f_pos
+=
ret
;
return
ret
;
}
...
...
kernel/trace/trace.h
View file @
98580960
...
...
@@ -264,7 +264,8 @@ enum print_line_t {
*/
struct
tracer
{
const
char
*
name
;
void
(
*
init
)(
struct
trace_array
*
tr
);
/* Your tracer should raise a warning if init fails */
int
(
*
init
)(
struct
trace_array
*
tr
);
void
(
*
reset
)(
struct
trace_array
*
tr
);
void
(
*
start
)(
struct
trace_array
*
tr
);
void
(
*
stop
)(
struct
trace_array
*
tr
);
...
...
kernel/trace/trace_boot.c
View file @
98580960
...
...
@@ -47,7 +47,7 @@ static void reset_boot_trace(struct trace_array *tr)
tracing_reset
(
tr
,
cpu
);
}
static
void
boot_trace_init
(
struct
trace_array
*
tr
)
static
int
boot_trace_init
(
struct
trace_array
*
tr
)
{
int
cpu
;
boot_trace
=
tr
;
...
...
@@ -56,6 +56,7 @@ static void boot_trace_init(struct trace_array *tr)
tracing_reset
(
tr
,
cpu
);
tracing_sched_switch_assign_trace
(
tr
);
return
0
;
}
static
enum
print_line_t
...
...
kernel/trace/trace_branch.c
View file @
98580960
...
...
@@ -125,7 +125,7 @@ static void stop_branch_trace(struct trace_array *tr)
disable_branch_tracing
();
}
static
void
branch_trace_init
(
struct
trace_array
*
tr
)
static
int
branch_trace_init
(
struct
trace_array
*
tr
)
{
int
cpu
;
...
...
@@ -133,6 +133,7 @@ static void branch_trace_init(struct trace_array *tr)
tracing_reset
(
tr
,
cpu
);
start_branch_trace
(
tr
);
return
0
;
}
static
void
branch_trace_reset
(
struct
trace_array
*
tr
)
...
...
kernel/trace/trace_functions.c
View file @
98580960
...
...
@@ -42,9 +42,10 @@ static void stop_function_trace(struct trace_array *tr)
tracing_stop_cmdline_record
();
}
static
void
function_trace_init
(
struct
trace_array
*
tr
)
static
int
function_trace_init
(
struct
trace_array
*
tr
)
{
start_function_trace
(
tr
);
return
0
;
}
static
void
function_trace_reset
(
struct
trace_array
*
tr
)
...
...
kernel/trace/trace_functions_return.c
View file @
98580960
...
...
@@ -24,13 +24,14 @@ static void stop_return_trace(struct trace_array *tr)
unregister_ftrace_return
();
}
static
void
return_trace_init
(
struct
trace_array
*
tr
)
static
int
return_trace_init
(
struct
trace_array
*
tr
)
{
int
cpu
;
for_each_online_cpu
(
cpu
)
tracing_reset
(
tr
,
cpu
);
start_return_trace
(
tr
);
return
0
;
}
static
void
return_trace_reset
(
struct
trace_array
*
tr
)
...
...
kernel/trace/trace_irqsoff.c
View file @
98580960
...
...
@@ -416,11 +416,12 @@ static void irqsoff_tracer_close(struct trace_iterator *iter)
}
#ifdef CONFIG_IRQSOFF_TRACER
static
void
irqsoff_tracer_init
(
struct
trace_array
*
tr
)
static
int
irqsoff_tracer_init
(
struct
trace_array
*
tr
)
{
trace_type
=
TRACER_IRQS_OFF
;
__irqsoff_tracer_init
(
tr
);
return
0
;
}
static
struct
tracer
irqsoff_tracer
__read_mostly
=
{
...
...
@@ -442,11 +443,12 @@ static struct tracer irqsoff_tracer __read_mostly =
#endif
#ifdef CONFIG_PREEMPT_TRACER
static
void
preemptoff_tracer_init
(
struct
trace_array
*
tr
)
static
int
preemptoff_tracer_init
(
struct
trace_array
*
tr
)
{
trace_type
=
TRACER_PREEMPT_OFF
;
__irqsoff_tracer_init
(
tr
);
return
0
;
}
static
struct
tracer
preemptoff_tracer
__read_mostly
=
...
...
@@ -471,11 +473,12 @@ static struct tracer preemptoff_tracer __read_mostly =
#if defined(CONFIG_IRQSOFF_TRACER) && \
defined(CONFIG_PREEMPT_TRACER)
static
void
preemptirqsoff_tracer_init
(
struct
trace_array
*
tr
)
static
int
preemptirqsoff_tracer_init
(
struct
trace_array
*
tr
)
{
trace_type
=
TRACER_IRQS_OFF
|
TRACER_PREEMPT_OFF
;
__irqsoff_tracer_init
(
tr
);
return
0
;
}
static
struct
tracer
preemptirqsoff_tracer
__read_mostly
=
...
...
kernel/trace/trace_mmiotrace.c
View file @
98580960
...
...
@@ -30,13 +30,14 @@ static void mmio_reset_data(struct trace_array *tr)
tracing_reset
(
tr
,
cpu
);
}
static
void
mmio_trace_init
(
struct
trace_array
*
tr
)
static
int
mmio_trace_init
(
struct
trace_array
*
tr
)
{
pr_debug
(
"in %s
\n
"
,
__func__
);
mmio_trace_array
=
tr
;
mmio_reset_data
(
tr
);
enable_mmiotrace
();
return
0
;
}
static
void
mmio_trace_reset
(
struct
trace_array
*
tr
)
...
...
kernel/trace/trace_nop.c
View file @
98580960
...
...
@@ -24,7 +24,7 @@ static void stop_nop_trace(struct trace_array *tr)
/* Nothing to do! */
}
static
void
nop_trace_init
(
struct
trace_array
*
tr
)
static
int
nop_trace_init
(
struct
trace_array
*
tr
)
{
int
cpu
;
ctx_trace
=
tr
;
...
...
@@ -33,6 +33,7 @@ static void nop_trace_init(struct trace_array *tr)
tracing_reset
(
tr
,
cpu
);
start_nop_trace
(
tr
);
return
0
;
}
static
void
nop_trace_reset
(
struct
trace_array
*
tr
)
...
...
kernel/trace/trace_sched_switch.c
View file @
98580960
...
...
@@ -206,10 +206,11 @@ static void stop_sched_trace(struct trace_array *tr)
tracing_stop_sched_switch_record
();
}
static
void
sched_switch_trace_init
(
struct
trace_array
*
tr
)
static
int
sched_switch_trace_init
(
struct
trace_array
*
tr
)
{
ctx_trace
=
tr
;
start_sched_trace
(
tr
);
return
0
;
}
static
void
sched_switch_trace_reset
(
struct
trace_array
*
tr
)
...
...
kernel/trace/trace_sched_wakeup.c
View file @
98580960
...
...
@@ -331,10 +331,11 @@ static void stop_wakeup_tracer(struct trace_array *tr)
unregister_trace_sched_wakeup
(
probe_wakeup
);
}
static
void
wakeup_tracer_init
(
struct
trace_array
*
tr
)
static
int
wakeup_tracer_init
(
struct
trace_array
*
tr
)
{
wakeup_trace
=
tr
;
start_wakeup_tracer
(
tr
);
return
0
;
}
static
void
wakeup_tracer_reset
(
struct
trace_array
*
tr
)
...
...
kernel/trace/trace_selftest.c
View file @
98580960
...
...
@@ -52,7 +52,7 @@ static int trace_test_buffer(struct trace_array *tr, unsigned long *count)
int
cpu
,
ret
=
0
;
/* Don't allow flipping of max traces now */
raw_
local_irq_save
(
flags
);
local_irq_save
(
flags
);
__raw_spin_lock
(
&
ftrace_max_lock
);
cnt
=
ring_buffer_entries
(
tr
->
buffer
);
...
...
@@ -63,7 +63,7 @@ static int trace_test_buffer(struct trace_array *tr, unsigned long *count)
break
;
}
__raw_spin_unlock
(
&
ftrace_max_lock
);
raw_
local_irq_restore
(
flags
);
local_irq_restore
(
flags
);
if
(
count
)
*
count
=
cnt
;
...
...
@@ -71,6 +71,11 @@ static int trace_test_buffer(struct trace_array *tr, unsigned long *count)
return
ret
;
}
static
inline
void
warn_failed_init_tracer
(
struct
tracer
*
trace
,
int
init_ret
)
{
printk
(
KERN_WARNING
"Failed to init %s tracer, init returned %d
\n
"
,
trace
->
name
,
init_ret
);
}
#ifdef CONFIG_FUNCTION_TRACER
#ifdef CONFIG_DYNAMIC_FTRACE
...
...
@@ -111,7 +116,11 @@ int trace_selftest_startup_dynamic_tracing(struct tracer *trace,
ftrace_set_filter
(
func_name
,
strlen
(
func_name
),
1
);
/* enable tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
goto
out
;
}
/* Sleep for a 1/10 of a second */
msleep
(
100
);
...
...
@@ -181,7 +190,12 @@ trace_selftest_startup_function(struct tracer *trace, struct trace_array *tr)
ftrace_enabled
=
1
;
tracer_enabled
=
1
;
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
goto
out
;
}
/* Sleep for a 1/10 of a second */
msleep
(
100
);
/* stop the tracing. */
...
...
@@ -223,7 +237,12 @@ trace_selftest_startup_irqsoff(struct tracer *trace, struct trace_array *tr)
int
ret
;
/* start the tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
return
ret
;
}
/* reset the max latency */
tracing_max_latency
=
0
;
/* disable interrupts for a bit */
...
...
@@ -272,7 +291,12 @@ trace_selftest_startup_preemptoff(struct tracer *trace, struct trace_array *tr)
}
/* start the tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
return
ret
;
}
/* reset the max latency */
tracing_max_latency
=
0
;
/* disable preemption for a bit */
...
...
@@ -321,7 +345,11 @@ trace_selftest_startup_preemptirqsoff(struct tracer *trace, struct trace_array *
}
/* start the tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
goto
out
;
}
/* reset the max latency */
tracing_max_latency
=
0
;
...
...
@@ -449,7 +477,12 @@ trace_selftest_startup_wakeup(struct tracer *trace, struct trace_array *tr)
wait_for_completion
(
&
isrt
);
/* start the tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
return
ret
;
}
/* reset the max latency */
tracing_max_latency
=
0
;
...
...
@@ -505,7 +538,12 @@ trace_selftest_startup_sched_switch(struct tracer *trace, struct trace_array *tr
int
ret
;
/* start the tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
return
ret
;
}
/* Sleep for a 1/10 of a second */
msleep
(
100
);
/* stop the tracing. */
...
...
@@ -532,7 +570,12 @@ trace_selftest_startup_sysprof(struct tracer *trace, struct trace_array *tr)
int
ret
;
/* start the tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
return
0
;
}
/* Sleep for a 1/10 of a second */
msleep
(
100
);
/* stop the tracing. */
...
...
@@ -554,7 +597,12 @@ trace_selftest_startup_branch(struct tracer *trace, struct trace_array *tr)
int
ret
;
/* start the tracing */
trace
->
init
(
tr
);
ret
=
trace
->
init
(
tr
);
if
(
ret
)
{
warn_failed_init_tracer
(
trace
,
ret
);
return
ret
;
}
/* Sleep for a 1/10 of a second */
msleep
(
100
);
/* stop the tracing. */
...
...
kernel/trace/trace_sysprof.c
View file @
98580960
...
...
@@ -261,11 +261,12 @@ static void stop_stack_trace(struct trace_array *tr)
mutex_unlock
(
&
sample_timer_lock
);
}
static
void
stack_trace_init
(
struct
trace_array
*
tr
)
static
int
stack_trace_init
(
struct
trace_array
*
tr
)
{
sysprof_trace
=
tr
;
start_stack_trace
(
tr
);
return
0
;
}
static
void
stack_trace_reset
(
struct
trace_array
*
tr
)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment