diff options
author | andrew <andrew@FreeBSD.org> | 2013-01-06 00:42:09 +0000 |
---|---|---|
committer | andrew <andrew@FreeBSD.org> | 2013-01-06 00:42:09 +0000 |
commit | 72392dc5f8d5f2146b0868e4f713a15bce5ed9d0 (patch) | |
tree | 414f2f2ab6106c9c0ae8595e385cf55271d76742 /sys | |
parent | 47c050325d73daad19b9cc14091285fe246d51d9 (diff) | |
download | FreeBSD-src-72392dc5f8d5f2146b0868e4f713a15bce5ed9d0.zip FreeBSD-src-72392dc5f8d5f2146b0868e4f713a15bce5ed9d0.tar.gz |
Only work around errata when we are on a part where the erratum applies.
Reviewed by: gonzo
Diffstat (limited to 'sys')
-rw-r--r-- | sys/arm/arm/pl310.c | 50 | ||||
-rw-r--r-- | sys/arm/include/pl310.h | 1 |
2 files changed, 32 insertions, 19 deletions
diff --git a/sys/arm/arm/pl310.c b/sys/arm/arm/pl310.c index a5af23c..672c12c 100644 --- a/sys/arm/arm/pl310.c +++ b/sys/arm/arm/pl310.c @@ -135,11 +135,12 @@ pl310_cache_sync(void) return; #ifdef PL310_ERRATA_753970 - /* Write uncached PL310 register */ - pl310_write4(pl310_softc, 0x740, 0xffffffff); -#else - pl310_write4(pl310_softc, PL310_CACHE_SYNC, 0xffffffff); + if (sc->sc_rtl_release == CACHE_ID_RELEASE_r3p0) + /* Write uncached PL310 register */ + pl310_write4(pl310_softc, 0x740, 0xffffffff); + else #endif + pl310_write4(pl310_softc, PL310_CACHE_SYNC, 0xffffffff); } @@ -152,13 +153,17 @@ pl310_wbinv_all(void) PL310_LOCK(pl310_softc); #ifdef PL310_ERRATA_727915 - platform_pl310_write_debug(pl310_softc, 3); + if (sc->sc_rtl_release == CACHE_ID_RELEASE_r2p0 || + sc->sc_rtl_release == CACHE_ID_RELEASE_r3p0) + platform_pl310_write_debug(pl310_softc, 3); #endif pl310_write4(pl310_softc, PL310_CLEAN_INV_WAY, g_l2cache_way_mask); pl310_wait_background_op(PL310_CLEAN_INV_WAY, g_l2cache_way_mask); pl310_cache_sync(); #ifdef PL310_ERRATA_727915 - platform_pl310_write_debug(pl310_softc, 0); + if (sc->sc_rtl_release == CACHE_ID_RELEASE_r2p0 || + sc->sc_rtl_release == CACHE_ID_RELEASE_r3p0) + platform_pl310_write_debug(pl310_softc, 0); #endif PL310_UNLOCK(pl310_softc); } @@ -182,27 +187,32 @@ pl310_wbinv_range(vm_paddr_t start, vm_size_t size) #ifdef PL310_ERRATA_727915 - platform_pl310_write_debug(pl310_softc, 3); + if (sc->sc_rtl_release == CACHE_ID_RELEASE_r2p0 || + sc->sc_rtl_release == CACHE_ID_RELEASE_r3p0) + platform_pl310_write_debug(pl310_softc, 3); #endif while (size > 0) { #ifdef PL310_ERRATA_588369 - /* - * Errata 588369 says that clean + inv may keep the - * cache line if it was clean, the recommanded workaround - * is to clean then invalidate the cache line, with - * write-back and cache linefill disabled - */ - - pl310_write4(pl310_softc, PL310_CLEAN_LINE_PA, start); - pl310_write4(pl310_softc, PL310_INV_LINE_PA, start); -#else - pl310_write4(pl310_softc, PL310_CLEAN_INV_LINE_PA, start); + if (sc->sc_rtl_release <= CACHE_ID_RELEASE_r1p0) { + /* + * Errata 588369 says that clean + inv may keep the + * cache line if it was clean, the recommanded + * workaround is to clean then invalidate the cache + * line, with write-back and cache linefill disabled. + */ + pl310_write4(pl310_softc, PL310_CLEAN_LINE_PA, start); + pl310_write4(pl310_softc, PL310_INV_LINE_PA, start); + } else #endif + pl310_write4(pl310_softc, PL310_CLEAN_INV_LINE_PA, + start); start += g_l2cache_line_size; size -= g_l2cache_line_size; } #ifdef PL310_ERRATA_727915 - platform_pl310_write_debug(pl310_softc, 0); + if (sc->sc_rtl_release == CACHE_ID_RELEASE_r2p0 || + sc->sc_rtl_release == CACHE_ID_RELEASE_r3p0) + platform_pl310_write_debug(pl310_softc, 0); #endif pl310_cache_sync(); @@ -307,6 +317,8 @@ pl310_attach(device_t dev) pl310_filter, NULL, sc, &sc->sc_irq_h); cache_id = pl310_read4(sc, PL310_CACHE_ID); + sc->sc_rtl_release = (cache_id >> CACHE_ID_RELEASE_SHIFT) & + CACHE_ID_RELEASE_MASK; device_printf(dev, "Part number: 0x%x, release: 0x%x\n", (cache_id >> CACHE_ID_PARTNUM_SHIFT) & CACHE_ID_PARTNUM_MASK, (cache_id >> CACHE_ID_RELEASE_SHIFT) & CACHE_ID_RELEASE_MASK); diff --git a/sys/arm/include/pl310.h b/sys/arm/include/pl310.h index 26f6c60..a3c42d8 100644 --- a/sys/arm/include/pl310.h +++ b/sys/arm/include/pl310.h @@ -131,6 +131,7 @@ struct pl310_softc { void* sc_irq_h; int sc_enabled; struct mtx sc_mtx; + u_int sc_rtl_revision; }; /** |