Home | History | Annotate | Line # | Download | only in mips
cache_r4k.c revision 1.7
      1 /*	$NetBSD: cache_r4k.c,v 1.7 2002/11/07 23:03:21 cgd Exp $	*/
      2 
      3 /*
      4  * Copyright 2001 Wasabi Systems, Inc.
      5  * All rights reserved.
      6  *
      7  * Written by Jason R. Thorpe for Wasabi Systems, Inc.
      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 for the NetBSD Project by
     20  *	Wasabi Systems, Inc.
     21  * 4. The name of Wasabi Systems, Inc. may not be used to endorse
     22  *    or promote products derived from this software without specific prior
     23  *    written permission.
     24  *
     25  * THIS SOFTWARE IS PROVIDED BY WASABI SYSTEMS, INC. ``AS IS'' AND
     26  * 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 WASABI SYSTEMS, INC
     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 #include <sys/param.h>
     39 
     40 #include <mips/cache.h>
     41 #include <mips/cache_r4k.h>
     42 
     43 /*
     44  * Cache operations for R4000/R4400-style caches:
     45  *
     46  *	- Direct-mapped
     47  *	- Write-back
     48  *	- Virtually indexed, physically tagged
     49  *
     50  * XXX Does not handle split secondary caches.
     51  */
     52 
     53 #define	round_line(x)		(((x) + 15) & ~15)
     54 #define	trunc_line(x)		((x) & ~15)
     55 
     56 __asm(".set mips3");
     57 
     58 void
     59 r4k_icache_sync_all_16(void)
     60 {
     61 	vaddr_t va = MIPS_PHYS_TO_KSEG0(0);
     62 	vaddr_t eva = va + mips_picache_size;
     63 
     64 	mips_dcache_wbinv_all();
     65 
     66 	__asm __volatile("sync");
     67 
     68 	while (va < eva) {
     69 		cache_r4k_op_32lines_16(va, CACHE_R4K_I|CACHEOP_R4K_INDEX_INV);
     70 		va += (32 * 16);
     71 	}
     72 }
     73 
     74 void
     75 r4k_icache_sync_range_16(vaddr_t va, vsize_t size)
     76 {
     77 	vaddr_t eva = round_line(va + size);
     78 
     79 	va = trunc_line(va);
     80 
     81 	mips_dcache_wb_range(va, (eva - va));
     82 
     83 	__asm __volatile("sync");
     84 
     85 	while ((eva - va) >= (32 * 16)) {
     86 		cache_r4k_op_32lines_16(va, CACHE_R4K_I|CACHEOP_R4K_HIT_INV);
     87 		va += (32 * 16);
     88 	}
     89 
     90 	while (va < eva) {
     91 		cache_op_r4k_line(va, CACHE_R4K_I|CACHEOP_R4K_HIT_INV);
     92 		va += 16;
     93 	}
     94 }
     95 
     96 void
     97 r4k_icache_sync_range_index_16(vaddr_t va, vsize_t size)
     98 {
     99 	vaddr_t eva, orig_va;
    100 
    101 	orig_va = va;
    102 
    103 	eva = round_line(va + size);
    104 	va = trunc_line(va);
    105 
    106 	mips_dcache_wbinv_range_index(va, (eva - va));
    107 
    108 	__asm __volatile("sync");
    109 
    110 	/*
    111 	 * Since we're doing Index ops, we expect to not be able
    112 	 * to access the address we've been given.  So, get the
    113 	 * bits that determine the cache index, and make a KSEG0
    114 	 * address out of them.
    115 	 */
    116 	va = MIPS_PHYS_TO_KSEG0(orig_va & mips_picache_way_mask);
    117 
    118 	eva = round_line(va + size);
    119 	va = trunc_line(va);
    120 
    121 	while ((eva - va) >= (32 * 16)) {
    122 		cache_r4k_op_32lines_16(va, CACHE_R4K_I|CACHEOP_R4K_INDEX_INV);
    123 		va += (32 * 16);
    124 	}
    125 
    126 	while (va < eva) {
    127 		cache_op_r4k_line(va, CACHE_R4K_I|CACHEOP_R4K_INDEX_INV);
    128 		va += 16;
    129 	}
    130 }
    131 
    132 void
    133 r4k_pdcache_wbinv_all_16(void)
    134 {
    135 	vaddr_t va = MIPS_PHYS_TO_KSEG0(0);
    136 	vaddr_t eva = va + mips_pdcache_size;
    137 
    138 	while (va < eva) {
    139 		cache_r4k_op_32lines_16(va,
    140 		    CACHE_R4K_D|CACHEOP_R4K_INDEX_WB_INV);
    141 		va += (32 * 16);
    142 	}
    143 }
    144 
    145 void
    146 r4k_pdcache_wbinv_range_16(vaddr_t va, vsize_t size)
    147 {
    148 	vaddr_t eva = round_line(va + size);
    149 
    150 	va = trunc_line(va);
    151 
    152 	while ((eva - va) >= (32 * 16)) {
    153 		cache_r4k_op_32lines_16(va,
    154 		    CACHE_R4K_D|CACHEOP_R4K_HIT_WB_INV);
    155 		va += (32 * 16);
    156 	}
    157 
    158 	while (va < eva) {
    159 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_HIT_WB_INV);
    160 		va += 16;
    161 	}
    162 }
    163 
    164 void
    165 r4k_pdcache_wbinv_range_index_16(vaddr_t va, vsize_t size)
    166 {
    167 	vaddr_t eva;
    168 
    169 	/*
    170 	 * Since we're doing Index ops, we expect to not be able
    171 	 * to access the address we've been given.  So, get the
    172 	 * bits that determine the cache index, and make a KSEG0
    173 	 * address out of them.
    174 	 */
    175 	va = MIPS_PHYS_TO_KSEG0(va & (mips_pdcache_size - 1));
    176 
    177 	eva = round_line(va + size);
    178 	va = trunc_line(va);
    179 
    180 	while ((eva - va) >= (32 * 16)) {
    181 		cache_r4k_op_32lines_16(va,
    182 		    CACHE_R4K_D|CACHEOP_R4K_INDEX_WB_INV);
    183 		va += (32 * 16);
    184 	}
    185 
    186 	while (va < eva) {
    187 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_INDEX_WB_INV);
    188 		va += 16;
    189 	}
    190 }
    191 
    192 void
    193 r4k_pdcache_inv_range_16(vaddr_t va, vsize_t size)
    194 {
    195 	vaddr_t eva = round_line(va + size);
    196 
    197 	va = trunc_line(va);
    198 
    199 	while ((eva - va) >= (32 * 16)) {
    200 		cache_r4k_op_32lines_16(va, CACHE_R4K_D|CACHEOP_R4K_HIT_INV);
    201 		va += (32 * 16);
    202 	}
    203 
    204 	while (va < eva) {
    205 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_HIT_INV);
    206 		va += 16;
    207 	}
    208 }
    209 
    210 void
    211 r4k_pdcache_wb_range_16(vaddr_t va, vsize_t size)
    212 {
    213 	vaddr_t eva = round_line(va + size);
    214 
    215 	va = trunc_line(va);
    216 
    217 	while ((eva - va) >= (32 * 16)) {
    218 		cache_r4k_op_32lines_16(va, CACHE_R4K_D|CACHEOP_R4K_HIT_WB);
    219 		va += (32 * 16);
    220 	}
    221 
    222 	while (va < eva) {
    223 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_HIT_WB);
    224 		va += 16;
    225 	}
    226 }
    227 
    228 #undef round_line
    229 #undef trunc_line
    230 
    231 #define	round_line(x)		(((x) + 31) & ~31)
    232 #define	trunc_line(x)		((x) & ~31)
    233 
    234 void
    235 r4k_icache_sync_all_32(void)
    236 {
    237 	vaddr_t va = MIPS_PHYS_TO_KSEG0(0);
    238 	vaddr_t eva = va + mips_picache_size;
    239 
    240 	mips_dcache_wbinv_all();
    241 
    242 	__asm __volatile("sync");
    243 
    244 	while (va < eva) {
    245 		cache_r4k_op_32lines_32(va, CACHE_R4K_I|CACHEOP_R4K_INDEX_INV);
    246 		va += (32 * 32);
    247 	}
    248 }
    249 
    250 void
    251 r4k_icache_sync_range_32(vaddr_t va, vsize_t size)
    252 {
    253 	vaddr_t eva = round_line(va + size);
    254 
    255 	va = trunc_line(va);
    256 
    257 	mips_dcache_wb_range(va, (eva - va));
    258 
    259 	__asm __volatile("sync");
    260 
    261 	while ((eva - va) >= (32 * 32)) {
    262 		cache_r4k_op_32lines_32(va, CACHE_R4K_I|CACHEOP_R4K_HIT_INV);
    263 		va += (32 * 32);
    264 	}
    265 
    266 	while (va < eva) {
    267 		cache_op_r4k_line(va, CACHE_R4K_I|CACHEOP_R4K_HIT_INV);
    268 		va += 32;
    269 	}
    270 }
    271 
    272 void
    273 r4k_icache_sync_range_index_32(vaddr_t va, vsize_t size)
    274 {
    275 	vaddr_t eva;
    276 
    277 	eva = round_line(va + size);
    278 	va = trunc_line(va);
    279 
    280 	mips_dcache_wbinv_range_index(va, (eva - va));
    281 
    282 	__asm __volatile("sync");
    283 
    284 	/*
    285 	 * Since we're doing Index ops, we expect to not be able
    286 	 * to access the address we've been given.  So, get the
    287 	 * bits that determine the cache index, and make a KSEG0
    288 	 * address out of them.
    289 	 */
    290 	va = MIPS_PHYS_TO_KSEG0(va & mips_picache_way_mask);
    291 
    292 	eva = round_line(va + size);
    293 	va = trunc_line(va);
    294 
    295 	while ((eva - va) >= (32 * 32)) {
    296 		cache_r4k_op_32lines_32(va, CACHE_R4K_I|CACHEOP_R4K_INDEX_INV);
    297 		va += (32 * 32);
    298 	}
    299 
    300 	while (va < eva) {
    301 		cache_op_r4k_line(va, CACHE_R4K_I|CACHEOP_R4K_INDEX_INV);
    302 		va += 32;
    303 	}
    304 }
    305 
    306 void
    307 r4k_pdcache_wbinv_all_32(void)
    308 {
    309 	vaddr_t va = MIPS_PHYS_TO_KSEG0(0);
    310 	vaddr_t eva = va + mips_pdcache_size;
    311 
    312 	while (va < eva) {
    313 		cache_r4k_op_32lines_32(va,
    314 		    CACHE_R4K_D|CACHEOP_R4K_INDEX_WB_INV);
    315 		va += (32 * 32);
    316 	}
    317 }
    318 
    319 void
    320 r4k_pdcache_wbinv_range_32(vaddr_t va, vsize_t size)
    321 {
    322 	vaddr_t eva = round_line(va + size);
    323 
    324 	va = trunc_line(va);
    325 
    326 	while ((eva - va) >= (32 * 32)) {
    327 		cache_r4k_op_32lines_32(va,
    328 		    CACHE_R4K_D|CACHEOP_R4K_HIT_WB_INV);
    329 		va += (32 * 32);
    330 	}
    331 
    332 	while (va < eva) {
    333 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_HIT_WB_INV);
    334 		va += 32;
    335 	}
    336 }
    337 
    338 void
    339 r4k_pdcache_wbinv_range_index_32(vaddr_t va, vsize_t size)
    340 {
    341 	vaddr_t eva;
    342 
    343 	/*
    344 	 * Since we're doing Index ops, we expect to not be able
    345 	 * to access the address we've been given.  So, get the
    346 	 * bits that determine the cache index, and make a KSEG0
    347 	 * address out of them.
    348 	 */
    349 	va = MIPS_PHYS_TO_KSEG0(va & (mips_pdcache_size - 1));
    350 
    351 	eva = round_line(va + size);
    352 	va = trunc_line(va);
    353 
    354 	while ((eva - va) >= (32 * 32)) {
    355 		cache_r4k_op_32lines_32(va,
    356 		    CACHE_R4K_D|CACHEOP_R4K_INDEX_WB_INV);
    357 		va += (32 * 32);
    358 	}
    359 
    360 	while (va < eva) {
    361 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_INDEX_WB_INV);
    362 		va += 32;
    363 	}
    364 }
    365 
    366 void
    367 r4k_pdcache_inv_range_32(vaddr_t va, vsize_t size)
    368 {
    369 	vaddr_t eva = round_line(va + size);
    370 
    371 	va = trunc_line(va);
    372 
    373 	while ((eva - va) >= (32 * 32)) {
    374 		cache_r4k_op_32lines_32(va, CACHE_R4K_D|CACHEOP_R4K_HIT_INV);
    375 		va += (32 * 32);
    376 	}
    377 
    378 	while (va < eva) {
    379 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_HIT_INV);
    380 		va += 32;
    381 	}
    382 }
    383 
    384 void
    385 r4k_pdcache_wb_range_32(vaddr_t va, vsize_t size)
    386 {
    387 	vaddr_t eva = round_line(va + size);
    388 
    389 	va = trunc_line(va);
    390 
    391 	while ((eva - va) >= (32 * 32)) {
    392 		cache_r4k_op_32lines_32(va, CACHE_R4K_D|CACHEOP_R4K_HIT_WB);
    393 		va += (32 * 32);
    394 	}
    395 
    396 	while (va < eva) {
    397 		cache_op_r4k_line(va, CACHE_R4K_D|CACHEOP_R4K_HIT_WB);
    398 		va += 32;
    399 	}
    400 }
    401 
    402 void
    403 r4k_sdcache_wbinv_all_32(void)
    404 {
    405 	vaddr_t va = MIPS_PHYS_TO_KSEG0(0);
    406 	vaddr_t eva = va + mips_sdcache_size;
    407 
    408 	while (va < eva) {
    409 		cache_r4k_op_32lines_32(va,
    410 		    CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    411 		va += (32 * 32);
    412 	}
    413 }
    414 
    415 void
    416 r4k_sdcache_wbinv_range_32(vaddr_t va, vsize_t size)
    417 {
    418 	vaddr_t eva = round_line(va + size);
    419 
    420 	va = trunc_line(va);
    421 
    422 	while ((eva - va) >= (32 * 32)) {
    423 		cache_r4k_op_32lines_32(va,
    424 		    CACHE_R4K_SD|CACHEOP_R4K_HIT_WB_INV);
    425 		va += (32 * 32);
    426 	}
    427 
    428 	while (va < eva) {
    429 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB_INV);
    430 		va += 32;
    431 	}
    432 }
    433 
    434 void
    435 r4k_sdcache_wbinv_range_index_32(vaddr_t va, vsize_t size)
    436 {
    437 	vaddr_t eva;
    438 
    439 	/*
    440 	 * Since we're doing Index ops, we expect to not be able
    441 	 * to access the address we've been given.  So, get the
    442 	 * bits that determine the cache index, and make a KSEG0
    443 	 * address out of them.
    444 	 */
    445 	va = MIPS_PHYS_TO_KSEG0(va & (mips_sdcache_size - 1));
    446 
    447 	eva = round_line(va + size);
    448 	va = trunc_line(va);
    449 
    450 	while ((eva - va) >= (32 * 32)) {
    451 		cache_r4k_op_32lines_32(va,
    452 		    CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    453 		va += (32 * 32);
    454 	}
    455 
    456 	while (va < eva) {
    457 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    458 		va += 32;
    459 	}
    460 }
    461 
    462 void
    463 r4k_sdcache_inv_range_32(vaddr_t va, vsize_t size)
    464 {
    465 	vaddr_t eva = round_line(va + size);
    466 
    467 	va = trunc_line(va);
    468 
    469 	while ((eva - va) >= (32 * 32)) {
    470 		cache_r4k_op_32lines_32(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_INV);
    471 		va += (32 * 32);
    472 	}
    473 
    474 	while (va < eva) {
    475 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_INV);
    476 		va += 32;
    477 	}
    478 }
    479 
    480 void
    481 r4k_sdcache_wb_range_32(vaddr_t va, vsize_t size)
    482 {
    483 	vaddr_t eva = round_line(va + size);
    484 
    485 	va = trunc_line(va);
    486 
    487 	while ((eva - va) >= (32 * 32)) {
    488 		cache_r4k_op_32lines_32(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB);
    489 		va += (32 * 32);
    490 	}
    491 
    492 	while (va < eva) {
    493 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB);
    494 		va += 32;
    495 	}
    496 }
    497 
    498 #undef round_line
    499 #undef trunc_line
    500 
    501 #define	round_line(x)		(((x) + 127) & ~127)
    502 #define	trunc_line(x)		((x) & ~127)
    503 
    504 void
    505 r4k_sdcache_wbinv_all_128(void)
    506 {
    507 	vaddr_t va = MIPS_PHYS_TO_KSEG0(0);
    508 	vaddr_t eva = va + mips_sdcache_size;
    509 
    510 	while (va < eva) {
    511 		cache_r4k_op_32lines_128(va,
    512 		    CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    513 		va += (32 * 128);
    514 	}
    515 }
    516 
    517 void
    518 r4k_sdcache_wbinv_range_128(vaddr_t va, vsize_t size)
    519 {
    520 	vaddr_t eva = round_line(va + size);
    521 
    522 	va = trunc_line(va);
    523 
    524 	while ((eva - va) >= (32 * 128)) {
    525 		cache_r4k_op_32lines_128(va,
    526 		    CACHE_R4K_SD|CACHEOP_R4K_HIT_WB_INV);
    527 		va += (32 * 128);
    528 	}
    529 
    530 	while (va < eva) {
    531 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB_INV);
    532 		va += 128;
    533 	}
    534 }
    535 
    536 void
    537 r4k_sdcache_wbinv_range_index_128(vaddr_t va, vsize_t size)
    538 {
    539 	vaddr_t eva;
    540 
    541 	/*
    542 	 * Since we're doing Index ops, we expect to not be able
    543 	 * to access the address we've been given.  So, get the
    544 	 * bits that determine the cache index, and make a KSEG0
    545 	 * address out of them.
    546 	 */
    547 	va = MIPS_PHYS_TO_KSEG0(va & (mips_sdcache_size - 1));
    548 
    549 	eva = round_line(va + size);
    550 	va = trunc_line(va);
    551 
    552 	while ((eva - va) >= (32 * 128)) {
    553 		cache_r4k_op_32lines_128(va,
    554 		    CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    555 		va += (32 * 128);
    556 	}
    557 
    558 	while (va < eva) {
    559 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    560 		va += 128;
    561 	}
    562 }
    563 
    564 void
    565 r4k_sdcache_inv_range_128(vaddr_t va, vsize_t size)
    566 {
    567 	vaddr_t eva = round_line(va + size);
    568 
    569 	va = trunc_line(va);
    570 
    571 	while ((eva - va) >= (32 * 128)) {
    572 		cache_r4k_op_32lines_128(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_INV);
    573 		va += (32 * 128);
    574 	}
    575 
    576 	while (va < eva) {
    577 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_INV);
    578 		va += 128;
    579 	}
    580 }
    581 
    582 void
    583 r4k_sdcache_wb_range_128(vaddr_t va, vsize_t size)
    584 {
    585 	vaddr_t eva = round_line(va + size);
    586 
    587 	va = trunc_line(va);
    588 
    589 	while ((eva - va) >= (32 * 128)) {
    590 		cache_r4k_op_32lines_128(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB);
    591 		va += (32 * 128);
    592 	}
    593 
    594 	while (va < eva) {
    595 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB);
    596 		va += 128;
    597 	}
    598 }
    599 
    600 #undef round_line
    601 #undef trunc_line
    602 
    603 #define	round_line(x)		(((x) + mips_sdcache_line_size - 1) & ~(mips_sdcache_line_size - 1))
    604 #define	trunc_line(x)		((x) & ~(mips_sdcache_line_size - 1))
    605 
    606 void
    607 r4k_sdcache_wbinv_all_generic(void)
    608 {
    609 	vaddr_t va = MIPS_PHYS_TO_KSEG0(0);
    610 	vaddr_t eva = va + mips_sdcache_size;
    611 	int line_size = mips_sdcache_line_size;
    612 
    613 	while (va < eva) {
    614 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    615 		va += line_size;
    616 	}
    617 }
    618 
    619 void
    620 r4k_sdcache_wbinv_range_generic(vaddr_t va, vsize_t size)
    621 {
    622 	vaddr_t eva = round_line(va + size);
    623 	int line_size = mips_sdcache_line_size;
    624 
    625 	va = trunc_line(va);
    626 
    627 	while (va < eva) {
    628 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB_INV);
    629 		va += line_size;
    630 	}
    631 }
    632 
    633 void
    634 r4k_sdcache_wbinv_range_index_generic(vaddr_t va, vsize_t size)
    635 {
    636 	vaddr_t eva;
    637 	int line_size = mips_sdcache_line_size;
    638 
    639 	/*
    640 	 * Since we're doing Index ops, we expect to not be able
    641 	 * to access the address we've been given.  So, get the
    642 	 * bits that determine the cache index, and make a KSEG0
    643 	 * address out of them.
    644 	 */
    645 	va = MIPS_PHYS_TO_KSEG0(va & (mips_sdcache_size - 1));
    646 
    647 	eva = round_line(va + size);
    648 	va = trunc_line(va);
    649 
    650 	while (va < eva) {
    651 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_INDEX_WB_INV);
    652 		va += line_size;
    653 	}
    654 }
    655 
    656 void
    657 r4k_sdcache_inv_range_generic(vaddr_t va, vsize_t size)
    658 {
    659 	vaddr_t eva = round_line(va + size);
    660 	int line_size = mips_sdcache_line_size;
    661 
    662 	va = trunc_line(va);
    663 
    664 	while (va < eva) {
    665 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_INV);
    666 		va += line_size;
    667 	}
    668 }
    669 
    670 void
    671 r4k_sdcache_wb_range_generic(vaddr_t va, vsize_t size)
    672 {
    673 	vaddr_t eva = round_line(va + size);
    674 	int line_size = mips_sdcache_line_size;
    675 
    676 	va = trunc_line(va);
    677 
    678 	while (va < eva) {
    679 		cache_op_r4k_line(va, CACHE_R4K_SD|CACHEOP_R4K_HIT_WB);
    680 		va += line_size;
    681 	}
    682 }
    683 
    684 #undef round_line
    685 #undef trunc_line
    686