1*fbae48b9Sperry /* $NetBSD: bus.h,v 1.8 2006/02/16 20:17:13 perry Exp $ */ 295d00ea7Snisimura 395d00ea7Snisimura /*- 495d00ea7Snisimura * Copyright (c) 1996, 1997, 1998 The NetBSD Foundation, Inc. 595d00ea7Snisimura * All rights reserved. 695d00ea7Snisimura * 795d00ea7Snisimura * This code is derived from software contributed to The NetBSD Foundation 895d00ea7Snisimura * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility, 995d00ea7Snisimura * NASA Ames Research Center. 1095d00ea7Snisimura * 1195d00ea7Snisimura * Redistribution and use in source and binary forms, with or without 1295d00ea7Snisimura * modification, are permitted provided that the following conditions 1395d00ea7Snisimura * are met: 1495d00ea7Snisimura * 1. Redistributions of source code must retain the above copyright 1595d00ea7Snisimura * notice, this list of conditions and the following disclaimer. 1695d00ea7Snisimura * 2. Redistributions in binary form must reproduce the above copyright 1795d00ea7Snisimura * notice, this list of conditions and the following disclaimer in the 1895d00ea7Snisimura * documentation and/or other materials provided with the distribution. 1995d00ea7Snisimura * 3. All advertising materials mentioning features or use of this software 2095d00ea7Snisimura * must display the following acknowledgement: 2195d00ea7Snisimura * This product includes software developed by the NetBSD 2295d00ea7Snisimura * Foundation, Inc. and its contributors. 2395d00ea7Snisimura * 4. Neither the name of The NetBSD Foundation nor the names of its 2495d00ea7Snisimura * contributors may be used to endorse or promote products derived 2595d00ea7Snisimura * from this software without specific prior written permission. 2695d00ea7Snisimura * 2795d00ea7Snisimura * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 2895d00ea7Snisimura * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 2995d00ea7Snisimura * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 3095d00ea7Snisimura * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 3195d00ea7Snisimura * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 3295d00ea7Snisimura * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 3395d00ea7Snisimura * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 3495d00ea7Snisimura * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 3595d00ea7Snisimura * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 3695d00ea7Snisimura * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 3795d00ea7Snisimura * POSSIBILITY OF SUCH DAMAGE. 3895d00ea7Snisimura */ 3995d00ea7Snisimura 4095d00ea7Snisimura /* 4195d00ea7Snisimura * Copyright (C) 1997 Scott Reynolds. All rights reserved. 4295d00ea7Snisimura * 4395d00ea7Snisimura * Redistribution and use in source and binary forms, with or without 4495d00ea7Snisimura * modification, are permitted provided that the following conditions 4595d00ea7Snisimura * are met: 4695d00ea7Snisimura * 1. Redistributions of source code must retain the above copyright 4795d00ea7Snisimura * notice, this list of conditions and the following disclaimer. 4895d00ea7Snisimura * 2. Redistributions in binary form must reproduce the above copyright 4995d00ea7Snisimura * notice, this list of conditions and the following disclaimer in the 5095d00ea7Snisimura * documentation and/or other materials provided with the distribution. 5195d00ea7Snisimura * 3. The name of the author may not be used to endorse or promote products 5295d00ea7Snisimura * derived from this software without specific prior written permission 5395d00ea7Snisimura * 5495d00ea7Snisimura * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 5595d00ea7Snisimura * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 5695d00ea7Snisimura * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 5795d00ea7Snisimura * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 5895d00ea7Snisimura * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 5995d00ea7Snisimura * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 6095d00ea7Snisimura * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 6195d00ea7Snisimura * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 6295d00ea7Snisimura * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 6395d00ea7Snisimura * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 6495d00ea7Snisimura */ 6595d00ea7Snisimura 6695d00ea7Snisimura #ifndef _MACHINE_BUS_H_ 6795d00ea7Snisimura #define _MACHINE_BUS_H_ 6895d00ea7Snisimura 6995d00ea7Snisimura /* 7095d00ea7Snisimura * Value for the luna68k bus space tag, not to be used directly by MI code. 7195d00ea7Snisimura */ 7295d00ea7Snisimura #define MACHINE_BUS_SPACE_MEM 0 /* space is mem space */ 7395d00ea7Snisimura 7495d00ea7Snisimura /* 7595d00ea7Snisimura * Bus address and size types 7695d00ea7Snisimura */ 7795d00ea7Snisimura typedef u_long bus_addr_t; 7895d00ea7Snisimura typedef u_long bus_size_t; 7995d00ea7Snisimura 8095d00ea7Snisimura /* 8195d00ea7Snisimura * Access methods for bus resources and address space. 8295d00ea7Snisimura */ 8395d00ea7Snisimura typedef int bus_space_tag_t; 8495d00ea7Snisimura typedef u_long bus_space_handle_t; 8595d00ea7Snisimura 8695d00ea7Snisimura /* 8795d00ea7Snisimura * int bus_space_map __P((bus_space_tag_t t, bus_addr_t addr, 8895d00ea7Snisimura * bus_size_t size, int flags, bus_space_handle_t *bshp)); 8995d00ea7Snisimura * 9095d00ea7Snisimura * Map a region of bus space. 9195d00ea7Snisimura */ 9295d00ea7Snisimura 9395d00ea7Snisimura #define BUS_SPACE_MAP_CACHEABLE 0x01 9495d00ea7Snisimura #define BUS_SPACE_MAP_LINEAR 0x02 958eb798e6Sdrochner #define BUS_SPACE_MAP_PREFETCHABLE 0x04 9695d00ea7Snisimura 9795d00ea7Snisimura int bus_space_map __P((bus_space_tag_t, bus_addr_t, bus_size_t, 9895d00ea7Snisimura int, bus_space_handle_t *)); 9995d00ea7Snisimura 10095d00ea7Snisimura /* 10195d00ea7Snisimura * void bus_space_unmap __P((bus_space_tag_t t, 10295d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t size)); 10395d00ea7Snisimura * 10495d00ea7Snisimura * Unmap a region of bus space. 10595d00ea7Snisimura */ 10695d00ea7Snisimura 10795d00ea7Snisimura void bus_space_unmap __P((bus_space_tag_t, bus_space_handle_t, bus_size_t)); 10895d00ea7Snisimura 10995d00ea7Snisimura /* 11095d00ea7Snisimura * int bus_space_subregion __P((bus_space_tag_t t, 11195d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, bus_size_t size, 11295d00ea7Snisimura * bus_space_handle_t *nbshp)); 11395d00ea7Snisimura * 11495d00ea7Snisimura * Get a new handle for a subregion of an already-mapped area of bus space. 11595d00ea7Snisimura */ 11695d00ea7Snisimura 11795d00ea7Snisimura int bus_space_subregion __P((bus_space_tag_t t, bus_space_handle_t bsh, 11895d00ea7Snisimura bus_size_t offset, bus_size_t size, bus_space_handle_t *nbshp)); 11995d00ea7Snisimura 12095d00ea7Snisimura /* 12195d00ea7Snisimura * int bus_space_alloc __P((bus_space_tag_t t, bus_addr_t, rstart, 12295d00ea7Snisimura * bus_addr_t rend, bus_size_t size, bus_size_t align, 12395d00ea7Snisimura * bus_size_t boundary, int flags, bus_addr_t *addrp, 12495d00ea7Snisimura * bus_space_handle_t *bshp)); 12595d00ea7Snisimura * 12695d00ea7Snisimura * Allocate a region of bus space. 12795d00ea7Snisimura */ 12895d00ea7Snisimura 12995d00ea7Snisimura int bus_space_alloc __P((bus_space_tag_t t, bus_addr_t rstart, 13095d00ea7Snisimura bus_addr_t rend, bus_size_t size, bus_size_t align, 13195d00ea7Snisimura bus_size_t boundary, int cacheable, bus_addr_t *addrp, 13295d00ea7Snisimura bus_space_handle_t *bshp)); 13395d00ea7Snisimura 13495d00ea7Snisimura /* 13595d00ea7Snisimura * int bus_space_free __P((bus_space_tag_t t, 13695d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t size)); 13795d00ea7Snisimura * 13895d00ea7Snisimura * Free a region of bus space. 13995d00ea7Snisimura */ 14095d00ea7Snisimura 14195d00ea7Snisimura void bus_space_free __P((bus_space_tag_t t, bus_space_handle_t bsh, 14295d00ea7Snisimura bus_size_t size)); 14395d00ea7Snisimura 14495d00ea7Snisimura /* 14595d00ea7Snisimura * u_intN_t bus_space_read_N __P((bus_space_tag_t tag, 14695d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset)); 14795d00ea7Snisimura * 14895d00ea7Snisimura * Read a 1, 2, 4, or 8 byte quantity from bus space 14995d00ea7Snisimura * described by tag/handle/offset. 15095d00ea7Snisimura */ 15195d00ea7Snisimura 15295d00ea7Snisimura #define bus_space_read_1(t, h, o) \ 153f28fd518Snisimura ((void) t, (*(volatile u_int8_t *)((h) + 4*(o)))) 15495d00ea7Snisimura 15595d00ea7Snisimura #define bus_space_read_2(t, h, o) \ 156f28fd518Snisimura ((void) t, (*(volatile u_int16_t *)((h) + 4*(o)))) 15795d00ea7Snisimura 15895d00ea7Snisimura #define bus_space_read_4(t, h, o) \ 159f28fd518Snisimura ((void) t, (*(volatile u_int32_t *)((h) + 4*(o)))) 16095d00ea7Snisimura 16195d00ea7Snisimura #if 0 /* Cause a link error for bus_space_read_8 */ 16295d00ea7Snisimura #define bus_space_read_8(t, h, o) !!! bus_space_read_8 unimplemented !!! 16395d00ea7Snisimura #endif 16495d00ea7Snisimura 16595d00ea7Snisimura /* 16695d00ea7Snisimura * void bus_space_read_multi_N __P((bus_space_tag_t tag, 16795d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, 16895d00ea7Snisimura * u_intN_t *addr, size_t count)); 16995d00ea7Snisimura * 17095d00ea7Snisimura * Read `count' 1, 2, 4, or 8 byte quantities from bus space 17195d00ea7Snisimura * described by tag/handle/offset and copy into buffer provided. 17295d00ea7Snisimura */ 17395d00ea7Snisimura 17495d00ea7Snisimura #define bus_space_read_multi_1(t, h, o, a, c) do { \ 17595d00ea7Snisimura (void) t; \ 1765f1c88d7Sperry __asm volatile (" \ 177d0e2aef0Schs movl %0,%%a0 ; \ 178d0e2aef0Schs movl %1,%%a1 ; \ 179d0e2aef0Schs movl %2,%%d0 ; \ 180d0e2aef0Schs 1: movb %%a0@,%%a1@+ ; \ 181d0e2aef0Schs subql #1,%%d0 ; \ 18295d00ea7Snisimura jne 1b" : \ 18395d00ea7Snisimura : \ 18495d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 18595d00ea7Snisimura "a0","a1","d0"); \ 18695d00ea7Snisimura } while (0) 18795d00ea7Snisimura 18895d00ea7Snisimura #define bus_space_read_multi_2(t, h, o, a, c) do { \ 18995d00ea7Snisimura (void) t; \ 1905f1c88d7Sperry __asm volatile (" \ 191d0e2aef0Schs movl %0,%%a0 ; \ 192d0e2aef0Schs movl %1,%%a1 ; \ 193d0e2aef0Schs movl %2,%%d0 ; \ 194d0e2aef0Schs 1: movw %%a0@,%%a1@+ ; \ 195d0e2aef0Schs subql #1,%%d0 ; \ 19695d00ea7Snisimura jne 1b" : \ 19795d00ea7Snisimura : \ 19895d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 19995d00ea7Snisimura "a0","a1","d0"); \ 20095d00ea7Snisimura } while (0) 20195d00ea7Snisimura 20295d00ea7Snisimura #define bus_space_read_multi_4(t, h, o, a, c) do { \ 20395d00ea7Snisimura (void) t; \ 2045f1c88d7Sperry __asm volatile (" \ 205d0e2aef0Schs movl %0,%%a0 ; \ 206d0e2aef0Schs movl %1,%%a1 ; \ 207d0e2aef0Schs movl %2,%%d0 ; \ 208d0e2aef0Schs 1: movl %%a0@,%%a1@+ ; \ 209d0e2aef0Schs subql #1,%%d0 ; \ 21095d00ea7Snisimura jne 1b" : \ 21195d00ea7Snisimura : \ 21295d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 21395d00ea7Snisimura "a0","a1","d0"); \ 21495d00ea7Snisimura } while (0) 21595d00ea7Snisimura 21695d00ea7Snisimura #if 0 /* Cause a link error for bus_space_read_multi_8 */ 21795d00ea7Snisimura #define bus_space_read_multi_8 !!! bus_space_read_multi_8 unimplemented !!! 21895d00ea7Snisimura #endif 21995d00ea7Snisimura 22095d00ea7Snisimura /* 22195d00ea7Snisimura * void bus_space_read_region_N __P((bus_space_tag_t tag, 22295d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, 22395d00ea7Snisimura * u_intN_t *addr, size_t count)); 22495d00ea7Snisimura * 22595d00ea7Snisimura * Read `count' 1, 2, 4, or 8 byte quantities from bus space 22695d00ea7Snisimura * described by tag/handle and starting at `offset' and copy into 22795d00ea7Snisimura * buffer provided. 22895d00ea7Snisimura */ 22995d00ea7Snisimura 23095d00ea7Snisimura #define bus_space_read_region_1(t, h, o, a, c) do { \ 23195d00ea7Snisimura (void) t; \ 2325f1c88d7Sperry __asm volatile (" \ 233d0e2aef0Schs movl %0,%%a0 ; \ 234d0e2aef0Schs movl %1,%%a1 ; \ 235d0e2aef0Schs movl %2,%%d0 ; \ 236d0e2aef0Schs 1: movb %%a0@+,%%a1@+ ; \ 237d0e2aef0Schs subql #1,%%d0 ; \ 23895d00ea7Snisimura jne 1b" : \ 23995d00ea7Snisimura : \ 24095d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 24195d00ea7Snisimura "a0","a1","d0"); \ 24295d00ea7Snisimura } while (0) 24395d00ea7Snisimura 24495d00ea7Snisimura #define bus_space_read_region_2(t, h, o, a, c) do { \ 24595d00ea7Snisimura (void) t; \ 2465f1c88d7Sperry __asm volatile (" \ 247d0e2aef0Schs movl %0,%%a0 ; \ 248d0e2aef0Schs movl %1,%%a1 ; \ 249d0e2aef0Schs movl %2,%%d0 ; \ 250d0e2aef0Schs 1: movw %%a0@+,%%a1@+ ; \ 251d0e2aef0Schs subql #1,%%d0 ; \ 25295d00ea7Snisimura jne 1b" : \ 25395d00ea7Snisimura : \ 25495d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 25595d00ea7Snisimura "a0","a1","d0"); \ 25695d00ea7Snisimura } while (0) 25795d00ea7Snisimura 25895d00ea7Snisimura #define bus_space_read_region_4(t, h, o, a, c) do { \ 25995d00ea7Snisimura (void) t; \ 2605f1c88d7Sperry __asm volatile (" \ 261d0e2aef0Schs movl %0,%%a0 ; \ 262d0e2aef0Schs movl %1,%%a1 ; \ 263d0e2aef0Schs movl %2,%%d0 ; \ 264d0e2aef0Schs 1: movl %%a0@+,%%a1@+ ; \ 265d0e2aef0Schs subql #1,%%d0 ; \ 26695d00ea7Snisimura jne 1b" : \ 26795d00ea7Snisimura : \ 26895d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 26995d00ea7Snisimura "a0","a1","d0"); \ 27095d00ea7Snisimura } while (0) 27195d00ea7Snisimura 27295d00ea7Snisimura #if 0 /* Cause a link error for bus_space_read_region_8 */ 27395d00ea7Snisimura #define bus_space_read_region_8 !!! bus_space_read_region_8 unimplemented !!! 27495d00ea7Snisimura #endif 27595d00ea7Snisimura 27695d00ea7Snisimura /* 27795d00ea7Snisimura * void bus_space_write_N __P((bus_space_tag_t tag, 27895d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, 27995d00ea7Snisimura * u_intN_t value)); 28095d00ea7Snisimura * 28195d00ea7Snisimura * Write the 1, 2, 4, or 8 byte value `value' to bus space 28295d00ea7Snisimura * described by tag/handle/offset. 28395d00ea7Snisimura */ 28495d00ea7Snisimura 28595d00ea7Snisimura #define bus_space_write_1(t, h, o, v) \ 286f28fd518Snisimura ((void) t, ((void)(*(volatile u_int8_t *)((h) + 4*(o)) = (v)))) 28795d00ea7Snisimura 28895d00ea7Snisimura #define bus_space_write_2(t, h, o, v) \ 289f28fd518Snisimura ((void) t, ((void)(*(volatile u_int16_t *)((h) + 4*(o)) = (v)))) 29095d00ea7Snisimura 29195d00ea7Snisimura #define bus_space_write_4(t, h, o, v) \ 292f28fd518Snisimura ((void) t, ((void)(*(volatile u_int32_t *)((h) + 4*(o)) = (v)))) 29395d00ea7Snisimura 29495d00ea7Snisimura #if 0 /* Cause a link error for bus_space_write_8 */ 29595d00ea7Snisimura #define bus_space_write_8 !!! bus_space_write_8 not implemented !!! 29695d00ea7Snisimura #endif 29795d00ea7Snisimura 29895d00ea7Snisimura /* 29995d00ea7Snisimura * void bus_space_write_multi_N __P((bus_space_tag_t tag, 30095d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, 30195d00ea7Snisimura * const u_intN_t *addr, size_t count)); 30295d00ea7Snisimura * 30395d00ea7Snisimura * Write `count' 1, 2, 4, or 8 byte quantities from the buffer 30495d00ea7Snisimura * provided to bus space described by tag/handle/offset. 30595d00ea7Snisimura */ 30695d00ea7Snisimura 30795d00ea7Snisimura #define bus_space_write_multi_1(t, h, o, a, c) do { \ 30895d00ea7Snisimura (void) t; \ 3095f1c88d7Sperry __asm volatile (" \ 310d0e2aef0Schs movl %0,%%a0 ; \ 311d0e2aef0Schs movl %1,%%a1 ; \ 312d0e2aef0Schs movl %2,%%d0 ; \ 313ae2b6b31Stsutsui 1: movb %%a1@+,%%a0@ ; \ 314d0e2aef0Schs subql #1,%%d0 ; \ 31595d00ea7Snisimura jne 1b" : \ 31695d00ea7Snisimura : \ 31795d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 31895d00ea7Snisimura "a0","a1","d0"); \ 31995d00ea7Snisimura } while (0) 32095d00ea7Snisimura 32195d00ea7Snisimura #define bus_space_write_multi_2(t, h, o, a, c) do { \ 32295d00ea7Snisimura (void) t; \ 3235f1c88d7Sperry __asm volatile (" \ 324d0e2aef0Schs movl %0,%%a0 ; \ 325d0e2aef0Schs movl %1,%%a1 ; \ 326d0e2aef0Schs movl %2,%%d0 ; \ 327ae2b6b31Stsutsui 1: movw %%a1@+,%%a0@ ; \ 328d0e2aef0Schs subql #1,%%d0 ; \ 32995d00ea7Snisimura jne 1b" : \ 33095d00ea7Snisimura : \ 33195d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 33295d00ea7Snisimura "a0","a1","d0"); \ 33395d00ea7Snisimura } while (0) 33495d00ea7Snisimura 33595d00ea7Snisimura #define bus_space_write_multi_4(t, h, o, a, c) do { \ 33695d00ea7Snisimura (void) t; \ 3375f1c88d7Sperry __asm volatile (" \ 338d0e2aef0Schs movl %0,%%a0 ; \ 339d0e2aef0Schs movl %1,%%a1 ; \ 340d0e2aef0Schs movl %2,%%d0 ; \ 341ae2b6b31Stsutsui 1: movl %%a1@+,%%a0@ ; \ 342d0e2aef0Schs subql #1,%%d0 ; \ 34395d00ea7Snisimura jne 1b" : \ 34495d00ea7Snisimura : \ 34595d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 34695d00ea7Snisimura "a0","a1","d0"); \ 34795d00ea7Snisimura } while (0) 34895d00ea7Snisimura 34995d00ea7Snisimura #if 0 /* Cause a link error for bus_space_write_8 */ 35095d00ea7Snisimura #define bus_space_write_multi_8(t, h, o, a, c) \ 35195d00ea7Snisimura !!! bus_space_write_multi_8 unimplimented !!! 35295d00ea7Snisimura #endif 35395d00ea7Snisimura 35495d00ea7Snisimura /* 35595d00ea7Snisimura * void bus_space_write_region_N __P((bus_space_tag_t tag, 35695d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, 35795d00ea7Snisimura * const u_intN_t *addr, size_t count)); 35895d00ea7Snisimura * 35995d00ea7Snisimura * Write `count' 1, 2, 4, or 8 byte quantities from the buffer provided 36095d00ea7Snisimura * to bus space described by tag/handle starting at `offset'. 36195d00ea7Snisimura */ 36295d00ea7Snisimura 36395d00ea7Snisimura #define bus_space_write_region_1(t, h, o, a, c) do { \ 36495d00ea7Snisimura (void) t; \ 3655f1c88d7Sperry __asm volatile (" \ 366d0e2aef0Schs movl %0,%%a0 ; \ 367d0e2aef0Schs movl %1,%%a1 ; \ 368d0e2aef0Schs movl %2,%%d0 ; \ 369ae2b6b31Stsutsui 1: movb %%a1@+,%%a0@+ ; \ 370d0e2aef0Schs subql #1,%%d0 ; \ 37195d00ea7Snisimura jne 1b" : \ 37295d00ea7Snisimura : \ 37395d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 37495d00ea7Snisimura "a0","a1","d0"); \ 37595d00ea7Snisimura } while (0) 37695d00ea7Snisimura 37795d00ea7Snisimura #define bus_space_write_region_2(t, h, o, a, c) do { \ 37895d00ea7Snisimura (void) t; \ 3795f1c88d7Sperry __asm volatile (" \ 380d0e2aef0Schs movl %0,%%a0 ; \ 381d0e2aef0Schs movl %1,%%a1 ; \ 382d0e2aef0Schs movl %2,%%d0 ; \ 383ae2b6b31Stsutsui 1: movw %%a1@+,%%a0@+ ; \ 384d0e2aef0Schs subql #1,%%d0 ; \ 38595d00ea7Snisimura jne 1b" : \ 38695d00ea7Snisimura : \ 38795d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 38895d00ea7Snisimura "a0","a1","d0"); \ 38995d00ea7Snisimura } while (0) 39095d00ea7Snisimura 39195d00ea7Snisimura #define bus_space_write_region_4(t, h, o, a, c) do { \ 39295d00ea7Snisimura (void) t; \ 3935f1c88d7Sperry __asm volatile (" \ 394d0e2aef0Schs movl %0,%%a0 ; \ 395d0e2aef0Schs movl %1,%%a1 ; \ 396d0e2aef0Schs movl %2,%%d0 ; \ 397ae2b6b31Stsutsui 1: movl %%a1@+,%%a0@+ ; \ 398d0e2aef0Schs subql #1,%%d0 ; \ 39995d00ea7Snisimura jne 1b" : \ 40095d00ea7Snisimura : \ 40195d00ea7Snisimura "r" ((h) + (o)), "g" (a), "g" ((size_t)(c)) : \ 40295d00ea7Snisimura "a0","a1","d0"); \ 40395d00ea7Snisimura } while (0) 40495d00ea7Snisimura 40595d00ea7Snisimura #if 0 /* Cause a link error for bus_space_write_region_8 */ 40695d00ea7Snisimura #define bus_space_write_region_8 \ 40795d00ea7Snisimura !!! bus_space_write_region_8 unimplemented !!! 40895d00ea7Snisimura #endif 40995d00ea7Snisimura 41095d00ea7Snisimura /* 41195d00ea7Snisimura * void bus_space_set_multi_N __P((bus_space_tag_t tag, 41295d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, u_intN_t val, 41395d00ea7Snisimura * size_t count)); 41495d00ea7Snisimura * 41595d00ea7Snisimura * Write the 1, 2, 4, or 8 byte value `val' to bus space described 41695d00ea7Snisimura * by tag/handle/offset `count' times. 41795d00ea7Snisimura */ 41895d00ea7Snisimura 41995d00ea7Snisimura #define bus_space_set_multi_1(t, h, o, val, c) do { \ 42095d00ea7Snisimura (void) t; \ 4215f1c88d7Sperry __asm volatile (" \ 422d0e2aef0Schs movl %0,%%a0 ; \ 423d0e2aef0Schs movl %1,%%d1 ; \ 424d0e2aef0Schs movl %2,%%d0 ; \ 425d0e2aef0Schs 1: movb %%d1,%%a0@ ; \ 426d0e2aef0Schs subql #1,%%d0 ; \ 42795d00ea7Snisimura jne 1b" : \ 42895d00ea7Snisimura : \ 42995d00ea7Snisimura "r" ((h)+(o)), "g" ((u_long)val), \ 43095d00ea7Snisimura "g" ((size_t)(c)) : \ 43195d00ea7Snisimura "a0","d0","d1"); \ 43295d00ea7Snisimura } while (0) 43395d00ea7Snisimura 43495d00ea7Snisimura #define bus_space_set_multi_2(t, h, o, val, c) do { \ 43595d00ea7Snisimura (void) t; \ 4365f1c88d7Sperry __asm volatile (" \ 437d0e2aef0Schs movl %0,%%a0 ; \ 438d0e2aef0Schs movl %1,%%d1 ; \ 439d0e2aef0Schs movl %2,%%d0 ; \ 440d0e2aef0Schs 1: movw %%d1,%%a0@ ; \ 441d0e2aef0Schs subql #1,%%d0 ; \ 44295d00ea7Snisimura jne 1b" : \ 44395d00ea7Snisimura : \ 44495d00ea7Snisimura "r" ((h)+(o)), "g" ((u_long)val), \ 44595d00ea7Snisimura "g" ((size_t)(c)) : \ 44695d00ea7Snisimura "a0","d0","d1"); \ 44795d00ea7Snisimura } while (0) 44895d00ea7Snisimura 44995d00ea7Snisimura #define bus_space_set_multi_4(t, h, o, val, c) do { \ 45095d00ea7Snisimura (void) t; \ 4515f1c88d7Sperry __asm volatile (" \ 452d0e2aef0Schs movl %0,%%a0 ; \ 453d0e2aef0Schs movl %1,%%d1 ; \ 454d0e2aef0Schs movl %2,%%d0 ; \ 455d0e2aef0Schs 1: movl %%d1,%%a0@ ; \ 456d0e2aef0Schs subql #1,%%d0 ; \ 45795d00ea7Snisimura jne 1b" : \ 45895d00ea7Snisimura : \ 45995d00ea7Snisimura "r" ((h)+(o)), "g" ((u_long)val), \ 46095d00ea7Snisimura "g" ((size_t)(c)) : \ 46195d00ea7Snisimura "a0","d0","d1"); \ 46295d00ea7Snisimura } while (0) 46395d00ea7Snisimura 46495d00ea7Snisimura #if 0 /* Cause a link error for bus_space_set_multi_8 */ 46595d00ea7Snisimura #define bus_space_set_multi_8 \ 46695d00ea7Snisimura !!! bus_space_set_multi_8 unimplemented !!! 46795d00ea7Snisimura #endif 46895d00ea7Snisimura 46995d00ea7Snisimura /* 47095d00ea7Snisimura * void bus_space_set_region_N __P((bus_space_tag_t tag, 47195d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, u_intN_t val, 47295d00ea7Snisimura * size_t count)); 47395d00ea7Snisimura * 47495d00ea7Snisimura * Write `count' 1, 2, 4, or 8 byte value `val' to bus space described 47595d00ea7Snisimura * by tag/handle starting at `offset'. 47695d00ea7Snisimura */ 47795d00ea7Snisimura 47895d00ea7Snisimura #define bus_space_set_region_1(t, h, o, val, c) do { \ 47995d00ea7Snisimura (void) t; \ 4805f1c88d7Sperry __asm volatile (" \ 481d0e2aef0Schs movl %0,%%a0 ; \ 482d0e2aef0Schs movl %1,%%d1 ; \ 483d0e2aef0Schs movl %2,%%d0 ; \ 484d0e2aef0Schs 1: movb %%d1,%%a0@+ ; \ 485d0e2aef0Schs subql #1,%%d0 ; \ 48695d00ea7Snisimura jne 1b" : \ 48795d00ea7Snisimura : \ 48895d00ea7Snisimura "r" ((h)+(o)), "g" ((u_long)val), \ 48995d00ea7Snisimura "g" ((size_t)(c)) : \ 49095d00ea7Snisimura "a0","d0","d1"); \ 49195d00ea7Snisimura } while (0) 49295d00ea7Snisimura 49395d00ea7Snisimura #define bus_space_set_region_2(t, h, o, val, c) do { \ 49495d00ea7Snisimura (void) t; \ 4955f1c88d7Sperry __asm volatile (" \ 496d0e2aef0Schs movl %0,%%a0 ; \ 497d0e2aef0Schs movl %1,%%d1 ; \ 498d0e2aef0Schs movl %2,%%d0 ; \ 499d0e2aef0Schs 1: movw %%d1,%%a0@+ ; \ 500d0e2aef0Schs subql #1,%%d0 ; \ 50195d00ea7Snisimura jne 1b" : \ 50295d00ea7Snisimura : \ 50395d00ea7Snisimura "r" ((h)+(o)), "g" ((u_long)val), \ 50495d00ea7Snisimura "g" ((size_t)(c)) : \ 50595d00ea7Snisimura "a0","d0","d1"); \ 50695d00ea7Snisimura } while (0) 50795d00ea7Snisimura 50895d00ea7Snisimura #define bus_space_set_region_4(t, h, o, val, c) do { \ 50995d00ea7Snisimura (void) t; \ 5105f1c88d7Sperry __asm volatile (" \ 511d0e2aef0Schs movl %0,%%a0 ; \ 512d0e2aef0Schs movl %1,%%d1 ; \ 513d0e2aef0Schs movl %2,%%d0 ; \ 514d0e2aef0Schs 1: movl %%d1,%%a0@+ ; \ 515d0e2aef0Schs subql #1,%%d0 ; \ 51695d00ea7Snisimura jne 1b" : \ 51795d00ea7Snisimura : \ 51895d00ea7Snisimura "r" ((h)+(o)), "g" ((u_long)val), \ 51995d00ea7Snisimura "g" ((size_t)(c)) : \ 52095d00ea7Snisimura "a0","d0","d1"); \ 52195d00ea7Snisimura } while (0) 52295d00ea7Snisimura 52395d00ea7Snisimura #if 0 /* Cause a link error for bus_space_set_region_8 */ 52495d00ea7Snisimura #define bus_space_set_region_8 \ 52595d00ea7Snisimura !!! bus_space_set_region_8 unimplemented !!! 52695d00ea7Snisimura #endif 52795d00ea7Snisimura 52895d00ea7Snisimura /* 52995d00ea7Snisimura * void bus_space_copy_N __P((bus_space_tag_t tag, 53095d00ea7Snisimura * bus_space_handle_t bsh1, bus_size_t off1, 53195d00ea7Snisimura * bus_space_handle_t bsh2, bus_size_t off2, 53295d00ea7Snisimura * size_t count)); 53395d00ea7Snisimura * 53495d00ea7Snisimura * Copy `count' 1, 2, 4, or 8 byte values from bus space starting 53595d00ea7Snisimura * at tag/bsh1/off1 to bus space starting at tag/bsh2/off2. 53695d00ea7Snisimura */ 53795d00ea7Snisimura 53895d00ea7Snisimura #define __MACHINE_copy_region_N(BYTES) \ 539*fbae48b9Sperry static __inline void __CONCAT(bus_space_copy_region_,BYTES) \ 54095d00ea7Snisimura __P((bus_space_tag_t, \ 54195d00ea7Snisimura bus_space_handle_t bsh1, bus_size_t off1, \ 54295d00ea7Snisimura bus_space_handle_t bsh2, bus_size_t off2, \ 54395d00ea7Snisimura bus_size_t count)); \ 54495d00ea7Snisimura \ 545*fbae48b9Sperry static __inline void \ 54695d00ea7Snisimura __CONCAT(bus_space_copy_region_,BYTES)(t, h1, o1, h2, o2, c) \ 54795d00ea7Snisimura bus_space_tag_t t; \ 54895d00ea7Snisimura bus_space_handle_t h1, h2; \ 54995d00ea7Snisimura bus_size_t o1, o2, c; \ 55095d00ea7Snisimura { \ 55195d00ea7Snisimura bus_size_t o; \ 55295d00ea7Snisimura \ 55395d00ea7Snisimura if ((h1 + o1) >= (h2 + o2)) { \ 55495d00ea7Snisimura /* src after dest: copy forward */ \ 55595d00ea7Snisimura for (o = 0; c != 0; c--, o += BYTES) \ 55695d00ea7Snisimura __CONCAT(bus_space_write_,BYTES)(t, h2, o2 + o, \ 55795d00ea7Snisimura __CONCAT(bus_space_read_,BYTES)(t, h1, o1 + o)); \ 55895d00ea7Snisimura } else { \ 55995d00ea7Snisimura /* dest after src: copy backwards */ \ 56095d00ea7Snisimura for (o = (c - 1) * BYTES; c != 0; c--, o -= BYTES) \ 56195d00ea7Snisimura __CONCAT(bus_space_write_,BYTES)(t, h2, o2 + o, \ 56295d00ea7Snisimura __CONCAT(bus_space_read_,BYTES)(t, h1, o1 + o)); \ 56395d00ea7Snisimura } \ 56495d00ea7Snisimura } 56595d00ea7Snisimura __MACHINE_copy_region_N(1) 56695d00ea7Snisimura __MACHINE_copy_region_N(2) 56795d00ea7Snisimura __MACHINE_copy_region_N(4) 56895d00ea7Snisimura #if 0 /* Cause a link error for bus_space_copy_8 */ 56995d00ea7Snisimura #define bus_space_copy_8 \ 57095d00ea7Snisimura !!! bus_space_copy_8 unimplemented !!! 57195d00ea7Snisimura #endif 57295d00ea7Snisimura 57395d00ea7Snisimura #undef __MACHINE_copy_region_N 57495d00ea7Snisimura 57595d00ea7Snisimura /* 57695d00ea7Snisimura * Bus read/write barrier methods. 57795d00ea7Snisimura * 57895d00ea7Snisimura * void bus_space_barrier __P((bus_space_tag_t tag, 57995d00ea7Snisimura * bus_space_handle_t bsh, bus_size_t offset, 58095d00ea7Snisimura * bus_size_t len, int flags)); 58195d00ea7Snisimura * 58295d00ea7Snisimura * Note: the 680x0 does not currently require barriers, but we must 58395d00ea7Snisimura * provide the flags to MI code. 58495d00ea7Snisimura */ 58595d00ea7Snisimura #define bus_space_barrier(t, h, o, l, f) \ 58695d00ea7Snisimura ((void)((void)(t), (void)(h), (void)(o), (void)(l), (void)(f))) 58795d00ea7Snisimura #define BUS_SPACE_BARRIER_READ 0x01 /* force read barrier */ 58895d00ea7Snisimura #define BUS_SPACE_BARRIER_WRITE 0x02 /* force write barrier */ 58995d00ea7Snisimura 59095d00ea7Snisimura #define BUS_SPACE_ALIGNED_POINTER(p, t) ALIGNED_POINTER(p, t) 59195d00ea7Snisimura 59295d00ea7Snisimura #endif /* _MACHINE_BUS_H_ */ 593