1 /* $NetBSD: bus.h,v 1.8 1997/10/10 05:54:48 scottr Exp $ */ 2 3 /*- 4 * Copyright (c) 1996, 1997 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility, 9 * NASA Ames Research Center. 10 * 11 * Redistribution and use in source and binary forms, with or without 12 * modification, are permitted provided that the following conditions 13 * are met: 14 * 1. Redistributions of source code must retain the above copyright 15 * notice, this list of conditions and the following disclaimer. 16 * 2. Redistributions in binary form must reproduce the above copyright 17 * notice, this list of conditions and the following disclaimer in the 18 * documentation and/or other materials provided with the distribution. 19 * 3. All advertising materials mentioning features or use of this software 20 * must display the following acknowledgement: 21 * This product includes software developed by the NetBSD 22 * Foundation, Inc. and its contributors. 23 * 4. Neither the name of The NetBSD Foundation nor the names of its 24 * contributors may be used to endorse or promote products derived 25 * from this software without specific prior written permission. 26 * 27 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 28 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 29 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 30 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 31 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 32 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 33 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 34 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 35 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 36 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 37 * POSSIBILITY OF SUCH DAMAGE. 38 */ 39 40 /* 41 * Copyright (C) 1997 Scott Reynolds. All rights reserved. 42 * 43 * Redistribution and use in source and binary forms, with or without 44 * modification, are permitted provided that the following conditions 45 * are met: 46 * 1. Redistributions of source code must retain the above copyright 47 * notice, this list of conditions and the following disclaimer. 48 * 2. Redistributions in binary form must reproduce the above copyright 49 * notice, this list of conditions and the following disclaimer in the 50 * documentation and/or other materials provided with the distribution. 51 * 3. The name of the author may not be used to endorse or promote products 52 * derived from this software without specific prior written permission 53 * 54 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR 55 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES 56 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. 57 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 58 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 59 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 60 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 61 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 62 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 63 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 64 */ 65 66 #ifndef _MAC68K_BUS_H_ 67 #define _MAC68K_BUS_H_ 68 69 /* 70 * Value for the mac68k bus space tag, not to be used directly by MI code. 71 */ 72 #define MAC68K_BUS_SPACE_MEM 0 /* space is mem space */ 73 74 /* 75 * Bus address and size types 76 */ 77 typedef u_long bus_addr_t; 78 typedef u_long bus_size_t; 79 80 /* 81 * Access methods for bus resources and address space. 82 */ 83 typedef int bus_space_tag_t; 84 typedef u_long bus_space_handle_t; 85 86 int bus_space_map __P((bus_space_tag_t, bus_addr_t, bus_size_t, 87 int, bus_space_handle_t *)); 88 void bus_space_unmap __P((bus_space_tag_t, bus_space_handle_t, 89 bus_size_t)); 90 int bus_space_subregion __P((bus_space_tag_t t, bus_space_handle_t bsh, 91 bus_size_t offset, bus_size_t size, bus_space_handle_t *nbshp)); 92 93 int bus_space_alloc __P((bus_space_tag_t t, bus_addr_t rstart, 94 bus_addr_t rend, bus_size_t size, bus_size_t align, 95 bus_size_t boundary, int cacheable, bus_addr_t *addrp, 96 bus_space_handle_t *bshp)); 97 void bus_space_free __P((bus_space_tag_t t, bus_space_handle_t bsh, 98 bus_size_t size)); 99 100 /* 101 * u_intN_t bus_space_read_N __P((bus_space_tag_t tag, 102 * bus_space_handle_t bsh, bus_size_t offset)); 103 * 104 * Read a 1, 2, 4, or 8 byte quantity from bus space 105 * described by tag/handle/offset. 106 */ 107 108 #define bus_space_read_1(t, h, o) \ 109 ((void) t, (*(volatile u_int8_t *)((h) + (o)))) 110 111 #define bus_space_read_2(t, h, o) \ 112 ((void) t, (*(volatile u_int16_t *)((h) + (o)))) 113 114 #define bus_space_read_4(t, h, o) \ 115 ((void) t, (*(volatile u_int32_t *)((h) + (o)))) 116 117 #if 0 /* Cause a link error for bus_space_read_8 */ 118 #define bus_space_read_8(t, h, o) !!! bus_space_read_8 unimplemented !!! 119 #endif 120 121 /* 122 * void bus_space_read_multi_N __P((bus_space_tag_t tag, 123 * bus_space_handle_t bsh, bus_size_t offset, 124 * u_intN_t *addr, size_t count)); 125 * 126 * Read `count' 1, 2, 4, or 8 byte quantities from bus space 127 * described by tag/handle/offset and copy into buffer provided. 128 */ 129 130 #define bus_space_read_multi_1(t, h, o, a, c) do { \ 131 (void) t; \ 132 __asm __volatile (" \ 133 movl %0,a0 ; \ 134 movl %1,a1 ; \ 135 movl %2,d0 ; \ 136 1: movb a0@,a1@+ ; \ 137 subql #1,d0 ; \ 138 jne 1b" : \ 139 : \ 140 "r" ((h) + (o)), "g" (a), "g" (c) : \ 141 "a0","a1","d0"); \ 142 } while (0); 143 144 #define bus_space_read_multi_2(t, h, o, a, c) do { \ 145 (void) t; \ 146 __asm __volatile (" \ 147 movl %0,a0 ; \ 148 movl %1,a1 ; \ 149 movl %2,d0 ; \ 150 1: movw a0@,a1@+ ; \ 151 subql #1,d0 ; \ 152 jne 1b" : \ 153 : \ 154 "r" ((h) + (o)), "g" (a), "g" (c) : \ 155 "a0","a1","d0"); \ 156 } while (0); 157 158 #define bus_space_read_multi_4(t, h, o, a, c) do { \ 159 (void) t; \ 160 __asm __volatile (" \ 161 movl %0,a0 ; \ 162 movl %1,a1 ; \ 163 movl %2,d0 ; \ 164 1: movl a0@,a1@+ ; \ 165 subql #1,d0 ; \ 166 jne 1b" : \ 167 : \ 168 "r" ((h) + (o)), "g" (a), "g" (c) : \ 169 "a0","a1","d0"); \ 170 } while (0); 171 172 #if 0 /* Cause a link error for bus_space_read_multi_8 */ 173 #define bus_space_read_multi_8 !!! bus_space_read_multi_8 unimplemented !!! 174 #endif 175 176 /* 177 * void bus_space_read_region_N __P((bus_space_tag_t tag, 178 * bus_space_handle_t bsh, bus_size_t offset, 179 * u_intN_t *addr, size_t count)); 180 * 181 * Read `count' 1, 2, 4, or 8 byte quantities from bus space 182 * described by tag/handle and starting at `offset' and copy into 183 * buffer provided. 184 */ 185 186 #define bus_space_read_region_1(t, h, o, a, c) do { \ 187 (void) t; \ 188 __asm __volatile (" \ 189 movl %0,a0 ; \ 190 movl %1,a1 ; \ 191 movl %2,d0 ; \ 192 1: movb a0@+,a1@+ ; \ 193 subql #1,d0 ; \ 194 jne 1b" : \ 195 : \ 196 "r" ((h) + (o)), "g" (a), "g" (c) : \ 197 "a0","a1","d0"); \ 198 } while (0); 199 200 #define bus_space_read_region_2(t, h, o, a, c) do { \ 201 (void) t; \ 202 __asm __volatile (" \ 203 movl %0,a0 ; \ 204 movl %1,a1 ; \ 205 movl %2,d0 ; \ 206 1: movw a0@+,a1@+ ; \ 207 subql #1,d0 ; \ 208 jne 1b" : \ 209 : \ 210 "r" ((h) + (o)), "g" (a), "g" (c) : \ 211 "a0","a1","d0"); \ 212 } while (0); 213 214 #define bus_space_read_region_4(t, h, o, a, c) do { \ 215 (void) t; \ 216 __asm __volatile (" \ 217 movl %0,a0 ; \ 218 movl %1,a1 ; \ 219 movl %2,d0 ; \ 220 1: movl a0@+,a1@+ ; \ 221 subql #1,d0 ; \ 222 jne 1b" : \ 223 : \ 224 "r" ((h) + (o)), "g" (a), "g" (c) : \ 225 "a0","a1","d0"); \ 226 } while (0); 227 228 #if 0 /* Cause a link error for bus_space_read_region_8 */ 229 #define bus_space_read_region_8 !!! bus_space_read_region_8 unimplemented !!! 230 #endif 231 232 /* 233 * void bus_space_write_N __P((bus_space_tag_t tag, 234 * bus_space_handle_t bsh, bus_size_t offset, 235 * u_intN_t value)); 236 * 237 * Write the 1, 2, 4, or 8 byte value `value' to bus space 238 * described by tag/handle/offset. 239 */ 240 241 #define bus_space_write_1(t, h, o, v) \ 242 ((void) t, ((void)(*(volatile u_int8_t *)((h) + (o)) = (v)))) 243 244 #define bus_space_write_2(t, h, o, v) \ 245 ((void) t, ((void)(*(volatile u_int16_t *)((h) + (o)) = (v)))) 246 247 #define bus_space_write_4(t, h, o, v) \ 248 ((void) t, ((void)(*(volatile u_int32_t *)((h) + (o)) = (v)))) 249 250 #if 0 /* Cause a link error for bus_space_write_8 */ 251 #define bus_space_write_8 !!! bus_space_write_8 not implemented !!! 252 #endif 253 254 /* 255 * void bus_space_write_multi_N __P((bus_space_tag_t tag, 256 * bus_space_handle_t bsh, bus_size_t offset, 257 * const u_intN_t *addr, size_t count)); 258 * 259 * Write `count' 1, 2, 4, or 8 byte quantities from the buffer 260 * provided to bus space described by tag/handle/offset. 261 */ 262 263 #define bus_space_write_multi_1(t, h, o, a, c) do { \ 264 (void) t; \ 265 __asm __volatile (" \ 266 movl %0,a0 ; \ 267 movl %1,a1 ; \ 268 movl %2,d0 ; \ 269 1: movb a1@+,a0@ ; \ 270 subql #1,d0 ; \ 271 jne 1b" : \ 272 : \ 273 "r" ((h) + (o)), "g" (a), "g" (c) : \ 274 "a0","a1","d0"); \ 275 } while (0); 276 277 #define bus_space_write_multi_2(t, h, o, a, c) do { \ 278 (void) t; \ 279 __asm __volatile (" \ 280 movl %0,a0 ; \ 281 movl %1,a1 ; \ 282 movl %2,d0 ; \ 283 1: movw a1@+,a0@ ; \ 284 subql #1,d0 ; \ 285 jne 1b" : \ 286 : \ 287 "r" ((h) + (o)), "g" (a), "g" (c) : \ 288 "a0","a1","d0"); \ 289 } while (0); 290 291 #define bus_space_write_multi_4(t, h, o, a, c) do { \ 292 (void) t; \ 293 __asm __volatile (" \ 294 movl %0,a0 ; \ 295 movl %1,a1 ; \ 296 movl %2,d0 ; \ 297 1: movl a1@+,a0@ ; \ 298 subql #1,d0 ; \ 299 jne 1b" : \ 300 : \ 301 "r" ((h) + (o)), "g" (a), "g" (c) : \ 302 "a0","a1","d0"); \ 303 } while (0); 304 305 #if 0 /* Cause a link error for bus_space_write_8 */ 306 #define bus_space_write_multi_8(t, h, o, a, c) \ 307 !!! bus_space_write_multi_8 unimplimented !!! 308 #endif 309 310 /* 311 * void bus_space_write_region_N __P((bus_space_tag_t tag, 312 * bus_space_handle_t bsh, bus_size_t offset, 313 * const u_intN_t *addr, size_t count)); 314 * 315 * Write `count' 1, 2, 4, or 8 byte quantities from the buffer provided 316 * to bus space described by tag/handle starting at `offset'. 317 */ 318 319 #define bus_space_write_region_1(t, h, o, a, c) do { \ 320 (void) t; \ 321 __asm __volatile (" \ 322 movl %0,a0 ; \ 323 movl %1,a1 ; \ 324 movl %2,d0 ; \ 325 1: movb a1@+,a0@+ ; \ 326 subql #1,d0 ; \ 327 jne 1b" : \ 328 : \ 329 "r" ((h) + (o)), "g" (a), "g" (c) : \ 330 "a0","a1","d0"); \ 331 } while (0); 332 333 #define bus_space_write_region_2(t, h, o, a, c) do { \ 334 (void) t; \ 335 __asm __volatile (" \ 336 movl %0,a0 ; \ 337 movl %1,a1 ; \ 338 movl %2,d0 ; \ 339 1: movw a1@+,a0@+ ; \ 340 subql #1,d0 ; \ 341 jne 1b" : \ 342 : \ 343 "r" ((h) + (o)), "g" (a), "g" (c) : \ 344 "a0","a1","d0"); \ 345 } while (0); 346 347 #define bus_space_write_region_4(t, h, o, a, c) do { \ 348 (void) t; \ 349 __asm __volatile (" \ 350 movl %0,a0 ; \ 351 movl %1,a1 ; \ 352 movl %2,d0 ; \ 353 1: movl a1@+,a0@+ ; \ 354 subql #1,d0 ; \ 355 jne 1b" : \ 356 : \ 357 "r" ((h) + (o)), "g" (a), "g" (c) : \ 358 "a0","a1","d0"); \ 359 } while (0); 360 361 #if 0 /* Cause a link error for bus_space_write_region_8 */ 362 #define bus_space_write_region_8 \ 363 !!! bus_space_write_region_8 unimplemented !!! 364 #endif 365 366 /* 367 * void bus_space_set_multi_N __P((bus_space_tag_t tag, 368 * bus_space_handle_t bsh, bus_size_t offset, u_intN_t val, 369 * size_t count)); 370 * 371 * Write the 1, 2, 4, or 8 byte value `val' to bus space described 372 * by tag/handle/offset `count' times. 373 */ 374 375 #define bus_space_set_multi_1(t, h, o, val, c) do { \ 376 (void) t; \ 377 __asm __volatile (" \ 378 movl %0,a0 ; \ 379 movl %1,d1 ; \ 380 movl %2,d0 ; \ 381 1: movb d1,a0@ ; \ 382 subql #1,d0 ; \ 383 jne 1b" : \ 384 : \ 385 "r" ((h) + (o)), "g" (val), "g" (c) : \ 386 "a0","d0","d1"); \ 387 } while (0); 388 389 #define bus_space_set_multi_2(t, h, o, val, c) do { \ 390 (void) t; \ 391 __asm __volatile (" \ 392 movl %0,a0 ; \ 393 movl %1,d1 ; \ 394 movl %2,d0 ; \ 395 1: movw d1,a0@ ; \ 396 subql #1,d0 ; \ 397 jne 1b" : \ 398 : \ 399 "r" ((h) + (o)), "g" (val), "g" (c) : \ 400 "a0","d0","d1"); \ 401 } while (0); 402 403 #define bus_space_set_multi_4(t, h, o, val, c) do { \ 404 (void) t; \ 405 __asm __volatile (" \ 406 movl %0,a0 ; \ 407 movl %1,d1 ; \ 408 movl %2,d0 ; \ 409 1: movl d1,a0@ ; \ 410 subql #1,d0 ; \ 411 jne 1b" : \ 412 : \ 413 "r" ((h) + (o)), "g" (val), "g" (c) : \ 414 "a0","d0","d1"); \ 415 } while (0); 416 417 #if 0 /* Cause a link error for bus_space_set_multi_8 */ 418 #define bus_space_set_multi_8 \ 419 !!! bus_space_set_multi_8 unimplemented !!! 420 #endif 421 422 /* 423 * void bus_space_set_region_N __P((bus_space_tag_t tag, 424 * bus_space_handle_t bsh, bus_size_t offset, u_intN_t val, 425 * size_t count)); 426 * 427 * Write `count' 1, 2, 4, or 8 byte value `val' to bus space described 428 * by tag/handle starting at `offset'. 429 */ 430 431 #define bus_space_set_region_1(t, h, o, val, c) do { \ 432 (void) t; \ 433 __asm __volatile (" \ 434 movl %0,a0 ; \ 435 movl %1,d1 ; \ 436 movl %2,d0 ; \ 437 1: movb d1,a0@+ ; \ 438 subql #1,d0 ; \ 439 jne 1b" : \ 440 : \ 441 "r" ((h) + (o)), "g" (val), "g" (c) : \ 442 "a0","d0","d1"); \ 443 } while (0); 444 445 #define bus_space_set_region_2(t, h, o, val, c) do { \ 446 (void) t; \ 447 __asm __volatile (" \ 448 movl %0,a0 ; \ 449 movl %1,d1 ; \ 450 movl %2,d0 ; \ 451 1: movw d1,a0@+ ; \ 452 subql #1,d0 ; \ 453 jne 1b" : \ 454 : \ 455 "r" ((h) + (o)), "g" (val), "g" (c) : \ 456 "a0","d0","d1"); \ 457 } while (0); 458 459 #define bus_space_set_region_4(t, h, o, val, c) do { \ 460 (void) t; \ 461 __asm __volatile (" \ 462 movl %0,a0 ; \ 463 movl %1,d1 ; \ 464 movl %2,d0 ; \ 465 1: movl d1,a0@+ ; \ 466 subql #1,d0 ; \ 467 jne 1b" : \ 468 : \ 469 "r" ((h) + (o)), "g" (val), "g" (c) : \ 470 "a0","d0","d1"); \ 471 } while (0); 472 473 #if 0 /* Cause a link error for bus_space_set_region_8 */ 474 #define bus_space_set_region_8 \ 475 !!! bus_space_set_region_8 unimplemented !!! 476 #endif 477 478 /* 479 * void bus_space_copy_N __P((bus_space_tag_t tag, 480 * bus_space_handle_t bsh1, bus_size_t off1, 481 * bus_space_handle_t bsh2, bus_size_t off2, 482 * size_t count)); 483 * 484 * Copy `count' 1, 2, 4, or 8 byte values from bus space starting 485 * at tag/bsh1/off1 to bus space starting at tag/bsh2/off2. 486 */ 487 488 #define bus_space_copy_1(t, h1, o1, h2, o2, c) do { \ 489 (void) t; \ 490 __asm __volatile (" \ 491 movl %0,a0 ; \ 492 movl %1,a1 ; \ 493 movl %2,d0 ; \ 494 1: movb a0@+,a1@+ ; \ 495 subql #1,d0 ; \ 496 jne 1b" : \ 497 : \ 498 "r" ((h1) + (o1)), "r" ((h2) + (o2)), "g" (c) : \ 499 "a0","a1","d0"); \ 500 } while (0); 501 502 #define bus_space_copy_2(t, h1, o1, h2, o2, c) do { \ 503 (void) t; \ 504 __asm __volatile (" \ 505 movl %0,a0 ; \ 506 movl %1,a1 ; \ 507 movl %2,d0 ; \ 508 1: movw a0@+,a1@+ ; \ 509 subql #1,d0 ; \ 510 jne 1b" : \ 511 : \ 512 "r" ((h1) + (o1)), "r" ((h2) + (o2)), "g" (c) : \ 513 "a0","a1","d0"); \ 514 } while (0); 515 516 #define bus_space_copy_4(t, h1, o1, h2, o2, c) do { \ 517 (void) t; \ 518 __asm __volatile (" \ 519 movl %0,a0 ; \ 520 movl %1,a1 ; \ 521 movl %2,d0 ; \ 522 1: movl a0@+,a1@+ ; \ 523 subql #1,d0 ; \ 524 jne 1b" : \ 525 : \ 526 "r" ((h1) + (o1)), "r" ((h2) + (o2)), "g" (c) : \ 527 "a0","a1","d0"); \ 528 } while (0); 529 530 #if 0 /* Cause a link error for bus_space_copy_8 */ 531 #define bus_space_copy_8 \ 532 !!! bus_space_copy_8 unimplemented !!! 533 #endif 534 535 /* 536 * Bus read/write barrier methods. 537 * 538 * void bus_space_barrier __P((bus_space_tag_t tag, 539 * bus_space_handle_t bsh, bus_size_t offset, 540 * bus_size_t len, int flags)); 541 * 542 * Note: the 680x0 does not currently require barriers, but we must 543 * provide the flags to MI code. 544 */ 545 #define bus_space_barrier(t, h, o, l, f) \ 546 ((void)((void)(t), (void)(h), (void)(o), (void)(l), (void)(f))) 547 #define BUS_BARRIER_READ 0x01 /* force read barrier */ 548 #define BUS_BARRIER_WRITE 0x02 /* force write barrier */ 549 550 /* 551 * Machine-dependent extensions. 552 */ 553 int bus_probe __P((bus_space_tag_t t, bus_space_handle_t bsh, 554 bus_size_t offset, int sz)); 555 556 #endif /* _MAC68K_BUS_H_ */ 557