Hi all. I'm trying to use C++ and IAR for TMS470 uC's but I'm getting some weird troubles with C++. For example: I have a simple test code to receive CAN frames using interrupts. It compiles ok but when the frame arrives the application blows! If I use the same logic and configurations with C compiler everything works perfectly. I did a research for C++ Projects with TMS470 but didn't find anything... Do you have a link or a simple C++ IAR project using interrupts? Any help will be appreciated! Thanks a lot!
TMS470 with IAR C++ Compiler
Started by ●January 22, 2009
Reply by ●January 22, 20092009-01-22
On Thu, 22 Jan 2009 10:32:38 -0600, "Hagar" <mm283729@spamcorptastic.com> wrote:>Hi all. > >I'm trying to use C++ and IAR for TMS470 uC's but I'm getting some weird >troubles with C++. > >For example: I have a simple test code to receive CAN frames using >interrupts. It compiles ok but when the frame arrives the application >blows! >If I use the same logic and configurations with C compiler everything >works perfectly. > >I did a research for C++ Projects with TMS470 but didn't find anything... >Do you have a link or a simple C++ IAR project using interrupts? > > >Any help will be appreciated! > >Thanks a lot!C and C++ aren't interchangeable. Can you post the code? George
Reply by ●January 22, 20092009-01-22
Hi George! Thanks for the fast response! I know C and C++ aren't interchangeable. Sorry for bad explanation. I was at work trying to solve this problems and didn't explained well. I have got simple code from TI website which configures CAN module (SCC) to receive any CAN message. This code works well if I use IAR C Compiler Version 5.1, but if I create another project using IAR C++ Compiler it doesn't recognizes CAN interruption. In fact, when the message is received the software stops working, like if there wasn´t an IRQ routine! In C project all the configurations and register's setups are made in only one source file (main.c). In C++ project registers setup and configurations are the same, the difference are, of course, the compiler and a "Can" class. I'm sure the logic is the same (I've compared all the registers in both projects and they are identical). After many attempts to solve this (web researches, reference guide, datasheets, help files...) I decided to test both codes in IAR Version 4, which I have installed in an old machine, and both projects (C and C++) worked well! Reading IAR documents about the two versions (IAR V4 and V5) I didn't find any huge difference that could interfere in V5 C++ Compiler. I suspect of different startup operation (cstartup.s file) between this versions but didn't find more explanations about it! Does anyone have some material about startup code? Summarizing: - IAR Embedded Workbench V4: C and C++ projects working fine! - IAR Embedded Workbench V5: Only C version works. - The source codes used to test the different versions are the same! - No errors or warnings are shown in either version. - Code optimization is turned off. - With IAR Version 5 and C++ project the Interruption Routine seems to be "ignored" by the compiler (but it don't generate warning or errors). - I'm using the same IAR Development Board to test both projects. I'm at home now and don't have the code with me, but tomorrow I'll post it. Any idea that could show a new way? Sorry for huge email and thanks a lot for your attention and time!>On Thu, 22 Jan 2009 10:32:38 -0600, "Hagar" ><mm283729@spamcorptastic.com> wrote: > >>Hi all. >> >>I'm trying to use C++ and IAR for TMS470 uC's but I'm getting someweird>>troubles with C++. >> >>For example: I have a simple test code to receive CAN frames using >>interrupts. It compiles ok but when the frame arrives the application >>blows! >>If I use the same logic and configurations with C compiler everything >>works perfectly. >> >>I did a research for C++ Projects with TMS470 but didn't findanything...>>Do you have a link or a simple C++ IAR project using interrupts? >> >> >>Any help will be appreciated! >> >>Thanks a lot! > >C and C++ aren't interchangeable. Can you post the code? > >George >
Reply by ●January 23, 20092009-01-23
Here the codes: ================== C Working Code ========================= //IDE libraries #include "QuantumCanStack.h" //################### Functions Prototypes ################## void systemInit(void); //########################################################### int main() { systemInit(); __enable_interrupt(); HETDIR = 0xFFFFFFFF; // HETx Output direction HETDOUT = 0xFFFFFFFF; HETDOUT = 0x01; while(1) { if (!(GIODINA & 0x04)) HETDOUT = 0x00; if (!(GIODINA & 0x08)) HETDOUT = 0x01; } } /** Initializes the hardware **/ void systemInit(void) { //Clock Init GCR = 0x00000008; PCR = 0x00000006|PENABLE; // Use CANTX pin for the CAN transmit functions SCC1CANTIOC = TXFUNC; // Use CANRX pin for the CAN receive functions SCC1CANRIOC = RXFUNC; // Set SCC interrupt configuration. Mailbox 0 (receive mailbox) generates // low-priority interrupts (int line 1 --> CIM_SCCB). SCC1CANMIL = MIL0; // Use int line 1 for mbox 0 SCC1CANMIM = MIM0; // Enable int for mbox 0 SCC1CANGIM = I1EN; // Enable int line 1 // Setup master control register // Enable configuration mode, activate auto bus on after bus off condition SCC1CANMC = CCR + ABO; // Wait until CPU has access to CAN configuration registers while (!(SCC1CANES & CCE)); // Setup CAN bit timing for 125kbit/s according to CiA specifications: // 8us nominal bit time w/ 16TQs/bit, sample point is located at 7us (14TQ) // BRP = 5 (Prescaler 6, w/ ICLK = 12MHz) // Sample 3x, TSEG1 = 13, TSEG2 = 2, SJW = 1 SCC1CANBTC = (5 << 16) + SAM + TSEG1_13 + TSEG2_2 + SJW_1; // Setup local acceptance mask LAM0 // Receive any incoming standard/extended ID message SCC1CANLAM0 = LAMI + 0x1fffffff; // Configure mailbox 0 for receive SCC1CANMID0 = AME; // Use acceptance mask LAM0 SCC1CANMCF0 = 0x00; SCC1CANMDL0 = 0x00; SCC1CANMDH0 = 0x00; SCC1CANMD = MD0; // Use mbox 0 for RX SCC1CANOPC = OPC0; // Protect against overwrite SCC1CANME = ME0; // Enable mailbox 0 // Start CAN module SCC1CANMC &= ~CCR; // Wait until CAN module is started while (SCC1CANES & CCE); REQMASK = (1 << CIM_SCCB); } __irq __arm void IRQ_Handler() { switch ((IRQIVEC & 0xff) - 1) // Convert IVEC index to { // CIM interrupt channel case CIM_SCCB: // SCC interrupt B HETDOUT = 0x00; SCC1CANRMP = RMP0; break; } }
Reply by ●January 23, 20092009-01-23
================ C++ =============================== //IDE libraries #include "QuantumCanStack.h" #include "Can.h" #include "Clock.h" //################### Functions Prototypes ################## void systemInit(void); //########################################################### Clock clock; Can can; int main() { systemInit(); __enable_interrupt(); HETDIR = 0xFFFFFFFF; // HETx Output direction HETDOUT = 0xFFFFFFFF; HETDOUT = 0x01; while(1) { if (!(GIODINA & 0x04)) HETDOUT = 0x00; if (!(GIODINA & 0x08)) HETDOUT = 0x01; } } /** Initializes the hardware **/ void systemInit(void) { clock.init(); can.init(); //can.enableInterrupt(true); } __irq __arm void IRQ_Handler() { switch ((IRQIVEC & 0xff) - 1) // Convert IVEC index to { // CIM interrupt channel case CIM_SCCB: // SCC interrupt B HETDOUT = 0x00; SCC1CANRMP = RMP0; break; } } ========================== CAN Class ========================= #include "Can.h" void Can::init(void) { //Function pins SCC1CANTIOC = TXFUNC; //CANTX pin for CAN transmit functions SCC1CANRIOC = RXFUNC; //CANRX pin for CAN receive functions //Interrupt Configuration SCC1CANMIL = MIL0; //Interrupt generated in Line 1 SCC1CANMIM = MIM0; //Enable interrupt for mailbox 0 SCC1CANGIM = I1EN; //Enable interrupt in Line 1 //Enable configuration mode. Activate auto bus on after bus off condition SCC1CANMC = CCR + ABO; //CCR = write access requested, set bus off state. //ABO = after bus off state automatically returns to bus on state // Wait until CPU has access to CAN configuration registers while(!SCC1CANES & CCE); // Setup CAN bit timing for 125kbit/s according to CiA specifications: // 8us nominal bit time w/ 16TQs/bit, sample point is located at 7us (14TQ) // BRP = 5 (Prescaler 6, w/ ICLK = 12MHz) // Sample 3x, TSEG1 = 13, TSEG2 = 2, SJW = 1 SCC1CANBTC = (5 << 16) + SAM + TSEG1_13 + TSEG2_2 + SJW_1; //Set local acceptance mask for mailbox 0 SCC1CANLAM0 = LAMI + 0x1FFFFFFF; //LAMI = extended and standard frames can be received //0x1FFFFFFF = receive any package //Configure mailbox 0 for receive SCC1CANMID0 = AME; //aceptance mask is used //Can data register SCC1CANMCF0 = 0x00; SCC1CANMDL0 = 0x00; SCC1CANMDH0 = 0x00; //Configure maibox 0 for receive SCC1CANMD = MD0; //receive mailbox SCC1CANOPC = OPC0; //Protect against overwrite SCC1CANME = ME0; //Enable mailbox 0 // Start CAN module SCC1CANMC &= ~CCR; while (SCC1CANES & CCE); //Wait until CAN module is started REQMASK = (1 << CIM_SCCB); } void Can::enableInterrupt(bool b) { if(b) REQMASK = (1 << CIM_SCCB); else REQMASK = (0 << CIM_SCCB); }
Reply by ●January 23, 20092009-01-23
> __irq __arm void IRQ_Handler()Check in your map file that this function is actually linked in. If not, try: extern "C" __irq __arm void IRQ_Handler() Leo Havm�ller.
Reply by ●January 23, 20092009-01-23
It worked! extern "C" __irq __arm void IRQ_Handler(); Thank you so much! It was driving me crazy since yesterday!
Reply by ●January 23, 20092009-01-23
Hagar wrote:> > It worked! > > extern "C" __irq __arm void IRQ_Handler();In future, please do not top-post, especially on technical newsgroups. Your answer belongs after (or intermixed with) the quoted material to which you reply, after snipping all irrelevant material. See the following links: <http://www.catb.org/~esr/faqs/smart-questions.html> <http://www.caliburn.nl/topposting.html> <http://www.netmeister.org/news/learn2quote.html> <http://cfaj.freeshell.org/google/> (taming google) <http://members.fortunecity.com/nnqweb/> (newusers) -- [mail]: Chuck F (cbfalconer at maineline dot net) [page]: <http://cbfalconer.home.att.net> Try the download section.
Reply by ●January 23, 20092009-01-23
On Fri, 23 Jan 2009 09:24:44 -0600, "Hagar" <mm283729@spamcorptastic.com> wrote:>It worked! > >extern "C" __irq __arm void IRQ_Handler(); > >Thank you so much! >It was driving me crazy since yesterday!I see Leo beat me to it. I'm glad the solution was simple. I was worried that the C code was doing something that breaks in C++. Most people forget (or never knew) that C++ isn't a superset of C. The functional overlap is better than 99% but not all C code is legal C++ and some which is legal doesn't work the same. George