btrfs-progs: convert: add support for converting reiserfs

This patch adds support to convert reiserfs file systems in-place to btrfs.

It will convert extended attribute files to btrfs extended attributes,
translate ACLs, coalesce tails that consist of multiple items into one item,
and convert tails that are too big into indirect files.

This requires that libreiserfscore 3.6.27 be available.

Signed-off-by: Jeff Mahoney <jeffm@suse.com>
Signed-off-by: David Sterba <dsterba@suse.com>
master
Jeff Mahoney 2017-08-22 18:30:43 +02:00 committed by David Sterba
parent cbaa70b265
commit 99340c2ef7
8 changed files with 1151 additions and 10 deletions

View File

@ -113,7 +113,7 @@ libbtrfs_headers = send-stream.h send-utils.h send.h kernel-lib/rbtree.h btrfs-l
kernel-lib/radix-tree.h kernel-lib/sizes.h kernel-lib/raid56.h \
extent-cache.h extent_io.h ioctl.h ctree.h btrfsck.h version.h
convert_objects = convert/main.o convert/common.o convert/source-fs.o \
convert/source-ext2.o
convert/source-ext2.o convert/source-reiserfs.o
mkfs_objects = mkfs/main.o mkfs/common.o
TESTS = fsck-tests.sh convert-tests.sh
@ -195,6 +195,7 @@ endif
# external libs required by various binaries; for btrfs-foo,
# specify btrfs_foo_libs = <list of libs>; see $($(subst...)) rules below
btrfs_convert_cflags = -DBTRFSCONVERT_EXT2=$(BTRFSCONVERT_EXT2)
btrfs_convert_cflags += -DBTRFSCONVERT_REISERFS=$(BTRFSCONVERT_REISERFS)
btrfs_fragments_libs = -lgd -lpng -ljpeg -lfreetype
btrfs_debug_tree_objects = cmds-inspect-dump-tree.o
btrfs_show_super_objects = cmds-inspect-dump-super.o

View File

@ -12,6 +12,7 @@ INSTALL = @INSTALL@
DISABLE_DOCUMENTATION = @DISABLE_DOCUMENTATION@
DISABLE_BTRFSCONVERT = @DISABLE_BTRFSCONVERT@
BTRFSCONVERT_EXT2 = @BTRFSCONVERT_EXT2@
BTRFSCONVERT_REISERFS = @BTRFSCONVERT_REISERFS@
SUBST_CFLAGS = @CFLAGS@
SUBST_LDFLAGS = @LDFLAGS@
@ -31,6 +32,6 @@ udevruledir = ${udevdir}/rules.d
# external libs required by various binaries; for btrfs-foo,
# specify btrfs_foo_libs = <list of libs>; see $($(subst...)) rules in Makefile
btrfs_convert_libs = @EXT2FS_LIBS@ @COM_ERR_LIBS@
btrfs_convert_libs = @EXT2FS_LIBS@ @COM_ERR_LIBS@ @REISERFS_LIBS@
MAKEFILE_INC_INCLUDED = yes

View File

@ -106,7 +106,7 @@ AC_SUBST([DISABLE_BTRFSCONVERT])
AC_ARG_WITH([convert],
AS_HELP_STRING([[[]--with-convert[[=auto]]]], [built-in filesystems for convert (default: auto)
supported (comma separated list): ext2]),
supported (comma separated list): ext2,reiserfs]),
[], [with_convert=auto]
)
@ -120,6 +120,7 @@ fi
convertfs=
BTRFSCONVERT_EXT2=0
BTRFSCONVERT_REISERFS=0
if test "x$enable_convert" = xyes; then
if test "x$with_convert" = "xauto" || echo "$with_convert" | grep -q "ext2"; then
PKG_CHECK_MODULES(EXT2FS, [ext2fs >= 1.42],,
@ -131,11 +132,23 @@ if test "x$enable_convert" = xyes; then
convertfs="${convertfs:+$convertfs,}ext2"
BTRFSCONVERT_EXT2=1
fi
if test "x$with_convert" = "xauto"; then
PKG_CHECK_MODULES(REISERFS, [reiserfscore >= 3.6.27],
[BTRFSCONVERT_REISERFS=1],
[BTRFSCONVERT_REISERFS=0])
elif echo "$with_convert" | grep -q "reiserfs"; then
PKG_CHECK_MODULES(REISERFS, [reiserfscore >= 3.6.27],
[BTRFSCONVERT_REISERFS=1],[])
fi
if test "$BTRFSCONVERT_REISERFS" = 1; then
convertfs="${convertfs:+$convertfs,}reiserfs"
fi
fi
AC_SUBST([BTRFSCONVERT_EXT2])
AC_SUBST([BTRFSCONVERT_REISERFS])
# catch typos
tmp=$(echo "$with_convert" | sed -e 's/auto//' | sed -e 's/ext2//' | sed -e 's/,\+/,/')
tmp=$(echo "$with_convert" | sed -e 's/auto//' | sed -e 's/ext2//' | sed -e 's/reiserfs//' | sed -e 's/,\+/,/')
if ! test "x$tmp" = "x"; then
AC_MSG_ERROR([unknown tokens for --with-convert: $tmp])
fi

View File

@ -103,12 +103,16 @@
#include "convert/source-fs.h"
#include "fsfeatures.h"
const struct btrfs_convert_operations ext2_convert_ops;
extern const struct btrfs_convert_operations ext2_convert_ops;
extern const struct btrfs_convert_operations reiserfs_convert_ops;
static const struct btrfs_convert_operations *convert_operations[] = {
#if BTRFSCONVERT_EXT2
&ext2_convert_ops,
#endif
#if BTRFSCONVERT_REISERFS
&reiserfs_convert_ops,
#endif
};
static void *print_copied_inodes(void *p)
@ -416,7 +420,7 @@ static int migrate_one_reserved_range(struct btrfs_trans_handle *trans,
}
/*
* Relocate the used ext2 data in reserved ranges
* Relocate the used source fs data in reserved ranges
*/
static int migrate_reserved_ranges(struct btrfs_trans_handle *trans,
struct btrfs_root *root,
@ -1666,11 +1670,11 @@ static int do_rollback(const char *devname)
ret = btrfs_search_slot(NULL, fs_info->tree_root, &key, &path, 0, 0);
btrfs_release_path(&path);
if (ret > 0) {
error("unable to find ext2 image subvolume, is it deleted?");
error("unable to find source fs image subvolume, is it deleted?");
ret = -ENOENT;
goto close_fs;
} else if (ret < 0) {
error("failed to find ext2 image subvolume: %s",
error("failed to find source fs image subvolume: %s",
strerror(-ret));
goto close_fs;
}
@ -1788,6 +1792,7 @@ static void print_usage(void)
printf("\n");
printf("Supported filesystems:\n");
printf("\text2/3/4: %s\n", BTRFSCONVERT_EXT2 ? "yes" : "no");
printf("\treiserfs: %s\n", BTRFSCONVERT_REISERFS ? "yes" : "no");
}
int main(int argc, char *argv[])

File diff suppressed because it is too large Load Diff

View File

@ -0,0 +1,106 @@
/*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public
* License v2 as published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* General Public License for more details.
*
* You should have received a copy of the GNU General Public
* License along with this program; if not, write to the
* Free Software Foundation, Inc., 59 Temple Place - Suite 330,
* Boston, MA 021110-1307, USA.
*/
#ifndef __BTRFS_CONVERT_SOURCE_REISERFS_H__
#define __BTRFS_CONVERT_SOURCE_REISERFS_H__
#if BTRFSCONVERT_REISERFS
#include "kerncompat.h"
#include <reiserfs/misc.h>
#include <reiserfs/io.h>
#include <reiserfs/reiserfs_lib.h>
#include <reiserfs/reiserfs_fs.h>
#include <linux/kdev_t.h>
#include "convert/source-fs.h"
#define REISERFS_ACL_VERSION 0x0001
/* 23.2.5 acl_tag_t values */
#define ACL_UNDEFINED_TAG (0x00)
#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)
/* 23.2.7 ACL qualifier constants */
#define ACL_UNDEFINED_ID ((id_t)-1)
typedef struct {
__le16 e_tag;
__le16 e_perm;
__le32 e_id;
} ext2_acl_entry;
typedef struct {
__le16 e_tag;
__le16 e_perm;
} ext2_acl_entry_short;
typedef struct {
__le32 a_version;
} ext2_acl_header;
#define ACL_EA_VERSION 0x0002
typedef struct {
__le16 e_tag;
__le16 e_perm;
__le32 e_id;
} acl_ea_entry;
typedef struct {
__le32 a_version;
acl_ea_entry a_entries[0];
} acl_ea_header;
static inline int ext2_acl_count(size_t size)
{
ssize_t s;
size -= sizeof(ext2_acl_header);
s = size - 4 * sizeof(ext2_acl_entry_short);
if (s < 0) {
if (size % sizeof(ext2_acl_entry_short))
return -1;
return size / sizeof(ext2_acl_entry_short);
} else {
if (s % sizeof(ext2_acl_entry))
return -1;
return s / sizeof(ext2_acl_entry) + 4;
}
}
static inline size_t acl_ea_size(int count)
{
return sizeof(acl_ea_header) + count * sizeof(acl_ea_entry);
}
static inline dev_t new_decode_dev(u32 dev)
{
unsigned major = (dev & 0xfff00) >> 8;
unsigned minor = (dev & 0xff) | ((dev >> 12) & 0xfff00);
return MKDEV(major, minor);
}
#endif /* BTRFSCONVERT_REISERFS */
#endif

View File

@ -2707,7 +2707,7 @@ int btrfs_insert_file_extent(struct btrfs_trans_handle *trans,
u64 num_bytes);
int btrfs_insert_inline_extent(struct btrfs_trans_handle *trans,
struct btrfs_root *root, u64 objectid,
u64 offset, char *buffer, size_t size);
u64 offset, const char *buffer, size_t size);
int btrfs_csum_file_block(struct btrfs_trans_handle *trans,
struct btrfs_root *root, u64 alloc_end,
u64 bytenr, char *data, size_t len);

View File

@ -86,7 +86,7 @@ out:
int btrfs_insert_inline_extent(struct btrfs_trans_handle *trans,
struct btrfs_root *root, u64 objectid,
u64 offset, char *buffer, size_t size)
u64 offset, const char *buffer, size_t size)
{
struct btrfs_key key;
struct btrfs_path *path;