>>> add include file for capabilities. *** 105,110 **** --- 105,111 ---- #endif #include "sys/dlsap_register.h" #endif /* _IRIX4 */ + #include "sys/capability.h" #ifdef QDBG struct tr_qs fvqs;
*** 547,552 **** --- 548,554 ---- { struct fv_info *fv = &fv_info[unit]; struct ifnet *ifp = &fv->fv_if; + ASSERT(IFNET_ISLOCKED(ifp)); if ((ifp->if_flags & IFF_RUNNING) != 0) { DP(("if_fvinit%d: already running\n", fv->fv_unit)); >>> also in the init routine. Release the interface lock >>> before sleeping, reacquire it after the sleep returns. *** 553,560 **** return(0); } ! if (fv->fv_state < FV_STATE_OK) sleep((caddr_t)&fv->fv_state, PZERO|PCATCH); if (fv->fv_state != FV_STATE_OK) { return(EIO); } --- 555,565 ---- return(0); } ! if (fv->fv_state < FV_STATE_OK) { ! IFNET_UNLOCKNOSPL(ifp); sleep((caddr_t)&fv->fv_state, PZERO|PCATCH); + IFNET_LOCKNOSPL(ifp); + } if (fv->fv_state != FV_STATE_OK) { return(EIO); } >>> this is in the driver's ioctl routine. ASSERT that the >>> ioctl routine was called with interface lock held. *** 894,899 **** --- 899,905 ---- struct fv_info *fv = &fv_info[ifp->if_unit]; ASSERT(&fv->fv_ac == (struct arpcom*)ifp); + ASSERT(IFNET_ISLOCKED(ifp)); switch (cmd) { case SIOCSIFADDR: { struct ifaddr *ifa = (struct ifaddr *)data; >>> TrIRIX change for privilege check. *** 1167,1173 **** case SIOC_TR_ARM: { TR_SIOC *sioc = (TR_SIOC*)data; ! if (!suser()) { error = EPERM; break; } --- 1173,1179 ---- case SIOC_TR_ARM: { TR_SIOC *sioc = (TR_SIOC*)data; ! if (!_CAP_ABLE(CAP_NETWORK_MGT)) { error = EPERM; break; }
*** 1231,1236 **** --- 1237,1243 ---- printf("fv%d: early interrupt\n", unit); goto fvintr_ret; } + IFNET_LOCKNOSPL(&fv->fv_if); QDBGUP(fvints.tot,1); mem = fv->fv_mem; iloop: More of the interrupt handler. Free the lock as we exit. *** 1237,1242 **** --- 1244,1250 ---- /* get the type of interrupt */ cmdsts = io->sifcmd_stat; if ((cmdsts&TR_STAT_INTR) == 0) { + IFNET_UNLOCKNOSPL(&fv->fv_if); goto fvintr_ret; } found++; >>> still more of the interrupt handler. *** 1300,1305 **** --- 1308,1314 ---- fv->fv_state = FV_STATE_SICK; } QDBGUP(fvints.buf,1); + IFNET_UNLOCKNOSPL(&fv->fv_if); goto fvintr_ret; case TR_INT_SCB_CLEAR: >>> frame receive handler. Lock the IP input queue to add a packet to it. *** 2031,2044 **** switch (port) { case ETHERTYPE_IP: - schednetisr(NETISR_IP); ifq = &ipintrq; if (IF_QFULL(ifq)) { IF_DROP(ifq); fv->fv_if.if_iqdrops++; goto drop; } ! IF_ENQUEUE(ifq, m0); goto read_ret; case ETHERTYPE_ARP: if (sri) { --- 2041,2057 ---- switch (port) { case ETHERTYPE_IP: ifq = &ipintrq; + IFQ_LOCK(ifq); if (IF_QFULL(ifq)) { IF_DROP(ifq); fv->fv_if.if_iqdrops++; + IFQ_UNLOCK(ifq); goto drop; } ! IF_ENQUEUE_NOLOCK(ifq, m0); ! IFQ_UNLOCK(ifq); ! schednetisr(NETISR_IP); goto read_ret; case ETHERTYPE_ARP: if (sri) { >>> Output routine, assert caller has if structure >>> locked for us. *** 2269,2274 **** --- 2282,2288 ---- ASSERT((ifp->if_unit >= 0) && (ifp->if_unit < FV_MAXBD)); fv = &fv_info[ifp->if_unit]; ASSERT(0 != fv->FVIO && ifp == &fv->fv_if); + ASSERT(IFNET_ISLOCKED(ifp)); /* 2: make sure board has been initialized properly */ if (fv->fv_state != FV_STATE_OK || iff_dead(ifp->if_flags)) { >>> close routine. ASSERT caller locked interface, >>> release and reacquire lock around sleep. *** 3750,3761 **** --- 3765,3780 ---- FVMEM *mem = fv->fv_mem; DP(("fv%d: close%\n", fv->fv_unit)); + ASSERT(IFNET_ISLOCKED(&fv->fv_if)); + if (fv->fv_state != FV_STATE_OK) goto close_ret; while ((fv->cmd_Flags[TR_CMD_CLOSE]&CMD_BUSY) != 0) { fv->cmd_Flags[TR_CMD_CLOSE] |= CMD_PENDING; + IFNET_UNLOCKNOSPL(&fv->fv_if); sleep((caddr_t)&fv->cmd_Flags[TR_CMD_CLOSE],PZERO|PCATCH); + IFNET_LOCKNOSPL(&fv->fv_if); } fv->cmd_Flags[TR_CMD_CLOSE] |= CMD_BUSY; >>> later in the close routine, another release/reacquire around sleep. *** 3776,3782 **** --- 3795,3803 ---- io->sifcmd_stat = TR_CMD_INT_ADAPT | TR_CMD_EXECUTE | TR_CMD_SCB_REQUEST | TR_STAT_INTR; + IFNET_UNLOCKNOSPL(&fv->fv_if); sleep((caddr_t)&fv->cmd_Status[TR_CMD_CLOSE], PZERO|PCATCH); + IFNET_LOCKNOSPL(&fv->fv_if); if (fv->cmd_Status[TR_CMD_CLOSE] == 0) { fv->fv_state = FV_STATE_CLOSE; fv->fv_if.if_flags &= ~(IFF_UP|IFF_RUNNING);
>>> delete the mbinit() call, no longer needed. *** 3174,3183 **** IDP(("fv%u: IVEC set!\n", unit)); #endif /* !_IRIX4 */ - /* 3: start the mbufs */ - mbinit(); ! /* 4: setup PRIVATE data.*/ /* TBD: allocate mcast filter table. * Probably, ALLMULTI(via ffffffff) should be used * and locally calculate correct filter. --- 3174,3181 ---- IDP(("fv%u: IVEC set!\n", unit)); #endif /* !_IRIX4 */ ! /* setup PRIVATE data.*/ /* TBD: allocate mcast filter table. * Probably, ALLMULTI(via ffffffff) should be used * and locally calculate correct filter.