]> git.karo-electronics.de Git - karo-tx-linux.git/commitdiff
ENGR00288342 net:fec_ptp: fix the potential issue for storing timestamp
authorFugang Duan <B38611@freescale.com>
Mon, 18 Nov 2013 02:17:03 +0000 (10:17 +0800)
committerFugang Duan <B38611@freescale.com>
Mon, 18 Nov 2013 02:17:03 +0000 (10:17 +0800)
The timestamps generated in the i.MX drivers are generated by the
nanoseconds part coming from the 1588 clock. But the number of seconds
are maintained in a private structure of the interface. Those are
updated in a 1588 clock rollover interrupt.

The timestamp is generated right before a rollover of a second and the
timestamp value is constructed afterwards. Therefore the bigger part of
the timestamp is wrong (the second).

Suggested solution (pseudo-code):
If( actual-time.nsec < timestamp.nsec )
Timestamp.sec = fpp->prtc -1;
Else
Timestamp.sec = fpp->prtc;

Signed-off-by: Fugang Duan <B38611@freescale.com>
drivers/net/ethernet/freescale/fec_ptp.c

index 33f73df95b44b54c03949c340ec0f78f74fe84ad..2d6997bea89a58d5e4326b8c4bb24ece246d62f6 100644 (file)
@@ -362,6 +362,7 @@ void fec_ptp_store_txstamp(struct fec_enet_private *priv,
 {
        struct fec_ptp_ts_data tmp_tx_time;
        struct bufdesc_ex *bdp_ex = NULL;
+       struct ptp_rtc_time curr_time;
        u8 *ptp_loc;
        u16 eth_type;
 
@@ -389,7 +390,11 @@ void fec_ptp_store_txstamp(struct fec_enet_private *priv,
                memcpy(tmp_tx_time.ident.spid, &ptp_loc[PTP_SPID_OFFS],
                                                PTP_SOURCE_PORT_LENGTH);
                /* store tx timestamp */
-               tmp_tx_time.ts.sec = priv->prtc;
+               fec_get_curr_cnt(priv, &curr_time);
+               if (curr_time.rtc_time.nsec < bdp_ex->ts)
+                       tmp_tx_time.ts.sec = priv->prtc - 1;
+               else
+                       tmp_tx_time.ts.sec = priv->prtc;
                tmp_tx_time.ts.nsec = bdp_ex->ts;
                /* insert timestamp in circular buffer */
                fec_ptp_insert(&(priv->tx_timestamps), &tmp_tx_time);
@@ -402,6 +407,7 @@ void fec_ptp_store_rxstamp(struct fec_enet_private *priv,
 {
        struct fec_ptp_ts_data tmp_rx_time;
        struct bufdesc_ex *bdp_ex = NULL;
+       struct ptp_rtc_time curr_time;
        u8 *ptp_loc;
        u16 eth_type;
 
@@ -429,7 +435,11 @@ void fec_ptp_store_rxstamp(struct fec_enet_private *priv,
                memcpy(tmp_rx_time.ident.spid, &ptp_loc[PTP_SPID_OFFS],
                                                PTP_SOURCE_PORT_LENGTH);
                /* store rx timestamp */
-               tmp_rx_time.ts.sec = priv->prtc;
+               fec_get_curr_cnt(priv, &curr_time);
+               if (curr_time.rtc_time.nsec < bdp_ex->ts)
+                       tmp_rx_time.ts.sec = priv->prtc - 1;
+               else
+                       tmp_rx_time.ts.sec = priv->prtc;
                tmp_rx_time.ts.nsec = bdp_ex->ts;
 
                /* insert timestamp in circular buffer */