mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-10-14 12:37:32 +00:00
Merge branch 'master' of git://gitorious.org/linux-can/linux-can-next
This commit is contained in:
commit
9b97b84eb5
5 changed files with 65 additions and 27 deletions
|
@ -232,16 +232,16 @@ solution for a couple of reasons:
|
||||||
arbitration problems and error frames caused by the different
|
arbitration problems and error frames caused by the different
|
||||||
ECUs. The occurrence of detected errors are important for diagnosis
|
ECUs. The occurrence of detected errors are important for diagnosis
|
||||||
and have to be logged together with the exact timestamp. For this
|
and have to be logged together with the exact timestamp. For this
|
||||||
reason the CAN interface driver can generate so called Error Frames
|
reason the CAN interface driver can generate so called Error Message
|
||||||
that can optionally be passed to the user application in the same
|
Frames that can optionally be passed to the user application in the
|
||||||
way as other CAN frames. Whenever an error on the physical layer
|
same way as other CAN frames. Whenever an error on the physical layer
|
||||||
or the MAC layer is detected (e.g. by the CAN controller) the driver
|
or the MAC layer is detected (e.g. by the CAN controller) the driver
|
||||||
creates an appropriate error frame. Error frames can be requested by
|
creates an appropriate error message frame. Error messages frames can
|
||||||
the user application using the common CAN filter mechanisms. Inside
|
be requested by the user application using the common CAN filter
|
||||||
this filter definition the (interested) type of errors may be
|
mechanisms. Inside this filter definition the (interested) type of
|
||||||
selected. The reception of error frames is disabled by default.
|
errors may be selected. The reception of error messages is disabled
|
||||||
The format of the CAN error frame is briefly described in the Linux
|
by default. The format of the CAN error message frame is briefly
|
||||||
header file "include/linux/can/error.h".
|
described in the Linux header file "include/linux/can/error.h".
|
||||||
|
|
||||||
4. How to use Socket CAN
|
4. How to use Socket CAN
|
||||||
------------------------
|
------------------------
|
||||||
|
@ -383,7 +383,7 @@ solution for a couple of reasons:
|
||||||
defaults are set at RAW socket binding time:
|
defaults are set at RAW socket binding time:
|
||||||
|
|
||||||
- The filters are set to exactly one filter receiving everything
|
- The filters are set to exactly one filter receiving everything
|
||||||
- The socket only receives valid data frames (=> no error frames)
|
- The socket only receives valid data frames (=> no error message frames)
|
||||||
- The loopback of sent CAN frames is enabled (see chapter 3.2)
|
- The loopback of sent CAN frames is enabled (see chapter 3.2)
|
||||||
- The socket does not receive its own sent frames (in loopback mode)
|
- The socket does not receive its own sent frames (in loopback mode)
|
||||||
|
|
||||||
|
@ -434,7 +434,7 @@ solution for a couple of reasons:
|
||||||
4.1.2 RAW socket option CAN_RAW_ERR_FILTER
|
4.1.2 RAW socket option CAN_RAW_ERR_FILTER
|
||||||
|
|
||||||
As described in chapter 3.4 the CAN interface driver can generate so
|
As described in chapter 3.4 the CAN interface driver can generate so
|
||||||
called Error Frames that can optionally be passed to the user
|
called Error Message Frames that can optionally be passed to the user
|
||||||
application in the same way as other CAN frames. The possible
|
application in the same way as other CAN frames. The possible
|
||||||
errors are divided into different error classes that may be filtered
|
errors are divided into different error classes that may be filtered
|
||||||
using the appropriate error mask. To register for every possible
|
using the appropriate error mask. To register for every possible
|
||||||
|
@ -527,7 +527,7 @@ solution for a couple of reasons:
|
||||||
|
|
||||||
rcvlist_all - list for unfiltered entries (no filter operations)
|
rcvlist_all - list for unfiltered entries (no filter operations)
|
||||||
rcvlist_eff - list for single extended frame (EFF) entries
|
rcvlist_eff - list for single extended frame (EFF) entries
|
||||||
rcvlist_err - list for error frames masks
|
rcvlist_err - list for error message frames masks
|
||||||
rcvlist_fil - list for mask/value filters
|
rcvlist_fil - list for mask/value filters
|
||||||
rcvlist_inv - list for mask/value filters (inverse semantic)
|
rcvlist_inv - list for mask/value filters (inverse semantic)
|
||||||
rcvlist_sff - list for single standard frame (SFF) entries
|
rcvlist_sff - list for single standard frame (SFF) entries
|
||||||
|
@ -784,13 +784,13 @@ solution for a couple of reasons:
|
||||||
$ ip link set canX type can restart-ms 100
|
$ ip link set canX type can restart-ms 100
|
||||||
|
|
||||||
Alternatively, the application may realize the "bus-off" condition
|
Alternatively, the application may realize the "bus-off" condition
|
||||||
by monitoring CAN error frames and do a restart when appropriate with
|
by monitoring CAN error message frames and do a restart when
|
||||||
the command:
|
appropriate with the command:
|
||||||
|
|
||||||
$ ip link set canX type can restart
|
$ ip link set canX type can restart
|
||||||
|
|
||||||
Note that a restart will also create a CAN error frame (see also
|
Note that a restart will also create a CAN error message frame (see
|
||||||
chapter 3.4).
|
also chapter 3.4).
|
||||||
|
|
||||||
6.6 Supported CAN hardware
|
6.6 Supported CAN hardware
|
||||||
|
|
||||||
|
|
|
@ -1056,6 +1056,42 @@ static struct of_device_id flexcan_of_match[] = {
|
||||||
{},
|
{},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
#ifdef CONFIG_PM
|
||||||
|
static int flexcan_suspend(struct platform_device *pdev, pm_message_t state)
|
||||||
|
{
|
||||||
|
struct net_device *dev = platform_get_drvdata(pdev);
|
||||||
|
struct flexcan_priv *priv = netdev_priv(dev);
|
||||||
|
|
||||||
|
flexcan_chip_disable(priv);
|
||||||
|
|
||||||
|
if (netif_running(dev)) {
|
||||||
|
netif_stop_queue(dev);
|
||||||
|
netif_device_detach(dev);
|
||||||
|
}
|
||||||
|
priv->can.state = CAN_STATE_SLEEPING;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
static int flexcan_resume(struct platform_device *pdev)
|
||||||
|
{
|
||||||
|
struct net_device *dev = platform_get_drvdata(pdev);
|
||||||
|
struct flexcan_priv *priv = netdev_priv(dev);
|
||||||
|
|
||||||
|
priv->can.state = CAN_STATE_ERROR_ACTIVE;
|
||||||
|
if (netif_running(dev)) {
|
||||||
|
netif_device_attach(dev);
|
||||||
|
netif_start_queue(dev);
|
||||||
|
}
|
||||||
|
flexcan_chip_enable(priv);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
#else
|
||||||
|
#define flexcan_suspend NULL
|
||||||
|
#define flexcan_resume NULL
|
||||||
|
#endif
|
||||||
|
|
||||||
static struct platform_driver flexcan_driver = {
|
static struct platform_driver flexcan_driver = {
|
||||||
.driver = {
|
.driver = {
|
||||||
.name = DRV_NAME,
|
.name = DRV_NAME,
|
||||||
|
@ -1064,6 +1100,8 @@ static struct platform_driver flexcan_driver = {
|
||||||
},
|
},
|
||||||
.probe = flexcan_probe,
|
.probe = flexcan_probe,
|
||||||
.remove = __devexit_p(flexcan_remove),
|
.remove = __devexit_p(flexcan_remove),
|
||||||
|
.suspend = flexcan_suspend,
|
||||||
|
.resume = flexcan_resume,
|
||||||
};
|
};
|
||||||
|
|
||||||
module_platform_driver(flexcan_driver);
|
module_platform_driver(flexcan_driver);
|
||||||
|
|
|
@ -21,7 +21,7 @@
|
||||||
/* special address description flags for the CAN_ID */
|
/* special address description flags for the CAN_ID */
|
||||||
#define CAN_EFF_FLAG 0x80000000U /* EFF/SFF is set in the MSB */
|
#define CAN_EFF_FLAG 0x80000000U /* EFF/SFF is set in the MSB */
|
||||||
#define CAN_RTR_FLAG 0x40000000U /* remote transmission request */
|
#define CAN_RTR_FLAG 0x40000000U /* remote transmission request */
|
||||||
#define CAN_ERR_FLAG 0x20000000U /* error frame */
|
#define CAN_ERR_FLAG 0x20000000U /* error message frame */
|
||||||
|
|
||||||
/* valid bits in CAN ID for frame formats */
|
/* valid bits in CAN ID for frame formats */
|
||||||
#define CAN_SFF_MASK 0x000007FFU /* standard frame format (SFF) */
|
#define CAN_SFF_MASK 0x000007FFU /* standard frame format (SFF) */
|
||||||
|
@ -32,14 +32,14 @@
|
||||||
* Controller Area Network Identifier structure
|
* Controller Area Network Identifier structure
|
||||||
*
|
*
|
||||||
* bit 0-28 : CAN identifier (11/29 bit)
|
* bit 0-28 : CAN identifier (11/29 bit)
|
||||||
* bit 29 : error frame flag (0 = data frame, 1 = error frame)
|
* bit 29 : error message frame flag (0 = data frame, 1 = error message)
|
||||||
* bit 30 : remote transmission request flag (1 = rtr frame)
|
* bit 30 : remote transmission request flag (1 = rtr frame)
|
||||||
* bit 31 : frame format flag (0 = standard 11 bit, 1 = extended 29 bit)
|
* bit 31 : frame format flag (0 = standard 11 bit, 1 = extended 29 bit)
|
||||||
*/
|
*/
|
||||||
typedef __u32 canid_t;
|
typedef __u32 canid_t;
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Controller Area Network Error Frame Mask structure
|
* Controller Area Network Error Message Frame Mask structure
|
||||||
*
|
*
|
||||||
* bit 0-28 : error class mask (see include/linux/can/error.h)
|
* bit 0-28 : error class mask (see include/linux/can/error.h)
|
||||||
* bit 29-31 : set to zero
|
* bit 29-31 : set to zero
|
||||||
|
@ -97,7 +97,7 @@ struct sockaddr_can {
|
||||||
* <received_can_id> & mask == can_id & mask
|
* <received_can_id> & mask == can_id & mask
|
||||||
*
|
*
|
||||||
* The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can
|
* The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can
|
||||||
* filter for error frames (CAN_ERR_FLAG bit set in mask).
|
* filter for error message frames (CAN_ERR_FLAG bit set in mask).
|
||||||
*/
|
*/
|
||||||
struct can_filter {
|
struct can_filter {
|
||||||
canid_t can_id;
|
canid_t can_id;
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
/*
|
/*
|
||||||
* linux/can/error.h
|
* linux/can/error.h
|
||||||
*
|
*
|
||||||
* Definitions of the CAN error frame to be filtered and passed to the user.
|
* Definitions of the CAN error messages to be filtered and passed to the user.
|
||||||
*
|
*
|
||||||
* Author: Oliver Hartkopp <oliver.hartkopp@volkswagen.de>
|
* Author: Oliver Hartkopp <oliver.hartkopp@volkswagen.de>
|
||||||
* Copyright (c) 2002-2007 Volkswagen Group Electronic Research
|
* Copyright (c) 2002-2007 Volkswagen Group Electronic Research
|
||||||
|
@ -12,7 +12,7 @@
|
||||||
#ifndef CAN_ERROR_H
|
#ifndef CAN_ERROR_H
|
||||||
#define CAN_ERROR_H
|
#define CAN_ERROR_H
|
||||||
|
|
||||||
#define CAN_ERR_DLC 8 /* dlc for error frames */
|
#define CAN_ERR_DLC 8 /* dlc for error message frames */
|
||||||
|
|
||||||
/* error class (mask) in can_id */
|
/* error class (mask) in can_id */
|
||||||
#define CAN_ERR_TX_TIMEOUT 0x00000001U /* TX timeout (by netdevice driver) */
|
#define CAN_ERR_TX_TIMEOUT 0x00000001U /* TX timeout (by netdevice driver) */
|
||||||
|
|
|
@ -334,8 +334,8 @@ static struct dev_rcv_lists *find_dev_rcv_lists(struct net_device *dev)
|
||||||
* relevant bits for the filter.
|
* relevant bits for the filter.
|
||||||
*
|
*
|
||||||
* The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can
|
* The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can
|
||||||
* filter for error frames (CAN_ERR_FLAG bit set in mask). For error frames
|
* filter for error messages (CAN_ERR_FLAG bit set in mask). For error msg
|
||||||
* there is a special filterlist and a special rx path filter handling.
|
* frames there is a special filterlist and a special rx path filter handling.
|
||||||
*
|
*
|
||||||
* Return:
|
* Return:
|
||||||
* Pointer to optimal filterlist for the given can_id/mask pair.
|
* Pointer to optimal filterlist for the given can_id/mask pair.
|
||||||
|
@ -347,7 +347,7 @@ static struct hlist_head *find_rcv_list(canid_t *can_id, canid_t *mask,
|
||||||
{
|
{
|
||||||
canid_t inv = *can_id & CAN_INV_FILTER; /* save flag before masking */
|
canid_t inv = *can_id & CAN_INV_FILTER; /* save flag before masking */
|
||||||
|
|
||||||
/* filter for error frames in extra filterlist */
|
/* filter for error message frames in extra filterlist */
|
||||||
if (*mask & CAN_ERR_FLAG) {
|
if (*mask & CAN_ERR_FLAG) {
|
||||||
/* clear CAN_ERR_FLAG in filter entry */
|
/* clear CAN_ERR_FLAG in filter entry */
|
||||||
*mask &= CAN_ERR_MASK;
|
*mask &= CAN_ERR_MASK;
|
||||||
|
@ -408,7 +408,7 @@ static struct hlist_head *find_rcv_list(canid_t *can_id, canid_t *mask,
|
||||||
* <received_can_id> & mask == can_id & mask
|
* <received_can_id> & mask == can_id & mask
|
||||||
*
|
*
|
||||||
* The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can
|
* The filter can be inverted (CAN_INV_FILTER bit set in can_id) or it can
|
||||||
* filter for error frames (CAN_ERR_FLAG bit set in mask).
|
* filter for error message frames (CAN_ERR_FLAG bit set in mask).
|
||||||
*
|
*
|
||||||
* The provided pointer to the sk_buff is guaranteed to be valid as long as
|
* The provided pointer to the sk_buff is guaranteed to be valid as long as
|
||||||
* the callback function is running. The callback function must *not* free
|
* the callback function is running. The callback function must *not* free
|
||||||
|
@ -578,7 +578,7 @@ static int can_rcv_filter(struct dev_rcv_lists *d, struct sk_buff *skb)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
if (can_id & CAN_ERR_FLAG) {
|
if (can_id & CAN_ERR_FLAG) {
|
||||||
/* check for error frame entries only */
|
/* check for error message frame entries only */
|
||||||
hlist_for_each_entry_rcu(r, n, &d->rx[RX_ERR], list) {
|
hlist_for_each_entry_rcu(r, n, &d->rx[RX_ERR], list) {
|
||||||
if (can_id & r->mask) {
|
if (can_id & r->mask) {
|
||||||
deliver(skb, r);
|
deliver(skb, r);
|
||||||
|
|
Loading…
Reference in a new issue