cancel
Showing results for 
Search instead for 
Did you mean: 

CAN: Tx Delay Compensation is not working

Elmue
Associate II

Hello

I am trying to get the STMN32G431 processor to do what I want.
If I set the baudrates 500kB / 2MB and a samplepoint of 87.5% for both and send a CAN packet with FDF and BRS I get after 3 ms:
LastError = Recessive Bit Error and 8 Tx errors

and 2 ms later:
LastError = Recessive Bit Error,  248 Tx errors and Bus OFF !
Sometimes it is also a Dominant Bit Error.

This happens even in Internal loopback mode!
Therefore I set a Tx delay compensation of zero.
But also with other values for Tx delay compensation, it never works.

If I chose the samplepoint up to 85% all is still fine.
But with 87.5% I get a BusOff which is 100% reproducable.

Now comes the strange thing:

HAL_FDCAN_ConfigTxDelayCompensation(&can_handle, 0, 0);
HAL_FDCAN_EnableTxDelayCompensation(&can_handle);

will produce this problem, but with

HAL_FDCAN_DisableTxDelayCompensation(&can_handle);

it suddenly works correctly!

How is it possible that setting a delay of zero is not the same as a delay that is turned off?

Here my settings:
Clock 160 MHz

Nominal baudrate prescaler: 2
Segment 1 = 139
Segment 2 = 20
JSW = 8

Data baudrate prescaler: 5
Segment 1 = 13
Segment 2 = 2
JSW = 1
_____________________

Where can I find a documentation that explains in detail how to calculate the two values that I must pass to
HAL_FDCAN_ConfigTxDelayCompensation ?

I have been googling the whole day now and I have read the existing sparse documentation from ST and I still have absolutely no clue which values to pass to HAL_FDCAN_ConfigTxDelayCompensation ?

And as this compensates a hardware delay I also don't understand why must we not simply specify a fix delay in nanoseconds ?

If the CAN driver chip has a fix delay of 60 ns, I would expect a configuration where I enter 60 ns and that's it.
Why is this so complicated ?
And why is there no documentation how to calculate the values for offset and filter?

I found a posting that says to set the filter to zero and the offset to DataPrescaler * DataTimeSeg1.
But this does not work for 87.5%.
And it does not make sense to me.
The chip does not care about data segment 1.
The CAN bus transceiver chip has a fix hardware delay that never changes.
I would understand to calculate this delay from the clock frequency, but why from segment 1 ?

Can anybody explain me this in detail please?

14 REPLIES 14
Alex307
Associate II

I want to learn more about this

LCE
Principal II

Documentation is definitely very bad.
> Did you find anything about the second parameter to pass to HAL_FDCAN_ConfigTxDelayCompensation ?

That's what the reference manual is for.

In HAL_FDCAN_ConfigTxDelayCompensation you see that FDCAN->TDCR is written, check that in the ref manual.

 

And how to calculate TDC: well, check the transceiver datasheets for their delay, than change that into "mtq" units.
And that's real life with hardware: not all transceivers are the same...

Elmue
Associate II

Here I copy the answer that I received from the so called "Support".
It is a shame. ST has only employees who have no idea about the products that they are selling.
I'am wasting my time here.
Good bye!

 

To be completely honest the peripheral was (as whole standard) developed mostly by Bosch, including documentation (other manufactures are doing it the same way, you can check). If are unhappy with documentation you need more details (and as RM suggests) "described in detail in the ISO11898-1 specification" so if you need definite, unambiguous answer you can check directly the standard (it is not exactly question about peripheral, however rather standard itself).

About HAL_FDCAN_ConfigTxDelayCompensation() it is just writing the values to peripherals (directly may be seen (https://github.com/STMicroelectronics/stm32g4xx-hal-driver/blob/10138a41749ea62d53ecab65b2bc2a950acc04d2/Src/stm32g4xx_hal_fdcan.c#L1775)).

LCE
Principal II

The same for ETH / PTP offload :D , nobody at ST seems to know how that's working in detail.

Anyway, if still something's not working, there is probably something's wrong in your settings.

 

Just read your initial post again, and what you experience almost makes sense:

you set:

- internal loopback (no TDC needed)

- very "late" sample point 87.5% (at 2 Mbit that's 62.5 ns "before bit-time-end")

- TDC enabled (suppose that even at TDC = 0 enabling the extra delay (there's an extra bit in FDCANx->DBTP), the HW creates a few nanoseconds delay)

 

The 62.5 ns should be enough to make it work anyway.

So maybe your sampling point calculation is wrong, and the real sampling point is closer to the 100% ?

Elmue
Associate II

I finally solved the problem without the help of this forum and without the help of the ST support.

I finished and uploaded the new CANable firmware which also calculates the TDC.
If anybody comes here from Google and wants to know how to do this correctly you can now download my open source firmware and study my code.

I worked 3 month full time on the STM32G431 and I consider myself now an expert in CAN programming.
You can learn a lot from my code about STM32 programming.

My firmware works with up to 10 Mbaud on the very cheap MKS Makerbase CANable adapter which has a STM32G431 processor:

Adapter_CANable.png

I wrote also a Firmware Uploader which allows ordinary users without programming skills to upload their firmware with one click to their STM32 processor. It is based on the very sloppy open source code in the DfuSe application from ST where I had to fix dozens of bugs and added new features.

CANable STM32 Firmware Updater.png


I also wrote a CAN Terminal that allows to communicate with CAN bus, see the traffic, send packets, write logfiles and even write macro scripts to simulate any CAN bus device.

CAN Raw Terminal.png

I wrote a very long manual where you find detailed explanations.
You find it here:
https://netcult.ch/elmue/CANable%20Firmware%20Update