1 /* $NetBSD: bus_space_sparse.c,v 1.6 2001/09/10 21:19:31 chris Exp $ */ 2 /* NetBSD: bus_machdep.c,v 1.1 2000/01/26 18:48:00 drochner Exp */ 3 4 /*- 5 * Copyright (c) 1996, 1997, 1998 The NetBSD Foundation, Inc. 6 * All rights reserved. 7 * 8 * This code is derived from software contributed to The NetBSD Foundation 9 * by Charles M. Hannum and by Jason R. Thorpe of the Numerical Aerospace 10 * Simulation Facility, NASA Ames Research Center. 11 * 12 * Redistribution and use in source and binary forms, with or without 13 * modification, are permitted provided that the following conditions 14 * are met: 15 * 1. Redistributions of source code must retain the above copyright 16 * notice, this list of conditions and the following disclaimer. 17 * 2. Redistributions in binary form must reproduce the above copyright 18 * notice, this list of conditions and the following disclaimer in the 19 * documentation and/or other materials provided with the distribution. 20 * 3. All advertising materials mentioning features or use of this software 21 * must display the following acknowledgement: 22 * This product includes software developed by the NetBSD 23 * Foundation, Inc. and its contributors. 24 * 4. Neither the name of The NetBSD Foundation nor the names of its 25 * contributors may be used to endorse or promote products derived 26 * from this software without specific prior written permission. 27 * 28 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 29 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 30 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 31 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 32 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 33 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 34 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 35 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 36 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 37 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 38 * POSSIBILITY OF SUCH DAMAGE. 39 */ 40 41 /* 42 * For sparse bus space 43 * 44 * This bus_space uses KSEG2 mapping, if the physical address is not 45 * accessible via KSEG0/KSEG1. 46 */ 47 48 #include <sys/param.h> 49 #include <sys/systm.h> 50 #include <sys/malloc.h> 51 #include <sys/extent.h> 52 53 #include <uvm/uvm_extern.h> 54 55 #include <mips/cpuregs.h> 56 #include <mips/pte.h> 57 58 #include <machine/bus.h> 59 60 extern paddr_t kvtophys __P((vaddr_t)); /* XXX */ 61 62 void arc_kseg2_make_cacheable __P((vaddr_t vaddr, vsize_t size)); 63 64 void 65 arc_kseg2_make_cacheable(vaddr, size) 66 vaddr_t vaddr; 67 vsize_t size; 68 { 69 vaddr_t start, end; 70 pt_entry_t *pte; 71 u_int32_t entry, mask; 72 73 start = mips_trunc_page(vaddr); 74 end = mips_round_page(vaddr + size); 75 mask = ~(CPUISMIPS3 ? MIPS3_PG_UNCACHED : MIPS1_PG_N); 76 for (; start < end; start += NBPG) { 77 pte = kvtopte(start); 78 entry = pte->pt_entry & mask; 79 pte->pt_entry &= entry; 80 MachTLBUpdate(start, entry); 81 } 82 } 83 84 void 85 arc_sparse_bus_space_init(bst, name, paddr, start, size) 86 bus_space_tag_t bst; 87 const char *name; 88 paddr_t paddr; 89 bus_addr_t start; 90 bus_size_t size; 91 { 92 arc_bus_space_init(bst, name, paddr, ARC_BUS_SPACE_UNMAPPED, 93 start, size); 94 bst->bs_compose_handle = arc_sparse_bus_space_compose_handle; 95 bst->bs_dispose_handle = arc_sparse_bus_space_dispose_handle; 96 bst->bs_paddr = arc_sparse_bus_space_paddr; 97 } 98 99 int 100 arc_sparse_bus_space_compose_handle(bst, addr, size, flags, bshp) 101 bus_space_tag_t bst; 102 bus_addr_t addr; 103 bus_size_t size; 104 int flags; 105 bus_space_handle_t *bshp; 106 { 107 bus_size_t offset = addr - bst->bs_start; 108 /* 109 * Since all buses can be linearly mappable, we don't have to check 110 * BUS_SPACE_MAP_LINEAR and BUS_SPACE_MAP_PREFETCHABLE. 111 */ 112 int cacheable = (flags & BUS_SPACE_MAP_CACHEABLE); 113 114 /* 115 * XXX - `bst->bs_pbase' must be page aligned, 116 * mips_trunc/round_page() cannot treat paddr_t due to overflow. 117 */ 118 paddr_t start = bst->bs_pbase + mips_trunc_page(offset); 119 paddr_t end = bst->bs_pbase + mips_round_page(offset + size); 120 121 if (end <= MIPS_KSEG1_START - MIPS_KSEG0_START) { 122 /* mappable on KSEG0 or KSEG1 */ 123 *bshp = (cacheable ? 124 MIPS_PHYS_TO_KSEG0(start) : 125 MIPS_PHYS_TO_KSEG1(start)); 126 } else { 127 vaddr_t va, 128 vaddr = uvm_km_valloc(kernel_map, (vsize_t)(end - start)); 129 130 if (vaddr == NULL) 131 panic("arc_sparse_bus_space_compose_handle: " 132 "cannot allocate KVA 0x%llx..0x%llx", 133 start, end); 134 for (va = vaddr; start < end; start += NBPG, va += NBPG) 135 pmap_kenter_pa(va, start, VM_PROT_READ|VM_PROT_WRITE); 136 pmap_update(pmap_kernel()); 137 vaddr += (offset & PGOFSET); 138 if (cacheable) 139 arc_kseg2_make_cacheable(vaddr, size); 140 *bshp = vaddr; 141 } 142 return (0); 143 } 144 145 int 146 arc_sparse_bus_space_dispose_handle(bst, bsh, size) 147 bus_space_tag_t bst; 148 bus_space_handle_t bsh; 149 bus_size_t size; 150 { 151 vaddr_t start = mips_trunc_page(bsh); 152 vaddr_t end = mips_round_page(bsh + size); 153 154 if (start < MIPS_KSEG2_START) /* KSEG0/KSEG1 */ 155 return (0); 156 157 uvm_km_free(kernel_map, start, end - start); 158 return (0); 159 } 160 161 int 162 arc_sparse_bus_space_paddr(bst, bsh, pap) 163 bus_space_tag_t bst; 164 bus_space_handle_t bsh; 165 paddr_t *pap; 166 { 167 *pap = kvtophys(bsh); 168 return (0); 169 } 170