From e761b7725234276a802322549cee5255305a0930 Mon Sep 17 00:00:00 2001 From: Max Krasnyansky Date: Tue, 15 Jul 2008 04:43:49 -0700 Subject: cpu hotplug, sched: Introduce cpu_active_map and redo sched domain managment (take 2) This is based on Linus' idea of creating cpu_active_map that prevents scheduler load balancer from migrating tasks to the cpu that is going down. It allows us to simplify domain management code and avoid unecessary domain rebuilds during cpu hotplug event handling. Please ignore the cpusets part for now. It needs some more work in order to avoid crazy lock nesting. Although I did simplfy and unify domain reinitialization logic. We now simply call partition_sched_domains() in all the cases. This means that we're using exact same code paths as in cpusets case and hence the test below cover cpusets too. Cpuset changes to make rebuild_sched_domains() callable from various contexts are in the separate patch (right next after this one). This not only boots but also easily handles while true; do make clean; make -j 8; done and while true; do on-off-cpu 1; done at the same time. (on-off-cpu 1 simple does echo 0/1 > /sys/.../cpu1/online thing). Suprisingly the box (dual-core Core2) is quite usable. In fact I'm typing this on right now in gnome-terminal and things are moving just fine. Also this is running with most of the debug features enabled (lockdep, mutex, etc) no BUG_ONs or lockdep complaints so far. I believe I addressed all of the Dmitry's comments for original Linus' version. I changed both fair and rt balancer to mask out non-active cpus. And replaced cpu_is_offline() with !cpu_active() in the main scheduler code where it made sense (to me). Signed-off-by: Max Krasnyanskiy Acked-by: Linus Torvalds Acked-by: Peter Zijlstra Acked-by: Gregory Haskins Cc: dmitry.adamushko@gmail.com Cc: pj@sgi.com Signed-off-by: Ingo Molnar --- init/main.c | 7 +++++++ 1 file changed, 7 insertions(+) (limited to 'init/main.c') diff --git a/init/main.c b/init/main.c index edeace036fd..dd25259530e 100644 --- a/init/main.c +++ b/init/main.c @@ -415,6 +415,13 @@ static void __init smp_init(void) { unsigned int cpu; + /* + * Set up the current CPU as possible to migrate to. + * The other ones will be done by cpu_up/cpu_down() + */ + cpu = smp_processor_id(); + cpu_set(cpu, cpu_active_map); + /* FIXME: This should be done in userspace --RR */ for_each_present_cpu(cpu) { if (num_online_cpus() >= setup_max_cpus) -- cgit v1.2.3 From fb6624ebd912e3d6907ca6490248e73368223da9 Mon Sep 17 00:00:00 2001 From: Geert Uytterhoeven Date: Thu, 17 Jul 2008 21:16:36 +0200 Subject: initrd: Fix virtual/physical mix-up in overwrite test On recent kernels, I get the following error when using an initrd: | initrd overwritten (0x00b78000 < 0x07668000) - disabling it. My Amiga 4000 has 12 MiB of RAM at physical address 0x07400000 (virtual 0x00000000). The initrd is located at the end of RAM: 0x00b78000 - 0x00c00000 (virtual). The overwrite test compares the (virtual) initrd location to the (physical) first available memory location, which fails. This patch converts initrd_start to a page frame number, so it can safely be compared with min_low_pfn. Before the introduction of discontiguous memory support on m68k (12d810c1b8c2b913d48e629e2b5c01d105029839), min_low_pfn was just left untouched by the m68k-specific code (zero, I guess), and everything worked fine. Signed-off-by: Geert Uytterhoeven Signed-off-by: Linus Torvalds --- init/main.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) (limited to 'init/main.c') diff --git a/init/main.c b/init/main.c index edeace036fd..756eca4b821 100644 --- a/init/main.c +++ b/init/main.c @@ -630,9 +630,10 @@ asmlinkage void __init start_kernel(void) #ifdef CONFIG_BLK_DEV_INITRD if (initrd_start && !initrd_below_start_ok && - initrd_start < min_low_pfn << PAGE_SHIFT) { + page_to_pfn(virt_to_page(initrd_start)) < min_low_pfn) { printk(KERN_CRIT "initrd overwritten (0x%08lx < 0x%08lx) - " - "disabling it.\n",initrd_start,min_low_pfn << PAGE_SHIFT); + "disabling it.\n", + page_to_pfn(virt_to_page(initrd_start)), min_low_pfn); initrd_start = 0; } #endif -- cgit v1.2.3 From 3ae4eed34be0177a8e003411a84e4ee212adbced Mon Sep 17 00:00:00 2001 From: Adrian Bunk Date: Fri, 25 Jul 2008 01:48:34 -0700 Subject: proper pid{hash,map}_init() prototypes This patch adds proper prototypes for pid{hash,map}_init() in include/linux/pid_namespace.h Signed-off-by: Adrian Bunk Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- init/main.c | 2 -- 1 file changed, 2 deletions(-) (limited to 'init/main.c') diff --git a/init/main.c b/init/main.c index 2769dc031c6..0604cbcaf1e 100644 --- a/init/main.c +++ b/init/main.c @@ -87,8 +87,6 @@ extern void init_IRQ(void); extern void fork_init(unsigned long); extern void mca_init(void); extern void sbus_init(void); -extern void pidhash_init(void); -extern void pidmap_init(void); extern void prio_tree_init(void); extern void radix_tree_init(void); extern void free_initmem(void); -- cgit v1.2.3 From c2147a5092cfe13dbf3210e54e8a622015edeecc Mon Sep 17 00:00:00 2001 From: Eduard - Gabriel Munteanu Date: Fri, 25 Jul 2008 19:45:11 -0700 Subject: Better interface for hooking early initcalls Added early initcall (pre-SMP) support, using an identical interface to that of regular initcalls. Functions called from do_pre_smp_initcalls() could be converted to use this cleaner interface. This is required by CPU hotplug, because early users have to register notifiers before going SMP. One such CPU hotplug user is the relay interface with buffer-only channels, which needs to register such a notifier, to be usable in early code. This in turn is used by kmemtrace. Signed-off-by: Eduard - Gabriel Munteanu Cc: Tom Zanussi Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- init/main.c | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-) (limited to 'init/main.c') diff --git a/init/main.c b/init/main.c index 0604cbcaf1e..b6fec08dbbe 100644 --- a/init/main.c +++ b/init/main.c @@ -743,13 +743,13 @@ static void __init do_one_initcall(initcall_t fn) } -extern initcall_t __initcall_start[], __initcall_end[]; +extern initcall_t __initcall_start[], __initcall_end[], __early_initcall_end[]; static void __init do_initcalls(void) { initcall_t *call; - for (call = __initcall_start; call < __initcall_end; call++) + for (call = __early_initcall_end; call < __initcall_end; call++) do_one_initcall(*call); /* Make sure there is no pending stuff from the initcall sequence */ @@ -783,6 +783,14 @@ static int __init nosoftlockup_setup(char *str) } __setup("nosoftlockup", nosoftlockup_setup); +static void __init __do_pre_smp_initcalls(void) +{ + initcall_t *call; + + for (call = __initcall_start; call < __early_initcall_end; call++) + do_one_initcall(*call); +} + static void __init do_pre_smp_initcalls(void) { extern int spawn_ksoftirqd(void); @@ -865,6 +873,7 @@ static int __init kernel_init(void * unused) smp_prepare_cpus(setup_max_cpus); + __do_pre_smp_initcalls(); do_pre_smp_initcalls(); smp_init(); -- cgit v1.2.3 From 7babe8db99d305340cf4828ce1f5a1481d5622ef Mon Sep 17 00:00:00 2001 From: Eduard - Gabriel Munteanu Date: Fri, 25 Jul 2008 19:45:11 -0700 Subject: Full conversion to early_initcall() interface, remove old interface A previous patch added the early_initcall(), to allow a cleaner hooking of pre-SMP initcalls. Now we remove the older interface, converting all existing users to the new one. [akpm@linux-foundation.org: cleanups] [akpm@linux-foundation.org: build fix] [kosaki.motohiro@jp.fujitsu.com: warning fix] [kosaki.motohiro@jp.fujitsu.com: warning fix] Signed-off-by: Eduard - Gabriel Munteanu Cc: Tom Zanussi Signed-off-by: KOSAKI Motohiro Signed-off-by: Andrew Morton Signed-off-by: Linus Torvalds --- init/main.c | 23 +---------------------- 1 file changed, 1 insertion(+), 22 deletions(-) (limited to 'init/main.c') diff --git a/init/main.c b/init/main.c index b6fec08dbbe..20fdc9884b7 100644 --- a/init/main.c +++ b/init/main.c @@ -774,16 +774,7 @@ static void __init do_basic_setup(void) do_initcalls(); } -static int __initdata nosoftlockup; - -static int __init nosoftlockup_setup(char *str) -{ - nosoftlockup = 1; - return 1; -} -__setup("nosoftlockup", nosoftlockup_setup); - -static void __init __do_pre_smp_initcalls(void) +static void __init do_pre_smp_initcalls(void) { initcall_t *call; @@ -791,17 +782,6 @@ static void __init __do_pre_smp_initcalls(void) do_one_initcall(*call); } -static void __init do_pre_smp_initcalls(void) -{ - extern int spawn_ksoftirqd(void); - - init_call_single_data(); - migration_init(); - spawn_ksoftirqd(); - if (!nosoftlockup) - spawn_softlockup_task(); -} - static void run_init_process(char *init_filename) { argv_init[0] = init_filename; @@ -873,7 +853,6 @@ static int __init kernel_init(void * unused) smp_prepare_cpus(setup_max_cpus); - __do_pre_smp_initcalls(); do_pre_smp_initcalls(); smp_init(); -- cgit v1.2.3