]> CyberLeo.Net >> Repos - FreeBSD/stable/10.git/commit
MFC isp(4) driver changes:
authorken <ken@ccf9f872-aa2e-dd11-9fc8-001c23d0bc1f>
Tue, 3 Feb 2015 22:49:12 +0000 (22:49 +0000)
committerken <ken@ccf9f872-aa2e-dd11-9fc8-001c23d0bc1f>
Tue, 3 Feb 2015 22:49:12 +0000 (22:49 +0000)
commitacf934c4d3ebdea30265b373c8da8b585bbee93e
tree2b9ec720609395f11a906a25be1c880606798907
parent63c225dc12972816e90a36a7abcaa4dd893ebeb6
MFC isp(4) driver changes:

r276839, r276842, r277513, r277514, r277515

  ------------------------------------------------------------------------
  r276839 | ken | 2015-01-08 10:41:28 -0700 (Thu, 08 Jan 2015) | 49 lines

  Fix Fibre Channel Command Reference Number handling in the isp(4) driver.

  The Command Reference Number is used for precise delivery of
  commands, and is part of the FC-Tape functionality set.  (This is
  only enabled for devices that support precise delivery of commands.)
  It is an 8-bit unsigned number that increments from 1 to 255.  The
  commands sent by the initiator must be processed by the target in
  CRN order if the CRN is non-zero.

  There are certain scenarios where the Command Reference Number
  sequence needs to be reset.  When the target is power cycled, for
  instance, the initiator needs to reset the CRN to 1.  The initiator
  will know this because it will see a LIP (when directly connected)
  or get a logout/login event (when connected to a switch).

  The isp(4) driver was not resetting the CRN when a target
  went away and came back.  When it saw the target again after a
  power cycle, it would continue the CRN sequence where it left off.
  The target would ignore the command because the CRN sequence is
  supposed to be reset to 1 after a power cycle or other similar
  event.

  The symptom that the user would see is that there would be lots of
  aborted INQUIRY commands after a tape library was power cycled, and
  the library would fail to probe.  The INQUIRY commands were being
  ignored by the tape drive due to the CRN issue mentioned above.

  isp_freebsd.c:
   Add a new function, isp_fcp_reset_crn().  This will reset
   all of the CRNs for a given port, or the CRNs for all LUNs
   on a target.

   Reset the CRNs for all targets on a port when we get a LIP,
   loop reset, or loop down event.

   Reset the CRN for a particular target when it arrives, is changed
   or departs.  This is less precise behavior than the
   clearing behavior specified in the FCP-4 spec (which says
   that it should be reset for PRLI, PRLO, PLOGI and LOGO),
   but this is the level of information we have here.  If this
   is insufficient, then we will need to add more precise
   notification from the lower level isp(4) code.

  isp_freebsd.h:
   Add a prototype for isp_fcp_reset_crn().

  Sponsored by: Spectra Logic
  MFC after: 1 week

  ------------------------------------------------------------------------
  r276842 | ken | 2015-01-08 10:51:12 -0700 (Thu, 08 Jan 2015) | 44 lines

  Close a race in the isp(4) driver that caused devices to disappear
  and not automatically come back if they were gone for a short
  period of time.

  The isp(4) driver has a 30 second gone device timer that gets
  activated whenever a device goes away.  If the device comes back
  before the timer expires, we don't send a notification to CAM that
  it has gone away.  If, however, there is a command sent to the
  device while it is gone and before it comes back, the isp(4) driver
  sends the command back with CAM_SEL_TIMEOUT status.

  CAM responds to the CAM_SEL_TIMEOUT status by removing the device.
  In the case where a device comes back within the 30 second gone
  device timer window, though, we weren't telling CAM the device
  came back.

  So, fix this by tracking whether we have told CAM the device is
  gone, and if we have, send a rescan if it comes back within the 30
  second window.

  ispvar.h:
   In the fcportdb_t structure, add a new bitfield,
   reported_gone.  This gets set whenever we return a command
   with CAM_SEL_TIMEOUT status on a Fibre Channel device.

  isp_freebsd.c:
   In isp_done(), if we're sending CAM_SEL_TIMEOUT for for a
   command sent to a FC device, set the reported_gone bit.

   In isp_async(), in the ISPASYNC_DEV_STAYED case, rescan the
   device in question if it is mapped to a target ID and has
   been reported gone.

   In isp_make_here(), take a port database entry argument,
   and clear the reported_gone bit when we send a rescan to
   CAM.

   In isp_make_gone(), take a port database entry as an
   argument, and set the reported_gone bit when we send an
   async event telling CAM consumers that the device is gone.

  Sponsored by: Spectra Logic
  MFC after: 1 week

  ------------------------------------------------------------------------
  r277514 | will | 2015-01-21 13:27:11 -0700 (Wed, 21 Jan 2015) | 18 lines

  Force commit to record the correct log for r277513.

  If the user sends an XPT_RESET_DEV CCB, make sure to reset the
  Fibre Channel Command Reference Number if we're running on a FC
  controller.

  We send a SCSI Target Reset when we get this CCB, and as a result
  need to reset the CRN to 1 on the next command.

  isp_freebsd.c:
   In the XPT_RESET_DEV implementation in isp_action(), reset
   the CRN if we're on a FC controller.

  Submitted by: ken
  MFC after: 1 week
  Sponsored by: Spectra Logic
  MFSpectraBSD: 1112787 on 2015/01/15

  ------------------------------------------------------------------------
  r277515 | will | 2015-01-21 13:32:36 -0700 (Wed, 21 Jan 2015) | 25 lines

  Fix SCSI status byte reporting on 4Gb and 8Gb Qlogic boards.

  The newer boards don't have the response field that indicates
  whether the SCSI status byte is present.  You have to just look to
  see whether it is non-zero.

  The code was looking to see whether the sense length was valid
  before propagating the SCSI status byte (and sense information) up
  the stack.  With a status like Reservation Conflict, there is no
  sense information, only the SCSI status byte.  So it wasn't getting
  correctly returned.

  isp.c:
   In isp_intr(), if we are on a 2400 or 2500 type board and
   get a response, look at the actual contents of the
   SCSI status value and set the RQSF_GOT_STATUS flag
   accordingly so that return any SCSI status value we get.  The
   RQSF_GOT_SENSE flag will get set later on if there is
   actual sense information returned.

  Submitted by: ken
  MFC after: 1 week
  Sponsored by: Spectra Logic
  MFSpectraBSD: 1112791 on 2015/01/15

  ------------------------------------------------------------------------

Sponsored by: Spectra Logic

git-svn-id: svn://svn.freebsd.org/base/stable/10@278171 ccf9f872-aa2e-dd11-9fc8-001c23d0bc1f
sys/dev/isp/isp.c
sys/dev/isp/isp_freebsd.c
sys/dev/isp/isp_freebsd.h
sys/dev/isp/ispvar.h