Skip to content

Instantly share code, notes, and snippets.

@srics
Forked from kauailabs/VMX-pi-HAL-CANBusMonitor
Created December 22, 2022 07:32
Show Gist options
  • Save srics/4dcacc430c8d97ac7ae499f9313d0519 to your computer and use it in GitHub Desktop.
Save srics/4dcacc430c8d97ac7ae499f9313d0519 to your computer and use it in GitHub Desktop.
VMX-pi-HAL-CANBusMonitor
#include <stdio.h> /* printf() */
#include "VMXPi.h"
int main(int argc, char *argv[])
{
bool realtime = false;
uint8_t update_rate_hz = 50;
VMXPi vmx(realtime, update_rate_hz);
if(vmx.IsOpen()) {
/** CONFIGURE CAN; receive and display data; open 3 streams w/different address range /
VMXErrorCode vmxerr;
VMXCANReceiveStreamHandle canrxhandles[1];
if (vmx.can.OpenReceiveStream(canrxhandles[0], 0x0, 0x0, 100, &vmxerr)) {
printf("Opened CAN Receive Stream 1, handle: %d\n", canrxhandles[0]);
}
/* Flush Rx/Tx fifo not necessary if invoking reset above. */
if (vmx.can.FlushRxFIFO(&vmxerr)) {
printf("Flushed CAN RX FIFO\n");
}
if (vmx.can.FlushTxFIFO(&vmxerr)) {
printf("Flushed CAN TX FIFO\n");
}
if (vmx.can.SetMode(VMXCAN::VMXCAN_NORMAL)) {
printf("Set CAN Mode to Normal.\n");
}
/* It's recommended to delay 20 Milliseconds after transitioning modes -
* to allow the CAN circuitry to stabilize; otherwise, sometimes
* there will be errors transmitting data during this period.
*/
vmx.time.DelayMilliseconds(20);
VMXCAN::VMXCANMode can_mode;
if(vmx.can.GetMode(can_mode)) {
printf("Current CAN Mode: ");
switch(can_mode) {
case VMXCAN::VMXCAN_LISTEN:
printf("LISTEN");
break;
case VMXCAN::VMXCAN_LOOPBACK:
printf("LOOPBACK");
break;
case VMXCAN::VMXCAN_NORMAL:
printf("NORMAL");
break;
case VMXCAN::VMXCAN_CONFIG:
printf("CONFIG");
break;
case VMXCAN::VMXCAN_OFF:
printf("OFF (SLEEP)");
break;
}
printf("\n");
}
/* Allow time for some CAN messages to be received. */
for (int i = 0; i < 200; i++) {
vmx.time.DelayMilliseconds(50);
VMXCANBusStatus can_bus_status;
if (vmx.can.GetCANBUSStatus(can_bus_status, &vmxerr)) {
if(can_bus_status.busWarning) {
printf("CAN Bus Warning.\n");
}
if(can_bus_status.busPassiveError) {
printf("CAN Bus in Passive mode due to errors.\n");
}
if(can_bus_status.busOffError) {
printf("CAN Bus Transmitter Off due to errors.\n");
}
if(can_bus_status.transmitErrorCount > 0) {
printf("CAN Bus Tx Error Count: %d\n", can_bus_status.transmitErrorCount);
}
if(can_bus_status.receiveErrorCount > 0) {
printf("CAN Bus Rx Error Count: %d\n", can_bus_status.receiveErrorCount);
}
if(can_bus_status.busOffCount > 0) {
printf("CAN Bus Tx Off Count: %d\n", can_bus_status.busOffCount);
}
if(can_bus_status.txFullCount > 0) {
printf("CAN Bus Tx Full Count: %d\n", can_bus_status.txFullCount);
}
if(can_bus_status.hwRxOverflow) {
printf("CAN HW Receive Overflow detected.\n");
}
if(can_bus_status.swRxOverflow) {
printf("CAN SW Receive Overflow detected.\n");
}
if(can_bus_status.busError) {
printf("CAN Bus Error detected.\n");
}
if(can_bus_status.wake) {
printf("CAN Bus Wake occured.\n");
}
if(can_bus_status.messageError) {
printf("CAN Message Error detected.\n");
}
}
for (int i = 0; i < 1; i++) {
bool done = false;
while (!done) {
VMXCANTimestampedMessage stream_msg;
uint32_t num_msgs_read;
if (vmx.can.ReadReceiveStream(canrxhandles[i], &stream_msg, 1, num_msgs_read, &vmxerr)) {
if (num_msgs_read == 0) {
done = true;
} else {
bool is_eid = true;
if (stream_msg.messageID & VMXCAN_IS_FRAME_11BIT) {
is_eid = false;
stream_msg.messageID &= ~VMXCAN_IS_FRAME_11BIT;
}
stream_msg.messageID &= ~VMXCAN_IS_FRAME_REMOTE;
printf("[%10d] CAN Stream %d: %d bytes from %s 0x%x: ",
stream_msg.timeStampMS,
canrxhandles[i],
stream_msg.dataSize,
(is_eid ? "EID" : "ID "),
stream_msg.messageID);
for ( int j = 0; j < stream_msg.dataSize; j++) {
printf("%02X ", stream_msg.data[j]);
}
printf("\n");
}
}
}
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment