Remove concept of mbox_sleep_ok.

It was broken by design and unused for years due to conflicts between
different threads, fighting for the same set of mailbox registers, not
designed for multiple requests at a time.  So either request has to be
synchronous and spin under the lock, or it should be sent asynchronously
through the queues as Mailbox Command IOCB or some other way.

This removes any OS specifics from the wait code, so it can be inlined.
This commit is contained in:
Alexander Motin 2020-11-24 15:32:25 +00:00
parent 1553bf11b9
commit 384d27e04d
4 changed files with 16 additions and 100 deletions

View File

@ -3216,7 +3216,7 @@ isp_intr_mbox(ispsoftc_t *isp, uint16_t mbox0)
continue;
isp->isp_mboxtmp[i] = ISP_READ(isp, MBOX_OFF(i));
}
MBOX_NOTIFY_COMPLETE(isp);
isp->isp_mboxbsy = 0;
}
void
@ -3489,7 +3489,7 @@ isp_intr_async(ispsoftc_t *isp, uint16_t mbox)
if (isp->isp_mboxbsy) {
isp->isp_obits = 1;
isp->isp_mboxtmp[0] = MBOX_HOST_INTERFACE_ERROR;
MBOX_NOTIFY_COMPLETE(isp);
isp->isp_mboxbsy = 0;
}
/*
* It's up to the handler for isp_async to reinit stuff and
@ -4243,7 +4243,7 @@ isp_mboxcmd(ispsoftc_t *isp, mbreg_t *mbp)
{
const char *cname, *xname, *sname;
char tname[16], mname[16];
unsigned int ibits, obits, box, opcode;
unsigned int ibits, obits, box, opcode, t, to;
opcode = mbp->param[0];
if (opcode > MAX_FC_OPCODE) {
@ -4279,14 +4279,6 @@ isp_mboxcmd(ispsoftc_t *isp, mbreg_t *mbp)
return;
}
/*
* Get exclusive usage of mailbox registers.
*/
if (MBOX_ACQUIRE(isp)) {
mbp->param[0] = MBOX_REGS_BUSY;
goto out;
}
for (box = 0; box < ISP_NMBOX(isp); box++) {
if (ibits & (1 << box)) {
isp_prt(isp, ISP_LOGDEBUG3, "IN mbox %d = 0x%04x", box,
@ -4297,10 +4289,6 @@ isp_mboxcmd(ispsoftc_t *isp, mbreg_t *mbp)
}
isp->isp_lastmbxcmd = opcode;
/*
* We assume that we can't overwrite a previous command.
*/
isp->isp_obits = obits;
isp->isp_mboxbsy = 1;
@ -4312,14 +4300,24 @@ isp_mboxcmd(ispsoftc_t *isp, mbreg_t *mbp)
/*
* While we haven't finished the command, spin our wheels here.
*/
MBOX_WAIT_COMPLETE(isp, mbp);
to = (mbp->timeout == 0) ? MBCMD_DEFAULT_TIMEOUT : mbp->timeout;
for (t = 0; t < to; t += 100) {
if (!isp->isp_mboxbsy)
break;
ISP_RUN_ISR(isp);
if (!isp->isp_mboxbsy)
break;
ISP_DELAY(100);
}
/*
* Did the command time out?
*/
if (mbp->param[0] == MBOX_TIMEOUT) {
if (isp->isp_mboxbsy) {
isp->isp_mboxbsy = 0;
MBOX_RELEASE(isp);
isp_prt(isp, ISP_LOGWARN, "Mailbox Command (0x%x) Timeout (%uus) (%s:%d)",
isp->isp_lastmbxcmd, to, mbp->func, mbp->lineno);
mbp->param[0] = MBOX_TIMEOUT;
goto out;
}
@ -4334,8 +4332,6 @@ isp_mboxcmd(ispsoftc_t *isp, mbreg_t *mbp)
}
}
isp->isp_mboxbsy = 0;
MBOX_RELEASE(isp);
out:
if (mbp->logval == 0 || mbp->param[0] == MBOX_COMMAND_COMPLETE)
return;

View File

@ -3250,10 +3250,7 @@ isp_async(ispsoftc_t *isp, ispasync_t cmd, ...)
mbox1 = ISP_READ(isp, OUTMAILBOX1);
isp_prt(isp, ISP_LOGERR, "Internal Firmware Error @ RISC Address 0x%x", mbox1);
#if 0
mbox1 = isp->isp_osinfo.mbox_sleep_ok;
isp->isp_osinfo.mbox_sleep_ok = 0;
isp_reinit(isp, 1);
isp->isp_osinfo.mbox_sleep_ok = mbox1;
isp_async(isp, ISPASYNC_FW_RESTARTED, NULL);
#endif
break;
@ -3359,64 +3356,6 @@ isp_nanotime_sub(struct timespec *b, struct timespec *a)
return (elapsed);
}
int
isp_mbox_acquire(ispsoftc_t *isp)
{
if (isp->isp_osinfo.mboxbsy) {
return (1);
} else {
isp->isp_osinfo.mboxcmd_done = 0;
isp->isp_osinfo.mboxbsy = 1;
return (0);
}
}
void
isp_mbox_wait_complete(ispsoftc_t *isp, mbreg_t *mbp)
{
u_int t, to;
to = (mbp->timeout == 0) ? MBCMD_DEFAULT_TIMEOUT : mbp->timeout;
if (isp->isp_osinfo.mbox_sleep_ok) {
isp->isp_osinfo.mbox_sleep_ok = 0;
isp->isp_osinfo.mbox_sleeping = 1;
msleep_sbt(&isp->isp_osinfo.mboxcmd_done, &isp->isp_lock,
PRIBIO, "ispmbx_sleep", to * SBT_1US, 0, 0);
isp->isp_osinfo.mbox_sleep_ok = 1;
isp->isp_osinfo.mbox_sleeping = 0;
} else {
for (t = 0; t < to; t += 100) {
if (isp->isp_osinfo.mboxcmd_done)
break;
ISP_RUN_ISR(isp);
if (isp->isp_osinfo.mboxcmd_done)
break;
ISP_DELAY(100);
}
}
if (isp->isp_osinfo.mboxcmd_done == 0) {
isp_prt(isp, ISP_LOGWARN, "%s Mailbox Command (0x%x) Timeout (%uus) (%s:%d)",
isp->isp_osinfo.mbox_sleep_ok? "Interrupting" : "Polled",
isp->isp_lastmbxcmd, to, mbp->func, mbp->lineno);
mbp->param[0] = MBOX_TIMEOUT;
isp->isp_osinfo.mboxcmd_done = 1;
}
}
void
isp_mbox_notify_done(ispsoftc_t *isp)
{
isp->isp_osinfo.mboxcmd_done = 1;
if (isp->isp_osinfo.mbox_sleeping)
wakeup(&isp->isp_osinfo.mboxcmd_done);
}
void
isp_mbox_release(ispsoftc_t *isp)
{
isp->isp_osinfo.mboxbsy = 0;
}
int
isp_fc_scratch_acquire(ispsoftc_t *isp, int chan)
{

View File

@ -269,11 +269,6 @@ struct isposinfo {
struct isp_pcmd * pcmd_pool;
struct isp_pcmd * pcmd_free;
int mbox_sleeping;
int mbox_sleep_ok;
int mboxbsy;
int mboxcmd_done;
struct callout tmo; /* general timer */
/*
@ -428,11 +423,6 @@ default: \
break; \
}
#define MBOX_ACQUIRE isp_mbox_acquire
#define MBOX_WAIT_COMPLETE isp_mbox_wait_complete
#define MBOX_NOTIFY_COMPLETE isp_mbox_notify_done
#define MBOX_RELEASE isp_mbox_release
#define FC_SCRATCH_ACQUIRE isp_fc_scratch_acquire
#define FC_SCRATCH_RELEASE(isp, chan) isp->isp_osinfo.pc.fc[chan].fcbsy = 0
@ -631,10 +621,6 @@ extern int isp_quickboot_time;
void isp_prt(ispsoftc_t *, int level, const char *, ...) __printflike(3, 4);
void isp_xs_prt(ispsoftc_t *, XS_T *, int level, const char *, ...) __printflike(4, 5);
uint64_t isp_nanotime_sub(struct timespec *, struct timespec *);
int isp_mbox_acquire(ispsoftc_t *);
void isp_mbox_wait_complete(ispsoftc_t *, mbreg_t *);
void isp_mbox_notify_done(ispsoftc_t *);
void isp_mbox_release(ispsoftc_t *);
int isp_fc_scratch_acquire(ispsoftc_t *, int);
void isp_platform_intr(void *);
void isp_platform_intr_resp(void *);

View File

@ -831,11 +831,6 @@ void isp_async(ispsoftc_t *, ispasync_t, ...);
* various objects so that the ISP's and the system's view
* of the same object is consistent.
*
* MBOX_ACQUIRE(ispsoftc_t *) acquire lock on mailbox regs
* MBOX_WAIT_COMPLETE(ispsoftc_t *, mbreg_t *) wait for cmd to be done
* MBOX_NOTIFY_COMPLETE(ispsoftc_t *) notification of mbox cmd donee
* MBOX_RELEASE(ispsoftc_t *) release lock on mailbox regs
*
* FC_SCRATCH_ACQUIRE(ispsoftc_t *, chan) acquire lock on FC scratch area
* return -1 if you cannot
* FC_SCRATCH_RELEASE(ispsoftc_t *, chan) acquire lock on FC scratch area