1/*
2 *  (C) 2010,2011       Thomas Renninger <trenn@suse.de>, Novell Inc.
3 *
4 *  Licensed under the terms of the GNU GPL License version 2.
5 *
6 */
7
8#ifndef __CPUIDLE_INFO_HW__
9#define __CPUIDLE_INFO_HW__
10
11#include <stdarg.h>
12#include <time.h>
13
14#include "idle_monitor/idle_monitors.h"
15
16#define MONITORS_MAX 20
17#define MONITOR_NAME_LEN 20
18#define CSTATE_NAME_LEN 5
19#define CSTATE_DESC_LEN 60
20
21int cpu_count;
22
23/* Hard to define the right names ...: */
24enum power_range_e {
25	RANGE_THREAD,	/* Lowest in topology hierarcy, AMD: core, Intel: thread
26			   kernel sysfs: cpu */
27	RANGE_CORE,	/* AMD: unit, Intel: core, kernel_sysfs: core_id */
28	RANGE_PACKAGE,	/* Package, processor socket */
29	RANGE_MACHINE,	/* Machine, platform wide */
30	RANGE_MAX };
31
32typedef struct cstate {
33	int  id;
34	enum power_range_e range;
35	char name[CSTATE_NAME_LEN];
36	char desc[CSTATE_DESC_LEN];
37
38	/* either provide a percentage or a general count */
39	int (*get_count_percent)(unsigned int self_id, double *percent,
40				 unsigned int cpu);
41	int (*get_count)(unsigned int self_id, unsigned long long *count,
42			 unsigned int cpu);
43} cstate_t;
44
45struct cpuidle_monitor {
46	/* Name must not contain whitespaces */
47	char name[MONITOR_NAME_LEN];
48	int name_len;
49	int hw_states_num;
50	cstate_t *hw_states;
51	int (*start) (void);
52	int (*stop) (void);
53	struct cpuidle_monitor* (*do_register) (void);
54	void (*unregister)(void);
55	unsigned int overflow_s;
56	int needs_root;
57};
58
59extern long long timespec_diff_us(struct timespec start, struct timespec end);
60
61#define print_overflow_err(mes, ov)						\
62{										\
63	fprintf(stderr, gettext("Measure took %u seconds, but registers could "	\
64				"overflow at %u seconds, results "		\
65				"could be inaccurate\n"), mes, ov);		\
66}
67
68
69/* Taken over from x86info project sources  -> return 0 on success */
70#include <sched.h>
71#include <sys/types.h>
72#include <unistd.h>
73static inline int bind_cpu(int cpu)
74{
75	cpu_set_t set;
76
77	if (sched_getaffinity(getpid(), sizeof(set), &set) == 0) {
78		CPU_ZERO(&set);
79		CPU_SET(cpu, &set);
80		return sched_setaffinity(getpid(), sizeof(set), &set);
81	}
82	return 1;
83}
84
85#endif /* __CPUIDLE_INFO_HW__ */
86