Page 1 of 1

STM32F1 CAN RX Interrupt

Posted: Sun Sep 10, 2017 8:52 am
by ubis
Hello,
I'm trying to to use RX0 interrupt service on STM32F103C8T6 MCU.

I've got the following code:

Code: Select all

#include <stdio.h>
#include <string.h>

#include "ch.h"
#include "hal.h"
#include "board.h"
#include "chprintf.h"

#include "def.h"

CANRxFrame   txmsg;
SerialConfig uartCfg = { .speed = SERIAL_BAUDRATE };
CANConfig    cancfg  = { .mcr = CAN_MCR_ABOM | CAN_MCR_AWUM };

void SetBaudRate(int baud);

int main(void) {
   // system initialization
   halInit();
   chSysInit();

   // enable IRQ vector
   nvicEnableVector(CAN1_RX0_IRQn, CORTEX_PRIO_MASK(STM32_CAN_CAN1_IRQ_PRIORITY));

   // set pins
   palSetPadMode(GPIOA, 11, PAL_MODE_INPUT_PULLUP);               // CAN RX
   palSetPadMode(GPIOA, 12, PAL_MODE_STM32_ALTERNATE_PUSHPULL);   // CAN TX

   // serial initialization
   sdStart(&SD1, &uartCfg);
   PRINT("\r\n\n");
   PRINT("Running serial console at %d\r\n", SERIAL_BAUDRATE);

   SetBaudRate(250000);          // set can bus baud rate
   canStart(&CAND1, &cancfg);      // start can bus

   while (true) {
      /*msg_t t = canReceive(&CAND1, CAN_ANY_MAILBOX, &txmsg, TIME_IMMEDIATE);
      if (t == MSG_OK) {
         PRINT("received\r\n");
      }*/
      chThdSleepMilliseconds(100);
   }
}

void SetBaudRate(int baud) {
   int tmp  = 2000000 / baud - 1;
   cancfg.btr  = CAN_BTR_SJW(3);
   cancfg.btr |= CAN_BTR_TS1(11);
   cancfg.btr |= CAN_BTR_TS2(4);
   cancfg.btr |= CAN_BTR_BRP(tmp);
}

CH_IRQ_HANDLER(CAN1_RX0_IRQHandler) {
CH_IRQ_PROLOGUE();

   chSysLockFromISR();
   msg_t t = canReceive(&CAND1, CAN_ANY_MAILBOX, &txmsg, TIME_IMMEDIATE);
   if (t == MSG_OK) {
      PRINT("interrupt received\r\n");
   }
   chSysUnlockFromISR();

CH_IRQ_EPILOGUE();
}


I think i'm missing something. It doesn't trigger the interrupt.
However, if I use

Code: Select all

canReceive
in main loop cycle, it does receive CAN message.

Also PRINT is just a definition to chprintf.
It could be overhead to use chprintf in interrupt, so even setting pin to different state doesn't work.

Re: STM32F1 CAN RX Interrupt

Posted: Sun Sep 10, 2017 10:26 am
by Giovanni
Hi,

ChibiOS drivers enable interrupts and define interrupt vectors internally, there is no need for you to do that. If you want to access CAN at register level then you need to disable the CAN driver or there would be 2 ISRs for the same vector.

Giovanni