This 'Hello World' program uses many of the SEEED_CAN library functions to display the VIN number stored in a GMLAN ECU then display all CAN messages on the CAN-BUS.
Fork of Seeed_CAN_Hello_World by
main.cpp
00001 #include "mbed.h" 00002 #include "seeed_can.h" 00003 00004 SEEED_CAN can; // No parameters needed when Seeed Studios' CAN-BUS Shield is plugged into a FRDM-KL25Z mbed 00005 // or an LPC1768b and using pins p9, p10, p11, p12 and p13. 00006 Serial pc(USBTX, USBRX); // USB serial port TTYACM0 (or COMn in a Windows environment - use device manager to find 'n') 00007 00008 Ticker minute; 00009 Timer timestamp; 00010 00011 bool msgRxFlag = 0; 00012 00013 void canInterrupt() 00014 { 00015 can.attach(NULL); // Disable the interrupt - the application must re-anable the interrupt after it has acted upon it 00016 msgRxFlag = 1; // Set a 'Flag' to say that there is an interrupt that needs to be processed 00017 } 00018 00019 void resetTimestamp() // Resets the 'timestamp' Timer (attached to the 'minute' Ticker) 00020 { 00021 timestamp.reset(); 00022 } 00023 00024 void displayMessage() // Display a CAN message if there is one in a receive buffer 00025 { 00026 SEEED_CANMessage canMsg; 00027 00028 if (can.read(canMsg)) { 00029 printf("*** T%05dI%03xL%dD", timestamp.read_ms(), canMsg.id, canMsg.len); // Show a Timestamp in ms, message Id and message Length 00030 for (uint32_t i = 0; i < canMsg.len; i++) 00031 printf("%02x", canMsg.data[i]); // Show the message's data bytes in Hex representation 00032 printf(" ***\r"); 00033 } 00034 } 00035 00036 int main() 00037 { 00038 SEEED_CANMessage canMsg; 00039 char VIN[18] = {NULL}; // VIN code is 17 characters long + 1 for string terminator character (NULL or \0) 00040 char reqvin[] = {0x02,0x1A,0x90,0x00,0x00,0x00,0x00,0x00}; // CAN message to request VIN code 00041 char floctl[] = {0x30,0x00,0x00,0x00,0x00,0x00,0x00,0x00}; // CAN message to request all remaining frames in a multi-frame message 00042 00043 printf("Seeed Studios CAN-BUS Shield 'Hello World' program :-)\r\n"); 00044 timestamp.start(); 00045 minute.attach(&resetTimestamp, 60.0); // Reset the 'Timestamp' timer every minute 00046 can.open(500000, SEEED_CAN::Config); // Initialise Seeed Studios' CAN-BUS shield with a baudrate of 500 kbps (P-bus) 00047 can.mask(0, 0x7FF); // Configure Mask 0 to check all bits of a Standard CAN message Id 00048 can.mask(1, 0x7FF, CANStandard); // Configure Mask 1 to check all bits of a Standard CAN message Id 00049 can.filter(0, 0x7E8); // Configure Filter 0 - 0x7E8 is the id used by ECUs on GMLAN 00050 // Read and Display the VIN code stored in a GMLAN ECU 00051 // 00052 // ***!!! NOTE: Using while(...) as I am here is not a good idea because !!!*** 00053 // ***!!! this 'Hello World' will get stuck if the message never arrives !!!*** 00054 // ***!!! I should really perform checking and include a timeout. !!!*** 00055 // ***!!! It's sort of OK for a quick demo (Just don't show Nigel Jones) !!!*** 00056 // 00057 can.write(SEEED_CANMessage(0x7E0, reqvin)); // Request VIN using ReadDataByIdentifier method (GMLAN_DID) 00058 while (!(can.read(canMsg) && (canMsg.id == 0x7E8))); // Wait for the response 00059 memcpy(VIN+0, canMsg.data+4, 4); // 1st 4 Bytes are part of message protocol, last 4 bytes are 1st 4 characters of VIN 00060 can.write(SEEED_CANMessage(0x7E0, floctl)); // Send Trionic8 a "Flow Control Message to get the rest of the VIN 00061 while (!(can.read(canMsg) && (canMsg.id == 0x7E8))); // Wait for the 1st continuation message 00062 memcpy(VIN+4, canMsg.data+1, 7); // 1st Byte is message continuation sequence number, last 7 bytes are next 7 characters of VIN 00063 while (!(can.read(canMsg) && (canMsg.id == 0x7E8))); // Wait for the last message 00064 memcpy(VIN+11, canMsg.data+1, 6); // 1st Byte is message continuation sequence number, last 6 bytes are remaining characters of VIN 00065 printf("VIN code: %s\r\n",VIN); 00066 // Display all messages on the CAN-BUS 00067 can.monitor(1); // Select Moniter mode to listen only (do not ack messages on the CAN bus) 00068 can.mask(0, NULL); // Clear acceptance mask 0 (i.e. accept all meassages) 00069 can.attach(&canInterrupt, SEEED_CAN::RxAny); 00070 while (1) { 00071 if (msgRxFlag) { 00072 displayMessage(); 00073 if (can.interrupts(SEEED_CAN::RxAny)) { 00074 msgRxFlag = 0; 00075 can.attach(&canInterrupt, SEEED_CAN::RxAny); 00076 } 00077 } 00078 } 00079 }
Generated on Fri Jul 15 2022 00:44:18 by 1.7.2