diff options
author | 2015-08-04 12:17:53 -0700 | |
---|---|---|
committer | 2015-08-04 15:44:42 -0700 | |
commit | 9ca8dbcc65cfc63d6f5ef3312a33184e1d726e00 (patch) | |
tree | 1c9cafbcd35f783a87880a10f85d1a060db1a563 /kernel/arch/metag/mm/l2cache.c | |
parent | 98260f3884f4a202f9ca5eabed40b1354c489b29 (diff) |
Add the rt linux 4.1.3-rt3 as base
Import the rt linux 4.1.3-rt3 as OPNFV kvm base.
It's from git://git.kernel.org/pub/scm/linux/kernel/git/rt/linux-rt-devel.git linux-4.1.y-rt and
the base is:
commit 0917f823c59692d751951bf5ea699a2d1e2f26a2
Author: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
Date: Sat Jul 25 12:13:34 2015 +0200
Prepare v4.1.3-rt3
Signed-off-by: Sebastian Andrzej Siewior <bigeasy@linutronix.de>
We lose all the git history this way and it's not good. We
should apply another opnfv project repo in future.
Change-Id: I87543d81c9df70d99c5001fbdf646b202c19f423
Signed-off-by: Yunhong Jiang <yunhong.jiang@intel.com>
Diffstat (limited to 'kernel/arch/metag/mm/l2cache.c')
-rw-r--r-- | kernel/arch/metag/mm/l2cache.c | 192 |
1 files changed, 192 insertions, 0 deletions
diff --git a/kernel/arch/metag/mm/l2cache.c b/kernel/arch/metag/mm/l2cache.c new file mode 100644 index 000000000..c64ee615c --- /dev/null +++ b/kernel/arch/metag/mm/l2cache.c @@ -0,0 +1,192 @@ +#include <linux/init.h> +#include <linux/kernel.h> +#include <linux/delay.h> + +#include <asm/l2cache.h> +#include <asm/metag_isa.h> + +/* If non-0, then initialise the L2 cache */ +static int l2cache_init = 1; +/* If non-0, then initialise the L2 cache prefetch */ +static int l2cache_init_pf = 1; + +int l2c_pfenable; + +static volatile u32 l2c_testdata[16] __initdata __aligned(64); + +static int __init parse_l2cache(char *p) +{ + char *cp = p; + + if (get_option(&cp, &l2cache_init) != 1) { + pr_err("Bad l2cache parameter (%s)\n", p); + return 1; + } + return 0; +} +early_param("l2cache", parse_l2cache); + +static int __init parse_l2cache_pf(char *p) +{ + char *cp = p; + + if (get_option(&cp, &l2cache_init_pf) != 1) { + pr_err("Bad l2cache_pf parameter (%s)\n", p); + return 1; + } + return 0; +} +early_param("l2cache_pf", parse_l2cache_pf); + +static int __init meta_l2c_setup(void) +{ + /* + * If the L2 cache isn't even present, don't do anything, but say so in + * the log. + */ + if (!meta_l2c_is_present()) { + pr_info("L2 Cache: Not present\n"); + return 0; + } + + /* + * Check whether the line size is recognised. + */ + if (!meta_l2c_linesize()) { + pr_warn_once("L2 Cache: unknown line size id (config=0x%08x)\n", + meta_l2c_config()); + } + + /* + * Initialise state. + */ + l2c_pfenable = _meta_l2c_pf_is_enabled(); + + /* + * Enable the L2 cache and print to log whether it was already enabled + * by the bootloader. + */ + if (l2cache_init) { + pr_info("L2 Cache: Enabling... "); + if (meta_l2c_enable()) + pr_cont("already enabled\n"); + else + pr_cont("done\n"); + } else { + pr_info("L2 Cache: Not enabling\n"); + } + + /* + * Enable L2 cache prefetch. + */ + if (l2cache_init_pf) { + pr_info("L2 Cache: Enabling prefetch... "); + if (meta_l2c_pf_enable(1)) + pr_cont("already enabled\n"); + else + pr_cont("done\n"); + } else { + pr_info("L2 Cache: Not enabling prefetch\n"); + } + + return 0; +} +core_initcall(meta_l2c_setup); + +int meta_l2c_disable(void) +{ + unsigned long flags; + int en; + + if (!meta_l2c_is_present()) + return 1; + + /* + * Prevent other threads writing during the writeback, otherwise the + * writes will get "lost" when the L2 is disabled. + */ + __global_lock2(flags); + en = meta_l2c_is_enabled(); + if (likely(en)) { + _meta_l2c_pf_enable(0); + wr_fence(); + _meta_l2c_purge(); + _meta_l2c_enable(0); + } + __global_unlock2(flags); + + return !en; +} + +int meta_l2c_enable(void) +{ + unsigned long flags; + int en; + + if (!meta_l2c_is_present()) + return 0; + + /* + * Init (clearing the L2) can happen while the L2 is disabled, so other + * threads are safe to continue executing, however we must not init the + * cache if it's already enabled (dirty lines would be discarded), so + * this operation should still be atomic with other threads. + */ + __global_lock1(flags); + en = meta_l2c_is_enabled(); + if (likely(!en)) { + _meta_l2c_init(); + _meta_l2c_enable(1); + _meta_l2c_pf_enable(l2c_pfenable); + } + __global_unlock1(flags); + + return en; +} + +int meta_l2c_pf_enable(int pfenable) +{ + unsigned long flags; + int en = l2c_pfenable; + + if (!meta_l2c_is_present()) + return 0; + + /* + * We read modify write the enable register, so this operation must be + * atomic with other threads. + */ + __global_lock1(flags); + en = l2c_pfenable; + l2c_pfenable = pfenable; + if (meta_l2c_is_enabled()) + _meta_l2c_pf_enable(pfenable); + __global_unlock1(flags); + + return en; +} + +int meta_l2c_flush(void) +{ + unsigned long flags; + int en; + + /* + * Prevent other threads writing during the writeback. This also + * involves read modify writes. + */ + __global_lock2(flags); + en = meta_l2c_is_enabled(); + if (likely(en)) { + _meta_l2c_pf_enable(0); + wr_fence(); + _meta_l2c_purge(); + _meta_l2c_enable(0); + _meta_l2c_init(); + _meta_l2c_enable(1); + _meta_l2c_pf_enable(l2c_pfenable); + } + __global_unlock2(flags); + + return !en; +} |