Author: mav
Date: Fri Nov 20 19:36:34 2020
New Revision: 367909
URL: https://svnweb.freebsd.org/changeset/base/367909

Log:
  Increase queue depths from 1024/256 to 8192/1024 IOCBs.
  
  Qlogic chips store S/G lists in the same queue as requests themselves.  In
  the worst case 1MB I/O may require up to 52 IOCBs, that means queue of 1024
  IOCBs can store only 19 of such requests.  The increase reduces chances of
  overflow, while we should be able to afford additional 512KB of RAM per HBA.
  The Linux driver uses comparable numbers.
  
  While there, decouple ATIO queue size from response queue size.  There is
  no reason for them to be equal.

Modified:
  head/sys/dev/isp/isp.c
  head/sys/dev/isp/isp_freebsd.h
  head/sys/dev/isp/isp_pci.c
  head/sys/dev/isp/isp_target.c
  head/sys/dev/isp/ispvar.h

Modified: head/sys/dev/isp/isp.c
==============================================================================
--- head/sys/dev/isp/isp.c      Fri Nov 20 18:52:37 2020        (r367908)
+++ head/sys/dev/isp/isp.c      Fri Nov 20 19:36:34 2020        (r367909)
@@ -98,7 +98,7 @@ static const uint8_t alpa_map[] = {
 /*
  * Local function prototypes.
  */
-static int isp_handle_other_response(ispsoftc_t *, int, isphdr_t *, uint32_t 
*);
+static int isp_handle_other_response(ispsoftc_t *, int, isphdr_t *, uint32_t 
*, uint16_t);
 static void isp_parse_status_24xx(ispsoftc_t *, isp24xx_statusreq_t *, XS_T *, 
uint32_t *);
 static void isp_clear_portdb(ispsoftc_t *, int);
 static void isp_mark_portdb(ispsoftc_t *, int);
@@ -912,7 +912,7 @@ isp_init(ispsoftc_t *isp)
 
 #ifdef ISP_TARGET_MODE
        /* unconditionally set up the ATIO queue if we support target mode */
-       icbp->icb_atioqlen = RESULT_QUEUE_LEN(isp);
+       icbp->icb_atioqlen = ATIO_QUEUE_LEN(isp);
        if (icbp->icb_atioqlen < 8) {
                isp_prt(isp, ISP_LOGERR, "bad ATIO queue length %d", 
icbp->icb_atioqlen);
                return;
@@ -3179,14 +3179,15 @@ isp_intr_atioq(ispsoftc_t *isp)
                case RQSTYPE_ATIO:
                case RQSTYPE_NOTIFY_ACK:        /* Can be set to ATIO queue.*/
                case RQSTYPE_ABTS_RCVD:         /* Can be set to ATIO queue.*/
-                       (void) isp_target_notify(isp, addr, &oop);
+                       (void) isp_target_notify(isp, addr, &oop,
+                           ATIO_QUEUE_LEN(isp));
                        break;
                case RQSTYPE_RPT_ID_ACQ:        /* Can be set to ATIO queue.*/
                default:
                        isp_print_qentry(isp, "?ATIOQ entry?", oop, addr);
                        break;
                }
-               optr = ISP_NXT_QENTRY(oop, RESULT_QUEUE_LEN(isp));
+               optr = ISP_NXT_QENTRY(oop, ATIO_QUEUE_LEN(isp));
        }
        if (isp->isp_atioodx != optr) {
                ISP_WRITE(isp, BIU2400_ATIO_RSPOUTP, optr);
@@ -3287,7 +3288,8 @@ isp_intr_respq(ispsoftc_t *isp)
                        }
                        ISP_MEMZERO(hp, QENTRY_LEN);    /* PERF */
                        continue;
-               } else if (isp_handle_other_response(isp, etype, hp, &cptr)) {
+               } else if (isp_handle_other_response(isp, etype, hp,
+                   &cptr, RESULT_QUEUE_LEN(isp))) {
                        /* More then one IOCB could be consumed. */
                        while (sptr != cptr) {
                                ISP_MEMZERO(hp, QENTRY_LEN);    /* PERF */
@@ -3729,7 +3731,7 @@ isp_intr_async(ispsoftc_t *isp, uint16_t mbox)
  */
 
 static int
-isp_handle_other_response(ispsoftc_t *isp, int type, isphdr_t *hp, uint32_t 
*optrp)
+isp_handle_other_response(ispsoftc_t *isp, int type, isphdr_t *hp, uint32_t 
*optrp, uint16_t ql)
 {
        isp_ridacq_t rid;
        int chan, c;
@@ -3794,7 +3796,7 @@ isp_handle_other_response(ispsoftc_t *isp, int type, i
        case RQSTYPE_ABTS_RCVD:         /* Can be set to ATIO queue. */
        case RQSTYPE_ABTS_RSP:
 #ifdef ISP_TARGET_MODE
-               return (isp_target_notify(isp, hp, optrp));
+               return (isp_target_notify(isp, hp, optrp, ql));
 #endif
                /* FALLTHROUGH */
        default:

Modified: head/sys/dev/isp/isp_freebsd.h
==============================================================================
--- head/sys/dev/isp/isp_freebsd.h      Fri Nov 20 18:52:37 2020        
(r367908)
+++ head/sys/dev/isp/isp_freebsd.h      Fri Nov 20 19:36:34 2020        
(r367909)
@@ -349,8 +349,6 @@ struct isposinfo {
 #define        GET_NANOSEC(x)          ((x)->tv_sec * 1000000000 + 
(x)->tv_nsec)
 #define        NANOTIME_SUB            isp_nanotime_sub
 
-#define        MAXISPREQUEST(isp)      1024
-
 #define        MEMORYBARRIER(isp, type, offset, size, chan)            \
 switch (type) {                                                        \
 case SYNC_REQUEST:                                             \

Modified: head/sys/dev/isp/isp_pci.c
==============================================================================
--- head/sys/dev/isp/isp_pci.c  Fri Nov 20 18:52:37 2020        (r367908)
+++ head/sys/dev/isp/isp_pci.c  Fri Nov 20 19:36:34 2020        (r367909)
@@ -1009,9 +1009,9 @@ isp_pci_mbxdma(ispsoftc_t *isp)
 
 #ifdef ISP_TARGET_MODE
        /*
-        * Allocate and map ATIO queue on 24xx with target mode.
+        * Allocate and map ATIO queue.
         */
-       len = ISP_QUEUE_SIZE(RESULT_QUEUE_LEN(isp));
+       len = ISP_QUEUE_SIZE(ATIO_QUEUE_LEN(isp));
        if (bus_dma_tag_create(isp->isp_osinfo.dmat, QENTRY_LEN, slim,
            BUS_SPACE_MAXADDR, BUS_SPACE_MAXADDR, NULL, NULL,
            len, 1, len, 0, NULL, NULL, &isp->isp_osinfo.atiodmat)) {

Modified: head/sys/dev/isp/isp_target.c
==============================================================================
--- head/sys/dev/isp/isp_target.c       Fri Nov 20 18:52:37 2020        
(r367908)
+++ head/sys/dev/isp/isp_target.c       Fri Nov 20 19:36:34 2020        
(r367909)
@@ -109,7 +109,7 @@ static void isp_handle_notify_24xx(ispsoftc_t *, in_fc
  */
 
 int
-isp_target_notify(ispsoftc_t *isp, void *vptr, uint32_t *optrp)
+isp_target_notify(ispsoftc_t *isp, void *vptr, uint32_t *optrp, uint16_t ql)
 {
        union {
                at7_entry_t     *at7iop;
@@ -149,7 +149,7 @@ isp_target_notify(ispsoftc_t *isp, void *vptr, uint32_
                        len -= (QENTRY_LEN - 8);
                        isp_prt(isp, ISP_LOGINFO, "long IU length (%d) 
ignored", len);
                        while (len > 0) {
-                               *optrp =  ISP_NXT_QENTRY(*optrp, 
RESULT_QUEUE_LEN(isp));
+                               *optrp = ISP_NXT_QENTRY(*optrp, ql);
                                len -= QENTRY_LEN;
                        }
                }

Modified: head/sys/dev/isp/ispvar.h
==============================================================================
--- head/sys/dev/isp/ispvar.h   Fri Nov 20 18:52:37 2020        (r367908)
+++ head/sys/dev/isp/ispvar.h   Fri Nov 20 19:36:34 2020        (r367909)
@@ -128,20 +128,15 @@ struct ispmdvec {
 
 /*
  * Request/Response Queue defines and macros.
- * The maximum is defined per platform (and can be based on board type).
  */
 /* This is the size of a queue entry (request and response) */
 #define        QENTRY_LEN                      64
-/* Both request and result queue length must be a power of two */
-#define        RQUEST_QUEUE_LEN(x)             MAXISPREQUEST(x)
-#ifdef ISP_TARGET_MODE
-#define        RESULT_QUEUE_LEN(x)             MAXISPREQUEST(x)
-#else
-#define        RESULT_QUEUE_LEN(x)             \
-       (((MAXISPREQUEST(x) >> 2) < 64)? 64 : MAXISPREQUEST(x) >> 2)
-#endif
-#define        ISP_QUEUE_ENTRY(q, idx)         (((uint8_t *)q) + ((idx) * 
QENTRY_LEN))
-#define        ISP_QUEUE_SIZE(n)               ((n) * QENTRY_LEN)
+/* Queue lengths must be a power of two and at least 8 elements. */
+#define        RQUEST_QUEUE_LEN(x)             8192
+#define        RESULT_QUEUE_LEN(x)             1024
+#define        ATIO_QUEUE_LEN(x)               1024
+#define        ISP_QUEUE_ENTRY(q, idx)         (((uint8_t *)q) + 
((size_t)(idx) * QENTRY_LEN))
+#define        ISP_QUEUE_SIZE(n)               ((size_t)(n) * QENTRY_LEN)
 #define        ISP_NXT_QENTRY(idx, qlen)       (((idx) + 1) & ((qlen)-1))
 #define        ISP_QFREE(in, out, qlen)        \
        ((in == out)? (qlen - 1) : ((in > out)? \
@@ -944,7 +939,7 @@ void isp_async(ispsoftc_t *, ispasync_t, ...);
 /*
  * This function handles new response queue entry appropriate for target mode.
  */
-int isp_target_notify(ispsoftc_t *, void *, uint32_t *);
+int isp_target_notify(ispsoftc_t *, void *, uint32_t *, uint16_t);
 
 /*
  * This function externalizes the ability to acknowledge an Immediate Notify 
request.
_______________________________________________
svn-src-head@freebsd.org mailing list
https://lists.freebsd.org/mailman/listinfo/svn-src-head
To unsubscribe, send any mail to "svn-src-head-unsubscr...@freebsd.org"

Reply via email to