public inbox for u-boot@lists.denx.de
 help / color / mirror / Atom feed
From: Hans de Goede <hdegoede@redhat.com>
To: u-boot@lists.denx.de
Subject: [U-Boot] [PATCH 3/3] ahci: provide sunxi SATA driver using AHCI platform framework
Date: Sat, 19 Jul 2014 14:34:08 +0200	[thread overview]
Message-ID: <53CA65C0.2090406@redhat.com> (raw)
In-Reply-To: <1405712321-12334-3-git-send-email-ijc@hellion.org.uk>

Hi,

On 07/18/2014 09:38 PM, Ian Campbell wrote:
> This enables the necessary clocks, in AHB0 and in PLL6_CFG. This is done
> for sun7i only since I don't have access to any other sunxi platforms
> with sata included.
>
> The PHY setup is derived from the Alwinner releases and Linux, but is mostly
> undocumented.
>
> The Allwinner AHCI controller also requires some magic (and, again,
> undocumented) DMA initialisation when starting a port.  This is added under a
> suitable ifdef.
>
> This option is enabled for Cubieboard, Cubieboard2 and Cubietruck based on
> contents of Linux DTS files, including SATA power pin config taken from the
> DTS. All build tested, but runtime tested on Cubieboard2 and Cubietruck only.
>
> Signed-off-by: Ian Campbell <ijc@hellion.org.uk>

Looks good to me:

Acked-by: Hans de Goede <hdegoede@redhat.com>

Regards,

Hans

> ---
>   arch/arm/cpu/armv7/sunxi/clock_sun4i.c        |  4 ++
>   arch/arm/include/asm/arch-sunxi/clock_sun4i.h | 11 ++--
>   board/sunxi/Makefile                          |  1 +
>   board/sunxi/ahci.c                            | 84 +++++++++++++++++++++++++++
>   boards.cfg                                    | 10 ++--
>   drivers/block/ahci.c                          | 16 +++++
>   include/ahci.h                                |  4 ++
>   include/configs/sunxi-common.h                | 12 ++++
>   8 files changed, 133 insertions(+), 9 deletions(-)
>   create mode 100644 board/sunxi/ahci.c
>
> diff --git a/arch/arm/cpu/armv7/sunxi/clock_sun4i.c b/arch/arm/cpu/armv7/sunxi/clock_sun4i.c
> index b8b16cf..ecbdb01 100644
> --- a/arch/arm/cpu/armv7/sunxi/clock_sun4i.c
> +++ b/arch/arm/cpu/armv7/sunxi/clock_sun4i.c
> @@ -39,6 +39,10 @@ void clock_init_safe(void)
>   	setbits_le32(&ccm->ahb_gate0, 0x1 << AHB_GATE_OFFSET_DMA);
>   #endif
>   	writel(PLL6_CFG_DEFAULT, &ccm->pll6_cfg);
> +#ifdef CONFIG_SUNXI_AHCI
> +	setbits_le32(&ccm->ahb_gate0, 0x1 << AHB_GATE_OFFSET_SATA);
> +	setbits_le32(&ccm->pll6_cfg, 0x1 << CCM_PLL6_CTRL_SATA_EN_SHIFT);
> +#endif
>   }
>   #endif
>
> diff --git a/arch/arm/include/asm/arch-sunxi/clock_sun4i.h b/arch/arm/include/asm/arch-sunxi/clock_sun4i.h
> index 928f3f2..2531cbd 100644
> --- a/arch/arm/include/asm/arch-sunxi/clock_sun4i.h
> +++ b/arch/arm/include/asm/arch-sunxi/clock_sun4i.h
> @@ -218,10 +218,13 @@ struct sunxi_ccm_reg {
>   #define CCM_PLL5_CTRL_BYPASS (0x1 << 30)
>   #define CCM_PLL5_CTRL_EN (0x1 << 31)
>
> -#define CCM_PLL6_CTRL_N_SHIFT	8
> -#define CCM_PLL6_CTRL_N_MASK	(0x1f << CCM_PLL6_CTRL_N_SHIFT)
> -#define CCM_PLL6_CTRL_K_SHIFT	4
> -#define CCM_PLL6_CTRL_K_MASK	(0x3 << CCM_PLL6_CTRL_K_SHIFT)
> +#define CCM_PLL6_CTRL_EN		31
> +#define CCM_PLL6_CTRL_BYPASS_EN		30
> +#define CCM_PLL6_CTRL_SATA_EN_SHIFT	14
> +#define CCM_PLL6_CTRL_N_SHIFT		8
> +#define CCM_PLL6_CTRL_N_MASK		(0x1f << CCM_PLL6_CTRL_N_SHIFT)
> +#define CCM_PLL6_CTRL_K_SHIFT		4
> +#define CCM_PLL6_CTRL_K_MASK		(0x3 << CCM_PLL6_CTRL_K_SHIFT)
>
>   #define CCM_GPS_CTRL_RESET (0x1 << 0)
>   #define CCM_GPS_CTRL_GATE (0x1 << 1)
> diff --git a/board/sunxi/Makefile b/board/sunxi/Makefile
> index 62acb8f..03f55cc 100644
> --- a/board/sunxi/Makefile
> +++ b/board/sunxi/Makefile
> @@ -10,6 +10,7 @@
>   #
>   obj-y	+= board.o
>   obj-$(CONFIG_SUNXI_GMAC)	+= gmac.o
> +obj-$(CONFIG_SUNXI_AHCI)	+= ahci.o
>   obj-$(CONFIG_A13_OLINUXINOM)	+= dram_a13_oli_micro.o
>   obj-$(CONFIG_CUBIEBOARD)	+= dram_cubieboard.o
>   obj-$(CONFIG_CUBIEBOARD2)	+= dram_cubieboard2.o
> diff --git a/board/sunxi/ahci.c b/board/sunxi/ahci.c
> new file mode 100644
> index 0000000..0c262ea
> --- /dev/null
> +++ b/board/sunxi/ahci.c
> @@ -0,0 +1,84 @@
> +#include <common.h>
> +#include <ahci.h>
> +#include <scsi.h>
> +#include <errno.h>
> +#include <asm/io.h>
> +#include <asm/gpio.h>
> +
> +#define AHCI_PHYCS0R 0x00c0
> +#define AHCI_PHYCS1R 0x00c4
> +#define AHCI_PHYCS2R 0x00c8
> +#define AHCI_RWCR    0x00fc
> +
> +/* This magic PHY initialisation was taken from the Allwinner releases
> + * and Linux driver, but is completely undocumented.
> + */
> +static int sunxi_ahci_phy_init(u32 base)
> +{
> +	u8 *reg_base = (u8 *)base;
> +	u32 reg_val;
> +	int timeout;
> +
> +	writel(0, reg_base + AHCI_RWCR);
> +	mdelay(5);
> +
> +	setbits_le32(reg_base + AHCI_PHYCS1R, 0x1 << 19);
> +	clrsetbits_le32(reg_base + AHCI_PHYCS0R,
> +			(0x7 << 24),
> +			(0x5 << 24) | (0x1 << 23) | (0x1 << 18));
> +	clrsetbits_le32(reg_base + AHCI_PHYCS1R,
> +			(0x3 << 16) | (0x1f << 8) | (0x3 << 6),
> +			(0x2 << 16) | (0x6 << 8) | (0x2 << 6));
> +	setbits_le32(reg_base + AHCI_PHYCS1R, (0x1 << 28) | (0x1 << 15));
> +	clrbits_le32(reg_base + AHCI_PHYCS1R, (0x1 << 19));
> +	clrsetbits_le32(reg_base + AHCI_PHYCS0R, (0x7 << 20), (0x3 << 20));
> +	clrsetbits_le32(reg_base + AHCI_PHYCS2R, (0x1f << 5), (0x19 << 5));
> +	mdelay(5);
> +
> +	setbits_le32(reg_base + AHCI_PHYCS0R, (0x1 << 19));
> +
> +	timeout = 250; /* Power up takes approx 50 us */
> +	for (;;) {
> +		reg_val = readl(reg_base + AHCI_PHYCS0R) & (0x7 << 28);
> +		if (reg_val == (0x2 << 28))
> +			break;
> +		if (--timeout == 0) {
> +			printf("AHCI PHY power up failed.\n");
> +			return -EIO;
> +		}
> +		udelay(1);
> +	};
> +
> +	setbits_le32(reg_base + AHCI_PHYCS2R, (0x1 << 24));
> +
> +	timeout = 100; /* Calibration takes approx 10 us */
> +	for (;;) {
> +		reg_val = readl(reg_base + AHCI_PHYCS2R) & (0x1 << 24);
> +		if (reg_val == 0x0)
> +			break;
> +		if (--timeout == 0) {
> +			printf("AHCI PHY calibration failed.\n");
> +			return -EIO;
> +		}
> +		udelay(1);
> +	}
> +
> +	mdelay(15);
> +
> +	writel(0x7, reg_base + AHCI_RWCR);
> +
> +	return 0;
> +}
> +
> +void scsi_init(void)
> +{
> +	printf("SUNXI SCSI INIT\n");
> +#ifdef CONFIG_SATAPWR
> +	gpio_direction_output(CONFIG_SATAPWR, 1);
> +#endif
> +
> +	if (sunxi_ahci_phy_init(SUNXI_SATA_BASE) < 0)
> +		return;
> +
> +	ahci_init(SUNXI_SATA_BASE);
> +}
> diff --git a/boards.cfg b/boards.cfg
> index 035b5c7..f69bd32 100644
> --- a/boards.cfg
> +++ b/boards.cfg
> @@ -378,11 +378,11 @@ Active  arm         armv7          s5pc1xx     samsung         goni
>   Active  arm         armv7          s5pc1xx     samsung         smdkc100            smdkc100                              -                                                                                                                                 Minkyu Kang <mk7.kang@samsung.com>
>   Active  arm         armv7          socfpga     altera          socfpga             socfpga_cyclone5                      -                                                                                                                                 -
>   Active  arm         armv7          sunxi       -               sunxi               A13-OLinuXinoM                        sun5i:A13_OLINUXINOM,SPL,CONS_INDEX=2                                                                                             Hans de Goede <hdegoede@redhat.com>
> -Active  arm         armv7          sunxi       -               sunxi               Cubieboard                            sun4i:CUBIEBOARD,SPL,AXP209_POWER,SUNXI_EMAC                                                                                      Hans de Goede <hdegoede@redhat.com>
> -Active  arm         armv7          sunxi       -               sunxi               Cubieboard2                           sun7i:CUBIEBOARD2,SPL,SUNXI_GMAC                                                                                                  Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
> -Active  arm         armv7          sunxi       -               sunxi               Cubieboard2_FEL                       sun7i:CUBIEBOARD2,SPL_FEL,SUNXI_GMAC                                                                                              Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
> -Active  arm         armv7          sunxi       -               sunxi               Cubietruck                            sun7i:CUBIETRUCK,SPL,AXP209_POWER,SUNXI_GMAC,RGMII                                                                                Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
> -Active  arm         armv7          sunxi       -               sunxi               Cubietruck_FEL                        sun7i:CUBIETRUCK,SPL_FEL,AXP209_POWER,SUNXI_GMAC,RGMII                                                                            Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
> +Active  arm         armv7          sunxi       -               sunxi               Cubieboard                            sun4i:CUBIEBOARD,SPL,AXP209_POWER,SUNXI_EMAC,AHCI,SATAPWR=SUNXI_GPB(8)                                                            Hans de Goede <hdegoede@redhat.com>
> +Active  arm         armv7          sunxi       -               sunxi               Cubieboard2                           sun7i:CUBIEBOARD2,SPL,SUNXI_GMAC,AHCI,SATAPWR=SUNXI_GPB(8)                                                                        Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
> +Active  arm         armv7          sunxi       -               sunxi               Cubieboard2_FEL                       sun7i:CUBIEBOARD2,SPL_FEL,SUNXI_GMAC,AHCI,SATAPWR=SUNXI_GPB(8)                                                                    Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
> +Active  arm         armv7          sunxi       -               sunxi               Cubietruck                            sun7i:CUBIETRUCK,SPL,AXP209_POWER,SUNXI_GMAC,RGMII,AHCI,SATAPWR=SUNXI_GPH(12)                                                     Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
> +Active  arm         armv7          sunxi       -               sunxi               Cubietruck_FEL                        sun7i:CUBIETRUCK,SPL_FEL,AXP209_POWER,SUNXI_GMAC,RGMII,AHCI,SATAPWR=SUNXI_GPH(12)                                                 Ian Campbell <ijc@hellion.org.uk>:Hans de Goede <hdegoede@redhat.com>
>   Active  arm         armv7          sunxi       -               sunxi               r7-tv-dongle                          sun5i:R7DONGLE,SPL,AXP152_POWER                                                                                                   Hans de Goede <hdegoede@redhat.com>
>   Active  arm         armv7          u8500       st-ericsson     snowball            snowball                              -                                                                                                                                 Mathieu Poirier <mathieu.poirier@linaro.org>
>   Active  arm         armv7          u8500       st-ericsson     u8500               u8500_href                            -                                                                                                                                 -
> diff --git a/drivers/block/ahci.c b/drivers/block/ahci.c
> index 4df8046..dce99ad 100644
> --- a/drivers/block/ahci.c
> +++ b/drivers/block/ahci.c
> @@ -129,6 +129,14 @@ int __weak ahci_link_up(struct ahci_probe_ent *probe_ent, u8 port)
>   	return 1;
>   }
>
> +#ifdef CONFIG_SUNXI_AHCI
> +/* The sunxi AHCI controller requires this undocumented setup */
> +static void sunxi_dma_init(volatile u8 *port_mmio)
> +{
> +	clrsetbits_le32(port_mmio + PORT_P0DMACR, 0x0000ff00, 0x00004400);
> +}
> +#endif
> +
>   static int ahci_host_init(struct ahci_probe_ent *probe_ent)
>   {
>   #ifndef CONFIG_SCSI_AHCI_PLAT
> @@ -213,6 +221,10 @@ static int ahci_host_init(struct ahci_probe_ent *probe_ent)
>   			msleep(500);
>   		}
>
> +#ifdef CONFIG_SUNXI_AHCI
> +		sunxi_dma_init(port_mmio);
> +#endif
> +
>   		/* Add the spinup command to whatever mode bits may
>   		 * already be on in the command register.
>   		 */
> @@ -545,6 +557,10 @@ static int ahci_port_start(u8 port)
>
>   	writel_with_flush(pp->rx_fis, port_mmio + PORT_FIS_ADDR);
>
> +#ifdef CONFIG_SUNXI_AHCI
> +	sunxi_dma_init(port_mmio);
> +#endif
> +
>   	writel_with_flush(PORT_CMD_ICC_ACTIVE | PORT_CMD_FIS_RX |
>   			  PORT_CMD_POWER_ON | PORT_CMD_SPIN_UP |
>   			  PORT_CMD_START, port_mmio + PORT_CMD);
> diff --git a/include/ahci.h b/include/ahci.h
> index 90e8509..35b8a8c 100644
> --- a/include/ahci.h
> +++ b/include/ahci.h
> @@ -58,6 +58,10 @@
>   #define PORT_SCR_ERR		0x30 /* SATA phy register: SError */
>   #define PORT_SCR_ACT		0x34 /* SATA phy register: SActive */
>
> +#ifdef CONFIG_SUNXI_AHCI
> +#define PORT_P0DMACR		0x70 /* SUNXI specific "DMA register" */
> +#endif
> +
>   /* PORT_IRQ_{STAT,MASK} bits */
>   #define PORT_IRQ_COLD_PRES	(1 << 31) /* cold presence detect */
>   #define PORT_IRQ_TF_ERR		(1 << 30) /* task file error */
> diff --git a/include/configs/sunxi-common.h b/include/configs/sunxi-common.h
> index 845b004..43eb718 100644
> --- a/include/configs/sunxi-common.h
> +++ b/include/configs/sunxi-common.h
> @@ -57,6 +57,18 @@
>   #define PHYS_SDRAM_0			CONFIG_SYS_SDRAM_BASE
>   #define PHYS_SDRAM_0_SIZE		0x80000000 /* 2 GiB */
>
> +#ifdef CONFIG_AHCI
> +#define CONFIG_LIBATA
> +#define CONFIG_SCSI_AHCI
> +#define CONFIG_SCSI_AHCI_PLAT
> +#define CONFIG_SUNXI_AHCI
> +#define CONFIG_SYS_SCSI_MAX_SCSI_ID	1
> +#define CONFIG_SYS_SCSI_MAX_LUN		1
> +#define CONFIG_SYS_SCSI_MAX_DEVICE	(CONFIG_SYS_SCSI_MAX_SCSI_ID * \
> +					 CONFIG_SYS_SCSI_MAX_LUN)
> +#define CONFIG_CMD_SCSI
> +#endif
> +
>   #define CONFIG_CMD_MEMORY
>   #define CONFIG_CMD_SETEXPR
>
>

  reply	other threads:[~2014-07-19 12:34 UTC|newest]

Thread overview: 17+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2014-07-18 19:38 [U-Boot] [PATCH v3 0/3] sunxi: AHCI support Ian Campbell
2014-07-18 19:38 ` [U-Boot] [PATCH 1/3] AHCI: Increase link timeout to 200ms Ian Campbell
2014-07-19 12:33   ` Hans de Goede
2014-07-19 23:22   ` Wolfgang Denk
2014-07-20  7:06     ` Ian Campbell
2014-07-22 19:24   ` [U-Boot] [U-Boot,1/3] " Tom Rini
2014-07-18 19:38 ` [U-Boot] [PATCH 2/3] board_r: run scsi init() on ARM too Ian Campbell
2014-07-19  3:12   ` Simon Glass
2014-07-21 18:23     ` Ian Campbell
2014-07-22 19:24       ` [U-Boot] [U-Boot,2/3] " Tom Rini
2014-07-18 19:38 ` [U-Boot] [PATCH 3/3] ahci: provide sunxi SATA driver using AHCI platform framework Ian Campbell
2014-07-19 12:34   ` Hans de Goede [this message]
2014-07-22 22:01   ` Tom Rini
2014-07-23  6:59     ` Ian Campbell
2014-07-23  8:14       ` Ian Campbell
2014-07-23 13:04       ` Tom Rini
2014-07-23 13:08         ` [U-Boot] [linux-sunxi] " Ian Campbell

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=53CA65C0.2090406@redhat.com \
    --to=hdegoede@redhat.com \
    --cc=u-boot@lists.denx.de \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox