]> arthur.barton.de Git - netatalk.git/commitdiff
ad cp nearly done
authorFrank Lahm <franklahm@googlemail.com>
Sun, 10 Oct 2010 07:21:15 +0000 (09:21 +0200)
committerFrank Lahm <franklahm@googlemail.com>
Sun, 10 Oct 2010 07:21:15 +0000 (09:21 +0200)
bin/ad/ad.c
bin/ad/ad.h
bin/ad/ad_cp.c
bin/ad/ad_util.c
libatalk/vfs/unix.c
libatalk/vfs/vfs.c

index 381b05bffe45ac0063a2cb662aaaf3812f94c3b3..c18268e6fd8a76662d20afc83734714dbe26e1f1 100644 (file)
@@ -36,7 +36,7 @@ static void usage_main(void)
 /*
     printf("Usage: ad ls|rm|cp|mv|set [file|dir, ...]\n");
 */
-    printf("Usage: ad ls [file|dir, ...]\n");
+    printf("Usage: ad ls|cp [file|dir, ...]\n");
 }
 
 int main(int argc, char **argv)
index 4cc7c43cd9878e357a80d1078cb13f33078f9ec2..964f316400fe790d9f64d900354f80b529836aad 100644 (file)
@@ -56,7 +56,10 @@ extern int ad_cp(int argc, char **argv);
 /* ad_util.c */
 extern int openvol(const char *path, afpvol_t *vol);
 extern void closevol(afpvol_t *vol);
-extern cnid_t cnid_for_path(const struct volinfo *vi, const struct vol *vol, const char *path);
+extern cnid_t cnid_for_path(const struct volinfo *vi,
+                            const struct vol *vol,
+                            const char *path,
+                            cnid_t *did);
 extern char *utompath(const struct volinfo *volinfo, const char *upath);
 
 struct FTWELEM {
index 3593602a3b2a4a5ecdbb3603190bfe590386314f..dfb2b7362d788010ea3bff61871ab10b5d8fd8b7 100644 (file)
@@ -319,10 +319,8 @@ static int copy(const char *path,
         dir = path;
     else
         dir++;
-    if (check_netatalk_dirs(dir) != NULL) {
-        SLOG("Skipping Netatalk dir %s", path);
+    if (check_netatalk_dirs(dir) != NULL)
         return FTW_SKIP_SUBTREE;
-    }
 
     /*
      * If we are in case (2) above, we need to append the
@@ -428,31 +426,27 @@ static int copy(const char *path,
 
         /* Create ad dir and copy ".Parent" */
         if (dvolume.volinfo.v_path && dvolume.volinfo.v_adouble == AD_VERSION2) {
+
             /* Create ".AppleDouble" dir */
             mode_t omask = umask(0);
             bstring addir = bfromcstr(to.p_path);
             bcatcstr(addir, "/.AppleDouble");
             mkdir(cfrombstr(addir), 02777);
+            bdestroy(addir);
 
             if (svolume.volinfo.v_path && svolume.volinfo.v_adouble == AD_VERSION2) {
                 /* copy ".Parent" file */
-                bcatcstr(addir, "/.Parent");
-                bstring sdir = bfromcstr(path);
-                bcatcstr(sdir, "/.AppleDouble/.Parent");
-                if (copy_file(-1, cfrombstr(sdir), cfrombstr(addir), 0666) != 0) {
-                    SLOG("Error copying %s -> %s", cfrombstr(sdir), cfrombstr(addir));
+                SLOG("Copying adouble for %s -> %s", path, to.p_path);
+                if (dvolume.volume.vfs->vfs_copyfile(&dvolume.volume, -1, path, to.p_path)) {
+                    SLOG("Error copying adouble for %s -> %s", path, to.p_path);
                     badcp = rval = 1;
                     break;
                 }
-                bdestroy(sdir);
             }
-            bdestroy(addir);
 
             /* Get CNID of Parent and add new childir to CNID database */
             ppdid = pdid;
-            pdid = did;
-            did = cnid_for_path(&dvolume.volinfo, &dvolume.volume, to.p_path);
-            SLOG("got CNID: %u for path: %s", ntohl(did), to.p_path);
+            did = cnid_for_path(&dvolume.volinfo, &dvolume.volume, to.p_path, &pdid);
 
             struct adouble ad;
             struct stat st;
@@ -464,8 +458,13 @@ static int copy(const char *path,
             if (ad_open_metadata(to.p_path, ADFLAGS_DIR, O_RDWR | O_CREAT, &ad) != 0) {
                 ERROR("Error opening adouble for: %s", to.p_path);
             }
+            SLOG("Setting CNID %u for %s", ntohl(did), to.p_path);
             ad_setid( &ad, st.st_dev, st.st_ino, did, pdid, dvolume.db_stamp);
-            ad_setname(&ad, utompath(&dvolume.volinfo, path + ftw->base));
+            ad_setname(&ad, utompath(&dvolume.volinfo, basename(to.p_path)));
+            ad_setdate(&ad, AD_DATE_CREATE | AD_DATE_UNIX, st.st_mtime);
+            ad_setdate(&ad, AD_DATE_MODIFY | AD_DATE_UNIX, st.st_mtime);
+            ad_setdate(&ad, AD_DATE_ACCESS | AD_DATE_UNIX, st.st_mtime);
+            ad_setdate(&ad, AD_DATE_BACKUP, AD_DATE_START);
             ad_flush(&ad);
             ad_close_metadata(&ad);
 
@@ -498,17 +497,19 @@ static int copy(const char *path,
 
         if (dvolume.volinfo.v_path && dvolume.volinfo.v_adouble == AD_VERSION2) {
 
-            SLOG("ad for file: %s", to.p_path);
             mode_t omask = umask(0);
             if (svolume.volinfo.v_path && svolume.volinfo.v_adouble == AD_VERSION2) {
                 /* copy ad-file */
-                if (dvolume.volume.vfs->vfs_copyfile(&dvolume.volume, -1, path, to.p_path))
+                if (dvolume.volume.vfs->vfs_copyfile(&dvolume.volume, -1, path, to.p_path)) {
+                    SLOG("Error copying adouble for %s -> %s", path, to.p_path);
                     badcp = rval = 1;
+                    break;
+                }
             }
 
             /* Get CNID of Parent and add new childir to CNID database */
-            cnid_t cnid = cnid_for_path(&dvolume.volinfo, &dvolume.volume, to.p_path);
-            SLOG("got CNID: %u for path: %s", ntohl(cnid), to.p_path);
+            pdid = did;
+            cnid_t cnid = cnid_for_path(&dvolume.volinfo, &dvolume.volume, to.p_path, &did);
 
             struct adouble ad;
             struct stat st;
@@ -520,8 +521,13 @@ static int copy(const char *path,
             if (ad_open_metadata(to.p_path, 0, O_RDWR | O_CREAT, &ad) != 0) {
                 ERROR("Error opening adouble for: %s", to.p_path);
             }
+            SLOG("setid: DID: %u, CNID: %u, %s", ntohl(did), ntohl(cnid), to.p_path);
             ad_setid( &ad, st.st_dev, st.st_ino, cnid, did, dvolume.db_stamp);
-            ad_setname(&ad, utompath(&dvolume.volinfo, path + ftw->base));
+            ad_setname(&ad, utompath(&dvolume.volinfo, basename(to.p_path)));
+            ad_setdate(&ad, AD_DATE_CREATE | AD_DATE_UNIX, st.st_mtime);
+            ad_setdate(&ad, AD_DATE_MODIFY | AD_DATE_UNIX, st.st_mtime);
+            ad_setdate(&ad, AD_DATE_ACCESS | AD_DATE_UNIX, st.st_mtime);
+            ad_setdate(&ad, AD_DATE_BACKUP, AD_DATE_START);
             ad_flush(&ad);
             ad_close_metadata(&ad);
             umask(omask);
index 8366546a57df24bf0303ac941552564565d19eb9..ac05fc0a8807d09b360330da0d9e6aeef0a12ee0 100644 (file)
@@ -204,11 +204,9 @@ static bstring rel_path_in_vol(const char *path, const char *volpath)
             EC_ZERO(bcatcstr(fpath, "/"));
         EC_ZERO(bcatcstr(fpath, path));
         BSTRING_STRIP_SLASH(fpath);
-        SLOG("Built path: %s", cfrombstr(fpath));
     } else {
         EC_NULL(fpath = bfromcstr(path));
         BSTRING_STRIP_SLASH(fpath);
-        SLOG("Built path: %s", cfrombstr(fpath));
     }
 
     /*
@@ -218,7 +216,6 @@ static bstring rel_path_in_vol(const char *path, const char *volpath)
      * we want: "dir/bla"
      */
     EC_ZERO(bdelete(fpath, 0, strlen(volpath)));
-    SLOG("rel path: %s", cfrombstr(fpath));    
     return fpath;
 
 EC_CLEANUP:
@@ -241,44 +238,47 @@ EC_CLEANUP:
  * 2) ...until we have the CNID for
  *    a) "/afp_volume/topdir/dir"
  *    b) "/afp_volume/dir" (no recursion required)
+ *
+ * @param vi   (r) pointer to volinfo struct
+ * @param vol  (r) pointer to vol struct
+ * @param path (r) path, see above
+ * @param did  (rw) parent CNID of returned CNID
+ *
+ * @returns CNID of path
  */
 cnid_t cnid_for_path(const struct volinfo *vi,
                      const struct vol *vol,
-                     const char *path)
+                     const char *path,
+                     cnid_t *did)
 {
     EC_INIT;
 
-    cnid_t did;
     cnid_t cnid;
     bstring rpath = NULL;
     bstring statpath = NULL;
     struct bstrList *l = NULL;
     struct stat st;
 
-    EC_NULL(rpath = rel_path_in_vol(path, vi->v_path));
-    SLOG("vol:%s, path: %s, rpath: %s", vi->v_path, path, bdata(rpath));
-
-    cnid = htonl(2);
+    cnid = *did = htonl(2);
 
+    EC_NULL(rpath = rel_path_in_vol(path, vi->v_path));
     EC_NULL(statpath = bfromcstr(vi->v_path));
 
     l = bsplit(rpath, '/');
-    SLOG("elem: %s, qty: %u", cfrombstr(l->entry[0]), l->qty);
     for(int i = 0; i < l->qty ; i++) {
-        did = cnid;
+        *did = cnid;
         EC_ZERO(bconcat(statpath, l->entry[i]));
-        SLOG("statpath: %s", cfrombstr(statpath));
         EC_ZERO_LOG(stat(cfrombstr(statpath), &st));
-        SLOG("db query: did: %u, name: %s, dev: %08x, ino: %08x",
-             ntohl(did), cfrombstr(l->entry[i]), st.st_dev, st.st_ino);
+
         cnid = cnid_add(vol->v_cdb,
                         &st,
-                        did,
+                        *did,
                         cfrombstr(l->entry[i]),
                         blength(l->entry[i]),
                         0);
 
         EC_ZERO(bcatcstr(statpath, "/"));
+        
     }
 
 EC_CLEANUP:
index 4812e96421ad49846bc501d042170ff332423bf0..e1eb6a1a979d7c1a1ab1095c32a2ae494c100cab 100644 (file)
@@ -1,9 +1,6 @@
 /*
- * $Id: unix.c,v 1.11 2010-04-18 16:14:51 hat001 Exp $
- *
  * Copyright (c) 1990,1993 Regents of The University of Michigan.
  * All Rights Reserved.  See COPYRIGHT.
- *
  */
 
 #ifdef HAVE_CONFIG_H
@@ -214,7 +211,7 @@ int copy_file(int dirfd, const char *src, const char *dst, mode_t mode)
         return -1;
     }
 
-    if ((dfd = open(dst, O_WRONLY | O_CREAT | O_EXCL, mode)) < 0) {
+    if ((dfd = open(dst, O_WRONLY | O_CREAT | O_TRUNC, mode)) < 0) {
         LOG(log_error, logtype_afpd, "copy_file('%s'/'%s'): open '%s' error: %s",
             src, dst, dst, strerror(errno));
         ret = -1;
index 959a9a5565126aa08cc79995284ef3e35ed1a625..8213dbe24af65d4b7f5ccac3f672cd2b3e9e343e 100644 (file)
@@ -21,6 +21,9 @@
 #include "config.h"
 #endif /* HAVE_CONFIG_H */
 
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <unistd.h>
 #include <string.h>
 #include <stdio.h>
 #include <stdlib.h>
@@ -329,36 +332,53 @@ static int RF_copyfile_adouble(VFS_FUNC_ARGS_COPYFILE)
 {
     EC_INIT;
     bstring s = NULL, d = NULL;
-    const char *name;
-    char *dir = NULL;
-
-    /* get basename */
-    EC_NULL(name = strrchr(src, '/'));
-    name++;
-
-    /* build src path to AppleDouble file*/
-    EC_NULL(dir = dirname(strdup(src)));
-    EC_NULL(s = bfromcstr(dir));
-    EC_ZERO(bcatcstr(s, "/.AppleDouble/"));
-    EC_ZERO(bcatcstr(s, name));
-    free(dir);
-    dir = NULL;
-
-    /* build dst path to AppleDouble file*/
-    EC_NULL(dir = dirname(strdup(dst)));
-    EC_NULL(d = bfromcstr(dir));
-    EC_ZERO(bcatcstr(d, "/.AppleDouble/"));
-    EC_ZERO(bcatcstr(d, name));
-
-    free(dir);
-    dir = NULL;
+    char *dup1 = NULL;
+    char *dup2 = NULL;
+    char *dup3 = NULL;
+    const char *name = NULL;
+    const char *dir = NULL;
+
+    struct stat st;
+    EC_ZERO(stat(dst, &st));
+
+    if (S_ISDIR(st.st_mode)) {
+        /* build src path to AppleDouble file*/
+        EC_NULL(s = bfromcstr(src));
+        EC_ZERO(bcatcstr(s, "/.AppleDouble/.Parent"));
+
+        /* build dst path to AppleDouble file*/
+        EC_NULL(d = bfromcstr(dst));
+        EC_ZERO(bcatcstr(d, "/.AppleDouble/.Parent"));
+    } else {
+        /* get basename */
+        EC_NULL(dup1 = strdup(dst));
+        EC_NULL(name = basename(strdup(dup1)));
+
+        /* build src path to AppleDouble file*/
+        EC_NULL(dup2 = strdup(src));
+        EC_NULL(dir = dirname(dup2));
+        EC_NULL(s = bfromcstr(dir));
+
+        /* build dst path to AppleDouble file*/
+        EC_NULL(dup3 = strdup(dst));
+        EC_NULL(dir = dirname(dup3));
+        EC_NULL(d = bfromcstr(dir));
+
+        EC_ZERO(bcatcstr(s, "/.AppleDouble/"));
+        EC_ZERO(bcatcstr(d, "/.AppleDouble/"));
+        EC_ZERO(bcatcstr(s, name));
+        EC_ZERO(bcatcstr(d, name));
+    }
 
     EC_ZERO(copy_file(sfd, cfrombstr(s), cfrombstr(d), 0666));
 
 EC_CLEANUP:
     bdestroy(s);
     bdestroy(d);
-    if (dir) free(dir);
+    if (dup1) free(dup1);
+    if (dup2) free(dup2);
+    if (dup3) free(dup3);
+
     EC_EXIT;
 }