linux-can-fixes-for-4.2-20150712
-----BEGIN PGP SIGNATURE----- iQEcBAABCgAGBQJVorxbAAoJEP5prqPJtc/H5zgH/2nvkmT3aQ1gBKdU8L+Ten5D LIKYyDJ67agNoMfEC/5xWOm7P3X8Qi8cGc326/9AZE22QLE5x6fMCq/SmEC4MA25 GKu2ocwosdPVhIDQOY33IYZHxxtV8UZjt5KdNbQnNO6+iqE6tX5CbgueMlcWusry WmPCOlezTqHydXo0TYYLPjmqJ66RlrQMWYKvcB0SaxLYQfkBGbkW+fei3wdE4kW1 t7cocRj6Ievv59wCeF+G+fpviTVQVR5bknGA0J3lku9onATOYfdArEAD9FRajygG KhA/eNr0YEA40VO/baUInuEAJ/YvDqdk9LoyJ1DOXgUv1ysxYSxu/44G/IcZsOU= =+zVD -----END PGP SIGNATURE----- Merge tag 'linux-can-fixes-for-4.2-20150712' of git://git.kernel.org/pub/scm/linux/kernel/git/mkl/linux-can Marc Kleine-Budde says: ==================== pull-request: can 2015-07-12 this is a pull request of 8 patchs for net/master. Sergei Shtylyov contributes 5 patches for the rcar_can driver, fixing the IRQ check and several info and error messages. There are two patches by J.D. Schroeder and Roger Quadros for the c_can driver and dra7x-evm device tree, which precent a glitch in the DCAN1 pinmux. Oliver Hartkopp provides a better approach to make the CAN skbs unique, the timestamp is replaced by a counter. ==================== Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
Коммит
cee9f6d018
|
@ -686,7 +686,8 @@
|
|||
|
||||
&dcan1 {
|
||||
status = "ok";
|
||||
pinctrl-names = "default", "sleep";
|
||||
pinctrl-0 = <&dcan1_pins_default>;
|
||||
pinctrl-names = "default", "sleep", "active";
|
||||
pinctrl-0 = <&dcan1_pins_sleep>;
|
||||
pinctrl-1 = <&dcan1_pins_sleep>;
|
||||
pinctrl-2 = <&dcan1_pins_default>;
|
||||
};
|
||||
|
|
|
@ -587,9 +587,10 @@
|
|||
|
||||
&dcan1 {
|
||||
status = "ok";
|
||||
pinctrl-names = "default", "sleep";
|
||||
pinctrl-0 = <&dcan1_pins_default>;
|
||||
pinctrl-names = "default", "sleep", "active";
|
||||
pinctrl-0 = <&dcan1_pins_sleep>;
|
||||
pinctrl-1 = <&dcan1_pins_sleep>;
|
||||
pinctrl-2 = <&dcan1_pins_default>;
|
||||
};
|
||||
|
||||
&qspi {
|
||||
|
|
|
@ -592,6 +592,7 @@ static int c_can_start(struct net_device *dev)
|
|||
{
|
||||
struct c_can_priv *priv = netdev_priv(dev);
|
||||
int err;
|
||||
struct pinctrl *p;
|
||||
|
||||
/* basic c_can configuration */
|
||||
err = c_can_chip_config(dev);
|
||||
|
@ -604,8 +605,13 @@ static int c_can_start(struct net_device *dev)
|
|||
|
||||
priv->can.state = CAN_STATE_ERROR_ACTIVE;
|
||||
|
||||
/* activate pins */
|
||||
pinctrl_pm_select_default_state(dev->dev.parent);
|
||||
/* Attempt to use "active" if available else use "default" */
|
||||
p = pinctrl_get_select(priv->device, "active");
|
||||
if (!IS_ERR(p))
|
||||
pinctrl_put(p);
|
||||
else
|
||||
pinctrl_pm_select_default_state(priv->device);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -440,9 +440,6 @@ unsigned int can_get_echo_skb(struct net_device *dev, unsigned int idx)
|
|||
struct can_frame *cf = (struct can_frame *)skb->data;
|
||||
u8 dlc = cf->can_dlc;
|
||||
|
||||
if (!(skb->tstamp.tv64))
|
||||
__net_timestamp(skb);
|
||||
|
||||
netif_rx(priv->echo_skb[idx]);
|
||||
priv->echo_skb[idx] = NULL;
|
||||
|
||||
|
@ -578,7 +575,6 @@ struct sk_buff *alloc_can_skb(struct net_device *dev, struct can_frame **cf)
|
|||
if (unlikely(!skb))
|
||||
return NULL;
|
||||
|
||||
__net_timestamp(skb);
|
||||
skb->protocol = htons(ETH_P_CAN);
|
||||
skb->pkt_type = PACKET_BROADCAST;
|
||||
skb->ip_summed = CHECKSUM_UNNECESSARY;
|
||||
|
@ -589,6 +585,7 @@ struct sk_buff *alloc_can_skb(struct net_device *dev, struct can_frame **cf)
|
|||
|
||||
can_skb_reserve(skb);
|
||||
can_skb_prv(skb)->ifindex = dev->ifindex;
|
||||
can_skb_prv(skb)->skbcnt = 0;
|
||||
|
||||
*cf = (struct can_frame *)skb_put(skb, sizeof(struct can_frame));
|
||||
memset(*cf, 0, sizeof(struct can_frame));
|
||||
|
@ -607,7 +604,6 @@ struct sk_buff *alloc_canfd_skb(struct net_device *dev,
|
|||
if (unlikely(!skb))
|
||||
return NULL;
|
||||
|
||||
__net_timestamp(skb);
|
||||
skb->protocol = htons(ETH_P_CANFD);
|
||||
skb->pkt_type = PACKET_BROADCAST;
|
||||
skb->ip_summed = CHECKSUM_UNNECESSARY;
|
||||
|
@ -618,6 +614,7 @@ struct sk_buff *alloc_canfd_skb(struct net_device *dev,
|
|||
|
||||
can_skb_reserve(skb);
|
||||
can_skb_prv(skb)->ifindex = dev->ifindex;
|
||||
can_skb_prv(skb)->skbcnt = 0;
|
||||
|
||||
*cfd = (struct canfd_frame *)skb_put(skb, sizeof(struct canfd_frame));
|
||||
memset(*cfd, 0, sizeof(struct canfd_frame));
|
||||
|
|
|
@ -508,7 +508,8 @@ static int rcar_can_open(struct net_device *ndev)
|
|||
|
||||
err = clk_prepare_enable(priv->clk);
|
||||
if (err) {
|
||||
netdev_err(ndev, "failed to enable periperal clock, error %d\n",
|
||||
netdev_err(ndev,
|
||||
"failed to enable peripheral clock, error %d\n",
|
||||
err);
|
||||
goto out;
|
||||
}
|
||||
|
@ -526,7 +527,8 @@ static int rcar_can_open(struct net_device *ndev)
|
|||
napi_enable(&priv->napi);
|
||||
err = request_irq(ndev->irq, rcar_can_interrupt, 0, ndev->name, ndev);
|
||||
if (err) {
|
||||
netdev_err(ndev, "error requesting interrupt %x\n", ndev->irq);
|
||||
netdev_err(ndev, "request_irq(%d) failed, error %d\n",
|
||||
ndev->irq, err);
|
||||
goto out_close;
|
||||
}
|
||||
can_led_event(ndev, CAN_LED_EVENT_OPEN);
|
||||
|
@ -758,8 +760,9 @@ static int rcar_can_probe(struct platform_device *pdev)
|
|||
}
|
||||
|
||||
irq = platform_get_irq(pdev, 0);
|
||||
if (!irq) {
|
||||
if (irq < 0) {
|
||||
dev_err(&pdev->dev, "No IRQ resource\n");
|
||||
err = irq;
|
||||
goto fail;
|
||||
}
|
||||
|
||||
|
@ -782,7 +785,8 @@ static int rcar_can_probe(struct platform_device *pdev)
|
|||
priv->clk = devm_clk_get(&pdev->dev, "clkp1");
|
||||
if (IS_ERR(priv->clk)) {
|
||||
err = PTR_ERR(priv->clk);
|
||||
dev_err(&pdev->dev, "cannot get peripheral clock: %d\n", err);
|
||||
dev_err(&pdev->dev, "cannot get peripheral clock, error %d\n",
|
||||
err);
|
||||
goto fail_clk;
|
||||
}
|
||||
|
||||
|
@ -794,7 +798,7 @@ static int rcar_can_probe(struct platform_device *pdev)
|
|||
priv->can_clk = devm_clk_get(&pdev->dev, clock_names[clock_select]);
|
||||
if (IS_ERR(priv->can_clk)) {
|
||||
err = PTR_ERR(priv->can_clk);
|
||||
dev_err(&pdev->dev, "cannot get CAN clock: %d\n", err);
|
||||
dev_err(&pdev->dev, "cannot get CAN clock, error %d\n", err);
|
||||
goto fail_clk;
|
||||
}
|
||||
|
||||
|
@ -823,7 +827,7 @@ static int rcar_can_probe(struct platform_device *pdev)
|
|||
|
||||
devm_can_led_init(ndev);
|
||||
|
||||
dev_info(&pdev->dev, "device registered (reg_base=%p, irq=%u)\n",
|
||||
dev_info(&pdev->dev, "device registered (regs @ %p, IRQ%d)\n",
|
||||
priv->regs, ndev->irq);
|
||||
|
||||
return 0;
|
||||
|
|
|
@ -207,7 +207,6 @@ static void slc_bump(struct slcan *sl)
|
|||
if (!skb)
|
||||
return;
|
||||
|
||||
__net_timestamp(skb);
|
||||
skb->dev = sl->dev;
|
||||
skb->protocol = htons(ETH_P_CAN);
|
||||
skb->pkt_type = PACKET_BROADCAST;
|
||||
|
@ -215,6 +214,7 @@ static void slc_bump(struct slcan *sl)
|
|||
|
||||
can_skb_reserve(skb);
|
||||
can_skb_prv(skb)->ifindex = sl->dev->ifindex;
|
||||
can_skb_prv(skb)->skbcnt = 0;
|
||||
|
||||
memcpy(skb_put(skb, sizeof(struct can_frame)),
|
||||
&cf, sizeof(struct can_frame));
|
||||
|
|
|
@ -78,9 +78,6 @@ static void vcan_rx(struct sk_buff *skb, struct net_device *dev)
|
|||
skb->dev = dev;
|
||||
skb->ip_summed = CHECKSUM_UNNECESSARY;
|
||||
|
||||
if (!(skb->tstamp.tv64))
|
||||
__net_timestamp(skb);
|
||||
|
||||
netif_rx_ni(skb);
|
||||
}
|
||||
|
||||
|
|
|
@ -27,10 +27,12 @@
|
|||
/**
|
||||
* struct can_skb_priv - private additional data inside CAN sk_buffs
|
||||
* @ifindex: ifindex of the first interface the CAN frame appeared on
|
||||
* @skbcnt: atomic counter to have an unique id together with skb pointer
|
||||
* @cf: align to the following CAN frame at skb->data
|
||||
*/
|
||||
struct can_skb_priv {
|
||||
int ifindex;
|
||||
int skbcnt;
|
||||
struct can_frame cf[0];
|
||||
};
|
||||
|
||||
|
|
|
@ -89,6 +89,8 @@ struct timer_list can_stattimer; /* timer for statistics update */
|
|||
struct s_stats can_stats; /* packet statistics */
|
||||
struct s_pstats can_pstats; /* receive list statistics */
|
||||
|
||||
static atomic_t skbcounter = ATOMIC_INIT(0);
|
||||
|
||||
/*
|
||||
* af_can socket functions
|
||||
*/
|
||||
|
@ -310,12 +312,8 @@ int can_send(struct sk_buff *skb, int loop)
|
|||
return err;
|
||||
}
|
||||
|
||||
if (newskb) {
|
||||
if (!(newskb->tstamp.tv64))
|
||||
__net_timestamp(newskb);
|
||||
|
||||
if (newskb)
|
||||
netif_rx_ni(newskb);
|
||||
}
|
||||
|
||||
/* update statistics */
|
||||
can_stats.tx_frames++;
|
||||
|
@ -683,6 +681,10 @@ static void can_receive(struct sk_buff *skb, struct net_device *dev)
|
|||
can_stats.rx_frames++;
|
||||
can_stats.rx_frames_delta++;
|
||||
|
||||
/* create non-zero unique skb identifier together with *skb */
|
||||
while (!(can_skb_prv(skb)->skbcnt))
|
||||
can_skb_prv(skb)->skbcnt = atomic_inc_return(&skbcounter);
|
||||
|
||||
rcu_read_lock();
|
||||
|
||||
/* deliver the packet to sockets listening on all devices */
|
||||
|
|
|
@ -261,6 +261,7 @@ static void bcm_can_tx(struct bcm_op *op)
|
|||
|
||||
can_skb_reserve(skb);
|
||||
can_skb_prv(skb)->ifindex = dev->ifindex;
|
||||
can_skb_prv(skb)->skbcnt = 0;
|
||||
|
||||
memcpy(skb_put(skb, CFSIZ), cf, CFSIZ);
|
||||
|
||||
|
@ -1217,6 +1218,7 @@ static int bcm_tx_send(struct msghdr *msg, int ifindex, struct sock *sk)
|
|||
}
|
||||
|
||||
can_skb_prv(skb)->ifindex = dev->ifindex;
|
||||
can_skb_prv(skb)->skbcnt = 0;
|
||||
skb->dev = dev;
|
||||
can_skb_set_owner(skb, sk);
|
||||
err = can_send(skb, 1); /* send with loopback */
|
||||
|
|
|
@ -75,7 +75,7 @@ MODULE_ALIAS("can-proto-1");
|
|||
*/
|
||||
|
||||
struct uniqframe {
|
||||
ktime_t tstamp;
|
||||
int skbcnt;
|
||||
const struct sk_buff *skb;
|
||||
unsigned int join_rx_count;
|
||||
};
|
||||
|
@ -133,7 +133,7 @@ static void raw_rcv(struct sk_buff *oskb, void *data)
|
|||
|
||||
/* eliminate multiple filter matches for the same skb */
|
||||
if (this_cpu_ptr(ro->uniq)->skb == oskb &&
|
||||
ktime_equal(this_cpu_ptr(ro->uniq)->tstamp, oskb->tstamp)) {
|
||||
this_cpu_ptr(ro->uniq)->skbcnt == can_skb_prv(oskb)->skbcnt) {
|
||||
if (ro->join_filters) {
|
||||
this_cpu_inc(ro->uniq->join_rx_count);
|
||||
/* drop frame until all enabled filters matched */
|
||||
|
@ -144,7 +144,7 @@ static void raw_rcv(struct sk_buff *oskb, void *data)
|
|||
}
|
||||
} else {
|
||||
this_cpu_ptr(ro->uniq)->skb = oskb;
|
||||
this_cpu_ptr(ro->uniq)->tstamp = oskb->tstamp;
|
||||
this_cpu_ptr(ro->uniq)->skbcnt = can_skb_prv(oskb)->skbcnt;
|
||||
this_cpu_ptr(ro->uniq)->join_rx_count = 1;
|
||||
/* drop first frame to check all enabled filters? */
|
||||
if (ro->join_filters && ro->count > 1)
|
||||
|
@ -749,6 +749,7 @@ static int raw_sendmsg(struct socket *sock, struct msghdr *msg, size_t size)
|
|||
|
||||
can_skb_reserve(skb);
|
||||
can_skb_prv(skb)->ifindex = dev->ifindex;
|
||||
can_skb_prv(skb)->skbcnt = 0;
|
||||
|
||||
err = memcpy_from_msg(skb_put(skb, size), msg, size);
|
||||
if (err < 0)
|
||||
|
|
Загрузка…
Ссылка в новой задаче