Commit e9a22d1f authored by Ingo Molnar's avatar Ingo Molnar

x86, bts: cleanups

Impact: cleanup, no code changed

Cc: Markus Metzger <markus.t.metzger@intel.com>
LKML-Reference: <20090313104218.A30096@sedona.ch.intel.com>
Signed-off-by: default avatarIngo Molnar <mingo@elte.hu>
parent 321bb5e1
...@@ -19,43 +19,52 @@ ...@@ -19,43 +19,52 @@
* Markus Metzger <markus.t.metzger@intel.com>, 2007-2009 * Markus Metzger <markus.t.metzger@intel.com>, 2007-2009
*/ */
#include <linux/kernel.h>
#include <asm/ds.h>
#include <linux/errno.h>
#include <linux/string.h> #include <linux/string.h>
#include <linux/slab.h> #include <linux/errno.h>
#include <linux/sched.h> #include <linux/sched.h>
#include <linux/slab.h>
#include <linux/mm.h> #include <linux/mm.h>
#include <linux/kernel.h>
#include <asm/ds.h>
#include "ds_selftest.h" #include "ds_selftest.h"
/* /*
* The configuration for a particular DS hardware implementation. * The configuration for a particular DS hardware implementation:
*/ */
struct ds_configuration { struct ds_configuration {
/* The name of the configuration. */ /* The name of the configuration: */
const char *name; const char *name;
/* The size of pointer-typed fields in DS, BTS, and PEBS. */
/* The size of pointer-typed fields in DS, BTS, and PEBS: */
unsigned char sizeof_ptr_field; unsigned char sizeof_ptr_field;
/* The size of a BTS/PEBS record in bytes. */
/* The size of a BTS/PEBS record in bytes: */
unsigned char sizeof_rec[2]; unsigned char sizeof_rec[2];
/* Control bit-masks indexed by enum ds_feature. */
/* Control bit-masks indexed by enum ds_feature: */
unsigned long ctl[dsf_ctl_max]; unsigned long ctl[dsf_ctl_max];
}; };
static DEFINE_PER_CPU(struct ds_configuration, ds_cfg_array); static DEFINE_PER_CPU(struct ds_configuration, ds_cfg_array);
#define ds_cfg per_cpu(ds_cfg_array, smp_processor_id()) #define ds_cfg per_cpu(ds_cfg_array, smp_processor_id())
#define MAX_SIZEOF_DS (12 * 8) /* Maximal size of a DS configuration. */ /* Maximal size of a DS configuration: */
#define MAX_SIZEOF_BTS (3 * 8) /* Maximal size of a BTS record. */ #define MAX_SIZEOF_DS (12 * 8)
#define DS_ALIGNMENT (1 << 3) /* BTS and PEBS buffer alignment. */
#define BTS_CONTROL \ /* Maximal size of a BTS record: */
(ds_cfg.ctl[dsf_bts] | ds_cfg.ctl[dsf_bts_kernel] | ds_cfg.ctl[dsf_bts_user] |\ #define MAX_SIZEOF_BTS (3 * 8)
ds_cfg.ctl[dsf_bts_overflow])
/* BTS and PEBS buffer alignment: */
#define DS_ALIGNMENT (1 << 3)
/* Mask of control bits in the DS MSR register: */
#define BTS_CONTROL \
( ds_cfg.ctl[dsf_bts] | \
ds_cfg.ctl[dsf_bts_kernel] | \
ds_cfg.ctl[dsf_bts_user] | \
ds_cfg.ctl[dsf_bts_overflow] )
/* /*
* A BTS or PEBS tracer. * A BTS or PEBS tracer.
...@@ -72,20 +81,24 @@ struct ds_tracer { ...@@ -72,20 +81,24 @@ struct ds_tracer {
}; };
struct bts_tracer { struct bts_tracer {
/* The common DS part. */ /* The common DS part: */
struct ds_tracer ds; struct ds_tracer ds;
/* The trace including the DS configuration. */
/* The trace including the DS configuration: */
struct bts_trace trace; struct bts_trace trace;
/* Buffer overflow notification function. */
/* Buffer overflow notification function: */
bts_ovfl_callback_t ovfl; bts_ovfl_callback_t ovfl;
}; };
struct pebs_tracer { struct pebs_tracer {
/* The common DS part. */ /* The common DS part: */
struct ds_tracer ds; struct ds_tracer ds;
/* The trace including the DS configuration. */
/* The trace including the DS configuration: */
struct pebs_trace trace; struct pebs_trace trace;
/* Buffer overflow notification function. */
/* Buffer overflow notification function: */
pebs_ovfl_callback_t ovfl; pebs_ovfl_callback_t ovfl;
}; };
...@@ -95,6 +108,7 @@ struct pebs_tracer { ...@@ -95,6 +108,7 @@ struct pebs_tracer {
* *
* The DS configuration consists of the following fields; different * The DS configuration consists of the following fields; different
* architetures vary in the size of those fields. * architetures vary in the size of those fields.
*
* - double-word aligned base linear address of the BTS buffer * - double-word aligned base linear address of the BTS buffer
* - write pointer into the BTS buffer * - write pointer into the BTS buffer
* - end linear address of the BTS buffer (one byte beyond the end of * - end linear address of the BTS buffer (one byte beyond the end of
...@@ -137,15 +151,16 @@ enum ds_qualifier { ...@@ -137,15 +151,16 @@ enum ds_qualifier {
ds_pebs ds_pebs
}; };
static inline unsigned long ds_get(const unsigned char *base, static inline unsigned long
enum ds_qualifier qual, enum ds_field field) ds_get(const unsigned char *base, enum ds_qualifier qual, enum ds_field field)
{ {
base += (ds_cfg.sizeof_ptr_field * (field + (4 * qual))); base += (ds_cfg.sizeof_ptr_field * (field + (4 * qual)));
return *(unsigned long *)base; return *(unsigned long *)base;
} }
static inline void ds_set(unsigned char *base, enum ds_qualifier qual, static inline void
enum ds_field field, unsigned long value) ds_set(unsigned char *base, enum ds_qualifier qual, enum ds_field field,
unsigned long value)
{ {
base += (ds_cfg.sizeof_ptr_field * (field + (4 * qual))); base += (ds_cfg.sizeof_ptr_field * (field + (4 * qual)));
(*(unsigned long *)base) = value; (*(unsigned long *)base) = value;
...@@ -157,7 +172,6 @@ static inline void ds_set(unsigned char *base, enum ds_qualifier qual, ...@@ -157,7 +172,6 @@ static inline void ds_set(unsigned char *base, enum ds_qualifier qual,
*/ */
static DEFINE_SPINLOCK(ds_lock); static DEFINE_SPINLOCK(ds_lock);
/* /*
* We either support (system-wide) per-cpu or per-thread allocation. * We either support (system-wide) per-cpu or per-thread allocation.
* We distinguish the two based on the task_struct pointer, where a * We distinguish the two based on the task_struct pointer, where a
...@@ -211,16 +225,20 @@ static inline int check_tracer(struct task_struct *task) ...@@ -211,16 +225,20 @@ static inline int check_tracer(struct task_struct *task)
* deallocated when the last user puts the context. * deallocated when the last user puts the context.
*/ */
struct ds_context { struct ds_context {
/* The DS configuration; goes into MSR_IA32_DS_AREA. */ /* The DS configuration; goes into MSR_IA32_DS_AREA: */
unsigned char ds[MAX_SIZEOF_DS]; unsigned char ds[MAX_SIZEOF_DS];
/* The owner of the BTS and PEBS configuration, respectively. */
/* The owner of the BTS and PEBS configuration, respectively: */
struct bts_tracer *bts_master; struct bts_tracer *bts_master;
struct pebs_tracer *pebs_master; struct pebs_tracer *pebs_master;
/* Use count. */
/* Use count: */
unsigned long count; unsigned long count;
/* Pointer to the context pointer field. */
/* Pointer to the context pointer field: */
struct ds_context **this; struct ds_context **this;
/* The traced task; NULL for current cpu. */
/* The traced task; NULL for current cpu: */
struct task_struct *task; struct task_struct *task;
}; };
...@@ -461,8 +479,8 @@ static inline void bts_set(char *base, enum bts_field field, unsigned long val) ...@@ -461,8 +479,8 @@ static inline void bts_set(char *base, enum bts_field field, unsigned long val)
* *
* return: bytes read/written on success; -Eerrno, otherwise * return: bytes read/written on success; -Eerrno, otherwise
*/ */
static int bts_read(struct bts_tracer *tracer, const void *at, static int
struct bts_struct *out) bts_read(struct bts_tracer *tracer, const void *at, struct bts_struct *out)
{ {
if (!tracer) if (!tracer)
return -EINVAL; return -EINVAL;
......
...@@ -12,4 +12,4 @@ extern int ds_selftest_pebs(void); ...@@ -12,4 +12,4 @@ extern int ds_selftest_pebs(void);
#else #else
static inline int ds_selftest_bts(void) { return 0; } static inline int ds_selftest_bts(void) { return 0; }
static inline int ds_selftest_pebs(void) { return 0; } static inline int ds_selftest_pebs(void) { return 0; }
#endif /* CONFIG_X86_DS_SELFTEST */ #endif
/* /*
* h/w branch tracer for x86 based on bts * h/w branch tracer for x86 based on BTS
* *
* Copyright (C) 2008-2009 Intel Corporation. * Copyright (C) 2008-2009 Intel Corporation.
* Markus Metzger <markus.t.metzger@gmail.com>, 2008-2009 * Markus Metzger <markus.t.metzger@gmail.com>, 2008-2009
...@@ -15,8 +15,8 @@ ...@@ -15,8 +15,8 @@
#include <asm/ds.h> #include <asm/ds.h>
#include "trace.h"
#include "trace_output.h" #include "trace_output.h"
#include "trace.h"
#define BTS_BUFFER_SIZE (1 << 13) #define BTS_BUFFER_SIZE (1 << 13)
...@@ -197,10 +197,10 @@ static void bts_trace_print_header(struct seq_file *m) ...@@ -197,10 +197,10 @@ static void bts_trace_print_header(struct seq_file *m)
static enum print_line_t bts_trace_print_line(struct trace_iterator *iter) static enum print_line_t bts_trace_print_line(struct trace_iterator *iter)
{ {
unsigned long symflags = TRACE_ITER_SYM_OFFSET;
struct trace_entry *entry = iter->ent; struct trace_entry *entry = iter->ent;
struct trace_seq *seq = &iter->seq; struct trace_seq *seq = &iter->seq;
struct hw_branch_entry *it; struct hw_branch_entry *it;
unsigned long symflags = TRACE_ITER_SYM_OFFSET;
trace_assign_type(it, entry); trace_assign_type(it, entry);
......
...@@ -189,6 +189,7 @@ int trace_selftest_startup_dynamic_tracing(struct tracer *trace, ...@@ -189,6 +189,7 @@ int trace_selftest_startup_dynamic_tracing(struct tracer *trace,
#else #else
# define trace_selftest_startup_dynamic_tracing(trace, tr, func) ({ 0; }) # define trace_selftest_startup_dynamic_tracing(trace, tr, func) ({ 0; })
#endif /* CONFIG_DYNAMIC_FTRACE */ #endif /* CONFIG_DYNAMIC_FTRACE */
/* /*
* Simple verification test of ftrace function tracer. * Simple verification test of ftrace function tracer.
* Enable ftrace, sleep 1/10 second, and then read the trace * Enable ftrace, sleep 1/10 second, and then read the trace
...@@ -698,10 +699,10 @@ int ...@@ -698,10 +699,10 @@ int
trace_selftest_startup_hw_branches(struct tracer *trace, trace_selftest_startup_hw_branches(struct tracer *trace,
struct trace_array *tr) struct trace_array *tr)
{ {
unsigned long count;
int ret;
struct trace_iterator iter; struct trace_iterator iter;
struct tracer tracer; struct tracer tracer;
unsigned long count;
int ret;
if (!trace->open) { if (!trace->open) {
printk(KERN_CONT "missing open function..."); printk(KERN_CONT "missing open function...");
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment