1 /* $NetBSD: bus_space_large.c,v 1.2 2000/06/29 08:34:09 mrg Exp $ */ 2 3 /*- 4 * Copyright (c) 1996, 1997, 1998 The NetBSD Foundation, Inc. 5 * All rights reserved. 6 * 7 * This code is derived from software contributed to The NetBSD Foundation 8 * by Charles M. Hannum and by Jason R. Thorpe of the Numerical Aerospace 9 * Simulation Facility, 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 * For large sparse bus space 42 * (e.g. NEC RISCstation 2250 PCI memory space: 432MB) 43 * 44 * This bus_space uses either wired TLB or normal KSEG2 mapping 45 * for each bus space region. 46 * 47 * Wired TLB will be used on the following cases: 48 * - If requested region is already mapped by wired TLBs. 49 * This is needed for some critical resources which are used 50 * on kernel early stage (e.g. console device resources) 51 * - If requested region size >= ARC_THRESHOLD_TO_USE_WIRED_TLB, 52 * and enough wired TLBs are still free. 53 * In this case, the size of wired TLBs becomes always 54 * ARC_WIRED_PAGE_SIZE (i.e. 16MB). (See wired_map.c for detail.) 55 */ 56 57 #include <sys/param.h> 58 #include <sys/systm.h> 59 #include <sys/malloc.h> 60 #include <sys/extent.h> 61 62 #include <uvm/uvm_extern.h> 63 64 #include <machine/bus.h> 65 #include <arc/arc/wired_map.h> 66 67 static int arc_large_bus_space_compose_handle __P((bus_space_tag_t, 68 bus_addr_t, bus_size_t, int, bus_space_handle_t *)); 69 static int arc_large_bus_space_dispose_handle __P((bus_space_tag_t, 70 bus_space_handle_t, bus_size_t)); 71 static int arc_large_bus_space_paddr __P((bus_space_tag_t, 72 bus_space_handle_t, paddr_t *)); 73 74 void 75 arc_large_bus_space_init(bst, name, paddr, start, size) 76 bus_space_tag_t bst; 77 const char *name; 78 paddr_t paddr; 79 bus_addr_t start; 80 bus_size_t size; 81 { 82 arc_sparse_bus_space_init(bst, name, paddr, start, size); 83 bst->bs_compose_handle = arc_large_bus_space_compose_handle; 84 bst->bs_dispose_handle = arc_large_bus_space_dispose_handle; 85 bst->bs_paddr = arc_large_bus_space_paddr; 86 } 87 88 static int 89 arc_large_bus_space_compose_handle(bst, addr, size, flags, bshp) 90 bus_space_tag_t bst; 91 bus_addr_t addr; 92 bus_size_t size; 93 int flags; 94 bus_space_handle_t *bshp; 95 { 96 paddr_t pa; 97 vaddr_t va; 98 99 pa = bst->bs_pbase + (addr - bst->bs_start); 100 /* 101 * Check whether the physical address is already wired mapped 102 * or not. If not mapped but requested region is large enough, 103 * try to use wired TLB. 104 */ 105 if ((va = arc_contiguously_wired_mapped(pa, size)) != 0 || 106 (/* requested region is large enough? */ 107 size >= ARC_THRESHOLD_TO_USE_WIRED_TLB && 108 /* enough wired TLBs are still available? */ 109 (va = arc_map_wired(pa, size)) != 0)) { 110 #ifdef DIAGNOSTIC 111 /* 112 * If wired TLB is used, 113 * we will not make this bus_space region cacheable, 114 * since other bus_space might share this wired TLB. 115 */ 116 if (flags & BUS_SPACE_MAP_CACHEABLE) 117 printf("arc_large_bus_space_compose_handle: " 118 "ignore cacheable 0x%llx..0x%llx\n", 119 pa, pa + size - 1); 120 #endif 121 *bshp = va; 122 return (0); 123 } 124 return (arc_sparse_bus_space_compose_handle(bst, addr, size, flags, 125 bshp)); 126 } 127 128 static int 129 arc_large_bus_space_dispose_handle(bst, bsh, size) 130 bus_space_tag_t bst; 131 bus_space_handle_t bsh; 132 bus_size_t size; 133 { 134 paddr_t pa; 135 136 /* 137 * We never free already wired TLB entries, 138 * since the TLBs might be used for other bus_space region. 139 */ 140 if (arc_wired_map_extract(bsh, &pa)) 141 return (0); 142 return (arc_sparse_bus_space_dispose_handle(bst, bsh, size)); 143 } 144 145 static int 146 arc_large_bus_space_paddr(bst, bsh, pap) 147 bus_space_tag_t bst; 148 bus_space_handle_t bsh; 149 paddr_t *pap; 150 { 151 if (arc_wired_map_extract(bsh, pap)) 152 return (0); 153 return (arc_sparse_bus_space_paddr(bst, bsh, pap)); 154 } 155