cpufunc.h revision 200
1/*
2 * Functions to provide access to special i386 instructions.
3 * XXX - bezillions more are defined in locore.s but are not declared anywhere.
4 */
5
6#include <sys/cdefs.h>
7#include <sys/types.h>
8
9#ifdef	__GNUC__
10
11static __inline int bdb(void)
12{
13	extern int bdb_exists;
14
15	if (!bdb_exists)
16		return (0);
17	__asm("int $3");
18	return (1);
19}
20
21static __inline void
22disable_intr(void)
23{
24	__asm __volatile("cli");
25}
26
27static __inline void
28enable_intr(void)
29{
30	__asm __volatile("sti");
31}
32
33/*
34 * This roundabout method of returning a u_char helps stop gcc-1.40 from
35 * generating unnecessary movzbl's.
36 */
37#define	inb(port)	((u_char) u_int_inb(port))
38
39static __inline u_int
40u_int_inb(u_int port)
41{
42	u_char	data;
43	/*
44	 * We use %%dx and not %1 here because i/o is done at %dx and not at
45	 * %edx, while gcc-2.2.2 generates inferior code (movw instead of movl)
46	 * if we tell it to load (u_short) port.
47	 */
48	__asm __volatile("inb %%dx,%0" : "=a" (data) : "d" (port));
49	return data;
50}
51
52static __inline void
53outb(u_int port, u_char data)
54{
55	register u_char	al asm("ax");
56
57	al = data;		/* help gcc-1.40's register allocator */
58	__asm __volatile("outb %0,%%dx" : : "a" (al), "d" (port));
59}
60
61static __inline__
62imin(a, b)
63	int a, b;
64{
65
66	return (a < b ? a : b);
67}
68
69static __inline__
70imax(a, b)
71	int a, b;
72{
73
74	return (a > b ? a : b);
75}
76
77static __inline__
78unsigned int
79min(a, b)
80	unsigned int a, b;
81{
82
83	return (a < b ? a : b);
84}
85
86static __inline__
87unsigned int
88max(a, b)
89	unsigned int a, b;
90{
91
92	return (a > b ? a : b);
93}
94
95static __inline__
96long
97lmin(a, b)
98	long a, b;
99{
100
101	return (a < b ? a : b);
102}
103
104static __inline__
105long
106lmax(a, b)
107	long a, b;
108{
109
110	return (a > b ? a : b);
111}
112
113static __inline__
114unsigned long
115ulmin(a, b)
116	unsigned long a, b;
117{
118
119	return (a < b ? a : b);
120}
121
122static __inline__
123unsigned long
124ulmax(a, b)
125	unsigned long a, b;
126{
127
128	return (a > b ? a : b);
129}
130
131static __inline__
132ffs(mask)
133	register long mask;
134{
135	register int bit;
136
137	if (!mask)
138		return(0);
139	for (bit = 1;; ++bit) {
140		if (mask&0x01)
141			return(bit);
142		mask >>= 1;
143	}
144}
145
146static __inline__
147bcmp(v1, v2, len)
148	void *v1, *v2;
149	register unsigned len;
150{
151	register u_char *s1 = v1, *s2 = v2;
152
153	while (len--)
154		if (*s1++ != *s2++)
155			return (1);
156	return (0);
157}
158
159static __inline__
160size_t
161strlen(s1)
162	register __const__ char *s1;
163{
164	register size_t len;
165
166	for (len = 0; *s1++ != '\0'; len++)
167		;
168	return (len);
169}
170
171#else /* not __GNUC__ */
172
173int	bdb		__P((void));
174void	disable_intr	__P((void));
175void	enable_intr	__P((void));
176u_char	inb		__P((u_int port));
177void	outb		__P((u_int port, u_int data));	/* XXX - incompat */
178
179#endif	/* __GNUC__ */
180
181#define	really_u_int	int	/* XXX */
182#define	really_void	int	/* XXX */
183
184void	load_cr0	__P((u_int cr0));
185really_u_int	rcr0	__P((void));
186
187#ifdef notyet
188really_void	setidt	__P((int idx, /*XXX*/caddr_t func, int typ, int dpl));
189#endif
190
191#undef	really_u_int
192#undef	really_void
193
194