Re: [PATCH net-next 7/8] net: eth: altera: tse: add msgdma prefetcher

2018-11-27 Thread Dalon Westergreen
On Fri, 2018-11-16 at 09:20 -0600, Thor Thayer wrote:
> Hi Dalon,
> 
> Just a few comments/questions.
> 
> On 11/14/18 6:50 PM, Dalon Westergreen wrote:
> > From: Dalon Westergreen 
> > 
> > Add support for the mSGDMA prefetcher.  The prefetcher adds support
> > for a linked list of descriptors in system memory.  The prefetcher
> > feeds these to the mSGDMA dispatcher.
> > 
> > The prefetcher is configured to poll for the next descriptor in the
> > list to be owned by hardware, then pass the descriptor to the
> > dispatcher.  It will then poll the next descriptor until it is
> > owned by hardware.
> > 
> > The dispatcher responses are written back to the appropriate
> > descriptor, and the owned by hardware bit is cleared.
> > 
> > The driver sets up a linked list twice the tx and rx ring sizes,
> > with the last descriptor pointing back to the first.  This ensures
> > that the ring of descriptors will always have inactive descriptors
> > preventing the prefetcher from looping over and reusing descriptors
> > inappropriately.  The prefetcher will continuously loop over these
> > descriptors.  The driver modifies descriptors as required to update
> > the skb address and length as well as the owned by hardware bit.
> > 
> > In addition to the above, the mSGDMA prefetcher can be used to
> > handle rx and tx timestamps coming from the ethernet ip.  These
> > can be included in the prefetcher response in the descriptor.
> > 
> > Signed-off-by: Dalon Westergreen 
> > ---
> >   drivers/net/ethernet/altera/Makefile  |   2 +-
> >   .../altera/altera_msgdma_prefetcher.c | 433 ++
> >   .../altera/altera_msgdma_prefetcher.h |  30 ++
> >   .../altera/altera_msgdmahw_prefetcher.h   |  87 
> >   drivers/net/ethernet/altera/altera_tse.h  |  14 +
> >   drivers/net/ethernet/altera/altera_tse_main.c |  51 +++
> >   6 files changed, 616 insertions(+), 1 deletion(-)
> >   create mode 100644 drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
> >   create mode 100644 drivers/net/ethernet/altera/altera_msgdma_prefetcher.h
> >   create mode 100644
> > drivers/net/ethernet/altera/altera_msgdmahw_prefetcher.h
> > 
> > diff --git a/drivers/net/ethernet/altera/Makefile
> > b/drivers/net/ethernet/altera/Makefile
> > index ad80be42fa26..73b32876f126 100644
> > --- a/drivers/net/ethernet/altera/Makefile
> > +++ b/drivers/net/ethernet/altera/Makefile
> > @@ -5,4 +5,4 @@
> >   obj-$(CONFIG_ALTERA_TSE) += altera_tse.o
> >   altera_tse-objs := altera_tse_main.o altera_tse_ethtool.o \
> >altera_msgdma.o altera_sgdma.o altera_utils.o \
> > -  altera_ptp.o
> > +  altera_ptp.o altera_msgdma_prefetcher.o
> > diff --git a/drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
> > b/drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
> > new file mode 100644
> > index 0000..55b475e9e15b
> > --- /dev/null
> > +++ b/drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
> > @@ -0,0 +1,433 @@
> > +// SPDX-License-Identifier: GPL-2.0
> > +/* MSGDMA Prefetcher driver for Altera ethernet devices
> > + *
> > + * Copyright (C) 2018 Intel Corporation. All rights reserved.
> > + * Author(s):
> > + *   Dalon Westergreen 
> > + */
> > +
> > +#include 
> > +#include 
> > +#include 
> > +#include "altera_utils.h"
> > +#include "altera_tse.h"
> > +#include "altera_msgdma.h"
> > +#include "altera_msgdmahw.h"
> > +#include "altera_msgdma_prefetcher.h"
> > +#include "altera_msgdmahw_prefetcher.h"
> 
> These could be alphabetized - tse and utils at the end.

sure thing.

> > +
> > +int msgdma_pref_initialize(struct altera_tse_private *priv)
> > +{
> > +   int i;
> > +   struct msgdma_pref_extended_desc *rx_descs;
> > +   struct msgdma_pref_extended_desc *tx_descs;
> > +   dma_addr_t rx_descsphys;
> > +   dma_addr_t tx_descsphys;
> > +   u32 rx_ring_size;
> > +   u32 tx_ring_size;
> > +
> > +   priv->pref_rxdescphys = (dma_addr_t)0;
> > +   priv->pref_txdescphys = (dma_addr_t)0;
> > +
> > +   /* we need to allocate more pref descriptors than ringsize, for now
> > +* just double ringsize
> > +*/
> > +   rx_ring_size = priv->rx_ring_size * 2;
> > +   tx_ring_size = priv->tx_ring_size * 2;
> > +
> > +   /* The prefetcher requires the descriptors to be aligned to the

Re: [PATCH net-next 6/8] net: eth: altera: tse: add support for ptp and timestamping

2018-11-16 Thread Dalon Westergreen
On Thu, 2018-11-15 at 18:14 -0800, Richard Cochran wrote:
> On Thu, Nov 15, 2018 at 06:55:29AM -0800, Dalon Westergreen wrote:
> > I would prefer to keep altera just to be consistent with the altera_tse
> > stuff,
> > and i intend to reusethis code for a 10GbE driver, so perhaps altera_tod to
> > reference the fpga ip name?
> 
> So the IP core is called "tod"?  Really?

For naming, how about intel_fpga_tod ?

--dalon

> 
> Thanks,
> Richard



Re: [PATCH net-next 6/8] net: eth: altera: tse: add support for ptp and timestamping

2018-11-16 Thread Dalon Westergreen
On Thu, 2018-11-15 at 18:14 -0800, Richard Cochran wrote:
> On Thu, Nov 15, 2018 at 06:55:29AM -0800, Dalon Westergreen wrote:
> > Sure, I would like to keep the debugfs entries for disabling freq
> > correction,and
> > reading the current scaled_ppm value.  I intend to use these to tune
> > anexternal
> > vcxo.  If there is a better way to do this, please let me know.
> 
> Yes, there is.  The external VCXO should be a proper PHC.  Then, with
> a minor change to the linuxptp stack (already in the pipe), you can
> just use that.
> 
> You should not disable frequency correction in the driver.  Leave that
> decision to the user space PTP stack.

Good to know, thanks.

> 
> > I would prefer to keep altera just to be consistent with the altera_tse
> > stuff,
> > and i intend to reusethis code for a 10GbE driver, so perhaps altera_tod to
> > reference the fpga ip name?
> 
> So the IP core is called "tod"?  Really?

yes, i am afraid so. "Time of Day"

--dalon

> 
> Thanks,
> Richard



[PATCH net-next 5/8] net: eth: altera: tse: Move common functions to altera_utils

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

Move request_and_map and other shared functions to altera_utils. This
is the first step to moving common code out of tse specific code so
that it can be shared with future altera ethernet ip.

Signed-off-by: Dalon Westergreen 
---
 drivers/net/ethernet/altera/altera_tse.h  | 45 --
 .../net/ethernet/altera/altera_tse_ethtool.c  |  1 +
 drivers/net/ethernet/altera/altera_tse_main.c | 32 +
 drivers/net/ethernet/altera/altera_utils.c| 30 
 drivers/net/ethernet/altera/altera_utils.h| 46 +++
 5 files changed, 78 insertions(+), 76 deletions(-)

diff --git a/drivers/net/ethernet/altera/altera_tse.h 
b/drivers/net/ethernet/altera/altera_tse.h
index 7f246040135d..f435fb0eca90 100644
--- a/drivers/net/ethernet/altera/altera_tse.h
+++ b/drivers/net/ethernet/altera/altera_tse.h
@@ -500,49 +500,4 @@ struct altera_tse_private {
  */
 void altera_tse_set_ethtool_ops(struct net_device *);
 
-static inline
-u32 csrrd32(void __iomem *mac, size_t offs)
-{
-   void __iomem *paddr = (void __iomem *)((uintptr_t)mac + offs);
-   return readl(paddr);
-}
-
-static inline
-u16 csrrd16(void __iomem *mac, size_t offs)
-{
-   void __iomem *paddr = (void __iomem *)((uintptr_t)mac + offs);
-   return readw(paddr);
-}
-
-static inline
-u8 csrrd8(void __iomem *mac, size_t offs)
-{
-   void __iomem *paddr = (void __iomem *)((uintptr_t)mac + offs);
-   return readb(paddr);
-}
-
-static inline
-void csrwr32(u32 val, void __iomem *mac, size_t offs)
-{
-   void __iomem *paddr = (void __iomem *)((uintptr_t)mac + offs);
-
-   writel(val, paddr);
-}
-
-static inline
-void csrwr16(u16 val, void __iomem *mac, size_t offs)
-{
-   void __iomem *paddr = (void __iomem *)((uintptr_t)mac + offs);
-
-   writew(val, paddr);
-}
-
-static inline
-void csrwr8(u8 val, void __iomem *mac, size_t offs)
-{
-   void __iomem *paddr = (void __iomem *)((uintptr_t)mac + offs);
-
-   writeb(val, paddr);
-}
-
 #endif /* __ALTERA_TSE_H__ */
diff --git a/drivers/net/ethernet/altera/altera_tse_ethtool.c 
b/drivers/net/ethernet/altera/altera_tse_ethtool.c
index 7c367713c3e6..2998655ab316 100644
--- a/drivers/net/ethernet/altera/altera_tse_ethtool.c
+++ b/drivers/net/ethernet/altera/altera_tse_ethtool.c
@@ -33,6 +33,7 @@
 #include 
 
 #include "altera_tse.h"
+#include "altera_utils.h"
 
 #define TSE_STATS_LEN  31
 #define TSE_NUM_REGS   128
diff --git a/drivers/net/ethernet/altera/altera_tse_main.c 
b/drivers/net/ethernet/altera/altera_tse_main.c
index f6b6a14b1ce9..b25d03506470 100644
--- a/drivers/net/ethernet/altera/altera_tse_main.c
+++ b/drivers/net/ethernet/altera/altera_tse_main.c
@@ -34,7 +34,6 @@
 #include 
 #include 
 #include 
-#include 
 #include 
 #include 
 #include 
@@ -44,7 +43,7 @@
 #include 
 #include 
 #include 
-#include 
+#include 
 #include 
 #include 
 
@@ -1332,35 +1331,6 @@ static struct net_device_ops altera_tse_netdev_ops = {
.ndo_validate_addr  = eth_validate_addr,
 };
 
-static int request_and_map(struct platform_device *pdev, const char *name,
-  struct resource **res, void __iomem **ptr)
-{
-   struct resource *region;
-   struct device *device = >dev;
-
-   *res = platform_get_resource_byname(pdev, IORESOURCE_MEM, name);
-   if (*res == NULL) {
-   dev_err(device, "resource %s not defined\n", name);
-   return -ENODEV;
-   }
-
-   region = devm_request_mem_region(device, (*res)->start,
-resource_size(*res), dev_name(device));
-   if (region == NULL) {
-   dev_err(device, "unable to request %s\n", name);
-   return -EBUSY;
-   }
-
-   *ptr = devm_ioremap_nocache(device, region->start,
-   resource_size(region));
-   if (*ptr == NULL) {
-   dev_err(device, "ioremap_nocache of %s failed!", name);
-   return -ENOMEM;
-   }
-
-   return 0;
-}
-
 /* Probe Altera TSE MAC device
  */
 static int altera_tse_probe(struct platform_device *pdev)
diff --git a/drivers/net/ethernet/altera/altera_utils.c 
b/drivers/net/ethernet/altera/altera_utils.c
index d7eeb1713ad2..bc33b7f0b0c5 100644
--- a/drivers/net/ethernet/altera/altera_utils.c
+++ b/drivers/net/ethernet/altera/altera_utils.c
@@ -42,3 +42,33 @@ int tse_bit_is_clear(void __iomem *ioaddr, size_t offs, u32 
bit_mask)
u32 value = csrrd32(ioaddr, offs);
return (value & bit_mask) ? 0 : 1;
 }
+
+int request_and_map(struct platform_device *pdev, const char *name,
+   struct resource **res, void __iomem **ptr)
+{
+   struct resource *region;
+   struct device *device = >dev;
+
+   *res = platform_get_resource_byname(pdev, IORESOURCE_MEM, name);
+   if (!*res) {
+   dev_err(device, "resource %s not define

[PATCH net-next 8/8] net: eth: altera: tse: update devicetree bindings documentation

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

Update devicetree bindings documentation to include msgdma
prefetcher and ptp bindings.

Signed-off-by: Dalon Westergreen 
---
 .../devicetree/bindings/net/altera_tse.txt| 98 +++
 1 file changed, 79 insertions(+), 19 deletions(-)

diff --git a/Documentation/devicetree/bindings/net/altera_tse.txt 
b/Documentation/devicetree/bindings/net/altera_tse.txt
index 0e21df94a53f..d35806942a8f 100644
--- a/Documentation/devicetree/bindings/net/altera_tse.txt
+++ b/Documentation/devicetree/bindings/net/altera_tse.txt
@@ -2,50 +2,79 @@
 
 Required properties:
 - compatible: Should be "altr,tse-1.0" for legacy SGDMA based TSE, and should
-   be "altr,tse-msgdma-1.0" for the preferred MSGDMA based TSE.
+   be "altr,tse-msgdma-1.0" for the preferred MSGDMA based TSE,
+   and "altr,tse-msgdma-2.0" for MSGDMA with prefetcher based
+   implementations.
ALTR is supported for legacy device trees, but is deprecated.
altr should be used for all new designs.
 - reg: Address and length of the register set for the device. It contains
   the information of registers in the same order as described by reg-names
 - reg-names: Should contain the reg names
-  "control_port": MAC configuration space region
-  "tx_csr":   xDMA Tx dispatcher control and status space region
-  "tx_desc":  MSGDMA Tx dispatcher descriptor space region
-  "rx_csr" :  xDMA Rx dispatcher control and status space region
-  "rx_desc":  MSGDMA Rx dispatcher descriptor space region
-  "rx_resp":  MSGDMA Rx dispatcher response space region
-  "s1":  SGDMA descriptor memory
 - interrupts: Should contain the TSE interrupts and it's mode.
 - interrupt-names: Should contain the interrupt names
-  "rx_irq":   xDMA Rx dispatcher interrupt
-  "tx_irq":   xDMA Tx dispatcher interrupt
+  "rx_irq":   DMA Rx dispatcher interrupt
+  "tx_irq":   DMA Tx dispatcher interrupt
 - rx-fifo-depth: MAC receive FIFO buffer depth in bytes
 - tx-fifo-depth: MAC transmit FIFO buffer depth in bytes
 - phy-mode: See ethernet.txt in the same directory.
 - phy-handle: See ethernet.txt in the same directory.
 - phy-addr: See ethernet.txt in the same directory. A configuration should
include phy-handle or phy-addr.
-- altr,has-supplementary-unicast:
-   If present, TSE supports additional unicast addresses.
-   Otherwise additional unicast addresses are not supported.
-- altr,has-hash-multicast-filter:
-   If present, TSE supports a hash based multicast filter.
-   Otherwise, hash-based multicast filtering is not supported.
-
 - mdio device tree subnode: When the TSE has a phy connected to its local
mdio, there must be device tree subnode with the following
required properties:
-
- compatible: Must be "altr,tse-mdio".
- #address-cells: Must be <1>.
- #size-cells: Must be <0>.
 
For each phy on the mdio bus, there must be a node with the following
fields:
-
- reg: phy id used to communicate to phy.
- device_type: Must be "ethernet-phy".
 
+- altr,has-supplementary-unicast:
+   If present, TSE supports additional unicast addresses.
+   Otherwise additional unicast addresses are not supported.
+- altr,has-hash-multicast-filter:
+   If present, TSE supports a hash based multicast filter.
+   Otherwise, hash-based multicast filtering is not supported.
+- altr,has-ptp:
+   If present, TSE supports 1588 timestamping.  Currently only
+   supported with the msgdma prefetcher.
+- altr,tx-poll-cnt:
+   Optional cycle count for Tx prefetcher to poll descriptor
+   list.  If not present, defaults to 128, which at 125MHz is
+   roughly 1usec. Only for "altr,tse-msgdma-2.0".
+- altr,rx-poll-cnt:
+   Optional cycle count for Tx prefetcher to poll descriptor
+   list.  If not present, defaults to 128, which at 125MHz is
+   roughly 1usec. Only for "altr,tse-msgdma-2.0".
+
+Required registers by compatibility string:
+ - "altr,tse-1.0"
+   "control_port": MAC configuration space region
+   "tx_csr":   DMA Tx dispatcher control and status space region
+   "rx_csr" :  DMA Rx dispatcher control and status space region
+   "s1":   DMA descriptor memory
+
+ - "altr,tse-msgdma-1.0"
+   "control_port": MAC configuration space region
+   "tx_csr":   DMA Tx dispatcher control and status space region
+   "tx_desc":  DMA

[PATCH net-next 7/8] net: eth: altera: tse: add msgdma prefetcher

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

Add support for the mSGDMA prefetcher.  The prefetcher adds support
for a linked list of descriptors in system memory.  The prefetcher
feeds these to the mSGDMA dispatcher.

The prefetcher is configured to poll for the next descriptor in the
list to be owned by hardware, then pass the descriptor to the
dispatcher.  It will then poll the next descriptor until it is
owned by hardware.

The dispatcher responses are written back to the appropriate
descriptor, and the owned by hardware bit is cleared.

The driver sets up a linked list twice the tx and rx ring sizes,
with the last descriptor pointing back to the first.  This ensures
that the ring of descriptors will always have inactive descriptors
preventing the prefetcher from looping over and reusing descriptors
inappropriately.  The prefetcher will continuously loop over these
descriptors.  The driver modifies descriptors as required to update
the skb address and length as well as the owned by hardware bit.

In addition to the above, the mSGDMA prefetcher can be used to
handle rx and tx timestamps coming from the ethernet ip.  These
can be included in the prefetcher response in the descriptor.

Signed-off-by: Dalon Westergreen 
---
 drivers/net/ethernet/altera/Makefile  |   2 +-
 .../altera/altera_msgdma_prefetcher.c | 433 ++
 .../altera/altera_msgdma_prefetcher.h |  30 ++
 .../altera/altera_msgdmahw_prefetcher.h   |  87 
 drivers/net/ethernet/altera/altera_tse.h  |  14 +
 drivers/net/ethernet/altera/altera_tse_main.c |  51 +++
 6 files changed, 616 insertions(+), 1 deletion(-)
 create mode 100644 drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
 create mode 100644 drivers/net/ethernet/altera/altera_msgdma_prefetcher.h
 create mode 100644 drivers/net/ethernet/altera/altera_msgdmahw_prefetcher.h

diff --git a/drivers/net/ethernet/altera/Makefile 
b/drivers/net/ethernet/altera/Makefile
index ad80be42fa26..73b32876f126 100644
--- a/drivers/net/ethernet/altera/Makefile
+++ b/drivers/net/ethernet/altera/Makefile
@@ -5,4 +5,4 @@
 obj-$(CONFIG_ALTERA_TSE) += altera_tse.o
 altera_tse-objs := altera_tse_main.o altera_tse_ethtool.o \
   altera_msgdma.o altera_sgdma.o altera_utils.o \
-  altera_ptp.o
+  altera_ptp.o altera_msgdma_prefetcher.o
diff --git a/drivers/net/ethernet/altera/altera_msgdma_prefetcher.c 
b/drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
new file mode 100644
index ..55b475e9e15b
--- /dev/null
+++ b/drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
@@ -0,0 +1,433 @@
+// SPDX-License-Identifier: GPL-2.0
+/* MSGDMA Prefetcher driver for Altera ethernet devices
+ *
+ * Copyright (C) 2018 Intel Corporation. All rights reserved.
+ * Author(s):
+ *   Dalon Westergreen 
+ */
+
+#include 
+#include 
+#include 
+#include "altera_utils.h"
+#include "altera_tse.h"
+#include "altera_msgdma.h"
+#include "altera_msgdmahw.h"
+#include "altera_msgdma_prefetcher.h"
+#include "altera_msgdmahw_prefetcher.h"
+
+int msgdma_pref_initialize(struct altera_tse_private *priv)
+{
+   int i;
+   struct msgdma_pref_extended_desc *rx_descs;
+   struct msgdma_pref_extended_desc *tx_descs;
+   dma_addr_t rx_descsphys;
+   dma_addr_t tx_descsphys;
+   u32 rx_ring_size;
+   u32 tx_ring_size;
+
+   priv->pref_rxdescphys = (dma_addr_t)0;
+   priv->pref_txdescphys = (dma_addr_t)0;
+
+   /* we need to allocate more pref descriptors than ringsize, for now
+* just double ringsize
+*/
+   rx_ring_size = priv->rx_ring_size * 2;
+   tx_ring_size = priv->tx_ring_size * 2;
+
+   /* The prefetcher requires the descriptors to be aligned to the
+* descriptor read/write master's data width which worst case is
+* 512 bits.  Currently we DO NOT CHECK THIS and only support 32-bit
+* prefetcher masters.
+*/
+
+   /* allocate memory for rx descriptors */
+   priv->pref_rxdesc =
+   dma_zalloc_coherent(priv->device,
+   sizeof(struct msgdma_pref_extended_desc)
+   * rx_ring_size,
+   >pref_rxdescphys, GFP_KERNEL);
+
+   if (!priv->pref_rxdesc)
+   goto err_rx;
+
+   /* allocate memory for tx descriptors */
+   priv->pref_txdesc =
+   dma_zalloc_coherent(priv->device,
+   sizeof(struct msgdma_pref_extended_desc)
+   * tx_ring_size,
+   >pref_txdescphys, GFP_KERNEL);
+
+   if (!priv->pref_txdesc)
+   goto err_tx;
+
+   /* setup base descriptor ring for tx & rx */
+   rx_descs = (struct msgdma_pref_extended_desc *)priv->pref_rxdesc;
+   tx_descs = (struct msgdma_pref_exten

[PATCH net-next 4/8] net: eth: altera: tse: add optional function to start tx dma

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

Allow for optional start up of tx dma if the start_txdma
function is defined in altera_dmaops.

Signed-off-by: Dalon Westergreen 
---
 drivers/net/ethernet/altera/altera_tse.h  | 1 +
 drivers/net/ethernet/altera/altera_tse_main.c | 5 +
 2 files changed, 6 insertions(+)

diff --git a/drivers/net/ethernet/altera/altera_tse.h 
b/drivers/net/ethernet/altera/altera_tse.h
index d5b97e02e6d6..7f246040135d 100644
--- a/drivers/net/ethernet/altera/altera_tse.h
+++ b/drivers/net/ethernet/altera/altera_tse.h
@@ -412,6 +412,7 @@ struct altera_dmaops {
int (*init_dma)(struct altera_tse_private *priv);
void (*uninit_dma)(struct altera_tse_private *priv);
void (*start_rxdma)(struct altera_tse_private *priv);
+   void (*start_txdma)(struct altera_tse_private *priv);
 };
 
 /* This structure is private to each device.
diff --git a/drivers/net/ethernet/altera/altera_tse_main.c 
b/drivers/net/ethernet/altera/altera_tse_main.c
index 0c0e8f9bba9b..f6b6a14b1ce9 100644
--- a/drivers/net/ethernet/altera/altera_tse_main.c
+++ b/drivers/net/ethernet/altera/altera_tse_main.c
@@ -1256,6 +1256,9 @@ static int tse_open(struct net_device *dev)
 
priv->dmaops->start_rxdma(priv);
 
+   if (priv->dmaops->start_txdma)
+   priv->dmaops->start_txdma(priv);
+
/* Start MAC Rx/Tx */
spin_lock(>mac_cfg_lock);
tse_set_mac(priv, true);
@@ -1658,6 +1661,7 @@ static const struct altera_dmaops altera_dtype_sgdma = {
.init_dma = sgdma_initialize,
.uninit_dma = sgdma_uninitialize,
.start_rxdma = sgdma_start_rxdma,
+   .start_txdma = NULL,
 };
 
 static const struct altera_dmaops altera_dtype_msgdma = {
@@ -1677,6 +1681,7 @@ static const struct altera_dmaops altera_dtype_msgdma = {
.init_dma = msgdma_initialize,
.uninit_dma = msgdma_uninitialize,
.start_rxdma = msgdma_start_rxdma,
+   .start_txdma = NULL,
 };
 
 static const struct of_device_id altera_tse_ids[] = {
-- 
2.19.1



[PATCH net-next 6/8] net: eth: altera: tse: add support for ptp and timestamping

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

Add support for the ptp clock used with the tse, and update
the driver to support timestamping when enabled.  We also
enable debugfs entries for the ptp clock to allow some user
control and interaction with the ptp clock.

Signed-off-by: Dalon Westergreen 
---
 drivers/net/ethernet/altera/Kconfig   |   1 +
 drivers/net/ethernet/altera/Makefile  |   3 +-
 drivers/net/ethernet/altera/altera_ptp.c  | 473 ++
 drivers/net/ethernet/altera/altera_ptp.h  |  77 +++
 drivers/net/ethernet/altera/altera_tse.h  |  10 +
 .../net/ethernet/altera/altera_tse_ethtool.c  |  28 ++
 drivers/net/ethernet/altera/altera_tse_main.c | 164 +-
 7 files changed, 754 insertions(+), 2 deletions(-)
 create mode 100644 drivers/net/ethernet/altera/altera_ptp.c
 create mode 100644 drivers/net/ethernet/altera/altera_ptp.h

diff --git a/drivers/net/ethernet/altera/Kconfig 
b/drivers/net/ethernet/altera/Kconfig
index fdddba51473e..36aee0fc0b51 100644
--- a/drivers/net/ethernet/altera/Kconfig
+++ b/drivers/net/ethernet/altera/Kconfig
@@ -2,6 +2,7 @@ config ALTERA_TSE
tristate "Altera Triple-Speed Ethernet MAC support"
depends on HAS_DMA
select PHYLIB
+   select PTP_1588_CLOCK
---help---
  This driver supports the Altera Triple-Speed (TSE) Ethernet MAC.
 
diff --git a/drivers/net/ethernet/altera/Makefile 
b/drivers/net/ethernet/altera/Makefile
index d4a187e45369..ad80be42fa26 100644
--- a/drivers/net/ethernet/altera/Makefile
+++ b/drivers/net/ethernet/altera/Makefile
@@ -4,4 +4,5 @@
 
 obj-$(CONFIG_ALTERA_TSE) += altera_tse.o
 altera_tse-objs := altera_tse_main.o altera_tse_ethtool.o \
-altera_msgdma.o altera_sgdma.o altera_utils.o
+  altera_msgdma.o altera_sgdma.o altera_utils.o \
+  altera_ptp.o
diff --git a/drivers/net/ethernet/altera/altera_ptp.c 
b/drivers/net/ethernet/altera/altera_ptp.c
new file mode 100644
index ..4467b3c90c59
--- /dev/null
+++ b/drivers/net/ethernet/altera/altera_ptp.c
@@ -0,0 +1,473 @@
+// SPDX-License-Identifier: GPL-2.0
+/* Altera PTP Hardware Clock (PHC) Linux driver
+ * Copyright (C) 2015-2016 Altera Corporation. All rights reserved.
+ * Copyright (C) 2017-2018 Intel Corporation. All rights reserved.
+ *
+ * Author(s):
+ * Dalon Westergreen 
+ */
+
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+#include 
+
+#include "altera_ptp.h"
+#include "altera_utils.h"
+
+#define NOMINAL_PPB10ULL
+#define TOD_PERIOD_MAX 0xf
+#define TOD_PERIOD_MIN 0
+#define TOD_DRIFT_ADJUST_FNS_MAX   0x
+#define TOD_DRIFT_ADJUST_RATE_MAX  0x
+#define TOD_ADJUST_COUNT_MAX   0xf
+#define TOD_ADJUST_MS_MAX  (TOD_PERIOD_MAX) >> 16) + 1) * \
+ ((TOD_ADJUST_COUNT_MAX) + 1)) /  \
+100UL)
+
+/* A fine ToD HW clock offset adjustment.
+ * To perform the fine offset adjustment the AdjustPeriod register is used
+ * to replace the Period register for AdjustCount clock cycles in hardware.
+ */
+static int fine_adjust_tod_clock(struct altera_ptp_private *priv,
+u32 adjust_period, u32 adjust_count)
+{
+   int limit;
+
+   csrwr32(adjust_period, priv->tod_ctrl, tod_csroffs(adjust_period));
+   csrwr32(adjust_count, priv->tod_ctrl, tod_csroffs(adjust_count));
+
+   /* Wait for present offset adjustment update to complete */
+   limit = TOD_ADJUST_MS_MAX;
+   while (limit--) {
+   if (!csrrd32(priv->tod_ctrl, tod_csroffs(adjust_count)))
+   break;
+   mdelay(1);
+   }
+   if (limit < 0)
+   return -EBUSY;
+
+   return 0;
+}
+
+/* A coarse ToD HW clock offset adjustment.
+ * The coarse time adjustment performs by adding or subtracting the delta value
+ * from the current ToD HW clock time.
+ */
+static int coarse_adjust_tod_clock(struct altera_ptp_private *priv, s64 delta)
+{
+   u64 seconds;
+   u32 seconds_msb;
+   u32 seconds_lsb;
+   u32 nanosec;
+   u64 now;
+
+   if (delta == 0)
+   goto out;
+
+   /* Get current time */
+   nanosec = csrrd32(priv->tod_ctrl, tod_csroffs(nanosec));
+   seconds_lsb = csrrd32(priv->tod_ctrl, tod_csroffs(seconds_lsb));
+   seconds_msb = csrrd32(priv->tod_ctrl, tod_csroffs(seconds_msb));
+
+   /* Calculate new time */
+   seconds = (((u64)(seconds_msb & 0x)) << 32) | seconds_lsb;
+   now = seconds * NSEC_PER_SEC + nanosec + delta;
+
+   seconds = div_u64_rem(now, NSEC_PER_SEC, );
+   seconds_msb = upper_32_bits(seconds) & 0x;
+   seconds_lsb = lower_32_bits(seconds);
+
+   /* Set corrected time */
+   csrwr32(seconds_msb, priv->tod_ct

[PATCH net-next 0/8] net: eth: altera: tse: Add PTP and mSGDMA prefetcher

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

This patch series cleans up the Altera TSE driver and adds support
for the newer msgdma prefetcher as well as ptp support when using
the msgdma prefetcher.

Dalon Westergreen (8):
  net: eth: altera: tse_start_xmit ignores tx_buffer call response
  net: eth: altera: set rx and tx ring size before init_dma call
  net: eth: altera: tse: fix altera_dmaops declaration
  net: eth: altera: tse: add optional function to start tx dma
  net: eth: altera: tse: Move common functions to altera_utils
  net: eth: altera: tse: add support for ptp and timestamping
  net: eth: altera: tse: add msgdma prefetcher
  net: eth: altera: tse: update devicetree bindings documentation

 .../devicetree/bindings/net/altera_tse.txt|  98 +++-
 drivers/net/ethernet/altera/Kconfig   |   1 +
 drivers/net/ethernet/altera/Makefile  |   3 +-
 .../altera/altera_msgdma_prefetcher.c | 433 
 .../altera/altera_msgdma_prefetcher.h |  30 ++
 .../altera/altera_msgdmahw_prefetcher.h   |  87 
 drivers/net/ethernet/altera/altera_ptp.c  | 473 ++
 drivers/net/ethernet/altera/altera_ptp.h  |  77 +++
 drivers/net/ethernet/altera/altera_sgdma.c|  14 +-
 drivers/net/ethernet/altera/altera_tse.h  | 100 ++--
 .../net/ethernet/altera/altera_tse_ethtool.c  |  29 ++
 drivers/net/ethernet/altera/altera_tse_main.c | 244 -
 drivers/net/ethernet/altera/altera_utils.c|  30 ++
 drivers/net/ethernet/altera/altera_utils.h|  46 ++
 14 files changed, 1554 insertions(+), 111 deletions(-)
 create mode 100644 drivers/net/ethernet/altera/altera_msgdma_prefetcher.c
 create mode 100644 drivers/net/ethernet/altera/altera_msgdma_prefetcher.h
 create mode 100644 drivers/net/ethernet/altera/altera_msgdmahw_prefetcher.h
 create mode 100644 drivers/net/ethernet/altera/altera_ptp.c
 create mode 100644 drivers/net/ethernet/altera/altera_ptp.h

-- 
2.19.1



[PATCH net-next 3/8] net: eth: altera: tse: fix altera_dmaops declaration

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

The declaration of struct altera_dmaops does not have
identifier names.  Add identifier names to confrom with
required coding styles.

Signed-off-by: Dalon Westergreen 
---
 drivers/net/ethernet/altera/altera_tse.h | 30 +---
 1 file changed, 16 insertions(+), 14 deletions(-)

diff --git a/drivers/net/ethernet/altera/altera_tse.h 
b/drivers/net/ethernet/altera/altera_tse.h
index e2feee87180a..d5b97e02e6d6 100644
--- a/drivers/net/ethernet/altera/altera_tse.h
+++ b/drivers/net/ethernet/altera/altera_tse.h
@@ -396,20 +396,22 @@ struct altera_tse_private;
 struct altera_dmaops {
int altera_dtype;
int dmamask;
-   void (*reset_dma)(struct altera_tse_private *);
-   void (*enable_txirq)(struct altera_tse_private *);
-   void (*enable_rxirq)(struct altera_tse_private *);
-   void (*disable_txirq)(struct altera_tse_private *);
-   void (*disable_rxirq)(struct altera_tse_private *);
-   void (*clear_txirq)(struct altera_tse_private *);
-   void (*clear_rxirq)(struct altera_tse_private *);
-   int (*tx_buffer)(struct altera_tse_private *, struct tse_buffer *);
-   u32 (*tx_completions)(struct altera_tse_private *);
-   void (*add_rx_desc)(struct altera_tse_private *, struct tse_buffer *);
-   u32 (*get_rx_status)(struct altera_tse_private *);
-   int (*init_dma)(struct altera_tse_private *);
-   void (*uninit_dma)(struct altera_tse_private *);
-   void (*start_rxdma)(struct altera_tse_private *);
+   void (*reset_dma)(struct altera_tse_private *priv);
+   void (*enable_txirq)(struct altera_tse_private *priv);
+   void (*enable_rxirq)(struct altera_tse_private *priv);
+   void (*disable_txirq)(struct altera_tse_private *priv);
+   void (*disable_rxirq)(struct altera_tse_private *priv);
+   void (*clear_txirq)(struct altera_tse_private *priv);
+   void (*clear_rxirq)(struct altera_tse_private *priv);
+   int (*tx_buffer)(struct altera_tse_private *priv,
+struct tse_buffer *buffer);
+   u32 (*tx_completions)(struct altera_tse_private *priv);
+   void (*add_rx_desc)(struct altera_tse_private *priv,
+   struct tse_buffer *buffer);
+   u32 (*get_rx_status)(struct altera_tse_private *priv);
+   int (*init_dma)(struct altera_tse_private *priv);
+   void (*uninit_dma)(struct altera_tse_private *priv);
+   void (*start_rxdma)(struct altera_tse_private *priv);
 };
 
 /* This structure is private to each device.
-- 
2.19.1



[PATCH net-next 2/8] net: eth: altera: set rx and tx ring size before init_dma call

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

It is more appropriate to set the rx and tx ring size before calling
the init function for the dma.

Signed-off-by: Dalon Westergreen 
---
 drivers/net/ethernet/altera/altera_tse_main.c | 6 --
 1 file changed, 4 insertions(+), 2 deletions(-)

diff --git a/drivers/net/ethernet/altera/altera_tse_main.c 
b/drivers/net/ethernet/altera/altera_tse_main.c
index dcb330129e23..0c0e8f9bba9b 100644
--- a/drivers/net/ethernet/altera/altera_tse_main.c
+++ b/drivers/net/ethernet/altera/altera_tse_main.c
@@ -1166,6 +1166,10 @@ static int tse_open(struct net_device *dev)
int i;
unsigned long int flags;
 
+   /* set tx and rx ring size */
+   priv->rx_ring_size = dma_rx_num;
+   priv->tx_ring_size = dma_tx_num;
+
/* Reset and configure TSE MAC and probe associated PHY */
ret = priv->dmaops->init_dma(priv);
if (ret != 0) {
@@ -1208,8 +1212,6 @@ static int tse_open(struct net_device *dev)
priv->dmaops->reset_dma(priv);
 
/* Create and initialize the TX/RX descriptors chains. */
-   priv->rx_ring_size = dma_rx_num;
-   priv->tx_ring_size = dma_tx_num;
ret = alloc_init_skbufs(priv);
if (ret) {
netdev_err(dev, "DMA descriptors initialization failed\n");
-- 
2.19.1



[PATCH net-next 1/8] net: eth: altera: tse_start_xmit ignores tx_buffer call response

2018-11-14 Thread Dalon Westergreen
From: Dalon Westergreen 

The return from tx_buffer call in tse_start_xmit is
inapropriately ignored.  tse_buffer calls should return
0 for success or NETDEV_TX_BUSY.  tse_start_xmit should
return not report a successful transmit when the tse_buffer
call returns an error condition.

In addition to the above, the msgdma and sgdma do not return
the same value on success or failure.  The sgdma_tx_buffer
returned 0 on failure and a positive number of transmitted
packets on success.  Given that it only ever sends 1 packet,
this made no sense.  The msgdma implementation msgdma_tx_buffer
returns 0 on success.

  -> Don't ignore the return from tse_buffer calls
  -> Fix sgdma tse_buffer call to return 0 on success
 and NETDEV_TX_BUSY on failure.

Signed-off-by: Dalon Westergreen 
---
 drivers/net/ethernet/altera/altera_sgdma.c| 14 --
 drivers/net/ethernet/altera/altera_tse_main.c |  4 +++-
 2 files changed, 11 insertions(+), 7 deletions(-)

diff --git a/drivers/net/ethernet/altera/altera_sgdma.c 
b/drivers/net/ethernet/altera/altera_sgdma.c
index 88ef67a998b4..eb47b9b820bb 100644
--- a/drivers/net/ethernet/altera/altera_sgdma.c
+++ b/drivers/net/ethernet/altera/altera_sgdma.c
@@ -15,6 +15,7 @@
  */
 
 #include 
+#include 
 #include "altera_utils.h"
 #include "altera_tse.h"
 #include "altera_sgdmahw.h"
@@ -170,10 +171,11 @@ void sgdma_clear_txirq(struct altera_tse_private *priv)
SGDMA_CTRLREG_CLRINT);
 }
 
-/* transmits buffer through SGDMA. Returns number of buffers
- * transmitted, 0 if not possible.
- *
- * tx_lock is held by the caller
+/* transmits buffer through SGDMA.
+ *   original behavior returned the number of transmitted packets (always 1) &
+ *   returned 0 on error.  This differs from the msgdma.  the calling function
+ *   will now actually look at the code, so from now, 0 is good and return
+ *   NETDEV_TX_BUSY when busy.
  */
 int sgdma_tx_buffer(struct altera_tse_private *priv, struct tse_buffer *buffer)
 {
@@ -185,7 +187,7 @@ int sgdma_tx_buffer(struct altera_tse_private *priv, struct 
tse_buffer *buffer)
 
/* wait 'til the tx sgdma is ready for the next transmit request */
if (sgdma_txbusy(priv))
-   return 0;
+   return NETDEV_TX_BUSY;
 
sgdma_setup_descrip(cdesc,  /* current descriptor */
ndesc,  /* next descriptor */
@@ -202,7 +204,7 @@ int sgdma_tx_buffer(struct altera_tse_private *priv, struct 
tse_buffer *buffer)
/* enqueue the request to the pending transmit queue */
queue_tx(priv, buffer);
 
-   return 1;
+   return 0;
 }
 
 
diff --git a/drivers/net/ethernet/altera/altera_tse_main.c 
b/drivers/net/ethernet/altera/altera_tse_main.c
index baca8f704a45..dcb330129e23 100644
--- a/drivers/net/ethernet/altera/altera_tse_main.c
+++ b/drivers/net/ethernet/altera/altera_tse_main.c
@@ -606,7 +606,9 @@ static int tse_start_xmit(struct sk_buff *skb, struct 
net_device *dev)
buffer->dma_addr = dma_addr;
buffer->len = nopaged_len;
 
-   priv->dmaops->tx_buffer(priv, buffer);
+   ret = priv->dmaops->tx_buffer(priv, buffer);
+   if (ret)
+   goto out;
 
skb_tx_timestamp(skb);
 
-- 
2.19.1