Hi Yago,
my tdx-info output is:
Software summary
Bootloader: U-Boot
Kernel version: 5.15.148-6.7.0+git.bfdbfb2c85fb #1-TorizonCore SMP PREEMPT Thu Jun 20 15:59:41 UTC 2024
Kernel command line: root=LABEL=otaroot rootfstype=ext4 quiet logo.nologo vt.global_cursor_default=0 plymouth.ignore-serial-consoles splash fbcon=map:3 ostree=/ostree/boot.1/torizon/bc8150e4d70ac4642d17b5145c80286f23ef76241d52ed3655a9e2fd6054f963/0
Distro name: NAME=“TorizonCore”
Distro version: VERSION_ID=6.7.0-build.18
Distro variant: VARIANT=“Docker”
Hostname: verdin-imx8mm-06944461
Hardware info
HW model: Toradex Verdin iMX8M Mini WB on Verdin Development Board
Toradex version: 0060 V1.1B
Serial number: 06944461
Processor arch: aarch64
Hi Yago, as I wrote, it seems that everything is fine on the A53 side. As soon as it boots, I see the message ‘Hello World!’ on the M4 console. If I send data from A53, I can see it on the M4 console. The problem is when I write from M4 to A53.
My task running on M4 is.
static struct rpmsg_lite_instance *volatile rpmsghndRpmsg;
static struct rpmsg_lite_endpoint *volatile rpmsghndEpt = NULL;
static volatile rpmsg_queue_handle rpmsghndQueue = NULL;
static char buf[512];
static uint32_t len;
void saldatrice_task(void *param)
{
volatile uint32_t rpmsghndRemoteAddr;
int32_t result;
void *rx_buf;
void *tx_buf;
uint32_t size = RL_BUFFER_PAYLOAD_SIZE;
PRINTF("Saldatrice Task started ...\n");
// Init RPMSG
PRINTF("\r\nRpmsgHnd init ...\r\n");
rpmsghndRpmsg = rpmsg_lite_remote_init((void *)RPMSG_LITE_SHMEM_BASE, RPMSG_LITE_LINK_ID, RL_NO_FLAGS);
// Attesa link
rpmsg_lite_wait_for_link_up(rpmsghndRpmsg, RL_BLOCK);
PRINTF("\r\nLink up...\r\n");
// Creazione coda e endpoint
rpmsghndQueue = rpmsg_queue_create(rpmsghndRpmsg);
rpmsghndEpt = rpmsg_lite_create_ept(rpmsghndRpmsg, LOCAL_EPT_ADDR, rpmsg_queue_rx_cb, rpmsghndQueue);
// Announcement
SDK_DelayAtLeastUs(2000000U,SDK_DEVICE_MAXIMUM_CPU_CLOCK_FREQUENCY);
(void)rpmsg_ns_announce(rpmsghndRpmsg, rpmsghndEpt, RPMSG_LITE_NS_ANNOUNCE_STRING, RL_NS_CREATE);
PRINTF("\r\nRpmsgHnd nameservice sent, ready for incoming messages...\r\n");
#ifdef RPMSG_LITE_MASTER_IS_LINUX
(void)rpmsg_queue_recv(rpmsghndRpmsg, rpmsghndQueue, (uint32_t *)&rpmsghndRemoteAddr, buf, sizeof(buf), &len, RL_BLOCK);
buf[len] = 0;
PRINTF(“\r\n%s…%ld\r\n”, buf, len);
#endif
while(1)
{
/* Get RPMsg rx buffer with message */
result = rpmsg_queue_recv(rpmsghndRpmsg, rpmsghndQueue, (uint32_t *)&rpmsghndRemoteAddr, buf, sizeof(buf), &len, RL_BLOCK);
if (result != 0)
break;
PRINTF("\r\n\r\nRpmsgHnd Get Message From Master Side:\r\n");
for (size_t i = 0; i < len; i++) {
PRINTF("%02X,", buf[i]);
}
buf[len] = 0;
result = rpmsg_lite_send(rpmsghndRpmsg, rpmsghndEpt, rpmsghndRemoteAddr, buf, len, RL_BLOCK);
if (result != 0)
break;
PRINTF("Saldatrice Task running ...\n");
// rpmsghndReceiveNoCopy((char *)buf, &buflen);
// vTaskDelay(10);
// rpmsghndTransmitNoCopy((char *)buf, buflen);
}
vTaskDelay(100);
}
I tried both using the functions rpmsg_queue_recv_nocopy
and rpmsg_lite_send_nocopy
, as well as rpmsg_queue_recv
and rpmsg_lite_send
, copying exactly the example provided in the NXP SDK. The problem always lies with the send operations. Sometimes, some sends go through, but then it goes into a hard fault. Other times, if it doesn’t crash, the following condition is triggered:
int32_t virtqueue_add_consumed_buffer(struct virtqueue *vq, uint16_t head_idx, uint32_t len)
{
if (head_idx > vq->vq_nentries)
{
return (ERROR_VRING_NO_BUFF);
}
}
Rightly so, because head_idx
has absurd values beyond the number of entries in the queue.
I’m debugging on the M4 core on a Linux machine using VSCode and CMake.
My config.cmake is:
set(CONFIG_COMPILER gcc)
set(CONFIG_TOOLCHAIN armgcc)
set(CONFIG_USE_COMPONENT_CONFIGURATION false)
set(CONFIG_USE_middleware_multicore_rpmsg_lite_imx8mm_m4_freertos true)
set(CONFIG_USE_middleware_multicore_rpmsg_lite_freertos true)
set(CONFIG_USE_middleware_multicore_rpmsg_lite true)
set(CONFIG_USE_middleware_freertos-kernel_heap_4 true)
set(CONFIG_USE_driver_clock true)
set(CONFIG_USE_driver_mu true)
set(CONFIG_USE_middleware_freertos-kernel true)
set(CONFIG_USE_driver_common true)
set(CONFIG_USE_driver_rdc true)
set(CONFIG_USE_driver_igpio true)
set(CONFIG_USE_driver_ii2c true)
set(CONFIG_USE_driver_ipwm true)
set(CONFIG_USE_driver_gpt true)
set(CONFIG_USE_device_MIMX8MM6_CMSIS true)
set(CONFIG_USE_utility_debug_console true)
set(CONFIG_USE_component_iuart_adapter true)
set(CONFIG_USE_component_serial_manager_uart true)
set(CONFIG_USE_component_serial_manager true)
set(CONFIG_USE_driver_iuart true)
set(CONFIG_USE_component_lists true)
set(CONFIG_USE_device_MIMX8MM6_startup true)
set(CONFIG_USE_utility_assert true)
set(CONFIG_USE_utilities_misc_utilities true)
set(CONFIG_USE_middleware_freertos-kernel_template true)
set(CONFIG_USE_middleware_freertos-kernel_extension true)
set(CONFIG_USE_CMSIS_Include_core_cm true)
set(CONFIG_USE_device_MIMX8MM6_system true)
set(CONFIG_CORE cm4f)
set(CONFIG_DEVICE MIMX8MM6)
set(CONFIG_BOARD evkmimx8mm)
set(CONFIG_KIT evkmimx8mm)
set(CONFIG_DEVICE_ID MIMX8MM6xxxLZ)
set(CONFIG_FPU SP_FPU)
set(CONFIG_DSP NO_DSP)
Memory sections in my .ld file are:
/* Entry Point */
ENTRY(Reset_Handler)
HEAP_SIZE = DEFINED(heap_size) ? heap_size : 0x400;
STACK_SIZE = DEFINED(stack_size) ? stack_size : 0x400;
/* Specify the memory areas */
MEMORY
{
m_interrupts (RX) : ORIGIN = 0x1FFE0000, LENGTH = 0x00000240
m_text (RX) : ORIGIN = 0x1FFE0240, LENGTH = 0x0001FDC0
m_data (RW) : ORIGIN = 0x20000000, LENGTH = 0x00020000
m_data2 (RW) : ORIGIN = 0x80000000, LENGTH = 0x01000000
}
I really don’t know how to solve this. I tried running the M4 application both through the debugger and by loading it following your guide. In both cases, as soon as it tries to send, it crashes.
But the receive works perfectly.
If I remove the send from my M4 application, everything works.
Thanks