chiark / gitweb /
Allow superblock to be written without fsync.
authorDan Sheppard <dan.sheppard.circle@gmail.com>
Mon, 28 Apr 2025 12:46:22 +0000 (13:46 +0100)
committerDan Sheppard <dan.sheppard.circle@gmail.com>
Mon, 28 Apr 2025 12:46:22 +0000 (13:46 +0100)
If we're going to store book fsync watermarks there, we need to be able not to fsync here, to avoid the cost of an unnecessary double fsync.

src/main.c
src/page.c
src/page.h
src/superblock.c
src/superblock.h

index 48acc2d2cda13ed351addfa35561f22c8aaf12f1..7f90a4fe75cd2b83327a8aa1fe967a9144773cc3 100644 (file)
@@ -32,7 +32,7 @@ int main() {
     bail(&cq,r);
     r = cq_super_load(&cq,COQUET_FILE_MAIN,&super,1);
     bail(&cq,r);
-    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1);
+    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1,1);
     r = (cq.vfs_funcs.close)(cq.vfs_data,COQUET_FILE_MAIN);
     bail(&cq,r);
     r = coquet_finish(&cq);
index 33f4fdef02e11b19ffddc3783262071036415b8d..f20d9e925291df0067e1157a98fb7da29967c005 100644 (file)
@@ -110,7 +110,7 @@ void test_page() {
     test_bail(&cq,r);
 
     cq_super_load(&cq,COQUET_FILE_MAIN,&super,1);
-    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1);
+    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1,1);
 
     r = coquet_write_start(&cq,COQUET_FILE_MAIN,1);
     test_bail(&cq,r);
index a3a0348d4d166fa594b8af2d814ae6a30607c5dc..6e572adf4faec820302ec3e8ee0d3ea5a13c5f33 100644 (file)
@@ -4,6 +4,27 @@
 #include <stdint.h>
 #include "coquet.h"
 
+/* Pages begin with flags discriminating page type, followed by a series of
+ * zero or more headers determined by type. There is then the data tail. Headers
+ * are sequenced in the order of the declarations below.
+ */
+
+/* A true root page, a pt_root header follows */
+#define COQUET_PT_ROOT 0x01
+
+struct pt_root {
+    /* TODO nursery id */
+    uint64_t book_length; /* Pages to next pt_root, (0 = this is first) */
+    uint8_t page_hash[32]; /* HMAC SHA512-256 using global_iv */
+    uint8_t section_hash[32]; /* HMAC SHA512-256 using global_iv */
+};
+
+struct cq_page {
+    uint8_t flags;
+    struct pt_root root;
+    uint64_t data;
+};
+
 /* byte offset of given main page. Note pgids are 1-based */
 off_t cq_offset_main_page(coquet_t *cq, int which_file, u_int64_t pgid);
 
index 2cd96fcbcf5871587b246fc16e0ad04ef3c086da..c3dcafa64f56fc2d1e1b3b0166c02f0563c99bcf 100644 (file)
@@ -194,7 +194,7 @@ static int super_write(coquet_t *cq, struct cq_super *super,
     return r;
 }
 
-int cq_super_save(coquet_t *cq, int which_file, struct cq_super *super, bool wait) {
+int cq_super_save(coquet_t *cq, int which_file, struct cq_super *super, bool wait, bool sync) {
     int r, ret;
     struct cq_super old;
 
@@ -215,7 +215,9 @@ int cq_super_save(coquet_t *cq, int which_file, struct cq_super *super, bool wai
     }
 
     /* sync */
-    ret = (cq->vfs_funcs.sync)(cq->vfs_data,COQUET_FILE_MAIN,1);
+    if(sync) {
+        ret = (cq->vfs_funcs.sync)(cq->vfs_data,COQUET_FILE_MAIN,1);
+    }
 
     /* unlock */
     r = lock_super(cq,which_file,COQUET_LMODE_UN,wait);
@@ -281,12 +283,12 @@ void test_superblock_main() {
     r = cq_super_load(&cq,COQUET_FILE_MAIN,&super,1);
     test_bail(&cq,r);
 
-    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1);
+    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1,1);
     test_bail(&cq,r);
 
     super.desired.nursery_size = 11; /* change something for B */
     cq_super_set_desc(&super,"test file");
-    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1);
+    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1,1);
     test_bail(&cq,r);
 
     test_close(&cq);
@@ -338,7 +340,7 @@ void test_superblock_main() {
     /* check updated in file successfully */
     test_open(&cq);
 
-    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1);
+    cq_super_save(&cq,COQUET_FILE_MAIN,&super,1,1);
 
     test_close(&cq);
     test_open(&cq);
@@ -372,10 +374,10 @@ static void make_superblock(coquet_t *cq, bool also_b,
     test_open(cq);
     r = cq_super_load(cq,COQUET_FILE_MAIN,&super,1);
     super.current.nursery_size = 12;
-    cq_super_save(cq,COQUET_FILE_MAIN,&super,1);
+    cq_super_save(cq,COQUET_FILE_MAIN,&super,1,1);
     if(also_b) {
         super.current.nursery_size = 11;
-        cq_super_save(cq,COQUET_FILE_MAIN,&super,1);
+        cq_super_save(cq,COQUET_FILE_MAIN,&super,1,1);
     }
     if(corrupt>-1) {
         r = (cq->vfs_funcs.read)(cq->vfs_data,COQUET_FILE_MAIN,&d,corrupt,1);
index 82ff11adc0633a586b5d68f6a18a5b838ce3ee34..9a2155c5a176d87d2d7699841d92ac6bdfb4f4ac 100644 (file)
@@ -33,7 +33,7 @@ struct cq_super {
 
 #include "coquet.h"
 
-int cq_super_save(coquet_t *cq, int which_file, struct cq_super *super, bool wait);
+int cq_super_save(coquet_t *cq, int which_file, struct cq_super *super, bool wait, bool sync);
 int cq_super_load(coquet_t *cq, int which_file, struct cq_super *super, bool create);
 void cq_super_set_desc(struct cq_super *super, char *desc);
 char * cq_super_get_desc(struct cq_super *super);