ktr.h revision 68004
1/*-
2 * Copyright (c) 1996 Berkeley Software Design, Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 * 1. Redistributions of source code must retain the above copyright
8 *    notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright
10 *    notice, this list of conditions and the following disclaimer in the
11 *    documentation and/or other materials provided with the distribution.
12 * 3. Berkeley Software Design Inc's name may not be used to endorse or
13 *    promote products derived from this software without specific prior
14 *    written permission.
15 *
16 * THIS SOFTWARE IS PROVIDED BY BERKELEY SOFTWARE DESIGN INC ``AS IS'' AND
17 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
19 * ARE DISCLAIMED.  IN NO EVENT SHALL BERKELEY SOFTWARE DESIGN INC BE LIABLE
20 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
22 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
23 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
24 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
25 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26 * SUCH DAMAGE.
27 *
28 *	from BSDI $Id: ktr.h,v 1.10.2.7 2000/03/16 21:44:42 cp Exp $
29 * $FreeBSD: head/sys/sys/ktr.h 68004 2000-10-30 20:37:45Z phk $
30 */
31
32/*
33 *	Wraparound kernel trace buffer support.
34 */
35
36#ifndef _SYS_KTR_H_
37#define _SYS_KTR_H_
38
39/* Requires sys/types.h, sys/time.h, machine/atomic.h, and machine/cpufunc.h */
40
41#include <machine/atomic.h>
42#include <machine/cpufunc.h>
43
44/*
45 * Trace classes
46 */
47#define	KTR_GEN		0x00000001		/* General (TR) */
48#define	KTR_NET		0x00000002		/* Network */
49#define	KTR_DEV		0x00000004		/* Device driver */
50#define	KTR_LOCK	0x00000008		/* MP locking */
51#define	KTR_SMP		0x00000010		/* MP general */
52#define	KTR_FS		0x00000020		/* Filesystem */
53#define KTR_PMAP	0x00000040		/* Pmap tracing */
54#define KTR_MALLOC	0x00000080		/* Malloc tracing */
55#define	KTR_TRAP	0x00000100		/* Trap processing */
56#define	KTR_INTR	0x00000200		/* Interrupt tracing */
57#define KTR_SIG		0x00000400		/* Signal processing */
58#define	KTR_CLK		0x00000800		/* hardclock verbose */
59#define	KTR_PROC	0x00001000		/* Process scheduling */
60#define	KTR_SYSC	0x00002000		/* System call */
61#define	KTR_INIT	0x00004000		/* System initialization */
62#define KTR_KGDB	0x00008000		/* Trace kgdb internals */
63#define	KTR_IO		0x00010000		/* Upper I/O  */
64#define KTR_LOCKMGR	0x00020000
65#define KTR_NFS		0x00040000		/* The obvious */
66#define KTR_VOP		0x00080000		/* The obvious */
67#define KTR_VM		0x00100000		/* The virtual memory system */
68#define KTR_IDLELOOP	0x00200000		/* checks done in the idle process */
69
70/*
71 * Trace classes which can be assigned to particular use at compile time
72 * These must remain in high 22 as some assembly code counts on it
73 */
74#define KTR_CT1		0x010000000
75#define KTR_CT2		0x020000000
76#define KTR_CT3		0x040000000
77#define KTR_CT4		0x080000000
78#define KTR_CT5		0x100000000
79#define KTR_CT6		0x200000000
80#define KTR_CT7		0x400000000
81#define KTR_CT8		0x800000000
82
83/* Trace classes to compile in */
84#ifndef KTR_COMPILE
85#define	KTR_COMPILE	(KTR_GEN)
86#endif
87
88#ifndef KTR_MASK
89#define	KTR_MASK	(KTR_GEN)
90#endif
91
92#ifndef KTR_CPUMASK
93#define	KTR_CPUMASK	(~0)
94#endif
95
96#ifndef LOCORE
97
98#include <sys/time.h>
99
100struct ktr_entry {
101	struct	timespec ktr_tv;
102#ifdef KTR_EXTEND
103#ifndef KTRDESCSIZE
104#define KTRDESCSIZE 80
105#endif
106#ifndef KTRFILENAMESIZE
107#define KTRFILENAMESIZE 32
108#endif
109	char	ktr_desc [KTRDESCSIZE];
110	char    ktr_filename [KTRFILENAMESIZE];
111	int	ktr_line;
112	int	ktr_cpu;
113#else
114	char	*ktr_desc;
115	u_long	ktr_parm1;
116	u_long	ktr_parm2;
117	u_long	ktr_parm3;
118	u_long	ktr_parm4;
119	u_long	ktr_parm5;
120#endif
121};
122
123/* These variables are used by gdb to analyse the output */
124extern int ktr_extend;
125
126extern int ktr_cpumask;
127extern int ktr_mask;
128extern int ktr_entries;
129
130extern volatile int ktr_idx;
131extern struct ktr_entry ktr_buf[];
132
133#endif /* !LOCORE */
134#ifdef KTR
135
136#ifndef KTR_ENTRIES
137#define	KTR_ENTRIES	1024
138#endif
139
140#ifdef KTR_EXTEND
141#ifndef _TR_CPU
142#ifdef SMP
143#define _TR_CPU		cpuid
144#else
145#define _TR_CPU		0
146#endif
147#endif
148#ifndef _TR
149#define _TR()							\
150        struct ktr_entry *_ktrptr;				\
151	int _ktr_newidx, _ktr_saveidx;				\
152	int _tr_intrsave = save_intr();				\
153	disable_intr();						\
154	do {							\
155		_ktr_saveidx = ktr_idx;				\
156		_ktr_newidx = (ktr_idx + 1) & (KTR_ENTRIES - 1); \
157	} while (atomic_cmpset_int(&ktr_idx, _ktr_saveidx, _ktr_newidx) == 0); \
158	_ktrptr = &ktr_buf[_ktr_saveidx];			\
159	restore_intr(_tr_intrsave);				\
160	nanotime(&_ktrptr->ktr_tv);				\
161	snprintf (_ktrptr->ktr_filename, KTRFILENAMESIZE, "%s", __FILE__); \
162        _ktrptr->ktr_line = __LINE__;				\
163	_ktrptr->ktr_cpu = _TR_CPU;
164#endif
165#define	CTR0(m, _desc) 						\
166	if (KTR_COMPILE & (m)) {				\
167		if ((ktr_mask & (m)) && ((1 << _TR_CPU) & ktr_cpumask)) { \
168			_TR()					\
169			memcpy (_ktrptr->ktr_desc, _desc, KTRDESCSIZE);	\
170		}						\
171	}
172#define	CTR1(m, _desc, _p1)					\
173	if (KTR_COMPILE & (m)) {				\
174		if ((ktr_mask & (m)) && ((1 << _TR_CPU) & ktr_cpumask)) { \
175			_TR()					\
176			snprintf (_ktrptr->ktr_desc, KTRDESCSIZE, _desc, _p1);	\
177		}						\
178	}
179#define	CTR2(m, _desc, _p1, _p2) 				\
180	if (KTR_COMPILE & (m)) {				\
181		if ((ktr_mask & (m)) && ((1 << _TR_CPU) & ktr_cpumask)) { \
182			_TR()					\
183			snprintf (_ktrptr->ktr_desc, KTRDESCSIZE, _desc, _p1, _p2);	\
184		}						\
185	}
186#define	CTR3(m, _desc, _p1, _p2, _p3) 				\
187	if (KTR_COMPILE & (m)) {				\
188		if ((ktr_mask & (m)) && ((1 << _TR_CPU) & ktr_cpumask)) { \
189			_TR()					\
190			snprintf (_ktrptr->ktr_desc, KTRDESCSIZE, _desc, _p1, _p2, _p3);	\
191		}						\
192	}
193#define	CTR4(m, _desc, _p1, _p2, _p3, _p4) 			\
194	if (KTR_COMPILE & (m)) {				\
195		if ((ktr_mask & (m)) && ((1 << _TR_CPU) & ktr_cpumask)) { \
196			_TR()					\
197			snprintf (_ktrptr->ktr_desc, KTRDESCSIZE, _desc, _p1, _p2, _p3, _p4);	\
198		}						\
199	}
200#define	CTR5(m, _desc, _p1, _p2, _p3, _p4, _p5) 		\
201	if (KTR_COMPILE & (m)) {					\
202		if ((ktr_mask & (m)) && ((1 << _TR_CPU) & ktr_cpumask)) { \
203			_TR()					\
204			snprintf (_ktrptr->ktr_desc, KTRDESCSIZE, _desc, _p1, _p2, _p3, _p4, _p5);	\
205		}						\
206	}
207
208#else							    /* not extended */
209#ifndef _TR
210#define _TR(_desc)						\
211        struct ktr_entry *_ktrptr;				\
212	int _ktr_newidx, _ktr_saveidx;				\
213	do {							\
214		_ktr_saveidx = ktr_idx;				\
215		_ktr_newidx = (ktr_idx + 1) & (KTR_ENTRIES - 1); \
216	} while (atomic_cmpset_int(&ktr_idx, _ktr_saveidx, _ktr_newidx) == 0); \
217	_ktrptr = &ktr_buf[_ktr_saveidx];			\
218	nanotime(&_ktrptr->ktr_tv);				\
219	_ktrptr->ktr_desc = (_desc);
220#endif
221#define	CTR0(m, _desc) 						\
222	if (KTR_COMPILE & (m)) {				\
223		if (ktr_mask & (m)) {				\
224			_TR(_desc)				\
225		}						\
226	}
227#define	CTR1(m, _desc, _p1)					\
228	if (KTR_COMPILE & (m)) {				\
229		if (ktr_mask & (m)) {				\
230			_TR(_desc)				\
231			_ktrptr->ktr_parm1 = (u_long)(_p1);	\
232		}						\
233	}
234#define	CTR2(m, _desc, _p1, _p2) 				\
235	if (KTR_COMPILE & (m)) {				\
236		if (ktr_mask & (m)) {				\
237			_TR(_desc)				\
238			_ktrptr->ktr_parm1 = (u_long)(_p1);	\
239			_ktrptr->ktr_parm2 = (u_long)(_p2);	\
240		}						\
241	}
242#define	CTR3(m, _desc, _p1, _p2, _p3) 				\
243	if (KTR_COMPILE & (m)) {				\
244		if (ktr_mask & (m)) {				\
245			_TR(_desc)				\
246			_ktrptr->ktr_parm1 = (u_long)(_p1);	\
247			_ktrptr->ktr_parm2 = (u_long)(_p2);	\
248			_ktrptr->ktr_parm3 = (u_long)(_p3);	\
249		}						\
250	}
251#define	CTR4(m, _desc, _p1, _p2, _p3, _p4) 			\
252	if (KTR_COMPILE & (m)) {				\
253		if (ktr_mask & (m)) {				\
254			_TR(_desc)				\
255			_ktrptr->ktr_parm1 = (u_long)(_p1);	\
256			_ktrptr->ktr_parm2 = (u_long)(_p2);	\
257			_ktrptr->ktr_parm3 = (u_long)(_p3);	\
258			_ktrptr->ktr_parm4 = (u_long)(_p4);	\
259		}						\
260	}
261#define	CTR5(m, _desc, _p1, _p2, _p3, _p4, _p5) 		\
262	if (KTR_COMPILE & (m)) {				\
263		if (ktr_mask & (m)) {				\
264			_TR(_desc)				\
265			_ktrptr->ktr_parm1 = (u_long)(_p1);	\
266			_ktrptr->ktr_parm2 = (u_long)(_p2);	\
267			_ktrptr->ktr_parm3 = (u_long)(_p3);	\
268			_ktrptr->ktr_parm4 = (u_long)(_p4);	\
269			_ktrptr->ktr_parm5 = (u_long)(_p5);	\
270		}						\
271	}
272#endif
273#else	/* KTR */
274#undef KTR_COMPILE
275#define KTR_COMPILE 0
276#define	CTR0(m, d)
277#define	CTR1(m, d, p1)
278#define	CTR2(m, d, p1, p2)
279#define	CTR3(m, d, p1, p2, p3)
280#define	CTR4(m, d, p1, p2, p3, p4)
281#define	CTR5(m, d, p1, p2, p3, p4, p5)
282/* XXX vvvvvvvv ??? */
283#define	SEG_ATR(d,s)
284#define	SEG_ATR_DESC(d,s)
285#define	ATR(d)
286#define	CATR(f,d,n)
287#define	CATRD(f,d,n)
288#endif	/* KTR */
289
290#define	TR0(d)				CTR0(KTR_GEN, d)
291#define	TR1(d, p1)			CTR1(KTR_GEN, d, p1)
292#define	TR2(d, p1, p2)			CTR2(KTR_GEN, d, p1, p2)
293#define	TR3(d, p1, p2, p3)		CTR3(KTR_GEN, d, p1, p2, p3)
294#define	TR4(d, p1, p2, p3, p4)		CTR4(KTR_GEN, d, p1, p2, p3, p4)
295#define	TR5(d, p1, p2, p3, p4, p5)	CTR5(KTR_GEN, d, p1, p2, p3, p4, p5)
296
297/*
298 * Trace initialization events, similar to CTR with KTR_INIT, but
299 * completely ifdef'ed out if KTR_INIT isn't in KTR_COMPILE (to
300 * save string space, the compiler doesn't optimize out strings
301 * for the conditional ones above).
302 */
303#if (KTR_COMPILE & KTR_INIT) != 0
304#define	ITR0(d)				CTR0(KTR_INIT, d)
305#define	ITR1(d, p1)			CTR1(KTR_INIT, d, p1)
306#define	ITR2(d, p1, p2)			CTR2(KTR_INIT, d, p1, p2)
307#define	ITR3(d, p1, p2, p3)		CTR3(KTR_INIT, d, p1, p2, p3)
308#define	ITR4(d, p1, p2, p3, p4)		CTR4(KTR_INIT, d, p1, p2, p3, p4)
309#define	ITR5(d, p1, p2, p3, p4, p5)	CTR5(KTR_INIT, d, p1, p2, p3, p4, p5)
310#else
311#define	ITR0(d)
312#define	ITR1(d, p1)
313#define	ITR2(d, p1, p2)
314#define	ITR3(d, p1, p2, p3)
315#define	ITR4(d, p1, p2, p3, p4)
316#define	ITR5(d, p1, p2, p3, p4, p5)
317#endif
318
319#endif /* !_SYS_KTR_H_ */
320