[linux,dev-5.4] fsi: aspeed: Add clock debugfs
diff mbox series

Message ID 20200124002742.251946-1-joel@jms.id.au
State New
Headers show
Series
  • [linux,dev-5.4] fsi: aspeed: Add clock debugfs
Related show

Commit Message

Joel Stanley Jan. 24, 2020, 12:27 a.m. UTC
The bus clock speed is commonly tweaked during bringup and testing.

This could be come a device tree property in the future.

Signed-off-by: Joel Stanley <joel@jms.id.au>
---
 drivers/fsi/fsi-master-aspeed.c | 52 +++++++++++++++++++++++++++++++++
 1 file changed, 52 insertions(+)

Patch
diff mbox series

diff --git a/drivers/fsi/fsi-master-aspeed.c b/drivers/fsi/fsi-master-aspeed.c
index f49742b310c2..24563bbba8ff 100644
--- a/drivers/fsi/fsi-master-aspeed.c
+++ b/drivers/fsi/fsi-master-aspeed.c
@@ -4,6 +4,7 @@ 
 
 #include <linux/clk.h>
 #include <linux/delay.h>
+#include <linux/debugfs.h>
 #include <linux/fsi.h>
 #include <linux/io.h>
 #include <linux/mfd/syscon.h>
@@ -21,6 +22,7 @@  struct fsi_master_aspeed {
 	struct device		*dev;
 	void __iomem		*base;
 	struct clk		*clk;
+	struct dentry           *debugfs_dir;
 };
 
 #define to_fsi_master_aspeed(m) \
@@ -419,6 +421,49 @@  static int aspeed_master_init(struct fsi_master_aspeed *aspeed)
 	return 0;
 }
 
+static int fsi_master_aspeed_clock_debugfs_get(void *data, u64 *val)
+{
+	struct fsi_master_aspeed *aspeed = data;
+	__be32 out;
+	int rc;
+
+	rc = opb_readl(aspeed, ctrl_base, &out);
+	if (rc)
+		return rc;
+
+	*val = (be32_to_cpu(out) >> FSI_MMODE_CRS0SHFT) & FSI_MMODE_CRS0MASK;
+
+	return 0;
+}
+
+static int fsi_master_aspeed_clock_debugfs_set(void *data, u64 val)
+{
+	struct fsi_master_aspeed *aspeed = data;
+	u32 reg, rc;
+	__be32 raw;
+
+	if (val > 0x3ff)
+		return -EINVAL;
+
+	rc = opb_readl(aspeed, ctrl_base, &raw);
+	if (rc)
+		return rc;
+
+	reg = be32_to_cpu(raw);
+
+	reg &= ~(FSI_MMODE_CRS0MASK << FSI_MMODE_CRS0SHFT);
+	reg |= fsi_mmode_crs0(val);
+
+	rc = opb_writel(aspeed, ctrl_base, cpu_to_be32(reg));
+	if (rc)
+		return rc;
+
+	return 0;
+}
+DEFINE_DEBUGFS_ATTRIBUTE(fsi_master_aspeed_clock_debugfs_ops,
+			 fsi_master_aspeed_clock_debugfs_get,
+			 fsi_master_aspeed_clock_debugfs_set, "0x%llx\n");
+
 static int fsi_master_aspeed_probe(struct platform_device *pdev)
 {
 	struct fsi_master_aspeed *aspeed;
@@ -509,6 +554,11 @@  static int fsi_master_aspeed_probe(struct platform_device *pdev)
 	 * we're ready.
 	 */
 	get_device(&aspeed->master.dev);
+
+	aspeed->debugfs_dir = debugfs_create_dir("fsi-master-aspeed", NULL);
+	debugfs_create_file("clock_div", 0644, aspeed->debugfs_dir,
+			    aspeed, &fsi_master_aspeed_clock_debugfs_ops);
+
 	return 0;
 
 err_release:
@@ -523,6 +573,8 @@  static int fsi_master_aspeed_remove(struct platform_device *pdev)
 	fsi_master_unregister(&aspeed->master);
 	clk_disable_unprepare(aspeed->clk);
 
+	debugfs_remove_recursive(aspeed->debugfs_dir);
+
 	return 0;
 }