patch-2.1.120 linux/arch/i386/kernel/process.c

Next file: linux/arch/i386/kernel/setup.c
Previous file: linux/arch/i386/kernel/irq.h
Back to the patch index
Back to the overall index

diff -u --recursive --new-file v2.1.119/linux/arch/i386/kernel/process.c linux/arch/i386/kernel/process.c
@@ -488,21 +488,19 @@
 
 void release_segments(struct mm_struct *mm)
 {
-	void * ldt = mm->segments;
-	int nr;
-
 	/* forget local segments */
-	__asm__ __volatile__("movl %w0,%%fs ; movl %w0,%%gs ; lldt %w0"
+	__asm__ __volatile__("movl %w0,%%fs ; movl %w0,%%gs"
 		: /* no outputs */
 		: "r" (0));
-	current->tss.ldt = 0;
-	/*
-	 * Set the GDT entry back to the default.
-	 */
-	nr = current->tarray_ptr - &task[0];
-	set_ldt_desc(gdt+(nr<<1)+FIRST_LDT_ENTRY, &default_ldt, 1);
+	if (mm->segments) {
+		void * ldt = mm->segments;
+
+		/*
+		 * Get the LDT entry from init_task.
+		 */
+		current->tss.ldt = _LDT(0);
+		load_ldt(0);
 
-	if (ldt) {
 		mm->segments = NULL;
 		vfree(ldt);
 	}
@@ -557,23 +555,22 @@
 	void * old_ldt = old_mm->segments, * ldt = old_ldt;
 	int ldt_size = LDT_ENTRIES;
 
-	p->tss.ldt = _LDT(nr);
+	/* "default_ldt" - use the one from init_task */
+	p->tss.ldt = _LDT(0);
 	if (old_ldt) {
 		if (new_mm) {
 			ldt = vmalloc(LDT_ENTRIES*LDT_ENTRY_SIZE);
 			new_mm->segments = ldt;
 			if (!ldt) {
 				printk(KERN_WARNING "ldt allocation failed\n");
-				goto no_ldt;
+				return;
 			}
 			memcpy(ldt, old_ldt, LDT_ENTRIES*LDT_ENTRY_SIZE);
 		}
-	} else {
-	no_ldt:
-		ldt = &default_ldt;
-		ldt_size = 1;
+		p->tss.ldt = _LDT(nr);
+		set_ldt_desc(gdt+(nr<<1)+FIRST_LDT_ENTRY, ldt, ldt_size);
+		return;
 	}
-	set_ldt_desc(gdt+(nr<<1)+FIRST_LDT_ENTRY, ldt, ldt_size);
 }
 
 /*

FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen, slshen@lbl.gov