2 years, 4 months ago.

How to use CAN filter function?

In the CAN.h file (CAN.h) there is a format function like so...

      /** Filter out incoming messages
      *
      *  @param id the id to filter on
      *  @param mask the mask applied to the id
      *  @param format format to filter on (Default CANAny)
      *  @param handle message filter handle (Optional)
      *
      *  @returns
      *    0 if filter change failed or unsupported,
      *    new filter handle if successful
      */

        int filter(unsigned int id, unsigned int mask, CANFormat format = CANAny, int handle = 0);

Then there's also the read function

     /** Read a CANMessage from the bus.
      *
      *  @param msg A CANMessage to read to.
      *  @param handle message filter handle (0 for any message)
      *
      *  @returns
      *    0 if no message arrived,
      *    1 if message arrived
      */

     int read(CANMessage &msg, int handle = 0);

I'm not very experienced with CAN, and so I don't really understand much of how this filtering works, and I don't understand what the handle parameter works. Does it mean I can setup a filter for a few options, and then choose which filter I implement in the read? E.g. If I passed handle 1 to filter function, then calling read with handle 1 will use only this filter? Is it sort of like a filter number, to represent that filter by?

1 Answer

2 years, 4 months ago.

Hello W K,

Each filter is a 32-bit filter defined by a filter ID and a filter mask. If no filter is set up then no CAN message is accepted! That's why filter #0 is set up in the constructor to accept all CAN messages by default. On reception of a message it is compared with filter #0. If there is a match, the message is accepted and stored. If there is no match, the incoming identifier is then compared with the next filter. If the received identifier does not match any of the identifiers configured in the filters, the message is discarded by hardware without disturbing the software.

  • id - 'Filter ID' defines the bit values to be compared with the corresponding received bits.
  • mask - 'Filter mask' defines which bits of the 'Filter ID' are compared with the received bits and which are disregarded.
  • format - This parameter can be CANAny, CANStandard, CANExtended
  • handle - Selects the filter. This parameter should be a number between 0 and 13 (could be more for some targets).

This Mbed 2 (aka Mbed classic) example might help to get started:

  • Remember that filter #0 is set up in the constructor to accept all CAN messages by default. So we have to reconfigure it. If we were set up filter #1 then filter #0 would accept all the messages and no message would reach filter #1!
  • Then you can setup more filters: filter 1, 2 ... up to 13 (Maybe some targets allow even more. I'm not sure.)
  • Also notice that in Mbed 5 (aka Mbed OS) an attempt to use a mutex from within an ISR is treated as a fatal system error. Hence, in contrary to Mbed 2, we cannot call the read() function in ISR. We have to poll the CAN bus (call read()) in the main() function instead.

Accepted Answer