SJA1000+XC7Z030,SJA1000初始化及PS数据读取
本人某高校研究生,剛剛研一,接觸了一些小項目,想單純記錄一下項目進度以及成果。水平不足,僅供參考,希望能夠對大家有所幫助。
板卡介紹:板卡上共4片SJA1000-T芯片,具體芯片功能不進行贅述了,布線方面,四片SJA1000的AD0~AD7拉成了一套數據地址總線,RD#、WR#、RST均是總線形式,ALE、INT#、CS#則是每片使用。
以下是SJA1000的具體原理圖,采用了兩片晶振分別為16MHZ和12MHZ,通過撥碼開關進行選擇。
接下來進行SJA1000初始化的具體操作:
Vivado部分:
首先,在Vivado中加入system.bd以及AXI GPIO IP核,此程序選擇dual channel 模式:
Auto Connect以后生成以下design。其中GPIO_0是所有的控制引腳,GPIO2_0則為AD0~AD7(需要注意的是,這里的信號反向全部使用IO,在SDK中我們可以通過XGpio_SetDirection函數進行輸入輸出方向的設置,其內部原理就是控制IOBUF中的IO_t引腳高低電平)
之后Create?HDL——Genrate Output——xdc管腳約束——generate bitstream——export hardware——launch sdk
SDK部分:
1.首先我們要根據Datasheet中給出的寄存器偏移地址寫出SJA1000.h文件方便之后寄存器調用
#ifndef ?__SJA1000_H__
#define ?__SJA1000_H__
#include ?"string.h"
#define ?SJA_BaseAdr ?0X00
#define ? ? ? ? REG_CONTROL ? ? ? SJA_BaseAdr+0x00 ? ? ? //內部控制寄存器
#define ? ? ? ? REG_COMMAND ? ? ? SJA_BaseAdr+0x01 ? ? ? //命令寄存器 ? ? ?只寫
#define ? ? ? ? REG_STATUS ? ? ? ?SJA_BaseAdr+0x02 ? ? ? //狀態寄存器 ? ? ?只讀
#define ? ? ? ? REG_INTERRUPT ? ? SJA_BaseAdr+0x03 ? ? ? //中斷寄存器 ? ? ?只讀
#define ? ? ? ? REG_INTENABLE ? ? SJA_BaseAdr+0x04 ? ? ? //中斷使能寄存器 ? 可讀可寫
#define ? ? ? ? REG_RESVER0 ? ? ? SJA_BaseAdr+0x05 ? ? ? //保留0
#define ? ? ? ? REG_BTR0 ? ? ? ? ?SJA_BaseAdr+0x06 ? ? ? //總線定時寄存器0 ?復位模式讀寫
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?//定義了波特率預設值BRP 和同步跳轉寬度SJW 的值
#define ? ? ? ? REG_BTR1 ? ? ? ? ?SJA_BaseAdr+0x07 ? ? ? //總線定時寄存器1 ?復位模式讀寫
//總線定時寄存器1 定義了每個位周期的長度采樣點的位置和在每個采樣點的采樣數目
#define ? ? ? ? REG_OCR ? ? ? ? ? SJA_BaseAdr+0x08 ? ? ? //輸出控制寄存器 ?復位模式讀寫
//輸出控制寄存器實現了由軟件控制不同輸出驅動配置的建立
#define ? ? ? ? REG_TEST ? ? ? ? ?SJA_BaseAdr+0x09 ? ? ? //測試寄存器
#define ? ? ? ? REG_RESVER1 ? ? ? SJA_BaseAdr+0x0A ? ? ? //保留1
#define ? ? ? ? REG_ARBITRATE ? ? SJA_BaseAdr+0x0B ? ? ? //仲裁丟失捕捉 ? ?只讀
#define ? ? ? ? REG_ERRCATCH ? ? ?SJA_BaseAdr+0x0C ? ? ? //錯誤代碼捕捉 ? ?只讀
#define ? ? ? ? REG_ERRLIMIT ? ? ?SJA_BaseAdr+0x0D ? ? ? //錯誤報警限額 ? ?工作模式只讀 復位模式可讀寫
#define ? ? ? ? REG_RXERR ? ? ? ? SJA_BaseAdr+0x0E ? ? ? ? //接收錯誤計數器工作模式只讀 復位模式可讀寫
#define ? ? ? ? REG_TXERR ? ? ? ? SJA_BaseAdr+0x0F ? ? ? ? //發送錯誤計數器工作模式只讀 復位模式可讀寫
#define ? ? ? ? REG_ACR0 ? ? ? ? ?SJA_BaseAdr+0x10 ? ? ? //驗收代碼寄存器
#define ? ? ? ? REG_ACR1 ? ? ? ? ?SJA_BaseAdr+0x11 ? ? ? //驗收代碼寄存器
#define ? ? ? ? REG_ACR2 ? ? ? ? ?SJA_BaseAdr+0x12 ? ? ? //驗收代碼寄存器
#define ? ? ? ? REG_ACR3 ? ? ? ? ?SJA_BaseAdr+0x13 ? ? ? //驗收代碼寄存器
#define ? ? ? ? REG_AMR0 ? ? ? ? ?SJA_BaseAdr+0x14 ? ? ? //驗收屏蔽寄存器
#define ? ? ? ? REG_AMR1 ? ? ? ? ?SJA_BaseAdr+0x15 ? ? ? //驗收屏蔽寄存器
#define ? ? ? ? REG_AMR2 ? ? ? ? ?SJA_BaseAdr+0x16 ? ? ? //驗收屏蔽寄存器
#define ? ? ? ? REG_AMR3 ? ? ? ? ?SJA_BaseAdr+0x17 ? ? ? //驗收屏蔽寄存器
// 發送緩沖區寄存器 ?(發送緩沖區長13字節,在CAN地址是16-28即0x10-0x1c)
#define ? ? ? ? REG_TXBuffer1 ? ? SJA_BaseAdr+0x10 ? ? ? ? //發送緩沖區1
#define ? ? ? ? REG_TXBuffer2 ? ? SJA_BaseAdr+0x11 ? ? ? ? //發送緩沖區2
#define ? ? ? ? REG_TXBuffer3 ? ? SJA_BaseAdr+0x12 ? ? ? ? //發送緩沖區3
#define ? ? ? ? REG_TXBuffer4 ? ? SJA_BaseAdr+0x13 ? ? ? ? //發送緩沖區4
#define ? ? ? ? REG_TXBuffer5 ? ? SJA_BaseAdr+0x14 ? ? ? ? //發送緩沖區5
#define ? ? ? ? REG_TXBuffer6 ? ? SJA_BaseAdr+0x15 ? ? ? ? //發送緩沖區6
#define ? ? ? ? REG_TXBuffer7 ? ? SJA_BaseAdr+0x16 ? ? ? ? //發送緩沖區7
#define ? ? ? ? REG_TXBuffer8 ? ? SJA_BaseAdr+0x17 ? ? ? ? //發送緩沖區8
#define ? ? ? ? REG_TXBuffer9 ? ? SJA_BaseAdr+0x18 ? ? ? ? //發送緩沖區9
#define ? ? ? ? REG_TXBuffer10 ? ?SJA_BaseAdr+0x19 ? ? ? ? //發送緩沖區10
#define ? ? ? ? REG_TXBuffer11 ? ?SJA_BaseAdr+0x1A ? ? ? ? //發送緩沖區11
#define ? ? ? ? REG_TXBuffer12 ? ?SJA_BaseAdr+0x1B ? ? ? ? //發送緩沖區12
#define ? ? ? ? REG_TXBuffer13 ? ?SJA_BaseAdr+0x1C ? ? ? ? //發送緩沖區13
// 接收緩沖區寄存器 ? (接收緩沖區長13字節,在CAN地址是16-28即0x10-0x1c)
#define ? ? ? ? REG_RXBuffer1 ? ? SJA_BaseAdr+0x10 ? ? ? //接收緩沖區1
#define ? ? ? ? REG_RXBuffer2 ? ? SJA_BaseAdr+0x11 ? ? ? //接收緩沖區2
#define ? ? ? ? REG_RXBuffer3 ? ? SJA_BaseAdr+0x12 ? ? ? ?//接收緩沖區3
#define ? ? ? ? REG_RXBuffer4 ? ? SJA_BaseAdr+0x13 ? ? ? //接收緩沖區4
#define ? ? ? ? REG_RXBuffer5 ? ? SJA_BaseAdr+0x14 ? ? ? ?//接收緩沖區5
#define ? ? ? ? REG_RXBuffer6 ? ? SJA_BaseAdr+0x15 ? ? ? ? //接收緩沖區6
#define ? ? ? ? REG_RXBuffer7 ? ? SJA_BaseAdr+0x16 ? ? ? ? //接收緩沖區7
#define ? ? ? ? REG_RXBuffer8 ? ? SJA_BaseAdr+0x17 ? ? ? ? //接收緩沖區8
#define ? ? ? ? REG_RXBuffer9 ? ? SJA_BaseAdr+0x18 ? ? ? ? //接收緩沖區9
#define ? ? ? ? REG_RXBuffer10 ? ?SJA_BaseAdr+0x19 ? ? ? ?//接收緩沖區10
#define ? ? ? ? REG_RXBuffer11 ? ?SJA_BaseAdr+0x1A ? ? ? ?//接收緩沖區11
#define ? ? ? ? REG_RXBuffer12 ? ?SJA_BaseAdr+0x1B ? ? ? ?//接收緩沖區12
#define ? ? ? ? REG_RXBuffer13 ? ?SJA_BaseAdr+0x1C ? ? ? ?//接收緩沖區13
#define ? ? ? ? REG_RXCOUNT ? ? ? SJA_BaseAdr+0x1D ? ? ? ? //RX報文計數器 ?只讀 RX信息計數器(RMC)反應RXFIFO中可用的信息數目
#define ? ? ? ? REG_RBSA ? ? ? ? ?SJA_BaseAdr+0x1E ? ? ? ? //RX緩沖器起始地址寄存器(RBSA)可讀寫 復位模式只寫
? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?//反映了當前可用來存儲位于接收緩沖器窗口中的信息的內部RAM地址
#define ? ? ? ? REG_CDR ? ? ? ? ? SJA_BaseAdr+0x1F ? ? ? ? //時鐘分頻寄存器
//時鐘分頻寄存器為微控制器控制CLKOUT 的頻率以及屏蔽CLKOUT 引腳而且它還控制著TX1上
//的專用接收中斷脈沖接收比較通道和BasicCAN 模式與PeliCAN 模式的選擇
/*
功能說明: ? CAN控制器SJA1000通訊波特率.SJA1000的晶振為必須為16MHZ*/
#define ? ? ? ? BTR0_Rate_20k ? ? ?0x53 ? ? ? ? ?//20KBPS的預設值
#define ? ? ? ? BTR1_Rate_20k ? ? ?0x2F ? ? ? ? ?//20KBPS的預設值
#define ? ? ? ? BTR0_Rate_40k ? ? ?0x87 ? ? ? ? ?//40KBPS的預設值
#define ? ? ? ? BTR1_Rate_40k ? ? ?0xFF ? ? ? ? ?//40KBPS的預設值
#define ? ? ? ? BTR0_Rate_50k ? ? ?0x47 ? ? ? ? ?//50KBPS的預設值
#define ? ? ? ? BTR1_Rate_50k ? ? ?0x2F ? ? ? ? ?//50KBPS的預設值
#define ? ? ? ? BTR0_Rate_80k ? ? ?0x83 ? ? ? ? ?//80KBPS的預設值
#define ? ? ? ? BTR1_Rate_80k ? ? ?0xFF ? ? ? ? ?//80KBPS的預設值
#define ? ? ? ? BTR0_Rate_100k ? ? 0x43 ? ? ? ? ?//100KBPS的預設值
#define ? ? ? ? BTR1_Rate_100k ? ? 0x2f ? ? ? ? ?//100KBPS的預設值
#define ? ? ? ? BTR0_Rate_125k ? ? 0x03 ? ? ? ? ?//125KBPS的預設值
#define ? ? ? ? BTR1_Rate_125k ? ? 0x1c ? ? ? ? ?//125KBPS的預設值
#define ? ? ? ? BTR0_Rate_200k ? ? 0x81 ? ? ? ? ?//200KBPS的預設值
#define ? ? ? ? BTR1_Rate_200k ? ? 0xFA ? ? ? ? ?//200KBPS的預設值
#define ? ? ? ? BTR0_Rate_250k ? ? 0x01 ? ? ? ? ?//250KBPS的預設值
#define ? ? ? ? BTR1_Rate_250k ? ? 0x1c ? ? ? ? ?//250KBPS的預設值
#define ? ? ? ? BTR0_Rate_400k ? ? 0x43 ? ? ? ? ?//400KBPS的預設值
#define ? ? ? ? BTR1_Rate_400k ? ? 0x11 ? ? ? ? ?//400KBPS的預設值
#define ? ? ? ? BTR0_Rate_500k ? ? 0x81 ? ? ? ? ?//500KBPS的預設值
#define ? ? ? ? BTR1_Rate_500k ? ? 0x23 ? ? ? ? ?//500KBPS的預設值
#define ? ? ? ? BTR0_Rate_666k ? ? 0x41 ? ? ? ? ?//666KBPS的預設值
#define ? ? ? ? BTR1_Rate_666k ? ? 0x12 ? ? ? ? ?//666KBPS的預設值
#define ? ? ? ? BTR0_Rate_800k ? ? 0x41 ? ? ? ? ?//800KBPS的預設值
#define ? ? ? ? BTR1_Rate_800k ? ? 0x11 ? ? ? ? ?//800KBPS的預設值
#define ? ? ? ? BTR0_Rate_1000k ? ?0x40 ? ? ? ? ?//1000KBPS的預設值
#define ? ? ? ? BTR1_Rate_1000k ? ?0x23 ? ? ? ? ?//1000KBPS的預設值
//BPS
//功能說明: ? CAN控制器SJA1000通訊波特率.SJA1000的晶振為必須為24MHZ*/
#define ? ? ? ? BTR0_Rate_10k ? ? ?0xEF ? ? ? ? ?//20KBPS的預設值
#define ? ? ? ? BTR1_Rate_10k ? ? ?0xFF ? ? ? ? ?//20KBPS的預設值
#define ? ? ? ? ByteRate_10k ? ? ? 10
#define ? ? ? ? ByteRate_20k ? ? ? 20
#define ? ? ? ? ByteRate_40k ? ? ? 40
#define ? ? ? ? ByteRate_50k ? ? ? 50
#define ? ? ? ? ByteRate_80k ? ? ? 80
#define ? ? ? ? ByteRate_100k ? ? ?100
#define ? ? ? ? ByteRate_125k ? ? ?125
#define ? ? ? ? ByteRate_200k ? ? ?200
#define ? ? ? ? ByteRate_250k ? ? ?250
#define ? ? ? ? ByteRate_400k ? ? ?400
#define ? ? ? ? ByteRate_500k ? ? ?500
#define ? ? ? ? ByteRate_800k ? ? ?800
#define ? ? ? ? ByteRate_1000k ? ? 1000
//命令字
#define ? ?TR_CMD ? ? 0X01 ?//CMR.0發送請求位
#define ? ?AT_CMD ? ? 0X02 ?//CMR.1中止發送位
#define ? ?RRB_CMD ? ?0X04 ?//CMR.2釋放接收緩沖器
#define ? ?COS_CMD ? ?0X08 ?//CMR.3清除數據溢出
#define ? ?SRR_CMD ? ?0X10 ?//CMR.4自接收模式
#define ? ?GTS_CMD ? ?0X10 ?//????CMR.5.CMR7保留位
//錯誤字
#define CAN_INTERFACE_OK ? ? ?0 ? ? //CAN總線接口OK
#define CAN_BUS_OK ? ? ? ? ? ?0 ? ? //CAN總線OK
#define CAN_INTERFACE_ERR ? ? 0XFF ?//CAN總線接口錯誤
#define CAN_ENTERSET_ERR ? ? ?0XFE ?//CAN總線初始化錯誤
#define CAN_QUITSET_ERR ? ? ? 0XFD ?//CAN總線退出復位模式錯誤
#define CAN_INITOBJECT_ERR ? ?0XFC ?//CAN總線初始化對象錯誤
#define CAN_INITBTR_ERR ? ? ? 0XFB ?//?
#define CAN_INITOUTCTL_ERR ? ?0XFA ?//??
#define CAN_INTCLKDIV_ERR ? ? 0XF9 ?//??
#define CAN_BUS_ERR ? ? ? ? ? 0XF8 ?//CAN總線錯誤
#define ID28_21 ? ?0X0A;
#define ID20_13 ? ?0X4A;
#define ID12_5 ? ? 0X6B;
#define ID4_0 ? ? ?0XE8; //低三位不影響設為0
//定義擴展模式數據幀ID
//Basic CAN模式標準幀格式 :幀信息,TX識別碼1-2,TX數據字節1-8
//Pelican模式擴展幀格式 ? :幀信息,TX識別碼1-4,TX數據字節1-8
#endif
?
2.根據時序圖進行寄存器讀寫操作,因為我采用的是Intel模式,這里只給出Intel的時序圖。
貼入部分代碼,以下SJA1000_WR_Time_1是通過控制CS,ALE,RD,WR根據SJA1000的datasheet給出的時序圖進行地址鎖存以及數據讀寫,這將應用在之后的SJA1000初始化時各寄存器的讀寫。
SJA1000_Read_1則是單純的寄存器數據讀。
(注:這兩個程序只是SJA1000中1片的讀寫,因為各片CS,ALE連接至PL端的引腳不同,所以每個都需要重新編寫)
?? ?int SJA1000_WR_Time_1(unsigned int Address,unsigned int Data)
{
/* Set the direction for all signals as inputs except the LED output */
//WRITE
?? ?int s;
?? ?XGpio_SetDataDirection(&Gpio1, CAN_CHANNEL1, 0x8E01);//all output except CAN_INT-input
?? ?XGpio_SetDataDirection(&Gpio2, CAN_CHANNEL2, 0x00);//all output AD0~AD7
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFF);//Test_Reg,ALE-1,WR-1,RD-1,CS-1,INT-1
?? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, Address);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFD);//Test_Reg,ALE-0,WR-1,RD-1,CS-1,INT-1,KEEP-ADDRESS
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FDD);//Test_Reg,ALE-0,WR-1,RD-1,CS-0,INT-1,KEEP-ADDRESS
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FD5);//Test_Reg,ALE-0,WR-0,RD-1,CS-0,ADDRESS-FREE
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FD5);//Test_Reg,SET-DATA,ALE-0,WR-0,RD-1,CS-0
?? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, Data);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FDD);//Test_Reg,SET-DATA,ALE-0,WR-1,RD-1,CS-0
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x99);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFD);//Test_Reg,SET-DATA,ALE-0,WR-1,RD-1,CS-1
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x99);
?? ?Delay_ms(1000);
//READ
?? ?//CHANNEL1:0:CAN1_INT,1:CAN1_ALE,2:CAN_RST,3:CAN_WR,4:CAN_RD,5:CAN1_CS,6:CAN2_CS,7:CAN3_CS,8:CAN4_CS
?? ?//CHANNEL2:0~7:AD0~AD7
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFF);//Test_Reg,ALE-1,WR-1,RD-1,CS-1,SET-ADDRESS
?? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, Address);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFD);//Test_Reg,ALE-0,WR-1,RD-1,CS-1,KEEP-ADDRESS
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FDD);//Test_Reg,ALE-0,WR-1,RD-1,CS-0,KEEP-ADDRESS
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FCD);//Test_Reg,ALE-0,WR-1,RD-0,CS-0,ADDRESS-FREE
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_SetDataDirection(&Gpio2, CAN_CHANNEL2, 0xFF);
?? ?Delay_ms(1000);
?? ?s = XGpio_DiscreteRead(&Gpio2, CAN_CHANNEL2);//Test_Reg,READ_DATA,ALE-0,WR-1,RD-0,CS-0
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FDD);//Test_Reg,ALE-0,WR-1,RD-1,CS-0?
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFD);//Test_Reg,ALE-0,WR-1,RD-1,CS-1
?? ?if(s == Data) return 1;
?? ?else ?return 0;
}
///
?? ?int SJA1000_Read_1(unsigned int Address)
{
?? ?int s;
?? ?XGpio_SetDataDirection(&Gpio1, CAN_CHANNEL1, 0x8E01);//all output except CAN_INT-input
?? ?XGpio_SetDataDirection(&Gpio2, CAN_CHANNEL2, 0x00);//all output AD0~AD7
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFF);//Test_Reg,ALE-1,WR-1,RD-1,CS-1,SET-ADDRESS
?? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, Address);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFD);//Test_Reg,ALE-0,WR-1,RD-1,CS-1,KEEP-ADDRESS
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FDD);//Test_Reg,ALE-0,WR-1,RD-1,CS-0,KEEP-ADDRESS
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FCD);//Test_Reg,ALE-0,WR-1,RD-0,CS-0,ADDRESS-FREE
//?? ??? ?XGpio_DiscreteWrite(&Gpio2, CAN_CHANNEL2, 0x09);
?? ?Delay_ms(1000);
?? ?XGpio_SetDataDirection(&Gpio2, CAN_CHANNEL2, 0xFF);
?? ?Delay_ms(1000);
?? ?s = XGpio_DiscreteRead(&Gpio2, CAN_CHANNEL2);//Test_Reg,READ_DATA,ALE-0,WR-1,RD-0,CS-0
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FDD);//Test_Reg,ALE-0,WR-1,RD-1,CS-0?
?? ?Delay_ms(1000);
?? ?XGpio_DiscreteWrite(&Gpio1, CAN_CHANNEL1, 0x0FFD);//Test_Reg,ALE-0,WR-1,RD-1,CS-1
?? ?return s;
}
3.SJA1000的初始化:這里給出的是一片SJA1000的初始化操作(這些是包含在主函數內部的,AXI GPIO的初始化等操作不再贅述了,看SDK內部例程即可),具體各寄存器內部配置請參考SJA1000的datasheet,大致就是要先進行測試寄存器讀寫判斷通道是否正常,時序是否有問題,之后進入復位模式,配置波特率,ACR,AMR,工作模式等,最后退出復位模式。
?? ?while(c==0){
?? ??? ??? ?if(SJA1000_WR_Time_4(REG_TEST,0XAA)==1)//sja_interface_test();
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Interface is OK!\r\n");
?? ??? ??? ??? ??? ?a = 1;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Interface error!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_CONTROL,0x09)==1 && a==1) //sja_init();
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Enter RST Mode is OK!\r\n");
?? ??? ??? ??? ??? ?b = SJA1000_Read_4(REG_CONTROL);//0X09
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("RST Mode fail\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_TEST,0xAA)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Test PASS!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Test Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_CDR,0xC8)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Clock Set is ok!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Clock Set Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_ACR0,0x0A)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("ACR0 SET 0X0A!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_ACR1,0x4A)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("ACR1 SET 0X4A!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_ACR2,0x6B)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("ACR2 SET 0X6B!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_ACR3,0x78)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("ACR3 SET 0X78!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_AMR0,0x00)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("AMR0 SET MODE 0X00!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_AMR1,0x00)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("AMR1 SET MODE 0X4A!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_AMR2,0x00)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("AMR2 SET MODE 0X6B!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_AMR3,0x03)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("AMR3 SET MODE 0X78!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_BTR0,BTR0_Rate_1000k)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("BANDRATE1 SET IS OK!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_BTR1,BTR1_Rate_1000k)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("BANDRATE2 SET IS OK!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_INTENABLE,0xFF)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Interrupt SET IS OK!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_OCR,0x1A)==1 && a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("OUTPUT MODE SET!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("OUTPUT MODE Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(SJA1000_WR_Time_4(REG_CONTROL,0x08) == 1 && a==1)//?
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("RST MODE IS QUIT!\r\n");
?? ??? ??? ??? ?}
?? ??? ??? ??? ?else
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("RST MODE QUIT Fail!\r\n");
?? ??? ??? ??? ??? ?a = 0;
?? ??? ??? ??? ?}
?? ??? ??? ??? ?if(a==1)
?? ??? ??? ??? ?{
?? ??? ??? ??? ??? ?printf("SJA1000_4 Init is OK\r\n");
?? ??? ??? ??? ??? ?c = 1;
?? ??? ??? ??? ?}
?? ?}
4.通過中斷信號進行數據讀取:
這里只是簡單的數據讀取,當SJA1000內部RXBuffer接收到數據時,會產生INT引腳拉低的情況,我的初步思考是通過讀取引腳電平,進行相應的數據讀取。
之前也考慮過中斷觸發的方式,但看了例程和網上PL-PS點燈的程序后,感覺也是進行中斷使能讀取的操作,不知道有沒有大佬給講講為什么要采用中斷方式,我這種直接讀取電平方式會有什么問題。
?? ?while(b)
?? ?{//4093 2045 1111 1111 1101 ? 0111 1111 1101
?? ? ? ?Which_SJA1000 = XGpio_DiscreteRead(&Gpio1, CAN_CHANNEL1);
?? ? ? ??? ?if((Which_SJA1000 & 0x0800) == 0)
?? ? ? ??? ?{
?? ? ? ??? ??? ?data1 = SJA1000_Read_4(REG_RXBuffer1);
?? ? ? ??? ?}
?? ? ? ??? ?else if((Which_SJA1000 & 0x0400) == 0)
?? ? ? ??? ?{
?? ? ? ??? ??? ?data2 = SJA1000_Read_3(REG_RXBuffer1);
?? ? ? ??? ?}
?? ? ? ??? ?else if((Which_SJA1000 & 0x0200) == 0)
?? ? ? ??? ?{
?? ? ? ??? ??? ?data3 = SJA1000_Read_2(REG_RXBuffer1);
?? ? ? ??? ?}
?? ? ? ??? ?else if((Which_SJA1000 & 0x0001) == 0)
?? ? ? ??? ?{
?? ? ? ??? ??? ?data4 = SJA1000_Read_1(REG_RXBuffer1);
?? ? ? ??? ?}
?? ?}
}
以上就是SJA1000的調試過程,歷經兩個星期調到了現在這個程度,感覺自己還是有點云里霧里的,有一個重點就是在起初的管腳約束時,引腳一定要分配正確!!!我就是因為xdc問題,導致開始無法正確讀寫寄存器數據,搞了很久最后發現是XDC的問題。大家引以為戒,如果有任何建議和問題,請告訴我,我們共同進步。
總結
以上是生活随笔為你收集整理的SJA1000+XC7Z030,SJA1000初始化及PS数据读取的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 王岚老师计算机,平凡中演绎精彩——优秀教
- 下一篇: 利用有限元数值模拟技术辅助静电场学习