--- linux-2.4.30/drivers/md/raid1.c.pre-fr1 Mon Apr 4 03:42:19 2005 +++ linux-2.4.30/drivers/md/raid1.c Wed Apr 6 22:38:41 2005 @@ -400,13 +465,65 @@ static void inline sync_request_done (un static void raid1_end_bh_io (struct raid1_bh *r1_bh, int uptodate) { struct buffer_head *bh = r1_bh->master_bh; +#if defined(CONFIG_MD_FR1) || defined(CONFIG_MD_FR1_MODULE) + raid1_conf_t * conf = mddev_to_conf(r1_bh->mddev); + + /* if nobody has done the final end_io yet, do it now */ + if (!test_and_set_bit(R1BH_AsyncPhase, &r1_bh->state)) { + + PRINTK(KERN_DEBUG "raid1: sync end i/o on sectors %lu-%lu\n", + bh->b_rsector, bh->b_rsector + (bh->b_size >> 9) - 1); + io_request_done(bh->b_rsector, conf, + test_bit(R1BH_SyncPhase, &r1_bh->state)); + bh->b_end_io(bh, uptodate); + } +#else io_request_done(bh->b_rsector, mddev_to_conf(r1_bh->mddev), test_bit(R1BH_SyncPhase, &r1_bh->state)); bh->b_end_io(bh, uptodate); +#endif /* CONFIG_MD_FR1 */ + +#if defined(CONFIG_MD_FR1) || defined(CONFIG_MD_FR1_MODULE) + /* if we should mark the bitmap clean, do so */ + if (uptodate && r1_bh->cmd == WRITE && r1_bh->nonoperational <= 0) { + struct bitmap * bitmap = conf->bitmap; + if (bitmap && bitmap->active(bitmap)) { + bitmap->clearbits(bitmap, (bitmap_offset_t) (bh->b_rsector >> 1), bh->b_size >> 10); + } + } + /* PTB calculate the latency of the read device */ + if (uptodate && (r1_bh->cmd == READ || r1_bh->cmd == READA)) { + unsigned long latency = jiffies - r1_bh->start_jiffies; + kdev_t dev = (&r1_bh->bh_req)->b_dev; + int i; + + /* PTB find the mirror component being read */ + for (i = 0; i < conf->raid_disks; i++) { + if (conf->mirrors[i].dev == dev) + break; + } + if (i < conf->raid_disks) { + if (latency < 120 * HZ && latency >= 0) { + /* PTB count in 1/10ths if we have total weights 9+1 = 10 */ + latency *= LATENCY_SUM_WEIGHT * LATENCY_SUM_WEIGHT; + conf->latency[i] = LATENCY_OLD_WEIGHT * conf->latency[i] + + LATENCY_NEW_WEIGHT * latency; + conf->latency[i] /= LATENCY_SUM_WEIGHT; + } else { + printk(KERN_ERR "raid1: bad latency %lu jiffies\n", + latency); + } + } else { + printk(KERN_ERR "raid1: could not find dev %02x:%02x\n", + MAJOR(dev), MINOR(dev)); + } + } +#endif /* CONFIG_MD_FR1 */ raid1_free_r1bh(r1_bh); } + void raid1_end_request (struct buffer_head *bh, int uptodate) { struct raid1_bh * r1_bh = (struct raid1_bh *)(bh->b_private);