Author: mav Date: Tue Sep 15 09:36:46 2015 New Revision: 287816 URL: https://svnweb.freebsd.org/changeset/base/287816
Log: Close potential race between datamove and HA failover. Modified: head/sys/cam/ctl/ctl.c Modified: head/sys/cam/ctl/ctl.c ============================================================================== --- head/sys/cam/ctl/ctl.c Tue Sep 15 08:50:44 2015 (r287815) +++ head/sys/cam/ctl/ctl.c Tue Sep 15 09:36:46 2015 (r287816) @@ -10950,6 +10950,7 @@ ctl_failover_lun(struct ctl_lun *lun) if (io->flags & CTL_FLAG_FROM_OTHER_SC) { if (io->flags & CTL_FLAG_IO_ACTIVE) { io->flags |= CTL_FLAG_ABORT; + io->flags |= CTL_FLAG_FAILOVER; } else { /* This can be only due to DATAMOVE */ io->msg_type = CTL_MSG_DATAMOVE_DONE; io->flags |= CTL_FLAG_IO_ACTIVE; @@ -12102,12 +12103,14 @@ ctl_datamove_timer_wakeup(void *arg) void ctl_datamove(union ctl_io *io) { + struct ctl_lun *lun; void (*fe_datamove)(union ctl_io *io); mtx_assert(&control_softc->ctl_lock, MA_NOTOWNED); CTL_DEBUG_PRINT(("ctl_datamove\n")); + lun = (struct ctl_lun *)io->io_hdr.ctl_private[CTL_PRIV_LUN].ptr; #ifdef CTL_TIME_IO if ((time_uptime - io->io_hdr.start_time) > ctl_time_io_secs) { char str[256]; @@ -12148,9 +12151,6 @@ ctl_datamove(union ctl_io *io) if (io->io_hdr.flags & CTL_FLAG_DELAY_DONE) { io->io_hdr.flags &= ~CTL_FLAG_DELAY_DONE; } else { - struct ctl_lun *lun; - - lun =(struct ctl_lun *)io->io_hdr.ctl_private[CTL_PRIV_LUN].ptr; if ((lun != NULL) && (lun->delay_info.datamove_delay > 0)) { @@ -12326,7 +12326,24 @@ ctl_datamove(union ctl_io *io) msg.dt.sent_sg_entries = sg_entries_sent; } + + /* + * Officially handover the request from us to peer. + * If failover has just happened, then we must return error. + * If failover happen just after, then it is not our problem. + */ + if (lun) + mtx_lock(&lun->lun_lock); + if (io->io_hdr.flags & CTL_FLAG_FAILOVER) { + if (lun) + mtx_unlock(&lun->lun_lock); + io->io_hdr.port_status = 31342; + io->scsiio.be_move_done(io); + return; + } io->io_hdr.flags &= ~CTL_FLAG_IO_ACTIVE; + if (lun) + mtx_unlock(&lun->lun_lock); } else { /* _______________________________________________ svn-src-all@freebsd.org mailing list https://lists.freebsd.org/mailman/listinfo/svn-src-all To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"