- cur = fs_devices->alloc_list.next;
- index = 0;
- i = 0;
-
- calc_size = __btrfs_calc_stripe_size(fs_devices, calc_size, type,
- num_stripes, 0);
-
- if (type & BTRFS_BLOCK_GROUP_DUP) {
- min_free = calc_size * 2;
- min_devices = 1;
- } else {
- min_free = calc_size;
- min_devices = min_stripes;
- }
-
- INIT_LIST_HEAD(&private_devs);
- while (index < num_stripes) {
- device = list_entry(cur, struct btrfs_device, dev_alloc_list);
- BUG_ON(!device->writeable);
- if (device->total_bytes > device->bytes_used)
- avail = device->total_bytes - device->bytes_used;
- else
- avail = 0;
- cur = cur->next;
-
- if (device->in_fs_metadata && avail >= min_free) {
- ret = find_free_dev_extent(trans, device, min_free,
- &devices_info[i].dev_offset,
- &devices_info[i].max_avail);
- if (ret == 0) {
- list_move_tail(&device->dev_alloc_list,
- &private_devs);
- map->stripes[index].dev = device;
- map->stripes[index].physical =
- devices_info[i].dev_offset;
- index++;
- if (type & BTRFS_BLOCK_GROUP_DUP) {
- map->stripes[index].dev = device;
- map->stripes[index].physical =
- devices_info[i].dev_offset +
- calc_size;
- index++;
- }
- } else if (ret != -ENOSPC)
- goto error;
-
- devices_info[i].dev = device;
- i++;
- } else if (device->in_fs_metadata &&
- avail >= BTRFS_STRIPE_LEN) {
- devices_info[i].dev = device;
- devices_info[i].max_avail = avail;
- i++;
- }
-
- if (cur == &fs_devices->alloc_list)
- break;
- }
-
- list_splice(&private_devs, &fs_devices->alloc_list);
- if (index < num_stripes) {
- if (index >= min_stripes) {
- num_stripes = index;
- if (type & (BTRFS_BLOCK_GROUP_RAID10)) {
- num_stripes /= sub_stripes;
- num_stripes *= sub_stripes;
- }
-
- map = __shrink_map_lookup_stripes(map, num_stripes);
- } else if (i >= min_devices) {
- ret = __btrfs_alloc_tiny_space(trans, fs_devices,
- devices_info, i, type,
- &map, min_stripes,
- &calc_size);
- if (ret)
- goto error;
- } else {
- ret = -ENOSPC;
- goto error;