Pārlūkot izejas kodu

Basic tree caching

Implemented basic tree caching so that `csldb:OpenTree` function does not create unnecessary userdata objects.
How ever, it will create new tree userdata, if database object was previously collected by garbage collector.
IVogel 2 gadi atpakaļ
vecāks
revīzija
97574ae6f6
4 mainītis faili ar 109 papildinājumiem un 84 dzēšanām
  1. 37 39
      src/ldb.rs
  2. 34 9
      src/lib.lua
  3. 9 5
      src/lib.rs
  4. 29 31
      src/ltree.rs

+ 37 - 39
src/ldb.rs

@@ -296,45 +296,43 @@ impl LDb {
         }
     }
 
-    fn metatable(state: lua_State) {
-        unsafe {
-            if lua::Lnewmetatable(state, lua::cstr!("csldb")) {
-                lua::pushvalue(state, -1);
-                lua::setfield(state, -2, lua::cstr!("__index"));
-                insert_function!(state, "__gc", Self::__gc);
-                insert_function!(state, "Name", Self::lm_name);
-                insert_function!(state, "Clear", Self::lm_clear);
-                insert_function!(state, "Get", Self::lm_get);
-                insert_function!(state, "GetStruct", Self::lm_get_struct);
-                insert_function!(state, "Insert", Self::lm_insert);
-                insert_function!(state, "InsertStruct", Self::lm_insert_struct);
-                insert_function!(state, "Remove", Self::lm_remove);
-                insert_function!(state, "Range", Self::lm_range);
-                insert_function!(state, "ScanPrefix", Self::lm_scan_prefix);
-                insert_function!(state, "TreeNames", Self::lm_tree_names);
-                insert_function!(state, "OpenTree", Self::lm_open_tree);
-                insert_function!(state, "GenerateID", Self::lm_generate_id);
-                insert_function!(state, "Export", Self::lm_export);
-                insert_function!(state, "Import", Self::lm_import);
-                insert_function!(state, "DropTree", Self::lm_drop_tree);
-                insert_function!(state, "WasRecovered", Self::lm_was_recovered);
-                insert_function!(state, "SizeOnDisk", Self::lm_size_on_disk);
-                insert_function!(state, "Flush", Self::lm_flush);
-                insert_function!(state, "Checksum", Self::lm_checksum);
-                insert_function!(state, "ContainsKey", Self::lm_contains_key);
-                insert_function!(state, "GetLT", Self::lm_get_lt);
-                insert_function!(state, "GetLTStruct", Self::lm_get_lt_struct);
-                insert_function!(state, "GetGT", Self::lm_get_gt);
-                insert_function!(state, "GetGTStruct", Self::lm_get_gt_struct);
-                insert_function!(state, "First", Self::lm_first);
-                insert_function!(state, "FirstStruct", Self::lm_first_struct);
-                insert_function!(state, "Last", Self::lm_last);
-                insert_function!(state, "LastStruct", Self::lm_last_struct);
-                insert_function!(state, "PopMax", Self::lm_pop_max);
-                insert_function!(state, "PopMaxStruct", Self::lm_pop_max_struct);
-                insert_function!(state, "PopMin", Self::lm_pop_min);
-                insert_function!(state, "PopMinStruct", Self::lm_pop_min_struct);
-            }
+    pub unsafe fn metatable(state: lua_State) {
+        if lua::Lnewmetatable(state, lua::cstr!("csldb")) {
+            lua::pushvalue(state, -1);
+            lua::setfield(state, -2, lua::cstr!("__index"));
+            insert_function!(state, "__gc", Self::__gc);
+            insert_function!(state, "Name", Self::lm_name);
+            insert_function!(state, "Clear", Self::lm_clear);
+            insert_function!(state, "Get", Self::lm_get);
+            insert_function!(state, "GetStruct", Self::lm_get_struct);
+            insert_function!(state, "Insert", Self::lm_insert);
+            insert_function!(state, "InsertStruct", Self::lm_insert_struct);
+            insert_function!(state, "Remove", Self::lm_remove);
+            insert_function!(state, "Range", Self::lm_range);
+            insert_function!(state, "ScanPrefix", Self::lm_scan_prefix);
+            insert_function!(state, "TreeNames", Self::lm_tree_names);
+            insert_function!(state, "OpenTree", Self::lm_open_tree);
+            insert_function!(state, "GenerateID", Self::lm_generate_id);
+            insert_function!(state, "Export", Self::lm_export);
+            insert_function!(state, "Import", Self::lm_import);
+            insert_function!(state, "DropTree", Self::lm_drop_tree);
+            insert_function!(state, "WasRecovered", Self::lm_was_recovered);
+            insert_function!(state, "SizeOnDisk", Self::lm_size_on_disk);
+            insert_function!(state, "Flush", Self::lm_flush);
+            insert_function!(state, "Checksum", Self::lm_checksum);
+            insert_function!(state, "ContainsKey", Self::lm_contains_key);
+            insert_function!(state, "GetLT", Self::lm_get_lt);
+            insert_function!(state, "GetLTStruct", Self::lm_get_lt_struct);
+            insert_function!(state, "GetGT", Self::lm_get_gt);
+            insert_function!(state, "GetGTStruct", Self::lm_get_gt_struct);
+            insert_function!(state, "First", Self::lm_first);
+            insert_function!(state, "FirstStruct", Self::lm_first_struct);
+            insert_function!(state, "Last", Self::lm_last);
+            insert_function!(state, "LastStruct", Self::lm_last_struct);
+            insert_function!(state, "PopMax", Self::lm_pop_max);
+            insert_function!(state, "PopMaxStruct", Self::lm_pop_max_struct);
+            insert_function!(state, "PopMin", Self::lm_pop_min);
+            insert_function!(state, "PopMinStruct", Self::lm_pop_min_struct);
         }
     }
 }

+ 34 - 9
src/lib.lua

@@ -1,10 +1,35 @@
-local sled_open = sled.Open
-local cache = setmetatable({}, {__mode = "v"})
-
-function sled.Open(name)
-    local db = cache[name]
-    if db then return db end
-    db = sled_open(name)
-    cache[name] = db
-    return db
+-- TODO: implement basic table-like indexing functionality
+
+local CSLDB_META, CSLT_META = ...;
+
+do
+    local sled_open = sled.Open
+    local cache = setmetatable({}, {__mode = "v"})
+
+    function sled.Open(name)
+        local db = cache[name]
+        if db then return db end
+        db = sled_open(name)
+        cache[name] = db
+        return db
+    end
+end
+
+do
+    local tree_cache = setmetatable({}, {__mode = "k"})
+    local csldb_open_tree = CSLDB_META.OpenTree
+
+    function CSLDB_META:OpenTree(name)
+        local trees = tree_cache[self];
+        if not trees then
+            trees = setmetatable({}, {__mode = "v"})
+            tree_cache[self] = trees
+        end
+        local tree = trees[name]
+        if not tree then
+            tree = csldb_open_tree(self, name)
+            trees[name] = tree
+        end
+        return tree
+    end
 end

+ 9 - 5
src/lib.rs

@@ -26,12 +26,16 @@ unsafe extern "C" fn gmod13_open(state: lua_State) -> i32 {
             lua::cstr!("@includes/modules/lsled.lua"),
             lua::cstr!("t"),
         ) {
-            lua::Status::Ok => match lua::pcall(state, 0, 0, 0) {
-                lua::Status::RuntimeError | lua::Status::MemoryError | lua::Status::Error => {
-                    lua::error(state);
+            lua::Status::Ok => {
+                ldb::LDb::metatable(state);
+                ltree::LTree::metatable(state);
+                match lua::pcall(state, 2, 0, 0) {
+                    lua::Status::RuntimeError | lua::Status::MemoryError | lua::Status::Error => {
+                        lua::error(state);
+                    }
+                    _ => {}
                 }
-                _ => {}
-            },
+            }
             _ => {
                 lua::error(state);
             }

+ 29 - 31
src/ltree.rs

@@ -186,37 +186,35 @@ impl LTree {
         }
     }
 
-    pub fn metatable(state: lua_State) {
-        unsafe {
-            if lua::Lnewmetatable(state, lua::cstr!("cslt")) {
-                lua::pushvalue(state, -1);
-                lua::setfield(state, -2, lua::cstr!("__index"));
-                insert_function!(state, "__gc", Self::__gc);
-                insert_function!(state, "Name", Self::lm_name);
-                insert_function!(state, "Clear", Self::lm_clear);
-                insert_function!(state, "Get", Self::lm_get);
-                insert_function!(state, "GetStruct", Self::lm_get_struct);
-                insert_function!(state, "Insert", Self::lm_insert);
-                insert_function!(state, "InsertStruct", Self::lm_insert_struct);
-                insert_function!(state, "Remove", Self::lm_remove);
-                insert_function!(state, "Range", Self::lm_range);
-                insert_function!(state, "ScanPrefix", Self::lm_scan_prefix);
-                insert_function!(state, "Flush", Self::lm_flush);
-                insert_function!(state, "Checksum", Self::lm_checksum);
-                insert_function!(state, "ContainsKey", Self::lm_contains_key);
-                insert_function!(state, "GetLT", Self::lm_get_lt);
-                insert_function!(state, "GetLTStruct", Self::lm_get_lt_struct);
-                insert_function!(state, "GetGT", Self::lm_get_gt);
-                insert_function!(state, "GetGTStruct", Self::lm_get_gt_struct);
-                insert_function!(state, "First", Self::lm_first);
-                insert_function!(state, "FirstStruct", Self::lm_first_struct);
-                insert_function!(state, "Last", Self::lm_last);
-                insert_function!(state, "LastStruct", Self::lm_last_struct);
-                insert_function!(state, "PopMax", Self::lm_pop_max);
-                insert_function!(state, "PopMaxStruct", Self::lm_pop_max_struct);
-                insert_function!(state, "PopMin", Self::lm_pop_min);
-                insert_function!(state, "PopMinStruct", Self::lm_pop_min_struct);
-            }
+    pub unsafe fn metatable(state: lua_State) {
+        if lua::Lnewmetatable(state, lua::cstr!("cslt")) {
+            lua::pushvalue(state, -1);
+            lua::setfield(state, -2, lua::cstr!("__index"));
+            insert_function!(state, "__gc", Self::__gc);
+            insert_function!(state, "Name", Self::lm_name);
+            insert_function!(state, "Clear", Self::lm_clear);
+            insert_function!(state, "Get", Self::lm_get);
+            insert_function!(state, "GetStruct", Self::lm_get_struct);
+            insert_function!(state, "Insert", Self::lm_insert);
+            insert_function!(state, "InsertStruct", Self::lm_insert_struct);
+            insert_function!(state, "Remove", Self::lm_remove);
+            insert_function!(state, "Range", Self::lm_range);
+            insert_function!(state, "ScanPrefix", Self::lm_scan_prefix);
+            insert_function!(state, "Flush", Self::lm_flush);
+            insert_function!(state, "Checksum", Self::lm_checksum);
+            insert_function!(state, "ContainsKey", Self::lm_contains_key);
+            insert_function!(state, "GetLT", Self::lm_get_lt);
+            insert_function!(state, "GetLTStruct", Self::lm_get_lt_struct);
+            insert_function!(state, "GetGT", Self::lm_get_gt);
+            insert_function!(state, "GetGTStruct", Self::lm_get_gt_struct);
+            insert_function!(state, "First", Self::lm_first);
+            insert_function!(state, "FirstStruct", Self::lm_first_struct);
+            insert_function!(state, "Last", Self::lm_last);
+            insert_function!(state, "LastStruct", Self::lm_last_struct);
+            insert_function!(state, "PopMax", Self::lm_pop_max);
+            insert_function!(state, "PopMaxStruct", Self::lm_pop_max_struct);
+            insert_function!(state, "PopMin", Self::lm_pop_min);
+            insert_function!(state, "PopMinStruct", Self::lm_pop_min_struct);
         }
     }
 }