⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 riotable.c

📁 h内核
💻 C
📖 第 1 页 / 共 3 页
字号:
			continue;		}		/*		** Its an RTA entry, so fill in the host mapping entries for it		** and the port mapping entries. Notice that entry zero is for		** ID one.		*/		HostMapP = &HostP->Mapping[MapP->ID-1];		if (MapP->Flags & SLOT_IN_USE) {			rio_dprintk (RIO_DEBUG_TABLE, "Rta entry found. Name %s\n", MapP->Name);			/*			** structure assign, then sort out the bits we shouldn't have done			*/			*HostMapP = *MapP;			HostMapP->Flags = SLOT_IN_USE;			if (MapP->Flags & RTA16_SECOND_SLOT)				HostMapP->Flags |= RTA16_SECOND_SLOT;			RIOReMapPorts(p, HostP, HostMapP );		}		else {			rio_dprintk (RIO_DEBUG_TABLE, "TENTATIVE Rta entry found. Name %s\n", MapP->Name);		}	}	for ( Entry=0; Entry< TOTAL_MAP_ENTRIES; Entry++ ) {		p->RIOSavedTable[Entry] = p->RIOConnectTable[Entry];	}	for ( Host=0; Host<p->RIONumHosts; Host++ ) {		for ( SubEnt=0; SubEnt<LINKS_PER_UNIT; SubEnt++ ) {			p->RIOHosts[Host].Topology[SubEnt].Unit = ROUTE_DISCONNECT;			p->RIOHosts[Host].Topology[SubEnt].Link = NO_LINK;		}		for ( Entry=0; Entry<MAX_RUP; Entry++ ) {			for ( SubEnt=0; SubEnt<LINKS_PER_UNIT; SubEnt++ ) {				p->RIOHosts[Host].Mapping[Entry].Topology[SubEnt].Unit = 								ROUTE_DISCONNECT;				p->RIOHosts[Host].Mapping[Entry].Topology[SubEnt].Link = 								NO_LINK;			}		}		if ( !p->RIOHosts[Host].Name[0] ) {			bcopy("HOST 1",p->RIOHosts[Host].Name,7);			p->RIOHosts[Host].Name[5] += Host;		}		/*		** Check that default name assigned is unique.		*/		Host1 = Host;		NameIsUnique = 0;		while (!NameIsUnique) {			NameIsUnique = 1;			for ( Host2=0; Host2<p->RIONumHosts; Host2++ ) {				if (Host2 == Host)					continue;				if (strcmp(p->RIOHosts[Host].Name, p->RIOHosts[Host2].Name)									 == 0) {					NameIsUnique = 0;					Host1++;					if (Host1 >= p->RIONumHosts)						Host1 = 0;					p->RIOHosts[Host].Name[5] = '1' + Host1;				}			}		}		/*		** Rename host if name already used.		*/		if (Host1 != Host)		{			rio_dprintk (RIO_DEBUG_TABLE, "Default name %s already used\n", p->RIOHosts[Host].Name);			bcopy("HOST 1",p->RIOHosts[Host].Name,7);			p->RIOHosts[Host].Name[5] += Host1;		}		rio_dprintk (RIO_DEBUG_TABLE, "Assigning default name %s\n", p->RIOHosts[Host].Name);	}	return 0;}/*** User process needs the config table - build it from first** principles.*/intRIOApel(p)struct rio_info *	p;{	int Host;	int link;	int Rup;	int Next = 0;	struct Map *MapP;	struct Host *HostP;	long oldspl;	disable(oldspl);		/* strange but true! */ 	rio_dprintk (RIO_DEBUG_TABLE, "Generating a table to return to config.rio\n");	bzero((caddr_t)&p->RIOConnectTable[0], 					sizeof(struct Map) * TOTAL_MAP_ENTRIES );	for ( Host=0; Host<RIO_HOSTS; Host++ ) {		rio_dprintk (RIO_DEBUG_TABLE, "Processing host %d\n", Host);		HostP = &p->RIOHosts[Host];		MapP = &p->RIOConnectTable[Next++];		MapP->HostUniqueNum = HostP->UniqueNum;		if ( (HostP->Flags & RUN_STATE) != RC_RUNNING )			continue;		MapP->RtaUniqueNum = 0;		MapP->ID = 0;		MapP->Flags = SLOT_IN_USE;		MapP->SysPort = NO_PORT;		for ( link=0; link<LINKS_PER_UNIT; link++ )			MapP->Topology[link] = HostP->Topology[link];		bcopy(HostP->Name,MapP->Name,MAX_NAME_LEN);		for ( Rup=0; Rup<MAX_RUP; Rup++ ) {			if ( HostP->Mapping[Rup].Flags & (SLOT_IN_USE|SLOT_TENTATIVE) ) {				p->RIOConnectTable[Next] = HostP->Mapping[Rup];				if ( HostP->Mapping[Rup].Flags & SLOT_IN_USE)					p->RIOConnectTable[Next].Flags |= SLOT_IN_USE;				if ( HostP->Mapping[Rup].Flags & SLOT_TENTATIVE)					p->RIOConnectTable[Next].Flags |= SLOT_TENTATIVE;				if ( HostP->Mapping[Rup].Flags & RTA16_SECOND_SLOT )					p->RIOConnectTable[Next].Flags |= RTA16_SECOND_SLOT;				Next++;			}		}	}	restore(oldspl);	return 0;}/*** config.rio has taken a dislike to one of the gross maps entries.** if the entry is suitably inactive, then we can gob on it and remove** it from the table.*/intRIODeleteRta(p, MapP)struct rio_info *p;struct Map *MapP;{	int host, entry, port, link;	int SysPort;	struct Host *HostP;	struct Map *HostMapP;	struct Port *PortP;	int work_done = 0;	unsigned long lock_flags, sem_flags;	rio_dprintk (RIO_DEBUG_TABLE, "Delete entry on host %x, rta %x\n",								MapP->HostUniqueNum, MapP->RtaUniqueNum);	for ( host=0; host < p->RIONumHosts; host++ ) {		HostP = &p->RIOHosts[host];		rio_spin_lock_irqsave( &HostP->HostLock, lock_flags );		if ( (HostP->Flags & RUN_STATE) != RC_RUNNING ) {			rio_spin_unlock_irqrestore(&HostP->HostLock, lock_flags);			continue;		}		for ( entry=0; entry<MAX_RUP; entry++ ) {			if ( MapP->RtaUniqueNum == HostP->Mapping[entry].RtaUniqueNum ) {				HostMapP = &HostP->Mapping[entry];				rio_dprintk (RIO_DEBUG_TABLE, "Found entry offset %d on host %s\n", 						entry, HostP->Name);				/*				** Check all four links of the unit are disconnected				*/				for ( link=0; link< LINKS_PER_UNIT; link++ ) {					if ( HostMapP->Topology[link].Unit != ROUTE_DISCONNECT ) {						rio_dprintk (RIO_DEBUG_TABLE, "Entry is in use and cannot be deleted!\n");						p->RIOError.Error = UNIT_IS_IN_USE;						rio_spin_unlock_irqrestore( &HostP->HostLock, lock_flags);						return -EBUSY;					}				}				/*				** Slot has been allocated, BUT not booted/routed/				** connected/selected or anything else-ed				*/				SysPort = HostMapP->SysPort;				if ( SysPort != NO_PORT ) {					for (port=SysPort; port < SysPort+PORTS_PER_RTA; port++) {						PortP = p->RIOPortp[port];						rio_dprintk (RIO_DEBUG_TABLE, "Unmap port\n");						rio_spin_lock_irqsave( &PortP->portSem, sem_flags );						PortP->Mapped = 0;						if ( PortP->State & (RIO_MOPEN|RIO_LOPEN) ) {							rio_dprintk (RIO_DEBUG_TABLE, "Gob on port\n");							PortP->TxBufferIn = PortP->TxBufferOut = 0;							/* What should I do 							wakeup( &PortP->TxBufferIn );							wakeup( &PortP->TxBufferOut);							*/							PortP->InUse = NOT_INUSE;							/* What should I do 							wakeup( &PortP->InUse );							signal(PortP->TtyP->t_pgrp,SIGKILL);							ttyflush(PortP->TtyP,(FREAD|FWRITE));							*/							PortP->State |= RIO_CLOSING | RIO_DELETED;						}						/*						** For the second slot of a 16 port RTA, the						** driver needs to reset the changes made to						** the phb to port mappings in RIORouteRup.						*/						if (PortP->SecondBlock) {							ushort dest_unit = HostMapP->ID;							ushort dest_port = port - SysPort;							WORD	 *TxPktP;							PKT	*Pkt;							for (TxPktP = PortP->TxStart;								TxPktP <= PortP->TxEnd; TxPktP++) {								/*								** *TxPktP is the pointer to the								** transmit packet on the host card.								** This needs to be translated into								** a 32 bit pointer so it can be								** accessed from the driver.								*/								Pkt = (PKT *) RIO_PTR(HostP->Caddr,								 	RWORD(*TxPktP));								rio_dprintk (RIO_DEBUG_TABLE, 						"Tx packet (%x) destination: Old %x:%x New %x:%x\n",								 *TxPktP, Pkt->dest_unit,								 Pkt->dest_port, dest_unit, dest_port);								WWORD(Pkt->dest_unit, dest_unit);								WWORD(Pkt->dest_port, dest_port);							}							rio_dprintk (RIO_DEBUG_TABLE, 						"Port %d phb destination: Old %x:%x New %x:%x\n",							 port, PortP->PhbP->destination & 0xff,							 (PortP->PhbP->destination >> 8) & 0xff,							 dest_unit, dest_port);							WWORD(PortP->PhbP->destination,							 dest_unit + (dest_port << 8));						}						rio_spin_unlock_irqrestore(&PortP->portSem, sem_flags);					}				}				rio_dprintk (RIO_DEBUG_TABLE, "Entry nulled.\n");				bzero((char *)HostMapP,sizeof(struct Map));				work_done++;			}		}		rio_spin_unlock_irqrestore(&HostP->HostLock, lock_flags);	}	/* XXXXX lock me up */	for ( entry=0; entry< TOTAL_MAP_ENTRIES; entry++ ) {		if ( p->RIOSavedTable[entry].RtaUniqueNum == MapP->RtaUniqueNum ) {			bzero((char *)&p->RIOSavedTable[entry],sizeof(struct Map));			work_done++;		}		if ( p->RIOConnectTable[entry].RtaUniqueNum == MapP->RtaUniqueNum ) {			bzero((char *)&p->RIOConnectTable[entry],sizeof(struct Map));			work_done++;		}	}	if ( work_done )		return 0;	rio_dprintk (RIO_DEBUG_TABLE, "Couldn't find entry to be deleted\n");	p->RIOError.Error = COULDNT_FIND_ENTRY;	return -ENXIO;}int RIOAssignRta( struct rio_info *p, struct Map *MapP ){    int host;    struct Map *HostMapP;    char *sptr;    int	link;    rio_dprintk (RIO_DEBUG_TABLE, "Assign entry on host %x, rta %x, ID %d, Sysport %d\n",				MapP->HostUniqueNum,MapP->RtaUniqueNum,				MapP->ID, (int)MapP->SysPort);    if ((MapP->ID != (ushort)-1) &&	((int)MapP->ID < (int)1 || (int)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;    }    if (MapP->RtaUniqueNum == 0)    {	rio_dprintk (RIO_DEBUG_TABLE, "Rta Unique number zero!\n");	p->RIOError.Error = RTA_UNIQUE_NUMBER_ZERO;	return -EINVAL;    }    if ( (MapP->SysPort != NO_PORT) && (MapP->SysPort % PORTS_PER_RTA) )    {	rio_dprintk (RIO_DEBUG_TABLE, "Port %d not multiple of %d!\n",(int)MapP->SysPort,PORTS_PER_RTA);	p->RIOError.Error = TTY_NUMBER_OUT_OF_RANGE;	return -EINVAL;    }    if ( (MapP->SysPort != NO_PORT) && (MapP->SysPort >= RIO_PORTS) )    {	rio_dprintk (RIO_DEBUG_TABLE, "Port %d not valid!\n",(int)MapP->SysPort);	p->RIOError.Error = TTY_NUMBER_OUT_OF_RANGE;	return -EINVAL;    }    /*    ** Copy the name across to the map entry.    */    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;	    }	    /*

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -