From: Roman Zippel <zippel@linux-m68k.org>

These four patches reduce the role of thread_info and makes the thread stack
more visible.  The main change of these patches is the change from the
thread_info to the stack field in task_struct to abstract away the direct
access to the thread_info.  I have been very careful with these changes (e.g. 
I manually reverted the patches and compared the result to prevent typos), so
I'm quite sure these patches don't introduce any new problems.


This patch:

This adds a new field stack to task_struct.  Its value is identical to
thread_info, but on m68k it doesn't point to the thread_info.  This allows to
convert direct accesses to the thread_info field to either convert to using
the stack field, end_of_stack() or task_thread_info().

Signed-off-by: Roman Zippel <zippel@linux-m68k.org>
Signed-off-by: Andrew Morton <akpm@osdl.org>
---

 include/asm-m68k/thread_info.h |    4 ++--
 include/linux/init_task.h      |    1 +
 include/linux/sched.h          |    5 +++--
 kernel/fork.c                  |    1 +
 4 files changed, 7 insertions(+), 4 deletions(-)

diff -puN include/asm-m68k/thread_info.h~add-stack-field-to-task_struct include/asm-m68k/thread_info.h
--- devel/include/asm-m68k/thread_info.h~add-stack-field-to-task_struct	2005-09-07 20:11:05.000000000 -0700
+++ devel-akpm/include/asm-m68k/thread_info.h	2005-09-07 20:11:05.000000000 -0700
@@ -42,11 +42,11 @@ struct thread_info {
 #define __HAVE_THREAD_FUNCTIONS
 
 #define setup_thread_stack(p, org) ({			\
-	*(struct task_struct **)(p)->thread_info = (p);	\
+	*(struct task_struct **)(p)->stack = (p);	\
 	task_thread_info(p)->task = (p);		\
 })
 
-#define end_of_stack(p) ((unsigned long *)(p)->thread_info + 1)
+#define end_of_stack(p) ((unsigned long *)(p)->stack + 1)
 
 /* entry.S relies on these definitions!
  * bits 0-7 are tested at every exception exit
diff -puN include/linux/init_task.h~add-stack-field-to-task_struct include/linux/init_task.h
--- devel/include/linux/init_task.h~add-stack-field-to-task_struct	2005-09-07 20:11:05.000000000 -0700
+++ devel-akpm/include/linux/init_task.h	2005-09-07 20:11:05.000000000 -0700
@@ -71,6 +71,7 @@ extern struct group_info init_groups;
 {									\
 	.state		= 0,						\
 	.thread_info	= &init_thread_info,				\
+	.stack		= &init_stack,					\
 	.usage		= ATOMIC_INIT(2),				\
 	.flags		= 0,						\
 	.lock_depth	= -1,						\
diff -puN include/linux/sched.h~add-stack-field-to-task_struct include/linux/sched.h
--- devel/include/linux/sched.h~add-stack-field-to-task_struct	2005-09-07 20:11:05.000000000 -0700
+++ devel-akpm/include/linux/sched.h	2005-09-07 20:11:05.000000000 -0700
@@ -635,6 +635,7 @@ struct mempolicy;
 struct task_struct {
 	volatile long state;	/* -1 unrunnable, 0 runnable, >0 stopped */
 	struct thread_info *thread_info;
+	void *stack;
 	atomic_t usage;
 	unsigned long flags;	/* per process flags, defined below */
 	unsigned long ptrace;
@@ -1184,7 +1185,7 @@ static inline void task_unlock(struct ta
 
 #ifndef __HAVE_THREAD_FUNCTIONS
 
-#define task_thread_info(task) (task)->thread_info
+#define task_thread_info(task) ((struct thread_info *)(task)->stack)
 
 static inline void setup_thread_stack(struct task_struct *p, struct task_struct *org)
 {
@@ -1194,7 +1195,7 @@ static inline void setup_thread_stack(st
 
 static inline unsigned long *end_of_stack(struct task_struct *p)
 {
-	return (unsigned long *)(p->thread_info + 1);
+	return (unsigned long *)(task_thread_info(p) + 1);
 }
 
 #endif
diff -puN kernel/fork.c~add-stack-field-to-task_struct kernel/fork.c
--- devel/kernel/fork.c~add-stack-field-to-task_struct	2005-09-07 20:11:05.000000000 -0700
+++ devel-akpm/kernel/fork.c	2005-09-07 20:11:05.000000000 -0700
@@ -171,6 +171,7 @@ static struct task_struct *dup_task_stru
 
 	*tsk = *orig;
 	tsk->thread_info = ti;
+	tsk->stack = ti;
 	setup_thread_stack(tsk, orig);
 
 	/* One for us, one for whoever does the "release_task()" (usually parent) */
_