patch-2.3.45 linux/mm/mmap.c

Next file: linux/net/core/dev.c
Previous file: linux/mm/memory.c
Back to the patch index
Back to the overall index

diff -u --recursive --new-file v2.3.44/linux/mm/mmap.c linux/mm/mmap.c
@@ -75,13 +75,14 @@
 	struct file * file = vma->vm_file;
 
 	if (file) {
+		struct inode *inode = file->f_dentry->d_inode;
 		if (vma->vm_flags & VM_DENYWRITE)
-			atomic_inc(&file->f_dentry->d_inode->i_writecount);
-		spin_lock(&file->f_dentry->d_inode->i_shared_lock);
+			atomic_inc(&inode->i_writecount);
+		spin_lock(&inode->i_mapping->i_shared_lock);
 		if(vma->vm_next_share)
 			vma->vm_next_share->vm_pprev_share = vma->vm_pprev_share;
 		*vma->vm_pprev_share = vma->vm_next_share;
-		spin_unlock(&file->f_dentry->d_inode->i_shared_lock);
+		spin_unlock(&inode->i_mapping->i_shared_lock);
 	}
 }
 
@@ -580,6 +581,7 @@
 {
 	unsigned long first = start & PGDIR_MASK;
 	unsigned long last = (end + PGDIR_SIZE - 1) & PGDIR_MASK;
+	unsigned long start_index, end_index;
 
 	if (!prev) {
 		prev = mm->mmap;
@@ -607,12 +609,14 @@
 		break;
 	}
 no_mmaps:
-	first = first >> PGDIR_SHIFT;
-	last = last >> PGDIR_SHIFT;
-	if (last > first) {
-		clear_page_tables(mm, first, last-first);
-		flush_tlb_pgtables(mm, first << PGDIR_SHIFT, last << PGDIR_SHIFT);
-	}
+	/*
+	 * If the PGD bits are not consecutive in the virtual address, the
+	 * old method of shifting the VA >> by PGDIR_SHIFT doesn't work.
+	 */
+	start_index = pgd_index(first);
+	end_index = pgd_index(last);
+	if (end_index > start_index)
+		clear_page_tables(mm, start_index, end_index - start_index);
 }
 
 /* Munmap is split into 2 main parts -- this part which finds
@@ -884,16 +888,17 @@
 	file = vmp->vm_file;
 	if (file) {
 		struct inode * inode = file->f_dentry->d_inode;
+		struct address_space *mapping = inode->i_mapping;
 		if (vmp->vm_flags & VM_DENYWRITE)
 			atomic_dec(&inode->i_writecount);
       
 		/* insert vmp into inode's share list */
-		spin_lock(&inode->i_shared_lock);
-		if((vmp->vm_next_share = inode->i_mmap) != NULL)
-			inode->i_mmap->vm_pprev_share = &vmp->vm_next_share;
-		inode->i_mmap = vmp;
-		vmp->vm_pprev_share = &inode->i_mmap;
-		spin_unlock(&inode->i_shared_lock);
+		spin_lock(&mapping->i_shared_lock);
+		if((vmp->vm_next_share = mapping->i_mmap) != NULL)
+			mapping->i_mmap->vm_pprev_share = &vmp->vm_next_share;
+		mapping->i_mmap = vmp;
+		vmp->vm_pprev_share = &mapping->i_mmap;
+		spin_unlock(&mapping->i_shared_lock);
 	}
 }
 

FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)