[RFC PATCH net-next 3/6] net: ethernet: implement OA TC6 configuration function

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Read STDCAP register for the MAC-PHY capability and check against the
configuration parameters such as chunk payload, tx cut through and rx cut
through to configure the MAC-PHY. It also configures the control command
protected/unprotected mode.

In cut through mode configuration the MAC-PHY doesn't buffer the incoming
data. In tx case, it passes the data to the network if the configured cps
of data available. In rx case, it passes the data to the SPI host if the
configured cps of data available from the network. Also disables all the
errors mask in the IMASK0 register to check for the errors.

Signed-off-by: Parthiban Veerasooran <Parthiban.Veerasooran@xxxxxxxxxxxxx>
---
 drivers/net/ethernet/oa_tc6.c | 39 +++++++++++++++++++++++++++++++++++
 include/linux/oa_tc6.h        | 28 ++++++++++++++++++++++---
 2 files changed, 64 insertions(+), 3 deletions(-)

diff --git a/drivers/net/ethernet/oa_tc6.c b/drivers/net/ethernet/oa_tc6.c
index 0019f70345b6..65a7317f768d 100644
--- a/drivers/net/ethernet/oa_tc6.c
+++ b/drivers/net/ethernet/oa_tc6.c
@@ -287,6 +287,45 @@ int oa_tc6_read_register(struct oa_tc6 *tc6, u32 addr, u32 val[], u8 len)
 }
 EXPORT_SYMBOL_GPL(oa_tc6_read_register);
 
+int oa_tc6_configure(struct oa_tc6 *tc6, u8 cps, bool ctrl_prot, bool tx_cut_thr,
+		     bool rx_cut_thr)
+{
+	u32 regval;
+	int ret;
+
+	/* Read and configure the IMASK0 register for unmasking the interrupts */
+	ret = oa_tc6_read_register(tc6, OA_TC6_IMASK0, &regval, 1);
+	if (ret)
+		return ret;
+
+	regval &= TXPEM & TXBOEM & TXBUEM & RXBOEM & LOFEM & HDREM;
+	ret = oa_tc6_write_register(tc6, OA_TC6_IMASK0, &regval, 1);
+	if (ret)
+		return ret;
+
+	/* Configure the CONFIG0 register with the required configurations */
+	regval = SYNC;
+	if (ctrl_prot)
+		regval |= PROTE;
+	if (tx_cut_thr)
+		regval |= TXCTE;
+	if (rx_cut_thr)
+		regval |= RXCTE;
+	regval |= FIELD_PREP(CPS, ilog2(cps) / ilog2(2));
+
+	ret = oa_tc6_write_register(tc6, OA_TC6_CONFIG0, &regval, 1);
+	if (ret)
+		return ret;
+
+	tc6->cps = cps;
+	tc6->ctrl_prot = ctrl_prot;
+	tc6->tx_cut_thr = tx_cut_thr;
+	tc6->rx_cut_thr = rx_cut_thr;
+
+	return 0;
+}
+EXPORT_SYMBOL_GPL(oa_tc6_configure);
+
 struct oa_tc6 *oa_tc6_init(struct spi_device *spi)
 {
 	struct oa_tc6 *tc6;
diff --git a/include/linux/oa_tc6.h b/include/linux/oa_tc6.h
index 315f061c2dfe..fa29c4e09720 100644
--- a/include/linux/oa_tc6.h
+++ b/include/linux/oa_tc6.h
@@ -19,11 +19,28 @@
 
 /* Open Alliance TC6 Standard Control and Status Registers */
 #define OA_TC6_RESET	0x0003		/* Reset Control and Status Register */
+#define OA_TC6_CONFIG0	0x0004		/* Configuration Register #0 */
 #define OA_TC6_STS0	0x0008		/* Status Register #0 */
+#define OA_TC6_IMASK0	0x000C		/* Interrupt Mask Register #0 */
 
 /* RESET register field */
 #define SW_RESET	BIT(0)		/* Software Reset */
 
+/* CONFIG0 register fields */
+#define SYNC		BIT(15)		/* Configuration Synchronization */
+#define TXCTE		BIT(9)		/* Tx cut-through enable */
+#define RXCTE		BIT(8)		/* Rx cut-through enable */
+#define PROTE		BIT(5)		/* Ctrl read/write Protection Enable */
+#define CPS		GENMASK(2, 0)	/* Chunk Payload Size */
+
+/* Unmasking interrupt fields in IMASK0 */
+#define HDREM		~BIT(5)		/* Header Error Mask */
+#define LOFEM		~BIT(4)		/* Loss of Framing Error Mask */
+#define RXBOEM		~BIT(3)		/* Rx Buffer Overflow Error Mask */
+#define TXBUEM		~BIT(2)		/* Tx Buffer Underflow Error Mask */
+#define TXBOEM		~BIT(1)		/* Tx Buffer Overflow Error Mask */
+#define TXPEM		~BIT(0)		/* Tx Protocol Error Mask */
+
 /* STATUS0 register field */
 #define RESETC		BIT(6)		/* Reset Complete */
 
@@ -31,15 +48,20 @@
 #define TC6_FTR_SIZE	4		/* Ctrl command footer size ss per OA */
 
 struct oa_tc6 {
-	struct spi_device *spi;
-	bool ctrl_prot;
+	struct completion rst_complete;
 	struct task_struct *tc6_task;
 	wait_queue_head_t tc6_wq;
+	struct spi_device *spi;
+	bool tx_cut_thr;
+	bool rx_cut_thr;
+	bool ctrl_prot;
 	bool int_flag;
-	struct completion rst_complete;
+	u8 cps;
 };
 
 struct oa_tc6 *oa_tc6_init(struct spi_device *spi);
 int oa_tc6_deinit(struct oa_tc6 *tc6);
 int oa_tc6_write_register(struct oa_tc6 *tc6, u32 addr, u32 value[], u8 len);
 int oa_tc6_read_register(struct oa_tc6 *tc6, u32 addr, u32 value[], u8 len);
+int oa_tc6_configure(struct oa_tc6 *tc6, u8 cps, bool ctrl_prot, bool tx_cut_thr,
+		     bool rx_cut_thr);
-- 
2.34.1




[Index of Archives]     [Kernel Newbies]     [Security]     [Netfilter]     [Bugtraq]     [Linux FS]     [Yosemite Forum]     [MIPS Linux]     [ARM Linux]     [Linux Security]     [Linux RAID]     [Samba]     [Video 4 Linux]     [Device Mapper]     [Linux Resources]

  Powered by Linux