Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch Add support SPI driver for i.MX6.
details: https://anonhg.NetBSD.org/src/rev/b9e47b794695
branches: trunk
changeset: 964847:b9e47b794695
user: hkenken <hkenken%NetBSD.org@localhost>
date: Mon Aug 19 11:41:36 2019 +0000
description:
Add support SPI driver for i.MX6.
diffstat:
sys/arch/arm/imx/fdt/files.imx6 | 10 +-
sys/arch/arm/imx/fdt/imx6_spi.c | 156 ++++++++++++++++++++++++++++++
sys/arch/arm/imx/imx51_spi.c | 42 +++++--
sys/arch/arm/imx/imx51reg.h | 3 +-
sys/arch/arm/imx/imxspi.c | 64 ++++++-----
sys/arch/arm/imx/imxspivar.h | 21 +--
sys/arch/evbarm/conf/IMX | 12 ++-
sys/arch/evbarm/netwalker/netwalker_spi.c | 53 ++++++---
8 files changed, 281 insertions(+), 80 deletions(-)
diffs (truncated from 587 to 300 lines):
diff -r e888d241f292 -r b9e47b794695 sys/arch/arm/imx/fdt/files.imx6
--- a/sys/arch/arm/imx/fdt/files.imx6 Mon Aug 19 10:56:33 2019 +0000
+++ b/sys/arch/arm/imx/fdt/files.imx6 Mon Aug 19 11:41:36 2019 +0000
@@ -1,4 +1,4 @@
-# $NetBSD: files.imx6,v 1.5 2019/08/12 11:45:53 skrll Exp $
+# $NetBSD: files.imx6,v 1.6 2019/08/19 11:41:36 hkenken Exp $
#
# Configuration info for the Freescale i.MX6
#
@@ -76,3 +76,11 @@
attach imxi2c at fdt
file arch/arm/imx/imxi2c.c imxi2c
file arch/arm/imx/fdt/imx6_i2c.c imxi2c
+
+# SPI bus controlloer
+device imxspi : spibus
+attach imxspi at fdt with imxspi_fdt
+file arch/arm/imx/imxspi.c imxspi
+file arch/arm/imx/fdt/imx6_spi.c imxspi_fdt
+defparam opt_imxspi.h IMXSPINSLAVES
+
diff -r e888d241f292 -r b9e47b794695 sys/arch/arm/imx/fdt/imx6_spi.c
--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/sys/arch/arm/imx/fdt/imx6_spi.c Mon Aug 19 11:41:36 2019 +0000
@@ -0,0 +1,156 @@
+/* $NetBSD: imx6_spi.c,v 1.1 2019/08/19 11:41:36 hkenken Exp $ */
+/*-
+ * Copyright (c) 2019 Genetec Corporation. All rights reserved.
+ * Written by Hashimoto Kenichi for Genetec Corporation.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
+ * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
+ * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
+ * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
+ * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ */
+#include <sys/cdefs.h>
+__KERNEL_RCSID(0, "$NetBSD: imx6_spi.c,v 1.1 2019/08/19 11:41:36 hkenken Exp $");
+
+#include "opt_imxspi.h"
+
+#include <sys/param.h>
+#include <sys/bus.h>
+#include <sys/device.h>
+#include <sys/kmem.h>
+#include <sys/gpio.h>
+
+#include <arm/imx/imxspivar.h>
+
+#include <dev/fdt/fdtvar.h>
+
+struct imxspi_fdt_softc {
+ struct imxspi_softc sc_imxspi; /* Must be first */
+
+ struct spi_chipset_tag sc_tag;
+ struct clk *sc_clk;
+
+ struct fdtbus_gpio_pin **sc_pin_cs;
+};
+
+static const struct of_compat_data compat_data[] = {
+ { "fsl,imx6q-ecspi", true },
+ { NULL }
+};
+
+CFATTACH_DECL_NEW(imxspi_fdt, sizeof(struct imxspi_fdt_softc),
+ imxspi_match, imxspi_attach, NULL, NULL);
+
+static int
+imxspi_cs_enable(void *arg, int slave)
+{
+ struct imxspi_fdt_softc * const sc = arg;
+ fdtbus_gpio_write(sc->sc_pin_cs[slave], 1);
+ return 0;
+}
+
+static int
+imxspi_cs_disable(void *arg, int slave)
+{
+ struct imxspi_fdt_softc * const sc = arg;
+ fdtbus_gpio_write(sc->sc_pin_cs[slave], 0);
+ return 0;
+}
+
+int
+imxspi_match(device_t parent, cfdata_t cf, void *aux)
+{
+ struct fdt_attach_args * const faa = aux;
+
+ return of_match_compat_data(faa->faa_phandle, compat_data);
+}
+
+void
+imxspi_attach(device_t parent, device_t self, void *aux)
+{
+ struct imxspi_fdt_softc * const ifsc = device_private(self);
+ struct imxspi_softc * const sc = &ifsc->sc_imxspi;
+ struct fdt_attach_args * const faa = aux;
+ char intrstr[128];
+ const int phandle = faa->faa_phandle;
+ bus_addr_t addr;
+ bus_size_t size;
+ int error;
+
+ u_int nslaves;
+ error = of_getprop_uint32(phandle, "fsl,spi-num-chipselects", &nslaves);
+ if (error)
+ nslaves = IMXSPINSLAVES;
+
+ ifsc->sc_pin_cs = kmem_alloc(sizeof(struct fdtbus_gpio_pin *) * nslaves, KM_SLEEP);
+
+ for (int i = 0; i < nslaves; i++) {
+ ifsc->sc_pin_cs[i] = fdtbus_gpio_acquire_index(phandle, "cs-gpios", i,
+ GPIO_PIN_OUTPUT);
+ }
+
+ ifsc->sc_clk = fdtbus_clock_get_index(phandle, 0);
+ if (ifsc->sc_clk == NULL) {
+ aprint_error(": couldn't get clock\n");
+ return;
+ }
+
+ error = clk_enable(ifsc->sc_clk);
+ if (error) {
+ aprint_error_dev(sc->sc_dev, "couldn't enable: %d\n", error);
+ return;
+ }
+
+ ifsc->sc_tag.cookie = ifsc;
+ ifsc->sc_tag.spi_cs_enable = imxspi_cs_enable;
+ ifsc->sc_tag.spi_cs_disable = imxspi_cs_disable;
+
+ sc->sc_phandle = phandle;
+ sc->sc_iot = faa->faa_bst;
+ sc->sc_enhanced = of_search_compatible(phandle, compat_data)->data;
+
+ sc->sc_nslaves = nslaves;
+ sc->sc_freq = clk_get_rate(ifsc->sc_clk);
+ sc->sc_tag = &ifsc->sc_tag;
+
+ if (fdtbus_get_reg(phandle, 0, &addr, &size) != 0) {
+ aprint_error(": couldn't get iomux registers\n");
+ return;
+ }
+
+ if (bus_space_map(sc->sc_iot, addr, size, 0, &sc->sc_ioh)) {
+ aprint_error_dev(sc->sc_dev, "couldn't map registers\n");
+ return;
+ }
+
+ if (!fdtbus_intr_str(faa->faa_phandle, 0, intrstr, sizeof(intrstr))) {
+ aprint_error_dev(self, "failed to decode interrupt\n");
+ return;
+ }
+
+ sc->sc_ih = fdtbus_intr_establish(phandle, 0, IPL_VM,
+ FDT_INTR_MPSAFE, imxspi_intr, &ifsc->sc_imxspi);
+ if (sc->sc_ih == NULL) {
+ aprint_error_dev(self, "couldn't establish interrupt on %s\n",
+ intrstr);
+ return;
+ }
+ aprint_normal_dev(self, "interrupting on %s\n", intrstr);
+
+ imxspi_attach_common(self);
+}
diff -r e888d241f292 -r b9e47b794695 sys/arch/arm/imx/imx51_spi.c
--- a/sys/arch/arm/imx/imx51_spi.c Mon Aug 19 10:56:33 2019 +0000
+++ b/sys/arch/arm/imx/imx51_spi.c Mon Aug 19 11:41:36 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: imx51_spi.c,v 1.1 2014/03/22 09:28:08 hkenken Exp $ */
+/* $NetBSD: imx51_spi.c,v 1.2 2019/08/19 11:41:36 hkenken Exp $ */
/*-
* Copyright (c) 2014 Genetec Corporation. All rights reserved.
@@ -27,7 +27,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: imx51_spi.c,v 1.1 2014/03/22 09:28:08 hkenken Exp $");
+__KERNEL_RCSID(0, "$NetBSD: imx51_spi.c,v 1.2 2019/08/19 11:41:36 hkenken Exp $");
#include "locators.h"
#include "opt_imx.h"
@@ -43,7 +43,8 @@
#include <arm/imx/imx51_ccmvar.h>
struct imx51spi_softc {
- struct imxspi_softc sc_spi;
+ struct imxspi_softc sc_spi; /* Must be first */
+
struct spi_chipset_tag sc_tag;
};
@@ -74,26 +75,39 @@
void
imxspi_attach(device_t parent, device_t self, void *aux)
{
- struct imx51spi_softc *sc = device_private(self);
+ struct imx51spi_softc *isc = device_private(self);
+ struct imxspi_softc *sc = &isc->sc_spi;
struct axi_attach_args *aa = aux;
struct imxspi_attach_args saa;
int cf_flags = device_cfdata(self)->cf_flags;
+ bus_addr_t addr;
+ bus_size_t size;
+ int error;
+
+ addr = aa->aa_addr;
+ size = aa->aa_size;
+ if (size <= 0)
+ size = SPI_SIZE;
sc->sc_tag.cookie = sc;
sc->sc_tag.spi_cs_enable = imxspi_cs_enable;
sc->sc_tag.spi_cs_disable = imxspi_cs_disable;
- saa.saa_iot = aa->aa_iot;
- saa.saa_addr = aa->aa_addr;
- saa.saa_size = aa->aa_size;
- saa.saa_irq = aa->aa_irq;
- saa.saa_enhanced = cf_flags;
+ sc->sc_iot = aa->aa_iot;
+ sc->sc_enhanced = cf_flags;
+
+ sc->sc_nslaves = IMXSPINSLAVES;
+ sc->sc_freq = imx51_get_clock(IMX51CLK_CSPI_CLK_ROOT);
+ sc->sc_tag = &sc->sc_tag;
- saa.saa_nslaves = IMXSPINSLAVES;
- saa.saa_freq = imx51_get_clock(IMX51CLK_CSPI_CLK_ROOT);
- saa.saa_tag = &sc->sc_tag;
+ if (bus_space_map(sc->sc_iot, addr, size, 0, &sc->sc_ioh)) {
+ aprint_error_dev(sc->sc_dev, "couldn't map registers\n");
+ return;
+ }
- sc->sc_spi.sc_dev = self;
+ /* enable device interrupts */
+ sc->sc_ih = intr_establish(aa->aa_irq, IPL_BIO, IST_LEVEL,
+ imxspi_intr, sc);
- imxspi_attach_common(parent, &sc->sc_spi, &saa);
+ imxspi_attach_common(self);
}
diff -r e888d241f292 -r b9e47b794695 sys/arch/arm/imx/imx51reg.h
--- a/sys/arch/arm/imx/imx51reg.h Mon Aug 19 10:56:33 2019 +0000
+++ b/sys/arch/arm/imx/imx51reg.h Mon Aug 19 11:41:36 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: imx51reg.h,v 1.7 2015/05/07 04:37:29 hkenken Exp $ */
+/* $NetBSD: imx51reg.h,v 1.8 2019/08/19 11:41:36 hkenken Exp $ */
/*-
* Copyright (c) 2007 The NetBSD Foundation, Inc.
* All rights reserved.
@@ -140,7 +140,6 @@
#define ECSPI1_BASE (AIPSTZ1_BASE + 0x00010000)
#define ECSPI2_BASE (AIPSTZ2_BASE + 0x03fac000)
-#define ECSPI_SIZE 0x4000
#define SSI1_BASE (AIPSTZ2_BASE + 0x03fcc000)
#define SSI2_BASE (AIPSTZ1_BASE + 0x00014000)
diff -r e888d241f292 -r b9e47b794695 sys/arch/arm/imx/imxspi.c
--- a/sys/arch/arm/imx/imxspi.c Mon Aug 19 10:56:33 2019 +0000
+++ b/sys/arch/arm/imx/imxspi.c Mon Aug 19 11:41:36 2019 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: imxspi.c,v 1.4 2019/08/13 17:03:10 tnn Exp $ */
+/* $NetBSD: imxspi.c,v 1.5 2019/08/19 11:41:36 hkenken Exp $ */
/*-
* Copyright (c) 2014 Genetec Corporation. All rights reserved.
@@ -32,10 +32,11 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: imxspi.c,v 1.4 2019/08/13 17:03:10 tnn Exp $");
+__KERNEL_RCSID(0, "$NetBSD: imxspi.c,v 1.5 2019/08/19 11:41:36 hkenken Exp $");
#include "opt_imx.h"
#include "opt_imxspi.h"
+#include "opt_fdt.h"
#include <sys/param.h>
#include <sys/systm.h>
@@ -52,11 +53,14 @@
Home |
Main Index |
Thread Index |
Old Index