|
Packit |
577717 |
/* $Id: perfctr.h,v 1.95 2005/10/02 13:01:30 mikpe Exp $
|
|
Packit |
577717 |
* Performance-Monitoring Counters driver
|
|
Packit |
577717 |
*
|
|
Packit |
577717 |
* Copyright (C) 1999-2005 Mikael Pettersson
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
#ifndef _LINUX_PERFCTR_H
|
|
Packit |
577717 |
#define _LINUX_PERFCTR_H
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#ifdef CONFIG_PERFCTR /* don't break archs without <asm/perfctr.h> */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#include <asm/perfctr.h>
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* cpu_features flag bits */
|
|
Packit |
577717 |
#define PERFCTR_FEATURE_RDPMC 0x01
|
|
Packit |
577717 |
#define PERFCTR_FEATURE_RDTSC 0x02
|
|
Packit |
577717 |
#define PERFCTR_FEATURE_PCINT 0x04
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* virtual perfctr control object */
|
|
Packit |
577717 |
struct vperfctr_control {
|
|
Packit |
577717 |
__s32 si_signo;
|
|
Packit |
577717 |
__u32 preserve;
|
|
Packit |
577717 |
};
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* commands for sys_vperfctr_control() */
|
|
Packit |
577717 |
#define VPERFCTR_CONTROL_UNLINK 0x01
|
|
Packit |
577717 |
#define VPERFCTR_CONTROL_SUSPEND 0x02
|
|
Packit |
577717 |
#define VPERFCTR_CONTROL_RESUME 0x03
|
|
Packit |
577717 |
#define VPERFCTR_CONTROL_CLEAR 0x04
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* common description of an arch-specific control register */
|
|
Packit |
577717 |
struct perfctr_cpu_reg {
|
|
Packit |
577717 |
__u64 nr;
|
|
Packit |
577717 |
__u64 value;
|
|
Packit |
577717 |
};
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* state and control domain numbers
|
|
Packit |
577717 |
0-127 are for architecture-neutral domains
|
|
Packit |
577717 |
128-255 are for architecture-specific domains */
|
|
Packit |
577717 |
#define VPERFCTR_DOMAIN_SUM 1 /* struct perfctr_sum_ctrs */
|
|
Packit |
577717 |
#define VPERFCTR_DOMAIN_CONTROL 2 /* struct vperfctr_control */
|
|
Packit |
577717 |
#define VPERFCTR_DOMAIN_CHILDREN 3 /* struct perfctr_sum_ctrs */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* domain numbers for common arch-specific control data */
|
|
Packit |
577717 |
#define PERFCTR_DOMAIN_CPU_CONTROL 128 /* struct perfctr_cpu_control_header */
|
|
Packit |
577717 |
#define PERFCTR_DOMAIN_CPU_MAP 129 /* __u32[] */
|
|
Packit |
577717 |
#define PERFCTR_DOMAIN_CPU_REGS 130 /* struct perfctr_cpu_reg[] */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#endif /* CONFIG_PERFCTR */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#ifdef __KERNEL__
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* The perfctr system calls.
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
asmlinkage long sys_vperfctr_open(int tid, int creat);
|
|
Packit |
577717 |
asmlinkage long sys_vperfctr_control(int fd, unsigned int cmd);
|
|
Packit |
577717 |
asmlinkage long sys_vperfctr_write(int fd, unsigned int domain,
|
|
Packit |
577717 |
const void __user *argp,
|
|
Packit |
577717 |
unsigned int argbytes);
|
|
Packit |
577717 |
asmlinkage long sys_vperfctr_read(int fd, unsigned int domain,
|
|
Packit |
577717 |
void __user *argp,
|
|
Packit |
577717 |
unsigned int argbytes);
|
|
Packit |
577717 |
|
|
Packit |
577717 |
struct perfctr_info {
|
|
Packit |
577717 |
unsigned int cpu_features;
|
|
Packit |
577717 |
unsigned int cpu_khz;
|
|
Packit |
577717 |
unsigned int tsc_to_cpu_mult;
|
|
Packit |
577717 |
};
|
|
Packit |
577717 |
|
|
Packit |
577717 |
extern struct perfctr_info perfctr_info;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#ifdef CONFIG_PERFCTR_VIRTUAL
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/*
|
|
Packit |
577717 |
* Virtual per-process performance-monitoring counters.
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
struct vperfctr; /* opaque */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* process management operations */
|
|
Packit |
577717 |
extern void __vperfctr_copy(struct task_struct*, struct pt_regs*);
|
|
Packit |
577717 |
extern void __vperfctr_release(struct task_struct*);
|
|
Packit |
577717 |
extern void __vperfctr_exit(struct vperfctr*);
|
|
Packit |
577717 |
extern void __vperfctr_suspend(struct vperfctr*);
|
|
Packit |
577717 |
extern void __vperfctr_resume(struct vperfctr*);
|
|
Packit |
577717 |
extern void __vperfctr_sample(struct vperfctr*);
|
|
Packit |
577717 |
extern void __vperfctr_set_cpus_allowed(struct task_struct*, struct vperfctr*, cpumask_t);
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_copy_task(struct task_struct *tsk, struct pt_regs *regs)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
if (tsk->thread.perfctr)
|
|
Packit |
577717 |
__vperfctr_copy(tsk, regs);
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_release_task(struct task_struct *tsk)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
if (tsk->thread.perfctr)
|
|
Packit |
577717 |
__vperfctr_release(tsk);
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_exit_thread(struct thread_struct *thread)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
struct vperfctr *perfctr;
|
|
Packit |
577717 |
perfctr = thread->perfctr;
|
|
Packit |
577717 |
if (perfctr)
|
|
Packit |
577717 |
__vperfctr_exit(perfctr);
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_suspend_thread(struct thread_struct *prev)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
struct vperfctr *perfctr;
|
|
Packit |
577717 |
perfctr = prev->perfctr;
|
|
Packit |
577717 |
if (perfctr)
|
|
Packit |
577717 |
__vperfctr_suspend(perfctr);
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_resume_thread(struct thread_struct *next)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
struct vperfctr *perfctr;
|
|
Packit |
577717 |
perfctr = next->perfctr;
|
|
Packit |
577717 |
if (perfctr)
|
|
Packit |
577717 |
__vperfctr_resume(perfctr);
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_sample_thread(struct thread_struct *thread)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
struct vperfctr *perfctr;
|
|
Packit |
577717 |
perfctr = thread->perfctr;
|
|
Packit |
577717 |
if (perfctr)
|
|
Packit |
577717 |
__vperfctr_sample(perfctr);
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_set_cpus_allowed(struct task_struct *p, cpumask_t new_mask)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
#ifdef CONFIG_PERFCTR_CPUS_FORBIDDEN_MASK
|
|
Packit |
577717 |
struct vperfctr *perfctr;
|
|
Packit |
577717 |
|
|
Packit |
577717 |
task_lock(p);
|
|
Packit |
577717 |
perfctr = p->thread.perfctr;
|
|
Packit |
577717 |
if (perfctr)
|
|
Packit |
577717 |
__vperfctr_set_cpus_allowed(p, perfctr, new_mask);
|
|
Packit |
577717 |
task_unlock(p);
|
|
Packit |
577717 |
#endif
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#else /* !CONFIG_PERFCTR_VIRTUAL */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void perfctr_copy_task(struct task_struct *p, struct pt_regs *r) { }
|
|
Packit |
577717 |
static inline void perfctr_release_task(struct task_struct *p) { }
|
|
Packit |
577717 |
static inline void perfctr_exit_thread(struct thread_struct *t) { }
|
|
Packit |
577717 |
static inline void perfctr_suspend_thread(struct thread_struct *t) { }
|
|
Packit |
577717 |
static inline void perfctr_resume_thread(struct thread_struct *t) { }
|
|
Packit |
577717 |
static inline void perfctr_sample_thread(struct thread_struct *t) { }
|
|
Packit |
577717 |
static inline void perfctr_set_cpus_allowed(struct task_struct *p, cpumask_t m) { }
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#endif /* CONFIG_PERFCTR_VIRTUAL */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
/* These routines are identical to write_seqcount_begin() and
|
|
Packit |
577717 |
* write_seqcount_end(), except they take an explicit __u32 rather
|
|
Packit |
577717 |
* than a seqcount_t. That's because this sequence lock is user from
|
|
Packit |
577717 |
* userspace, so we have to pin down the counter's type explicitly to
|
|
Packit |
577717 |
* have a clear ABI. They also omit the SMP write barriers since we
|
|
Packit |
577717 |
* only support mmap() based sampling for self-monitoring tasks.
|
|
Packit |
577717 |
*/
|
|
Packit |
577717 |
static inline void write_perfseq_begin(__u32 *seq)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
++*seq;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
static inline void write_perfseq_end(__u32 *seq)
|
|
Packit |
577717 |
{
|
|
Packit |
577717 |
++*seq;
|
|
Packit |
577717 |
}
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#endif /* __KERNEL__ */
|
|
Packit |
577717 |
|
|
Packit |
577717 |
#endif /* _LINUX_PERFCTR_H */
|