Here is a patch to

-remove a wrong comment in atmel mcan ioctl
-add ioctls to set/get bit timing in stm32l4
-add ioctl hooks to allow future management of can id filters.
This commit is contained in:
Sebastien Lorquet 2016-06-21 06:21:01 -06:00 committed by Gregory Nutt
parent 951c71041d
commit 8b1a607671
4 changed files with 487 additions and 81 deletions

View File

@ -2602,8 +2602,6 @@ static int mcan_ioctl(FAR struct can_dev_s *dev, int cmd, unsigned long arg)
break;
}
/* No CAN ioctls are supported */
return ret;
}

View File

@ -6333,21 +6333,21 @@ config STM32_USB_ITRMP
F3 family and selects the use of the dedicated USB interrupts.
menu "CAN driver configuration"
depends on STM32_CAN1 || STM32_CAN2
depends on STM32_CAN
config CAN1_BAUD
int "CAN1 BAUD"
default 250000
depends on STM32_CAN1
---help---
CAN1 BAUD rate. Required if STM32_CAN1 is defined.
CAN1 BAUD rate. Required if CONFIG_STM32_CAN1 is defined.
config CAN2_BAUD
int "CAN2 BAUD"
default 250000
depends on STM32_CAN2
---help---
CAN2 BAUD rate. Required if STM32_CAN2 is defined.
CAN2 BAUD rate. Required if CONFIG_STM32_CAN2 is defined.
config CAN_TSEG1
int "TSEG1 quanta"
@ -6360,6 +6360,15 @@ config CAN_TSEG2
default 7
---help---
The number of CAN time quanta in segment 2. Default: 7
config STM32_CAN_REGDEBUG
bool "CAN Register level debug"
depends on DEBUG_CAN_INFO
default n
---help---
Output detailed register-level CAN device debug information.
Requires also CONFIG_DEBUG_CAN_INFO.
endmenu
if STM32_LTDC

View File

@ -871,7 +871,7 @@ config CAN1_BAUD
default 250000
depends on STM32L4_CAN1
---help---
CAN1 BAUD rate. Required if STM32L4_CAN1 is defined.
CAN1 BAUD rate. Required if CONFIG_STM32L4_CAN1 is defined.
config CAN_TSEG1
int "TSEG1 quanta"
@ -884,6 +884,15 @@ config CAN_TSEG2
default 7
---help---
The number of CAN time quanta in segment 2. Default: 7
config STM32L4_CAN_REGDEBUG
bool "CAN Register level debug"
depends on DEBUG_CAN_INFO
default n
---help---
Output detailed register-level CAN device debug information.
Requires also CONFIG_DEBUG_CAN_INFO.
endmenu
endif # ARCH_CHIP_STM32L4

View File

@ -83,7 +83,7 @@
#define CAN_BIT_QUANTA (CONFIG_CAN_TSEG1 + CONFIG_CAN_TSEG2 + 1)
#ifndef CONFIG_DEBUG_CAN_INFO
# undef CONFIG_STM32_CAN_REGDEBUG
# undef CONFIG_STM32L4_CAN_REGDEBUG
#endif
/****************************************************************************
@ -107,14 +107,14 @@ struct stm32l4_can_s
/* CAN Register access */
static uint32_t can_getreg(struct stm32l4_can_s *priv, int offset);
static uint32_t can_getfreg(struct stm32l4_can_s *priv, int offset);
static void can_putreg(struct stm32l4_can_s *priv, int offset, uint32_t value);
static void can_putfreg(struct stm32l4_can_s *priv, int offset, uint32_t value);
#ifdef CONFIG_STM32_CAN_REGDEBUG
static void can_dumpctrlregs(struct stm32l4_can_s *priv, FAR const char *msg);
static void can_dumpmbregs(struct stm32l4_can_s *priv, FAR const char *msg);
static void can_dumpfiltregs(struct stm32l4_can_s *priv, FAR const char *msg);
static uint32_t can_getreg(FAR struct stm32l4_can_s *priv, int offset);
static uint32_t can_getfreg(FAR struct stm32l4_can_s *priv, int offset);
static void can_putreg(FAR struct stm32l4_can_s *priv, int offset, uint32_t value);
static void can_putfreg(FAR struct stm32l4_can_s *priv, int offset, uint32_t value);
#ifdef CONFIG_STM32L4_CAN_REGDEBUG
static void can_dumpctrlregs(FAR struct stm32l4_can_s *priv, FAR const char *msg);
static void can_dumpmbregs(FAR struct stm32l4_can_s *priv, FAR const char *msg);
static void can_dumpfiltregs(FAR struct stm32l4_can_s *priv, FAR const char *msg);
#else
# define can_dumpctrlregs(priv,msg)
# define can_dumpmbregs(priv,msg)
@ -136,14 +136,23 @@ static bool can_txempty(FAR struct can_dev_s *dev);
/* CAN interrupt handling */
static int can_rx0interrupt(int irq, void *context);
static int can_txinterrupt(int irq, void *context);
static int can_rx0interrupt(int irq, FAR void *context);
static int can_txinterrupt(int irq, FAR void *context);
/* Initialization */
static int can_bittiming(struct stm32l4_can_s *priv);
static int can_cellinit(struct stm32l4_can_s *priv);
static int can_filterinit(struct stm32l4_can_s *priv);
static int can_enterinitmode(FAR struct stm32l4_can_s *priv);
static int can_exitinitmode(FAR struct stm32l4_can_s *priv);
static int can_bittiming(FAR struct stm32l4_can_s *priv);
static int can_cellinit(FAR struct stm32l4_can_s *priv);
static int can_filterinit(FAR struct stm32l4_can_s *priv);
/* Filtering (todo) */
static int stm32l4_can_addextfilter(FAR struct stm32l4_can_s *priv, FAR struct canioc_extfilter_s *arg);
static int stm32l4_can_delextfilter(FAR struct stm32l4_can_s *priv, int arg);
static int stm32l4_can_addstdfilter(FAR struct stm32l4_can_s *priv, FAR struct canioc_stdfilter_s *arg);
static int stm32l4_can_delstdfilter(FAR struct stm32l4_can_s *priv, int arg);
/****************************************************************************
* Private Data
@ -201,7 +210,7 @@ static struct can_dev_s g_can1dev =
*
****************************************************************************/
#ifdef CONFIG_STM32_CAN_REGDEBUG
#ifdef CONFIG_STM32L4_CAN_REGDEBUG
static uint32_t can_vgetreg(uint32_t addr)
{
static uint32_t prevaddr = 0;
@ -255,23 +264,23 @@ static uint32_t can_vgetreg(uint32_t addr)
return val;
}
static uint32_t can_getreg(struct stm32l4_can_s *priv, int offset)
static uint32_t can_getreg(FAR struct stm32l4_can_s *priv, int offset)
{
return can_vgetreg(priv->base + offset);
}
static uint32_t can_getfreg(struct stm32l4_can_s *priv, int offset)
static uint32_t can_getfreg(FAR struct stm32l4_can_s *priv, int offset)
{
return can_vgetreg(priv->fbase + offset);
}
#else
static uint32_t can_getreg(struct stm32l4_can_s *priv, int offset)
static uint32_t can_getreg(FAR struct stm32l4_can_s *priv, int offset)
{
return getreg32(priv->base + offset);
}
static uint32_t can_getfreg(struct stm32l4_can_s *priv, int offset)
static uint32_t can_getfreg(FAR struct stm32l4_can_s *priv, int offset)
{
return getreg32(priv->fbase + offset);
}
@ -295,7 +304,7 @@ static uint32_t can_getfreg(struct stm32l4_can_s *priv, int offset)
*
****************************************************************************/
#ifdef CONFIG_STM32_CAN_REGDEBUG
#ifdef CONFIG_STM32L4_CAN_REGDEBUG
static void can_vputreg(uint32_t addr, uint32_t value)
{
/* Show the register value being written */
@ -307,23 +316,23 @@ static void can_vputreg(uint32_t addr, uint32_t value)
putreg32(value, addr);
}
static void can_putreg(struct stm32l4_can_s *priv, int offset, uint32_t value)
static void can_putreg(FAR struct stm32l4_can_s *priv, int offset, uint32_t value)
{
can_vputreg(priv->base + offset, value);
}
static void can_putfreg(struct stm32l4_can_s *priv, int offset, uint32_t value)
static void can_putfreg(FAR struct stm32l4_can_s *priv, int offset, uint32_t value)
{
can_vputreg(priv->fbase + offset, value);
}
#else
static void can_putreg(struct stm32l4_can_s *priv, int offset, uint32_t value)
static void can_putreg(FAR struct stm32l4_can_s *priv, int offset, uint32_t value)
{
putreg32(value, priv->base + offset);
}
static void can_putfreg(struct stm32l4_can_s *priv, int offset, uint32_t value)
static void can_putfreg(FAR struct stm32l4_can_s *priv, int offset, uint32_t value)
{
putreg32(value, priv->fbase + offset);
}
@ -343,8 +352,8 @@ static void can_putfreg(struct stm32l4_can_s *priv, int offset, uint32_t value)
*
****************************************************************************/
#ifdef CONFIG_STM32_CAN_REGDEBUG
static void can_dumpctrlregs(struct stm32l4_can_s *priv, FAR const char *msg)
#ifdef CONFIG_STM32L4_CAN_REGDEBUG
static void can_dumpctrlregs(FAR struct stm32l4_can_s *priv, FAR const char *msg)
{
if (msg)
{
@ -387,8 +396,8 @@ static void can_dumpctrlregs(struct stm32l4_can_s *priv, FAR const char *msg)
*
****************************************************************************/
#ifdef CONFIG_STM32_CAN_REGDEBUG
static void can_dumpmbregs(struct stm32l4_can_s *priv, FAR const char *msg)
#ifdef CONFIG_STM32L4_CAN_REGDEBUG
static void can_dumpmbregs(FAR struct stm32l4_can_s *priv, FAR const char *msg)
{
if (msg)
{
@ -447,8 +456,8 @@ static void can_dumpmbregs(struct stm32l4_can_s *priv, FAR const char *msg)
*
****************************************************************************/
#ifdef CONFIG_STM32_CAN_REGDEBUG
static void can_dumpfiltregs(struct stm32l4_can_s *priv, FAR const char *msg)
#ifdef CONFIG_STM32L4_CAN_REGDEBUG
static void can_dumpfiltregs(FAR struct stm32l4_can_s *priv, FAR const char *msg)
{
int i;
@ -724,9 +733,241 @@ static void can_txint(FAR struct can_dev_s *dev, bool enable)
static int can_ioctl(FAR struct can_dev_s *dev, int cmd, unsigned long arg)
{
/* No CAN ioctls are supported */
FAR struct stm32l4_can_s *priv;
int ret = -ENOTTY;
return -ENOTTY;
caninfo("cmd=%04x arg=%lu\n", cmd, arg);
DEBUGASSERT(dev && dev->cd_priv);
priv = dev->cd_priv;
/* Handle the command */
switch (cmd)
{
/* CANIOC_GET_BITTIMING:
* Description: Return the current bit timing settings
* Argument: A pointer to a write-able instance of struct
* canioc_bittiming_s in which current bit timing values
* will be returned.
* Returned Value: Zero (OK) is returned on success. Otherwise -1 (ERROR)
* is returned with the errno variable set to indicate the
* nature of the error.
* Dependencies: None
*/
case CANIOC_GET_BITTIMING:
{
FAR struct canioc_bittiming_s *bt =
(FAR struct canioc_bittiming_s *)arg;
uint32_t regval;
uint32_t brp;
DEBUGASSERT(bt != NULL);
regval = can_getreg(priv, STM32L4_CAN_BTR_OFFSET);
bt->bt_sjw = ((regval & CAN_BTR_SJW_MASK) >> CAN_BTR_SJW_SHIFT) + 1;
bt->bt_tseg1 = ((regval & CAN_BTR_TS1_MASK) >> CAN_BTR_TS1_SHIFT) + 1;
bt->bt_tseg2 = ((regval & CAN_BTR_TS2_MASK) >> CAN_BTR_TS2_SHIFT) + 1;
brp = ((regval & CAN_BTR_BRP_MASK) >> CAN_BTR_BRP_SHIFT) + 1;
bt->bt_baud = STM32L4_PCLK1_FREQUENCY /
(brp * (bt->bt_tseg1 + bt->bt_tseg2 + 1));
ret = OK;
}
break;
/* CANIOC_SET_BITTIMING:
* Description: Set new current bit timing values
* Argument: A pointer to a read-able instance of struct
* canioc_bittiming_s in which the new bit timing values
* are provided.
* Returned Value: Zero (OK) is returned on success. Otherwise -1 (ERROR)
* is returned with the errno variable set to indicate the
* nature of the error.
* Dependencies: None
*
* REVISIT: There is probably a limitation here: If there are multiple
* threads trying to send CAN packets, when one of these threads reconfigures
* the bitrate, the MCAN hardware will be reset and the context of operation
* will be lost. Hence, this IOCTL can only safely be executed in quiescent
* time periods.
*/
case CANIOC_SET_BITTIMING:
{
FAR const struct canioc_bittiming_s *bt =
(FAR const struct canioc_bittiming_s *)arg;
uint32_t brp;
uint32_t can_bit_quanta;
uint32_t tmp;
DEBUGASSERT(bt != NULL);
DEBUGASSERT(bt->bt_baud < STM32L4_PCLK1_FREQUENCY);
DEBUGASSERT(bt->bt_sjw > 0 && bt->bt_sjw <= 4);
DEBUGASSERT(bt->bt_tseg1 > 0 && bt->bt_tseg1 <= 16);
DEBUGASSERT(bt->bt_tseg2 > 0 && bt->bt_tseg2 <= 8);
/* Extract bit timing data */
/* tmp is in clocks per bit time */
tmp = STM32L4_PCLK1_FREQUENCY / bt->bt_baud;
/* This value is dynamic as requested by user */
can_bit_quanta = bt->bt_tseg1 + bt->bt_tseg2 + 1;
if (tmp < can_bit_quanta)
{
#if 0
/* At the smallest brp value (1), there are already too few
* bit times (PCLK1 / baud) to meet our goal. brp must be one
* and we need make some reasonable guesses about ts1 and ts2.
*/
brp = 1;
/* In this case, we have to guess a good value for ts1 and ts2 */
tseg1 = (tmp - 1) >> 1; /* cut available time in half */
tseg2 = tmp - tseg1 - 1; /* ts2 uses the rest minus one */
/* if we can, try to approximate the CAN requirements,
* which are not exactly "cut baud time in half"
*/
if (tseg1 == tseg2 && tseg1 > 1 && tseg2 < CAN_BTR_TSEG2_MAX)
{
tseg1--;
tseg2++;
}
#else
ret = -EINVAL;
#endif
}
/* Otherwise, nquanta is can_bit_quanta, ts1 and ts2 are provided
* by the user and we calculate brp to achieve can_bit_quanta
* quanta in the bit time
*/
else
{
brp = (tmp + (can_bit_quanta/2)) / can_bit_quanta;
DEBUGASSERT(brp >= 1 && brp <= CAN_BTR_BRP_MAX);
}
caninfo("TS1: %d TS2: %d BRP: %d\n", bt->bt_tseg1, bt->bt_tseg2, brp);
/* Configure bit timing. This also does the following, less obvious
* things. Unless loopback mode is enabled, it:
*
* - Disables silent mode.
* - Disables loopback mode.
*
*/
tmp = ((brp - 1) << CAN_BTR_BRP_SHIFT) |
((bt->bt_tseg1 - 1) << CAN_BTR_TS1_SHIFT) |
((bt->bt_tseg2 - 1) << CAN_BTR_TS2_SHIFT) |
((bt->bt_sjw - 1) << CAN_BTR_SJW_SHIFT);
#ifdef CONFIG_CAN_LOOPBACK
tmp |= CAN_BTR_LBKM;
#endif
/* Bit timing can only be configured in init mode.
* No registers are changed.
*/
ret = can_enterinitmode(priv);
if (ret != 0)
{
break;
}
can_putreg(priv, STM32L4_CAN_BTR_OFFSET, tmp);
ret = can_exitinitmode(priv);
if (ret == 0)
{
priv->baud = STM32L4_PCLK1_FREQUENCY / (brp * (bt->bt_tseg1 + bt->bt_tseg2 + 1));
}
}
break;
#ifdef CONFIG_CAN_EXTID
/* CANIOC_ADD_EXTFILTER:
* Description: Add an address filter for a extended 29 bit
* address.
* Argument: A reference to struct canioc_extfilter_s
* Returned Value: A non-negative filter ID is returned on success.
* Otherwise -1 (ERROR) is returned with the errno
* variable set to indicate the nature of the error.
*/
case CANIOC_ADD_EXTFILTER:
{
DEBUGASSERT(arg != 0);
ret = stm32l4_can_addextfilter(priv, (FAR struct canioc_extfilter_s *)arg);
}
break;
/* CANIOC_DEL_EXTFILTER:
* Description: Remove an address filter for a standard 29 bit address.
* Argument: The filter index previously returned by the
* CANIOC_ADD_EXTFILTER command
* Returned Value: Zero (OK) is returned on success. Otherwise -1 (ERROR)
* is returned with the errno variable set to indicate the
* nature of the error.
*/
case CANIOC_DEL_EXTFILTER:
{
DEBUGASSERT(arg <= priv->config->nextfilters);
ret = stm32l4_can_delextfilter(priv, (int)arg);
}
break;
#endif
/* CANIOC_ADD_STDFILTER:
* Description: Add an address filter for a standard 11 bit
* address.
* Argument: A reference to struct canioc_stdfilter_s
* Returned Value: A non-negative filter ID is returned on success.
* Otherwise -1 (ERROR) is returned with the errno
* variable set to indicate the nature of the error.
*/
case CANIOC_ADD_STDFILTER:
{
DEBUGASSERT(arg != 0);
ret = stm32l4_can_addstdfilter(priv, (FAR struct canioc_stdfilter_s *)arg);
}
break;
/* CANIOC_DEL_STDFILTER:
* Description: Remove an address filter for a standard 11 bit address.
* Argument: The filter index previously returned by the
* CANIOC_ADD_STDFILTER command
* Returned Value: Zero (OK) is returned on success. Otherwise -1 (ERROR)
* is returned with the errno variable set to indicate the
* nature of the error.
*/
case CANIOC_DEL_STDFILTER:
{
DEBUGASSERT(arg <= priv->config->nstdfilters);
ret = stm32l4_can_delstdfilter(priv, (int)arg);
}
break;
/* Unsupported/unrecognized command */
default:
canerr("ERROR: Unrecognized command: %04x\n", cmd);
break;
}
return ret;
}
/****************************************************************************
@ -996,7 +1237,7 @@ static bool can_txempty(FAR struct can_dev_s *dev)
*
****************************************************************************/
static int can_rx0interrupt(int irq, void *context)
static int can_rx0interrupt(int irq, FAR void *context)
{
FAR struct can_dev_s *dev = NULL;
FAR struct stm32l4_can_s *priv;
@ -1107,7 +1348,7 @@ errout:
*
****************************************************************************/
static int can_txinterrupt(int irq, void *context)
static int can_txinterrupt(int irq, FAR void *context)
{
FAR struct can_dev_s *dev = NULL;
FAR struct stm32l4_can_s *priv;
@ -1227,6 +1468,7 @@ static int can_txinterrupt(int irq, void *context)
* Tbs1 = Tq * ts1
* Tbs2 = Tq * ts2
* Tq = brp * Tpclk1
* baud = Fpclk1 / (brp * (1 + ts1 + ts2)))
*
* Where:
* Tpclk1 is the period of the APB1 clock (PCLK1).
@ -1239,7 +1481,7 @@ static int can_txinterrupt(int irq, void *context)
*
****************************************************************************/
static int can_bittiming(struct stm32l4_can_s *priv)
static int can_bittiming(FAR struct stm32l4_can_s *priv)
{
uint32_t tmp;
uint32_t brp;
@ -1324,10 +1566,12 @@ static int can_bittiming(struct stm32l4_can_s *priv)
}
/****************************************************************************
* Name: can_cellinit
* Name: can_enterinitmode
*
* Description:
* CAN cell initialization
* Put the CAN cell in Initialization mode. This only disconnects the CAN
* peripheral, no registers are changed. The initialization mode is
* required to change the baud rate.
*
* Input Parameter:
* priv - A pointer to the private data structure for this CAN block
@ -1337,27 +1581,17 @@ static int can_bittiming(struct stm32l4_can_s *priv)
*
****************************************************************************/
static int can_cellinit(struct stm32l4_can_s *priv)
static int can_enterinitmode(FAR struct stm32l4_can_s *priv)
{
volatile uint32_t timeout;
uint32_t regval;
volatile uint32_t timeout;
int ret;
caninfo("CAN%d\n", priv->port);
/* Exit from sleep mode */
regval = can_getreg(priv, STM32L4_CAN_MCR_OFFSET);
regval &= ~CAN_MCR_SLEEP;
can_putreg(priv, STM32L4_CAN_MCR_OFFSET, regval);
/* Configure CAN behavior. Priority driven request order, not message ID. */
regval |= CAN_MCR_TXFP;
can_putreg(priv, STM32L4_CAN_MCR_OFFSET, regval);
/* Enter initialization mode */
regval = can_getreg(priv, STM32L4_CAN_MCR_OFFSET);
regval |= CAN_MCR_INRQ;
can_putreg(priv, STM32L4_CAN_MCR_OFFSET, regval);
@ -1382,30 +1616,29 @@ static int can_cellinit(struct stm32l4_can_s *priv)
return -ETIMEDOUT;
}
/* Disable the following modes:
*
* - Time triggered communication mode
* - Automatic bus-off management
* - Automatic wake-up mode
* - No automatic retransmission
* - Receive FIFO locked mode
* - Transmit FIFO priority
*/
return 0;
}
regval = can_getreg(priv, STM32L4_CAN_MCR_OFFSET);
regval &= ~(CAN_MCR_TXFP | CAN_MCR_RFLM | CAN_MCR_NART | CAN_MCR_AWUM | CAN_MCR_ABOM | CAN_MCR_TTCM);
can_putreg(priv, STM32L4_CAN_MCR_OFFSET, regval);
/****************************************************************************
* Name: can_exitinitmode
*
* Description:
* Put the CAN cell out of the Initialization mode (to Normal mode)
*
* Input Parameter:
* priv - A pointer to the private data structure for this CAN block
*
* Returned Value:
* Zero on success; a negated errno value on failure.
*
****************************************************************************/
/* Configure bit timing. */
static int can_exitinitmode(FAR struct stm32l4_can_s *priv)
{
uint32_t regval;
volatile uint32_t timeout;
ret = can_bittiming(priv);
if (ret < 0)
{
canerr("ERROR: Failed to set bit timing: %d\n", ret);
return ret;
}
/* Exit initialization mode */
/* Exit Initialization mode, enter Normal mode */
regval = can_getreg(priv, STM32L4_CAN_MCR_OFFSET);
regval &= ~CAN_MCR_INRQ;
@ -1432,7 +1665,72 @@ static int can_cellinit(struct stm32l4_can_s *priv)
return -ETIMEDOUT;
}
return OK;
return 0;
}
/****************************************************************************
* Name: can_cellinit
*
* Description:
* CAN cell initialization
*
* Input Parameter:
* priv - A pointer to the private data structure for this CAN block
*
* Returned Value:
* Zero on success; a negated errno value on failure.
*
****************************************************************************/
static int can_cellinit(FAR struct stm32l4_can_s *priv)
{
uint32_t regval;
int ret;
caninfo("CAN%d\n", priv->port);
/* Exit from sleep mode */
regval = can_getreg(priv, STM32L4_CAN_MCR_OFFSET);
regval &= ~CAN_MCR_SLEEP;
can_putreg(priv, STM32L4_CAN_MCR_OFFSET, regval);
/* Configure CAN behavior. Priority driven request order, not message ID. */
regval |= CAN_MCR_TXFP;
can_putreg(priv, STM32L4_CAN_MCR_OFFSET, regval);
ret = can_enterinitmode(priv);
if(ret != 0)
{
return ret;
}
/* Disable the following modes:
*
* - Time triggered communication mode
* - Automatic bus-off management
* - Automatic wake-up mode
* - No automatic retransmission
* - Receive FIFO locked mode
* - Transmit FIFO priority
*/
regval = can_getreg(priv, STM32L4_CAN_MCR_OFFSET);
regval &= ~(CAN_MCR_TXFP | CAN_MCR_RFLM | CAN_MCR_NART | CAN_MCR_AWUM |
CAN_MCR_ABOM | CAN_MCR_TTCM);
can_putreg(priv, STM32L4_CAN_MCR_OFFSET, regval);
/* Configure bit timing. */
ret = can_bittiming(priv);
if (ret < 0)
{
canerr("ERROR: Failed to set bit timing: %d\n", ret);
return ret;
}
return can_exitinitmode(priv);
}
/****************************************************************************
@ -1452,7 +1750,7 @@ static int can_cellinit(struct stm32l4_can_s *priv)
* finer control of the filtering.
*
* There is no need to set up one filter for each CAN since STM32L4 only
* contains one CAN devices. If one day some STM32L4 has 2 CANs, then
* contains one CAN device. If one day some STM32L4 has 2 CANs, then
* code will have to be imported from the STM32 port.
*
* 32-bit IdMask mode is configured. However, both the ID and the MASK
@ -1467,7 +1765,7 @@ static int can_cellinit(struct stm32l4_can_s *priv)
*
****************************************************************************/
static int can_filterinit(struct stm32l4_can_s *priv)
static int can_filterinit(FAR struct stm32l4_can_s *priv)
{
uint32_t regval;
uint32_t bitmask;
@ -1529,6 +1827,98 @@ static int can_filterinit(struct stm32l4_can_s *priv)
return OK;
}
/****************************************************************************
* Name: stm32l4_can_addextfilter
*
* Description:
* Add a filter for extended CAN IDs
*
* Input Parameter:
* priv - A pointer to the private data structure for this CAN block
* arg - A pointer to a structure describing the filter
*
* Returned Value:
* A non-negative filter ID is returned on success.
* Otherwise -1 (ERROR) is returned with the errno
* set to indicate the nature of the error.
*
****************************************************************************/
static int stm32l4_can_addextfilter(FAR struct stm32l4_can_s *priv,
FAR struct canioc_extfilter_s *arg)
{
return -ENOTTY;
}
/****************************************************************************
* Name: stm32l4_can_delextfilter
*
* Description:
* Remove a filter for extended CAN IDs
*
* Input Parameter:
* priv - A pointer to the private data structure for this CAN block
* arg - The filter index previously returned by the
* CANIOC_ADD_EXTFILTER command
*
* Returned Value:
* Zero (OK) is returned on success. Otherwise -1 (ERROR)
* returned with the errno variable set to indicate the
* of the error.
*
****************************************************************************/
static int stm32l4_can_delextfilter(FAR struct stm32l4_can_s *priv, int arg)
{
return -ENOTTY;
}
/****************************************************************************
* Name: stm32l4_can_addextfilter
*
* Description:
* Add a filter for standard CAN IDs
*
* Input Parameter:
* priv - A pointer to the private data structure for this CAN block
* arg - A pointer to a structure describing the filter
*
* Returned Value:
* A non-negative filter ID is returned on success.
* Otherwise -1 (ERROR) is returned with the errno
* set to indicate the nature of the error.
*
****************************************************************************/
static int stm32l4_can_addstdfilter(FAR struct stm32l4_can_s *priv,
FAR struct canioc_stdfilter_s *arg)
{
return -ENOTTY;
}
/****************************************************************************
* Name: stm32l4_can_delstdfilter
*
* Description:
* Remove a filter for standard CAN IDs
*
* Input Parameter:
* priv - A pointer to the private data structure for this CAN block
* arg - The filter index previously returned by the
* CANIOC_ADD_STDFILTER command
*
* Returned Value:
* Zero (OK) is returned on success. Otherwise -1 (ERROR)
* returned with the errno variable set to indicate the
* of the error.
*
****************************************************************************/
static int stm32l4_can_delstdfilter(FAR struct stm32l4_can_s *priv, int arg)
{
return -ENOTTY;
}
/****************************************************************************
* Public Functions
****************************************************************************/
@ -1549,7 +1939,7 @@ static int can_filterinit(struct stm32l4_can_s *priv)
FAR struct can_dev_s *stm32l4_caninitialize(int port)
{
struct can_dev_s *dev = NULL;
FAR struct can_dev_s *dev = NULL;
caninfo("CAN%d\n", port);