xref: /netbsd/sys/arch/atari/atari/be_bus.c (revision 60e2ec70)
1 /*	$NetBSD: be_bus.c,v 1.18 2023/01/06 10:28:27 tsutsui Exp $	*/
2 
3 /*-
4  * Copyright (c) 1998 The NetBSD Foundation, Inc.
5  * All rights reserved.
6  *
7  * This code is derived from software contributed to The NetBSD Foundation
8  * by Leo Weppelman.
9  *
10  * Redistribution and use in source and binary forms, with or without
11  * modification, are permitted provided that the following conditions
12  * are met:
13  * 1. Redistributions of source code must retain the above copyright
14  *    notice, this list of conditions and the following disclaimer.
15  * 2. Redistributions in binary form must reproduce the above copyright
16  *    notice, this list of conditions and the following disclaimer in the
17  *    documentation and/or other materials provided with the distribution.
18  *
19  * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22  * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29  * POSSIBILITY OF SUCH DAMAGE.
30  */
31 
32 #include <sys/cdefs.h>
33 __KERNEL_RCSID(0, "$NetBSD: be_bus.c,v 1.18 2023/01/06 10:28:27 tsutsui Exp $");
34 
35 #include <sys/types.h>
36 #include <sys/param.h>
37 #include <sys/systm.h>
38 #include <sys/kmem.h>
39 #include <machine/cpu.h>
40 #include <sys/bus.h>
41 
42 /*
43  * This file contains the common functions for using a big endian (linear)
44  * bus on a big endian atari.
45  */
46 
47 	/* Autoconf detection stuff */
48 static int		beb_bus_space_peek_1(bus_space_tag_t,
49 				bus_space_handle_t, bus_size_t);
50 static int		beb_bus_space_peek_2(bus_space_tag_t,
51 				bus_space_handle_t, bus_size_t);
52 static int		beb_bus_space_peek_4(bus_space_tag_t,
53 				bus_space_handle_t, bus_size_t);
54 static int		beb_bus_space_peek_8(bus_space_tag_t,
55 				bus_space_handle_t, bus_size_t);
56 
57 	/* read (single) */
58 static uint8_t		beb_bus_space_read_1(bus_space_tag_t,
59 				bus_space_handle_t, bus_size_t);
60 static uint16_t		beb_bus_space_read_2(bus_space_tag_t,
61 				bus_space_handle_t, bus_size_t);
62 static uint32_t		beb_bus_space_read_4(bus_space_tag_t,
63 				bus_space_handle_t, bus_size_t);
64 static uint64_t		beb_bus_space_read_8(bus_space_tag_t,
65 				bus_space_handle_t, bus_size_t);
66 
67 	/* write (single) */
68 static void		beb_bus_space_write_1(bus_space_tag_t,
69 				bus_space_handle_t, bus_size_t, uint8_t);
70 static void		beb_bus_space_write_2(bus_space_tag_t,
71 				bus_space_handle_t, bus_size_t, uint16_t);
72 static void		beb_bus_space_write_4(bus_space_tag_t,
73 				bus_space_handle_t, bus_size_t, uint32_t);
74 static void		beb_bus_space_write_8(bus_space_tag_t,
75 				bus_space_handle_t, bus_size_t, uint64_t);
76 
77 	/* read multiple */
78 static void		beb_bus_space_read_multi_1(bus_space_tag_t,
79 				bus_space_handle_t, bus_size_t, uint8_t *,
80 				bus_size_t);
81 static void		beb_bus_space_read_multi_2(bus_space_tag_t,
82 				bus_space_handle_t, bus_size_t, uint16_t *,
83 				bus_size_t);
84 static void		beb_bus_space_read_multi_4(bus_space_tag_t,
85 				bus_space_handle_t, bus_size_t, uint32_t *,
86 				bus_size_t);
87 static void		beb_bus_space_read_multi_8(bus_space_tag_t,
88 				bus_space_handle_t, bus_size_t, uint64_t *,
89 				bus_size_t);
90 
91 	/* write multiple */
92 static void		beb_bus_space_write_multi_1(bus_space_tag_t,
93 				bus_space_handle_t, bus_size_t,
94 				const uint8_t *, bus_size_t);
95 static void		beb_bus_space_write_multi_2(bus_space_tag_t,
96 				bus_space_handle_t, bus_size_t,
97 				const uint16_t *, bus_size_t);
98 static void		beb_bus_space_write_multi_4(bus_space_tag_t,
99 				bus_space_handle_t, bus_size_t,
100 				const uint32_t *, bus_size_t);
101 static void		beb_bus_space_write_multi_8(bus_space_tag_t,
102 				bus_space_handle_t, bus_size_t,
103 				const uint64_t *, bus_size_t);
104 
105 	/* read region */
106 static void		beb_bus_space_read_region_1(bus_space_tag_t,
107 				bus_space_handle_t, bus_size_t, uint8_t *,
108 				bus_size_t);
109 static void		beb_bus_space_read_region_2(bus_space_tag_t,
110 				bus_space_handle_t, bus_size_t, uint16_t *,
111 				bus_size_t);
112 static void		beb_bus_space_read_region_4(bus_space_tag_t,
113 				bus_space_handle_t, bus_size_t, uint32_t *,
114 				bus_size_t);
115 static void		beb_bus_space_read_region_8(bus_space_tag_t,
116 				bus_space_handle_t, bus_size_t, uint64_t *,
117 				bus_size_t);
118 
119 	/* read region */
120 static void		beb_bus_space_write_region_1(bus_space_tag_t,
121 				bus_space_handle_t, bus_size_t,
122 				const uint8_t *, bus_size_t);
123 static void		beb_bus_space_write_region_2(bus_space_tag_t,
124 				bus_space_handle_t, bus_size_t,
125 				const uint16_t *, bus_size_t);
126 static void		beb_bus_space_write_region_4(bus_space_tag_t,
127 				bus_space_handle_t, bus_size_t,
128 				const uint32_t *, bus_size_t);
129 static void		beb_bus_space_write_region_8(bus_space_tag_t,
130 				bus_space_handle_t, bus_size_t,
131 				const uint64_t *, bus_size_t);
132 
133 	/* set multi */
134 static void		beb_bus_space_set_multi_1(bus_space_tag_t,
135 				bus_space_handle_t, bus_size_t, uint8_t,
136 				bus_size_t);
137 static void		beb_bus_space_set_multi_2(bus_space_tag_t,
138 				bus_space_handle_t, bus_size_t, uint16_t,
139 				bus_size_t);
140 static void		beb_bus_space_set_multi_4(bus_space_tag_t,
141 				bus_space_handle_t, bus_size_t, uint32_t,
142 				bus_size_t);
143 static void		beb_bus_space_set_multi_8(bus_space_tag_t,
144 				bus_space_handle_t, bus_size_t, uint64_t,
145 				bus_size_t);
146 
147 	/* set region */
148 static void		beb_bus_space_set_region_1(bus_space_tag_t,
149 				bus_space_handle_t, bus_size_t, uint8_t,
150 				bus_size_t);
151 static void		beb_bus_space_set_region_2(bus_space_tag_t,
152 				bus_space_handle_t, bus_size_t, uint16_t,
153 				bus_size_t);
154 static void		beb_bus_space_set_region_4(bus_space_tag_t,
155 				bus_space_handle_t, bus_size_t, uint32_t,
156 				bus_size_t);
157 static void		beb_bus_space_set_region_8(bus_space_tag_t,
158 				bus_space_handle_t, bus_size_t, uint64_t,
159 				bus_size_t);
160 
161 /*
162  * Don't force a function call overhead on these primitives...
163  */
164 #define __read_1(h, o)		*((volatile uint8_t  *)((h) + (o)))
165 #define __read_2(h, o)		*((volatile uint16_t *)((h) + (o)))
166 #define __read_4(h, o)		*((volatile uint32_t *)((h) + (o)))
167 #define __read_8(h, o)		*((volatile uint64_t *)((h) + (o)))
168 
169 #define __write_1(h, o, v)	*((volatile uint8_t  *)((h) + (o))) = (v)
170 #define __write_2(h, o, v)	*((volatile uint16_t *)((h) + (o))) = (v)
171 #define __write_4(h, o, v)	*((volatile uint32_t *)((h) + (o))) = (v)
172 #define __write_8(h, o, v)	*((volatile uint64_t *)((h) + (o))) = (v)
173 
174 bus_space_tag_t
beb_alloc_bus_space_tag(bus_space_tag_t storage)175 beb_alloc_bus_space_tag(bus_space_tag_t storage)
176 {
177 	bus_space_tag_t	beb_t;
178 
179 	/*
180 	 * Allow the caller to specify storage space for the tag. This
181 	 * is used during console config (when kmem_alloc() can't be used).
182 	 */
183 	if (storage != NULL)
184 		beb_t = storage;
185 	else {
186 		beb_t = kmem_alloc(sizeof(*beb_t), KM_SLEEP);
187 	}
188 	memset(beb_t, 0, sizeof(*beb_t));
189 
190 	beb_t->abs_p_1   = beb_bus_space_peek_1;
191 	beb_t->abs_p_2   = beb_bus_space_peek_2;
192 	beb_t->abs_p_4   = beb_bus_space_peek_4;
193 	beb_t->abs_p_8   = beb_bus_space_peek_8;
194 	beb_t->abs_r_1   = beb_bus_space_read_1;
195 	beb_t->abs_r_2   = beb_bus_space_read_2;
196 	beb_t->abs_r_4   = beb_bus_space_read_4;
197 	beb_t->abs_r_8   = beb_bus_space_read_8;
198 	beb_t->abs_rs_1  = beb_bus_space_read_1;
199 	beb_t->abs_rs_2  = beb_bus_space_read_2;
200 	beb_t->abs_rs_4  = beb_bus_space_read_4;
201 	beb_t->abs_rs_8  = beb_bus_space_read_8;
202 	beb_t->abs_rm_1  = beb_bus_space_read_multi_1;
203 	beb_t->abs_rm_2  = beb_bus_space_read_multi_2;
204 	beb_t->abs_rm_4  = beb_bus_space_read_multi_4;
205 	beb_t->abs_rm_8  = beb_bus_space_read_multi_8;
206 	beb_t->abs_rms_1 = beb_bus_space_read_multi_1;
207 	beb_t->abs_rms_2 = beb_bus_space_read_multi_2;
208 	beb_t->abs_rms_4 = beb_bus_space_read_multi_4;
209 	beb_t->abs_rms_8 = beb_bus_space_read_multi_8;
210 	beb_t->abs_rr_1  = beb_bus_space_read_region_1;
211 	beb_t->abs_rr_2  = beb_bus_space_read_region_2;
212 	beb_t->abs_rr_4  = beb_bus_space_read_region_4;
213 	beb_t->abs_rr_8  = beb_bus_space_read_region_8;
214 	beb_t->abs_rrs_1 = beb_bus_space_read_region_1;
215 	beb_t->abs_rrs_2 = beb_bus_space_read_region_2;
216 	beb_t->abs_rrs_4 = beb_bus_space_read_region_4;
217 	beb_t->abs_rrs_8 = beb_bus_space_read_region_8;
218 	beb_t->abs_w_1   = beb_bus_space_write_1;
219 	beb_t->abs_w_2   = beb_bus_space_write_2;
220 	beb_t->abs_w_4   = beb_bus_space_write_4;
221 	beb_t->abs_w_8   = beb_bus_space_write_8;
222 	beb_t->abs_ws_1  = beb_bus_space_write_1;
223 	beb_t->abs_ws_2  = beb_bus_space_write_2;
224 	beb_t->abs_ws_4  = beb_bus_space_write_4;
225 	beb_t->abs_ws_8  = beb_bus_space_write_8;
226 	beb_t->abs_wm_1  = beb_bus_space_write_multi_1;
227 	beb_t->abs_wm_2  = beb_bus_space_write_multi_2;
228 	beb_t->abs_wm_4  = beb_bus_space_write_multi_4;
229 	beb_t->abs_wm_8  = beb_bus_space_write_multi_8;
230 	beb_t->abs_wms_1 = beb_bus_space_write_multi_1;
231 	beb_t->abs_wms_2 = beb_bus_space_write_multi_2;
232 	beb_t->abs_wms_4 = beb_bus_space_write_multi_4;
233 	beb_t->abs_wms_8 = beb_bus_space_write_multi_8;
234 	beb_t->abs_wr_1  = beb_bus_space_write_region_1;
235 	beb_t->abs_wr_2  = beb_bus_space_write_region_2;
236 	beb_t->abs_wr_4  = beb_bus_space_write_region_4;
237 	beb_t->abs_wr_8  = beb_bus_space_write_region_8;
238 	beb_t->abs_wrs_1 = beb_bus_space_write_region_1;
239 	beb_t->abs_wrs_2 = beb_bus_space_write_region_2;
240 	beb_t->abs_wrs_4 = beb_bus_space_write_region_4;
241 	beb_t->abs_wrs_8 = beb_bus_space_write_region_8;
242 	beb_t->abs_sm_1  = beb_bus_space_set_multi_1;
243 	beb_t->abs_sm_2  = beb_bus_space_set_multi_2;
244 	beb_t->abs_sm_4  = beb_bus_space_set_multi_4;
245 	beb_t->abs_sm_8  = beb_bus_space_set_multi_8;
246 	beb_t->abs_sr_1  = beb_bus_space_set_region_1;
247 	beb_t->abs_sr_2  = beb_bus_space_set_region_2;
248 	beb_t->abs_sr_4  = beb_bus_space_set_region_4;
249 	beb_t->abs_sr_8  = beb_bus_space_set_region_8;
250 
251 	return beb_t;
252 }
253 
254 
255 /*
256  * The various access functions
257  */
258 
259 /*
260  *	int bus_space_peek_N(bus_space_tag_t tag,
261  *		bus_space_handle_t sh, bus_size_t offset);
262  *
263  * Check if the address is suitable for reading N-byte quantities.
264  */
265 static int
beb_bus_space_peek_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)266 beb_bus_space_peek_1(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
267 {
268 
269 	return !badbaddr((void *)(h + o), 1);
270 }
271 
272 static int
beb_bus_space_peek_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)273 beb_bus_space_peek_2(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
274 {
275 
276 	return !badbaddr((void *)(h + o), 2);
277 }
278 
279 static int
beb_bus_space_peek_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)280 beb_bus_space_peek_4(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
281 {
282 
283 	return !badbaddr((void *)(h + o), 4);
284 }
285 
286 static int
beb_bus_space_peek_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)287 beb_bus_space_peek_8(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
288 {
289 
290 	return !badbaddr((void *)(h + o), 8);
291 }
292 
293 /*
294  *	uintX_t bus_space_read_N(bus_space_tag_t tag,
295  *		bus_space_handle_t bsh, bus_size_t offset);
296  *
297  * Return an 1, 2, 4, or 8 byte value read from the bus_space described
298  * by tag/handle at `offset'. The value is converted to host-endian.
299  */
300 static uint8_t
beb_bus_space_read_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)301 beb_bus_space_read_1(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
302 {
303 
304 	return __read_1(h, o);
305 }
306 
307 static uint16_t
beb_bus_space_read_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)308 beb_bus_space_read_2(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
309 {
310 
311 	return __read_2(h, o);
312 }
313 
314 static uint32_t
beb_bus_space_read_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)315 beb_bus_space_read_4(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
316 {
317 
318 	return __read_4(h, o);
319 }
320 
321 static uint64_t
beb_bus_space_read_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o)322 beb_bus_space_read_8(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o)
323 {
324 
325 	return __read_8(h, o);
326 }
327 
328 /*
329  *	uintX_t bus_space_write_N(bus_space_tag_t tag,
330  *		bus_space_handle_t bsh, bus_size_t offset, uintX_t val);
331  *
332  * Write an 1, 2, 4, or 8 byte value to the bus_space described by tag/handle
333  * at `offset'. The value `val' is converted from host to bus endianness
334  * before being written.
335  */
336 static void
beb_bus_space_write_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint8_t v)337 beb_bus_space_write_1(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o,
338     uint8_t v)
339 {
340 
341 	__write_1(h, o, v);
342 }
343 
344 static void
beb_bus_space_write_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint16_t v)345 beb_bus_space_write_2(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o,
346     uint16_t v)
347 {
348 
349 	__write_2(h, o, v);
350 }
351 
352 static void
beb_bus_space_write_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint32_t v)353 beb_bus_space_write_4(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o,
354     uint32_t v)
355 {
356 
357 	__write_4(h, o, v);
358 }
359 
360 static void
beb_bus_space_write_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint64_t v)361 beb_bus_space_write_8(bus_space_tag_t t, bus_space_handle_t h, bus_size_t o,
362     uint64_t v)
363 {
364 
365 	__write_8(h, o, v);
366 }
367 
368 /*
369  *	void bus_space_read_multi_N(bus_space_tag_t tag,
370  *		bus_space_handle_t bsh, bus_size_t offset, uintX_t *address,
371  *		bus_size_t count);
372  *
373  * Read 'count' 1, 2, 4, or 8 byte values from the bus_space described by
374  * tag/handle at `offset' and store them in the address range starting at
375  * 'address'. The values are converted to CPU endian order before being
376  * being stored.
377  */
378 static void
beb_bus_space_read_multi_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint8_t * a,bus_size_t c)379 beb_bus_space_read_multi_1(bus_space_tag_t t, bus_space_handle_t h,
380     bus_size_t o, uint8_t *a, bus_size_t c)
381 {
382 
383 	for (; c; a++, c--)
384 		*a = __read_1(h, o);
385 }
386 
387 static void
beb_bus_space_read_multi_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint16_t * a,bus_size_t c)388 beb_bus_space_read_multi_2(bus_space_tag_t t, bus_space_handle_t h,
389     bus_size_t o, uint16_t *a, bus_size_t c)
390 {
391 
392 	for (; c; a++, c--)
393 		*a = __read_2(h, o);
394 }
395 
396 static void
beb_bus_space_read_multi_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint32_t * a,bus_size_t c)397 beb_bus_space_read_multi_4(bus_space_tag_t t, bus_space_handle_t h,
398     bus_size_t o, uint32_t *a, bus_size_t c)
399 {
400 
401 	for (; c; a++, c--)
402 		*a = __read_4(h, o);
403 }
404 
405 static void
beb_bus_space_read_multi_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint64_t * a,bus_size_t c)406 beb_bus_space_read_multi_8(bus_space_tag_t t, bus_space_handle_t h,
407     bus_size_t o, uint64_t *a, bus_size_t c)
408 {
409 
410 	for (; c; a++, c--)
411 		*a = __read_8(h, o);
412 }
413 
414 /*
415  *	void bus_space_write_multi_N(bus_space_tag_t tag,
416  *		bus_space_handle_t bsh, bus_size_t offset,
417  *		const uintX_t *address, bus_size_t count);
418  *
419  * Write 'count' 1, 2, 4, or 8 byte values from the address range starting
420  * at 'address' to the bus_space described by tag/handle at `offset'.
421  * The values are converted to bus endian order before being written to
422  * the bus.
423  */
424 static void
beb_bus_space_write_multi_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint8_t * a,bus_size_t c)425 beb_bus_space_write_multi_1(bus_space_tag_t t, bus_space_handle_t h,
426     bus_size_t o, const uint8_t *a, bus_size_t c)
427 {
428 
429 	for (; c; a++, c--)
430 		__write_1(h, o, *a);
431 }
432 
433 static void
beb_bus_space_write_multi_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint16_t * a,bus_size_t c)434 beb_bus_space_write_multi_2(bus_space_tag_t t, bus_space_handle_t h,
435     bus_size_t o, const uint16_t *a, bus_size_t c)
436 {
437 
438 	for (; c; a++, c--)
439 		__write_2(h, o, *a);
440 }
441 
442 static void
beb_bus_space_write_multi_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint32_t * a,bus_size_t c)443 beb_bus_space_write_multi_4(bus_space_tag_t t, bus_space_handle_t h,
444     bus_size_t o, const uint32_t *a, bus_size_t c)
445 {
446 
447 	for (; c; a++, c--)
448 		__write_4(h, o, *a);
449 }
450 
451 static void
beb_bus_space_write_multi_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint64_t * a,bus_size_t c)452 beb_bus_space_write_multi_8(bus_space_tag_t t, bus_space_handle_t h,
453     bus_size_t o, const uint64_t *a, bus_size_t c)
454 {
455 
456 	for (; c; a++, c--)
457 		__write_8(h, o, *a);
458 }
459 
460 /*
461  *	void bus_space_read_region_N(bus_space_tag_t tag,
462  *		bus_space_handle_t bsh, bus_size_t offset,
463  *		uintN_t *addr, bus_size_t count);
464  *
465  * Read `count' 1, 2, 4, or 8 byte quantities from bus space
466  * described by tag/handle and starting at `offset' and copy into
467  * buffer provided.
468  */
469 static void
beb_bus_space_read_region_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint8_t * a,bus_size_t c)470 beb_bus_space_read_region_1(bus_space_tag_t t, bus_space_handle_t h,
471     bus_size_t o, uint8_t *a, bus_size_t c)
472 {
473 
474 	for (; c; a++, o++, c--)
475 		*a = __read_1(h, o);
476 }
477 
478 static void
beb_bus_space_read_region_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint16_t * a,bus_size_t c)479 beb_bus_space_read_region_2(bus_space_tag_t t, bus_space_handle_t h,
480     bus_size_t o, uint16_t *a, bus_size_t c)
481 {
482 
483 	for (; c; a++, o += 2, c--)
484 		*a = __read_2(h, o);
485 }
486 
487 static void
beb_bus_space_read_region_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint32_t * a,bus_size_t c)488 beb_bus_space_read_region_4(bus_space_tag_t t, bus_space_handle_t h,
489     bus_size_t o, uint32_t *a, bus_size_t c)
490 {
491 
492 	for (; c; a++, o += 4, c--)
493 		*a = __read_4(h, o);
494 }
495 
496 static void
beb_bus_space_read_region_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint64_t * a,bus_size_t c)497 beb_bus_space_read_region_8(bus_space_tag_t t, bus_space_handle_t h,
498     bus_size_t o, uint64_t *a, bus_size_t c)
499 {
500 
501 	for (; c; a++, o += 8, c--)
502 		*a = __read_8(h, o);
503 }
504 
505 /*
506  *	void bus_space_write_region_N(bus_space_tag_t tag,
507  *		bus_space_handle_t bsh, bus_size_t offset,
508  *		uintN_t *addr, bus_size_t count);
509  *
510  * Copy `count' 1, 2, 4, or 8 byte quantities from the buffer provided
511  * into the bus space described by tag/handle and starting at `offset'.
512  */
513 static void
beb_bus_space_write_region_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint8_t * a,bus_size_t c)514 beb_bus_space_write_region_1(bus_space_tag_t t, bus_space_handle_t h,
515     bus_size_t o, const uint8_t *a, bus_size_t c)
516 {
517 
518 	for (; c; a++, o++, c--)
519 		__write_1(h, o, *a);
520 }
521 
522 static void
beb_bus_space_write_region_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint16_t * a,bus_size_t c)523 beb_bus_space_write_region_2(bus_space_tag_t t, bus_space_handle_t h,
524     bus_size_t o, const uint16_t *a, bus_size_t c)
525 {
526 
527 	for (; c; a++, o += 2, c--)
528 		__write_2(h, o, *a);
529 }
530 
531 static void
beb_bus_space_write_region_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint32_t * a,bus_size_t c)532 beb_bus_space_write_region_4(bus_space_tag_t t, bus_space_handle_t h,
533     bus_size_t o, const uint32_t *a, bus_size_t c)
534 {
535 
536 	for (; c; a++, o += 4, c--)
537 		__write_4(h, o, *a);
538 }
539 
540 static void
beb_bus_space_write_region_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,const uint64_t * a,bus_size_t c)541 beb_bus_space_write_region_8(bus_space_tag_t t, bus_space_handle_t h,
542     bus_size_t o, const uint64_t *a, bus_size_t c)
543 {
544 
545 	for (; c; a++, o += 8, c--)
546 		__write_8(h, o, *a);
547 }
548 
549 /*
550  *	void bus_space_set_multi_N(bus_space_tag_t tag,
551  *		bus_space_handle_t bsh, bus_size_t offset, uintN_t val,
552  *		bus_size_t count);
553  *
554  * Write the 1, 2, 4, or 8 byte value `val' to bus space described
555  * by tag/handle/offset `count' times.
556  */
557 
558 static void
beb_bus_space_set_multi_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint8_t v,bus_size_t c)559 beb_bus_space_set_multi_1(bus_space_tag_t t, bus_space_handle_t h,
560     bus_size_t o, uint8_t v, bus_size_t c)
561 {
562 
563 	for (; c; c--)
564 		__write_1(h, o, v);
565 }
566 
567 static void
beb_bus_space_set_multi_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint16_t v,bus_size_t c)568 beb_bus_space_set_multi_2(bus_space_tag_t t, bus_space_handle_t h,
569     bus_size_t o, uint16_t v, bus_size_t c)
570 {
571 
572 	for (; c; c--)
573 		__write_2(h, o, v);
574 }
575 
576 static void
beb_bus_space_set_multi_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint32_t v,bus_size_t c)577 beb_bus_space_set_multi_4(bus_space_tag_t t, bus_space_handle_t h,
578     bus_size_t o, uint32_t v, bus_size_t c)
579 {
580 
581 	for (; c; c--)
582 		__write_4(h, o, v);
583 }
584 
585 static void
beb_bus_space_set_multi_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint64_t v,bus_size_t c)586 beb_bus_space_set_multi_8(bus_space_tag_t t, bus_space_handle_t h,
587     bus_size_t o, uint64_t v, bus_size_t c)
588 {
589 
590 	for (; c; c--)
591 		__write_8(h, o, v);
592 }
593 
594 /*
595  *	void bus_space_set_region_N(bus_space_tag_t tag,
596  *		bus_space_handle_t bsh, bus_size_t offset, uintN_t val,
597  *		bus_size_t count);
598  *
599  * Write `count' 1, 2, 4, or 8 byte value `val' to bus space described
600  * by tag/handle starting at `offset'.
601  */
602 static void
beb_bus_space_set_region_1(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint8_t v,bus_size_t c)603 beb_bus_space_set_region_1(bus_space_tag_t t, bus_space_handle_t h,
604     bus_size_t o, uint8_t v, bus_size_t c)
605 {
606 
607 	for (; c; o++, c--)
608 		__write_1(h, o, v);
609 }
610 
611 static void
beb_bus_space_set_region_2(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint16_t v,bus_size_t c)612 beb_bus_space_set_region_2(bus_space_tag_t t, bus_space_handle_t h,
613     bus_size_t o, uint16_t v, bus_size_t c)
614 {
615 
616 	for (; c; o += 2, c--)
617 		__write_2(h, o, v);
618 }
619 
620 static void
beb_bus_space_set_region_4(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint32_t v,bus_size_t c)621 beb_bus_space_set_region_4(bus_space_tag_t t, bus_space_handle_t h,
622     bus_size_t o, uint32_t v, bus_size_t c)
623 {
624 
625 	for (; c; o += 4, c--)
626 		__write_4(h, o, v);
627 }
628 
629 static void
beb_bus_space_set_region_8(bus_space_tag_t t,bus_space_handle_t h,bus_size_t o,uint64_t v,bus_size_t c)630 beb_bus_space_set_region_8(bus_space_tag_t t, bus_space_handle_t h,
631     bus_size_t o, uint64_t v, bus_size_t c)
632 {
633 
634 	for (; c; o += 8, c--)
635 		__write_8(h, o, v);
636 }
637