]> arthur.barton.de Git - netatalk.git/commitdiff
Better checking for duplicated or bogus CNIDs from AppleDouble files
authorFrank Lahm <franklahm@googlemail.com>
Wed, 7 Sep 2011 10:24:21 +0000 (12:24 +0200)
committerFrank Lahm <franklahm@googlemail.com>
Wed, 7 Sep 2011 10:24:21 +0000 (12:24 +0200)
NEWS
etc/cnid_dbd/cmd_dbd_scanvol.c
etc/cnid_dbd/dbd_rebuild_add.c
etc/cnid_dbd/dbd_resolve.c

diff --git a/NEWS b/NEWS
index 3d244199799c9d84a698696edb6ca412d2d39572..29be671d2ed716f141b79693a703decf41c97b97 100644 (file)
--- a/NEWS
+++ b/NEWS
@@ -1,3 +1,7 @@
+Changes in 2.2.2
+================
+* FIX: dbd: Better checking for duplicated or bogus CNIDs from AppleDouble files
+
 Changes in 2.2.1
 ================
 
index ece70dd48953cb33e4523813de26eb1667c49e8e..50433c66de807a1dab6888ad7ca815a4cbd9729b 100644 (file)
@@ -755,24 +755,22 @@ static cnid_t check_cnid(const char *name, cnid_t did, struct stat *st, int adfi
         /* Everything is fine */
         return db_cnid;
     } else if (ad_cnid && db_cnid && (ad_cnid != db_cnid)) {
-        /* Mismatch ? Delete both from db and re-add data from file */
+        /* Mismatch, overwrite ad file with value from db */
         dbd_log( LOGSTD, "CNID mismatch for '%s/%s', db: %u, ad-file: %u", cwdbuf, name, ntohl(db_cnid), ntohl(ad_cnid));
         if ( ! (dbd_flags & DBD_FLAGS_SCAN)) {
-            rqst.cnid = db_cnid;
-            ret = dbd_delete(dbd, &rqst, &rply, DBIF_CNID);
-            if (dbif_txn_close(dbd, ret) != 0)
-                return CNID_INVALID;
-
-            rqst.cnid = ad_cnid;
-            ret = dbd_delete(dbd, &rqst, &rply, DBIF_CNID);
-            if (dbif_txn_close(dbd, ret) != 0)
-                return CNID_INVALID;
-
-            ret = dbd_rebuild_add(dbd, &rqst, &rply);
-            if (dbif_txn_close(dbd, ret) != 0)
+            dbd_log(LOGSTD, "Updating AppleDouble file for '%s/%s' with CNID: %u from database",
+                            cwdbuf, name, ntohl(db_cnid));
+            ad_init(&ad, myvolinfo->v_adouble, myvolinfo->v_ad_options);
+            if (ad_open_metadata( name, adflags, O_RDWR, &ad) != 0) {
+                dbd_log(LOGSTD, "Error opening AppleDouble file for '%s/%s': %s",
+                        cwdbuf, name, strerror(errno));
                 return CNID_INVALID;
+            }
+            ad_setid( &ad, st->st_dev, st->st_ino, db_cnid, did, stamp);
+            ad_flush(&ad);
+            ad_close_metadata(&ad);
         }
-        return ad_cnid;
+        return db_cnid;
     } else if (ad_cnid && (db_cnid == 0)) {
         /* in ad-file but not in db */
         if ( ! (dbd_flags & DBD_FLAGS_SCAN)) {
@@ -782,7 +780,7 @@ static cnid_t check_cnid(const char *name, cnid_t did, struct stat *st, int adfi
 
             rqst.cnid = ad_cnid;
             ret = dbd_resolve(dbd, &rqst, &rply);
-            if (ret == CNID_DBD_RES_OK) {
+            if (rply.result == CNID_DBD_RES_OK) {
                 /* Occupied! Choose another, update ad-file */
                 ret = dbd_add(dbd, &rqst, &rply, 1);
                 if (dbif_txn_close(dbd, ret) != 0)
index 90b2ffd3e1238b485406fde186492b536b9c2c30..f3a93e4ca54d3d9ae03fb3bd0f60771f3551542e 100644 (file)
@@ -48,6 +48,11 @@ int dbd_rebuild_add(DBD *dbd, struct cnid_dbd_rqst *rqst, struct cnid_dbd_rply *
         return -1;
     }
 
+    LOG(log_debug, logtype_cnid,
+        "dbd_rebuild_add(CNID: %u, did: %u, name: \"%s\", dev/ino:0x%llx/0x%llx): success",
+        ntohl(rqst->cnid), ntohl(rqst->did), rqst->name,
+        (unsigned long long)rqst->dev, (unsigned long long)rqst->ino);
+
     key.data = ROOTINFO_KEY;
     key.size = ROOTINFO_KEYLEN;
 
index 17a42de0ff1a5f362885edd4826fd9bbbc6e0521..1c2e2da914bc0143df5d1c54f523be86c99e5281 100644 (file)
@@ -53,8 +53,8 @@ int dbd_resolve(DBD *dbd, struct cnid_dbd_rqst *rqst, struct cnid_dbd_rply *rply
     rply->namelen = data.size;
     rply->name = (char *)data.data;
 
-    LOG(log_debug, logtype_cnid, "dbd_resolve: Resolving CNID %u to did %u name %s",
-        ntohl(rqst->cnid), ntohl(rply->did), rply->name);
+    LOG(log_debug, logtype_cnid, "dbd_resolve(CNID: %u): did: %u, name: \"%s\"",
+        ntohl(rqst->cnid), ntohl(rply->did), rply->name + CNID_NAME_OFS);
 
     rply->result = CNID_DBD_RES_OK;
     return 1;