I have a st32f205 and set up both Can 1&2.
Can 1, will send and receive. Can 2, will send, not receive.
I can see the data with a tool, so I know the data is on the wire but the ARM_CAN_EVENT_RECEIVE will not pick it up. The ARM_CAN_EVENT_SEND_COMPLETE is working fine.
Here is my can2 had to remove all comments to fit in post. What could I have done wrong?
#define CAN_CONTROLLER 2 #define _CA_Driver_(n) Driver_CAN##n #define CAN_Driver_(n) _CAN_Driver_(n) extern ARM_DRIVER_CAN CAN_Driver_(CAN_CONTROLLER); #define ptrCAN (&CAN_Driver_(CAN_CONTROLLER)) uint32_t rx1_obj_idx; uint8_t rx1_data[8]; ARM_CAN_MSG_INFO rx1_msg_info; uint32_t tx1_obj_idx; uint8_t tx1_data[8]; ARM_CAN_MSG_INFO tx1_msg_info; static bool sendCompleted = false; static int ID_Read; static int _TIMEOUT = 100; void CAN1_SignalUnitEvent (uint32_t event) { switch (event) { case ARM_CAN_EVENT_UNIT_ACTIVE: break; case ARM_CAN_EVENT_UNIT_WARNING: break; case ARM_CAN_EVENT_UNIT_PASSIVE: break; case ARM_CAN_EVENT_UNIT_BUS_OFF: break; } } void CAN1_SignalObjectEvent (uint32_t obj_idx, uint32_t event) { if (event == ARM_CAN_EVENT_RECEIVE) { if (obj_idx == rx1_obj_idx) { ptrCAN->MessageRead(rx1_obj_idx, &rx1_msg_info, rx1_data, 8U); ID_Read = rx1_msg_info.id; } } if (event == ARM_CAN_EVENT_SEND_COMPLETE) { if (obj_idx == tx1_obj_idx) { sendCompleted=true; } } } bool CAN1_Initialize (int CAN_BITRATE_NOMINAL) { ARM_CAN_CAPABILITIES can_cap; ARM_CAN_OBJ_CAPABILITIES can_obj_cap; int32_t status; uint32_t i, num_objects, clock; can_cap = ptrCAN->GetCapabilities (); num_objects = can_cap.num_objects; status = ptrCAN->Initialize (CAN1_SignalUnitEvent, CAN1_SignalObjectEvent); if (status != ARM_DRIVER_OK) { return false; } status = ptrCAN->PowerControl (ARM_POWER_FULL); if (status != ARM_DRIVER_OK) { return false; } status = ptrCAN->SetMode (ARM_CAN_MODE_INITIALIZATION); if (status != ARM_DRIVER_OK) { return false; } clock = ptrCAN->GetClock(); if ((clock % (8U*CAN_BITRATE_NOMINAL)) == 0U) { status = ptrCAN->SetBitrate (ARM_CAN_BITRATE_NOMINAL, CAN_BITRATE_NOMINAL, ARM_CAN_BIT_PROP_SEG (5U) | ARM_CAN_BIT_PHASE_SEG1(1U) | ARM_CAN_BIT_PHASE_SEG2(1U) | ARM_CAN_BIT_SJW (1U)); } else if ((clock % (10U*CAN_BITRATE_NOMINAL)) == 0U) { status = ptrCAN->SetBitrate (ARM_CAN_BITRATE_NOMINAL, CAN_BITRATE_NOMINAL, ARM_CAN_BIT_PROP_SEG (7U) | ARM_CAN_BIT_PHASE_SEG1(1U) | ARM_CAN_BIT_PHASE_SEG2(1U) | ARM_CAN_BIT_SJW (1U)); } else if ((clock % (12U*CAN_BITRATE_NOMINAL)) == 0U) { status = ptrCAN->SetBitrate (ARM_CAN_BITRATE_NOMINAL, CAN_BITRATE_NOMINAL, ARM_CAN_BIT_PROP_SEG (7U) | ARM_CAN_BIT_PHASE_SEG1(2U) | ARM_CAN_BIT_PHASE_SEG2(2U) | ARM_CAN_BIT_SJW (2U)); } else { return false; } if (status != ARM_DRIVER_OK) { return false; } rx1_obj_idx = 0xFFFFFFFFU; tx1_obj_idx = 0xFFFFFFFFU; for (i = 0U; i < num_objects; i++) { can_obj_cap = ptrCAN->ObjectGetCapabilities (i); if ((rx1_obj_idx == 0xFFFFFFFFU) && (can_obj_cap.rx == 1U)) { rx1_obj_idx = i; } else if ((tx1_obj_idx == 0xFFFFFFFFU) && (can_obj_cap.tx == 1U)) { tx1_obj_idx = i; break; } } if ((rx1_obj_idx == 0xFFFFFFFFU) || (tx1_obj_idx == 0xFFFFFFFFU)) { return false; } status = ptrCAN->ObjectSetFilter(rx1_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, 0xfff, 0U); if (status != ARM_DRIVER_OK) { return false; } status = ptrCAN->ObjectConfigure(tx1_obj_idx, ARM_CAN_OBJ_TX); if (status != ARM_DRIVER_OK) { return false; } status = ptrCAN->ObjectConfigure(rx1_obj_idx, ARM_CAN_OBJ_RX); if (status != ARM_DRIVER_OK) { return false; } status = ptrCAN->SetMode (ARM_CAN_MODE_NORMAL); if (status != ARM_DRIVER_OK) { return false; } return true; } void setFilters_HS(long ID1, long ID2, long ID3, long ID4, long ID5) { ptrCAN->SetMode (ARM_CAN_MODE_INITIALIZATION); ptrCAN->ObjectSetFilter(rx1_obj_idx, ARM_CAN_FILTER_ID_RANGE_REMOVE , 0x100, 0xfff); if (ID1 > 0) ptrCAN->ObjectSetFilter(rx1_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID1, 0U); if (ID2 > 0) ptrCAN->ObjectSetFilter(rx1_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID2, 0U); if (ID3 > 0) ptrCAN->ObjectSetFilter(rx1_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID3, 0U); if (ID4 > 0) ptrCAN->ObjectSetFilter(rx1_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID4, 0U); if (ID5 > 0) ptrCAN->ObjectSetFilter(rx1_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID5, 0U); ptrCAN->SetMode (ARM_CAN_MODE_NORMAL); } void CANWrite_HS (int ECU, unsigned char data[]) { sendCompleted=false; ID_Read=0; memset(&rx1_data, 0U, 8); memset(&tx1_msg_info, 0U, sizeof(ARM_CAN_MSG_INFO)); tx1_msg_info.id = ECU; ptrCAN->MessageSend(tx1_obj_idx, &tx1_msg_info, data, 8U); } int CANRead_HS (int ECU, unsigned char data, char position) { memset(&command_Data, 0U, 8); for (int t=0;t <_TIMEOUT;t++) { osDelay(10); if (ID_Read > 0) { if (ECU == 0 ) { memcpy(&command_Data, &rx1_data,8); if (data != 0) { if (command_Data[position] == data) return 1; } else return 1; } if (ECU == ID_Read) { memcpy(&command_Data, &rx1_data,8); if (data != 0) { if (command_Data[position] == data) return 1; } else return 1; } } } return 0; }
So removing must be done one by one? That may be my issue. I will also try changing channels.
Problem was right there this entire time. Just didnt see it.
if (ID1 > 0) ptrCAN->ObjectSetFilter(tx2_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID1, 0U); if (ID2 > 0) ptrCAN->ObjectSetFilter(tx2_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID2, 0U); if (ID3 > 0) ptrCAN->ObjectSetFilter(tx2_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID3, 0U); if (ID4 > 0) ptrCAN->ObjectSetFilter(tx2_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID4, 0U); if (ID5 > 0) ptrCAN->ObjectSetFilter(tx2_obj_idx, ARM_CAN_FILTER_ID_EXACT_ADD, ID5, 0U);
tx2_obj_idx is not going to work for a filter... Somehow I had tx instead of rx.
I thought you were trying to see if anyone read your posts. That line stood out like a sore thumb.