/** * @file test_can_communication.c * @brief Integration tests for CAN communication */ #include "unity.h" #include "kernel.h" #include "can_driver.h" #include "can_tp.h" #include "can_nm.h" #include /* CAN test variables */ static CanMessage_t test_message; static volatile bool message_received = false; static volatile bool message_sent = false; static volatile uint32_t rx_count = 0; /* Callback functions */ static void test_rx_callback(const CanMessage_t* message) { message_received = true; rx_count++; memcpy(&test_message, message, sizeof(CanMessage_t)); } static void test_tx_callback(uint32_t mailbox, bool success) { message_sent = success; } /* Setup */ void setUp(void) { kernel_init(); message_received = false; message_sent = false; rx_count = 0; /* Initialize CAN */ CanConfig_t config = { .nominal_baudrate = CAN_BAUD_500K, .data_baudrate = CAN_BAUD_500K, .frame_type = CAN_FRAME_CLASSIC, .enable_fd = false, .enable_automatic_retransmission = true, .rx_callback = test_rx_callback, .tx_callback = test_tx_callback, .filter_count = 0 }; can_init(&config); } /* Teardown */ void tearDown(void) { can_deinit(); kernel_stop(); } /* ============================================================================ * Test Cases * ============================================================================ */ /** * @brief Test CAN initialization */ void test_can_init(void) { CanStatistics_t stats; TEST_ASSERT_EQUAL(KERNEL_OK, can_get_statistics(&stats)); TEST_ASSERT_EQUAL(0, stats.tx_messages); TEST_ASSERT_EQUAL(0, stats.rx_messages); } /** * @brief Test CAN message send */ void test_can_send(void) { CanMessage_t msg = { .id = {.id = 0x100, .is_extended = false}, .length = 8, .data = {1, 2, 3, 4, 5, 6, 7, 8} }; TEST_ASSERT_EQUAL(KERNEL_OK, can_send_message(&msg, 1000)); /* Wait for transmission */ kernel_delay(10); TEST_ASSERT_TRUE(message_sent); } /** * @brief Test CAN message receive */ void test_can_receive(void) { CanMessage_t msg = { .id = {.id = 0x200, .is_extended = false}, .length = 4, .data = {0xAA, 0xBB, 0xCC, 0xDD} }; /* Simulate received message */ can_process_interrupt(); TEST_ASSERT_TRUE(message_received); TEST_ASSERT_EQUAL(0x200, test_message.id.id); TEST_ASSERT_EQUAL(4, test_message.length); } /** * @brief Test CAN TP multi-frame message */ void test_can_tp_multiframe(void) { CanTpConfig_t tp_config = { .addressing_format = CAN_TP_ADDRESSING_NORMAL, .source_address = 0x100, .target_address = 0x200, .timeout_ms = 1000, .stmin = 10, .block_size = 8, .padding_enabled = true, .padding_byte = 0xAA }; can_tp_init(&tp_config); /* Create test message */ uint8_t data[100]; for (int i = 0; i < 100; i++) { data[i] = i; } CanTpMessage_t tp_msg = { .message_id = 0x300, .data = data, .length = 100, .addressing_format = CAN_TP_ADDRESSING_NORMAL }; TEST_ASSERT_EQUAL(KERNEL_OK, can_tp_send_message(&tp_msg, 5000)); } /** * @brief Test CAN network management */ void test_can_nm(void) { CanNmConfig_t nm_config = { .node_id = 1, .network_id = 0, .message_id = 0x400, .timeout_ms = 2000, .repeat_message_time_ms = 500, .is_coordinator = false, .sleep_ack_timeout_ms = 100 }; TEST_ASSERT_EQUAL(KERNEL_OK, can_nm_init(&nm_config)); TEST_ASSERT_EQUAL(KERNEL_OK, can_nm_start()); kernel_delay(100); TEST_ASSERT_EQUAL(CAN_NM_NORMAL_OPERATION, can_nm_get_state()); } /* ============================================================================ * Test Runner * ============================================================================ */ int main(void) { UNITY_BEGIN(); RUN_TEST(test_can_init); RUN_TEST(test_can_send); RUN_TEST(test_can_receive); RUN_TEST(test_can_tp_multiframe); RUN_TEST(test_can_nm); return UNITY_END(); }