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

📄 sja1000.c

📁 canbus4linux,来自www.sourceforge.net
💻 C
📖 第 1 页 / 共 3 页
字号:
 		TRACE("Error Warning IRQ"); 		//sja1000_WriteRegister(pSja1000Par, 1,0x0e);                 // Release Receive Buffer + ClearDataOverrun + AbortTransmission (danach erfolgt ein Transmit-IRQ) 		//sja1000_WriteRegister(pSja1000Par, 0, ~0x01 & sja1000_ReadRegister(pSja1000Par,0));       // resetMode l鰏chen 		ev.event = CANBUS_EVENT_WARNING;  		pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev); 	}  	if (irq & 0x08)				// Overrun Interrupt 	{ 		TRACE("Overrun IRQ"); 		sja1000_WriteRegister(pSja1000Par, 1,0x0c); // Release Receive Buffer + ClearDataOverrun 		ev.event = CANBUS_EVENT_OVERRUN;  		pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev); 	}  	if (irq & 0x10)				// WakeUp Interrupt 	{ 		TRACE("WakeUp IRQ"); 		ev.event = CANBUS_EVENT_LEAVING_STANDBY;  		pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev);  	}  	if (irq & 0x20)				// Error Passive Interrupt 	{ 		TRACE("Error passive IRQ"); 		ev.event = CANBUS_EVENT_PASSIVE;  		pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev); 	}  	if (irq & 0x40)				// Arbitration lost Interrupt 	{ 		TRACE("Arbitration lost IRQ"); 		ev.event = CANBUS_EVENT_ARBITRATION_LOST;  		pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev); 	}  	if (irq & 0x80)				// Error Passive Interrupt 	{ 		TRACE("Buserror IRQ"); 		sja1000_WriteRegister(pSja1000Par, 1,0x0e);                 // Release Receive Buffer + ClearDataOverrun + AbortTransmission (danach erfolgt ein Transmit-IRQ) 		sja1000_WriteRegister(pSja1000Par, 0, ~0x01 & sja1000_ReadRegister(pSja1000Par,0));       // resetMode l鰏chen 		ev.event = CANBUS_EVENT_BUS_ERROR;  		pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev); 	}  	return 1;		// TRUE = IRQ wurde bedient}/***************************************************************************************/int BasicCanISR(struct sja1000_admin *pSja1000Par){    u8 irq;	u8 status;	struct canbus_event ev;	int   t;	irq = sja1000_ReadRegister(pSja1000Par, 3);                                                // Interrupt-Register lesen	TRACE("BasicCan IRQ 0x%x",irq);	if (!(irq & 0x1f))		return 0;	TRACE("IRQ wird bearbeitet");	if(pSja1000Par->isr)	{ 		if (irq & 0x01)			// Receive Interrupt  		{  			TRACE("Receive IRQ");  			ev.event = CANBUS_EVENT_RECEIVED; 			ev.data.identifier = sja1000_ReadRegister(pSja1000Par, 20); 			status = sja1000_ReadRegister(pSja1000Par, 21);  			ev.data.fmt = CANBUS_TRANS_FMT_STD;  			ev.data.identifier = (ev.data.identifier << 3) + ((status & 0xe0)>>5);  			ev.data.rtr = (status & 0x10) >> 4;  			ev.data.dlc = (status & 0x0f);  			for(t=0;(t<8) && (t<ev.data.dlc);t++)  			{ 				ev.data.msg[t] = sja1000_ReadRegister(pSja1000Par, (u8)22+t);  			} 			sja1000_WriteRegister(pSja1000Par, 1,0x04); // ReleaseReceiveBuffer (Rx Buffer wird dadurch ung黮tig)  			pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev);  		}  		if (irq & 0x02)			// Transmit Interrupt  		{  			TRACE("Transmit IRQ");  			ev.event = CANBUS_EVENT_TRANSMITTED;  			pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev);  		}  		if (irq & 0x04)			// Error Interrupt  		{  			TRACE("Error IRQ"); 			sja1000_WriteRegister(pSja1000Par, 1,0x0e);                 // Release Receive Buffer + ClearDataOverrun + AbortTransmission (danach erfolgt ein Transmit-IRQ) 			status = sja1000_ReadRegister(pSja1000Par, 0);             // Status einlesen  			status = status & 0xfe; // ResetMode l鰏chen 			sja1000_WriteRegister(pSja1000Par, 0,status);         			ev.event = CANBUS_EVENT_BUS_ERROR;  			pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev);  		}  		if (irq & 0x08)			// Overrun Interrupt  		{  			TRACE("Overrun IRQ"); 			sja1000_WriteRegister(pSja1000Par, 1,0x0c); // Release Receive Buffer + ClearDataOverrun  			ev.event = CANBUS_EVENT_OVERRUN;  			pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev);  		}  		if (irq & 0x10)			// WakeUp Interrupt  		{  			TRACE("WakeUp IRQ");  			ev.event = CANBUS_EVENT_LEAVING_STANDBY;  			pSja1000Par->isr(pSja1000Par->pCanBusParm, pSja1000Par->pCanBusParm, &ev);  		}  	}  	else    // Setze nur die Bits zur點k  	{ 		if (irq & 0x01)				// Receive Interrupt  		{ 			sja1000_WriteRegister(pSja1000Par, 1,0x04); // ReleaseReceiveBuffer (Rx Buffer wird dadurch ung黮tig)  		}  		if (irq & 0x04)				// Error Interrupt  		{ 			sja1000_WriteRegister(pSja1000Par, 1,0x0e);                 // Release Receive Buffer + ClearDataOverrun + AbortTransmission (danach erfolgt ein Transmit-IRQ) 			status = sja1000_ReadRegister(pSja1000Par, 0);             // read state  			status = status & 0xfe; // clear ResetMode 			sja1000_WriteRegister(pSja1000Par, 0,status);         		}  		if (irq & 0x08)				// Overrun Interrupt  		{ 			sja1000_WriteRegister(pSja1000Par, 1,0x0c); // Release Receive Buffer + ClearDataOverrun  		}  	}  	return 1;		// TRUE = IRQ was served}/***************************************************************************************//*int sja1000_interrupt(void *pSpecificPar, struct sja1000_admin *pSja1000Par){	int ret=0;	int x=30;	if(!pSja1000Par)		return 0;//  HMM: Rubini's linux device drivers has erroneous statement about spin_trylock return value//	the right treatment is as follows: 0 - failed, non-0 got lock (rubini: 0 - got lock)//	see Linux Device Drivers 2nd edition, page 282.//	XTRACE("InterruptProcedure - before spin_trylock...");	if (!spin_trylock(&pSja1000Par->irq_lock))	{//		XTRACE("...xxx");//		XTRACE("spin_is_locked: %i", spin_is_locked(&pSja1000Par->irq_lock));		return 0;	// irq handling is disabled for this chip	}	TRACE("InterruptProcedure");	if (pSja1000Par->bCan_2B)	{		while(x>0)		{			if(PeliCanISR(pSja1000Par))				ret=1;			else				break;			x--;		}	}	else	{		while(x>0)		{			if(BasicCanISR(pSja1000Par))				ret=1;			else				break;			x--;		}	}	spin_unlock(&pSja1000Par->irq_lock);	return ret;}*/int sja1000_interrupt(void *pSpecificPar, struct sja1000_admin *pSja1000Par){	int ret=0;	int x=30;	if(!pSja1000Par)		return 0;	TRACE("InterruptProcedure");	if (pSja1000Par->bCan_2B)	{		while(x>0)		{			if(PeliCanISR(pSja1000Par))				ret=1;			else				break;			x--;		}	}	else	{		while(x>0)		{			if(BasicCanISR(pSja1000Par))				ret=1;			else				break;			x--;		}	}	return ret;}/***************************************************************************************/int sja1000_register_isr(struct sja1000_admin *pSja1000Par, canbus_isr pIsr, struct canbus_admin *pCanBusPar){	TRACE("registering isr()");	if(!pSja1000Par)		return -EINVAL;	pSja1000Par->isr = pIsr;	pSja1000Par->pCanBusParm = pCanBusPar;	return 0;}/***************************************************************************************/int sja1000_unregister_isr(struct sja1000_admin *pSja1000Par){	TRACE("unregistering isr()");	if(!pSja1000Par)		return -EINVAL;	pSja1000Par->isr = 0;	pSja1000Par->pCanBusParm = NULL;	return 0;}/***************************************************************************************/int sja1000_register_device(char *name, int version, void *pSpecificPar, struct sja1000_access *access, int prefered_min, int prefered_max){	int t,p;	char buffer[MAX_DEVICE_NAME_LENGTH*2];		TRACE("registering can device: %s",name);	for(t=0;t<NUM_SJA1000_DEVICES;t++) // searching a free structure	{		if(sja1000_admin[t].in_use == 0)		{			struct canbus_access caccess;						memset(&caccess,0,sizeof(caccess));			memset(&sja1000_admin[t],0,sizeof(struct sja1000_admin));			memcpy(&sja1000_admin[t].access, access,sizeof(struct sja1000_access));			strcpy(buffer,name);			buffer[MAX_DEVICE_NAME_LENGTH-1] = 0;			strcpy(sja1000_admin[t].cDeviceName,buffer);			for(p=0;p<strlen(sja1000_admin[t].cDeviceName);p++)			{				if(sja1000_admin[t].cDeviceName[p] == '|') // only device name				{					sja1000_admin[t].cDeviceName[p] = 0;					break;				}			}			strcpy(&buffer[strlen(buffer)],"|SJA 1000 Chipset driver");			sja1000_admin[t].pDeviceParm = pSpecificPar;			sja1000_admin[t].irq_lock = SPIN_LOCK_UNLOCKED;			spin_lock_init(&(sja1000_admin[t].irq_lock));			if (access->pRegisterIsr) 				(access->pRegisterIsr)(pSpecificPar, sja1000_interrupt, &sja1000_admin[t]);			sja1000_admin[t].in_use = 1; 			caccess.pRegisterIsr   = (canbus_registerIsr)	sja1000_register_isr; 			caccess.pUnregisterIsr = (canbus_unregisterIsr)	sja1000_unregister_isr;   			caccess.pOpen  = (canbus_open_device)  sja1000_open_device; 			caccess.pClose = (canbus_close_device) sja1000_close_device; 			caccess.pInit  = (canbus_init_device)  sja1000_init_device;  			caccess.pSetBaudrate  = (canbus_set_baudrate)	sja1000_set_baudrate; 			caccess.pGetProperty  = (canbus_get_properties)	sja1000_get_properties; 			caccess.pSetRegister  = (canbus_set_register)	sja1000_set_register; 			caccess.pGetRegister  = (canbus_get_register)	sja1000_get_register; 			caccess.pSetCanMode   = (canbus_set_can_mode)	sja1000_set_can_mode; 			caccess.pSetBaudrateByConstant = (canbus_set_baudrate_by_constant) 															sja1000_set_baudrate_by_constant; 			caccess.pSetAcceptanceFilter = (canbus_set_acceptance_filter) 															sja1000_set_acceptance_filter;  			caccess.pSetCommand   = (canbus_set_command)	sja1000_set_command; 			caccess.pTransmitData = (canbus_transmit_data)	sja1000_transmit_data; 			caccess.pTestDevice   = (canbus_test_device)	sja1000_test_device;			sja1000_admin[t].canbus_admin_number = canbus4linux_register_device(buffer, CANBUS4LINUX_VERSION, &sja1000_admin[t], &caccess, prefered_min, prefered_max);			TRACE("sja1000_register_device() - finished");			return t;		}	}		return -1;}/***************************************************************************************/int sja1000_unregister_device(int can_num){ 	if (sja1000_admin[can_num].in_use == 0) 		return 0;  	TRACE("unregistering can device: %s",sja1000_admin[can_num].cDeviceName); 	sja1000_admin[can_num].canbus_admin_number = canbus4linux_unregister_device(sja1000_admin[can_num].canbus_admin_number); 	if (sja1000_admin[can_num].access.pUnregisterIsr) 		(sja1000_admin[can_num].access.pUnregisterIsr)(sja1000_admin[can_num].pDeviceParm);  	memset(&sja1000_admin[can_num],0,sizeof(struct sja1000_admin));	return 0;}/***************************************************************************************/int init_module(void){	TRACE("init_module()");	memset(sja1000_admin,0,sizeof(sja1000_admin));  	return 0;}/***************************************************************************************/void cleanup_module(void){  	TRACE("cleanup");}/***************************************************************************************/EXPORT_SYMBOL(sja1000_unregister_device);EXPORT_SYMBOL(sja1000_register_device);MODULE_AUTHOR("Juergen Eder  <Juergen.Eder@gmx.de>");MODULE_DESCRIPTION("SJA1000 chipset driver");

⌨️ 快捷键说明

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