Tip / Sign in to post questions, reply, level up, and achieve exciting badges. Know more

DAVE™ Forum Discussions

Not applicable

Could anyone enlighten me on how best to configure a CAN tx FIFO ?

From what I can see, an instance of MULTICAN_CONFIG APP, is just the ticket for FIFO configure.
But that APP lacks CAN tx/rx pin configure, so I presume you still need a CAN_NODE APP instance, for that.
Except for the pin configure, I can see that MULTICAN_CONFIG looks to be a superset of CAN_NODE.
And I suspect that overlap, is what causes DAVE to error with 'unable to grant' resources, when I try ticking
'Enable node', in MULTICAN_CONFIG.

How should I best configure a CAN tx FIFO ?

Best regards,

12 Replies
Not applicable
SOLVED: I chanced on the following thread, first part of which answered my question:
So I've configured up as described. For receive pin, you use HW Signal Connections, to link DIGITAL_IO pin to MULTICAN_CONFIG.
Whereas for transmit pin, you use HW Signal Connections, to link MULTICAN_CONFIG tx_pin_node0 to DIGITAL_IO pin.
DAVE seems like a puzzle guessing game sometimes..
For tx FIFO, I've configured up per MO1+2 in the Infineon MULTICAN example project.
Just waiting on our USB-to-CAN adaptor, to be able to check if works..
Not applicable
And unfortunately it doesn't

I am seeing activity on the CAN receive pin, P14.3.
I know that because I have added some temporary code to our main.c loop, to copy state of P14.3, to an LED.
Loop duration, as measured with existing metrics code, is 6 to 72 us.
And when I use our USB-to-CAN adapter and corresponding PC util, to scan for CAN devices, I see blipping activity on the LED.
The activity is visibly synchronised, to the stepping of the % search bar in the util.
We're using emtas CANopen Device Explorer 2.6.2, with the emtas-supplied USB-CANmodul (SYS TEC electronic), with latest firmware.
The adaptor itself reports no errors.

But if I breakpoint the CAN receive interrupt handler in our code, nothing.

We know the CAN transceiver on our board is working fine, as we've checked using the basic CAN_NODE app,
rather than the MULTICAN_CONFIG app.

So it's likely a matter of something I've guessed wrong, in configuring MULTICAN_CONFIG.

Any ideas, Infineon, or forum members ?

A couple of screengrabs attached, showing how all setup
LMO_2 through LMO_15 identical
For LMO_0, I've tried LIST set instead to 'List 1(Node 0)'. And MMC Selection set instead to 'Receive FIFO base object'. And both.

Spot any bloopers ?


Level 1
Level 1
I think there are 2 problems with configuration of message object 0 (LMO_0):
1. It is not allocated to any list. You have to choose the list with the CAN-node on which the message object should receive messages
2. If desired to catch all CAN-Messages change Identifier value and Mask value to 0x0. With your settings only messages with ID 0x7FF are catched.
Not applicable
Hi Tobias,

I much appreciate the input, thank you.

On 1, hmm I wondered about that. I'll try with LMO_0 LIST set instead to 'List 1(Node 0)',
and also the following:

On 2, ahh I'd forgotten about how identifier and mask work, for message receive acceptance.
I'll try as you say. With the basic CAN_NODE app, we have Identifier 0x7FF, and Mask 0.
I must admit I didn't spot that for MULTICAN_CONFIG app, I had Mask set differently.
For message receive, if Mask is 0, Identifier value is immaterial, I think. But your suggested
Identifier 0 is more sensible, I'll try that for both apps.

We use CAN_NODE for receive-only of all messages from another bus. For MULTICAN_CONFIG,
we'll need to do the same. We need to process most messages, and need anyway to receive all,
as the project has a usage reporting requirement, for each bus.

Best regards,

First solution authored First like received
Hi David,

have you managed to solve your issue? If there are some more issues, I can help by assisting you at solving them too 🙂

Best regards,
Not applicable
Tobias: I'm pleased to say that the 2 changes that you suggested to our MULTICAN_CONFIG app settings, have successfully resulted in my receiving CAN messages 🙂 First Light !
I've checked, and as expected, both changes are indeed needed. And for our basic CAN_NODE app, I've changed Identifier from 0x7FF to 0, and the app continues to work fine 🙂
So many thanks for pointing out the bloopers with my configuration.

Deni: Many thanks for the offer of assistance. I can see you've posted on MULTICAN_CONFIG app, on the forum. Thus far the received message identifier and 8-byte content accords
with what the emtas CANopen Device Explorer (CDE) is transmitting. Also the app is sending reply messages to CDE, but thus far, the identifier and content is just the default values
configured in the app settings, rather than what my code populates LMO_1 with. So that's one for tomorrow, to work out why. But if I get stuck with that or subsequent issues, I'll post up.
I'll post also results. Thanks !
Not applicable
Deni/Tobias: Actually yes, if you can spot any bloopers on the transmit side. I'm not entirely sure whether I should be writing my
outgoing message to the transmit FIFO base object (LMO_1), or the transmit FIFO last slave object (LMO_15). And whether
I should have transmit interrupt ticked just on LMO_1.
Not applicable
Hi Deni/Tobias,

Some updated info: I have debug-stepped through my code, as below
and watched it place into LMO_1, a correct response to a CDE SDO object 1000h read.
But when XMC_CAN_MO_Transmit( ) is called, what gets transmitted is the message in the

/* Populate message object */
MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr->can_identifier = buffer->ident & 0x07FFU;
MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr->can_data_length = buffer->ident >> 12U;
memcpy(MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr->can_data_byte, buffer->data, 8);

/* Queue message transmit */
error = XMC_CAN_MO_Transmit( MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr );

Within XMC_CAN_MO_Transmit( ), as expected, the first code line below, is what causes the
settings response message to appear in CDE:

/* set TXRQ bit */

As a test, I have set LMO_1 preset data different from any other MO (eg bytes 0x12 0x34 0x56 etc),
and that is what CDE receives. It is almost as if, the XMC43 has consumed into its internal CAN
output buffer, the message in the MULTICAN_CONFIG_0 LMO_1 settings. And never accepts
FIFO inflow of any subsequent message.

I'm trying to study Readme_MULTICAN_CONFIG_EXAMPLE_XMC47.pdf and the accompanying main.c,
to understand what I am doing differently/wrong. Nothing apparent, thus far. I did spot one PDF glitch:
Top of page 3, MO_3 and MO_4, should read MO_2 and MO_3, respectively. At least, to accord with the
screengrabs they title.

Best regards,

First solution authored First like received
Hi David,

what you additionally need is "XMC_CAN_MO_UpdateData(MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr)"; once the data is changed in MULTICAN_CONFIG_0 structure the message objects needs to be updated. You can see that in the "MULTICAN_CONFIG_EXAMPLE_XMC47" example too. Try adding mentioned line of code and gives a progress on your issues.

P.S thanks for the remarks on the .pdf file.

Best regards,
Not applicable
Hi Deni,

Many thanks. After a closer look at the example main.c, I reached that conclusion too 🙂
And also, that I need an XMC_CAN_MO_SetIdentifier( ) call, as identifier varies, for my outgoing messages.
Naively, I'd assumed that populating the MO members sufficed. I didn't appreciate there was a step 2 needed,
to transfer the MO member content, to the relevant XMC MultiCAN peripheral registers.

Before, I tried also reverting my tx FIFO, to a standard message object. Same result, the outgoing message was
just per the MULTICAN_CONFIG_0 settings. But after the described corrections, standard message object and tx FIFO,
both transmit what I intend. Here's the code. Bit of clean-up needed to unduplicate the buffer->ident & 0x07FFU..
..but it works.

/* Populate message object */
MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr->can_identifier = buffer->ident & 0x07FFU;
MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr->can_data_length = buffer->ident >> 12U;
memcpy(MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr->can_data_byte, buffer->data, 8);

/* Update identifier */
XMC_CAN_MO_SetIdentifier(MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr, buffer->ident & 0x07FFU);

/* Update transmission data */
status = XMC_CAN_MO_UpdateData(MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr);
/* Queue message transmit */
error = XMC_CAN_MO_Transmit( MULTICAN_CONFIG_0.lmobj_ptr[1]->mo_ptr );

Many thanks,

Not applicable
Hi Deni / Tobias,

I could perhaps still use a little assistance in understanding how to correctly use a CAN tx FIFO.
As mentioned, I have LMO_1 set as the tx base, with LMO_2 to LMO_15 inclusive, as tx slaves.
And in LMO_1, I have bottom pointer set to LMO_1, top pointer set to LMO_15.
This in accordance with the example project PDF, in including the tx base, in the pointer range.
But reading the XMC43 ref manual, perhaps it shouldn't be included, and bottom pointer should instead be LMO_2.
But perhaps different considerations apply for the example project tx FIFO as it is gateway usage, whereas I am not.

Anyway, my understanding is, that LMO_1 acts as virtual conduit to one of the 14 tx slaves, LMO_2 to LMO_15.
And if I have say three 8-byte messages to go every 10ms, I simply throw them one after the other at LMO_1,
using the code in my previous post.
And the peripheral looks after filing them into the 14 entry FIFO, and transmitting them on the CANbus in due course.

At the moment, XMC_CAN_MO_Transmit returns a busy error sometimes. But I don't quite understand why,
I thought XMC_CAN_MO_Transmit would always succeed, and the peripheral would just file the message
into the FIFO, ready for send in due course.

This morning, I've tried this changing the LMO_1 bottom pointer from LMO_1 to LMO_2.
But it made no difference to the busy error rate (I increment a count).
And indeed, CAN traffic pattern remained unchanged.

Further, I've tried reading out from the XMC43, the MOSTAT 32-bit register, for each MO.
All content looks plausible, with one exception: For LMO_2, the XMC43 ref manual tells me
(on page 1860), that for the first slave (LMO_2), PPREV points to itself. However, I don't see this.
It instead points to LMO_1. In contrast to the last slave (LMO_15), for which page 1860 says PNEXT
points to itself, which is indeed what I see. These findings are true regardless of whether I have the
LMO_1 bottom pointer set to LMO_1 or LMO_2. Maybe this is why the tx FIFO is throwing busy errors,
presumably because it's not being a queue.

The 32-bit Message Object FIFO/Gateway Pointer (MOFGPR) register content, for each MO, looks sensible though:
For LMO_1, BOT 1, TOP F, CUR cycling 1 to F then repeat, SEL 1. And for LMO_2 to LMO_15 inclusive, just CUR 1,
and other 3 bytes 0. Likewise that finding true regardless of whether I have the LMO_1 bottom pointer set to LMO_1 or LMO_2.

What I would like also, is to be able to report how many tx messages are queuing.
I've tried some test code, running just after my XMC_CAN_MO_Transmit( ) call,
that loops through the MOSTAT register for LMO_1 to LMO_15 inclusive (I've also
tried just LMO_2 to LMO_15 inclusive).

For each single bit, the code sums the instances of bits that are 1. None of my sums
report anything other than 15, or 0, with one exception: Summing the NEWDAT bit reports 1,
but only if I include LMO_1, so it must be from there.

Which makes me think, no actual queuing is occurring. And the busy errors I get,
are when my code is trying to queue two messages one after the other. In other words,
just the sort of thing a FIFO should be for..

Best regards,

Not applicable
Hi Deni / Tobias,

Just wondered, any further thoughts on this ?

Maybe, transmit queuing is actually occurring. Certainly, as mentioned, CUR is cycling, 1 to F, then repeat.
So perhaps that's the evidence that transmit queuing is happening.

If so, my question then, would be how should the queue be fed ?

When I have a message to submit to the queue, I don't want to have to sit in a polling loop,
waiting for the hardware to report it is not busy, before I can submit the message. And the
question always, is how long is too long, to wait, before timing out, and declaring failure to submit..

Of course, if the hardware reports busy, I could just defer the submit, until I get an interrupt, telling me the transmit
queue has dropped below some threshold, or is empty, and is not busy, and ready to receive a submission.
But unlike for the UART FIFOs, there's no such interrupt. Only a transmit complete interrupt, for the head of the queue,
on completing serialise out onto the CANbus. And a queue full interrupt.

BTW, just to ask, about the transmit complete interrupt, when does this fire? End of ack delimiter? End of EOF 8-bit field?
End of Interframe 3-bit field ?

Asking, as I'm running queue-less presently, awaiting resolution. And to meet the project performance remit,
I don't want any idle dwell, between frames.

Best regards,