diff options
author | Cristian Ciocaltea <cristian.ciocaltea@collabora.com> | 2023-05-30 23:54:13 +0300 |
---|---|---|
committer | Cristian Ciocaltea <cristian.ciocaltea@collabora.com> | 2023-06-05 12:09:55 +0300 |
commit | ba9f34069605788154e13385b36a96974d1455bc (patch) | |
tree | be6a8f249d32407c64a5ab03ce37b6434a9ae23b /drivers/md/raid10.c | |
parent | e786aef0869c711a70680d315ac2b838f03448ed (diff) | |
parent | fa74641fb6b93a19ccb50579886ecc98320230f9 (diff) | |
download | linux-ba9f34069605788154e13385b36a96974d1455bc.tar.gz |
Merge tag 'v6.1.29' into amd-staging-drm-next
Fix conflicts: drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd.h drivers/gpu/drm/amd/amdgpu/amdgpu_amdkfd_gpuvm.c drivers/gpu/drm/amd/amdgpu/amdgpu_drv.c drivers/gpu/drm/amd/amdgpu/amdgpu_mes.c drivers/gpu/drm/amd/amdgpu/amdgpu_psp.c drivers/gpu/drm/amd/amdgpu/amdgpu_ucode.h drivers/gpu/drm/amd/amdgpu/amdgpu_vcn.c drivers/gpu/drm/amd/amdgpu/soc21.c drivers/gpu/drm/amd/amdkfd/kfd_chardev.c drivers/gpu/drm/amd/amdkfd/kfd_crat.c drivers/gpu/drm/amd/amdkfd/kfd_device.c drivers/gpu/drm/amd/amdkfd/kfd_migrate.c drivers/gpu/drm/amd/amdkfd/kfd_topology.c drivers/gpu/drm/amd/amdkfd/kfd_topology.h drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_crtc.c drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_helpers.c drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_psr.c drivers/gpu/drm/amd/display/dc/clk_mgr/dcn314/dcn314_smu.c drivers/gpu/drm/amd/display/dc/core/dc_link.c drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c drivers/gpu/drm/amd/display/dc/dc_link.h drivers/gpu/drm/amd/display/dc/dcn21/dcn21_resource.c drivers/gpu/drm/amd/display/dc/dcn30/dcn30_optc.c drivers/gpu/drm/amd/display/dc/dcn30/dcn30_resource.c drivers/gpu/drm/amd/display/dc/dcn302/dcn302_resource.c drivers/gpu/drm/amd/display/dc/dcn303/dcn303_resource.c drivers/gpu/drm/amd/display/dc/dcn314/dcn314_dio_stream_encoder.c drivers/gpu/drm/amd/display/dc/dcn314/dcn314_hwseq.c drivers/gpu/drm/amd/display/dc/dcn314/dcn314_hwseq.h drivers/gpu/drm/amd/display/dc/dcn32/dcn32_hwseq.c drivers/gpu/drm/amd/display/dc/dcn32/dcn32_resource.h drivers/gpu/drm/amd/display/dc/dcn321/dcn321_resource.c drivers/gpu/drm/amd/display/dc/dml/dcn20/dcn20_fpu.c drivers/gpu/drm/amd/display/dc/dml/dcn32/dcn32_fpu.c drivers/gpu/drm/amd/display/dc/dml/dcn32/display_mode_vba_32.c drivers/gpu/drm/amd/display/dc/dml/dcn32/display_mode_vba_32.h drivers/gpu/drm/amd/display/dc/dml/dcn321/dcn321_fpu.c drivers/gpu/drm/amd/display/dc/inc/hw/dccg.h drivers/gpu/drm/amd/display/modules/power/power_helpers.c drivers/gpu/drm/amd/display/modules/power/power_helpers.h drivers/gpu/drm/amd/pm/amdgpu_pm.c drivers/gpu/drm/amd/pm/swsmu/inc/pmfw_if/smu13_driver_if_v13_0_4.h drivers/gpu/drm/amd/pm/swsmu/inc/smu_v13_0.h drivers/gpu/drm/amd/pm/swsmu/smu13/smu_v13_0_7_ppt.c drivers/gpu/drm/drm_edid.c drivers/gpu/drm/i915/display/intel_fbdev.c drivers/gpu/drm/msm/disp/dpu1/dpu_hw_catalog.c drivers/gpu/drm/msm/msm_drv.c drivers/gpu/drm/nouveau/dispnv50/disp.c drivers/gpu/drm/ttm/ttm_pool.c drivers/gpu/drm/vmwgfx/vmwgfx_kms.c drivers/gpu/drm/vmwgfx/vmwgfx_ldu.c drivers/thunderbolt/quirks.c Signed-off-by: Cristian Ciocaltea <cristian.ciocaltea@collabora.com>
Diffstat (limited to 'drivers/md/raid10.c')
-rw-r--r-- | drivers/md/raid10.c | 96 |
1 files changed, 53 insertions, 43 deletions
diff --git a/drivers/md/raid10.c b/drivers/md/raid10.c index 9a6503f5cb98..67398394cc9c 100644 --- a/drivers/md/raid10.c +++ b/drivers/md/raid10.c @@ -995,11 +995,15 @@ static bool stop_waiting_barrier(struct r10conf *conf) (!bio_list_empty(&bio_list[0]) || !bio_list_empty(&bio_list[1]))) return true; - /* move on if recovery thread is blocked by us */ - if (conf->mddev->thread->tsk == current && - test_bit(MD_RECOVERY_RUNNING, &conf->mddev->recovery) && - conf->nr_queued > 0) + /* + * move on if io is issued from raid10d(), nr_pending is not released + * from original io(see handle_read_error()). All raise barrier is + * blocked until this io is done. + */ + if (conf->mddev->thread->tsk == current) { + WARN_ON_ONCE(atomic_read(&conf->nr_pending) == 0); return true; + } return false; } @@ -1244,7 +1248,8 @@ static void raid10_read_request(struct mddev *mddev, struct bio *bio, } slot = r10_bio->read_slot; - if (blk_queue_io_stat(bio->bi_bdev->bd_disk->queue)) + if (!r10_bio->start_time && + blk_queue_io_stat(bio->bi_bdev->bd_disk->queue)) r10_bio->start_time = bio_start_io_acct(bio); read_bio = bio_alloc_clone(rdev->bdev, bio, gfp, &mddev->bio_set); @@ -1574,6 +1579,7 @@ static void __make_request(struct mddev *mddev, struct bio *bio, int sectors) r10_bio->sector = bio->bi_iter.bi_sector; r10_bio->state = 0; r10_bio->read_slot = -1; + r10_bio->start_time = 0; memset(r10_bio->devs, 0, sizeof(r10_bio->devs[0]) * conf->geo.raid_disks); @@ -2609,11 +2615,22 @@ static void recovery_request_write(struct mddev *mddev, struct r10bio *r10_bio) { struct r10conf *conf = mddev->private; int d; - struct bio *wbio, *wbio2; + struct bio *wbio = r10_bio->devs[1].bio; + struct bio *wbio2 = r10_bio->devs[1].repl_bio; + + /* Need to test wbio2->bi_end_io before we call + * submit_bio_noacct as if the former is NULL, + * the latter is free to free wbio2. + */ + if (wbio2 && !wbio2->bi_end_io) + wbio2 = NULL; if (!test_bit(R10BIO_Uptodate, &r10_bio->state)) { fix_recovery_read_error(r10_bio); - end_sync_request(r10_bio); + if (wbio->bi_end_io) + end_sync_request(r10_bio); + if (wbio2) + end_sync_request(r10_bio); return; } @@ -2622,14 +2639,6 @@ static void recovery_request_write(struct mddev *mddev, struct r10bio *r10_bio) * and submit the write request */ d = r10_bio->devs[1].devnum; - wbio = r10_bio->devs[1].bio; - wbio2 = r10_bio->devs[1].repl_bio; - /* Need to test wbio2->bi_end_io before we call - * submit_bio_noacct as if the former is NULL, - * the latter is free to free wbio2. - */ - if (wbio2 && !wbio2->bi_end_io) - wbio2 = NULL; if (wbio->bi_end_io) { atomic_inc(&conf->mirrors[d].rdev->nr_pending); md_sync_acct(conf->mirrors[d].rdev->bdev, bio_sectors(wbio)); @@ -2978,9 +2987,13 @@ static void handle_read_error(struct mddev *mddev, struct r10bio *r10_bio) md_error(mddev, rdev); rdev_dec_pending(rdev, mddev); - allow_barrier(conf); r10_bio->state = 0; raid10_read_request(mddev, r10_bio->master_bio, r10_bio); + /* + * allow_barrier after re-submit to ensure no sync io + * can be issued while regular io pending. + */ + allow_barrier(conf); } static void handle_write_completed(struct r10conf *conf, struct r10bio *r10_bio) @@ -3289,10 +3302,6 @@ static sector_t raid10_sync_request(struct mddev *mddev, sector_t sector_nr, sector_t chunk_mask = conf->geo.chunk_mask; int page_idx = 0; - if (!mempool_initialized(&conf->r10buf_pool)) - if (init_resync(conf)) - return 0; - /* * Allow skipping a full rebuild for incremental assembly * of a clean array, like RAID1 does. @@ -3308,6 +3317,10 @@ static sector_t raid10_sync_request(struct mddev *mddev, sector_t sector_nr, return mddev->dev_sectors - sector_nr; } + if (!mempool_initialized(&conf->r10buf_pool)) + if (init_resync(conf)) + return 0; + skipped: max_sector = mddev->dev_sectors; if (test_bit(MD_RECOVERY_SYNC, &mddev->recovery) || @@ -4004,6 +4017,20 @@ static int setup_geo(struct geom *geo, struct mddev *mddev, enum geo_type new) return nc*fc; } +static void raid10_free_conf(struct r10conf *conf) +{ + if (!conf) + return; + + mempool_exit(&conf->r10bio_pool); + kfree(conf->mirrors); + kfree(conf->mirrors_old); + kfree(conf->mirrors_new); + safe_put_page(conf->tmppage); + bioset_exit(&conf->bio_split); + kfree(conf); +} + static struct r10conf *setup_conf(struct mddev *mddev) { struct r10conf *conf = NULL; @@ -4086,13 +4113,7 @@ static struct r10conf *setup_conf(struct mddev *mddev) return conf; out: - if (conf) { - mempool_exit(&conf->r10bio_pool); - kfree(conf->mirrors); - safe_put_page(conf->tmppage); - bioset_exit(&conf->bio_split); - kfree(conf); - } + raid10_free_conf(conf); return ERR_PTR(err); } @@ -4129,6 +4150,9 @@ static int raid10_run(struct mddev *mddev) if (!conf) goto out; + mddev->thread = conf->thread; + conf->thread = NULL; + if (mddev_is_clustered(conf->mddev)) { int fc, fo; @@ -4141,9 +4165,6 @@ static int raid10_run(struct mddev *mddev) } } - mddev->thread = conf->thread; - conf->thread = NULL; - if (mddev->queue) { blk_queue_max_write_zeroes_sectors(mddev->queue, 0); blk_queue_io_min(mddev->queue, mddev->chunk_sectors << 9); @@ -4283,10 +4304,7 @@ static int raid10_run(struct mddev *mddev) out_free_conf: md_unregister_thread(&mddev->thread); - mempool_exit(&conf->r10bio_pool); - safe_put_page(conf->tmppage); - kfree(conf->mirrors); - kfree(conf); + raid10_free_conf(conf); mddev->private = NULL; out: return -EIO; @@ -4294,15 +4312,7 @@ out: static void raid10_free(struct mddev *mddev, void *priv) { - struct r10conf *conf = priv; - - mempool_exit(&conf->r10bio_pool); - safe_put_page(conf->tmppage); - kfree(conf->mirrors); - kfree(conf->mirrors_old); - kfree(conf->mirrors_new); - bioset_exit(&conf->bio_split); - kfree(conf); + raid10_free_conf(priv); } static void raid10_quiesce(struct mddev *mddev, int quiesce) |