Board logo

标题: S12 CAN的ID识别问题 [打印本页]

作者: qianwei920    时间: 2005-9-19 10:01     标题: S12 CAN的ID识别问题

CAN的ID过滤是由MSCAN模块硬件实现的吗?也就是说软件上并不需要去比较接收到的数据帧的ID是不是等于本节点的ID。是这样吗?
CANIDAC寄存器中的IDHIT2~0位怎么用,是不是根据设置的滤波方式,由mscan的硬件去判断是否ID命中了?也就是说软件上不需要任何程序关于ID过滤
作者: brucesj    时间: 2005-9-20 09:11

是靠软件的设置来硬件实现的!
作者: qianwei920    时间: 2005-9-20 14:59

软件不就设置一下屏蔽id的那几个字节吗,是否匹配是由硬件比较完成的呀。
作者: yunfeng    时间: 2005-9-20 19:45

请到飞思卡尔网站网站上看这个文档
Application notes
AN2010/D  -  Using The Motorola msCAN Filter Configuration Tool
作者: dreamcatcher    时间: 2006-4-25 21:45

请问msCAN的ID是怎么设置的?怎么得到的?

作者: zhwdy81    时间: 2006-4-26 11:59

d0-d31
d0 RTR位,为0
d19 IDE 1
d20 SRR 1
d27 DP 0
d28 R 0

其他位填入ID

就是行了
比如说
id:18ff0088
填入后变为:c7fe0110
作者: dreamcatcher    时间: 2006-4-26 15:51

28,27,26, 25, 24,23,22, 21,
20,19,18,SSR,IDE,17,16, 15,
14,13,12, 11, 10, 9, 8, 7,
6, 5, 4, 3, 2, 1, 0,RTR
我明白了!!
非常感谢!!
那么IDR和IDAR寄存器的值是不是应该相同呢?
作者: lingxiang    时间: 2006-4-26 16:19

我现在也正在调试CAN,但是老是不通,请问有谁知道CAN的滤波网络到底是怎样工作的啊?
当MCU接收到CAN总线上的数据时,是样识别本地ID的啊?
作者: lingxiang    时间: 2006-4-26 16:23

还有谁能告诉我一下,CAN如果向另一方发送数据时,对方收不到的话,是不是发送方就停止向外发送数据啊,也及CAN总线上无信号产生啊.
作者: dreamcatcher    时间: 2006-4-26 19:52

我觉得当接收到的IDR寄存器的值与设定的IDAR寄存器的值相同的时候,如果对应的屏蔽寄存器没有屏蔽的话,即过滤器命中,也就是接受成功了!

作者: lingxiang    时间: 2006-4-27 15:04

为什么我的MCU中的CAN在自发自收的情况下是可以通信的,但是在加上MC33989后与另外一个CAN模块进行通信时却始终没有任何信号啊?
有谁遇到过这样的情况啊?
请帮小弟一下,我实在是失去信心在调下去了.一点结果都没有.
作者: dreamcatcher    时间: 2006-4-27 20:09

可能是IDR,IDAR,IDMR寄存器的值不合理把?
你试过给IDMR=$FF,全屏蔽掉,可以通信吗?
作者: lingxiang    时间: 2006-4-28 09:17

上面这位仁兄,我现在把程序也发给你,给我看看好吗?
我现在觉得到不是IDR,IDAR,IDMR的问题,到是MC33989之间不能通信啊.
MC33989该如何使用啊?
#include /* for EnableInterrupts macro */
#include /* include peripheral declarations */

//---------------------定义全局变量------------------//

unsigned int SPI_count=0; //SPI 计数器

void CAN_Transmit(void);


//----------------- transmit SPI program ------------------//

void transmit_SPI (unsigned char SPI_data)
{
PTC_PTC2 = 0 ; PTC_PTC2 = 0 ; PTC_PTC2 = 0 ;
PTC_PTC2 = 0 ; PTC_PTC2 = 0 ; PTC_PTC2 = 0 ; //SPI 端口拉低

while(SPSCR_SPTE==0);
SPDR=SPI_data;

PTC_PTC2 = 0 ; PTC_PTC2 = 0 ; PTC_PTC2 = 0 ;
PTC_PTC2 = 0 ; PTC_PTC2 = 0 ; PTC_PTC2 = 0 ; //SPI 继续端口拉低

PTC_PTC2 = 1 ; PTC_PTC2 = 1 ; // SPI 端口拉高

}




//------------------display function---------------------//
void delay(void) {
int i ;

for( i = 0; i < 100; i++) {


}
}


//------------------timer interrupt program------------------------//

interrupt 4 void TimerInterrupt(void)
{
PSC_PSTOP = 0x01;
PSC_POF = 0x00;
PSC_PRST = 0x01; //clear PSC_POF and let timer modul execute again


__RESET_WATCHDOG(); // kicks the watchdog


SPI_count++;

if(SPI_count==5) //every 100ms SPI W/D
{
transmit_SPI(0xB3);

SPI_count = 0;

CAN_Transmit();

}



PSC_PSTOP = 0;

}


interrupt 17 void CAN_Receive(void) {
unsigned char receive[8]={0,0,0,0,0,0,0,0};
unsigned char id[4] = {0,0,0,0};
PTA_PTA7 = 1;
delay();
PTA_PTA7 = 0;
delay();
id[0] = REC_IDR0;
id[1] = REC_IDR1;
id[2] = REC_IDR2;
id[3] = REC_IDR3;

receive[0] = REC_DSR0;
receive[1] = REC_DSR1;
receive[2] = REC_DSR2;
receive[3] = REC_DSR3;
receive[4] = REC_DSR4;
receive[5] = REC_DSR5;
receive[6] = REC_DSR6;
receive[7] = REC_DSR7;
CRFLG_RXF = 1;


}
//--------------------------- CAN transmit program ----------------------//

void CAN_Transmit(void){

unsigned char emptytest;
unsigned char emptytest0;
unsigned char emptytest1;
unsigned char emptytest2;

emptytest = CTFLG;

emptytest0 = emptytest&0x01; //判断接受区为空
emptytest1 = emptytest&0x02;
emptytest2 = emptytest&0x04;



if(emptytest0!=0)
{
DLR0 = 0x08;


DSR00 = 0xff;
DSR10 = 0x00;
DSR20 = 0xff;
DSR30 = 0x00;
DSR40 = 0xff;
DSR50 = 0x00;
DSR60 = 0xff;
DSR70 = 0x00;


IDR00 = 0x33; // DP256:0x11; AZ60:0x33; GZ16:0x22; MPC555:0x44
IDR10 = 0xFF;
IDR20 = 0xFF;
IDR30 = 0xFE; //extended identifers

TBPR0 = 0x01;

CTFLG = 0x01; //buffer0 启动发送


}



else if(emptytest1!=0)
{
DLR1 = 0x08;


DSR01 = 0xff;
DSR11 = 0x00;
DSR21 = 0xff;
DSR31 = 0x00;
DSR41 = 0xff;
DSR51 = 0x00;
DSR61 = 0xff;
DSR71 = 0x00;

IDR01 = 0x33; // DP256:0x11; AZ60:0x33; GZ16:0x22; MPC555:0x44
IDR11 = 0xFF;
IDR21 = 0xFF;
IDR31 = 0xFE; //extended identifers

TBPR1 = 0x01;

CTFLG = 0x02; //buffer1 启动发送


}




else if(emptytest2!=0)
{
DLR2 = 0x08;


DSR02 = 0xff;
DSR12 = 0x00;
DSR22 = 0xff;
DSR32 = 0x00;
DSR42 = 0xff;
DSR52 = 0x00;
DSR62 = 0xff;
DSR72 = 0x00;

IDR02 = 0x33; // DP256:0x11; AZ60:0x33; GZ16:0x22; MPC555:0x44
IDR12 = 0xFF;
IDR22 = 0xFF;
IDR32 = 0xFE; //extended identifers

TBPR2 = 0x01;

CTFLG = 0x04; //buffer2 启动发送


}


}





//------------------------ Ports initial ------------------------------//
void Init_PORT(void){
DDRA_DDRA7 = 1;

DDRC_DDRC2 = 1; //MC33989 CSB choice
DDRC_DDRC4 = 1;
DDRC_DDRC5 = 1;


DDRE_DDRE4 = 0x0; //PTE4==high, AZ32A als master wird

PTA_PTA7 = 0;
PTC_PTC2 = 1 ;
PTC_PTC4 = 0 ;
PTC_PTC5 = 0 ;

}


//-------------------------SPI initial program-------------------------//

void Init_SPI(void){

SPCR_SPE =1; //设置SPI寄存器
SPCR_SPMSTR = 1;

SPSCR_SPR0=0;
SPSCR_SPR1=0; //bund rate =500k ,CGMOUT=2M hz ,intenal bus clock =1M hz

PTC_PTC2 = 1 ;

}


//--------------------------MSCAN initial program-----------------------//

void Init_MSCAN08(void){

CMCR0 = 0x01; //CAN模块为软复位状态
CMCR1 = 0x04;
CBTR0 = 0x43;
CBTR1 = 0xA3; //波特率为62.5K


CIDAC = 0x00; //接收滤波为32位滤波


CIDAR0 = 0x00; //滤波使它接收一帧
CIDAR1 = 0x00;
CIDAR2 = 0x00;
CIDAR3 = 0x00; //extended identifers

CIDMR0 = 0xFF;
CIDMR1 = 0xFF;
CIDMR2 = 0xFF;
CIDMR3 = 0xFF; //extended identifers



CMCR0 = 0x00; //把CAN模块设置为数据输入输出状态

CRIER = 0xff; //CAN接收中断使能

}





//------------------------MCU initial program------------------------//

void Init_AZ32A(void)
{

//CONFIG1 = 0x70; //cop module enable
//CONFIG2 = 0x09; //配置寄存器初始化,外接晶振4MHZ,内部总线1MHZ
//MORA_COPD = 0x70;

PSC_PPS = 0; //1分频
PSC_POIE = 1; //PIT interrupt enable

PMODH = 0x03;
PMODL = 0xe8; //定时器设置成为1ms产生一次中断

PSC_PSTOP = 0; //PIT 计数器启动

Init_PORT();
Init_MSCAN08(); //MSCAN initial
Init_SPI(); //SPI initial


}

//----------------------------main function----------------------------//

void main(void){

EnableInterrupts; //中断使能

Init_AZ32A(); //调用单片机初始化子程序

//set MC33989 status by SPI
transmit_SPI(0xB3); //set MC33889 watchdog works at no window mode and 350ms
transmit_SPI(0x11); //set MC33889 MCR Reg,and MC33889 works at Normal status
transmit_SPI(0x50); //set MC33889 CAN Reg,and CAN works normal status

for(;;){
/*delay();
transmit_SPI(0xB3);
delay();
CAN_Transmit(); */

//__RESET_WATCHDOG(); /* feeds the dog */
}
}


如果是自发自收,我通过单步调试是可以通信的.也就是我发送成功,接收缓冲寄存器也相应地正确地接收到发送的值.

可是我用2块板子之间进行调试时始终看不到总线上有信号.

请哪位高手帮忙看一下我的程序代码有何问题?

在此谢过!

作者: lingxiang    时间: 2006-4-28 09:20

我始终努力地坚持着,一定要把它调通,这就是我们这个行业的敬业精神!
作者: yanjihu    时间: 2006-4-30 01:31

简单的很,只要打通V2即可,你对手册没有看透
作者: lingxiang    时间: 2006-4-30 13:04

什么意思?
我是个初学者,敬请详细讲解!
大侠,救救在下!
作者: lingxiang    时间: 2006-4-30 13:18

对了, 我上面的程序是属于自发自收的,如果是在2块板子之间通信,那要把寄存器设置改为
CMCR1 = 0x00;
作者: lingxiang    时间: 2006-5-8 15:09

yanjihu大侠:
救救俺!
作者: yanjihu    时间: 2006-5-10 15:44

你的电源工作没有正常,你可以通过示波器观察989的复位,如果989的复位没有出现350ms的复位,那就说明工作基本正常,这是可以将复位与MCU的复位相连接了,如果你的989的寄存器写的正确,(先写B3,后写11),如果你的SPI硬件连接正常,应该V2就正常了!
transmit_SPI989(0xB3);
transmit_SPI989(0x11);
作者: lingxiang    时间: 2006-5-10 16:09

yanjihu兄弟,谢谢你.我还想请教个问题:就是CAN在没有接收端,只有发送端的情况下一直向外发送会不会有数据产生啊?
我现在的情况就是MCU的CAN的发送端无任何信号.
结果我把2块板子的MCU的CAN发送端的TX与接收端的RX和发送端的RX与接收端的TX相连接,结果在CAN的发送端产生了方波信号.
请问这是什么原因?
作者: lingxiang    时间: 2006-5-10 16:11

yan大侠你所说的V2到底指的是什么?
是不是收发器啊?




欢迎光临 电子技术论坛_中国专业的电子工程师学习交流社区-中电网技术论坛 (http://bbs.eccn.com/) Powered by Discuz! 7.0.0