Implement Database.block_size (previously hard coded to 0x1000), change Database...
authorNick Downing <nick@ndcode.org>
Sat, 8 Jan 2022 00:53:18 +0000 (19:53 -0500)
committerNick Downing <nick@ndcode.org>
Sat, 8 Jan 2022 01:42:21 +0000 (12:42 +1100)
Database.mjs
Transaction.mjs

index d3f9af3..732401c 100644 (file)
@@ -7,16 +7,17 @@ import Transaction from './Transaction.mjs'
 let open_angle = Buffer.from('\n<', 'utf-8')
 let close_angle = Buffer.from('>\n', 'utf-8')
 class Database {
-  constructor(read_timeout, write_timeout) {
+  constructor(read_timeout, write_timeout, block_size) {
     this.read_timeout = read_timeout || 3600
     this.write_timeout = write_timeout || 5
+    this.block_size = block_size || 0x1000
     this.mutex = new Mutex()
     this.log = null
-    this.eof = 0 // before write_list
-    this.eof1 = 0 // after write_list
+    this.eof = 0
     this.value = undefined
     this.read_cache = {}
     this.write_list = []
+    this.write_list_len = 0
     this.write_count = 0
   }
 
@@ -25,10 +26,10 @@ class Database {
     assert(this.log === null)
 
     this.eof = 0 // before write_list
-    this.eof1 = 0 // after write_list
     this.value = undefined
     this.read_cache = {}
     this.write_list = []
+    this.write_list_len = 0
     this.write_count = 0
  
     try {
@@ -45,15 +46,15 @@ class Database {
       return
     }
 
-    this.eof = this.eof1 = (await this.log.stat()).size
+    this.eof = (await this.log.stat()).size
 
     let eof_buffer
     try {
       eof_buffer = await (
         async () => {
-          let ptr = this.eof & ~0xfff
-          let count = this.eof & 0xfff
-          let buffer = Buffer.alloc(0x1001)
+          let ptr = this.eof & ~(this.block_size - 1)
+          let count = this.eof & (this.block_size - 1)
+          let buffer = Buffer.alloc(this.block_size + 1)
           assert(
             (await this.log.read(buffer, 0, count, ptr)).bytesRead === count
           )
@@ -70,17 +71,17 @@ class Database {
 
                 if (ptr === 0)
                   break
-                ptr -= 0x1000
+                ptr -= this.block_size
                 if (count) {
-                  buffer[0x1000] = buffer[0]
-                  count = 0x1001
+                  buffer[this.block_size] = buffer[0]
+                  count = this.block_size + 1
                 }
                 else
-                  count = 0x1000
+                  count = this.block_size
                 assert(
-                  (await this.log.read(buffer, 0, 0x1000, ptr)).bytesRead === 0x1000
+                  (await this.log.read(buffer, 0, this.block_size, ptr)).bytesRead === this.block_size
                 )
-                blocks.push(buffer.slice(0, 0x1000))
+                blocks.push(buffer.slice(0, this.block_size))
               }
 
               // special case for < at start of database
@@ -92,15 +93,15 @@ class Database {
 
             if (ptr === 0)
               break
-            ptr -= 0x1000
+            ptr -= this.block_size
             if (count) {
-              buffer[0x1000] = buffer[0]
-              count = 0x1001
+              buffer[this.block_size] = buffer[0]
+              count = this.block_size + 1
             }
             else
-              count = 0x1000
+              count = this.block_size
             assert(
-              (await this.log.read(buffer, 0, 0x1000, ptr)).bytesRead === 0x1000
+              (await this.log.read(buffer, 0, this.block_size, ptr)).bytesRead === this.block_size
             )
           }
 
@@ -123,7 +124,6 @@ class Database {
       console.log('warning: garbage after root, truncating database file')
       await this.log.truncate(eof)
       this.eof = eof
-      this.eof1 = eof
     }
 
     this.mutex.release()
@@ -172,7 +172,7 @@ class Database {
       'utf-8'
     )
 
-    let ptr = this.eof1
+    let ptr = this.eof + this.write_list_len
     let len = buffer.length
 
     //console.log('addw', ptr)
@@ -180,7 +180,7 @@ class Database {
     this.read_cache[ptr] = new CachedValue(1, value, this.read_timeout)
 
     this.write_list.push(buffer)
-    this.eof1 += len
+    this.write_list_len += len
 
     return [ptr, len - 1]
   }
@@ -192,14 +192,14 @@ class Database {
       'utf-8'
     )
     this.write_list.push(buffer)
-    this.eof1 += buffer.length
+    this.write_list_len += buffer.length
   }
 
   async flush() {
     // hold mutex whilst calling this function
     let ptr = this.eof, len = 0, i = 0, j = 0
     for (; j < this.write_list.length; ++j) {
-      if (len >= 0x1000) {
+      if (len >= this.block_size) {
         let buffer = Buffer.concat(this.write_list.slice(i, j))
         assert(buffer.length === len)
         assert(
@@ -218,7 +218,7 @@ class Database {
       (await this.log.write(buffer, 0, len, ptr)).bytesWritten === len
     )
     ptr += len
-    assert(ptr === this.eof1)
+    assert(ptr === this.eof + this.write_list_len)
 
     // each block in write list is also pinned in read cache, unpin
     // note: do this afterwards as needs to be on disk when unpinned
@@ -233,10 +233,11 @@ class Database {
       }
       ptr += this.write_list[i].length
     }
-    assert(ptr === this.eof1)
+    assert(ptr === this.eof + this.write_list_len)
 
     this.eof = ptr
     this.write_list = []
+    this.write_list_len = 0
   }
 
   Transaction() {
index 9938de7..e23110e 100644 (file)
@@ -59,10 +59,7 @@ class Transaction {
       this.database.value = this.value
     }
 
-    if (
-      this.database.eof1 > this.database.eof &&
-      this.database.write_count === 0
-    ) {
+    if (this.database.write_list_len && this.database.write_count === 0) {
       if (this.database.write_timeout === 0)
         await this.database.flush()
       else