tux3: Support mmap write: Add support of mlock page handling

Signed-off-by: OGAWA Hirofumi <hirofumi@mail.parknet.co.jp>
diff --git a/fs/tux3/buffer_fork.c b/fs/tux3/buffer_fork.c
index c1530c2..add08ae 100644
--- a/fs/tux3/buffer_fork.c
+++ b/fs/tux3/buffer_fork.c
@@ -365,7 +365,8 @@
 	BUG_ON(PageForked(oldpage));
 
 	/* FIXME: right? */
-	BUG_ON(PageUnevictable(oldpage));
+	BUG_ON(PageSwapCache(oldpage));
+	BUG_ON(PageSwapBacked(oldpage));
 	BUG_ON(PageHuge(oldpage));
 	if (PageError(oldpage))
 		SetPageError(newpage);
@@ -385,9 +386,10 @@
 	 */
 	cpupid = page_cpupid_xchg_last(oldpage, -1);
 	page_cpupid_xchg_last(newpage, cpupid);
-
-	mlock_migrate_page(newpage, page);
-	ksm_migrate_page(newpage, page);
+#endif
+	mlock_migrate_page(newpage, oldpage);
+#if 0
+	ksm_migrate_page(newpage, oldpage);
 #endif
 
 	/* Lock newpage before visible via radix tree */
diff --git a/fs/tux3/mmap_builtin_hack.h b/fs/tux3/mmap_builtin_hack.h
index b313506..2ffffdc 100644
--- a/fs/tux3/mmap_builtin_hack.h
+++ b/fs/tux3/mmap_builtin_hack.h
@@ -1,6 +1,34 @@
 #ifndef _MMAP_HACK_H
 #define _MMAP_HACK_H
 
+/*
+ * FIXME: copied from mm/internal.h. We should move some functions to
+ * mm/, then share codes.
+ */
+static inline void mlock_migrate_page(struct page *newpage, struct page *page)
+{
+	if (TestClearPageMlocked(page)) {
+		unsigned long flags;
+		int nr_pages = hpage_nr_pages(page);
+
+		local_irq_save(flags);
+		__mod_zone_page_state(page_zone(page), NR_MLOCK, -nr_pages);
+		SetPageMlocked(newpage);
+		__mod_zone_page_state(page_zone(newpage), NR_MLOCK, nr_pages);
+		local_irq_restore(flags);
+#if 0
+		/*
+		 * FIXME: maybe, we should remove page from LRU, then
+		 * putback to LRU. With it, Unevictable will be removed.
+		 *
+		 * if (!isolate_lru_page(page))
+		 *     putback_lru_page(page);
+		 */
+		BUG_ON(PageUnevictable(page));
+#endif
+	}
+}
+
 #ifdef CONFIG_TUX3_MMAP
 int page_cow_file(struct page *oldpage, struct page *newpage);
 #else