Re: [RFC v7 net-next 10/13] mfd: ocelot: add support for the vsc7512 chip via spi
From: Vladimir Oltean <vladimir.oltean@nxp.com>
Date: 2022-03-08 14:37:58
Also in:
linux-arm-kernel, linux-gpio, linux-phy, lkml
On Sun, Mar 06, 2022 at 06:12:05PM -0800, Colin Foster wrote:
The VSC7512 is a networking chip that contains several peripherals. Many of
these peripherals are currently supported by the VSC7513 and VSC7514 chips,
but those run on an internal CPU. The VSC7512 lacks this CPU, and must be
controlled externally.
Utilize the existing drivers by referencing the chip as an MFD. Add support
for the two MDIO buses, the internal phys, pinctrl, serial GPIO, and HSIO.
Signed-off-by: Colin Foster <colin.foster@in-advantage.com>
---
+#define VSC7512_MIIM0_RES_START 0x7107009c
+#define VSC7512_MIIM0_RES_SIZE 0x24
+
+#define VSC7512_MIIM1_RES_START 0x710700c0
+#define VSC7512_MIIM1_RES_SIZE 0x24
+
+#define VSC7512_PHY_RES_START 0x710700f0
+#define VSC7512_PHY_RES_SIZE 0x4
+
+#define VSC7512_HSIO_RES_START 0x710d0000
+#define VSC7512_HSIO_RES_SIZE 0x10000
+
+#define VSC7512_GPIO_RES_START 0x71070034
+#define VSC7512_GPIO_RES_SIZE 0x6c
+
+#define VSC7512_SIO_RES_START 0x710700f8
+#define VSC7512_SIO_RES_SIZE 0x100
+
+static const struct resource vsc7512_gcb_resource =
+ DEFINE_RES_REG_NAMED(VSC7512_GCB_RES_START, VSC7512_GCB_RES_SIZE,
+ "devcpu_gcb_chip_regs");
+static const struct resource vsc7512_miim0_resources[] = {
+ DEFINE_RES_REG_NAMED(VSC7512_MIIM0_RES_START, VSC7512_MIIM0_RES_SIZE,
+ "gcb_miim0"),
+ DEFINE_RES_REG_NAMED(VSC7512_PHY_RES_START, VSC7512_PHY_RES_SIZE,
+ "gcb_phy"),
+};
+
+static const struct resource vsc7512_miim1_resources[] = {
+ DEFINE_RES_REG_NAMED(VSC7512_MIIM1_RES_START, VSC7512_MIIM1_RES_SIZE,
+ "gcb_miim1"),
+};
+
+static const struct resource vsc7512_hsio_resources[] = {
+ DEFINE_RES_REG_NAMED(VSC7512_HSIO_RES_START, VSC7512_HSIO_RES_SIZE,
+ "hsio"),
+};
+
+static const struct resource vsc7512_pinctrl_resources[] = {
+ DEFINE_RES_REG_NAMED(VSC7512_GPIO_RES_START, VSC7512_GPIO_RES_SIZE,
+ "gcb_gpio"),
+};
+
+static const struct resource vsc7512_sgpio_resources[] = {
+ DEFINE_RES_REG_NAMED(VSC7512_SIO_RES_START, VSC7512_SIO_RES_SIZE,
+ "gcb_sio"),
+};
+
+static const struct mfd_cell vsc7512_devs[] = {
+ {
+ .name = "ocelot-pinctrl",
+ .of_compatible = "mscc,ocelot-pinctrl",
+ .num_resources = ARRAY_SIZE(vsc7512_pinctrl_resources),
+ .resources = vsc7512_pinctrl_resources,
+ }, {
+ .name = "ocelot-sgpio",
+ .of_compatible = "mscc,ocelot-sgpio",
+ .num_resources = ARRAY_SIZE(vsc7512_sgpio_resources),
+ .resources = vsc7512_sgpio_resources,
+ }, {
+ .name = "ocelot-miim0",
+ .of_compatible = "mscc,ocelot-miim",
+ .num_resources = ARRAY_SIZE(vsc7512_miim0_resources),
+ .resources = vsc7512_miim0_resources,
+ }, {
+ .name = "ocelot-miim1",
+ .of_compatible = "mscc,ocelot-miim",
+ .num_resources = ARRAY_SIZE(vsc7512_miim1_resources),
+ .resources = vsc7512_miim1_resources,I'm looking at mfd_match_of_node_to_dev() and I don't really understand how the first MDIO bus matches the first mfd_cell's resources, and the second MDIO bus the second mfd_cell? By order of definition?
+ }, {
+ .name = "ocelot-serdes",
+ .of_compatible = "mscc,vsc7514-serdes",
+ .num_resources = ARRAY_SIZE(vsc7512_hsio_resources),
+ .resources = vsc7512_hsio_resources,
+ },
+};
+
+int ocelot_core_init(struct ocelot_core *core)
+{
+ struct device *dev = core->dev;
+ int ret;
+
+ dev_set_drvdata(dev, core);
+
+ core->gcb_regmap = ocelot_devm_regmap_init(core, dev,
+ &vsc7512_gcb_resource);
+ if (IS_ERR(core->gcb_regmap))
+ return -ENOMEM;
+
+ ret = ocelot_reset(core);
+ if (ret) {
+ dev_err(dev, "Failed to reset device: %d\n", ret);
+ return ret;
+ }
+
+ /*
+ * A chip reset will clear the SPI configuration, so it needs to be done
+ * again before we can access any registers
+ */
+ ret = ocelot_spi_initialize(core);
+ if (ret) {
+ dev_err(dev, "Failed to initialize SPI interface: %d\n", ret);
+ return ret;
+ }
+
+ ret = devm_mfd_add_devices(dev, PLATFORM_DEVID_AUTO, vsc7512_devs,
+ ARRAY_SIZE(vsc7512_devs), NULL, 0, NULL);
+ if (ret) {
+ dev_err(dev, "Failed to add sub-devices: %d\n", ret);
+ return ret;
+ }
+
+ return 0;
+}
+EXPORT_SYMBOL(ocelot_core_init);
--
2.25.1