From: William Lee Irwin III It fixes the fork-idle consolidation. During that consolidation, the generic code was made to pass a pointer to on-stack pt_regs that had been memset() to 0. ia64, however, requires a NULL pt_regs pointer argument and dispatches on that in its copy_thread() function to do SMP trampoline-specific RSE -related setup. Passing pointers to zeroed pt_regs resulted in SMP wakeup -time deadlocks and exceptions. Signed-off-by: Andrew Morton --- 25-akpm/arch/ia64/kernel/smpboot.c | 5 +++++ 25-akpm/kernel/fork.c | 9 +++++++-- 2 files changed, 12 insertions(+), 2 deletions(-) diff -puN arch/ia64/kernel/smpboot.c~kill-clone_idletask-fix arch/ia64/kernel/smpboot.c --- 25/arch/ia64/kernel/smpboot.c~kill-clone_idletask-fix 2004-08-15 13:58:20.595928160 -0700 +++ 25-akpm/arch/ia64/kernel/smpboot.c 2004-08-15 13:58:20.601927248 -0700 @@ -356,6 +356,11 @@ start_secondary (void *unused) return cpu_idle(); } +struct pt_regs * __init idle_regs(struct pt_regs *regs) +{ + return NULL; +} + struct create_idle { struct task_struct *idle; struct completion done; diff -puN kernel/fork.c~kill-clone_idletask-fix kernel/fork.c --- 25/kernel/fork.c~kill-clone_idletask-fix 2004-08-15 13:58:20.597927856 -0700 +++ 25-akpm/kernel/fork.c 2004-08-15 13:58:20.602927096 -0700 @@ -1190,13 +1190,18 @@ bad_fork_free: goto fork_out; } +struct pt_regs * __init __attribute__((weak)) idle_regs(struct pt_regs *regs) +{ + memset(regs, 0, sizeof(struct pt_regs)); + return regs; +} + task_t * __init fork_idle(int cpu) { task_t *task; struct pt_regs regs; - memset(®s, 0, sizeof(struct pt_regs)); - task = copy_process(CLONE_VM, 0, ®s, 0, NULL, NULL, 0); + task = copy_process(CLONE_VM, 0, idle_regs(®s), 0, NULL, NULL, 0); if (!task) return ERR_PTR(-ENOMEM); init_idle(task, cpu); _