Communication between two NUCLEO 144 using CAN bus.

Dependencies:   mbed CANMsg

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers main.cpp Source File

main.cpp

00001 /*
00002  * An example showing how to use the mbed CAN API:
00003  *
00004  * Two affordable (about $2 on ebay) STM32F103C8T6 boards (20kB SRAM, 64kB Flash),
00005  * (see [https://developer.mbed.org/users/hudakz/code/STM32F103C8T6_Hello/] for more details)
00006  * are connected to the same CAN bus via transceivers (MCP2551 or TJA1040, or etc.).
00007  * CAN transceivers are not part of NUCLEO boards, therefore must be added by you.
00008  * Remember also that CAN bus (even a short one) must be terminated with 120 Ohm resitors at both ends.
00009  *
00010  *
00011  * The same code is used for both mbed boards, but:
00012  *      For board #1 compile the example without any change.
00013  *      For board #2 comment out line 21 before compiling
00014  *
00015  * Once the binaries have been downloaded to the boards reset both boards at the same time.
00016  *
00017  */
00018 
00019 #define TARGET_NUCLEOF767ZI   1       // uncomment this line to use STM32F103C8T6 boards
00020 
00021 #define BOARD1                  1       // comment out this line when compiling for board #2
00022 
00023 #if defined(TARGET_NUCLEOF767ZI)
00024     #define LED_PIN     PB_7
00025     const int           OFF = 1;
00026     const int           ON = 0;
00027 #else
00028     #define LED_PIN     PB_7
00029     const int           OFF = 0;
00030     const int           ON = 1;
00031 #endif
00032 
00033 #if defined(BOARD1)
00034     const unsigned int  RX_ID = 0x100;
00035     const unsigned int  TX_ID = 0x101;
00036 #else
00037     const unsigned int  RX_ID = 0x101;
00038     const unsigned int  TX_ID = 0x100;
00039 #endif
00040 
00041 #include "mbed.h"
00042 #include "CANMsg.h"
00043 #include "mbed_error.h"
00044 CircularBuffer<char, 1024> rxbuf;    // PC receiving Buffer
00045 Serial              pc(USBTX, USBRX);
00046 CAN                 can(PD_0, PD_1);  // CAN Rx pin name, CAN Tx pin name
00047 //CAN                 can(p30, p29);  // CAN Rx pin name, CAN Tx pin name
00048 CANMsg              rxMsg;
00049 CANMsg              txMsg;
00050 DigitalOut          led(LED_PIN);
00051 Timer               timer;
00052 uint8_t             counter = 0;
00053 AnalogIn            analogIn(A0);
00054 float               voltage;
00055 
00056 /**
00057  * @brief   Prints CAN message to PC's serial terminal
00058  * @note
00059  * @param   CANMessage to print
00060  * @retval
00061  */
00062 void printMsg(CANMessage& msg)
00063 {
00064     pc.printf("  ID      = 0x%.3x\r\n", msg.id);
00065     pc.printf("  Type    = %d\r\n", msg.type);
00066     pc.printf("  Format  = %d\r\n", msg.format);
00067     pc.printf("  Length  = %d\r\n", msg.len);
00068     pc.printf("  Data    =");
00069     for(int i = 0; i < msg.len; i++)
00070         pc.printf(" 0x%.2X", msg.data[i]);
00071     pc.printf("\r\n");
00072 }
00073 
00074 /**
00075  * @brief   Handles received CAN messages
00076  * @note    Called on 'CAN message received' interrupt.
00077  * @param
00078  * @retval
00079  */
00080  
00081  
00082  
00083  
00084  
00085 void onCanReceived(void)
00086 {
00087     can.read(rxMsg);
00088     pc.printf("-------------------------------------\r\n");
00089     pc.printf("CAN message received\r\n");
00090     printMsg(rxMsg);
00091  
00092     rxbuf.reset();
00093 
00094     if (rxMsg.id == RX_ID) {
00095         // extract data from the received CAN message 
00096         // in the same order as it was added on the transmitter side
00097         rxMsg >> counter;
00098         rxMsg >> voltage;   
00099         pc.printf("  counter = %d\r\n", counter);
00100         pc.printf("  voltage = %e V\r\n", voltage);
00101     }
00102     
00103     timer.start(); // to transmit next message in main
00104 }
00105 
00106 
00107 /**
00108  * @brief   Main
00109  * @note
00110  * @param
00111  * @retval
00112  */
00113 
00114 
00115 
00116 int main(void)
00117 {
00118     pc.baud(9600);          // set serial speed
00119     can.frequency(1000000); // set CAN bit rate to 1Mbps
00120     can.filter(RX_ID, 0xFFF, CANStandard, 0); // set filter #0 to accept only standard messages with ID == RX_ID
00121     can.attach(onCanReceived);                // attach ISR to handle received messages
00122 
00123     
00124 #if defined(BOARD1)
00125     led = ON;               // turn the LED on
00126     timer.start();          // start timer
00127     pc.printf("reset pressed from board #1\r\n");
00128 #else
00129     led = OFF;      // turn LED off
00130     pc.printf("reset pressed from board #2\r\n");
00131 #endif
00132     while(1) {
00133         if(timer.read_ms() >= 3000) {    // check for timeout
00134             timer.stop();                // stop timer
00135             timer.reset();               // reset timer
00136             counter++;                   // increment counter
00137             voltage = analogIn * 3.3f;   // read the small drift voltage from analog input
00138             txMsg.clear();               // clear Tx message storage
00139             txMsg.id = TX_ID;            // set ID
00140             // append data (total data length must not exceed 8 bytes!)
00141             txMsg << counter;   // one byte
00142             txMsg << voltage;   // four bytes
00143              if (counter==10){
00144                  break;
00145                  }
00146             if(can.write(txMsg)) {       // transmit message
00147                 led = OFF;               // turn the LED off
00148                 pc.printf("-------------------------------------\r\n");
00149                 pc.printf("-------------------------------------\r\n");
00150                 pc.printf("CAN message sent\r\n");
00151                 printMsg(txMsg);
00152                 pc.printf("  counter = %d\r\n", counter);
00153                 pc.printf("  voltage = %e V\r\n", voltage);
00154             }
00155             else
00156                 pc.printf("Transmission error\r\n");
00157                 
00158                 
00159         }
00160     }
00161 }