📄 riotable.c
字号:
** Now we have a host we need to allocate an ID ** if the entry does not already have one. */ if (MapP->ID == (ushort)-1) { int nNewID; rio_dprintk (RIO_DEBUG_TABLE, "Attempting to get a new ID for rta \"%s\"\n", MapP->Name); /* ** The idea here is to allow RTA's to be assigned ** before they actually appear on the network. ** This allows the addition of RTA's without having ** to plug them in. ** What we do is: ** - Find a free ID and allocate it to the RTA. ** - If this map entry is the second half of a ** 16 port entry then find the other half and ** make sure the 2 cross reference each other. */ if (RIOFindFreeID(p, &p->RIOHosts[host], &nNewID, NULL) != 0) { p->RIOError.Error = COULDNT_FIND_ENTRY; return -EBUSY; } MapP->ID = (ushort)nNewID + 1; rio_dprintk (RIO_DEBUG_TABLE, "Allocated ID %d for this new RTA.\n", MapP->ID); HostMapP = &p->RIOHosts[host].Mapping[nNewID]; HostMapP->RtaUniqueNum = MapP->RtaUniqueNum; HostMapP->HostUniqueNum = MapP->HostUniqueNum; HostMapP->ID = MapP->ID; for (link = 0; link < LINKS_PER_UNIT; link++) { HostMapP->Topology[link].Unit = ROUTE_DISCONNECT; HostMapP->Topology[link].Link = NO_LINK; } if (MapP->Flags & RTA16_SECOND_SLOT) { int unit; for (unit = 0; unit < MAX_RUP; unit++) if (p->RIOHosts[host].Mapping[unit].RtaUniqueNum == MapP->RtaUniqueNum) break; if (unit == MAX_RUP) { p->RIOError.Error = COULDNT_FIND_ENTRY; return -EBUSY; } HostMapP->Flags |= RTA16_SECOND_SLOT; HostMapP->ID2 = MapP->ID2 = p->RIOHosts[host].Mapping[unit].ID; p->RIOHosts[host].Mapping[unit].ID2 = MapP->ID; rio_dprintk (RIO_DEBUG_TABLE, "Cross referenced id %d to ID %d.\n", MapP->ID, p->RIOHosts[host].Mapping[unit].ID); } } HostMapP = &p->RIOHosts[host].Mapping[MapP->ID-1]; if ( HostMapP->Flags & SLOT_IN_USE ) { rio_dprintk (RIO_DEBUG_TABLE, "Map table slot for ID %d is already in use.\n", MapP->ID); p->RIOError.Error = ID_ALREADY_IN_USE; return -EBUSY; } /* ** Assign the sys ports and the name, and mark the slot as ** being in use. */ HostMapP->SysPort = MapP->SysPort; if ((MapP->Flags & RTA16_SECOND_SLOT) == 0) CCOPY( MapP->Name, HostMapP->Name, MAX_NAME_LEN ); HostMapP->Flags = SLOT_IN_USE | RTA_BOOTED;#ifdef NEED_TO_FIX RIO_SV_BROADCAST(p->RIOHosts[host].svFlags[MapP->ID-1]);#endif if (MapP->Flags & RTA16_SECOND_SLOT) HostMapP->Flags |= RTA16_SECOND_SLOT; RIOReMapPorts( p, &p->RIOHosts[host], HostMapP ); /* ** Adjust 2nd block of 8 phbs */ if (MapP->Flags & RTA16_SECOND_SLOT) RIOFixPhbs(p, &p->RIOHosts[host], HostMapP->ID - 1); if ( HostMapP->SysPort != NO_PORT ) { if ( HostMapP->SysPort < p->RIOFirstPortsBooted ) p->RIOFirstPortsBooted = HostMapP->SysPort; if ( HostMapP->SysPort > p->RIOLastPortsBooted ) p->RIOLastPortsBooted = HostMapP->SysPort; } if (MapP->Flags & RTA16_SECOND_SLOT) rio_dprintk (RIO_DEBUG_TABLE, "Second map of RTA %s added to configuration\n", p->RIOHosts[host].Mapping[MapP->ID2 - 1].Name); else rio_dprintk (RIO_DEBUG_TABLE, "RTA %s added to configuration\n", MapP->Name); return 0; } } p->RIOError.Error = UNKNOWN_HOST_NUMBER; rio_dprintk (RIO_DEBUG_TABLE, "Unknown host %x\n", MapP->HostUniqueNum); return -ENXIO;}intRIOReMapPorts(p, HostP, HostMapP)struct rio_info * p;struct Host *HostP;struct Map *HostMapP; { register struct Port *PortP; uint SubEnt; uint HostPort; uint SysPort; ushort RtaType; unsigned long flags;#ifdef CHECK CheckHostP( HostP ); CheckHostMapP( HostMapP );#endif rio_dprintk (RIO_DEBUG_TABLE, "Mapping sysport %d to id %d\n", (int)HostMapP->SysPort, HostMapP->ID); /* ** We need to tell the UnixRups which sysport the rup corresponds to */ HostP->UnixRups[HostMapP->ID-1].BaseSysPort = HostMapP->SysPort; if ( HostMapP->SysPort == NO_PORT ) return(0); RtaType = GetUnitType(HostMapP->RtaUniqueNum); rio_dprintk (RIO_DEBUG_TABLE, "Mapping sysport %d-%d\n", (int)HostMapP->SysPort, (int)HostMapP->SysPort+PORTS_PER_RTA-1); /* ** now map each of its eight ports */ for ( SubEnt=0; SubEnt<PORTS_PER_RTA; SubEnt++) { rio_dprintk (RIO_DEBUG_TABLE, "subent = %d, HostMapP->SysPort = %d\n", SubEnt, (int)HostMapP->SysPort); SysPort = HostMapP->SysPort+SubEnt; /* portnumber within system */ /* portnumber on host */ HostPort = (HostMapP->ID-1)*PORTS_PER_RTA+SubEnt; rio_dprintk (RIO_DEBUG_TABLE, "c1 p = %p, p->rioPortp = %p\n", p, p->RIOPortp); PortP = p->RIOPortp[SysPort];#if 0 PortP->TtyP = &p->channel[SysPort];#endif rio_dprintk (RIO_DEBUG_TABLE, "Map port\n"); /* ** Point at all the real neat data structures */ rio_spin_lock_irqsave(&PortP->portSem, flags); PortP->HostP = HostP; PortP->Caddr = HostP->Caddr; /* ** The PhbP cannot be filled in yet ** unless the host has been booted */ if ((HostP->Flags & RUN_STATE) == RC_RUNNING) { struct PHB *PhbP = PortP->PhbP = &HostP->PhbP[HostPort]; PortP->TxAdd =(WORD *)RIO_PTR(HostP->Caddr,RWORD(PhbP->tx_add)); PortP->TxStart =(WORD *)RIO_PTR(HostP->Caddr,RWORD(PhbP->tx_start)); PortP->TxEnd =(WORD *)RIO_PTR(HostP->Caddr,RWORD(PhbP->tx_end)); PortP->RxRemove=(WORD *)RIO_PTR(HostP->Caddr, RWORD(PhbP->rx_remove)); PortP->RxStart =(WORD *)RIO_PTR(HostP->Caddr,RWORD(PhbP->rx_start)); PortP->RxEnd =(WORD *)RIO_PTR(HostP->Caddr,RWORD(PhbP->rx_end)); } else PortP->PhbP = NULL; /* ** port related flags */ PortP->HostPort = HostPort; /* ** For each part of a 16 port RTA, RupNum is ID - 1. */ PortP->RupNum = HostMapP->ID - 1; if (HostMapP->Flags & RTA16_SECOND_SLOT) { PortP->ID2 = HostMapP->ID2 - 1; PortP->SecondBlock = TRUE; } else { PortP->ID2 = 0; PortP->SecondBlock = FALSE; } PortP->RtaUniqueNum = HostMapP->RtaUniqueNum; /* ** If the port was already mapped then thats all we need to do. */ if (PortP->Mapped) { rio_spin_unlock_irqrestore( &PortP->portSem, flags); continue; } else HostMapP->Flags &= ~RTA_NEWBOOT; PortP->State = 0; PortP->Config = 0; /* ** Check out the module type - if it is special (read only etc.) ** then we need to set flags in the PortP->Config. ** Note: For 16 port RTA, all ports are of the same type. */ if (RtaType == TYPE_RTA16) { PortP->Config |= p->RIOModuleTypes[HostP->UnixRups [HostMapP->ID-1].ModTypes].Flags[SubEnt % PORTS_PER_MODULE]; } else { if ( SubEnt < PORTS_PER_MODULE ) PortP->Config |= p->RIOModuleTypes[LONYBLE(HostP->UnixRups [HostMapP->ID-1].ModTypes)].Flags[SubEnt % PORTS_PER_MODULE]; else PortP->Config |= p->RIOModuleTypes[HINYBLE(HostP->UnixRups [HostMapP->ID-1].ModTypes)].Flags[SubEnt % PORTS_PER_MODULE]; } /* ** more port related flags */ PortP->PortState = 0; PortP->ModemLines = 0; PortP->ModemState = 0; PortP->CookMode = COOK_WELL; PortP->ParamSem = 0; PortP->FlushCmdBodge= 0; PortP->WflushFlag = 0; PortP->MagicFlags = 0; PortP->Lock = 0; PortP->Store = 0; PortP->FirstOpen = 1; /* ** Buffers 'n things */ PortP->RxDataStart = 0; PortP->Cor2Copy = 0; PortP->Name = &HostMapP->Name[0];#ifdef STATS bzero( (caddr_t)&PortP->Stat, sizeof(struct RIOStats) );#endif PortP->statsGather = 0; PortP->txchars = 0; PortP->rxchars = 0; PortP->opens = 0; PortP->closes = 0; PortP->ioctls = 0; if ( PortP->TxRingBuffer ) bzero( PortP->TxRingBuffer, p->RIOBufferSize ); else if ( p->RIOBufferSize ) { PortP->TxRingBuffer = sysbrk(p->RIOBufferSize); bzero( PortP->TxRingBuffer, p->RIOBufferSize ); } PortP->TxBufferOut = 0; PortP->TxBufferIn = 0; PortP->Debug = 0; /* ** LastRxTgl stores the state of the rx toggle bit for this ** port, to be compared with the state of the next pkt received. ** If the same, we have received the same rx pkt from the RTA ** twice. Initialise to a value not equal to PHB_RX_TGL or 0. */ PortP->LastRxTgl = ~(uchar)PHB_RX_TGL; /* ** and mark the port as usable */ PortP->Mapped = 1; rio_spin_unlock_irqrestore(&PortP->portSem, flags); } if ( HostMapP->SysPort < p->RIOFirstPortsMapped ) p->RIOFirstPortsMapped = HostMapP->SysPort; if ( HostMapP->SysPort > p->RIOLastPortsMapped ) p->RIOLastPortsMapped = HostMapP->SysPort; return 0;}intRIOChangeName(p, MapP)struct rio_info *p;struct Map* MapP; { int host; struct Map *HostMapP; char *sptr; rio_dprintk (RIO_DEBUG_TABLE, "Change name entry on host %x, rta %x, ID %d, Sysport %d\n", MapP->HostUniqueNum,MapP->RtaUniqueNum, MapP->ID, (int)MapP->SysPort); if ( MapP->ID > MAX_RUP ) { rio_dprintk (RIO_DEBUG_TABLE, "Bad ID in map entry!\n"); p->RIOError.Error = ID_NUMBER_OUT_OF_RANGE; return -EINVAL; } MapP->Name[MAX_NAME_LEN-1] = '\0'; sptr = MapP->Name; while ( *sptr ) { if ( *sptr<' ' || *sptr>'~' ) { rio_dprintk (RIO_DEBUG_TABLE, "Name entry contains non-printing characters!\n"); p->RIOError.Error = BAD_CHARACTER_IN_NAME; return -EINVAL; } sptr++; } for ( host=0; host < p->RIONumHosts; host++ ) { if ( MapP->HostUniqueNum == p->RIOHosts[host].UniqueNum ) { if ( (p->RIOHosts[host].Flags & RUN_STATE) != RC_RUNNING ) { p->RIOError.Error = HOST_NOT_RUNNING; return -ENXIO; } if ( MapP->ID==0 ) { CCOPY( MapP->Name, p->RIOHosts[host].Name, MAX_NAME_LEN ); return 0; } HostMapP = &p->RIOHosts[host].Mapping[MapP->ID-1]; if ( HostMapP->RtaUniqueNum != MapP->RtaUniqueNum ) { p->RIOError.Error = RTA_NUMBER_WRONG; return -ENXIO; } CCOPY( MapP->Name, HostMapP->Name, MAX_NAME_LEN ); return 0; } } p->RIOError.Error = UNKNOWN_HOST_NUMBER; rio_dprintk (RIO_DEBUG_TABLE, "Unknown host %x\n", MapP->HostUniqueNum); return -ENXIO;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -