Fixed failing hunks.
[rsync/rsync-patches.git] / osx-create-time.diff
CommitLineData
55175a2c
WD
1This patch handles the creation time on OS X by putting it into an
2extended attribute. This is a modified version of a patch that was
3provided by Wesley W. Terpstra.
4
5To use this patch, run these commands for a successful build:
6
7 patch -p1 <patches/osx-create-time.diff
8 ./configure (optional if already run)
9 make
10
11--- old/lib/sysxattrs.c
12+++ new/lib/sysxattrs.c
13@@ -52,29 +52,106 @@ ssize_t sys_llistxattr(const char *path,
14
15 #elif HAVE_OSX_XATTRS
16
17+#include <sys/attr.h>
18+
19+#define CRTIME_XATTR "com.apple.crtime96"
20+#define IS_CRTIME(name) (*(name) == *CRTIME_XATTR && strcmp(name, CRTIME_XATTR) == 0)
21+#define CRTIME_XATTR_LEN (8+4)
22+
23+struct CreationTime {
24+ unsigned long length;
25+ struct timespec date;
26+};
27+
28+static ssize_t getCreationTime(const char *path, char *buf, size_t size)
29+{
30+ struct attrlist attrList;
31+ struct CreationTime attrBuf;
32+
33+ if (buf == NULL)
34+ return CRTIME_XATTR_LEN;
35+ if (size < CRTIME_XATTR_LEN)
36+ return -1; /* Doesn't happen with rsync code... */
37+
38+ memset(&attrList, 0, sizeof attrList);
39+ attrList.bitmapcount = ATTR_BIT_MAP_COUNT;
40+ attrList.commonattr = ATTR_CMN_CRTIME;
510434c7 41+ if (getattrlist(path, &attrList, &attrBuf, sizeof attrBuf, FSOPT_NOFOLLOW) < 0)
55175a2c
WD
42+ return -1;
43+
44+ SIVAL(buf, 0, attrBuf.date.tv_sec);
45+#if SIZEOF_TIME_T > 4
46+ SIVAL(buf, 4, attrBuf.date.tv_sec >> 32);
47+#else
48+ SIVAL(buf, 4, 0);
49+#endif
50+ SIVAL(buf, 8, attrBuf.date.tv_nsec);
51+
52+ return CRTIME_XATTR_LEN;
53+}
54+
55+static int setCreationTime(const char *path, const char *buf, size_t size)
56+{
57+ struct attrlist attrList;
58+ struct timespec date;
59+
60+ if (size != CRTIME_XATTR_LEN)
61+ return -1;
62+
63+ date.tv_sec = IVAL(buf, 0);
64+#if SIZEOF_TIME_T > 4
65+ date.tv_sec += (time_t)IVAL(buf, 4) << 32;
66+#endif
67+ date.tv_nsec = IVAL(buf, 8);
68+
69+ memset(&attrList, 0, sizeof attrList);
70+ attrList.bitmapcount = ATTR_BIT_MAP_COUNT;
71+ attrList.commonattr = ATTR_CMN_CRTIME;
510434c7 72+ return setattrlist(path, &attrList, &date, sizeof date, FSOPT_NOFOLLOW);
55175a2c
WD
73+}
74+
75 ssize_t sys_lgetxattr(const char *path, const char *name, void *value, size_t size)
76 {
77+ if (IS_CRTIME(name))
78+ return getCreationTime(path, value, size);
79 return getxattr(path, name, value, size, 0, XATTR_NOFOLLOW);
80 }
81
82 ssize_t sys_fgetxattr(int filedes, const char *name, void *value, size_t size)
83 {
84+ /* XXX Figure out how to get creation date from an open filedes? */
85 return fgetxattr(filedes, name, value, size, 0, 0);
86 }
87
88 int sys_lsetxattr(const char *path, const char *name, const void *value, size_t size)
89 {
90+ if (IS_CRTIME(name))
91+ return setCreationTime(path, value, size);
92 return setxattr(path, name, value, size, 0, XATTR_NOFOLLOW);
93 }
94
95 int sys_lremovexattr(const char *path, const char *name)
96 {
97+ /* Every file on hfs+ has this; you can't remove it... */
98+ if (IS_CRTIME(name))
99+ return 0;
100 return removexattr(path, name, XATTR_NOFOLLOW);
101 }
102
103 ssize_t sys_llistxattr(const char *path, char *list, size_t size)
104 {
105- return listxattr(path, list, size, XATTR_NOFOLLOW);
106+ ssize_t ret = listxattr(path, list, size, XATTR_NOFOLLOW);
107+ if (ret < 0)
108+ return ret;
109+ ret += sizeof CRTIME_XATTR;
110+ if (list) {
111+ if ((size_t)ret > size) {
112+ errno = ERANGE;
113+ return -1;
114+ }
115+ memcpy(list + ret - sizeof CRTIME_XATTR, CRTIME_XATTR, sizeof CRTIME_XATTR);
116+ }
117+ return ret;
118 }
119
120 #elif HAVE_FREEBSD_XATTRS