diff options
author | David Sterba <dsterba@suse.com> | 2015-09-01 16:00:12 +0200 |
---|---|---|
committer | David Sterba <dsterba@suse.com> | 2015-09-02 18:56:52 +0200 |
commit | 17e1e872d4e88e9b5ec524dd9dfb3da40a295096 (patch) | |
tree | 460e11645ac0c37e53073cbc652b50a06b0cf306 /utils.c | |
parent | c4123e1848db8066e5fed55545a334d3377c369f (diff) |
btrfs-progs: handle errors in btrfs_wipe_existing_sb
Failure during superblock wiping is not always a hard error as we're
going to overwrite it anyway but it may catch some errors earlier. The
error message is not very descriptive though, because we don't get back
much information from blkid.
Signed-off-by: David Sterba <dsterba@suse.com>
Diffstat (limited to 'utils.c')
-rw-r--r-- | utils.c | 39 |
1 files changed, 28 insertions, 11 deletions
@@ -798,40 +798,52 @@ err_nomem: return -ENOMEM; } -static void btrfs_wipe_existing_sb(int fd) +static int btrfs_wipe_existing_sb(int fd) { const char *off = NULL; size_t len = 0; loff_t offset; char buf[BUFSIZ]; - int rc = 0; + int ret = 0; blkid_probe pr = NULL; pr = blkid_new_probe(); if (!pr) - return; + return -1; - if (blkid_probe_set_device(pr, fd, 0, 0)) + if (blkid_probe_set_device(pr, fd, 0, 0)) { + ret = -1; goto out; + } - rc = blkid_probe_lookup_value(pr, "SBMAGIC_OFFSET", &off, NULL); - if (!rc) - rc = blkid_probe_lookup_value(pr, "SBMAGIC", NULL, &len); + ret = blkid_probe_lookup_value(pr, "SBMAGIC_OFFSET", &off, NULL); + if (!ret) + ret = blkid_probe_lookup_value(pr, "SBMAGIC", NULL, &len); - if (rc || len == 0 || off == NULL) + if (ret || len == 0 || off == NULL) { + /* + * If lookup fails, the probe did not find any values, eg. for + * a file image or a loop device. Soft error. + */ + ret = 1; goto out; + } offset = strtoll(off, NULL, 10); if (len > sizeof(buf)) len = sizeof(buf); memset(buf, 0, len); - rc = pwrite(fd, buf, len, offset); + ret = pwrite(fd, buf, len, offset); + if (ret != len) { + fprintf(stderr, "ERROR: cannot wipe existing superblock\n"); + ret = -1; + } fsync(fd); out: blkid_free_probe(pr); - return; + return ret; } int btrfs_prepare_device(int fd, char *file, int zero_end, u64 *block_count_ret, @@ -885,7 +897,12 @@ int btrfs_prepare_device(int fd, char *file, int zero_end, u64 *block_count_ret, return 1; } - btrfs_wipe_existing_sb(fd); + ret = btrfs_wipe_existing_sb(fd); + if (ret < 0) { + fprintf(stderr, "ERROR: cannot wipe superblocks on '%s'\n", + file); + return 1; + } *block_count_ret = block_count; return 0; |