-#if 0
-/*
- * If we're looking for any dead subvolume, take a shortcut and look
- * for any ORPHAN_ITEMs in the tree root
- */
-static int fs_has_dead_subvolumes(int fd)
-{
- int ret;
- struct btrfs_ioctl_search_args args;
- struct btrfs_ioctl_search_key *sk = &args.key;
- struct btrfs_ioctl_search_header sh;
- u64 min_subvolid = 0;
-
-again:
- sk->tree_id = BTRFS_ROOT_TREE_OBJECTID;
- sk->min_objectid = BTRFS_ORPHAN_OBJECTID;
- sk->max_objectid = BTRFS_ORPHAN_OBJECTID;
- sk->min_type = BTRFS_ORPHAN_ITEM_KEY;
- sk->max_type = BTRFS_ORPHAN_ITEM_KEY;
- sk->min_offset = min_subvolid;
- sk->max_offset = (u64)-1;
- sk->min_transid = 0;
- sk->max_transid = (u64)-1;
- sk->nr_items = 1;
-
- ret = ioctl(fd, BTRFS_IOC_TREE_SEARCH, &args);
- if (ret < 0)
- return -errno;
-
- if (!sk->nr_items)
- return 0;
-
- memcpy(&sh, args.buf, sizeof(sh));
- min_subvolid = sh.offset;
-
- /*
- * Verify that the root item is really there and we haven't hit
- * a stale orphan
- */
- sk->tree_id = BTRFS_ROOT_TREE_OBJECTID;
- sk->min_objectid = min_subvolid;
- sk->max_objectid = min_subvolid;
- sk->min_type = BTRFS_ROOT_ITEM_KEY;
- sk->max_type = BTRFS_ROOT_ITEM_KEY;
- sk->min_offset = 0;
- sk->max_offset = (u64)-1;
- sk->min_transid = 0;
- sk->max_transid = (u64)-1;
- sk->nr_items = 1;
-
- ret = ioctl(fd, BTRFS_IOC_TREE_SEARCH, &args);
- if (ret < 0)
- return -errno;
-
- /*
- * Stale orphan, try the next one
- */
- if (!sk->nr_items) {
- min_subvolid++;
- goto again;
- }
-
- return 1;
-}
-#endif
-
-#define SUBVOL_ID_BATCH 1024
-
-/*
- * Enumerate all dead subvolumes that exist in the filesystem.
- * Fill @ids and reallocate to bigger size if needed.
- */
-static int enumerate_dead_subvols(int fd, u64 **ids)
-{
- int ret;
- struct btrfs_ioctl_search_args args;
- struct btrfs_ioctl_search_key *sk = &args.key;
- int idx = 0;
- int count = 0;
-
- memset(&args, 0, sizeof(args));
-
- sk->tree_id = BTRFS_ROOT_TREE_OBJECTID;
- sk->min_objectid = BTRFS_ORPHAN_OBJECTID;
- sk->max_objectid = BTRFS_ORPHAN_OBJECTID;
- sk->min_type = BTRFS_ORPHAN_ITEM_KEY;
- sk->max_type = BTRFS_ORPHAN_ITEM_KEY;
- sk->min_offset = 0;
- sk->max_offset = (u64)-1;
- sk->min_transid = 0;
- sk->max_transid = (u64)-1;
- sk->nr_items = 4096;
-
- *ids = NULL;
- while (1) {
- struct btrfs_ioctl_search_header *sh;
- unsigned long off;
- int i;
-
- ret = ioctl(fd, BTRFS_IOC_TREE_SEARCH, &args);
- if (ret < 0)
- return -errno;
-
- if (!sk->nr_items)
- return idx;
-
- off = 0;
- for (i = 0; i < sk->nr_items; i++) {
- sh = (struct btrfs_ioctl_search_header*)(args.buf + off);
- off += sizeof(*sh);
-
- if (sh->type == BTRFS_ORPHAN_ITEM_KEY) {
- if (idx >= count) {
- u64 *newids;
-
- count += SUBVOL_ID_BATCH;
- newids = (u64*)realloc(*ids,
- count * sizeof(u64));
- if (!newids)
- return -ENOMEM;
- *ids = newids;
- }
- (*ids)[idx] = sh->offset;
- idx++;
- }
- off += sh->len;
-
- sk->min_objectid = sh->objectid;
- sk->min_type = sh->type;
- sk->min_offset = sh->offset;
- }
- if (sk->min_offset < (u64)-1)
- sk->min_offset++;
- else
- break;
- if (sk->min_type != BTRFS_ORPHAN_ITEM_KEY)
- break;
- if (sk->min_objectid != BTRFS_ORPHAN_OBJECTID)
- break;
- }
-
- return idx;
-}
-