From: Roland McGrath <roland@redhat.com>

This patch moves all the fields relating to job control from task_struct to
signal_struct, so that all this info is properly per-process rather than
being per-thread.

I have done basic testing that nothing obviously breaks running with this
patch.  I have also compiled a "make allyesconfig" kernel successfully,
though not tried to run that (if it's even possible to boot such a beast).
DESC
s390 fix for move-job-control-stuff-tosignal_struct.patch
EDESC
From: Arnd Bergmann <arnd@arndb.de>

These must have slipped through in the job control rework and are needed
for building 2.6.4-mm1 in some configurations.
DESC
Subject: [PATCH] 2.6.4-mm1 for ia64
EDESC
From: John Hawkes <hawkes@babylon.engr.sgi.com>

The following patches allow 2.6.4-mm1 to build and boot on an ia64 sn.

-- John Hawkes

DESC
move-job-control-stuff-tosignal_struct-sparc64-fix
EDESC
From: Marc-Christian Petersen <m.c.p@wolk-project.de>



---

 25-akpm/arch/ia64/kernel/unaligned.c    |    2 
 25-akpm/arch/sparc64/solaris/misc.c     |    2 
 25-akpm/drivers/char/n_tty.c            |    3 
 25-akpm/drivers/char/rocket.c           |    2 
 25-akpm/drivers/char/sx.c               |    2 
 25-akpm/drivers/char/tty_io.c           |  116 +++++++++++++-------------------
 25-akpm/drivers/char/vt.c               |    2 
 25-akpm/drivers/char/vt_ioctl.c         |    3 
 25-akpm/drivers/net/slip.c              |    2 
 25-akpm/drivers/s390/char/keyboard.c    |    2 
 25-akpm/fs/binfmt_elf.c                 |    4 -
 25-akpm/fs/compat_ioctl.c               |    2 
 25-akpm/fs/dquot.c                      |   10 +-
 25-akpm/fs/exec.c                       |    5 +
 25-akpm/fs/open.c                       |    2 
 25-akpm/fs/proc/array.c                 |   22 +++---
 25-akpm/include/linux/sched.h           |   17 ++--
 25-akpm/kernel/acct.c                   |    2 
 25-akpm/kernel/exit.c                   |   22 +++---
 25-akpm/kernel/fork.c                   |   10 +-
 25-akpm/kernel/pid.c                    |    8 +-
 25-akpm/kernel/signal.c                 |    5 -
 25-akpm/kernel/sys.c                    |   18 ++--
 25-akpm/net/ipv4/netfilter/ipt_owner.c  |    2 
 25-akpm/net/ipv6/netfilter/ip6t_owner.c |    2 
 25 files changed, 132 insertions(+), 135 deletions(-)

diff -puN drivers/char/n_tty.c~move-job-control-stuff-tosignal_struct drivers/char/n_tty.c
--- 25/drivers/char/n_tty.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:58.998274672 -0800
+++ 25-akpm/drivers/char/n_tty.c	2004-03-29 20:26:59.038268592 -0800
@@ -999,7 +999,8 @@ do_it_again:
 	/* NOTE: not yet done after every sleep pending a thorough
 	   check of the logic of this change. -- jlc */
 	/* don't stop on /dev/console */
-	if (file->f_op->write != redirected_tty_write && current->tty == tty) {
+	if (file->f_op->write != redirected_tty_write &&
+	    current->signal->tty == tty) {
 		if (tty->pgrp <= 0)
 			printk("read_chan: tty->pgrp <= 0!\n");
 		else if (process_group(current) != tty->pgrp) {
diff -puN drivers/char/rocket.c~move-job-control-stuff-tosignal_struct drivers/char/rocket.c
--- 25/drivers/char/rocket.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.000274368 -0800
+++ 25-akpm/drivers/char/rocket.c	2004-03-29 20:26:59.040268288 -0800
@@ -953,7 +953,7 @@ static int rp_open(struct tty_struct *tt
 	/*
 	 * Info->count is now 1; so it's safe to sleep now.
 	 */
-	info->session = current->session;
+	info->session = current->signal->session;
 	info->pgrp = process_group(current);
 
 	if ((info->flags & ROCKET_INITIALIZED) == 0) {
diff -puN drivers/char/tty_io.c~move-job-control-stuff-tosignal_struct drivers/char/tty_io.c
--- 25/drivers/char/tty_io.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.002274064 -0800
+++ 25-akpm/drivers/char/tty_io.c	2004-03-29 20:26:59.054266160 -0800
@@ -321,7 +321,7 @@ struct tty_driver *get_tty_driver(dev_t 
  */
 int tty_check_change(struct tty_struct * tty)
 {
-	if (current->tty != tty)
+	if (current->signal->tty != tty)
 		return 0;
 	if (tty->pgrp <= 0) {
 		printk(KERN_WARNING "tty_check_change: tty->pgrp <= 0!\n");
@@ -486,17 +486,14 @@ void do_tty_hangup(void *data)
 	if (tty->session > 0) {
 		struct list_head *l;
 		for_each_task_pid(tty->session, PIDTYPE_SID, p, l, pid) {
-			task_t *task = p;
-			do {
-				if (task->tty == tty)
-					task->tty = NULL;
-				if (task->leader) {
-					send_group_sig_info(SIGHUP, SEND_SIG_PRIV, task);
-					send_group_sig_info(SIGCONT, SEND_SIG_PRIV, task);
-				}
-			} while_each_thread(p, task);
+			if (p->signal->tty == tty)
+				p->signal->tty = NULL;
+			if (!p->signal->leader)
+				continue;
+			send_group_sig_info(SIGHUP, SEND_SIG_PRIV, p);
+			send_group_sig_info(SIGCONT, SEND_SIG_PRIV, p);
 			if (tty->pgrp > 0)
-				p->tty_old_pgrp = tty->pgrp;
+				p->signal->tty_old_pgrp = tty->pgrp;
 		}
 	}
 	read_unlock(&tasklist_lock);
@@ -575,15 +572,15 @@ void disassociate_ctty(int on_exit)
 
 	lock_kernel();
 
-	tty = current->tty;
+	tty = current->signal->tty;
 	if (tty) {
 		tty_pgrp = tty->pgrp;
 		if (on_exit && tty->driver->type != TTY_DRIVER_TYPE_PTY)
 			tty_vhangup(tty);
 	} else {
-		if (current->tty_old_pgrp) {
-			kill_pg(current->tty_old_pgrp, SIGHUP, on_exit);
-			kill_pg(current->tty_old_pgrp, SIGCONT, on_exit);
+		if (current->signal->tty_old_pgrp) {
+			kill_pg(current->signal->tty_old_pgrp, SIGHUP, on_exit);
+			kill_pg(current->signal->tty_old_pgrp, SIGCONT, on_exit);
 		}
 		unlock_kernel();	
 		return;
@@ -594,17 +591,13 @@ void disassociate_ctty(int on_exit)
 			kill_pg(tty_pgrp, SIGCONT, on_exit);
 	}
 
-	current->tty_old_pgrp = 0;
+	current->signal->tty_old_pgrp = 0;
 	tty->session = 0;
 	tty->pgrp = -1;
 
 	read_lock(&tasklist_lock);
-	for_each_task_pid(current->session, PIDTYPE_SID, p, l, pid) {
-		task_t *task = p;
-		do {
-			task->tty = NULL;
-		} while_each_thread(p, task);
-	}
+	for_each_task_pid(current->signal->session, PIDTYPE_SID, p, l, pid)
+		p->signal->tty = NULL;
 	read_unlock(&tasklist_lock);
 	unlock_kernel();
 }
@@ -1257,20 +1250,11 @@ static void release_dev(struct file * fi
 		struct pid *pid;
 
 		read_lock(&tasklist_lock);
-		for_each_task_pid(tty->session, PIDTYPE_SID, p, l, pid) {
-			task_t *task = p;
-			do {
-				task->tty = NULL;
-			} while_each_thread(p, task);
-		}
-		if (o_tty) {
-			for_each_task_pid(o_tty->session, PIDTYPE_SID, p,l, pid) {
-				task_t *task = p;
-				do {
-					task->tty = NULL;
-				} while_each_thread(p, task);
-			}
-		}
+		for_each_task_pid(tty->session, PIDTYPE_SID, p, l, pid)
+			p->signal->tty = NULL;
+		if (o_tty)
+			for_each_task_pid(o_tty->session, PIDTYPE_SID, p,l, pid)
+				p->signal->tty = NULL;
 		read_unlock(&tasklist_lock);
 	}
 
@@ -1341,10 +1325,10 @@ static int tty_open(struct inode * inode
 retry_open:
 	noctty = filp->f_flags & O_NOCTTY;
 	if (device == MKDEV(TTYAUX_MAJOR,0)) {
-		if (!current->tty)
+		if (!current->signal->tty)
 			return -ENXIO;
-		driver = current->tty->driver;
-		index = current->tty->index;
+		driver = current->signal->tty->driver;
+		index = current->signal->tty->index;
 		filp->f_flags |= O_NONBLOCK; /* Don't let /dev/tty block */
 		/* noctty = 1; */
 		goto got_driver;
@@ -1445,14 +1429,14 @@ got_driver:
 		goto retry_open;
 	}
 	if (!noctty &&
-	    current->leader &&
-	    !current->tty &&
+	    current->signal->leader &&
+	    !current->signal->tty &&
 	    tty->session == 0) {
 	    	task_lock(current);
-		current->tty = tty;
+		current->signal->tty = tty;
 		task_unlock(current);
-		current->tty_old_pgrp = 0;
-		tty->session = current->session;
+		current->signal->tty_old_pgrp = 0;
+		tty->session = current->signal->session;
 		tty->pgrp = process_group(current);
 	}
 	return 0;
@@ -1510,7 +1494,7 @@ static int tiocsti(struct tty_struct *tt
 {
 	char ch, mbz = 0;
 
-	if ((current->tty != tty) && !capable(CAP_SYS_ADMIN))
+	if ((current->signal->tty != tty) && !capable(CAP_SYS_ADMIN))
 		return -EPERM;
 	if (get_user(ch, arg))
 		return -EFAULT;
@@ -1601,14 +1585,14 @@ static int tiocsctty(struct tty_struct *
 	struct pid *pid;
 	task_t *p;
 
-	if (current->leader &&
-	    (current->session == tty->session))
+	if (current->signal->leader &&
+	    (current->signal->session == tty->session))
 		return 0;
 	/*
 	 * The process must be a session leader and
 	 * not have a controlling tty already.
 	 */
-	if (!current->leader || current->tty)
+	if (!current->signal->leader || current->signal->tty)
 		return -EPERM;
 	if (tty->session > 0) {
 		/*
@@ -1621,21 +1605,17 @@ static int tiocsctty(struct tty_struct *
 			 */
 
 			read_lock(&tasklist_lock);
-			for_each_task_pid(tty->session, PIDTYPE_SID, p, l, pid) {
-				task_t *task = p;
-				do {
-					task->tty = NULL;
-				} while_each_thread(p, task);
-			}
+			for_each_task_pid(tty->session, PIDTYPE_SID, p, l, pid)
+				p->signal->tty = NULL;
 			read_unlock(&tasklist_lock);
 		} else
 			return -EPERM;
 	}
 	task_lock(current);
-	current->tty = tty;
+	current->signal->tty = tty;
 	task_unlock(current);
-	current->tty_old_pgrp = 0;
-	tty->session = current->session;
+	current->signal->tty_old_pgrp = 0;
+	tty->session = current->signal->session;
 	tty->pgrp = process_group(current);
 	return 0;
 }
@@ -1646,7 +1626,7 @@ static int tiocgpgrp(struct tty_struct *
 	 * (tty == real_tty) is a cheap way of
 	 * testing if the tty is NOT a master pty.
 	 */
-	if (tty == real_tty && current->tty != real_tty)
+	if (tty == real_tty && current->signal->tty != real_tty)
 		return -ENOTTY;
 	return put_user(real_tty->pgrp, arg);
 }
@@ -1660,15 +1640,15 @@ static int tiocspgrp(struct tty_struct *
 		return -ENOTTY;
 	if (retval)
 		return retval;
-	if (!current->tty ||
-	    (current->tty != real_tty) ||
-	    (real_tty->session != current->session))
+	if (!current->signal->tty ||
+	    (current->signal->tty != real_tty) ||
+	    (real_tty->session != current->signal->session))
 		return -ENOTTY;
 	if (get_user(pgrp, (pid_t *) arg))
 		return -EFAULT;
 	if (pgrp < 0)
 		return -EINVAL;
-	if (session_of_pgrp(pgrp) != current->session)
+	if (session_of_pgrp(pgrp) != current->signal->session)
 		return -EPERM;
 	real_tty->pgrp = pgrp;
 	return 0;
@@ -1680,7 +1660,7 @@ static int tiocgsid(struct tty_struct *t
 	 * (tty == real_tty) is a cheap way of
 	 * testing if the tty is NOT a master pty.
 	*/
-	if (tty == real_tty && current->tty != real_tty)
+	if (tty == real_tty && current->signal->tty != real_tty)
 		return -ENOTTY;
 	if (real_tty->session <= 0)
 		return -ENOTTY;
@@ -1838,12 +1818,12 @@ int tty_ioctl(struct inode * inode, stru
 			clear_bit(TTY_EXCLUSIVE, &tty->flags);
 			return 0;
 		case TIOCNOTTY:
-			if (current->tty != tty)
+			if (current->signal->tty != tty)
 				return -ENOTTY;
-			if (current->leader)
+			if (current->signal->leader)
 				disassociate_ctty(0);
 			task_lock(current);
-			current->tty = NULL;
+			current->signal->tty = NULL;
 			task_unlock(current);
 			return 0;
 		case TIOCSCTTY:
@@ -1947,9 +1927,9 @@ static void __do_SAK(void *arg)
 		tty->driver->flush_buffer(tty);
 	read_lock(&tasklist_lock);
 	for_each_task_pid(session, PIDTYPE_SID, p, l, pid) {
-		if (p->tty == tty || session > 0) {
+		if (p->signal->tty == tty || session > 0) {
 			printk(KERN_NOTICE "SAK: killed process %d"
-			    " (%s): p->session==tty->session\n",
+			    " (%s): p->signal->session==tty->session\n",
 			    p->pid, p->comm);
 			send_sig(SIGKILL, p, 1);
 			continue;
diff -puN drivers/char/vt.c~move-job-control-stuff-tosignal_struct drivers/char/vt.c
--- 25/drivers/char/vt.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.004273760 -0800
+++ 25-akpm/drivers/char/vt.c	2004-03-29 20:26:59.056265856 -0800
@@ -2278,7 +2278,7 @@ int tioclinux(struct tty_struct *tty, un
 
 	if (tty->driver->type != TTY_DRIVER_TYPE_CONSOLE)
 		return -EINVAL;
-	if (current->tty != tty && !capable(CAP_SYS_ADMIN))
+	if (current->signal->tty != tty && !capable(CAP_SYS_ADMIN))
 		return -EPERM;
 	if (get_user(type, (char *)arg))
 		return -EFAULT;
diff -puN drivers/char/vt_ioctl.c~move-job-control-stuff-tosignal_struct drivers/char/vt_ioctl.c
--- 25/drivers/char/vt_ioctl.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.006273456 -0800
+++ 25-akpm/drivers/char/vt_ioctl.c	2004-03-29 20:26:59.058265552 -0800
@@ -382,7 +382,7 @@ int vt_ioctl(struct tty_struct *tty, str
 	 * to be the owner of the tty, or have CAP_SYS_TTY_CONFIG.
 	 */
 	perm = 0;
-	if (current->tty == tty || capable(CAP_SYS_TTY_CONFIG))
+	if (current->signal->tty == tty || capable(CAP_SYS_TTY_CONFIG))
 		perm = 1;
  
 	kbd = kbd_table + console;
@@ -1221,4 +1221,3 @@ void change_console(unsigned int new_con
 
 	complete_change_console(new_console);
 }
-
diff -puN drivers/net/slip.c~move-job-control-stuff-tosignal_struct drivers/net/slip.c
--- 25/drivers/net/slip.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.007273304 -0800
+++ 25-akpm/drivers/net/slip.c	2004-03-29 20:26:59.059265400 -0800
@@ -1307,7 +1307,7 @@ static int sl_ioctl(struct net_device *d
 		/* Resolve race condition, when ioctl'ing hanged up 
 		   and opened by another process device.
 		 */
-		if (sl->tty != current->tty && sl->pid != current->pid) {
+		if (sl->tty != current->signal->tty && sl->pid != current->pid) {
 			spin_unlock_bh(&sl->lock);
 			return -EPERM;
 		}
diff -puN fs/binfmt_elf.c~move-job-control-stuff-tosignal_struct fs/binfmt_elf.c
--- 25/fs/binfmt_elf.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.009273000 -0800
+++ 25-akpm/fs/binfmt_elf.c	2004-03-29 20:26:59.060265248 -0800
@@ -1129,7 +1129,7 @@ static void fill_prstatus(struct elf_prs
 	prstatus->pr_pid = p->pid;
 	prstatus->pr_ppid = p->parent->pid;
 	prstatus->pr_pgrp = process_group(p);
-	prstatus->pr_sid = p->session;
+	prstatus->pr_sid = p->signal->session;
 	jiffies_to_timeval(p->utime, &prstatus->pr_utime);
 	jiffies_to_timeval(p->stime, &prstatus->pr_stime);
 	jiffies_to_timeval(p->cutime, &prstatus->pr_cutime);
@@ -1157,7 +1157,7 @@ static void fill_psinfo(struct elf_prpsi
 	psinfo->pr_pid = p->pid;
 	psinfo->pr_ppid = p->parent->pid;
 	psinfo->pr_pgrp = process_group(p);
-	psinfo->pr_sid = p->session;
+	psinfo->pr_sid = p->signal->session;
 
 	i = p->state ? ffz(~p->state) + 1 : 0;
 	psinfo->pr_state = i;
diff -puN fs/dquot.c~move-job-control-stuff-tosignal_struct fs/dquot.c
--- 25/fs/dquot.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.010272848 -0800
+++ 25-akpm/fs/dquot.c	2004-03-29 20:26:59.061265096 -0800
@@ -771,12 +771,12 @@ static void print_warning(struct dquot *
 
 	if (!need_print_warning(dquot) || (flag && test_and_set_bit(flag, &dquot->dq_flags)))
 		return;
-	tty_write_message(current->tty, dquot->dq_sb->s_id);
+	tty_write_message(current->signal->tty, dquot->dq_sb->s_id);
 	if (warntype == ISOFTWARN || warntype == BSOFTWARN)
-		tty_write_message(current->tty, ": warning, ");
+		tty_write_message(current->signal->tty, ": warning, ");
 	else
-		tty_write_message(current->tty, ": write failed, ");
-	tty_write_message(current->tty, quotatypes[dquot->dq_type]);
+		tty_write_message(current->signal->tty, ": write failed, ");
+	tty_write_message(current->signal->tty, quotatypes[dquot->dq_type]);
 	switch (warntype) {
 		case IHARDWARN:
 			msg = " file limit reached.\n";
@@ -797,7 +797,7 @@ static void print_warning(struct dquot *
 			msg = " block quota exceeded.\n";
 			break;
 	}
-	tty_write_message(current->tty, msg);
+	tty_write_message(current->signal->tty, msg);
 }
 
 static inline void flush_warnings(struct dquot **dquots, char *warntype)
diff -puN fs/exec.c~move-job-control-stuff-tosignal_struct fs/exec.c
--- 25/fs/exec.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.012272544 -0800
+++ 25-akpm/fs/exec.c	2004-03-29 20:26:59.062264944 -0800
@@ -601,6 +601,11 @@ static inline int de_thread(struct task_
 		newsig->group_stop_count = 0;
 		newsig->curr_target = NULL;
 		init_sigpending(&newsig->shared_pending);
+
+		newsig->pgrp = oldsig->pgrp;
+		newsig->session = oldsig->session;
+		newsig->leader = oldsig->leader;
+		newsig->tty_old_pgrp = oldsig->tty_old_pgrp;
 	}
 
 	if (thread_group_empty(current))
diff -puN fs/open.c~move-job-control-stuff-tosignal_struct fs/open.c
--- 25/fs/open.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.013272392 -0800
+++ 25-akpm/fs/open.c	2004-03-29 20:26:59.063264792 -0800
@@ -1037,7 +1037,7 @@ EXPORT_SYMBOL(sys_close);
 asmlinkage long sys_vhangup(void)
 {
 	if (capable(CAP_SYS_TTY_CONFIG)) {
-		tty_vhangup(current->tty);
+		tty_vhangup(current->signal->tty);
 		return 0;
 	}
 	return -EPERM;
diff -puN fs/proc/array.c~move-job-control-stuff-tosignal_struct fs/proc/array.c
--- 25/fs/proc/array.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.015272088 -0800
+++ 25-akpm/fs/proc/array.c	2004-03-29 20:26:59.064264640 -0800
@@ -168,7 +168,7 @@ static inline char * task_state(struct t
 		p->pid && p->ptrace ? p->parent->pid : 0,
 		p->uid, p->euid, p->suid, p->fsuid,
 		p->gid, p->egid, p->sgid, p->fsgid);
-	read_unlock(&tasklist_lock);	
+	read_unlock(&tasklist_lock);
 	task_lock(p);
 	buffer += sprintf(buffer,
 		"FDSize:\t%d\n"
@@ -301,7 +301,7 @@ int proc_pid_stat(struct task_struct *ta
 	sigset_t sigign, sigcatch;
 	char state;
 	int res;
-	pid_t ppid;
+ 	pid_t ppid, pgid = -1, sid = -1;
 	int num_threads = 0;
 	struct mm_struct *mm;
 
@@ -311,10 +311,6 @@ int proc_pid_stat(struct task_struct *ta
 	mm = task->mm;
 	if(mm)
 		mm = mmgrab(mm);
-	if (task->tty) {
-		tty_pgrp = task->tty->pgrp;
-		tty_nr = new_encode_dev(tty_devnum(task->tty));
-	}
 	task_unlock(task);
 	if (mm) {
 		down_read(&mm->mmap_sem);
@@ -335,7 +331,15 @@ int proc_pid_stat(struct task_struct *ta
 		collect_sigign_sigcatch(task, &sigign, &sigcatch);
 		spin_unlock_irq(&task->sighand->siglock);
 	}
-	read_unlock(&tasklist_lock);		
+	if (task->signal) {
+		if (task->signal->tty) {
+			tty_pgrp = task->signal->tty->pgrp;
+			tty_nr = new_encode_dev(tty_devnum(task->signal->tty));
+		}
+		pgid = process_group(task);
+		sid = task->signal->session;
+	}
+	read_unlock(&tasklist_lock);
 
 	/* scale priority and nice values from timeslices to -20..20 */
 	/* to make it look like a "normal" Unix priority/nice value  */
@@ -352,8 +356,8 @@ int proc_pid_stat(struct task_struct *ta
 		task->comm,
 		state,
 		ppid,
-		process_group(task),
-		task->session,
+		pgid,
+		sid,
 		tty_nr,
 		tty_pgrp,
 		task->flags,
diff -puN include/linux/sched.h~move-job-control-stuff-tosignal_struct include/linux/sched.h
--- 25/include/linux/sched.h~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.016271936 -0800
+++ 25-akpm/include/linux/sched.h	2004-03-29 20:26:59.065264488 -0800
@@ -270,6 +270,15 @@ struct signal_struct {
 
 	/* thread group stop support, overloads group_exit_code too */
 	int			group_stop_count;
+
+	/* job control IDs */
+	pid_t pgrp;
+	pid_t tty_old_pgrp;
+	pid_t session;
+	/* boolean value for session group leader */
+	int leader;
+
+	struct tty_struct *tty; /* NULL if no tty */
 };
 
 /*
@@ -401,12 +410,7 @@ struct task_struct {
 	unsigned long personality;
 	int did_exec:1;
 	pid_t pid;
-	pid_t __pgrp;		/* Accessed via process_group() */
-	pid_t tty_old_pgrp;
-	pid_t session;
 	pid_t tgid;
-	/* boolean value for session group leader */
-	int leader;
 	/* 
 	 * pointers to (original) parent process, youngest child, younger sibling,
 	 * older sibling, respectively.  (p->father can be replaced with 
@@ -449,7 +453,6 @@ struct task_struct {
 	char comm[16];
 /* file system info */
 	int link_count, total_link_count;
-	struct tty_struct *tty; /* NULL if no tty */
 /* ipc stuff */
 	struct sysv_sem sysvsem;
 /* CPU-specific state of this task */
@@ -503,7 +506,7 @@ struct task_struct {
 
 static inline pid_t process_group(struct task_struct *tsk)
 {
-	return tsk->group_leader->__pgrp;
+	return tsk->signal->pgrp;
 }
 
 extern void __put_task_struct(struct task_struct *tsk);
diff -puN kernel/acct.c~move-job-control-stuff-tosignal_struct kernel/acct.c
--- 25/kernel/acct.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.017271784 -0800
+++ 25-akpm/kernel/acct.c	2004-03-29 20:26:59.065264488 -0800
@@ -347,7 +347,7 @@ static void do_acct_process(long exitcod
 	/* we really need to bite the bullet and change layout */
 	ac.ac_uid = current->uid;
 	ac.ac_gid = current->gid;
-	ac.ac_tty = current->tty ? old_encode_dev(tty_devnum(current->tty)) : 0;
+	ac.ac_tty = current->signal->tty ? old_encode_dev(tty_devnum(current->signal->tty)) : 0;
 
 	ac.ac_flag = 0;
 	if (current->flags & PF_FORKNOEXEC)
diff -puN kernel/exit.c~move-job-control-stuff-tosignal_struct kernel/exit.c
--- 25/kernel/exit.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.018271632 -0800
+++ 25-akpm/kernel/exit.c	2004-03-29 20:26:59.067264184 -0800
@@ -136,13 +136,13 @@ int session_of_pgrp(int pgrp)
 
 	read_lock(&tasklist_lock);
 	for_each_task_pid(pgrp, PIDTYPE_PGID, p, l, pid)
-		if (p->session > 0) {
-			sid = p->session;
+		if (p->signal->session > 0) {
+			sid = p->signal->session;
 			goto out;
 		}
 	p = find_task_by_pid(pgrp);
 	if (p)
-		sid = p->session;
+		sid = p->signal->session;
 out:
 	read_unlock(&tasklist_lock);
 	
@@ -170,7 +170,7 @@ static int will_become_orphaned_pgrp(int
 				|| p->real_parent->pid == 1)
 			continue;
 		if (process_group(p->real_parent) != pgrp
-			    && p->real_parent->session == p->session) {
+			    && p->real_parent->signal->session == p->signal->session) {
 			ret = 0;
 			break;
 		}
@@ -259,14 +259,14 @@ void __set_special_pids(pid_t session, p
 {
 	struct task_struct *curr = current;
 
-	if (curr->session != session) {
+	if (curr->signal->session != session) {
 		detach_pid(curr, PIDTYPE_SID);
-		curr->session = session;
+		curr->signal->session = session;
 		attach_pid(curr, PIDTYPE_SID, session);
 	}
 	if (process_group(curr) != pgrp) {
 		detach_pid(curr, PIDTYPE_PGID);
-		curr->group_leader->__pgrp = pgrp;
+		curr->signal->pgrp = pgrp;
 		attach_pid(curr, PIDTYPE_PGID, pgrp);
 	}
 }
@@ -341,7 +341,7 @@ void daemonize(const char *name, ...)
 	exit_mm(current);
 
 	set_special_pids(1, 1);
-	current->tty = NULL;
+	current->signal->tty = NULL;
 
 	/* Block and flush all signals */
 	sigfillset(&blocked);
@@ -564,7 +564,7 @@ static inline void reparent_thread(task_
 	 * outside, so the child pgrp is now orphaned.
 	 */
 	if ((process_group(p) != process_group(father)) &&
-	    (p->session == father->session)) {
+	    (p->signal->session == father->signal->session)) {
 		int pgrp = process_group(p);
 
 		if (will_become_orphaned_pgrp(pgrp, NULL) && has_stopped_jobs(pgrp)) {
@@ -675,7 +675,7 @@ static void exit_notify(struct task_stru
 	t = tsk->real_parent;
 	
 	if ((process_group(t) != process_group(tsk)) &&
-	    (t->session == tsk->session) &&
+	    (t->signal->session == tsk->signal->session) &&
 	    will_become_orphaned_pgrp(process_group(tsk), tsk) &&
 	    has_stopped_jobs(process_group(tsk))) {
 		__kill_pg_info(SIGHUP, (void *)1, process_group(tsk));
@@ -780,7 +780,7 @@ asmlinkage NORET_TYPE void do_exit(long 
 	exit_itimers(tsk);
 	exit_thread();
 
-	if (tsk->leader)
+	if (tsk->signal->leader)
 		disassociate_ctty(1);
 
 	module_put(tsk->thread_info->exec_domain->module);
diff -puN kernel/fork.c~move-job-control-stuff-tosignal_struct kernel/fork.c
--- 25/kernel/fork.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.020271328 -0800
+++ 25-akpm/kernel/fork.c	2004-03-29 20:26:59.068264032 -0800
@@ -814,6 +814,12 @@ static inline int copy_signal(unsigned l
 	sig->curr_target = NULL;
 	init_sigpending(&sig->shared_pending);
 
+	sig->tty = current->signal->tty;
+	sig->pgrp = process_group(current);
+	sig->session = current->signal->session;
+	sig->leader = 0;	/* session leadership doesn't inherit */
+	sig->tty_old_pgrp = 0;
+
 	return 0;
 }
 
@@ -938,8 +944,6 @@ struct task_struct *copy_process(unsigne
 	init_timer(&p->real_timer);
 	p->real_timer.data = (unsigned long) p;
 
-	p->leader = 0;		/* session leadership doesn't inherit */
-	p->tty_old_pgrp = 0;
 	p->utime = p->stime = 0;
 	p->cutime = p->cstime = 0;
 	p->lock_depth = -1;		/* -1 = no lock */
@@ -1061,7 +1065,7 @@ struct task_struct *copy_process(unsigne
 	if (thread_group_leader(p)) {
 		attach_pid(p, PIDTYPE_TGID, p->tgid);
 		attach_pid(p, PIDTYPE_PGID, process_group(p));
-		attach_pid(p, PIDTYPE_SID, p->session);
+		attach_pid(p, PIDTYPE_SID, p->signal->session);
 		if (p->pid)
 			__get_cpu_var(process_counts)++;
 	} else
diff -puN kernel/pid.c~move-job-control-stuff-tosignal_struct kernel/pid.c
--- 25/kernel/pid.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.021271176 -0800
+++ 25-akpm/kernel/pid.c	2004-03-29 20:26:59.068264032 -0800
@@ -255,14 +255,14 @@ void switch_exec_pids(task_t *leader, ta
 
 	attach_pid(thread, PIDTYPE_PID, thread->pid);
 	attach_pid(thread, PIDTYPE_TGID, thread->tgid);
-	attach_pid(thread, PIDTYPE_PGID, leader->__pgrp);
-	attach_pid(thread, PIDTYPE_SID, thread->session);
+	attach_pid(thread, PIDTYPE_PGID, thread->signal->pgrp);
+	attach_pid(thread, PIDTYPE_SID, thread->signal->session);
 	list_add_tail(&thread->tasks, &init_task.tasks);
 
 	attach_pid(leader, PIDTYPE_PID, leader->pid);
 	attach_pid(leader, PIDTYPE_TGID, leader->tgid);
-	attach_pid(leader, PIDTYPE_PGID, leader->__pgrp);
-	attach_pid(leader, PIDTYPE_SID, leader->session);
+	attach_pid(leader, PIDTYPE_PGID, leader->signal->pgrp);
+	attach_pid(leader, PIDTYPE_SID, leader->signal->session);
 }
 
 /*
diff -puN kernel/signal.c~move-job-control-stuff-tosignal_struct kernel/signal.c
--- 25/kernel/signal.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.023270872 -0800
+++ 25-akpm/kernel/signal.c	2004-03-29 20:26:59.070263728 -0800
@@ -588,7 +588,8 @@ static int check_kill_permission(int sig
 	error = -EPERM;
 	if ((!info || ((unsigned long)info != 1 &&
 			(unsigned long)info != 2 && SI_FROMUSER(info)))
-	    && ((sig != SIGCONT) || (current->session != t->session))
+	    && ((sig != SIGCONT) ||
+		(current->signal->session != t->signal->session))
 	    && (current->euid ^ t->suid) && (current->euid ^ t->uid)
 	    && (current->uid ^ t->suid) && (current->uid ^ t->uid)
 	    && !capable(CAP_KILL))
@@ -1103,7 +1104,7 @@ kill_sl_info(int sig, struct siginfo *in
 	retval = -ESRCH;
 	read_lock(&tasklist_lock);
 	for_each_task_pid(sid, PIDTYPE_SID, p, l, pid) {
-		if (!p->leader)
+		if (!p->signal->leader)
 			continue;
 		err = group_send_sig_info(sig, info, p);
 		if (retval)
diff -puN kernel/sys.c~move-job-control-stuff-tosignal_struct kernel/sys.c
--- 25/kernel/sys.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.024270720 -0800
+++ 25-akpm/kernel/sys.c	2004-03-29 20:26:59.072263424 -0800
@@ -985,7 +985,7 @@ asmlinkage long sys_setpgid(pid_t pid, p
 
 	if (p->parent == current || p->real_parent == current) {
 		err = -EPERM;
-		if (p->session != current->session)
+		if (p->signal->session != current->signal->session)
 			goto out;
 		err = -EACCES;
 		if (p->did_exec)
@@ -997,7 +997,7 @@ asmlinkage long sys_setpgid(pid_t pid, p
 	}
 
 	err = -EPERM;
-	if (p->leader)
+	if (p->signal->leader)
 		goto out;
 
 	if (pgid != pid) {
@@ -1006,7 +1006,7 @@ asmlinkage long sys_setpgid(pid_t pid, p
 		struct list_head *l;
 
 		for_each_task_pid(pgid, PIDTYPE_PGID, p, l, pid)
-			if (p->session == current->session)
+			if (p->signal->session == current->signal->session)
 				goto ok_pgid;
 		goto out;
 	}
@@ -1018,7 +1018,7 @@ ok_pgid:
 
 	if (process_group(p) != pgid) {
 		detach_pid(p, PIDTYPE_PGID);
-		p->group_leader->__pgrp = pgid;
+		p->signal->pgrp = pgid;
 		attach_pid(p, PIDTYPE_PGID, pgid);
 	}
 
@@ -1060,7 +1060,7 @@ asmlinkage long sys_getpgrp(void)
 asmlinkage long sys_getsid(pid_t pid)
 {
 	if (!pid) {
-		return current->session;
+		return current->signal->session;
 	} else {
 		int retval;
 		struct task_struct *p;
@@ -1072,7 +1072,7 @@ asmlinkage long sys_getsid(pid_t pid)
 		if(p) {
 			retval = security_task_getsid(p);
 			if (!retval)
-				retval = p->session;
+				retval = p->signal->session;
 		}
 		read_unlock(&tasklist_lock);
 		return retval;
@@ -1093,10 +1093,10 @@ asmlinkage long sys_setsid(void)
 	if (pid)
 		goto out;
 
-	current->leader = 1;
+	current->signal->leader = 1;
 	__set_special_pids(current->pid, current->pid);
-	current->tty = NULL;
-	current->tty_old_pgrp = 0;
+	current->signal->tty = NULL;
+	current->signal->tty_old_pgrp = 0;
 	err = process_group(current);
 out:
 	write_unlock_irq(&tasklist_lock);
diff -puN net/ipv4/netfilter/ipt_owner.c~move-job-control-stuff-tosignal_struct net/ipv4/netfilter/ipt_owner.c
--- 25/net/ipv4/netfilter/ipt_owner.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.025270568 -0800
+++ 25-akpm/net/ipv4/netfilter/ipt_owner.c	2004-03-29 20:26:59.072263424 -0800
@@ -95,7 +95,7 @@ match_sid(const struct sk_buff *skb, pid
 	read_lock(&tasklist_lock);
 	do_each_thread(g, p) {
 		struct files_struct *files;
-		if (p->session != sid)
+		if (p->signal->session != sid)
 			continue;
 
 		task_lock(p);
diff -puN net/ipv6/netfilter/ip6t_owner.c~move-job-control-stuff-tosignal_struct net/ipv6/netfilter/ip6t_owner.c
--- 25/net/ipv6/netfilter/ip6t_owner.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.026270416 -0800
+++ 25-akpm/net/ipv6/netfilter/ip6t_owner.c	2004-03-29 20:26:59.072263424 -0800
@@ -61,7 +61,7 @@ match_sid(const struct sk_buff *skb, pid
 	read_lock(&tasklist_lock);
 	do_each_thread(g, p) {
 		struct files_struct *files;
-		if (p->session != sid)
+		if (p->signal->session != sid)
 			continue;
 
 		task_lock(p);
diff -puN drivers/s390/char/keyboard.c~move-job-control-stuff-tosignal_struct drivers/s390/char/keyboard.c
--- 25/drivers/s390/char/keyboard.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.028270112 -0800
+++ 25-akpm/drivers/s390/char/keyboard.c	2004-03-29 20:26:59.073263272 -0800
@@ -471,7 +471,7 @@ kbd_ioctl(struct kbd_data *kbd, struct f
 	 * To have permissions to do most of the vt ioctls, we either have
 	 * to be the owner of the tty, or have CAP_SYS_TTY_CONFIG.
 	 */
-	perm = current->tty == kbd->tty || capable(CAP_SYS_TTY_CONFIG);
+	perm = current->signal->tty == kbd->tty || capable(CAP_SYS_TTY_CONFIG);
 	switch (cmd) {
 	case KDGKBTYPE:
 		return put_user(KB_101, (char*) arg);
diff -puN drivers/char/sx.c~move-job-control-stuff-tosignal_struct drivers/char/sx.c
--- 25/drivers/char/sx.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.029269960 -0800
+++ 25-akpm/drivers/char/sx.c	2004-03-29 20:26:59.075262968 -0800
@@ -1420,7 +1420,7 @@ static int sx_open  (struct tty_struct *
 
 	line = tty->index;
 	sx_dprintk (SX_DEBUG_OPEN, "%d: opening line %d. tty=%p ctty=%p, np=%d)\n", 
-	            current->pid, line, tty, current->tty, sx_nports);
+	            current->pid, line, tty, current->signal->tty, sx_nports);
 
 	if ((line < 0) || (line >= SX_NPORTS) || (line >= sx_nports))
 		return -ENODEV;
diff -puN arch/ia64/kernel/unaligned.c~move-job-control-stuff-tosignal_struct arch/ia64/kernel/unaligned.c
--- 25/arch/ia64/kernel/unaligned.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.031269656 -0800
+++ 25-akpm/arch/ia64/kernel/unaligned.c	2004-03-29 20:26:59.076262816 -0800
@@ -1337,7 +1337,7 @@ ia64_handle_unaligned (unsigned long ifa
 			 * be holding locks...
 			 */
 			if (user_mode(regs))
-				tty_write_message(current->tty, buf);
+				tty_write_message(current->signal->tty, buf);
 			buf[len-1] = '\0';	/* drop '\r' */
 			printk(KERN_WARNING "%s", buf);	/* watch for command names containing %s */
 		}
diff -puN fs/compat_ioctl.c~move-job-control-stuff-tosignal_struct fs/compat_ioctl.c
--- 25/fs/compat_ioctl.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.033269352 -0800
+++ 25-akpm/fs/compat_ioctl.c	2004-03-29 20:26:59.078262512 -0800
@@ -1604,7 +1604,7 @@ static int vt_check(struct file *file)
 	 * To have permissions to do most of the vt ioctls, we either have
 	 * to be the owner of the tty, or super-user.
 	 */
-	if (current->tty == tty || capable(CAP_SYS_ADMIN))
+	if (current->signal->tty == tty || capable(CAP_SYS_ADMIN))
 		return 1;
 	return 0;                                                    
 }
diff -puN arch/sparc64/solaris/misc.c~move-job-control-stuff-tosignal_struct arch/sparc64/solaris/misc.c
--- 25/arch/sparc64/solaris/misc.c~move-job-control-stuff-tosignal_struct	2004-03-29 20:26:59.035269048 -0800
+++ 25-akpm/arch/sparc64/solaris/misc.c	2004-03-29 20:26:59.079262360 -0800
@@ -402,7 +402,7 @@ asmlinkage int solaris_procids(int cmd, 
 			   Solaris setpgrp and setsid? */
 			ret = sys_setpgid(0, 0);
 			if (ret) return ret;
-			current->tty = NULL;
+			current->signal->tty = NULL;
 			return process_group(current);
 		}
 	case 2: /* getsid */

_