rpms/dump/devel dump-0.4b40-fixacl.patch, NONE, 1.1 dump.spec, 1.27, 1.28

fedora-cvs-commits at redhat.com fedora-cvs-commits at redhat.com
Thu Jun 9 09:25:32 UTC 2005


Author: jnovy

Update of /cvs/dist/rpms/dump/devel
In directory cvs.devel.redhat.com:/tmp/cvs-serv25028

Modified Files:
	dump.spec 
Added Files:
	dump-0.4b40-fixacl.patch 
Log Message:

- fix restoration of ext3 ACL's (#159617) - Stelian Pop



dump-0.4b40-fixacl.patch:
 CHANGES         |   12 ++-
 restore/tape.c  |    6 +
 restore/xattr.c |  220 +++++++++++++++++++++++++++++++++++++++++++++++++++++---
 3 files changed, 226 insertions(+), 12 deletions(-)

--- NEW FILE dump-0.4b40-fixacl.patch ---
Index: CHANGES
===================================================================
RCS file: /cvsroot/dump/dump/CHANGES,v
retrieving revision 1.275
retrieving revision 1.277
diff -u -r1.275 -r1.277
--- CHANGES	2 May 2005 15:13:40 -0000	1.275
+++ CHANGES	8 Jun 2005 13:24:08 -0000	1.277
@@ -1,4 +1,14 @@
-$Id: CHANGES,v 1.275 2005/05/02 15:13:40 stelian Exp $
+$Id: CHANGES,v 1.277 2005/06/08 13:24:08 stelian Exp $
+
+Changes between versions 0.4b40 and 0.4b41 (released ???????????)
+=================================================================
+
+1.	Fix restore of dumped Access Control Lists. The previous
+	code for EA works fine, but ACLs needed conversion from the
+	ext2/3 disk format to posix_acl format before restoring.
+
+2.	Fix some issues with restoration of EA on big endian
+	platforms.
 
 Changes between versions 0.4b39 and 0.4b40 (released May 2, 2005)
 =================================================================
Index: restore/tape.c
===================================================================
RCS file: /cvsroot/dump/dump/restore/tape.c,v
retrieving revision 1.89
retrieving revision 1.90
diff -u -r1.89 -r1.90
--- restore/tape.c	2 May 2005 15:10:46 -0000	1.89
+++ restore/tape.c	8 Jun 2005 13:24:11 -0000	1.90
@@ -42,7 +42,7 @@
 
 #ifndef lint
 static const char rcsid[] =
-	"$Id: tape.c,v 1.89 2005/05/02 15:10:46 stelian Exp $";
+	"$Id: tape.c,v 1.90 2005/06/08 13:24:11 stelian Exp $";
 #endif /* not lint */
 
 #include <config.h>
@@ -346,6 +346,7 @@
 #endif
 	FLUSHTAPEBUF();
 	findtapeblksize();
+	cvtflag = 0;
 	if (gethead(&spcl) == FAIL) {
 		blkcnt--; /* push back this block */
 		blksread--;
@@ -2412,6 +2413,7 @@
 		errx(1, "Tape read error on first record");
 
 	memcpy(&spclpt, tapebuf, TP_BSIZE);
+	cvtflag = 0;
 	if (converthead(&spclpt) == FAIL) {
 		cvtflag++;
 		if (converthead(&spclpt) == FAIL) {
@@ -2622,7 +2624,7 @@
 		if (checksum((int *)buf) == FAIL)
 			return (FAIL);
 		if (Bcvt)
-			swabst((u_char *)"8i4s31i528bi192b3i", (u_char *)buf);
+			swabst((u_char *)"8i4s1l29i528bi192b4i", (u_char *)buf);
 		goto good;
 	}
 	memcpy(&u_ospcl.s_ospcl, buf, TP_BSIZE);
Index: restore/xattr.c
===================================================================
RCS file: /cvsroot/dump/dump/restore/xattr.c,v
retrieving revision 1.1
retrieving revision 1.3
diff -u -r1.1 -r1.3
--- restore/xattr.c	2 May 2005 15:10:47 -0000	1.1
+++ restore/xattr.c	8 Jun 2005 13:24:12 -0000	1.3
@@ -29,7 +29,7 @@
 
 #ifndef lint
 static const char rcsid[] =
-	"$Id: xattr.c,v 1.1 2005/05/02 15:10:47 stelian Exp $";
+	"$Id: xattr.c,v 1.3 2005/06/08 13:24:12 stelian Exp $";
 #endif /* not lint */
 
 #include <config.h>
@@ -220,6 +220,187 @@
 	return SYSCALL(__NR_llistxattr, path, list, size);
 }
 
+#define POSIX_ACL_XATTR_VERSION 0x0002
+
+#define ACL_UNDEFINED_ID        (-1)
+
+#define ACL_USER_OBJ            (0x01)
+#define ACL_USER                (0x02)
+#define ACL_GROUP_OBJ           (0x04)
+#define ACL_GROUP               (0x08)
+#define ACL_MASK                (0x10)
+#define ACL_OTHER               (0x20)
+
+typedef struct {
+	u_int16_t	e_tag;
+	u_int16_t	e_perm;
+	u_int32_t	e_id;
+} posix_acl_xattr_entry;
+
+typedef struct {
+	u_int32_t		a_version;
+	posix_acl_xattr_entry	a_entries[0];
+} posix_acl_xattr_header;
+
+static inline size_t
+posix_acl_xattr_size(int count)
+{
+	return (sizeof(posix_acl_xattr_header) +
+		(count * sizeof(posix_acl_xattr_entry)));
+}
+
+struct posix_acl_entry {
+	short		e_tag;
+	unsigned short	e_perm;
+	unsigned int	e_id;
+};
+
+struct posix_acl {
+	unsigned int		a_count;
+	struct posix_acl_entry	a_entries[0];
+};
+
+#define EXT3_ACL_VERSION        0x0001
+
+typedef struct {
+	u_int16_t	e_tag;
+	u_int16_t	e_perm;
+	u_int32_t	e_id;
+} ext3_acl_entry;
+
+typedef struct {
+	u_int16_t	e_tag;
+	u_int16_t	e_perm;
+} ext3_acl_entry_short;
+
+typedef struct {
+	u_int32_t	a_version;
+} ext3_acl_header;
+
+static inline int ext3_acl_count(size_t size)
+{
+	ssize_t s;
+	size -= sizeof(ext3_acl_header);
+	s = size - 4 * sizeof(ext3_acl_entry_short);
+	if (s < 0) {
+		if (size % sizeof(ext3_acl_entry_short))
+			return -1;
+		return size / sizeof(ext3_acl_entry_short);
+	} else {
+		if (s % sizeof(ext3_acl_entry))
+			return -1;
+		return s / sizeof(ext3_acl_entry) + 4;
+	}
+}
+
+int
+posix_acl_to_xattr(const struct posix_acl *acl, void *buffer, size_t size) {
+	posix_acl_xattr_header *ext_acl = (posix_acl_xattr_header *)buffer;
+	posix_acl_xattr_entry *ext_entry = ext_acl->a_entries;
+	int real_size, n;
+
+	real_size = posix_acl_xattr_size(acl->a_count);
+	if (!buffer)
+		return real_size;
+	if (real_size > size) {
+		fprintf(stderr, "ACL: not enough space to convert (%d %d)\n", real_size, size);
+		return -1;
+	}
+
+	ext_acl->a_version = POSIX_ACL_XATTR_VERSION;
+#if BYTE_ORDER == BIG_ENDIAN
+	swabst("1i", (u_char *)ext_acl);
+#endif
+
+	for (n=0; n < acl->a_count; n++, ext_entry++) {
+		ext_entry->e_tag  = acl->a_entries[n].e_tag;
+		ext_entry->e_perm = acl->a_entries[n].e_perm;
+		ext_entry->e_id   = acl->a_entries[n].e_id;
+#if BYTE_ORDER == BIG_ENDIAN
+		swabst("2s1i", (u_char *)ext_entry);
+#endif
+	}
+	return real_size;
+}
+
+static struct posix_acl *
+ext3_acl_from_disk(const void *value, size_t size)
+{
+	const char *end = (char *)value + size;
+	int n, count;
+	struct posix_acl *acl;
+
+	if (!value)
+		return NULL;
+	if (size < sizeof(ext3_acl_header)) {
+		fprintf(stderr, "ACL size too little\n");
+		return NULL;
+	}
+#if BYTE_ORDER == BIG_ENDIAN
+	swabst("1i", (u_char *)value);
+#endif
+	if (((ext3_acl_header *)value)->a_version != EXT3_ACL_VERSION) {
+		fprintf(stderr, "ACL version unknown\n");
+		return NULL;
+	}
+	value = (char *)value + sizeof(ext3_acl_header);
+	count = ext3_acl_count(size);
+	if (count < 0) {
+		fprintf(stderr, "ACL bad count\n");
+		return NULL;
+	}
+	if (count == 0)
+		return NULL;
+	acl = malloc(sizeof(struct posix_acl) + count * sizeof(struct posix_acl_entry));
+	if (!acl) {
+		fprintf(stderr, "ACL malloc failed\n");
+		return NULL;
+	}
+	acl->a_count = count;
+
+	for (n=0; n < count; n++) {
+		ext3_acl_entry *entry = (ext3_acl_entry *)value;
+#if BYTE_ORDER == BIG_ENDIAN
+		swabst("2s", (u_char *)entry);
+#endif
+		if ((char *)value + sizeof(ext3_acl_entry_short) > end)
+			goto fail;
+		acl->a_entries[n].e_tag  = entry->e_tag;
+		acl->a_entries[n].e_perm = entry->e_perm;
+		switch(acl->a_entries[n].e_tag) {
+		case ACL_USER_OBJ:
+		case ACL_GROUP_OBJ:
+		case ACL_MASK:
+		case ACL_OTHER:
+			value = (char *)value + sizeof(ext3_acl_entry_short);
+			acl->a_entries[n].e_id = ACL_UNDEFINED_ID;
+			break;
+
+		case ACL_USER:
+		case ACL_GROUP:
+#if BYTE_ORDER == BIG_ENDIAN
+			swabst("4b1i", (u_char *)entry);
+#endif
+			value = (char *)value + sizeof(ext3_acl_entry);
+			if ((char *)value > end)
+				goto fail;
+			acl->a_entries[n].e_id = entry->e_id;
+			break;
+
+		default:
+			goto fail;
+		}
+	}
+	if (value != end)
+		goto fail;
+	return acl;
+
+fail:
+	fprintf(stderr, "ACL bad entry\n");
+	free(acl);
+	return NULL;
+}
+
 /*
  * Dump code starts here :)
  */
@@ -279,8 +460,9 @@
 
 	end = buffer + XATTR_MAXSIZE;
 
-	if (Bcvt)
-		swabst("4i", (u_char *)buffer);
+#if BYTE_ORDER == BIG_ENDIAN
+	swabst("4i", (u_char *)buffer);
+#endif
 
 	if (HDR(buffer)->h_magic != EXT2_XATTR_MAGIC &&
 	    HDR(buffer)->h_magic != EXT2_XATTR_MAGIC2) {
@@ -292,8 +474,9 @@
 
 	/* check the on-disk data structure */
 	entry = FIRST_ENTRY(buffer);
-	if (Bcvt) 
-		swabst("2b1s3i", (u_char *)entry);
+#if BYTE_ORDER == BIG_ENDIAN
+	swabst("2b1s3i", (u_char *)entry);
+#endif
 	while (!IS_LAST_ENTRY(entry)) {
 		struct ext2_xattr_entry *next = EXT2_XATTR_NEXT(entry);
 
@@ -302,8 +485,9 @@
 			return FAIL;
 		}
 		entry = next;
-		if (Bcvt) 
-			swabst("2b1s3i", (u_char *)entry);
+#if BYTE_ORDER == BIG_ENDIAN
+		swabst("2b1s3i", (u_char *)entry);
+#endif
 	}
 	return GOOD;
 }
@@ -333,14 +517,19 @@
 	     entry = EXT2_XATTR_NEXT(entry)) {
 	     	char name[XATTR_MAXSIZE], value[XATTR_MAXSIZE];
 		int off;
+		int convertacl = 0;
 
 		switch (entry->e_name_index) {
 		case EXT2_XATTR_INDEX_USER:
 			strcpy(name, "user.");
 			break;
 		case EXT2_XATTR_INDEX_POSIX_ACL_ACCESS:
+			strcpy(name, "system.posix_acl_access");
+			convertacl = 1;
+			break;
 		case EXT2_XATTR_INDEX_POSIX_ACL_DEFAULT:
-			strcpy(name, "system.");
+			strcpy(name, "system.posix_acl_default");
+			convertacl = 1;
 			break;
 		case EXT2_XATTR_INDEX_TRUSTED:
 			strcpy(name, "trusted.");
@@ -360,9 +549,22 @@
 		memcpy(name + off, entry->e_name, entry->e_name_len);
 		name[off + entry->e_name_len] = '\0';
 
-
 		memcpy(value, buffer + VALUE_OFFSET(buffer, entry), entry->e_value_size);
 
+		if (convertacl) {
+			struct posix_acl *acl;
+			int size;
+
+			acl = ext3_acl_from_disk(value, entry->e_value_size);
+			if (!acl)
+				return FAIL;
+			size = posix_acl_to_xattr(acl, value, XATTR_MAXSIZE);
+			if (size < 0)
+				return FAIL;
+			entry->e_value_size = size;
+			free(acl);
+		}
+
 		if (xattr_cb(name, value, entry->e_value_size, private) != GOOD)
 			return FAIL;
 	}


Index: dump.spec
===================================================================
RCS file: /cvs/dist/rpms/dump/devel/dump.spec,v
retrieving revision 1.27
retrieving revision 1.28
diff -u -r1.27 -r1.28
--- dump.spec	11 May 2005 07:38:54 -0000	1.27
+++ dump.spec	9 Jun 2005 09:25:30 -0000	1.28
@@ -5,11 +5,12 @@
 Summary: Programs for backing up and restoring ext2/ext3 filesystems.
 Name: dump
 Version: 0.4b40
-Release: 2
+Release: 3
 License: BSD
 Group: Applications/Archiving
 URL: http://dump.sourceforge.net
 Source: dump-%{version}.tar.bz2
+Patch0: dump-0.4b40-fixacl.patch
 BuildRoot: %{_tmppath}/%{name}-root
 BuildRequires: e2fsprogs-devel >= 1.18, readline-devel >= 4.2
 BuildRequires: libtermcap-devel, zlib-devel
@@ -43,6 +44,7 @@
 
 %prep
 %setup -q
+%patch0 -p0 -b .fixacl
 
 %build
 %configure %{myoptions} --enable-static --enable-rmt --enable-qfa
@@ -94,6 +96,9 @@
 %{_mandir}/man8/rmt.*
 
 %changelog
+* Thu Jun  9 2005 Jindrich Novy <jnovy at redhat.com> 0.4b40-3
+- fix restoration of ext3 ACL's (#159617) - Stelian Pop
+
 * Wed May 11 2005 Jindrich Novy <jnovy at redhat.com> 0.4b40-2
 - Don't strip binaries to get valid debuginfo
 




More information about the fedora-cvs-commits mailing list