Commit cee9f6d0 authored by David S. Miller's avatar David S. Miller

Merge tag 'linux-can-fixes-for-4.2-20150712' of...

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: default avatarDavid S. Miller <davem@davemloft.net>
parents 76b63da9 d3b58c47
...@@ -686,7 +686,8 @@ &davinci_mdio { ...@@ -686,7 +686,8 @@ &davinci_mdio {
&dcan1 { &dcan1 {
status = "ok"; status = "ok";
pinctrl-names = "default", "sleep"; pinctrl-names = "default", "sleep", "active";
pinctrl-0 = <&dcan1_pins_default>; pinctrl-0 = <&dcan1_pins_sleep>;
pinctrl-1 = <&dcan1_pins_sleep>; pinctrl-1 = <&dcan1_pins_sleep>;
pinctrl-2 = <&dcan1_pins_default>;
}; };
...@@ -587,9 +587,10 @@ &davinci_mdio { ...@@ -587,9 +587,10 @@ &davinci_mdio {
&dcan1 { &dcan1 {
status = "ok"; status = "ok";
pinctrl-names = "default", "sleep"; pinctrl-names = "default", "sleep", "active";
pinctrl-0 = <&dcan1_pins_default>; pinctrl-0 = <&dcan1_pins_sleep>;
pinctrl-1 = <&dcan1_pins_sleep>; pinctrl-1 = <&dcan1_pins_sleep>;
pinctrl-2 = <&dcan1_pins_default>;
}; };
&qspi { &qspi {
......
...@@ -592,6 +592,7 @@ static int c_can_start(struct net_device *dev) ...@@ -592,6 +592,7 @@ static int c_can_start(struct net_device *dev)
{ {
struct c_can_priv *priv = netdev_priv(dev); struct c_can_priv *priv = netdev_priv(dev);
int err; int err;
struct pinctrl *p;
/* basic c_can configuration */ /* basic c_can configuration */
err = c_can_chip_config(dev); err = c_can_chip_config(dev);
...@@ -604,8 +605,13 @@ static int c_can_start(struct net_device *dev) ...@@ -604,8 +605,13 @@ static int c_can_start(struct net_device *dev)
priv->can.state = CAN_STATE_ERROR_ACTIVE; priv->can.state = CAN_STATE_ERROR_ACTIVE;
/* activate pins */ /* Attempt to use "active" if available else use "default" */
pinctrl_pm_select_default_state(dev->dev.parent); p = pinctrl_get_select(priv->device, "active");
if (!IS_ERR(p))
pinctrl_put(p);
else
pinctrl_pm_select_default_state(priv->device);
return 0; return 0;
} }
......
...@@ -440,9 +440,6 @@ unsigned int can_get_echo_skb(struct net_device *dev, unsigned int idx) ...@@ -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; struct can_frame *cf = (struct can_frame *)skb->data;
u8 dlc = cf->can_dlc; u8 dlc = cf->can_dlc;
if (!(skb->tstamp.tv64))
__net_timestamp(skb);
netif_rx(priv->echo_skb[idx]); netif_rx(priv->echo_skb[idx]);
priv->echo_skb[idx] = NULL; priv->echo_skb[idx] = NULL;
...@@ -578,7 +575,6 @@ struct sk_buff *alloc_can_skb(struct net_device *dev, struct can_frame **cf) ...@@ -578,7 +575,6 @@ struct sk_buff *alloc_can_skb(struct net_device *dev, struct can_frame **cf)
if (unlikely(!skb)) if (unlikely(!skb))
return NULL; return NULL;
__net_timestamp(skb);
skb->protocol = htons(ETH_P_CAN); skb->protocol = htons(ETH_P_CAN);
skb->pkt_type = PACKET_BROADCAST; skb->pkt_type = PACKET_BROADCAST;
skb->ip_summed = CHECKSUM_UNNECESSARY; skb->ip_summed = CHECKSUM_UNNECESSARY;
...@@ -589,6 +585,7 @@ struct sk_buff *alloc_can_skb(struct net_device *dev, struct can_frame **cf) ...@@ -589,6 +585,7 @@ struct sk_buff *alloc_can_skb(struct net_device *dev, struct can_frame **cf)
can_skb_reserve(skb); can_skb_reserve(skb);
can_skb_prv(skb)->ifindex = dev->ifindex; can_skb_prv(skb)->ifindex = dev->ifindex;
can_skb_prv(skb)->skbcnt = 0;
*cf = (struct can_frame *)skb_put(skb, sizeof(struct can_frame)); *cf = (struct can_frame *)skb_put(skb, sizeof(struct can_frame));
memset(*cf, 0, 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, ...@@ -607,7 +604,6 @@ struct sk_buff *alloc_canfd_skb(struct net_device *dev,
if (unlikely(!skb)) if (unlikely(!skb))
return NULL; return NULL;
__net_timestamp(skb);
skb->protocol = htons(ETH_P_CANFD); skb->protocol = htons(ETH_P_CANFD);
skb->pkt_type = PACKET_BROADCAST; skb->pkt_type = PACKET_BROADCAST;
skb->ip_summed = CHECKSUM_UNNECESSARY; skb->ip_summed = CHECKSUM_UNNECESSARY;
...@@ -618,6 +614,7 @@ struct sk_buff *alloc_canfd_skb(struct net_device *dev, ...@@ -618,6 +614,7 @@ struct sk_buff *alloc_canfd_skb(struct net_device *dev,
can_skb_reserve(skb); can_skb_reserve(skb);
can_skb_prv(skb)->ifindex = dev->ifindex; can_skb_prv(skb)->ifindex = dev->ifindex;
can_skb_prv(skb)->skbcnt = 0;
*cfd = (struct canfd_frame *)skb_put(skb, sizeof(struct canfd_frame)); *cfd = (struct canfd_frame *)skb_put(skb, sizeof(struct canfd_frame));
memset(*cfd, 0, sizeof(struct canfd_frame)); memset(*cfd, 0, sizeof(struct canfd_frame));
......
...@@ -508,7 +508,8 @@ static int rcar_can_open(struct net_device *ndev) ...@@ -508,7 +508,8 @@ static int rcar_can_open(struct net_device *ndev)
err = clk_prepare_enable(priv->clk); err = clk_prepare_enable(priv->clk);
if (err) { 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); err);
goto out; goto out;
} }
...@@ -526,7 +527,8 @@ static int rcar_can_open(struct net_device *ndev) ...@@ -526,7 +527,8 @@ static int rcar_can_open(struct net_device *ndev)
napi_enable(&priv->napi); napi_enable(&priv->napi);
err = request_irq(ndev->irq, rcar_can_interrupt, 0, ndev->name, ndev); err = request_irq(ndev->irq, rcar_can_interrupt, 0, ndev->name, ndev);
if (err) { 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; goto out_close;
} }
can_led_event(ndev, CAN_LED_EVENT_OPEN); can_led_event(ndev, CAN_LED_EVENT_OPEN);
...@@ -758,8 +760,9 @@ static int rcar_can_probe(struct platform_device *pdev) ...@@ -758,8 +760,9 @@ static int rcar_can_probe(struct platform_device *pdev)
} }
irq = platform_get_irq(pdev, 0); irq = platform_get_irq(pdev, 0);
if (!irq) { if (irq < 0) {
dev_err(&pdev->dev, "No IRQ resource\n"); dev_err(&pdev->dev, "No IRQ resource\n");
err = irq;
goto fail; goto fail;
} }
...@@ -782,7 +785,8 @@ static int rcar_can_probe(struct platform_device *pdev) ...@@ -782,7 +785,8 @@ static int rcar_can_probe(struct platform_device *pdev)
priv->clk = devm_clk_get(&pdev->dev, "clkp1"); priv->clk = devm_clk_get(&pdev->dev, "clkp1");
if (IS_ERR(priv->clk)) { if (IS_ERR(priv->clk)) {
err = PTR_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; goto fail_clk;
} }
...@@ -794,7 +798,7 @@ static int rcar_can_probe(struct platform_device *pdev) ...@@ -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]); priv->can_clk = devm_clk_get(&pdev->dev, clock_names[clock_select]);
if (IS_ERR(priv->can_clk)) { if (IS_ERR(priv->can_clk)) {
err = PTR_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; goto fail_clk;
} }
...@@ -823,7 +827,7 @@ static int rcar_can_probe(struct platform_device *pdev) ...@@ -823,7 +827,7 @@ static int rcar_can_probe(struct platform_device *pdev)
devm_can_led_init(ndev); 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); priv->regs, ndev->irq);
return 0; return 0;
......
...@@ -207,7 +207,6 @@ static void slc_bump(struct slcan *sl) ...@@ -207,7 +207,6 @@ static void slc_bump(struct slcan *sl)
if (!skb) if (!skb)
return; return;
__net_timestamp(skb);
skb->dev = sl->dev; skb->dev = sl->dev;
skb->protocol = htons(ETH_P_CAN); skb->protocol = htons(ETH_P_CAN);
skb->pkt_type = PACKET_BROADCAST; skb->pkt_type = PACKET_BROADCAST;
...@@ -215,6 +214,7 @@ static void slc_bump(struct slcan *sl) ...@@ -215,6 +214,7 @@ static void slc_bump(struct slcan *sl)
can_skb_reserve(skb); can_skb_reserve(skb);
can_skb_prv(skb)->ifindex = sl->dev->ifindex; can_skb_prv(skb)->ifindex = sl->dev->ifindex;
can_skb_prv(skb)->skbcnt = 0;
memcpy(skb_put(skb, sizeof(struct can_frame)), memcpy(skb_put(skb, sizeof(struct can_frame)),
&cf, 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) ...@@ -78,9 +78,6 @@ static void vcan_rx(struct sk_buff *skb, struct net_device *dev)
skb->dev = dev; skb->dev = dev;
skb->ip_summed = CHECKSUM_UNNECESSARY; skb->ip_summed = CHECKSUM_UNNECESSARY;
if (!(skb->tstamp.tv64))
__net_timestamp(skb);
netif_rx_ni(skb); netif_rx_ni(skb);
} }
......
...@@ -27,10 +27,12 @@ ...@@ -27,10 +27,12 @@
/** /**
* struct can_skb_priv - private additional data inside CAN sk_buffs * struct can_skb_priv - private additional data inside CAN sk_buffs
* @ifindex: ifindex of the first interface the CAN frame appeared on * @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 * @cf: align to the following CAN frame at skb->data
*/ */
struct can_skb_priv { struct can_skb_priv {
int ifindex; int ifindex;
int skbcnt;
struct can_frame cf[0]; struct can_frame cf[0];
}; };
......
...@@ -89,6 +89,8 @@ struct timer_list can_stattimer; /* timer for statistics update */ ...@@ -89,6 +89,8 @@ struct timer_list can_stattimer; /* timer for statistics update */
struct s_stats can_stats; /* packet statistics */ struct s_stats can_stats; /* packet statistics */
struct s_pstats can_pstats; /* receive list statistics */ struct s_pstats can_pstats; /* receive list statistics */
static atomic_t skbcounter = ATOMIC_INIT(0);
/* /*
* af_can socket functions * af_can socket functions
*/ */
...@@ -310,12 +312,8 @@ int can_send(struct sk_buff *skb, int loop) ...@@ -310,12 +312,8 @@ int can_send(struct sk_buff *skb, int loop)
return err; return err;
} }
if (newskb) { if (newskb)
if (!(newskb->tstamp.tv64))
__net_timestamp(newskb);
netif_rx_ni(newskb); netif_rx_ni(newskb);
}
/* update statistics */ /* update statistics */
can_stats.tx_frames++; can_stats.tx_frames++;
...@@ -683,6 +681,10 @@ static void can_receive(struct sk_buff *skb, struct net_device *dev) ...@@ -683,6 +681,10 @@ static void can_receive(struct sk_buff *skb, struct net_device *dev)
can_stats.rx_frames++; can_stats.rx_frames++;
can_stats.rx_frames_delta++; 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(); rcu_read_lock();
/* deliver the packet to sockets listening on all devices */ /* deliver the packet to sockets listening on all devices */
......
...@@ -261,6 +261,7 @@ static void bcm_can_tx(struct bcm_op *op) ...@@ -261,6 +261,7 @@ static void bcm_can_tx(struct bcm_op *op)
can_skb_reserve(skb); can_skb_reserve(skb);
can_skb_prv(skb)->ifindex = dev->ifindex; can_skb_prv(skb)->ifindex = dev->ifindex;
can_skb_prv(skb)->skbcnt = 0;
memcpy(skb_put(skb, CFSIZ), cf, CFSIZ); memcpy(skb_put(skb, CFSIZ), cf, CFSIZ);
...@@ -1217,6 +1218,7 @@ static int bcm_tx_send(struct msghdr *msg, int ifindex, struct sock *sk) ...@@ -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)->ifindex = dev->ifindex;
can_skb_prv(skb)->skbcnt = 0;
skb->dev = dev; skb->dev = dev;
can_skb_set_owner(skb, sk); can_skb_set_owner(skb, sk);
err = can_send(skb, 1); /* send with loopback */ err = can_send(skb, 1); /* send with loopback */
......
...@@ -75,7 +75,7 @@ MODULE_ALIAS("can-proto-1"); ...@@ -75,7 +75,7 @@ MODULE_ALIAS("can-proto-1");
*/ */
struct uniqframe { struct uniqframe {
ktime_t tstamp; int skbcnt;
const struct sk_buff *skb; const struct sk_buff *skb;
unsigned int join_rx_count; unsigned int join_rx_count;
}; };
...@@ -133,7 +133,7 @@ static void raw_rcv(struct sk_buff *oskb, void *data) ...@@ -133,7 +133,7 @@ static void raw_rcv(struct sk_buff *oskb, void *data)
/* eliminate multiple filter matches for the same skb */ /* eliminate multiple filter matches for the same skb */
if (this_cpu_ptr(ro->uniq)->skb == oskb && 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) { if (ro->join_filters) {
this_cpu_inc(ro->uniq->join_rx_count); this_cpu_inc(ro->uniq->join_rx_count);
/* drop frame until all enabled filters matched */ /* drop frame until all enabled filters matched */
...@@ -144,7 +144,7 @@ static void raw_rcv(struct sk_buff *oskb, void *data) ...@@ -144,7 +144,7 @@ static void raw_rcv(struct sk_buff *oskb, void *data)
} }
} else { } else {
this_cpu_ptr(ro->uniq)->skb = oskb; 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; this_cpu_ptr(ro->uniq)->join_rx_count = 1;
/* drop first frame to check all enabled filters? */ /* drop first frame to check all enabled filters? */
if (ro->join_filters && ro->count > 1) if (ro->join_filters && ro->count > 1)
...@@ -749,6 +749,7 @@ static int raw_sendmsg(struct socket *sock, struct msghdr *msg, size_t size) ...@@ -749,6 +749,7 @@ static int raw_sendmsg(struct socket *sock, struct msghdr *msg, size_t size)
can_skb_reserve(skb); can_skb_reserve(skb);
can_skb_prv(skb)->ifindex = dev->ifindex; can_skb_prv(skb)->ifindex = dev->ifindex;
can_skb_prv(skb)->skbcnt = 0;
err = memcpy_from_msg(skb_put(skb, size), msg, size); err = memcpy_from_msg(skb_put(skb, size), msg, size);
if (err < 0) if (err < 0)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment