xref: /onnv-gate/usr/src/uts/common/sys/cap_util.h (revision 11389:dd00b884e84f)
1*11389SAlexander.Kolbasov@Sun.COM /*
2*11389SAlexander.Kolbasov@Sun.COM  * CDDL HEADER START
3*11389SAlexander.Kolbasov@Sun.COM  *
4*11389SAlexander.Kolbasov@Sun.COM  * The contents of this file are subject to the terms of the
5*11389SAlexander.Kolbasov@Sun.COM  * Common Development and Distribution License (the "License").
6*11389SAlexander.Kolbasov@Sun.COM  * You may not use this file except in compliance with the License.
7*11389SAlexander.Kolbasov@Sun.COM  *
8*11389SAlexander.Kolbasov@Sun.COM  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9*11389SAlexander.Kolbasov@Sun.COM  * or http://www.opensolaris.org/os/licensing.
10*11389SAlexander.Kolbasov@Sun.COM  * See the License for the specific language governing permissions
11*11389SAlexander.Kolbasov@Sun.COM  * and limitations under the License.
12*11389SAlexander.Kolbasov@Sun.COM  *
13*11389SAlexander.Kolbasov@Sun.COM  * When distributing Covered Code, include this CDDL HEADER in each
14*11389SAlexander.Kolbasov@Sun.COM  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15*11389SAlexander.Kolbasov@Sun.COM  * If applicable, add the following below this CDDL HEADER, with the
16*11389SAlexander.Kolbasov@Sun.COM  * fields enclosed by brackets "[]" replaced with your own identifying
17*11389SAlexander.Kolbasov@Sun.COM  * information: Portions Copyright [yyyy] [name of copyright owner]
18*11389SAlexander.Kolbasov@Sun.COM  *
19*11389SAlexander.Kolbasov@Sun.COM  * CDDL HEADER END
20*11389SAlexander.Kolbasov@Sun.COM  */
21*11389SAlexander.Kolbasov@Sun.COM 
22*11389SAlexander.Kolbasov@Sun.COM /*
23*11389SAlexander.Kolbasov@Sun.COM  * Copyright 2009 Sun Microsystems, Inc.  All rights reserved.
24*11389SAlexander.Kolbasov@Sun.COM  * Use is subject to license terms.
25*11389SAlexander.Kolbasov@Sun.COM  */
26*11389SAlexander.Kolbasov@Sun.COM 
27*11389SAlexander.Kolbasov@Sun.COM #ifndef	_SYS_CAP_UTIL_H
28*11389SAlexander.Kolbasov@Sun.COM #define	_SYS_CAP_UTIL_H
29*11389SAlexander.Kolbasov@Sun.COM 
30*11389SAlexander.Kolbasov@Sun.COM 
31*11389SAlexander.Kolbasov@Sun.COM #ifdef	__cplusplus
32*11389SAlexander.Kolbasov@Sun.COM extern "C" {
33*11389SAlexander.Kolbasov@Sun.COM #endif
34*11389SAlexander.Kolbasov@Sun.COM 
35*11389SAlexander.Kolbasov@Sun.COM #include <sys/types.h>
36*11389SAlexander.Kolbasov@Sun.COM #include <sys/kcpc.h>
37*11389SAlexander.Kolbasov@Sun.COM #include <sys/cpc_impl.h>
38*11389SAlexander.Kolbasov@Sun.COM #include <sys/pghw.h>
39*11389SAlexander.Kolbasov@Sun.COM #include <sys/cmt.h>
40*11389SAlexander.Kolbasov@Sun.COM 
41*11389SAlexander.Kolbasov@Sun.COM #ifdef	_KERNEL
42*11389SAlexander.Kolbasov@Sun.COM 
43*11389SAlexander.Kolbasov@Sun.COM /*
44*11389SAlexander.Kolbasov@Sun.COM  * Capacity and utilization flags for each CPU
45*11389SAlexander.Kolbasov@Sun.COM  */
46*11389SAlexander.Kolbasov@Sun.COM #define	CU_CPU_CNTRS_ON		1	/* CPU performance counters are on */
47*11389SAlexander.Kolbasov@Sun.COM #define	CU_CPU_CNTRS_OFF_ON	2	/* Off -> on transition */
48*11389SAlexander.Kolbasov@Sun.COM 
49*11389SAlexander.Kolbasov@Sun.COM /*
50*11389SAlexander.Kolbasov@Sun.COM  * Macro that returns whether CPU performance counters turned on for given CPU
51*11389SAlexander.Kolbasov@Sun.COM  */
52*11389SAlexander.Kolbasov@Sun.COM #define	CU_CPC_ON(cp) \
53*11389SAlexander.Kolbasov@Sun.COM 	((cp) != NULL && (cp)->cpu_cu_info != NULL && \
54*11389SAlexander.Kolbasov@Sun.COM 	    ((cp)->cpu_cu_info->cu_flag & CU_CPU_CNTRS_ON))
55*11389SAlexander.Kolbasov@Sun.COM 
56*11389SAlexander.Kolbasov@Sun.COM 
57*11389SAlexander.Kolbasov@Sun.COM /*
58*11389SAlexander.Kolbasov@Sun.COM  * Per counter statistics
59*11389SAlexander.Kolbasov@Sun.COM  */
60*11389SAlexander.Kolbasov@Sun.COM typedef struct cu_cntr_stats {
61*11389SAlexander.Kolbasov@Sun.COM 	hrtime_t	cs_time_running; /* running total of time counting */
62*11389SAlexander.Kolbasov@Sun.COM 	hrtime_t	cs_time_stopped; /* ... time not counting */
63*11389SAlexander.Kolbasov@Sun.COM 	hrtime_t	cs_time_start;	/* start time of current sample  */
64*11389SAlexander.Kolbasov@Sun.COM 	uint64_t	cs_value_start;	/* starting value for next sample */
65*11389SAlexander.Kolbasov@Sun.COM 	uint64_t	cs_value_last;	/* last value */
66*11389SAlexander.Kolbasov@Sun.COM 	uint64_t	cs_value_total;	/* running total */
67*11389SAlexander.Kolbasov@Sun.COM 	uint64_t	cs_rate;	/* observed rate since last */
68*11389SAlexander.Kolbasov@Sun.COM 	uint64_t	cs_rate_max;	/* maximum rate */
69*11389SAlexander.Kolbasov@Sun.COM 	kcpc_request_t	*cs_cpc_req;	/* corresponding CPC request */
70*11389SAlexander.Kolbasov@Sun.COM 	struct cpu	*cs_cpu_start;	/* CPU where starting value gotten */
71*11389SAlexander.Kolbasov@Sun.COM } cu_cntr_stats_t;
72*11389SAlexander.Kolbasov@Sun.COM 
73*11389SAlexander.Kolbasov@Sun.COM 
74*11389SAlexander.Kolbasov@Sun.COM /*
75*11389SAlexander.Kolbasov@Sun.COM  * Counter info for a PG hardware sharing relationship
76*11389SAlexander.Kolbasov@Sun.COM  */
77*11389SAlexander.Kolbasov@Sun.COM typedef struct cu_cntr_info {
78*11389SAlexander.Kolbasov@Sun.COM 	cpu_t		*ci_cpu;	/* CPU being measured */
79*11389SAlexander.Kolbasov@Sun.COM 	pghw_t		*ci_pg;		/* hardware PG being measured */
80*11389SAlexander.Kolbasov@Sun.COM 	kstat_t		*ci_kstat;	/* kstats being exported */
81*11389SAlexander.Kolbasov@Sun.COM 	cu_cntr_stats_t	*ci_stats;	/* counter statistics */
82*11389SAlexander.Kolbasov@Sun.COM 	uint_t		ci_nstats;	/* number of statistics */
83*11389SAlexander.Kolbasov@Sun.COM } cu_cntr_info_t;
84*11389SAlexander.Kolbasov@Sun.COM 
85*11389SAlexander.Kolbasov@Sun.COM 
86*11389SAlexander.Kolbasov@Sun.COM /*
87*11389SAlexander.Kolbasov@Sun.COM  * Each CPU can have one or more CPC contexts for measuring capacity and
88*11389SAlexander.Kolbasov@Sun.COM  * utilization
89*11389SAlexander.Kolbasov@Sun.COM  *
90*11389SAlexander.Kolbasov@Sun.COM  * One CPC context is needed per CPU if the counter events needed to measure
91*11389SAlexander.Kolbasov@Sun.COM  * capacity and utilization on each CPU can be programmed onto all the counters
92*11389SAlexander.Kolbasov@Sun.COM  * on a CPU at the same time and there are fewer or same number of desired
93*11389SAlexander.Kolbasov@Sun.COM  * counter events as counters on each CPU.  Otherwise, the desired counter
94*11389SAlexander.Kolbasov@Sun.COM  * events are assigned across multiple CPC contexts, so the contexts and their
95*11389SAlexander.Kolbasov@Sun.COM  * counter events can be multiplexed onto the counters over time to get the
96*11389SAlexander.Kolbasov@Sun.COM  * data for all of the counter events.
97*11389SAlexander.Kolbasov@Sun.COM  */
98*11389SAlexander.Kolbasov@Sun.COM typedef struct cu_cpc_ctx {
99*11389SAlexander.Kolbasov@Sun.COM 	int		cur_index;	/* index for current context */
100*11389SAlexander.Kolbasov@Sun.COM 	int		nctx;		/* number of CPC contexts */
101*11389SAlexander.Kolbasov@Sun.COM 	kcpc_ctx_t	**ctx_ptr_array; /* array of context pointers */
102*11389SAlexander.Kolbasov@Sun.COM 	size_t		ctx_ptr_array_sz; /* size of array */
103*11389SAlexander.Kolbasov@Sun.COM } cu_cpc_ctx_t;
104*11389SAlexander.Kolbasov@Sun.COM 
105*11389SAlexander.Kolbasov@Sun.COM /*
106*11389SAlexander.Kolbasov@Sun.COM  * Per CPU capacity and utilization info
107*11389SAlexander.Kolbasov@Sun.COM  */
108*11389SAlexander.Kolbasov@Sun.COM typedef struct cu_cpu_info {
109*11389SAlexander.Kolbasov@Sun.COM 	struct cpu	*cu_cpu;	/* CPU for the statistics */
110*11389SAlexander.Kolbasov@Sun.COM 	uint_t		cu_flag;	/* capacity & utilization flag */
111*11389SAlexander.Kolbasov@Sun.COM 	hrtime_t	cu_sample_time;	/* when last sample taken */
112*11389SAlexander.Kolbasov@Sun.COM 	cu_cpc_ctx_t	cu_cpc_ctx;	/* performance counter contexts */
113*11389SAlexander.Kolbasov@Sun.COM 	cu_cntr_stats_t	*cu_cntr_stats;	/* counter statistics array */
114*11389SAlexander.Kolbasov@Sun.COM 	uint_t		cu_ncntr_stats;	/* number of counter statistics */
115*11389SAlexander.Kolbasov@Sun.COM 	uint_t		cu_disabled;	/* count of disable requests */
116*11389SAlexander.Kolbasov@Sun.COM 	/*
117*11389SAlexander.Kolbasov@Sun.COM 	 * Per PG hardware sharing relationship counter info
118*11389SAlexander.Kolbasov@Sun.COM 	 */
119*11389SAlexander.Kolbasov@Sun.COM 	cu_cntr_info_t	*cu_cntr_info[PGHW_NUM_COMPONENTS];
120*11389SAlexander.Kolbasov@Sun.COM } cu_cpu_info_t;
121*11389SAlexander.Kolbasov@Sun.COM 
122*11389SAlexander.Kolbasov@Sun.COM /*
123*11389SAlexander.Kolbasov@Sun.COM  * COMMON INTERFACE ROUTINES
124*11389SAlexander.Kolbasov@Sun.COM  */
125*11389SAlexander.Kolbasov@Sun.COM 
126*11389SAlexander.Kolbasov@Sun.COM /*
127*11389SAlexander.Kolbasov@Sun.COM  * Setup capacity and utilization support
128*11389SAlexander.Kolbasov@Sun.COM  */
129*11389SAlexander.Kolbasov@Sun.COM extern void	cu_init(void);
130*11389SAlexander.Kolbasov@Sun.COM 
131*11389SAlexander.Kolbasov@Sun.COM /*
132*11389SAlexander.Kolbasov@Sun.COM  * Tear down capacity and utilization support
133*11389SAlexander.Kolbasov@Sun.COM  */
134*11389SAlexander.Kolbasov@Sun.COM extern int	cu_fini(void);
135*11389SAlexander.Kolbasov@Sun.COM 
136*11389SAlexander.Kolbasov@Sun.COM /*
137*11389SAlexander.Kolbasov@Sun.COM  * Program CPC for capacity and utilization on given CPU
138*11389SAlexander.Kolbasov@Sun.COM  */
139*11389SAlexander.Kolbasov@Sun.COM extern void	cu_cpc_program(struct cpu *, int *);
140*11389SAlexander.Kolbasov@Sun.COM 
141*11389SAlexander.Kolbasov@Sun.COM /*
142*11389SAlexander.Kolbasov@Sun.COM  * Unprogram CPC for capacity and utilization on given CPU
143*11389SAlexander.Kolbasov@Sun.COM  */
144*11389SAlexander.Kolbasov@Sun.COM extern void	cu_cpc_unprogram(struct cpu *, int *);
145*11389SAlexander.Kolbasov@Sun.COM 
146*11389SAlexander.Kolbasov@Sun.COM /*
147*11389SAlexander.Kolbasov@Sun.COM  * Update counter statistics on a given CPU
148*11389SAlexander.Kolbasov@Sun.COM  */
149*11389SAlexander.Kolbasov@Sun.COM extern int	cu_cpu_update(struct cpu *, boolean_t);
150*11389SAlexander.Kolbasov@Sun.COM 
151*11389SAlexander.Kolbasov@Sun.COM /*
152*11389SAlexander.Kolbasov@Sun.COM  * Update utilization and capacity data for CMT PG
153*11389SAlexander.Kolbasov@Sun.COM  */
154*11389SAlexander.Kolbasov@Sun.COM extern void	cu_pg_update(pghw_t *);
155*11389SAlexander.Kolbasov@Sun.COM 
156*11389SAlexander.Kolbasov@Sun.COM /*
157*11389SAlexander.Kolbasov@Sun.COM  * Disable or enable capacity and utilization on all CPUs
158*11389SAlexander.Kolbasov@Sun.COM  */
159*11389SAlexander.Kolbasov@Sun.COM extern void	cu_disable(void);
160*11389SAlexander.Kolbasov@Sun.COM extern void	cu_enable(void);
161*11389SAlexander.Kolbasov@Sun.COM 
162*11389SAlexander.Kolbasov@Sun.COM /*
163*11389SAlexander.Kolbasov@Sun.COM  * PLATFORM SPECIFIC INTERFACE ROUTINES
164*11389SAlexander.Kolbasov@Sun.COM  */
165*11389SAlexander.Kolbasov@Sun.COM extern int	cu_plat_cpc_init(cpu_t *, kcpc_request_list_t *, int);
166*11389SAlexander.Kolbasov@Sun.COM 
167*11389SAlexander.Kolbasov@Sun.COM #endif	/* _KERNEL */
168*11389SAlexander.Kolbasov@Sun.COM 
169*11389SAlexander.Kolbasov@Sun.COM #ifdef	__cplusplus
170*11389SAlexander.Kolbasov@Sun.COM }
171*11389SAlexander.Kolbasov@Sun.COM #endif
172*11389SAlexander.Kolbasov@Sun.COM 
173*11389SAlexander.Kolbasov@Sun.COM #endif /* _SYS_CAP_UTIL_H */
174