Deleted Added
sdiff udiff text old ( 77957 ) new ( 92842 )
full compact
1/*-
2 * Copyright (c) 1996, 1997, 1998 The NetBSD Foundation, Inc.
3 * All rights reserved.
4 *
5 * This code is derived from software contributed to The NetBSD Foundation
6 * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility,
7 * NASA Ames Research Center.
8 *
9 * Redistribution and use in source and binary forms, with or without
10 * modification, are permitted provided that the following conditions
11 * are met:
12 * 1. Redistributions of source code must retain the above copyright
13 * notice, this list of conditions and the following disclaimer.
14 * 2. Redistributions in binary form must reproduce the above copyright
15 * notice, this list of conditions and the following disclaimer in the
16 * documentation and/or other materials provided with the distribution.
17 * 3. All advertising materials mentioning features or use of this software
18 * must display the following acknowledgement:
19 * This product includes software developed by the NetBSD
20 * Foundation, Inc. and its contributors.
21 * 4. Neither the name of The NetBSD Foundation nor the names of its
22 * contributors may be used to endorse or promote products derived
23 * from this software without specific prior written permission.
24 *
25 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
26 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
27 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
28 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
29 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
30 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
31 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
32 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
33 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
34 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
35 * POSSIBILITY OF SUCH DAMAGE.
36 */
37
38/*
39 * Copyright (c) 1996 Charles M. Hannum. All rights reserved.
40 * Copyright (c) 1996 Christopher G. Demetriou. All rights reserved.
41 *
42 * Redistribution and use in source and binary forms, with or without
43 * modification, are permitted provided that the following conditions
44 * are met:
45 * 1. Redistributions of source code must retain the above copyright
46 * notice, this list of conditions and the following disclaimer.
47 * 2. Redistributions in binary form must reproduce the above copyright
48 * notice, this list of conditions and the following disclaimer in the
49 * documentation and/or other materials provided with the distribution.
50 * 3. All advertising materials mentioning features or use of this software
51 * must display the following acknowledgement:
52 * This product includes software developed by Christopher G. Demetriou
53 * for the NetBSD Project.
54 * 4. The name of the author may not be used to endorse or promote products
55 * derived from this software without specific prior written permission
56 *
57 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
58 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
59 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
60 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
61 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
62 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
63 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
64 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
65 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
66 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
67 *
68 * $NetBSD: bus.h,v 1.9.4.1 2000/06/30 16:27:30 simonb Exp $
69 * $FreeBSD: head/sys/powerpc/include/bus.h 77957 2001-06-10 02:39:37Z benno $
70 */
71
72#ifndef _MACPPC_BUS_H_
73#define _MACPPC_BUS_H_
74
75#include <machine/pio.h>
76
77/*
78 * Values for the macppc bus space tag, not to be used directly by MI code.
79 */
80
81#define __BUS_SPACE_HAS_STREAM_METHODS
82
83#define MACPPC_BUS_ADDR_MASK 0xfffff000
84#define MACPPC_BUS_STRIDE_MASK 0x0000000f
85
86#define macppc_make_bus_space_tag(addr, stride) \
87 (((addr) & MACPPC_BUS_ADDR_MASK) | (stride))
88#define __BA(t, h, o) ((void *)((h) + ((o) << ((t) & MACPPC_BUS_STRIDE_MASK))))
89
90/*
91 * Bus address and size types
92 */
93typedef u_int32_t bus_addr_t;
94typedef u_int32_t bus_size_t;
95
96/*
97 * Access methods for bus resources and address space.
98 */
99typedef u_int32_t bus_space_tag_t;
100typedef u_int32_t bus_space_handle_t;
101
102/*
103 * int bus_space_map __P((bus_space_tag_t t, bus_addr_t addr,
104 * bus_size_t size, int flags, bus_space_handle_t *bshp));
105 *
106 * Map a region of bus space.
107 */
108
109#define BUS_SPACE_MAP_CACHEABLE 0x01
110#define BUS_SPACE_MAP_LINEAR 0x02
111#define BUS_SPACE_MAP_PREFETCHABLE 0x04
112
113extern void *mapiodev(vm_offset_t, vm_size_t);
114
115static __inline int
116bus_space_map(bus_space_tag_t t, bus_addr_t addr, bus_size_t size, int flags,
117 bus_space_handle_t *bshp)
118{
119 vm_offset_t base = t & MACPPC_BUS_ADDR_MASK;
120 int stride = t & MACPPC_BUS_STRIDE_MASK;
121
122 *bshp = (bus_space_handle_t)
123 mapiodev(base + (addr << stride), size << stride);
124 return 0;
125}
126
127/*
128 * int bus_space_unmap __P((bus_space_tag_t t,
129 * bus_space_handle_t bsh, bus_size_t size));
130 *
131 * Unmap a region of bus space.
132 */
133
134#define bus_space_unmap(t, bsh, size)
135
136/*
137 * int bus_space_subregion __P((bus_space_tag_t t,
138 * bus_space_handle_t bsh, bus_size_t offset, bus_size_t size,
139 * bus_space_handle_t *nbshp));
140 *
141 * Get a new handle for a subregion of an already-mapped area of bus space.
142 */
143
144#define bus_space_subregion(t, bsh, offset, size, bshp) \
145 ((*(bshp) = (bus_space_handle_t)__BA(t, bsh, offset)), 0)
146
147/*
148 * int bus_space_alloc __P((bus_space_tag_t t, bus_addr_t rstart,
149 * bus_addr_t rend, bus_size_t size, bus_size_t align,
150 * bus_size_t boundary, int flags, bus_addr_t *addrp,
151 * bus_space_handle_t *bshp));
152 *
153 * Allocate a region of bus space.
154 */
155
156#if 0
157#define bus_space_alloc(t, rs, re, s, a, b, f, ap, hp) !!! unimplemented !!!
158#endif
159
160/*
161 * int bus_space_free __P((bus_space_tag_t t,
162 * bus_space_handle_t bsh, bus_size_t size));
163 *
164 * Free a region of bus space.
165 */
166#if 0
167#define bus_space_free(t, h, s) !!! unimplemented !!!
168#endif
169
170/*
171 * u_intN_t bus_space_read_N __P((bus_space_tag_t tag,
172 * bus_space_handle_t bsh, bus_size_t offset));
173 *
174 * Read a 1, 2, 4, or 8 byte quantity from bus space
175 * described by tag/handle/offset.
176 */
177
178#define bus_space_read_1(t, h, o) (in8(__BA(t, h, o)))
179#define bus_space_read_2(t, h, o) (in16rb(__BA(t, h, o)))
180#define bus_space_read_4(t, h, o) (in32rb(__BA(t, h, o)))
181#if 0 /* Cause a link error for bus_space_read_8 */
182#define bus_space_read_8(t, h, o) !!! unimplemented !!!
183#endif
184
185#define bus_space_read_stream_1(t, h, o) (in8(__BA(t, h, o)))
186#define bus_space_read_stream_2(t, h, o) (in16(__BA(t, h, o)))
187#define bus_space_read_stream_4(t, h, o) (in32(__BA(t, h, o)))
188#if 0 /* Cause a link error for bus_space_read_stream_8 */
189#define bus_space_read_8(t, h, o) !!! unimplemented !!!
190#endif
191
192/*
193 * void bus_space_read_multi_N __P((bus_space_tag_t tag,
194 * bus_space_handle_t bsh, bus_size_t offset,
195 * u_intN_t *addr, size_t count));
196 *
197 * Read `count' 1, 2, 4, or 8 byte quantities from bus space
198 * described by tag/handle/offset and copy into buffer provided.
199 */
200
201#define bus_space_read_multi_1(t, h, o, a, c) do { \
202 ins8(__BA(t, h, o), (a), (c)); \
203 } while (0)
204
205#define bus_space_read_multi_2(t, h, o, a, c) do { \
206 ins16rb(__BA(t, h, o), (a), (c)); \
207 } while (0)
208
209#define bus_space_read_multi_4(t, h, o, a, c) do { \
210 ins32rb(__BA(t, h, o), (a), (c)); \
211 } while (0)
212
213#if 0 /* Cause a link error for bus_space_read_multi_8 */
214#define bus_space_read_multi_8 !!! unimplemented !!!
215#endif
216
217#define bus_space_read_multi_stream_1(t, h, o, a, c) do { \
218 ins8(__BA(t, h, o), (a), (c)); \
219 } while (0)
220
221#define bus_space_read_multi_stream_2(t, h, o, a, c) do { \
222 ins16(__BA(t, h, o), (a), (c)); \
223 } while (0)
224
225#define bus_space_read_multi_stream_4(t, h, o, a, c) do { \
226 ins32(__BA(t, h, o), (a), (c)); \
227 } while (0)
228
229#if 0 /* Cause a link error for bus_space_read_multi_stream_8 */
230#define bus_space_read_multi_stream_8 !!! unimplemented !!!
231#endif
232
233/*
234 * void bus_space_read_region_N __P((bus_space_tag_t tag,
235 * bus_space_handle_t bsh, bus_size_t offset,
236 * u_intN_t *addr, size_t count));
237 *
238 * Read `count' 1, 2, 4, or 8 byte quantities from bus space
239 * described by tag/handle and starting at `offset' and copy into
240 * buffer provided.
241 */
242
243static __inline void
244bus_space_read_region_1(bus_space_tag_t tag, bus_space_handle_t bsh,
245 bus_size_t offset, u_int8_t *addr, size_t count)
246{
247 volatile u_int8_t *s = __BA(tag, bsh, offset);
248
249 while (count--)
250 *addr++ = *s++;
251 __asm __volatile("eieio; sync");
252}
253
254static __inline void
255bus_space_read_region_2(bus_space_tag_t tag, bus_space_handle_t bsh,
256 bus_size_t offset, u_int16_t *addr, size_t count)
257{
258 volatile u_int16_t *s = __BA(tag, bsh, offset);
259
260 while (count--)
261 __asm __volatile("lhbrx %0, 0, %1" :
262 "=r"(*addr++) : "r"(s++));
263 __asm __volatile("eieio; sync");
264}
265
266static __inline void
267bus_space_read_region_4(bus_space_tag_t tag, bus_space_handle_t bsh,
268 bus_size_t offset, u_int32_t *addr, size_t count)
269{
270 volatile u_int32_t *s = __BA(tag, bsh, offset);
271
272 while (count--)
273 __asm __volatile("lwbrx %0, 0, %1" :
274 "=r"(*addr++) : "r"(s++));
275 __asm __volatile("eieio; sync");
276}
277
278#if 0 /* Cause a link error for bus_space_read_region_8 */
279#define bus_space_read_region_8 !!! unimplemented !!!
280#endif
281
282static __inline void
283bus_space_read_region_stream_2(bus_space_tag_t tag, bus_space_handle_t bsh,
284 bus_size_t offset, u_int16_t *addr, size_t count)
285{
286 volatile u_int16_t *s = __BA(tag, bsh, offset);
287
288 while (count--)
289 *addr++ = *s++;
290 __asm __volatile("eieio; sync");
291}
292
293static __inline void
294bus_space_read_region_stream_4(bus_space_tag_t tag, bus_space_handle_t bsh,
295 bus_size_t offset, u_int32_t *addr, size_t count)
296{
297 volatile u_int32_t *s = __BA(tag, bsh, offset);
298
299 while (count--)
300 *addr++ = *s++;
301 __asm __volatile("eieio; sync");
302}
303
304#if 0 /* Cause a link error */
305#define bus_space_read_region_stream_8 !!! unimplemented !!!
306#endif
307
308/*
309 * void bus_space_write_N __P((bus_space_tag_t tag,
310 * bus_space_handle_t bsh, bus_size_t offset,
311 * u_intN_t value));
312 *
313 * Write the 1, 2, 4, or 8 byte value `value' to bus space
314 * described by tag/handle/offset.
315 */
316
317#define bus_space_write_1(t, h, o, v) out8(__BA(t, h, o), (v))
318#define bus_space_write_2(t, h, o, v) out16rb(__BA(t, h, o), (v))
319#define bus_space_write_4(t, h, o, v) out32rb(__BA(t, h, o), (v))
320
321#define bus_space_write_stream_1(t, h, o, v) out8(__BA(t, h, o), (v))
322#define bus_space_write_stream_2(t, h, o, v) out16(__BA(t, h, o), (v))
323#define bus_space_write_stream_4(t, h, o, v) out32(__BA(t, h, o), (v))
324
325#if 0 /* Cause a link error for bus_space_write_8 */
326#define bus_space_write_8 !!! unimplemented !!!
327#endif
328
329/*
330 * void bus_space_write_multi_N __P((bus_space_tag_t tag,
331 * bus_space_handle_t bsh, bus_size_t offset,
332 * const u_intN_t *addr, size_t count));
333 *
334 * Write `count' 1, 2, 4, or 8 byte quantities from the buffer
335 * provided to bus space described by tag/handle/offset.
336 */
337
338#define bus_space_write_multi_1(t, h, o, a, c) do { \
339 outsb(__BA(t, h, o), (a), (c)); \
340 } while (0)
341
342#define bus_space_write_multi_2(t, h, o, a, c) do { \
343 outsw(__BA(t, h, o), (a), (c)); \
344 } while (0)
345
346#define bus_space_write_multi_4(t, h, o, a, c) do { \
347 outsl(__BA(t, h, o), (a), (c)); \
348 } while (0)
349
350#if 0
351#define bus_space_write_multi_8 !!! unimplemented !!!
352#endif
353
354#define bus_space_write_multi_stream_2(t, h, o, a, c) do { \
355 outsw(__BA(t, h, o), (a), (c)); \
356 } while (0)
357
358#define bus_space_write_multi_stream_4(t, h, o, a, c) do { \
359 outsl(__BA(t, h, o), (a), (c)); \
360 } while (0)
361
362#if 0
363#define bus_space_write_multi_stream_8 !!! unimplemented !!!
364#endif
365
366/*
367 * void bus_space_write_region_N __P((bus_space_tag_t tag,
368 * bus_space_handle_t bsh, bus_size_t offset,
369 * const u_intN_t *addr, size_t count));
370 *
371 * Write `count' 1, 2, 4, or 8 byte quantities from the buffer provided
372 * to bus space described by tag/handle starting at `offset'.
373 */
374
375static __inline void
376bus_space_write_region_1(bus_space_tag_t tag, bus_space_handle_t bsh,
377 bus_size_t offset, const u_int8_t *addr, size_t count)
378{
379 volatile u_int8_t *d = __BA(tag, bsh, offset);
380
381 while (count--)
382 *d++ = *addr++;
383 __asm __volatile("eieio; sync");
384}
385
386static __inline void
387bus_space_write_region_2(bus_space_tag_t tag, bus_space_handle_t bsh,
388 bus_size_t offset, const u_int16_t *addr, size_t count)
389{
390 volatile u_int16_t *d = __BA(tag, bsh, offset);
391
392 while (count--)
393 __asm __volatile("sthbrx %0, 0, %1" ::
394 "r"(*addr++), "r"(d++));
395 __asm __volatile("eieio; sync");
396}
397
398static __inline void
399bus_space_write_region_4(bus_space_tag_t tag, bus_space_handle_t bsh,
400 bus_size_t offset, const u_int32_t *addr, size_t count)
401{
402 volatile u_int32_t *d = __BA(tag, bsh, offset);
403
404 while (count--)
405 __asm __volatile("stwbrx %0, 0, %1" ::
406 "r"(*addr++), "r"(d++));
407 __asm __volatile("eieio; sync");
408}
409
410#if 0
411#define bus_space_write_region_8 !!! bus_space_write_region_8 unimplemented !!!
412#endif
413
414static __inline void
415bus_space_write_region_stream_2(bus_space_tag_t tag, bus_space_handle_t bsh,
416 bus_size_t offset, const u_int16_t *addr, size_t count)
417{
418 volatile u_int16_t *d = __BA(tag, bsh, offset);
419
420 while (count--)
421 *d++ = *addr++;
422 __asm __volatile("eieio; sync");
423}
424
425static __inline void
426bus_space_write_region_stream_4(bus_space_tag_t tag, bus_space_handle_t bsh,
427 bus_size_t offset, const u_int32_t *addr, size_t count)
428{
429 volatile u_int32_t *d = __BA(tag, bsh, offset);
430
431 while (count--)
432 *d++ = *addr++;
433 __asm __volatile("eieio; sync");
434}
435
436#if 0
437#define bus_space_write_region_stream_8 !!! unimplemented !!!
438#endif
439
440/*
441 * void bus_space_set_multi_N __P((bus_space_tag_t tag,
442 * bus_space_handle_t bsh, bus_size_t offset, u_intN_t val,
443 * size_t count));
444 *
445 * Write the 1, 2, 4, or 8 byte value `val' to bus space described
446 * by tag/handle/offset `count' times.
447 */
448
449static __inline void
450bus_space_set_multi_1(bus_space_tag_t tag, bus_space_handle_t bsh,
451 bus_size_t offset, u_int8_t val, size_t count)
452{
453 volatile u_int8_t *d = __BA(tag, bsh, offset);
454
455 while (count--)
456 *d = val;
457 __asm __volatile("eieio; sync");
458}
459
460static __inline void
461bus_space_set_multi_2(bus_space_tag_t tag, bus_space_handle_t bsh,
462 bus_size_t offset, u_int16_t val, size_t count)
463{
464 volatile u_int16_t *d = __BA(tag, bsh, offset);
465
466 while (count--)
467 __asm __volatile("sthbrx %0, 0, %1" ::
468 "r"(val), "r"(d));
469 __asm __volatile("eieio; sync");
470}
471
472static __inline void
473bus_space_set_multi_4(bus_space_tag_t tag, bus_space_handle_t bsh,
474 bus_size_t offset, u_int32_t val, size_t count)
475{
476 volatile u_int32_t *d = __BA(tag, bsh, offset);
477
478 while (count--)
479 __asm __volatile("stwbrx %0, 0, %1" ::
480 "r"(val), "r"(d));
481 __asm __volatile("eieio; sync");
482}
483
484#if 0
485#define bus_space_set_multi_8 !!! bus_space_set_multi_8 unimplemented !!!
486#endif
487
488static __inline void
489bus_space_set_multi_stream_2(bus_space_tag_t tag, bus_space_handle_t bsh,
490 bus_size_t offset, u_int16_t val, size_t count)
491{
492 volatile u_int16_t *d = __BA(tag, bsh, offset);
493
494 while (count--)
495 *d = val;
496 __asm __volatile("eieio; sync");
497}
498
499static __inline void
500bus_space_set_multi_stream_4(bus_space_tag_t tag, bus_space_handle_t bsh,
501 bus_size_t offset, u_int32_t val, size_t count)
502{
503 volatile u_int32_t *d = __BA(tag, bsh, offset);
504
505 while (count--)
506 *d = val;
507 __asm __volatile("eieio; sync");
508}
509
510#if 0
511#define bus_space_set_multi_stream_8 !!! unimplemented !!!
512#endif
513
514/*
515 * void bus_space_set_region_N __P((bus_space_tag_t tag,
516 * bus_space_handle_t bsh, bus_size_t offset, u_intN_t val,
517 * size_t count));
518 *
519 * Write `count' 1, 2, 4, or 8 byte value `val' to bus space described
520 * by tag/handle starting at `offset'.
521 */
522
523static __inline void
524bus_space_set_region_1(bus_space_tag_t tag, bus_space_handle_t bsh,
525 bus_size_t offset, u_int8_t val, size_t count)
526{
527 volatile u_int8_t *d = __BA(tag, bsh, offset);
528
529 while (count--)
530 *d++ = val;
531 __asm __volatile("eieio; sync");
532}
533
534static __inline void
535bus_space_set_region_2(bus_space_tag_t tag, bus_space_handle_t bsh,
536 bus_size_t offset, u_int16_t val, size_t count)
537{
538 volatile u_int16_t *d = __BA(tag, bsh, offset);
539
540 while (count--)
541 __asm __volatile("sthbrx %0, 0, %1" ::
542 "r"(val), "r"(d++));
543 __asm __volatile("eieio; sync");
544}
545
546static __inline void
547bus_space_set_region_4(bus_space_tag_t tag, bus_space_handle_t bsh,
548 bus_size_t offset, u_int32_t val, size_t count)
549{
550 volatile u_int32_t *d = __BA(tag, bsh, offset);
551
552 while (count--)
553 __asm __volatile("stwbrx %0, 0, %1" ::
554 "r"(val), "r"(d++));
555 __asm __volatile("eieio; sync");
556}
557
558#if 0
559#define bus_space_set_region_8 !!! bus_space_set_region_8 unimplemented !!!
560#endif
561
562static __inline void
563bus_space_set_region_stream_2(bus_space_tag_t tag, bus_space_handle_t bsh,
564 bus_size_t offset, u_int16_t val, size_t count)
565{
566 volatile u_int16_t *d = __BA(tag, bsh, offset);
567
568 while (count--)
569 *d++ = val;
570 __asm __volatile("eieio; sync");
571}
572
573static __inline void
574bus_space_set_region_stream_4(bus_space_tag_t tag, bus_space_handle_t bsh,
575 bus_size_t offset, u_int32_t val, size_t count)
576{
577 volatile u_int32_t *d = __BA(tag, bsh, offset);
578
579 while (count--)
580 *d++ = val;
581 __asm __volatile("eieio; sync");
582}
583
584#if 0
585#define bus_space_set_region_stream_8 !!! unimplemented !!!
586#endif
587
588/*
589 * void bus_space_copy_region_N __P((bus_space_tag_t tag,
590 * bus_space_handle_t bsh1, bus_size_t off1,
591 * bus_space_handle_t bsh2, bus_size_t off2,
592 * size_t count));
593 *
594 * Copy `count' 1, 2, 4, or 8 byte values from bus space starting
595 * at tag/bsh1/off1 to bus space starting at tag/bsh2/off2.
596 */
597
598 /* XXX IMPLEMENT bus_space_copy_N() XXX */
599
600/*
601 * Bus read/write barrier methods.
602 *
603 * void bus_space_barrier __P((bus_space_tag_t tag,
604 * bus_space_handle_t bsh, bus_size_t offset,
605 * bus_size_t len, int flags));
606 *
607 * Note: the macppc does not currently require barriers, but we must
608 * provide the flags to MI code.
609 */
610
611#define bus_space_barrier(t, h, o, l, f) \
612 ((void)((void)(t), (void)(h), (void)(o), (void)(l), (void)(f)))
613#define BUS_SPACE_BARRIER_READ 0x01 /* force read barrier */
614#define BUS_SPACE_BARRIER_WRITE 0x02 /* force write barrier */
615
616#define BUS_SPACE_ALIGNED_POINTER(p, t) ALIGNED_POINTER(p, t)
617
618/*
619 * Bus DMA methods.
620 */
621
622/*
623 * Flags used in various bus DMA methods.
624 */
625#define BUS_DMA_WAITOK 0x00 /* safe to sleep (pseudo-flag) */
626#define BUS_DMA_NOWAIT 0x01 /* not safe to sleep */
627#define BUS_DMA_ALLOCNOW 0x02 /* perform resource allocation now */
628#define BUS_DMA_COHERENT 0x04 /* hint: map memory DMA coherent */
629#define BUS_DMA_BUS1 0x10 /* placeholders for bus functions... */
630#define BUS_DMA_BUS2 0x20
631#define BUS_DMA_BUS3 0x40
632#define BUS_DMA_BUS4 0x80
633
634/* Forwards needed by prototypes below. */
635struct mbuf;
636struct uio;
637
638/*
639 * Operations performed by bus_dmamap_sync().
640 */
641#define BUS_DMASYNC_PREREAD 0x01 /* pre-read synchronization */
642#define BUS_DMASYNC_POSTREAD 0x02 /* post-read synchronization */
643#define BUS_DMASYNC_PREWRITE 0x04 /* pre-write synchronization */
644#define BUS_DMASYNC_POSTWRITE 0x08 /* post-write synchronization */
645
646typedef struct macppc_bus_dma_tag *bus_dma_tag_t;
647typedef struct macppc_bus_dmamap *bus_dmamap_t;
648
649/*
650 * bus_dma_segment_t
651 *
652 * Describes a single contiguous DMA transaction. Values
653 * are suitable for programming into DMA registers.
654 */
655struct macppc_bus_dma_segment {
656 bus_addr_t ds_addr; /* DMA address */
657 bus_size_t ds_len; /* length of transfer */
658};
659typedef struct macppc_bus_dma_segment bus_dma_segment_t;
660
661/*
662 * bus_dma_tag_t
663 *
664 * A machine-dependent opaque type describing the implementation of
665 * DMA for a given bus.
666 */
667
668struct macppc_bus_dma_tag {
669 /*
670 * The `bounce threshold' is checked while we are loading
671 * the DMA map. If the physical address of the segment
672 * exceeds the threshold, an error will be returned. The
673 * caller can then take whatever action is necessary to
674 * bounce the transfer. If this value is 0, it will be
675 * ignored.
676 */
677 bus_addr_t _bounce_thresh;
678
679 /*
680 * DMA mapping methods.
681 */
682 int (*_dmamap_create) __P((bus_dma_tag_t, bus_size_t, int,
683 bus_size_t, bus_size_t, int, bus_dmamap_t *));
684 void (*_dmamap_destroy) __P((bus_dma_tag_t, bus_dmamap_t));
685 int (*_dmamap_load) __P((bus_dma_tag_t, bus_dmamap_t, void *,
686 bus_size_t, struct proc *, int));
687 int (*_dmamap_load_mbuf) __P((bus_dma_tag_t, bus_dmamap_t,
688 struct mbuf *, int));
689 int (*_dmamap_load_uio) __P((bus_dma_tag_t, bus_dmamap_t,
690 struct uio *, int));
691 int (*_dmamap_load_raw) __P((bus_dma_tag_t, bus_dmamap_t,
692 bus_dma_segment_t *, int, bus_size_t, int));
693 void (*_dmamap_unload) __P((bus_dma_tag_t, bus_dmamap_t));
694 void (*_dmamap_sync) __P((bus_dma_tag_t, bus_dmamap_t,
695 bus_addr_t, bus_size_t, int));
696
697 /*
698 * DMA memory utility functions.
699 */
700 int (*_dmamem_alloc) __P((bus_dma_tag_t, bus_size_t, bus_size_t,
701 bus_size_t, bus_dma_segment_t *, int, int *, int));
702 void (*_dmamem_free) __P((bus_dma_tag_t,
703 bus_dma_segment_t *, int));
704 int (*_dmamem_map) __P((bus_dma_tag_t, bus_dma_segment_t *,
705 int, size_t, caddr_t *, int));
706 void (*_dmamem_unmap) __P((bus_dma_tag_t, caddr_t, size_t));
707 vm_offset_t (*_dmamem_mmap) __P((bus_dma_tag_t, bus_dma_segment_t *,
708 int, off_t, int, int));
709};
710
711#define bus_dmamap_create(t, s, n, m, b, f, p) \
712 (*(t)->_dmamap_create)((t), (s), (n), (m), (b), (f), (p))
713#define bus_dmamap_destroy(t, p) \
714 (*(t)->_dmamap_destroy)((t), (p))
715#define bus_dmamap_load(t, m, b, s, p, f) \
716 (*(t)->_dmamap_load)((t), (m), (b), (s), (p), (f))
717#define bus_dmamap_load_mbuf(t, m, b, f) \
718 (*(t)->_dmamap_load_mbuf)((t), (m), (b), (f))
719#define bus_dmamap_load_uio(t, m, u, f) \
720 (*(t)->_dmamap_load_uio)((t), (m), (u), (f))
721#define bus_dmamap_load_raw(t, m, sg, n, s, f) \
722 (*(t)->_dmamap_load_raw)((t), (m), (sg), (n), (s), (f))
723#define bus_dmamap_unload(t, p) \
724 (*(t)->_dmamap_unload)((t), (p))
725#define bus_dmamap_sync(t, p, o, l, ops) \
726 (void)((t)->_dmamap_sync ? \
727 (*(t)->_dmamap_sync)((t), (p), (o), (l), (ops)) : (void)0)
728
729#define bus_dmamem_alloc(t, s, a, b, sg, n, r, f) \
730 (*(t)->_dmamem_alloc)((t), (s), (a), (b), (sg), (n), (r), (f))
731#define bus_dmamem_free(t, sg, n) \
732 (*(t)->_dmamem_free)((t), (sg), (n))
733#define bus_dmamem_map(t, sg, n, s, k, f) \
734 (*(t)->_dmamem_map)((t), (sg), (n), (s), (k), (f))
735#define bus_dmamem_unmap(t, k, s) \
736 (*(t)->_dmamem_unmap)((t), (k), (s))
737#define bus_dmamem_mmap(t, sg, n, o, p, f) \
738 (*(t)->_dmamem_mmap)((t), (sg), (n), (o), (p), (f))
739
740/*
741 * bus_dmamap_t
742 *
743 * Describes a DMA mapping.
744 */
745struct macppc_bus_dmamap {
746 /*
747 * PRIVATE MEMBERS: not for use my machine-independent code.
748 */
749 bus_size_t _dm_size; /* largest DMA transfer mappable */
750 int _dm_segcnt; /* number of segs this map can map */
751 bus_size_t _dm_maxsegsz; /* largest possible segment */
752 bus_size_t _dm_boundary; /* don't cross this */
753 bus_addr_t _dm_bounce_thresh; /* bounce threshold; see tag */
754 int _dm_flags; /* misc. flags */
755
756 void *_dm_cookie; /* cookie for bus-specific functions */
757
758 /*
759 * PUBLIC MEMBERS: these are used by machine-independent code.
760 */
761 bus_size_t dm_mapsize; /* size of the mapping */
762 int dm_nsegs; /* # valid segments in mapping */
763 bus_dma_segment_t dm_segs[1]; /* segments; variable length */
764};
765
766#ifdef _MACPPC_BUS_DMA_PRIVATE
767int _bus_dmamap_create __P((bus_dma_tag_t, bus_size_t, int, bus_size_t,
768 bus_size_t, int, bus_dmamap_t *));
769void _bus_dmamap_destroy __P((bus_dma_tag_t, bus_dmamap_t));
770int _bus_dmamap_load __P((bus_dma_tag_t, bus_dmamap_t, void *,
771 bus_size_t, struct proc *, int));
772int _bus_dmamap_load_mbuf __P((bus_dma_tag_t, bus_dmamap_t,
773 struct mbuf *, int));
774int _bus_dmamap_load_uio __P((bus_dma_tag_t, bus_dmamap_t,
775 struct uio *, int));
776int _bus_dmamap_load_raw __P((bus_dma_tag_t, bus_dmamap_t,
777 bus_dma_segment_t *, int, bus_size_t, int));
778void _bus_dmamap_unload __P((bus_dma_tag_t, bus_dmamap_t));
779void _bus_dmamap_sync __P((bus_dma_tag_t, bus_dmamap_t, bus_addr_t,
780 bus_size_t, int));
781
782int _bus_dmamem_alloc __P((bus_dma_tag_t tag, bus_size_t size,
783 bus_size_t alignment, bus_size_t boundary,
784 bus_dma_segment_t *segs, int nsegs, int *rsegs, int flags));
785void _bus_dmamem_free __P((bus_dma_tag_t tag, bus_dma_segment_t *segs,
786 int nsegs));
787int _bus_dmamem_map __P((bus_dma_tag_t tag, bus_dma_segment_t *segs,
788 int nsegs, size_t size, caddr_t *kvap, int flags));
789void _bus_dmamem_unmap __P((bus_dma_tag_t tag, caddr_t kva,
790 size_t size));
791vm_offset_t _bus_dmamem_mmap __P((bus_dma_tag_t tag,
792 bus_dma_segment_t *segs,
793 int nsegs, off_t off, int prot, int flags));
794
795int _bus_dmamem_alloc_range __P((bus_dma_tag_t tag, bus_size_t size,
796 bus_size_t alignment, bus_size_t boundary,
797 bus_dma_segment_t *segs, int nsegs, int *rsegs, int flags,
798 vm_offset_t low, vm_offset_t high));
799
800#endif /* _MACPPC_BUS_DMA_PRIVATE */
801
802#endif /* _MACPPC_BUS_H_ */