Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit f3344c54 authored by Linus Torvalds's avatar Linus Torvalds
Browse files
* 'for-linus' of ssh://master.kernel.org/pub/scm/linux/kernel/git/hskinnemoen/avr32-2.6:
  [AVR32] ARRAY_SIZE() cleanup
  [AVR32] Implement at32_add_device_cf()
  [AVR32] Implement more at32_add_device_foo() functions
  [AVR32] Fix a couple of sparse warnings
  [AVR32] Wire up AT73C213 sound driver on ATSTK1000 board
  [AVR32] Platform code for pata_at32
parents ba1c28a9 2298a1dd
Loading
Loading
Loading
Loading
+58 −0
Original line number Diff line number Diff line
@@ -16,6 +16,7 @@
#include <linux/string.h>
#include <linux/types.h>
#include <linux/spi/spi.h>
#include <linux/spi/at73c213.h>

#include <video/atmel_lcdc.h>

@@ -48,8 +49,27 @@ static struct eth_platform_data __initdata eth_data[2] = {
	},
};

#ifndef CONFIG_BOARD_ATSTK1002_SW1_CUSTOM
#ifndef CONFIG_BOARD_ATSTK1002_SW3_CUSTOM
static struct at73c213_board_info at73c213_data = {
	.ssc_id		= 0,
	.shortname	= "AVR32 STK1000 external DAC",
};
#endif
#endif

#ifndef CONFIG_BOARD_ATSTK1002_SW1_CUSTOM
static struct spi_board_info spi0_board_info[] __initdata = {
#ifndef CONFIG_BOARD_ATSTK1002_SW3_CUSTOM
	{
		/* AT73C213 */
		.modalias	= "at73c213",
		.max_speed_hz	= 200000,
		.chip_select	= 0,
		.mode		= SPI_MODE_1,
		.platform_data	= &at73c213_data,
	},
#endif
	{
		/* QVGA display */
		.modalias	= "ltv350qv",
@@ -180,6 +200,38 @@ static void setup_j2_leds(void)
}
#endif

#ifndef CONFIG_BOARD_ATSTK1002_SW1_CUSTOM
#ifndef CONFIG_BOARD_ATSTK1002_SW3_CUSTOM
static void __init at73c213_set_clk(struct at73c213_board_info *info)
{
	struct clk *gclk;
	struct clk *pll;

	gclk = clk_get(NULL, "gclk0");
	if (IS_ERR(gclk))
		goto err_gclk;
	pll = clk_get(NULL, "pll0");
	if (IS_ERR(pll))
		goto err_pll;

	if (clk_set_parent(gclk, pll)) {
		pr_debug("STK1000: failed to set pll0 as parent for DAC clock\n");
		goto err_set_clk;
	}

	at32_select_periph(GPIO_PIN_PA(30), GPIO_PERIPH_A, 0);
	info->dac_clk = gclk;

err_set_clk:
	clk_put(pll);
err_pll:
	clk_put(gclk);
err_gclk:
	return;
}
#endif
#endif

void __init setup_board(void)
{
#ifdef	CONFIG_BOARD_ATSTK1002_SW2_CUSTOM
@@ -248,6 +300,12 @@ static int __init atstk1002_init(void)

	setup_j2_leds();

#ifndef CONFIG_BOARD_ATSTK1002_SW3_CUSTOM
#ifndef CONFIG_BOARD_ATSTK1002_SW1_CUSTOM
	at73c213_set_clk(&at73c213_data);
#endif
#endif

	return 0;
}
postcore_initcall(atstk1002_init);
+344 −0
Original line number Diff line number Diff line
@@ -556,6 +556,17 @@ static struct clk pico_clk = {
	.users		= 1,
};

static struct resource dmaca0_resource[] = {
	{
		.start	= 0xff200000,
		.end	= 0xff20ffff,
		.flags	= IORESOURCE_MEM,
	},
	IRQ(2),
};
DEFINE_DEV(dmaca, 0);
DEV_CLK(hclk, dmaca0, hsb, 10);

/* --------------------------------------------------------------------
 * HMATRIX
 * -------------------------------------------------------------------- */
@@ -655,6 +666,7 @@ void __init at32_add_system_devices(void)
	platform_device_register(&at32_eic0_device);
	platform_device_register(&smc0_device);
	platform_device_register(&pdc_device);
	platform_device_register(&dmaca0_device);

	platform_device_register(&at32_systc0_device);

@@ -959,6 +971,96 @@ at32_add_device_spi(unsigned int id, struct spi_board_info *b, unsigned int n)
	return pdev;
}

/* --------------------------------------------------------------------
 *  TWI
 * -------------------------------------------------------------------- */
static struct resource atmel_twi0_resource[] __initdata = {
	PBMEM(0xffe00800),
	IRQ(5),
};
static struct clk atmel_twi0_pclk = {
	.name		= "twi_pclk",
	.parent		= &pba_clk,
	.mode		= pba_clk_mode,
	.get_rate	= pba_clk_get_rate,
	.index		= 2,
};

struct platform_device *__init at32_add_device_twi(unsigned int id)
{
	struct platform_device *pdev;

	if (id != 0)
		return NULL;

	pdev = platform_device_alloc("atmel_twi", id);
	if (!pdev)
		return NULL;

	if (platform_device_add_resources(pdev, atmel_twi0_resource,
				ARRAY_SIZE(atmel_twi0_resource)))
		goto err_add_resources;

	select_peripheral(PA(6),  PERIPH_A, 0);	/* SDA	*/
	select_peripheral(PA(7),  PERIPH_A, 0);	/* SDL	*/

	atmel_twi0_pclk.dev = &pdev->dev;

	platform_device_add(pdev);
	return pdev;

err_add_resources:
	platform_device_put(pdev);
	return NULL;
}

/* --------------------------------------------------------------------
 * MMC
 * -------------------------------------------------------------------- */
static struct resource atmel_mci0_resource[] __initdata = {
	PBMEM(0xfff02400),
	IRQ(28),
};
static struct clk atmel_mci0_pclk = {
	.name		= "mci_clk",
	.parent		= &pbb_clk,
	.mode		= pbb_clk_mode,
	.get_rate	= pbb_clk_get_rate,
	.index		= 9,
};

struct platform_device *__init at32_add_device_mci(unsigned int id)
{
	struct platform_device *pdev;

	if (id != 0)
		return NULL;

	pdev = platform_device_alloc("atmel_mci", id);
	if (!pdev)
		return NULL;

	if (platform_device_add_resources(pdev, atmel_mci0_resource,
				ARRAY_SIZE(atmel_mci0_resource)))
		goto err_add_resources;

	select_peripheral(PA(10), PERIPH_A, 0);	/* CLK	 */
	select_peripheral(PA(11), PERIPH_A, 0);	/* CMD	 */
	select_peripheral(PA(12), PERIPH_A, 0);	/* DATA0 */
	select_peripheral(PA(13), PERIPH_A, 0);	/* DATA1 */
	select_peripheral(PA(14), PERIPH_A, 0);	/* DATA2 */
	select_peripheral(PA(15), PERIPH_A, 0);	/* DATA3 */

	atmel_mci0_pclk.dev = &pdev->dev;

	platform_device_add(pdev);
	return pdev;

err_add_resources:
	platform_device_put(pdev);
	return NULL;
}

/* --------------------------------------------------------------------
 *  LCDC
 * -------------------------------------------------------------------- */
@@ -1227,6 +1329,241 @@ at32_add_device_usba(unsigned int id, struct usba_platform_data *data)
	return NULL;
}

/* --------------------------------------------------------------------
 * IDE / CompactFlash
 * -------------------------------------------------------------------- */
static struct resource at32_smc_cs4_resource[] __initdata = {
	{
		.start	= 0x04000000,
		.end	= 0x07ffffff,
		.flags	= IORESOURCE_MEM,
	},
	IRQ(~0UL), /* Magic IRQ will be overridden */
};
static struct resource at32_smc_cs5_resource[] __initdata = {
	{
		.start	= 0x20000000,
		.end	= 0x23ffffff,
		.flags	= IORESOURCE_MEM,
	},
	IRQ(~0UL), /* Magic IRQ will be overridden */
};

static int __init at32_init_ide_or_cf(struct platform_device *pdev,
		unsigned int cs, unsigned int extint)
{
	static unsigned int extint_pin_map[4] __initdata = {
		GPIO_PIN_PB(25),
		GPIO_PIN_PB(26),
		GPIO_PIN_PB(27),
		GPIO_PIN_PB(28),
	};
	static bool common_pins_initialized __initdata = false;
	unsigned int extint_pin;
	int ret;

	if (extint >= ARRAY_SIZE(extint_pin_map))
		return -EINVAL;
	extint_pin = extint_pin_map[extint];

	switch (cs) {
	case 4:
		ret = platform_device_add_resources(pdev,
				at32_smc_cs4_resource,
				ARRAY_SIZE(at32_smc_cs4_resource));
		if (ret)
			return ret;

		select_peripheral(PE(21), PERIPH_A, 0); /* NCS4   -> OE_N  */
		set_ebi_sfr_bits(HMATRIX_BIT(CS4A));
		break;
	case 5:
		ret = platform_device_add_resources(pdev,
				at32_smc_cs5_resource,
				ARRAY_SIZE(at32_smc_cs5_resource));
		if (ret)
			return ret;

		select_peripheral(PE(22), PERIPH_A, 0); /* NCS5   -> OE_N  */
		set_ebi_sfr_bits(HMATRIX_BIT(CS5A));
		break;
	default:
		return -EINVAL;
	}

	if (!common_pins_initialized) {
		select_peripheral(PE(19), PERIPH_A, 0);	/* CFCE1  -> CS0_N */
		select_peripheral(PE(20), PERIPH_A, 0);	/* CFCE2  -> CS1_N */
		select_peripheral(PE(23), PERIPH_A, 0); /* CFRNW  -> DIR   */
		select_peripheral(PE(24), PERIPH_A, 0); /* NWAIT  <- IORDY */
		common_pins_initialized = true;
	}

	at32_select_periph(extint_pin, GPIO_PERIPH_A, AT32_GPIOF_DEGLITCH);

	pdev->resource[1].start = EIM_IRQ_BASE + extint;
	pdev->resource[1].end = pdev->resource[1].start;

	return 0;
}

struct platform_device *__init
at32_add_device_ide(unsigned int id, unsigned int extint,
		    struct ide_platform_data *data)
{
	struct platform_device *pdev;

	pdev = platform_device_alloc("at32_ide", id);
	if (!pdev)
		goto fail;

	if (platform_device_add_data(pdev, data,
				sizeof(struct ide_platform_data)))
		goto fail;

	if (at32_init_ide_or_cf(pdev, data->cs, extint))
		goto fail;

	platform_device_add(pdev);
	return pdev;

fail:
	platform_device_put(pdev);
	return NULL;
}

struct platform_device *__init
at32_add_device_cf(unsigned int id, unsigned int extint,
		    struct cf_platform_data *data)
{
	struct platform_device *pdev;

	pdev = platform_device_alloc("at32_cf", id);
	if (!pdev)
		goto fail;

	if (platform_device_add_data(pdev, data,
				sizeof(struct cf_platform_data)))
		goto fail;

	if (at32_init_ide_or_cf(pdev, data->cs, extint))
		goto fail;

	if (data->detect_pin != GPIO_PIN_NONE)
		at32_select_gpio(data->detect_pin, AT32_GPIOF_DEGLITCH);
	if (data->reset_pin != GPIO_PIN_NONE)
		at32_select_gpio(data->reset_pin, 0);
	if (data->vcc_pin != GPIO_PIN_NONE)
		at32_select_gpio(data->vcc_pin, 0);
	/* READY is used as extint, so we can't select it as gpio */

	platform_device_add(pdev);
	return pdev;

fail:
	platform_device_put(pdev);
	return NULL;
}

/* --------------------------------------------------------------------
 * AC97C
 * -------------------------------------------------------------------- */
static struct resource atmel_ac97c0_resource[] __initdata = {
	PBMEM(0xfff02800),
	IRQ(29),
};
static struct clk atmel_ac97c0_pclk = {
	.name		= "pclk",
	.parent		= &pbb_clk,
	.mode		= pbb_clk_mode,
	.get_rate	= pbb_clk_get_rate,
	.index		= 10,
};

struct platform_device *__init at32_add_device_ac97c(unsigned int id)
{
	struct platform_device *pdev;

	if (id != 0)
		return NULL;

	pdev = platform_device_alloc("atmel_ac97c", id);
	if (!pdev)
		return NULL;

	if (platform_device_add_resources(pdev, atmel_ac97c0_resource,
				ARRAY_SIZE(atmel_ac97c0_resource)))
		goto err_add_resources;

	select_peripheral(PB(20), PERIPH_B, 0);	/* SYNC	*/
	select_peripheral(PB(21), PERIPH_B, 0);	/* SDO	*/
	select_peripheral(PB(22), PERIPH_B, 0);	/* SDI	*/
	select_peripheral(PB(23), PERIPH_B, 0);	/* SCLK	*/

	atmel_ac97c0_pclk.dev = &pdev->dev;

	platform_device_add(pdev);
	return pdev;

err_add_resources:
	platform_device_put(pdev);
	return NULL;
}

/* --------------------------------------------------------------------
 * ABDAC
 * -------------------------------------------------------------------- */
static struct resource abdac0_resource[] __initdata = {
	PBMEM(0xfff02000),
	IRQ(27),
};
static struct clk abdac0_pclk = {
	.name		= "pclk",
	.parent		= &pbb_clk,
	.mode		= pbb_clk_mode,
	.get_rate	= pbb_clk_get_rate,
	.index		= 8,
};
static struct clk abdac0_sample_clk = {
	.name		= "sample_clk",
	.mode		= genclk_mode,
	.get_rate	= genclk_get_rate,
	.set_rate	= genclk_set_rate,
	.set_parent	= genclk_set_parent,
	.index		= 6,
};

struct platform_device *__init at32_add_device_abdac(unsigned int id)
{
	struct platform_device *pdev;

	if (id != 0)
		return NULL;

	pdev = platform_device_alloc("abdac", id);
	if (!pdev)
		return NULL;

	if (platform_device_add_resources(pdev, abdac0_resource,
				ARRAY_SIZE(abdac0_resource)))
		goto err_add_resources;

	select_peripheral(PB(20), PERIPH_A, 0);	/* DATA1	*/
	select_peripheral(PB(21), PERIPH_A, 0);	/* DATA0	*/
	select_peripheral(PB(22), PERIPH_A, 0);	/* DATAN1	*/
	select_peripheral(PB(23), PERIPH_A, 0);	/* DATAN0	*/

	abdac0_pclk.dev = &pdev->dev;
	abdac0_sample_clk.dev = &pdev->dev;

	platform_device_add(pdev);
	return pdev;

err_add_resources:
	platform_device_put(pdev);
	return NULL;
}

/* --------------------------------------------------------------------
 *  GCLK
 * -------------------------------------------------------------------- */
@@ -1290,6 +1627,7 @@ struct clk *at32_clock_list[] = {
	&smc0_mck,
	&pdc_hclk,
	&pdc_pclk,
	&dmaca0_hclk,
	&pico_clk,
	&pio0_mck,
	&pio1_mck,
@@ -1307,6 +1645,8 @@ struct clk *at32_clock_list[] = {
	&macb1_pclk,
	&atmel_spi0_spi_clk,
	&atmel_spi1_spi_clk,
	&atmel_twi0_pclk,
	&atmel_mci0_pclk,
	&atmel_lcdfb0_hck1,
	&atmel_lcdfb0_pixclk,
	&ssc0_pclk,
@@ -1314,6 +1654,9 @@ struct clk *at32_clock_list[] = {
	&ssc2_pclk,
	&usba0_hclk,
	&usba0_pclk,
	&atmel_ac97c0_pclk,
	&abdac0_pclk,
	&abdac0_sample_clk,
	&gclk0,
	&gclk1,
	&gclk2,
@@ -1355,6 +1698,7 @@ void __init at32_clock_init(void)
	genclk_init_parent(&gclk3);
	genclk_init_parent(&gclk4);
	genclk_init_parent(&atmel_lcdfb0_pixclk);
	genclk_init_parent(&abdac0_sample_clk);

	/*
	 * Turn on all clocks that have at least one user already, and
+1 −1
Original line number Diff line number Diff line
@@ -142,7 +142,7 @@ static int eic_set_irq_type(unsigned int irq, unsigned int flow_type)
	return ret;
}

struct irq_chip eic_chip = {
static struct irq_chip eic_chip = {
	.name		= "eic",
	.ack		= eic_ack_irq,
	.mask		= eic_mask_irq,
+2 −2
Original line number Diff line number Diff line
@@ -113,8 +113,8 @@

/* Register access macros */
#define pm_readl(reg)							\
	__raw_readl((void __iomem *)AT32_PM_BASE + PM_##reg)
	__raw_readl((void __iomem __force *)AT32_PM_BASE + PM_##reg)
#define pm_writel(reg,value)						\
	__raw_writel((value), (void __iomem *)AT32_PM_BASE + PM_##reg)
	__raw_writel((value), (void __iomem __force *)AT32_PM_BASE + PM_##reg)

#endif /* __ARCH_AVR32_MACH_AT32AP_PM_H__ */
+1 −1
Original line number Diff line number Diff line
@@ -79,7 +79,7 @@ static int avr32_timer_calc_div_and_set_jiffies(struct clk *pclk)
{
	unsigned int cycles_max = (clocksource_avr32.mask + 1) / 2;
	unsigned int divs[] = { 4, 8, 16, 32 };
	int divs_size = sizeof(divs) / sizeof(*divs);
	int divs_size = ARRAY_SIZE(divs);
	int i = 0;
	unsigned long count_hz;
	unsigned long shift;
Loading