diff options
author | NeilBrown <neilb@suse.de> | 2011-07-25 21:35:35 -0400 |
---|---|---|
committer | NeilBrown <neilb@suse.de> | 2011-07-25 21:35:35 -0400 |
commit | cc94015a9eac5d511fe9b716624d8fdf9c6e64b2 (patch) | |
tree | f8bc6cb3e5733f7101ea66223c27e30dc09b9bb1 /drivers/md/raid5.c | |
parent | c5709ef6a094c72b56355590bfa55cc107e98376 (diff) |
md/raid5: move stripe_head_state and more code into handle_stripe.
By defining the 'stripe_head_state' in 'handle_stripe', we can move
some common code out of handle_stripe[56]() and into handle_stripe.
The means that all accesses for stripe_head_state in handle_stripe[56]
need to be 's->' instead of 's.', but the compiler should inline
those functions and just use a direct stack reference, and future
patches while hoist most of this code up into handle_stripe()
so we will revert to "s.".
Signed-off-by: NeilBrown <neilb@suse.de>
Reviewed-by: Namhyung Kim <namhyung@gmail.com>
Diffstat (limited to 'drivers/md/raid5.c')
-rw-r--r-- | drivers/md/raid5.c | 340 |
1 files changed, 158 insertions, 182 deletions
diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c index bc15f48be78d..36873cfc3291 100644 --- a/drivers/md/raid5.c +++ b/drivers/md/raid5.c | |||
@@ -2999,24 +2999,13 @@ static void handle_stripe_expansion(raid5_conf_t *conf, struct stripe_head *sh, | |||
2999 | * | 2999 | * |
3000 | */ | 3000 | */ |
3001 | 3001 | ||
3002 | static void handle_stripe5(struct stripe_head *sh) | 3002 | static void handle_stripe5(struct stripe_head *sh, struct stripe_head_state *s) |
3003 | { | 3003 | { |
3004 | raid5_conf_t *conf = sh->raid_conf; | 3004 | raid5_conf_t *conf = sh->raid_conf; |
3005 | int disks = sh->disks, i; | 3005 | int disks = sh->disks, i; |
3006 | struct stripe_head_state s; | ||
3007 | struct r5dev *dev; | 3006 | struct r5dev *dev; |
3008 | int prexor; | 3007 | int prexor; |
3009 | 3008 | ||
3010 | memset(&s, 0, sizeof(s)); | ||
3011 | pr_debug("handling stripe %llu, state=%#lx cnt=%d, pd_idx=%d check:%d " | ||
3012 | "reconstruct:%d\n", (unsigned long long)sh->sector, sh->state, | ||
3013 | atomic_read(&sh->count), sh->pd_idx, sh->check_state, | ||
3014 | sh->reconstruct_state); | ||
3015 | |||
3016 | s.syncing = test_bit(STRIPE_SYNCING, &sh->state); | ||
3017 | s.expanding = test_bit(STRIPE_EXPAND_SOURCE, &sh->state); | ||
3018 | s.expanded = test_bit(STRIPE_EXPAND_READY, &sh->state); | ||
3019 | |||
3020 | /* Now to look around and see what can be done */ | 3009 | /* Now to look around and see what can be done */ |
3021 | rcu_read_lock(); | 3010 | rcu_read_lock(); |
3022 | spin_lock_irq(&conf->device_lock); | 3011 | spin_lock_irq(&conf->device_lock); |
@@ -3039,25 +3028,28 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3039 | set_bit(R5_Wantfill, &dev->flags); | 3028 | set_bit(R5_Wantfill, &dev->flags); |
3040 | 3029 | ||
3041 | /* now count some things */ | 3030 | /* now count some things */ |
3042 | if (test_bit(R5_LOCKED, &dev->flags)) s.locked++; | 3031 | if (test_bit(R5_LOCKED, &dev->flags)) |
3043 | if (test_bit(R5_UPTODATE, &dev->flags)) s.uptodate++; | 3032 | s->locked++; |
3044 | if (test_bit(R5_Wantcompute, &dev->flags)) s.compute++; | 3033 | if (test_bit(R5_UPTODATE, &dev->flags)) |
3034 | s->uptodate++; | ||
3035 | if (test_bit(R5_Wantcompute, &dev->flags)) | ||
3036 | s->compute++; | ||
3045 | 3037 | ||
3046 | if (test_bit(R5_Wantfill, &dev->flags)) | 3038 | if (test_bit(R5_Wantfill, &dev->flags)) |
3047 | s.to_fill++; | 3039 | s->to_fill++; |
3048 | else if (dev->toread) | 3040 | else if (dev->toread) |
3049 | s.to_read++; | 3041 | s->to_read++; |
3050 | if (dev->towrite) { | 3042 | if (dev->towrite) { |
3051 | s.to_write++; | 3043 | s->to_write++; |
3052 | if (!test_bit(R5_OVERWRITE, &dev->flags)) | 3044 | if (!test_bit(R5_OVERWRITE, &dev->flags)) |
3053 | s.non_overwrite++; | 3045 | s->non_overwrite++; |
3054 | } | 3046 | } |
3055 | if (dev->written) | 3047 | if (dev->written) |
3056 | s.written++; | 3048 | s->written++; |
3057 | rdev = rcu_dereference(conf->disks[i].rdev); | 3049 | rdev = rcu_dereference(conf->disks[i].rdev); |
3058 | if (s.blocked_rdev == NULL && | 3050 | if (s->blocked_rdev == NULL && |
3059 | rdev && unlikely(test_bit(Blocked, &rdev->flags))) { | 3051 | rdev && unlikely(test_bit(Blocked, &rdev->flags))) { |
3060 | s.blocked_rdev = rdev; | 3052 | s->blocked_rdev = rdev; |
3061 | atomic_inc(&rdev->nr_pending); | 3053 | atomic_inc(&rdev->nr_pending); |
3062 | } | 3054 | } |
3063 | clear_bit(R5_Insync, &dev->flags); | 3055 | clear_bit(R5_Insync, &dev->flags); |
@@ -3078,62 +3070,62 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3078 | if (test_bit(R5_ReadError, &dev->flags)) | 3070 | if (test_bit(R5_ReadError, &dev->flags)) |
3079 | clear_bit(R5_Insync, &dev->flags); | 3071 | clear_bit(R5_Insync, &dev->flags); |
3080 | if (!test_bit(R5_Insync, &dev->flags)) { | 3072 | if (!test_bit(R5_Insync, &dev->flags)) { |
3081 | s.failed++; | 3073 | s->failed++; |
3082 | s.failed_num[0] = i; | 3074 | s->failed_num[0] = i; |
3083 | } | 3075 | } |
3084 | } | 3076 | } |
3085 | spin_unlock_irq(&conf->device_lock); | 3077 | spin_unlock_irq(&conf->device_lock); |
3086 | rcu_read_unlock(); | 3078 | rcu_read_unlock(); |
3087 | 3079 | ||
3088 | if (unlikely(s.blocked_rdev)) { | 3080 | if (unlikely(s->blocked_rdev)) { |
3089 | if (s.syncing || s.expanding || s.expanded || | 3081 | if (s->syncing || s->expanding || s->expanded || |
3090 | s.to_write || s.written) { | 3082 | s->to_write || s->written) { |
3091 | set_bit(STRIPE_HANDLE, &sh->state); | 3083 | set_bit(STRIPE_HANDLE, &sh->state); |
3092 | goto unlock; | 3084 | return; |
3093 | } | 3085 | } |
3094 | /* There is nothing for the blocked_rdev to block */ | 3086 | /* There is nothing for the blocked_rdev to block */ |
3095 | rdev_dec_pending(s.blocked_rdev, conf->mddev); | 3087 | rdev_dec_pending(s->blocked_rdev, conf->mddev); |
3096 | s.blocked_rdev = NULL; | 3088 | s->blocked_rdev = NULL; |
3097 | } | 3089 | } |
3098 | 3090 | ||
3099 | if (s.to_fill && !test_bit(STRIPE_BIOFILL_RUN, &sh->state)) { | 3091 | if (s->to_fill && !test_bit(STRIPE_BIOFILL_RUN, &sh->state)) { |
3100 | set_bit(STRIPE_OP_BIOFILL, &s.ops_request); | 3092 | set_bit(STRIPE_OP_BIOFILL, &s->ops_request); |
3101 | set_bit(STRIPE_BIOFILL_RUN, &sh->state); | 3093 | set_bit(STRIPE_BIOFILL_RUN, &sh->state); |
3102 | } | 3094 | } |
3103 | 3095 | ||
3104 | pr_debug("locked=%d uptodate=%d to_read=%d" | 3096 | pr_debug("locked=%d uptodate=%d to_read=%d" |
3105 | " to_write=%d failed=%d failed_num=%d\n", | 3097 | " to_write=%d failed=%d failed_num=%d\n", |
3106 | s.locked, s.uptodate, s.to_read, s.to_write, | 3098 | s->locked, s->uptodate, s->to_read, s->to_write, |
3107 | s.failed, s.failed_num[0]); | 3099 | s->failed, s->failed_num[0]); |
3108 | /* check if the array has lost two devices and, if so, some requests might | 3100 | /* check if the array has lost two devices and, if so, some requests might |
3109 | * need to be failed | 3101 | * need to be failed |
3110 | */ | 3102 | */ |
3111 | if (s.failed > 1 && s.to_read+s.to_write+s.written) | 3103 | if (s->failed > 1 && s->to_read+s->to_write+s->written) |
3112 | handle_failed_stripe(conf, sh, &s, disks, &s.return_bi); | 3104 | handle_failed_stripe(conf, sh, s, disks, &s->return_bi); |
3113 | if (s.failed > 1 && s.syncing) { | 3105 | if (s->failed > 1 && s->syncing) { |
3114 | md_done_sync(conf->mddev, STRIPE_SECTORS,0); | 3106 | md_done_sync(conf->mddev, STRIPE_SECTORS,0); |
3115 | clear_bit(STRIPE_SYNCING, &sh->state); | 3107 | clear_bit(STRIPE_SYNCING, &sh->state); |
3116 | s.syncing = 0; | 3108 | s->syncing = 0; |
3117 | } | 3109 | } |
3118 | 3110 | ||
3119 | /* might be able to return some write requests if the parity block | 3111 | /* might be able to return some write requests if the parity block |
3120 | * is safe, or on a failed drive | 3112 | * is safe, or on a failed drive |
3121 | */ | 3113 | */ |
3122 | dev = &sh->dev[sh->pd_idx]; | 3114 | dev = &sh->dev[sh->pd_idx]; |
3123 | if ( s.written && | 3115 | if (s->written && |
3124 | ((test_bit(R5_Insync, &dev->flags) && | 3116 | ((test_bit(R5_Insync, &dev->flags) && |
3125 | !test_bit(R5_LOCKED, &dev->flags) && | 3117 | !test_bit(R5_LOCKED, &dev->flags) && |
3126 | test_bit(R5_UPTODATE, &dev->flags)) || | 3118 | test_bit(R5_UPTODATE, &dev->flags)) || |
3127 | (s.failed == 1 && s.failed_num[0] == sh->pd_idx))) | 3119 | (s->failed == 1 && s->failed_num[0] == sh->pd_idx))) |
3128 | handle_stripe_clean_event(conf, sh, disks, &s.return_bi); | 3120 | handle_stripe_clean_event(conf, sh, disks, &s->return_bi); |
3129 | 3121 | ||
3130 | /* Now we might consider reading some blocks, either to check/generate | 3122 | /* Now we might consider reading some blocks, either to check/generate |
3131 | * parity, or to satisfy requests | 3123 | * parity, or to satisfy requests |
3132 | * or to load a block that is being partially written. | 3124 | * or to load a block that is being partially written. |
3133 | */ | 3125 | */ |
3134 | if (s.to_read || s.non_overwrite || | 3126 | if (s->to_read || s->non_overwrite || |
3135 | (s.syncing && (s.uptodate + s.compute < disks)) || s.expanding) | 3127 | (s->syncing && (s->uptodate + s->compute < disks)) || s->expanding) |
3136 | handle_stripe_fill5(sh, &s, disks); | 3128 | handle_stripe_fill5(sh, s, disks); |
3137 | 3129 | ||
3138 | /* Now we check to see if any write operations have recently | 3130 | /* Now we check to see if any write operations have recently |
3139 | * completed | 3131 | * completed |
@@ -3158,12 +3150,12 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3158 | if (prexor) | 3150 | if (prexor) |
3159 | continue; | 3151 | continue; |
3160 | if (!test_bit(R5_Insync, &dev->flags) || | 3152 | if (!test_bit(R5_Insync, &dev->flags) || |
3161 | (i == sh->pd_idx && s.failed == 0)) | 3153 | (i == sh->pd_idx && s->failed == 0)) |
3162 | set_bit(STRIPE_INSYNC, &sh->state); | 3154 | set_bit(STRIPE_INSYNC, &sh->state); |
3163 | } | 3155 | } |
3164 | } | 3156 | } |
3165 | if (test_and_clear_bit(STRIPE_PREREAD_ACTIVE, &sh->state)) | 3157 | if (test_and_clear_bit(STRIPE_PREREAD_ACTIVE, &sh->state)) |
3166 | s.dec_preread_active = 1; | 3158 | s->dec_preread_active = 1; |
3167 | } | 3159 | } |
3168 | 3160 | ||
3169 | /* Now to consider new write requests and what else, if anything | 3161 | /* Now to consider new write requests and what else, if anything |
@@ -3172,8 +3164,8 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3172 | * 2/ A 'check' operation is in flight, as it may clobber the parity | 3164 | * 2/ A 'check' operation is in flight, as it may clobber the parity |
3173 | * block. | 3165 | * block. |
3174 | */ | 3166 | */ |
3175 | if (s.to_write && !sh->reconstruct_state && !sh->check_state) | 3167 | if (s->to_write && !sh->reconstruct_state && !sh->check_state) |
3176 | handle_stripe_dirtying5(conf, sh, &s, disks); | 3168 | handle_stripe_dirtying5(conf, sh, s, disks); |
3177 | 3169 | ||
3178 | /* maybe we need to check and possibly fix the parity for this stripe | 3170 | /* maybe we need to check and possibly fix the parity for this stripe |
3179 | * Any reads will already have been scheduled, so we just see if enough | 3171 | * Any reads will already have been scheduled, so we just see if enough |
@@ -3181,12 +3173,13 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3181 | * dependent operations are in flight. | 3173 | * dependent operations are in flight. |
3182 | */ | 3174 | */ |
3183 | if (sh->check_state || | 3175 | if (sh->check_state || |
3184 | (s.syncing && s.locked == 0 && | 3176 | (s->syncing && s->locked == 0 && |
3185 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state) && | 3177 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state) && |
3186 | !test_bit(STRIPE_INSYNC, &sh->state))) | 3178 | !test_bit(STRIPE_INSYNC, &sh->state))) |
3187 | handle_parity_checks5(conf, sh, &s, disks); | 3179 | handle_parity_checks5(conf, sh, s, disks); |
3188 | 3180 | ||
3189 | if (s.syncing && s.locked == 0 && test_bit(STRIPE_INSYNC, &sh->state)) { | 3181 | if (s->syncing && s->locked == 0 |
3182 | && test_bit(STRIPE_INSYNC, &sh->state)) { | ||
3190 | md_done_sync(conf->mddev, STRIPE_SECTORS,1); | 3183 | md_done_sync(conf->mddev, STRIPE_SECTORS,1); |
3191 | clear_bit(STRIPE_SYNCING, &sh->state); | 3184 | clear_bit(STRIPE_SYNCING, &sh->state); |
3192 | } | 3185 | } |
@@ -3194,22 +3187,22 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3194 | /* If the failed drive is just a ReadError, then we might need to progress | 3187 | /* If the failed drive is just a ReadError, then we might need to progress |
3195 | * the repair/check process | 3188 | * the repair/check process |
3196 | */ | 3189 | */ |
3197 | if (s.failed == 1 && !conf->mddev->ro && | 3190 | if (s->failed == 1 && !conf->mddev->ro && |
3198 | test_bit(R5_ReadError, &sh->dev[s.failed_num[0]].flags) | 3191 | test_bit(R5_ReadError, &sh->dev[s->failed_num[0]].flags) |
3199 | && !test_bit(R5_LOCKED, &sh->dev[s.failed_num[0]].flags) | 3192 | && !test_bit(R5_LOCKED, &sh->dev[s->failed_num[0]].flags) |
3200 | && test_bit(R5_UPTODATE, &sh->dev[s.failed_num[0]].flags) | 3193 | && test_bit(R5_UPTODATE, &sh->dev[s->failed_num[0]].flags) |
3201 | ) { | 3194 | ) { |
3202 | dev = &sh->dev[s.failed_num[0]]; | 3195 | dev = &sh->dev[s->failed_num[0]]; |
3203 | if (!test_bit(R5_ReWrite, &dev->flags)) { | 3196 | if (!test_bit(R5_ReWrite, &dev->flags)) { |
3204 | set_bit(R5_Wantwrite, &dev->flags); | 3197 | set_bit(R5_Wantwrite, &dev->flags); |
3205 | set_bit(R5_ReWrite, &dev->flags); | 3198 | set_bit(R5_ReWrite, &dev->flags); |
3206 | set_bit(R5_LOCKED, &dev->flags); | 3199 | set_bit(R5_LOCKED, &dev->flags); |
3207 | s.locked++; | 3200 | s->locked++; |
3208 | } else { | 3201 | } else { |
3209 | /* let's read it back */ | 3202 | /* let's read it back */ |
3210 | set_bit(R5_Wantread, &dev->flags); | 3203 | set_bit(R5_Wantread, &dev->flags); |
3211 | set_bit(R5_LOCKED, &dev->flags); | 3204 | set_bit(R5_LOCKED, &dev->flags); |
3212 | s.locked++; | 3205 | s->locked++; |
3213 | } | 3206 | } |
3214 | } | 3207 | } |
3215 | 3208 | ||
@@ -3227,7 +3220,7 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3227 | &sh2->state)) | 3220 | &sh2->state)) |
3228 | atomic_inc(&conf->preread_active_stripes); | 3221 | atomic_inc(&conf->preread_active_stripes); |
3229 | release_stripe(sh2); | 3222 | release_stripe(sh2); |
3230 | goto unlock; | 3223 | return; |
3231 | } | 3224 | } |
3232 | if (sh2) | 3225 | if (sh2) |
3233 | release_stripe(sh2); | 3226 | release_stripe(sh2); |
@@ -3237,69 +3230,35 @@ static void handle_stripe5(struct stripe_head *sh) | |||
3237 | for (i = conf->raid_disks; i--; ) { | 3230 | for (i = conf->raid_disks; i--; ) { |
3238 | set_bit(R5_Wantwrite, &sh->dev[i].flags); | 3231 | set_bit(R5_Wantwrite, &sh->dev[i].flags); |
3239 | set_bit(R5_LOCKED, &sh->dev[i].flags); | 3232 | set_bit(R5_LOCKED, &sh->dev[i].flags); |
3240 | s.locked++; | 3233 | s->locked++; |
3241 | } | 3234 | } |
3242 | } | 3235 | } |
3243 | 3236 | ||
3244 | if (s.expanded && test_bit(STRIPE_EXPANDING, &sh->state) && | 3237 | if (s->expanded && test_bit(STRIPE_EXPANDING, &sh->state) && |
3245 | !sh->reconstruct_state) { | 3238 | !sh->reconstruct_state) { |
3246 | /* Need to write out all blocks after computing parity */ | 3239 | /* Need to write out all blocks after computing parity */ |
3247 | sh->disks = conf->raid_disks; | 3240 | sh->disks = conf->raid_disks; |
3248 | stripe_set_idx(sh->sector, conf, 0, sh); | 3241 | stripe_set_idx(sh->sector, conf, 0, sh); |
3249 | schedule_reconstruction(sh, &s, 1, 1); | 3242 | schedule_reconstruction(sh, s, 1, 1); |
3250 | } else if (s.expanded && !sh->reconstruct_state && s.locked == 0) { | 3243 | } else if (s->expanded && !sh->reconstruct_state && s->locked == 0) { |
3251 | clear_bit(STRIPE_EXPAND_READY, &sh->state); | 3244 | clear_bit(STRIPE_EXPAND_READY, &sh->state); |
3252 | atomic_dec(&conf->reshape_stripes); | 3245 | atomic_dec(&conf->reshape_stripes); |
3253 | wake_up(&conf->wait_for_overlap); | 3246 | wake_up(&conf->wait_for_overlap); |
3254 | md_done_sync(conf->mddev, STRIPE_SECTORS, 1); | 3247 | md_done_sync(conf->mddev, STRIPE_SECTORS, 1); |
3255 | } | 3248 | } |
3256 | 3249 | ||
3257 | if (s.expanding && s.locked == 0 && | 3250 | if (s->expanding && s->locked == 0 && |
3258 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state)) | 3251 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state)) |
3259 | handle_stripe_expansion(conf, sh, NULL); | 3252 | handle_stripe_expansion(conf, sh, NULL); |
3260 | |||
3261 | unlock: | ||
3262 | |||
3263 | /* wait for this device to become unblocked */ | ||
3264 | if (unlikely(s.blocked_rdev)) | ||
3265 | md_wait_for_blocked_rdev(s.blocked_rdev, conf->mddev); | ||
3266 | |||
3267 | if (s.ops_request) | ||
3268 | raid_run_ops(sh, s.ops_request); | ||
3269 | |||
3270 | ops_run_io(sh, &s); | ||
3271 | |||
3272 | if (s.dec_preread_active) { | ||
3273 | /* We delay this until after ops_run_io so that if make_request | ||
3274 | * is waiting on a flush, it won't continue until the writes | ||
3275 | * have actually been submitted. | ||
3276 | */ | ||
3277 | atomic_dec(&conf->preread_active_stripes); | ||
3278 | if (atomic_read(&conf->preread_active_stripes) < | ||
3279 | IO_THRESHOLD) | ||
3280 | md_wakeup_thread(conf->mddev->thread); | ||
3281 | } | ||
3282 | return_io(s.return_bi); | ||
3283 | } | 3253 | } |
3284 | 3254 | ||
3285 | static void handle_stripe6(struct stripe_head *sh) | 3255 | static void handle_stripe6(struct stripe_head *sh, struct stripe_head_state *s) |
3286 | { | 3256 | { |
3287 | raid5_conf_t *conf = sh->raid_conf; | 3257 | raid5_conf_t *conf = sh->raid_conf; |
3288 | int disks = sh->disks; | 3258 | int disks = sh->disks; |
3289 | int i, pd_idx = sh->pd_idx, qd_idx = sh->qd_idx; | 3259 | int i, pd_idx = sh->pd_idx, qd_idx = sh->qd_idx; |
3290 | struct stripe_head_state s; | ||
3291 | struct r5dev *dev, *pdev, *qdev; | 3260 | struct r5dev *dev, *pdev, *qdev; |
3292 | 3261 | ||
3293 | pr_debug("handling stripe %llu, state=%#lx cnt=%d, " | ||
3294 | "pd_idx=%d, qd_idx=%d\n, check:%d, reconstruct:%d\n", | ||
3295 | (unsigned long long)sh->sector, sh->state, | ||
3296 | atomic_read(&sh->count), pd_idx, qd_idx, | ||
3297 | sh->check_state, sh->reconstruct_state); | ||
3298 | memset(&s, 0, sizeof(s)); | ||
3299 | |||
3300 | s.syncing = test_bit(STRIPE_SYNCING, &sh->state); | ||
3301 | s.expanding = test_bit(STRIPE_EXPAND_SOURCE, &sh->state); | ||
3302 | s.expanded = test_bit(STRIPE_EXPAND_READY, &sh->state); | ||
3303 | /* Now to look around and see what can be done */ | 3262 | /* Now to look around and see what can be done */ |
3304 | 3263 | ||
3305 | rcu_read_lock(); | 3264 | rcu_read_lock(); |
@@ -3320,28 +3279,30 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3320 | set_bit(R5_Wantfill, &dev->flags); | 3279 | set_bit(R5_Wantfill, &dev->flags); |
3321 | 3280 | ||
3322 | /* now count some things */ | 3281 | /* now count some things */ |
3323 | if (test_bit(R5_LOCKED, &dev->flags)) s.locked++; | 3282 | if (test_bit(R5_LOCKED, &dev->flags)) |
3324 | if (test_bit(R5_UPTODATE, &dev->flags)) s.uptodate++; | 3283 | s->locked++; |
3284 | if (test_bit(R5_UPTODATE, &dev->flags)) | ||
3285 | s->uptodate++; | ||
3325 | if (test_bit(R5_Wantcompute, &dev->flags)) { | 3286 | if (test_bit(R5_Wantcompute, &dev->flags)) { |
3326 | s.compute++; | 3287 | s->compute++; |
3327 | BUG_ON(s.compute > 2); | 3288 | BUG_ON(s->compute > 2); |
3328 | } | 3289 | } |
3329 | 3290 | ||
3330 | if (test_bit(R5_Wantfill, &dev->flags)) { | 3291 | if (test_bit(R5_Wantfill, &dev->flags)) { |
3331 | s.to_fill++; | 3292 | s->to_fill++; |
3332 | } else if (dev->toread) | 3293 | } else if (dev->toread) |
3333 | s.to_read++; | 3294 | s->to_read++; |
3334 | if (dev->towrite) { | 3295 | if (dev->towrite) { |
3335 | s.to_write++; | 3296 | s->to_write++; |
3336 | if (!test_bit(R5_OVERWRITE, &dev->flags)) | 3297 | if (!test_bit(R5_OVERWRITE, &dev->flags)) |
3337 | s.non_overwrite++; | 3298 | s->non_overwrite++; |
3338 | } | 3299 | } |
3339 | if (dev->written) | 3300 | if (dev->written) |
3340 | s.written++; | 3301 | s->written++; |
3341 | rdev = rcu_dereference(conf->disks[i].rdev); | 3302 | rdev = rcu_dereference(conf->disks[i].rdev); |
3342 | if (s.blocked_rdev == NULL && | 3303 | if (s->blocked_rdev == NULL && |
3343 | rdev && unlikely(test_bit(Blocked, &rdev->flags))) { | 3304 | rdev && unlikely(test_bit(Blocked, &rdev->flags))) { |
3344 | s.blocked_rdev = rdev; | 3305 | s->blocked_rdev = rdev; |
3345 | atomic_inc(&rdev->nr_pending); | 3306 | atomic_inc(&rdev->nr_pending); |
3346 | } | 3307 | } |
3347 | clear_bit(R5_Insync, &dev->flags); | 3308 | clear_bit(R5_Insync, &dev->flags); |
@@ -3362,43 +3323,43 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3362 | if (test_bit(R5_ReadError, &dev->flags)) | 3323 | if (test_bit(R5_ReadError, &dev->flags)) |
3363 | clear_bit(R5_Insync, &dev->flags); | 3324 | clear_bit(R5_Insync, &dev->flags); |
3364 | if (!test_bit(R5_Insync, &dev->flags)) { | 3325 | if (!test_bit(R5_Insync, &dev->flags)) { |
3365 | if (s.failed < 2) | 3326 | if (s->failed < 2) |
3366 | s.failed_num[s.failed] = i; | 3327 | s->failed_num[s->failed] = i; |
3367 | s.failed++; | 3328 | s->failed++; |
3368 | } | 3329 | } |
3369 | } | 3330 | } |
3370 | spin_unlock_irq(&conf->device_lock); | 3331 | spin_unlock_irq(&conf->device_lock); |
3371 | rcu_read_unlock(); | 3332 | rcu_read_unlock(); |
3372 | 3333 | ||
3373 | if (unlikely(s.blocked_rdev)) { | 3334 | if (unlikely(s->blocked_rdev)) { |
3374 | if (s.syncing || s.expanding || s.expanded || | 3335 | if (s->syncing || s->expanding || s->expanded || |
3375 | s.to_write || s.written) { | 3336 | s->to_write || s->written) { |
3376 | set_bit(STRIPE_HANDLE, &sh->state); | 3337 | set_bit(STRIPE_HANDLE, &sh->state); |
3377 | goto unlock; | 3338 | return; |
3378 | } | 3339 | } |
3379 | /* There is nothing for the blocked_rdev to block */ | 3340 | /* There is nothing for the blocked_rdev to block */ |
3380 | rdev_dec_pending(s.blocked_rdev, conf->mddev); | 3341 | rdev_dec_pending(s->blocked_rdev, conf->mddev); |
3381 | s.blocked_rdev = NULL; | 3342 | s->blocked_rdev = NULL; |
3382 | } | 3343 | } |
3383 | 3344 | ||
3384 | if (s.to_fill && !test_bit(STRIPE_BIOFILL_RUN, &sh->state)) { | 3345 | if (s->to_fill && !test_bit(STRIPE_BIOFILL_RUN, &sh->state)) { |
3385 | set_bit(STRIPE_OP_BIOFILL, &s.ops_request); | 3346 | set_bit(STRIPE_OP_BIOFILL, &s->ops_request); |
3386 | set_bit(STRIPE_BIOFILL_RUN, &sh->state); | 3347 | set_bit(STRIPE_BIOFILL_RUN, &sh->state); |
3387 | } | 3348 | } |
3388 | 3349 | ||
3389 | pr_debug("locked=%d uptodate=%d to_read=%d" | 3350 | pr_debug("locked=%d uptodate=%d to_read=%d" |
3390 | " to_write=%d failed=%d failed_num=%d,%d\n", | 3351 | " to_write=%d failed=%d failed_num=%d,%d\n", |
3391 | s.locked, s.uptodate, s.to_read, s.to_write, s.failed, | 3352 | s->locked, s->uptodate, s->to_read, s->to_write, s->failed, |
3392 | s.failed_num[0], s.failed_num[1]); | 3353 | s->failed_num[0], s->failed_num[1]); |
3393 | /* check if the array has lost >2 devices and, if so, some requests | 3354 | /* check if the array has lost >2 devices and, if so, some requests |
3394 | * might need to be failed | 3355 | * might need to be failed |
3395 | */ | 3356 | */ |
3396 | if (s.failed > 2 && s.to_read+s.to_write+s.written) | 3357 | if (s->failed > 2 && s->to_read+s->to_write+s->written) |
3397 | handle_failed_stripe(conf, sh, &s, disks, &s.return_bi); | 3358 | handle_failed_stripe(conf, sh, s, disks, &s->return_bi); |
3398 | if (s.failed > 2 && s.syncing) { | 3359 | if (s->failed > 2 && s->syncing) { |
3399 | md_done_sync(conf->mddev, STRIPE_SECTORS,0); | 3360 | md_done_sync(conf->mddev, STRIPE_SECTORS,0); |
3400 | clear_bit(STRIPE_SYNCING, &sh->state); | 3361 | clear_bit(STRIPE_SYNCING, &sh->state); |
3401 | s.syncing = 0; | 3362 | s->syncing = 0; |
3402 | } | 3363 | } |
3403 | 3364 | ||
3404 | /* | 3365 | /* |
@@ -3406,28 +3367,28 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3406 | * are safe, or on a failed drive | 3367 | * are safe, or on a failed drive |
3407 | */ | 3368 | */ |
3408 | pdev = &sh->dev[pd_idx]; | 3369 | pdev = &sh->dev[pd_idx]; |
3409 | s.p_failed = (s.failed >= 1 && s.failed_num[0] == pd_idx) | 3370 | s->p_failed = (s->failed >= 1 && s->failed_num[0] == pd_idx) |
3410 | || (s.failed >= 2 && s.failed_num[1] == pd_idx); | 3371 | || (s->failed >= 2 && s->failed_num[1] == pd_idx); |
3411 | qdev = &sh->dev[qd_idx]; | 3372 | qdev = &sh->dev[qd_idx]; |
3412 | s.q_failed = (s.failed >= 1 && s.failed_num[0] == qd_idx) | 3373 | s->q_failed = (s->failed >= 1 && s->failed_num[0] == qd_idx) |
3413 | || (s.failed >= 2 && s.failed_num[1] == qd_idx); | 3374 | || (s->failed >= 2 && s->failed_num[1] == qd_idx); |
3414 | 3375 | ||
3415 | if (s.written && | 3376 | if (s->written && |
3416 | (s.p_failed || ((test_bit(R5_Insync, &pdev->flags) | 3377 | (s->p_failed || ((test_bit(R5_Insync, &pdev->flags) |
3417 | && !test_bit(R5_LOCKED, &pdev->flags) | 3378 | && !test_bit(R5_LOCKED, &pdev->flags) |
3418 | && test_bit(R5_UPTODATE, &pdev->flags)))) && | 3379 | && test_bit(R5_UPTODATE, &pdev->flags)))) && |
3419 | (s.q_failed || ((test_bit(R5_Insync, &qdev->flags) | 3380 | (s->q_failed || ((test_bit(R5_Insync, &qdev->flags) |
3420 | && !test_bit(R5_LOCKED, &qdev->flags) | 3381 | && !test_bit(R5_LOCKED, &qdev->flags) |
3421 | && test_bit(R5_UPTODATE, &qdev->flags))))) | 3382 | && test_bit(R5_UPTODATE, &qdev->flags))))) |
3422 | handle_stripe_clean_event(conf, sh, disks, &s.return_bi); | 3383 | handle_stripe_clean_event(conf, sh, disks, &s->return_bi); |
3423 | 3384 | ||
3424 | /* Now we might consider reading some blocks, either to check/generate | 3385 | /* Now we might consider reading some blocks, either to check/generate |
3425 | * parity, or to satisfy requests | 3386 | * parity, or to satisfy requests |
3426 | * or to load a block that is being partially written. | 3387 | * or to load a block that is being partially written. |
3427 | */ | 3388 | */ |
3428 | if (s.to_read || s.non_overwrite || (s.to_write && s.failed) || | 3389 | if (s->to_read || s->non_overwrite || (s->to_write && s->failed) || |
3429 | (s.syncing && (s.uptodate + s.compute < disks)) || s.expanding) | 3390 | (s->syncing && (s->uptodate + s->compute < disks)) || s->expanding) |
3430 | handle_stripe_fill6(sh, &s, disks); | 3391 | handle_stripe_fill6(sh, s, disks); |
3431 | 3392 | ||
3432 | /* Now we check to see if any write operations have recently | 3393 | /* Now we check to see if any write operations have recently |
3433 | * completed | 3394 | * completed |
@@ -3450,12 +3411,12 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3450 | set_bit(R5_Wantwrite, &dev->flags); | 3411 | set_bit(R5_Wantwrite, &dev->flags); |
3451 | if (!test_bit(R5_Insync, &dev->flags) || | 3412 | if (!test_bit(R5_Insync, &dev->flags) || |
3452 | ((i == sh->pd_idx || i == qd_idx) && | 3413 | ((i == sh->pd_idx || i == qd_idx) && |
3453 | s.failed == 0)) | 3414 | s->failed == 0)) |
3454 | set_bit(STRIPE_INSYNC, &sh->state); | 3415 | set_bit(STRIPE_INSYNC, &sh->state); |
3455 | } | 3416 | } |
3456 | } | 3417 | } |
3457 | if (test_and_clear_bit(STRIPE_PREREAD_ACTIVE, &sh->state)) | 3418 | if (test_and_clear_bit(STRIPE_PREREAD_ACTIVE, &sh->state)) |
3458 | s.dec_preread_active = 1; | 3419 | s->dec_preread_active = 1; |
3459 | } | 3420 | } |
3460 | 3421 | ||
3461 | /* Now to consider new write requests and what else, if anything | 3422 | /* Now to consider new write requests and what else, if anything |
@@ -3464,8 +3425,8 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3464 | * 2/ A 'check' operation is in flight, as it may clobber the parity | 3425 | * 2/ A 'check' operation is in flight, as it may clobber the parity |
3465 | * block. | 3426 | * block. |
3466 | */ | 3427 | */ |
3467 | if (s.to_write && !sh->reconstruct_state && !sh->check_state) | 3428 | if (s->to_write && !sh->reconstruct_state && !sh->check_state) |
3468 | handle_stripe_dirtying6(conf, sh, &s, disks); | 3429 | handle_stripe_dirtying6(conf, sh, s, disks); |
3469 | 3430 | ||
3470 | /* maybe we need to check and possibly fix the parity for this stripe | 3431 | /* maybe we need to check and possibly fix the parity for this stripe |
3471 | * Any reads will already have been scheduled, so we just see if enough | 3432 | * Any reads will already have been scheduled, so we just see if enough |
@@ -3473,12 +3434,13 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3473 | * dependent operations are in flight. | 3434 | * dependent operations are in flight. |
3474 | */ | 3435 | */ |
3475 | if (sh->check_state || | 3436 | if (sh->check_state || |
3476 | (s.syncing && s.locked == 0 && | 3437 | (s->syncing && s->locked == 0 && |
3477 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state) && | 3438 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state) && |
3478 | !test_bit(STRIPE_INSYNC, &sh->state))) | 3439 | !test_bit(STRIPE_INSYNC, &sh->state))) |
3479 | handle_parity_checks6(conf, sh, &s, disks); | 3440 | handle_parity_checks6(conf, sh, s, disks); |
3480 | 3441 | ||
3481 | if (s.syncing && s.locked == 0 && test_bit(STRIPE_INSYNC, &sh->state)) { | 3442 | if (s->syncing && s->locked == 0 |
3443 | && test_bit(STRIPE_INSYNC, &sh->state)) { | ||
3482 | md_done_sync(conf->mddev, STRIPE_SECTORS,1); | 3444 | md_done_sync(conf->mddev, STRIPE_SECTORS,1); |
3483 | clear_bit(STRIPE_SYNCING, &sh->state); | 3445 | clear_bit(STRIPE_SYNCING, &sh->state); |
3484 | } | 3446 | } |
@@ -3486,9 +3448,9 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3486 | /* If the failed drives are just a ReadError, then we might need | 3448 | /* If the failed drives are just a ReadError, then we might need |
3487 | * to progress the repair/check process | 3449 | * to progress the repair/check process |
3488 | */ | 3450 | */ |
3489 | if (s.failed <= 2 && !conf->mddev->ro) | 3451 | if (s->failed <= 2 && !conf->mddev->ro) |
3490 | for (i = 0; i < s.failed; i++) { | 3452 | for (i = 0; i < s->failed; i++) { |
3491 | dev = &sh->dev[s.failed_num[i]]; | 3453 | dev = &sh->dev[s->failed_num[i]]; |
3492 | if (test_bit(R5_ReadError, &dev->flags) | 3454 | if (test_bit(R5_ReadError, &dev->flags) |
3493 | && !test_bit(R5_LOCKED, &dev->flags) | 3455 | && !test_bit(R5_LOCKED, &dev->flags) |
3494 | && test_bit(R5_UPTODATE, &dev->flags) | 3456 | && test_bit(R5_UPTODATE, &dev->flags) |
@@ -3497,12 +3459,12 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3497 | set_bit(R5_Wantwrite, &dev->flags); | 3459 | set_bit(R5_Wantwrite, &dev->flags); |
3498 | set_bit(R5_ReWrite, &dev->flags); | 3460 | set_bit(R5_ReWrite, &dev->flags); |
3499 | set_bit(R5_LOCKED, &dev->flags); | 3461 | set_bit(R5_LOCKED, &dev->flags); |
3500 | s.locked++; | 3462 | s->locked++; |
3501 | } else { | 3463 | } else { |
3502 | /* let's read it back */ | 3464 | /* let's read it back */ |
3503 | set_bit(R5_Wantread, &dev->flags); | 3465 | set_bit(R5_Wantread, &dev->flags); |
3504 | set_bit(R5_LOCKED, &dev->flags); | 3466 | set_bit(R5_LOCKED, &dev->flags); |
3505 | s.locked++; | 3467 | s->locked++; |
3506 | } | 3468 | } |
3507 | } | 3469 | } |
3508 | } | 3470 | } |
@@ -3514,11 +3476,11 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3514 | for (i = conf->raid_disks; i--; ) { | 3476 | for (i = conf->raid_disks; i--; ) { |
3515 | set_bit(R5_Wantwrite, &sh->dev[i].flags); | 3477 | set_bit(R5_Wantwrite, &sh->dev[i].flags); |
3516 | set_bit(R5_LOCKED, &sh->dev[i].flags); | 3478 | set_bit(R5_LOCKED, &sh->dev[i].flags); |
3517 | s.locked++; | 3479 | s->locked++; |
3518 | } | 3480 | } |
3519 | } | 3481 | } |
3520 | 3482 | ||
3521 | if (s.expanded && test_bit(STRIPE_EXPANDING, &sh->state) && | 3483 | if (s->expanded && test_bit(STRIPE_EXPANDING, &sh->state) && |
3522 | !sh->reconstruct_state) { | 3484 | !sh->reconstruct_state) { |
3523 | struct stripe_head *sh2 | 3485 | struct stripe_head *sh2 |
3524 | = get_active_stripe(conf, sh->sector, 1, 1, 1); | 3486 | = get_active_stripe(conf, sh->sector, 1, 1, 1); |
@@ -3532,7 +3494,7 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3532 | &sh2->state)) | 3494 | &sh2->state)) |
3533 | atomic_inc(&conf->preread_active_stripes); | 3495 | atomic_inc(&conf->preread_active_stripes); |
3534 | release_stripe(sh2); | 3496 | release_stripe(sh2); |
3535 | goto unlock; | 3497 | return; |
3536 | } | 3498 | } |
3537 | if (sh2) | 3499 | if (sh2) |
3538 | release_stripe(sh2); | 3500 | release_stripe(sh2); |
@@ -3540,19 +3502,54 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3540 | /* Need to write out all blocks after computing P&Q */ | 3502 | /* Need to write out all blocks after computing P&Q */ |
3541 | sh->disks = conf->raid_disks; | 3503 | sh->disks = conf->raid_disks; |
3542 | stripe_set_idx(sh->sector, conf, 0, sh); | 3504 | stripe_set_idx(sh->sector, conf, 0, sh); |
3543 | schedule_reconstruction(sh, &s, 1, 1); | 3505 | schedule_reconstruction(sh, s, 1, 1); |
3544 | } else if (s.expanded && !sh->reconstruct_state && s.locked == 0) { | 3506 | } else if (s->expanded && !sh->reconstruct_state && s->locked == 0) { |
3545 | clear_bit(STRIPE_EXPAND_READY, &sh->state); | 3507 | clear_bit(STRIPE_EXPAND_READY, &sh->state); |
3546 | atomic_dec(&conf->reshape_stripes); | 3508 | atomic_dec(&conf->reshape_stripes); |
3547 | wake_up(&conf->wait_for_overlap); | 3509 | wake_up(&conf->wait_for_overlap); |
3548 | md_done_sync(conf->mddev, STRIPE_SECTORS, 1); | 3510 | md_done_sync(conf->mddev, STRIPE_SECTORS, 1); |
3549 | } | 3511 | } |
3550 | 3512 | ||
3551 | if (s.expanding && s.locked == 0 && | 3513 | if (s->expanding && s->locked == 0 && |
3552 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state)) | 3514 | !test_bit(STRIPE_COMPUTE_RUN, &sh->state)) |
3553 | handle_stripe_expansion(conf, sh, &s); | 3515 | handle_stripe_expansion(conf, sh, s); |
3516 | } | ||
3517 | |||
3518 | static void handle_stripe(struct stripe_head *sh) | ||
3519 | { | ||
3520 | struct stripe_head_state s; | ||
3521 | raid5_conf_t *conf = sh->raid_conf; | ||
3522 | |||
3523 | clear_bit(STRIPE_HANDLE, &sh->state); | ||
3524 | if (test_and_set_bit(STRIPE_ACTIVE, &sh->state)) { | ||
3525 | /* already being handled, ensure it gets handled | ||
3526 | * again when current action finishes */ | ||
3527 | set_bit(STRIPE_HANDLE, &sh->state); | ||
3528 | return; | ||
3529 | } | ||
3530 | |||
3531 | if (test_and_clear_bit(STRIPE_SYNC_REQUESTED, &sh->state)) { | ||
3532 | set_bit(STRIPE_SYNCING, &sh->state); | ||
3533 | clear_bit(STRIPE_INSYNC, &sh->state); | ||
3534 | } | ||
3535 | clear_bit(STRIPE_DELAYED, &sh->state); | ||
3536 | |||
3537 | pr_debug("handling stripe %llu, state=%#lx cnt=%d, " | ||
3538 | "pd_idx=%d, qd_idx=%d\n, check:%d, reconstruct:%d\n", | ||
3539 | (unsigned long long)sh->sector, sh->state, | ||
3540 | atomic_read(&sh->count), sh->pd_idx, sh->qd_idx, | ||
3541 | sh->check_state, sh->reconstruct_state); | ||
3542 | memset(&s, 0, sizeof(s)); | ||
3543 | |||
3544 | s.syncing = test_bit(STRIPE_SYNCING, &sh->state); | ||
3545 | s.expanding = test_bit(STRIPE_EXPAND_SOURCE, &sh->state); | ||
3546 | s.expanded = test_bit(STRIPE_EXPAND_READY, &sh->state); | ||
3547 | |||
3548 | if (conf->level == 6) | ||
3549 | handle_stripe6(sh, &s); | ||
3550 | else | ||
3551 | handle_stripe5(sh, &s); | ||
3554 | 3552 | ||
3555 | unlock: | ||
3556 | 3553 | ||
3557 | /* wait for this device to become unblocked */ | 3554 | /* wait for this device to become unblocked */ |
3558 | if (unlikely(s.blocked_rdev)) | 3555 | if (unlikely(s.blocked_rdev)) |
@@ -3576,28 +3573,7 @@ static void handle_stripe6(struct stripe_head *sh) | |||
3576 | } | 3573 | } |
3577 | 3574 | ||
3578 | return_io(s.return_bi); | 3575 | return_io(s.return_bi); |
3579 | } | ||
3580 | 3576 | ||
3581 | static void handle_stripe(struct stripe_head *sh) | ||
3582 | { | ||
3583 | clear_bit(STRIPE_HANDLE, &sh->state); | ||
3584 | if (test_and_set_bit(STRIPE_ACTIVE, &sh->state)) { | ||
3585 | /* already being handled, ensure it gets handled | ||
3586 | * again when current action finishes */ | ||
3587 | set_bit(STRIPE_HANDLE, &sh->state); | ||
3588 | return; | ||
3589 | } | ||
3590 | |||
3591 | if (test_and_clear_bit(STRIPE_SYNC_REQUESTED, &sh->state)) { | ||
3592 | set_bit(STRIPE_SYNCING, &sh->state); | ||
3593 | clear_bit(STRIPE_INSYNC, &sh->state); | ||
3594 | } | ||
3595 | clear_bit(STRIPE_DELAYED, &sh->state); | ||
3596 | |||
3597 | if (sh->raid_conf->level == 6) | ||
3598 | handle_stripe6(sh); | ||
3599 | else | ||
3600 | handle_stripe5(sh); | ||
3601 | clear_bit(STRIPE_ACTIVE, &sh->state); | 3577 | clear_bit(STRIPE_ACTIVE, &sh->state); |
3602 | } | 3578 | } |
3603 | 3579 | ||