timestamping.c (da733563be5a9da26fe81d9f007262d00b846e22) | timestamping.c (e62d2df084e2849edffb206559725fa81bb569a8) |
---|---|
1/* 2 * PTP 1588 clock support - support for timestamping in PHY devices 3 * 4 * Copyright (C) 2010 OMICRON electronics GmbH 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation; either version 2 of the License, or --- 9 unchanged lines hidden (view full) --- 18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 19 */ 20#include <linux/errqueue.h> 21#include <linux/phy.h> 22#include <linux/ptp_classify.h> 23#include <linux/skbuff.h> 24#include <linux/export.h> 25 | 1/* 2 * PTP 1588 clock support - support for timestamping in PHY devices 3 * 4 * Copyright (C) 2010 OMICRON electronics GmbH 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation; either version 2 of the License, or --- 9 unchanged lines hidden (view full) --- 18 * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 19 */ 20#include <linux/errqueue.h> 21#include <linux/phy.h> 22#include <linux/ptp_classify.h> 23#include <linux/skbuff.h> 24#include <linux/export.h> 25 |
26static struct sock_filter ptp_filter[] = { 27 PTP_FILTER 28}; | 26static struct sk_filter *ptp_insns __read_mostly; |
29 30static unsigned int classify(const struct sk_buff *skb) 31{ | 27 28static unsigned int classify(const struct sk_buff *skb) 29{ |
32 if (likely(skb->dev && 33 skb->dev->phydev && | 30 if (likely(skb->dev && skb->dev->phydev && |
34 skb->dev->phydev->drv)) | 31 skb->dev->phydev->drv)) |
35 return sk_run_filter(skb, ptp_filter); | 32 return SK_RUN_FILTER(ptp_insns, skb); |
36 else 37 return PTP_CLASS_NONE; 38} 39 40void skb_clone_tx_timestamp(struct sk_buff *skb) 41{ 42 struct phy_device *phydev; 43 struct sk_buff *clone; --- 11 unchanged lines hidden (view full) --- 55 case PTP_CLASS_V2_IPV4: 56 case PTP_CLASS_V2_IPV6: 57 case PTP_CLASS_V2_L2: 58 case PTP_CLASS_V2_VLAN: 59 phydev = skb->dev->phydev; 60 if (likely(phydev->drv->txtstamp)) { 61 if (!atomic_inc_not_zero(&sk->sk_refcnt)) 62 return; | 33 else 34 return PTP_CLASS_NONE; 35} 36 37void skb_clone_tx_timestamp(struct sk_buff *skb) 38{ 39 struct phy_device *phydev; 40 struct sk_buff *clone; --- 11 unchanged lines hidden (view full) --- 52 case PTP_CLASS_V2_IPV4: 53 case PTP_CLASS_V2_IPV6: 54 case PTP_CLASS_V2_L2: 55 case PTP_CLASS_V2_VLAN: 56 phydev = skb->dev->phydev; 57 if (likely(phydev->drv->txtstamp)) { 58 if (!atomic_inc_not_zero(&sk->sk_refcnt)) 59 return; |
60 |
|
63 clone = skb_clone(skb, GFP_ATOMIC); 64 if (!clone) { 65 sock_put(sk); 66 return; 67 } | 61 clone = skb_clone(skb, GFP_ATOMIC); 62 if (!clone) { 63 sock_put(sk); 64 return; 65 } |
66 |
|
68 clone->sk = sk; 69 phydev->drv->txtstamp(phydev, clone, type); 70 } 71 break; 72 default: 73 break; 74 } 75} --- 8 unchanged lines hidden (view full) --- 84 85 if (!hwtstamps) { 86 sock_put(sk); 87 kfree_skb(skb); 88 return; 89 } 90 91 *skb_hwtstamps(skb) = *hwtstamps; | 67 clone->sk = sk; 68 phydev->drv->txtstamp(phydev, clone, type); 69 } 70 break; 71 default: 72 break; 73 } 74} --- 8 unchanged lines hidden (view full) --- 83 84 if (!hwtstamps) { 85 sock_put(sk); 86 kfree_skb(skb); 87 return; 88 } 89 90 *skb_hwtstamps(skb) = *hwtstamps; |
91 |
|
92 serr = SKB_EXT_ERR(skb); 93 memset(serr, 0, sizeof(*serr)); 94 serr->ee.ee_errno = ENOMSG; 95 serr->ee.ee_origin = SO_EE_ORIGIN_TIMESTAMPING; 96 skb->sk = NULL; | 92 serr = SKB_EXT_ERR(skb); 93 memset(serr, 0, sizeof(*serr)); 94 serr->ee.ee_errno = ENOMSG; 95 serr->ee.ee_origin = SO_EE_ORIGIN_TIMESTAMPING; 96 skb->sk = NULL; |
97 |
|
97 err = sock_queue_err_skb(sk, skb); | 98 err = sock_queue_err_skb(sk, skb); |
99 |
|
98 sock_put(sk); 99 if (err) 100 kfree_skb(skb); 101} 102EXPORT_SYMBOL_GPL(skb_complete_tx_timestamp); 103 104bool skb_defer_rx_timestamp(struct sk_buff *skb) 105{ --- 24 unchanged lines hidden (view full) --- 130 } 131 132 return false; 133} 134EXPORT_SYMBOL_GPL(skb_defer_rx_timestamp); 135 136void __init skb_timestamping_init(void) 137{ | 100 sock_put(sk); 101 if (err) 102 kfree_skb(skb); 103} 104EXPORT_SYMBOL_GPL(skb_complete_tx_timestamp); 105 106bool skb_defer_rx_timestamp(struct sk_buff *skb) 107{ --- 24 unchanged lines hidden (view full) --- 132 } 133 134 return false; 135} 136EXPORT_SYMBOL_GPL(skb_defer_rx_timestamp); 137 138void __init skb_timestamping_init(void) 139{ |
138 BUG_ON(sk_chk_filter(ptp_filter, ARRAY_SIZE(ptp_filter))); | 140 static struct sock_filter ptp_filter[] = { PTP_FILTER }; 141 struct sock_fprog ptp_prog = { 142 .len = ARRAY_SIZE(ptp_filter), .filter = ptp_filter, 143 }; 144 145 BUG_ON(sk_unattached_filter_create(&ptp_insns, &ptp_prog)); |
139} | 146} |