📄 moto.c
字号:
/*********************************************************************
* Filename: MOTO.c
*
* Description: This example illustrates the "MOTO" feature.
*
* Deliberately let a transmit mailbox timeout and check whether the
* corresponding interrupt flag (MTOFn) and TOSn is set.
* Mailbox 0 is used in this example
*
* Last update: 12/26/2002
*********************************************************************/
#include "DSP28_Device.h"
// Variable declarations
long i;
int int0count = 0; // Counter to track the # of level 0 interrupts
int int1count = 0; // Counter to track the # of level 1 interrupts
// Prototype statements for functions found within this file.
interrupt void eCAN0INT_ISR(void);
interrupt void eCAN1INT_ISR(void);
/* Create a shadow register structure for the CAN control registers. This is
needed, since, only 32-bit access is allowed to these registers. 16-bit access
to these registers could potentially corrupt the register contents. This is
especially true while writing to a bit (or group of bits) among bits 16 - 31 */
struct ECAN_REGS ECanaShadow;
void InitECan(void);
main()
{
/* Initialize the CAN module */
InitECan();
/* Initialize PIE vector table To a Known State: */
// The PIE vector table is initialized with pointers to shell "Interrupt
// Service Routines (ISR)". The shell routines are found in DSP28_DefaultIsr.c.
// Insert user specific ISR code in the appropriate shell ISR routine in
// the DSP28_DefaultIsr.c file.
// InitPieVectTable(); // uncomment this line if the shell ISR routines are needed
// This function is found in DSP28_PieVect.c. It populates the PIE vector table
// with pointers to the shell ISR functions found in DSP28_DefaultIsr.c. This
// function is not useful in this code because the user-specific ISR is present
// in this file itself. The shell ISR routine in the DSP28_DefaultIsr.c file is
// not used. If the shell ISR routines are needed, uncomment this line and add
// DSP28_PieVect.c & DSP28_DefaultIsr.c files to the project
/* Disable and clear all CPU interrupts: */
DINT;
IER = 0x0000;
IFR = 0x0000;
/* Initialize Pie Control Registers To Default State */
InitPieCtrl(); // This function is found in the DSP28_PieCtrl.c file.
/* Write to the MSGID field */
ECanaMboxes.MBOX0.MSGID.all = 0x9555AA00;
/* Configure Mailbox under test as Tx */
ECanaRegs.CANMD.all = 0; // All mailboxes are made transmit..
/* Enable Mailbox under test */
ECanaShadow.CANME.all = ECanaRegs.CANME.all;
ECanaShadow.CANME.bit.ME0 = 1;
ECanaRegs.CANME.all = ECanaShadow.CANME.all;
/* Write to Master Control field */
ECanaMboxes.MBOX0.MCF.bit.DLC = 8;
/* Write to the mailbox RAM field */
ECanaMboxes.MBOX0.MDRL.all = 0x9555AAA0;
ECanaMboxes.MBOX0.MDRH.all = 0x89ABCDEF;
/* Configure CAN interrupts */
ECanaShadow.CANMIL.all = ECanaRegs.CANMIL.all;
ECanaShadow.CANMIL.bit.MIL0 = 0 ; // MBOX0 asserts MTOF0 (eCAN0INT)
//ECanaShadow.CANMIL.bit.MIL0 = 1 ; // MBOX0 asserts MTOF1 (eCAN1INT)
ECanaRegs.CANMIL.all = ECanaShadow.CANMIL.all;
ECanaShadow.CANGIM.all = 0;
ECanaShadow.CANGIM.bit.I0EN = 1; // Enable eCAN0INT
ECanaShadow.CANGIM.bit.I1EN = 1; // Enable eCAN1INT
ECanaShadow.CANGIM.bit.MTOM = 1; // Enable MBX Timeout interrupt
ECanaRegs.CANGIM.all = ECanaShadow.CANGIM.all;
/* Reassign ISRs. i.e. reassign the PIE vector for ECAN0INTA_ISR and ECAN0INTA_ISR
to point to a different ISR than the shell routine found in DSP28_DefaultIsr.c.
This is done if the user does not want to use the shell ISR routine but instead
wants to embed the ISR in this file itself. */
PieVectTable.ECAN0INTA = &eCAN0INT_ISR;
PieVectTable.ECAN1INTA = &eCAN1INT_ISR;
/* Configure PIE interrupts */
PieCtrlRegs.PIECRTL.bit.ENPIE = 1; // Enable vector fetching from PIE block
PieCtrlRegs.PIEACK.bit.ACK9 = 1; // Enables PIE to drive a pulse into the CPU
// The 'MOTO' interrupt can be asserted in either of the eCAN interrupt lines
// Comment out the unwanted line...
PieCtrlRegs.PIEIER9.bit.INTx5 = 1; // Enable INTx.5 of INT9 (eCAN0INT)
PieCtrlRegs.PIEIER9.bit.INTx6 = 1; // Enable INTx.6 of INT9 (eCAN1INT)
/* Configure system interrupts */
IER |= 0x0100; // Enable INT9 of CPU
EINT; // Global enable of interrupts
/* Write to MOTO reg of Mailbox under test */
ECanaMOTORegs.MOTO0 = 0x8D; // It was experimentally determined that
// this value would let MBX0 to timeout...MOTS0 contains
// 8Eh after transmission is complete..See Note 1
/* Enable time-out function for the mailbox */
ECanaShadow.CANTOC.all = 0;
ECanaShadow.CANTOC.bit.TOC0 = 1;
ECanaRegs.CANTOC.all = ECanaShadow.CANTOC.all;
/* Clear the "Time Stamp Counter" */
ECanaRegs.CANTSC = 0;
/* Begin transmitting */
ECanaShadow.CANTRS.all = 0;
ECanaShadow.CANTRS.bit.TRS0 = 1; // Set TRS for mailbox under test
ECanaRegs.CANTRS.all = ECanaShadow.CANTRS.all;
for(i=0; i<9999999; i++) // A very long loop. Code loops here when CAN module transmits
{ asm(" NOP"); } // the data and executes the ISR
asm(" ESTOP0"); // Code stops here after transmission
}
/* --------------------------------------------------- */
/* ISR for PIE INT9.5 */
/* Connected to HECC0-INTA eCAN */
/* ----------------------------------------------------*/
interrupt void eCAN0INT_ISR(void) // eCAN
{
ECanaShadow.CANTOS.all = ECanaRegs.CANTOS.all ; // Copy TOS reg for inspection
ECanaShadow.CANGIF0.all = ECanaRegs.CANGIF0.all; // Copy GIF0 reg for inspection
while(ECanaRegs.CANTA.bit.TA0 != 1 ) {} // TAn bit set?
// Clear TAn
ECanaShadow.CANTA.all = 0; // Initialize TA to zero before setting any
ECanaShadow.CANTA.bit.TA0 = 1 ; // bit in order to clear it. Otherwise, some
// other TAn bit that is set could be inadvertently cleared
ECanaRegs.CANTA.all = ECanaShadow.CANTA.all ; // Clear TAn bit
// Clear MTOF0
// MTOF0 cannot be manually cleared. It is automatically cleared when TOSn is cleared,
// which is automatically cleared when the message is successfully transmitted.
// Re-enable PIE and Core interrupts
PieCtrlRegs.PIEACK.bit.ACK9 = 1; // Enables PIE to drive a pulse into the CPU
IER |= 0x0100; // These 2 lines allow for nested interrupts
EINT; // Strictly not needed for this example.
int0count++;
return;
}
/* --------------------------------------------------- */
/* ISR for PIE INT9.6 */
/* Connected to HECC1-INTA eCAN */
/* ----------------------------------------------------*/
interrupt void eCAN1INT_ISR(void) // eCAN
{
ECanaShadow.CANTOS.all = ECanaRegs.CANTOS.all ; // Copy TOS reg for inspection
ECanaShadow.CANGIF1.all = ECanaRegs.CANGIF1.all; // Copy GIF1 reg for inspection
while(ECanaRegs.CANTA.bit.TA0 != 1 ) {} // TAn bit set?
// Clear TAn
ECanaShadow.CANTA.all = 0; // Initialize TA to zero before setting any
ECanaShadow.CANTA.bit.TA0 = 1 ; // bit in order to clear it. Otherwise, some
// other TAn bit that is set could be inadvertently cleared
ECanaRegs.CANTA.all = ECanaShadow.CANTA.all ; // Clear TAn bit
// Clear MTOF1
// MTOF1 cannot be manually cleared. It is automatically cleared when TOSn is cleared,
// which is automatically cleared when the message is successfully transmitted.
// Re-enable PIE and Core interrupts
PieCtrlRegs.PIEACK.bit.ACK9 = 1; // Enables PIE to drive a pulse into the CPU
IER |= 0x0100; // Enable INT9
EINT;
int1count++;
return;
}
/* Notes:
The TOS.n bit will be cleared upon (eventual) successful transmission.
The only way to ascertain if a time-out occured is to copy TOS and GIFn
registers in the ISR to check if the relevant bits were set when the
ISR was just entered.
It can be verified that whether the MTOF bit gets set in GIF0 or GIF1
depends on the value of MILn.
This example is useful to check that MTOFn gets cleared if TOSn is cleared.
Note 1: TSC does not start running until the bit timing registers
are configured. After configuration, it is a free running timer clocked by the
bit rate clock of the CAN module. The delay between the last instruction
that configures the bit timing to the instruction that initiates transmission will
therefore affect this "experimentally determined" value. Since the counter runs at
the bit clock rate, the fastest bit clock rate is 1 uS, which equates to 150 CPU
clock cycles (@ 150 MHz SYSCLKOUT). Therefore adding/deleting a few instructions
will not make a significant change. A delay loop would.
*/
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -