lists.openwall.net   lists  /  announce  owl-users  owl-dev  john-users  john-dev  passwdqc-users  yescrypt  popa3d-users  /  oss-security  kernel-hardening  musl  sabotage  tlsify  passwords  /  crypt-dev  xvendor  /  Bugtraq  Full-Disclosure  linux-kernel  linux-netdev  linux-ext4  PHC 
Open Source and information security mailing list archives
 
Hash Suite: Windows password security audit tool. GUI, reports in PDF.
[<prev] [next>] [<thread-prev] [thread-next>] [day] [month] [year] [list]
Date:	Mon, 29 Sep 2014 02:13:52 +0000
From:	"fugang.duan@...escale.com" <fugang.duan@...escale.com>
To:	"luwei.zhou@...escale.com" <luwei.zhou@...escale.com>,
	"davem@...emloft.net" <davem@...emloft.net>,
	"richardcochran@...il.com" <richardcochran@...il.com>
CC:	"netdev@...r.kernel.org" <netdev@...r.kernel.org>,
	"shawn.guo@...aro.org" <shawn.guo@...aro.org>,
	"bhutchings@...arflare.com" <bhutchings@...arflare.com>,
	"Fabio.Estevam@...escale.com" <Fabio.Estevam@...escale.com>,
	"Frank.Li@...escale.com" <Frank.Li@...escale.com>,
	"stephen@...workplumber.org" <stephen@...workplumber.org>
Subject: RE: [PATCH v2 2/4] net: fec: ptp: Use hardware algorithm to adjust
 PTP counter.

From: Luwei Zhou <b45643@...escale.com> Sent: Sunday, September 28, 2014 12:20 PM + 0800
>To: davem@...emloft.net; richardcochran@...il.com
>Cc: netdev@...r.kernel.org; shawn.guo@...aro.org;
>bhutchings@...arflare.com; Estevam Fabio-R49496; Duan Fugang-B38611; Li
>Frank-B20596; stephen@...workplumber.org
>Subject: [PATCH v2 2/4] net: fec: ptp: Use hardware algorithm to adjust
>PTP counter.
>
>The FEC IP supports hardware adjustment for ptp timer. Refer to the
>description of ENET_ATCOR and ENET_ATINC registers in the spec about the
>hardware adjustment. This patch uses hardware support to adjust the ptp
>offset and frequency on the slave side.
>
>Signed-off-by: Luwei Zhou <b45643@...escale.com>
>Signed-off-by: Frank Li <Frank.Li@...escale.com>
>Signed-off-by: Fugang Duan <b38611@...escale.com>
>---
> drivers/net/ethernet/freescale/fec.h     |  3 ++
> drivers/net/ethernet/freescale/fec_ptp.c | 66 ++++++++++++++++++++++++++-
>-----
> 2 files changed, 57 insertions(+), 12 deletions(-)
>
>diff --git a/drivers/net/ethernet/freescale/fec.h
>b/drivers/net/ethernet/freescale/fec.h
>index 354a309..b2e263e 100644
>--- a/drivers/net/ethernet/freescale/fec.h
>+++ b/drivers/net/ethernet/freescale/fec.h
>@@ -482,6 +482,9 @@ struct fec_enet_private {
> 	unsigned int tx_pkts_itr;
> 	unsigned int tx_time_itr;
> 	unsigned int itr_clk_rate;
>+
>+	/* ptp clock period in ns*/
>+	unsigned int ptp_inc;
> };
>
> void fec_ptp_init(struct platform_device *pdev); diff --git
>a/drivers/net/ethernet/freescale/fec_ptp.c
>b/drivers/net/ethernet/freescale/fec_ptp.c
>index 8016bdd..036d956 100644
>--- a/drivers/net/ethernet/freescale/fec_ptp.c
>+++ b/drivers/net/ethernet/freescale/fec_ptp.c
>@@ -71,6 +71,7 @@
>
> #define FEC_CC_MULT	(1 << 31)
> #define FEC_COUNTER_PERIOD	(1 << 31)
>+#define FEC_T_NSEC_PER_SEC	(1000000000UL)

Don't need redefine it, use NSEC_PER_SEC instead.
> /**
>  * fec_ptp_read - read raw cycle counter (to be used by time counter)
>  * @cc: the cyclecounter structure
>@@ -145,32 +146,59 @@ void fec_ptp_start_cyclecounter(struct net_device
>*ndev)
>  */
> static int fec_ptp_adjfreq(struct ptp_clock_info *ptp, s32 ppb)  {
>-	u64 diff;
> 	unsigned long flags;
> 	int neg_adj = 0;
>-	u32 mult = FEC_CC_MULT;
>+	u32 i, tmp;
>+	u32 corr_inc, corr_period;
>+	u32 corr_ns;
>+	u64 lhs, rhs;
>
> 	struct fec_enet_private *fep =
> 	    container_of(ptp, struct fec_enet_private, ptp_caps);
>
>+	if (ppb == 0)
>+		return 0;
>+
> 	if (ppb < 0) {
> 		ppb = -ppb;
> 		neg_adj = 1;
> 	}
>
>-	diff = mult;
>-	diff *= ppb;
>-	diff = div_u64(diff, 1000000000ULL);
>+	/* In theory, corr_inc/corr_period = ppb/FEC_T_NSEC_PER_SEC;
>+	 * Try to find the corr_inc  between 1 to fep->ptp_inc to
>+	 * meet adjustment requirement.
>+	 */
>+	lhs = FEC_T_NSEC_PER_SEC;
>+	rhs = (u64)ppb * (u64)fep->ptp_inc;
>+	for (i = 1; i <= fep->ptp_inc; i++) {
>+		if (lhs >= rhs) {
>+			corr_inc = i;
>+			corr_period = div_u64(lhs, rhs);
>+			break;
>+		}
>+		lhs += FEC_T_NSEC_PER_SEC;
>+	}
>+	/* Not found? Set it to high value - double speed
>+	 * correct in every clock step.
>+	 */
>+	if (i > fep->ptp_inc) {
>+		corr_inc = fep->ptp_inc;
>+		corr_period = 1;
>+	}
>+
>+	if (neg_adj)
>+		corr_ns = fep->ptp_inc - corr_inc;
>+	else
>+		corr_ns = fep->ptp_inc + corr_inc;
>
> 	spin_lock_irqsave(&fep->tmreg_lock, flags);
>-	/*
>-	 * dummy read to set cycle_last in tc to now.
>-	 * So use adjusted mult to calculate when next call
>-	 * timercounter_read.
>-	 */
>-	timecounter_read(&fep->tc);
>
>-	fep->cc.mult = neg_adj ? mult - diff : mult + diff;
>+	tmp = readl(fep->hwp + FEC_ATIME_INC) & FEC_T_INC_MASK;
>+	tmp |= corr_ns << FEC_T_INC_CORR_OFFSET;
>+	writel(tmp, fep->hwp + FEC_ATIME_INC);
>+	writel(corr_period, fep->hwp + FEC_ATIME_CORR);
>+	/* dummy read to update the timer. */
>+	timecounter_read(&fep->tc);
>
> 	spin_unlock_irqrestore(&fep->tmreg_lock, flags);
>
>@@ -190,12 +218,19 @@ static int fec_ptp_adjtime(struct ptp_clock_info
>*ptp, s64 delta)
> 	    container_of(ptp, struct fec_enet_private, ptp_caps);
> 	unsigned long flags;
> 	u64 now;
>+	u32 counter;
>
> 	spin_lock_irqsave(&fep->tmreg_lock, flags);
>
> 	now = timecounter_read(&fep->tc);
> 	now += delta;
>
>+	/* Get the timer value based on adjusted timestamp.
>+	 * Update the counter with the masked value.
>+	 */
>+	counter = now & fep->cc.mask;
>+	writel(counter, fep->hwp + FEC_ATIME);
>+
> 	/* reset the timecounter */
> 	timecounter_init(&fep->tc, &fep->cc, now);
>
>@@ -246,6 +281,7 @@ static int fec_ptp_settime(struct ptp_clock_info *ptp,
>
> 	u64 ns;
> 	unsigned long flags;
>+	u32 counter;
>
> 	mutex_lock(&fep->ptp_clk_mutex);
> 	/* Check the ptp clock */
>@@ -256,8 +292,13 @@ static int fec_ptp_settime(struct ptp_clock_info *ptp,
>
> 	ns = ts->tv_sec * 1000000000ULL;
> 	ns += ts->tv_nsec;
>+	/* Get the timer value based on timestamp.
>+	 * Update the counter with the masked value.
>+	 */
>+	counter = ns & fep->cc.mask;
>
> 	spin_lock_irqsave(&fep->tmreg_lock, flags);
>+	writel(counter, fep->hwp + FEC_ATIME);
> 	timecounter_init(&fep->tc, &fep->cc, ns);
> 	spin_unlock_irqrestore(&fep->tmreg_lock, flags);
> 	mutex_unlock(&fep->ptp_clk_mutex);
>@@ -396,6 +437,7 @@ void fec_ptp_init(struct platform_device *pdev)
> 	fep->ptp_caps.enable = fec_ptp_enable;
>
> 	fep->cycle_speed = clk_get_rate(fep->clk_ptp);
>+	fep->ptp_inc = FEC_T_NSEC_PER_SEC / fep->cycle_speed;
>
> 	spin_lock_init(&fep->tmreg_lock);
>
>--
>1.9.1

Regards,
Andy
--
To unsubscribe from this list: send the line "unsubscribe netdev" in
the body of a message to majordomo@...r.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html

Powered by blists - more mailing lists