From d1c0e3b5da5f1a62007b19bc0f45935ada5fc6c6 Mon Sep 17 00:00:00 2001
From: Jeremy Soller <jackpot51@gmail.com>
Date: Tue, 13 Sep 2016 11:20:55 -0600
Subject: [PATCH] Use flush_all instead of flush for performance

---
 context/memory.rs  | 50 +++++++++++++++++++++++++++++++++++++++++-----
 syscall/process.rs |  2 +-
 2 files changed, 46 insertions(+), 6 deletions(-)

diff --git a/context/memory.rs b/context/memory.rs
index c0b885b6..9cd57f2a 100644
--- a/context/memory.rs
+++ b/context/memory.rs
@@ -39,14 +39,22 @@ impl Memory {
     pub fn map(&mut self, flush: bool, clear: bool) {
         let mut active_table = unsafe { ActivePageTable::new() };
 
+        let mut flush_all = false;
+
         //TODO: Clear pages?
         for page in self.pages() {
             active_table.map(page, self.flags);
+
             if flush {
-                active_table.flush(page);
+                //active_table.flush(page);
+                flush_all = true;
             }
         }
 
+        if flush_all {
+            active_table.flush_all();
+        }
+
         if clear {
             assert!(flush);
             unsafe { memset(self.start_address().get() as *mut u8, 0, self.size); }
@@ -56,24 +64,40 @@ impl Memory {
     pub fn unmap(&mut self, flush: bool) {
         let mut active_table = unsafe { ActivePageTable::new() };
 
+        let mut flush_all = false;
+
         for page in self.pages() {
             active_table.unmap(page);
+
             if flush {
-                active_table.flush(page);
+                //active_table.flush(page);
+                flush_all = true;
             }
         }
+
+        if flush_all {
+            active_table.flush_all();
+        }
     }
 
     pub fn remap(&mut self, new_flags: EntryFlags, flush: bool) {
         let mut active_table = unsafe { ActivePageTable::new() };
 
+        let mut flush_all = false;
+
         for page in self.pages() {
             active_table.remap(page, new_flags);
+
             if flush {
-                active_table.flush(page);
+                //active_table.flush(page);
+                flush_all = true;
             }
         }
 
+        if flush_all {
+            active_table.flush_all();
+        }
+
         self.flags = new_flags;
     }
 
@@ -82,32 +106,48 @@ impl Memory {
 
         //TODO: Calculate page changes to minimize operations
         if new_size > self.size {
+            let mut flush_all = false;
+
             let start_page = Page::containing_address(VirtualAddress::new(self.start.get() + self.size));
             let end_page = Page::containing_address(VirtualAddress::new(self.start.get() + new_size - 1));
             for page in Page::range_inclusive(start_page, end_page) {
                 if active_table.translate_page(page).is_none() {
                     active_table.map(page, self.flags);
+
                     if flush {
-                        active_table.flush(page);
+                        //active_table.flush(page);
+                        flush_all = true;
                     }
                 }
             }
 
+            if flush_all {
+                active_table.flush_all();
+            }
+
             if clear {
                 assert!(flush);
                 unsafe { memset((self.start.get() + self.size) as *mut u8, 0, new_size - self.size); }
             }
         } else if new_size < self.size {
+            let mut flush_all = false;
+
             let start_page = Page::containing_address(VirtualAddress::new(self.start.get() + new_size));
             let end_page = Page::containing_address(VirtualAddress::new(self.start.get() + self.size - 1));
             for page in Page::range_inclusive(start_page, end_page) {
                 if active_table.translate_page(page).is_some() {
                     active_table.unmap(page);
+
                     if flush {
-                        active_table.flush(page);
+                        //active_table.flush(page);
+                        flush_all = true;
                     }
                 }
             }
+
+            if flush_all {
+                active_table.flush_all();
+            }
         }
 
         self.size = new_size;
diff --git a/syscall/process.rs b/syscall/process.rs
index 78e0bc69..ad1d107c 100644
--- a/syscall/process.rs
+++ b/syscall/process.rs
@@ -49,7 +49,7 @@ pub fn clone(flags: usize) -> Result<usize> {
 
 pub fn exit(status: usize) -> ! {
     println!("Exit {}", status);
-    
+
     {
         let contexts = context::contexts();
         let context_lock = contexts.current().expect("tried to exit without context");
-- 
GitLab