diff --git a/Documentation/arm/Samsung-S3C24XX/DMA.txt b/Documentation/arm/Samsung-S3C24XX/DMA.txt
new file mode 100644
index 000000000000..37f4edcc5d87
--- /dev/null
+++ b/Documentation/arm/Samsung-S3C24XX/DMA.txt
@@ -0,0 +1,46 @@
+ S3C2410 DMA
+ ===========
+
+Introduction
+------------
+
+ The kernel provides an interface to manage DMA transfers
+ using the DMA channels in the cpu, so that the central
+ duty of managing channel mappings, and programming the
+ channel generators is in one place.
+
+
+DMA Channel Ordering
+--------------------
+
+ Many of the range do not have connections for the DMA
+ channels to all sources, which means that some devices
+ have a restricted number of channels that can be used.
+
+ To allow flexibilty for each cpu type and board, the
+ dma code can be given an dma ordering structure which
+ allows the order of channel search to be specified, as
+ well as allowing the prohibition of certain claims.
+
+ struct s3c24xx_dma_order has a list of channels, and
+ each channel within has a slot for a list of dma
+ channel numbers. The slots are searched in order, for
+ the presence of a dma channel number with DMA_CH_VALID
+ orred in.
+
+ If the order has the flag DMA_CH_NEVER set, then after
+ checking the channel list, the system will return no
+ found channel, thus denying the request.
+
+ A board support file can call s3c24xx_dma_order_set()
+ to register an complete ordering set. The routine will
+ copy the data, so the original can be discared with
+ __initdata.
+
+
+Authour
+-------
+
+Ben Dooks,
+Copyright (c) 2007 Ben Dooks, Simtec Electronics
+Licensed under the GPL v2
diff --git a/Documentation/arm/Samsung-S3C24XX/Overview.txt b/Documentation/arm/Samsung-S3C24XX/Overview.txt
index 28d014714ab8..c31b76fa66c4 100644
--- a/Documentation/arm/Samsung-S3C24XX/Overview.txt
+++ b/Documentation/arm/Samsung-S3C24XX/Overview.txt
@@ -8,13 +8,10 @@ Introduction
The Samsung S3C24XX range of ARM9 System-on-Chip CPUs are supported
by the 's3c2410' architecture of ARM Linux. Currently the S3C2410,
- S3C2440 and S3C2442 devices are supported.
+ S3C2412, S3C2413, S3C2440 and S3C2442 devices are supported.
Support for the S3C2400 series is in progress.
- Support for the S3C2412 and S3C2413 CPUs is being merged.
-
-
Configuration
-------------
@@ -26,6 +23,22 @@ Configuration
please check the machine specific documentation.
+Layout
+------
+
+ The core support files are located in the platform code contained in
+ arch/arm/plat-s3c24xx with headers in include/asm-arm/plat-s3c24xx.
+ This directory should be kept to items shared between the platform
+ code (arch/arm/plat-s3c24xx) and the arch/arm/mach-s3c24* code.
+
+ Each cpu has a directory with the support files for it, and the
+ machines that carry the device. For example S3C2410 is contained
+ in arch/arm/mach-s3c2410 and S3C2440 in arch/arm/mach-s3c2440
+
+ Register, kernel and platform data definitions are held in the
+ include/asm-arm/arch-s3c2410 directory.
+
+
Machines
--------
diff --git a/arch/arm/Kconfig b/arch/arm/Kconfig
index a8298949d166..195650935c78 100644
--- a/arch/arm/Kconfig
+++ b/arch/arm/Kconfig
@@ -280,6 +280,7 @@ config ARCH_PXA
bool "PXA2xx-based"
depends on MMU
select ARCH_MTD_XIP
+ select GENERIC_TIME
help
Support for Intel's PXA2XX processor line.
@@ -303,7 +304,7 @@ config ARCH_SA1100
Support for StrongARM 11x0 based boards.
config ARCH_S3C2410
- bool "Samsung S3C2410, S3C2412, S3C2413, S3C2440, S3C2442"
+ bool "Samsung S3C2410, S3C2412, S3C2413, S3C2440, S3C2442, S3C2443"
help
Samsung S3C2410X CPU based systems, such as the Simtec Electronics
BAST (), the IPAQ 1940 or
@@ -363,7 +364,16 @@ source "arch/arm/mach-omap1/Kconfig"
source "arch/arm/mach-omap2/Kconfig"
+source "arch/arm/plat-s3c24xx/Kconfig"
+
+if ARCH_S3C2410
+source "arch/arm/mach-s3c2400/Kconfig"
source "arch/arm/mach-s3c2410/Kconfig"
+source "arch/arm/mach-s3c2412/Kconfig"
+source "arch/arm/mach-s3c2440/Kconfig"
+source "arch/arm/mach-s3c2442/Kconfig"
+source "arch/arm/mach-s3c2443/Kconfig"
+endif
source "arch/arm/mach-lh7a40x/Kconfig"
@@ -377,7 +387,7 @@ source "arch/arm/mach-aaec2000/Kconfig"
source "arch/arm/mach-realview/Kconfig"
-source "arch/arm/mach-at91rm9200/Kconfig"
+source "arch/arm/mach-at91/Kconfig"
source "arch/arm/mach-netx/Kconfig"
diff --git a/arch/arm/Makefile b/arch/arm/Makefile
index 000f1100b553..2cd871c82c96 100644
--- a/arch/arm/Makefile
+++ b/arch/arm/Makefile
@@ -124,7 +124,7 @@ endif
machine-$(CONFIG_ARCH_H720X) := h720x
machine-$(CONFIG_ARCH_AAEC2000) := aaec2000
machine-$(CONFIG_ARCH_REALVIEW) := realview
- machine-$(CONFIG_ARCH_AT91) := at91rm9200
+ machine-$(CONFIG_ARCH_AT91) := at91
machine-$(CONFIG_ARCH_EP93XX) := ep93xx
machine-$(CONFIG_ARCH_PNX4008) := pnx4008
machine-$(CONFIG_ARCH_NETX) := netx
@@ -149,7 +149,7 @@ MACHINE := arch/arm/mach-$(machine-y)/
else
MACHINE :=
endif
-
+
export TEXT_OFFSET GZFLAGS MMUEXT
# Do we have FASTFPE?
@@ -161,6 +161,11 @@ endif
# If we have a machine-specific directory, then include it in the build.
core-y += arch/arm/kernel/ arch/arm/mm/ arch/arm/common/
core-y += $(MACHINE)
+core-$(CONFIG_ARCH_S3C2410) += arch/arm/mach-s3c2400/
+core-$(CONFIG_ARCH_S3C2410) += arch/arm/mach-s3c2412/
+core-$(CONFIG_ARCH_S3C2410) += arch/arm/mach-s3c2440/
+core-$(CONFIG_ARCH_S3C2410) += arch/arm/mach-s3c2442/
+core-$(CONFIG_ARCH_S3C2410) += arch/arm/mach-s3c2443/
core-$(CONFIG_FPE_NWFPE) += arch/arm/nwfpe/
core-$(CONFIG_FPE_FASTFPE) += $(FASTFPE_OBJ)
core-$(CONFIG_VFP) += arch/arm/vfp/
@@ -168,6 +173,7 @@ core-$(CONFIG_VFP) += arch/arm/vfp/
# If we have a common platform directory, then include it in the build.
core-$(CONFIG_PLAT_IOP) += arch/arm/plat-iop/
core-$(CONFIG_ARCH_OMAP) += arch/arm/plat-omap/
+core-$(CONFIG_PLAT_S3C24XX) += arch/arm/plat-s3c24xx/
drivers-$(CONFIG_OPROFILE) += arch/arm/oprofile/
drivers-$(CONFIG_ARCH_CLPS7500) += drivers/acorn/char/
diff --git a/arch/arm/common/dmabounce.c b/arch/arm/common/dmabounce.c
index 4d5b031ac745..6fbe7722aa44 100644
--- a/arch/arm/common/dmabounce.c
+++ b/arch/arm/common/dmabounce.c
@@ -258,10 +258,14 @@ map_single(struct device *dev, void *ptr, size_t size,
ptr = buf->safe;
dma_addr = buf->safe_dma_addr;
+ } else {
+ /*
+ * We don't need to sync the DMA buffer since
+ * it was allocated via the coherent allocators.
+ */
+ consistent_sync(ptr, size, dir);
}
- consistent_sync(ptr, size, dir);
-
return dma_addr;
}
@@ -294,12 +298,12 @@ unmap_single(struct device *dev, dma_addr_t dma_addr, size_t size,
DO_STATS ( device_info->bounce_count++ );
if (dir == DMA_FROM_DEVICE || dir == DMA_BIDIRECTIONAL) {
- unsigned long ptr;
+ void *ptr = buf->ptr;
dev_dbg(dev,
"%s: copy back safe %p to unsafe %p size %d\n",
- __func__, buf->safe, buf->ptr, size);
- memcpy(buf->ptr, buf->safe, size);
+ __func__, buf->safe, ptr, size);
+ memcpy(ptr, buf->safe, size);
/*
* DMA buffers must have the same cache properties
@@ -309,8 +313,8 @@ unmap_single(struct device *dev, dma_addr_t dma_addr, size_t size,
* bidirectional case because we know the cache
* lines will be coherent with the data written.
*/
- ptr = (unsigned long)buf->ptr;
dmac_clean_range(ptr, ptr + size);
+ outer_clean_range(__pa(ptr), __pa(ptr) + size);
}
free_safe_buffer(device_info, buf);
}
@@ -374,7 +378,10 @@ sync_single(struct device *dev, dma_addr_t dma_addr, size_t size,
default:
BUG();
}
- consistent_sync(buf->safe, size, dir);
+ /*
+ * No need to sync the safe buffer - it was allocated
+ * via the coherent allocators.
+ */
} else {
consistent_sync(dma_to_virt(dev, dma_addr), size, dir);
}
diff --git a/arch/arm/common/gic.c b/arch/arm/common/gic.c
index 09b9d1b6844c..4deece5fbdf4 100644
--- a/arch/arm/common/gic.c
+++ b/arch/arm/common/gic.c
@@ -14,7 +14,9 @@
*
* o There is one CPU Interface per CPU, which sends interrupts sent
* by the Distributor, and interrupts generated locally, to the
- * associated CPU.
+ * associated CPU. The base address of the CPU interface is usually
+ * aliased so that the same address points to different chips depending
+ * on the CPU it is accessed from.
*
* Note that IRQs 0-31 are special - they are local to each CPU.
* As such, the enable set/clear, pending set/clear and active bit
@@ -31,10 +33,38 @@
#include
#include
-static void __iomem *gic_dist_base;
-static void __iomem *gic_cpu_base;
static DEFINE_SPINLOCK(irq_controller_lock);
+struct gic_chip_data {
+ unsigned int irq_offset;
+ void __iomem *dist_base;
+ void __iomem *cpu_base;
+};
+
+#ifndef MAX_GIC_NR
+#define MAX_GIC_NR 1
+#endif
+
+static struct gic_chip_data gic_data[MAX_GIC_NR];
+
+static inline void __iomem *gic_dist_base(unsigned int irq)
+{
+ struct gic_chip_data *gic_data = get_irq_chip_data(irq);
+ return gic_data->dist_base;
+}
+
+static inline void __iomem *gic_cpu_base(unsigned int irq)
+{
+ struct gic_chip_data *gic_data = get_irq_chip_data(irq);
+ return gic_data->cpu_base;
+}
+
+static inline unsigned int gic_irq(unsigned int irq)
+{
+ struct gic_chip_data *gic_data = get_irq_chip_data(irq);
+ return irq - gic_data->irq_offset;
+}
+
/*
* Routines to acknowledge, disable and enable interrupts
*
@@ -55,8 +85,8 @@ static void gic_ack_irq(unsigned int irq)
u32 mask = 1 << (irq % 32);
spin_lock(&irq_controller_lock);
- writel(mask, gic_dist_base + GIC_DIST_ENABLE_CLEAR + (irq / 32) * 4);
- writel(irq, gic_cpu_base + GIC_CPU_EOI);
+ writel(mask, gic_dist_base(irq) + GIC_DIST_ENABLE_CLEAR + (gic_irq(irq) / 32) * 4);
+ writel(gic_irq(irq), gic_cpu_base(irq) + GIC_CPU_EOI);
spin_unlock(&irq_controller_lock);
}
@@ -65,7 +95,7 @@ static void gic_mask_irq(unsigned int irq)
u32 mask = 1 << (irq % 32);
spin_lock(&irq_controller_lock);
- writel(mask, gic_dist_base + GIC_DIST_ENABLE_CLEAR + (irq / 32) * 4);
+ writel(mask, gic_dist_base(irq) + GIC_DIST_ENABLE_CLEAR + (gic_irq(irq) / 32) * 4);
spin_unlock(&irq_controller_lock);
}
@@ -74,14 +104,14 @@ static void gic_unmask_irq(unsigned int irq)
u32 mask = 1 << (irq % 32);
spin_lock(&irq_controller_lock);
- writel(mask, gic_dist_base + GIC_DIST_ENABLE_SET + (irq / 32) * 4);
+ writel(mask, gic_dist_base(irq) + GIC_DIST_ENABLE_SET + (gic_irq(irq) / 32) * 4);
spin_unlock(&irq_controller_lock);
}
#ifdef CONFIG_SMP
static void gic_set_cpu(unsigned int irq, cpumask_t mask_val)
{
- void __iomem *reg = gic_dist_base + GIC_DIST_TARGET + (irq & ~3);
+ void __iomem *reg = gic_dist_base(irq) + GIC_DIST_TARGET + (gic_irq(irq) & ~3);
unsigned int shift = (irq % 4) * 8;
unsigned int cpu = first_cpu(mask_val);
u32 val;
@@ -95,6 +125,37 @@ static void gic_set_cpu(unsigned int irq, cpumask_t mask_val)
}
#endif
+static void fastcall gic_handle_cascade_irq(unsigned int irq,
+ struct irq_desc *desc)
+{
+ struct gic_chip_data *chip_data = get_irq_data(irq);
+ struct irq_chip *chip = get_irq_chip(irq);
+ unsigned int cascade_irq;
+ unsigned long status;
+
+ /* primary controller ack'ing */
+ chip->ack(irq);
+
+ spin_lock(&irq_controller_lock);
+ status = readl(chip_data->cpu_base + GIC_CPU_INTACK);
+ spin_unlock(&irq_controller_lock);
+
+ cascade_irq = (status & 0x3ff);
+ if (cascade_irq > 1020)
+ goto out;
+ if (cascade_irq < 32 || cascade_irq >= NR_IRQS) {
+ do_bad_IRQ(cascade_irq, desc);
+ goto out;
+ }
+
+ cascade_irq += chip_data->irq_offset;
+ generic_handle_irq(cascade_irq);
+
+ out:
+ /* primary controller unmasking */
+ chip->unmask(irq);
+}
+
static struct irq_chip gic_chip = {
.name = "GIC",
.ack = gic_ack_irq,
@@ -105,15 +166,29 @@ static struct irq_chip gic_chip = {
#endif
};
-void __init gic_dist_init(void __iomem *base)
+void __init gic_cascade_irq(unsigned int gic_nr, unsigned int irq)
+{
+ if (gic_nr >= MAX_GIC_NR)
+ BUG();
+ if (set_irq_data(irq, &gic_data[gic_nr]) != 0)
+ BUG();
+ set_irq_chained_handler(irq, gic_handle_cascade_irq);
+}
+
+void __init gic_dist_init(unsigned int gic_nr, void __iomem *base,
+ unsigned int irq_start)
{
unsigned int max_irq, i;
u32 cpumask = 1 << smp_processor_id();
+ if (gic_nr >= MAX_GIC_NR)
+ BUG();
+
cpumask |= cpumask << 8;
cpumask |= cpumask << 16;
- gic_dist_base = base;
+ gic_data[gic_nr].dist_base = base;
+ gic_data[gic_nr].irq_offset = (irq_start - 1) & ~31;
writel(0, base + GIC_DIST_CTRL);
@@ -158,8 +233,9 @@ void __init gic_dist_init(void __iomem *base)
/*
* Setup the Linux IRQ subsystem.
*/
- for (i = 29; i < max_irq; i++) {
+ for (i = irq_start; i < gic_data[gic_nr].irq_offset + max_irq; i++) {
set_irq_chip(i, &gic_chip);
+ set_irq_chip_data(i, &gic_data[gic_nr]);
set_irq_handler(i, handle_level_irq);
set_irq_flags(i, IRQF_VALID | IRQF_PROBE);
}
@@ -167,9 +243,13 @@ void __init gic_dist_init(void __iomem *base)
writel(1, base + GIC_DIST_CTRL);
}
-void __cpuinit gic_cpu_init(void __iomem *base)
+void __cpuinit gic_cpu_init(unsigned int gic_nr, void __iomem *base)
{
- gic_cpu_base = base;
+ if (gic_nr >= MAX_GIC_NR)
+ BUG();
+
+ gic_data[gic_nr].cpu_base = base;
+
writel(0xf0, base + GIC_CPU_PRIMASK);
writel(1, base + GIC_CPU_CTRL);
}
@@ -179,6 +259,7 @@ void gic_raise_softirq(cpumask_t cpumask, unsigned int irq)
{
unsigned long map = *cpus_addr(cpumask);
- writel(map << 16 | irq, gic_dist_base + GIC_DIST_SOFTINT);
+ /* this always happens on GIC0 */
+ writel(map << 16 | irq, gic_data[0].dist_base + GIC_DIST_SOFTINT);
}
#endif
diff --git a/arch/arm/configs/at91sam9263ek_defconfig b/arch/arm/configs/at91sam9263ek_defconfig
new file mode 100644
index 000000000000..c72ab82873d5
--- /dev/null
+++ b/arch/arm/configs/at91sam9263ek_defconfig
@@ -0,0 +1,1184 @@
+#
+# Automatically generated make config: don't edit
+# Linux kernel version: 2.6.20-rc1
+# Mon Jan 8 16:06:54 2007
+#
+CONFIG_ARM=y
+# CONFIG_GENERIC_TIME is not set
+CONFIG_MMU=y
+CONFIG_GENERIC_HARDIRQS=y
+CONFIG_TRACE_IRQFLAGS_SUPPORT=y
+CONFIG_HARDIRQS_SW_RESEND=y
+CONFIG_GENERIC_IRQ_PROBE=y
+CONFIG_RWSEM_GENERIC_SPINLOCK=y
+# CONFIG_ARCH_HAS_ILOG2_U32 is not set
+# CONFIG_ARCH_HAS_ILOG2_U64 is not set
+CONFIG_GENERIC_HWEIGHT=y
+CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_VECTORS_BASE=0xffff0000
+CONFIG_DEFCONFIG_LIST="/lib/modules/$UNAME_RELEASE/.config"
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_BROKEN_ON_SMP=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
+
+#
+# General setup
+#
+CONFIG_LOCALVERSION=""
+# CONFIG_LOCALVERSION_AUTO is not set
+# CONFIG_SWAP is not set
+CONFIG_SYSVIPC=y
+# CONFIG_IPC_NS is not set
+# CONFIG_POSIX_MQUEUE is not set
+# CONFIG_BSD_PROCESS_ACCT is not set
+# CONFIG_TASKSTATS is not set
+# CONFIG_UTS_NS is not set
+# CONFIG_AUDIT is not set
+# CONFIG_IKCONFIG is not set
+CONFIG_SYSFS_DEPRECATED=y
+# CONFIG_RELAY is not set
+CONFIG_INITRAMFS_SOURCE=""
+CONFIG_CC_OPTIMIZE_FOR_SIZE=y
+CONFIG_SYSCTL=y
+# CONFIG_EMBEDDED is not set
+CONFIG_UID16=y
+CONFIG_SYSCTL_SYSCALL=y
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_ALL is not set
+# CONFIG_KALLSYMS_EXTRA_PASS is not set
+CONFIG_HOTPLUG=y
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_ELF_CORE=y
+CONFIG_BASE_FULL=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_SHMEM=y
+CONFIG_SLAB=y
+CONFIG_VM_EVENT_COUNTERS=y
+CONFIG_RT_MUTEXES=y
+# CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
+# CONFIG_SLOB is not set
+
+#
+# Loadable module support
+#
+CONFIG_MODULES=y
+CONFIG_MODULE_UNLOAD=y
+# CONFIG_MODULE_FORCE_UNLOAD is not set
+# CONFIG_MODVERSIONS is not set
+# CONFIG_MODULE_SRCVERSION_ALL is not set
+CONFIG_KMOD=y
+
+#
+# Block layer
+#
+CONFIG_BLOCK=y
+# CONFIG_LBD is not set
+# CONFIG_BLK_DEV_IO_TRACE is not set
+# CONFIG_LSF is not set
+
+#
+# IO Schedulers
+#
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+# CONFIG_IOSCHED_DEADLINE is not set
+# CONFIG_IOSCHED_CFQ is not set
+CONFIG_DEFAULT_AS=y
+# CONFIG_DEFAULT_DEADLINE is not set
+# CONFIG_DEFAULT_CFQ is not set
+# CONFIG_DEFAULT_NOOP is not set
+CONFIG_DEFAULT_IOSCHED="anticipatory"
+
+#
+# System Type
+#
+# CONFIG_ARCH_AAEC2000 is not set
+# CONFIG_ARCH_INTEGRATOR is not set
+# CONFIG_ARCH_REALVIEW is not set
+# CONFIG_ARCH_VERSATILE is not set
+CONFIG_ARCH_AT91=y
+# CONFIG_ARCH_CLPS7500 is not set
+# CONFIG_ARCH_CLPS711X is not set
+# CONFIG_ARCH_CO285 is not set
+# CONFIG_ARCH_EBSA110 is not set
+# CONFIG_ARCH_EP93XX is not set
+# CONFIG_ARCH_FOOTBRIDGE is not set
+# CONFIG_ARCH_NETX is not set
+# CONFIG_ARCH_H720X is not set
+# CONFIG_ARCH_IMX is not set
+# CONFIG_ARCH_IOP32X is not set
+# CONFIG_ARCH_IOP33X is not set
+# CONFIG_ARCH_IOP13XX is not set
+# CONFIG_ARCH_IXP4XX is not set
+# CONFIG_ARCH_IXP2000 is not set
+# CONFIG_ARCH_IXP23XX is not set
+# CONFIG_ARCH_L7200 is not set
+# CONFIG_ARCH_PNX4008 is not set
+# CONFIG_ARCH_PXA is not set
+# CONFIG_ARCH_RPC is not set
+# CONFIG_ARCH_SA1100 is not set
+# CONFIG_ARCH_S3C2410 is not set
+# CONFIG_ARCH_SHARK is not set
+# CONFIG_ARCH_LH7A40X is not set
+# CONFIG_ARCH_OMAP is not set
+
+#
+# Atmel AT91 System-on-Chip
+#
+# CONFIG_ARCH_AT91RM9200 is not set
+# CONFIG_ARCH_AT91SAM9260 is not set
+# CONFIG_ARCH_AT91SAM9261 is not set
+CONFIG_ARCH_AT91SAM9263=y
+
+#
+# AT91SAM9263 Board Type
+#
+CONFIG_MACH_AT91SAM9263EK=y
+
+#
+# AT91 Board Options
+#
+CONFIG_MTD_AT91_DATAFLASH_CARD=y
+# CONFIG_MTD_NAND_AT91_BUSWIDTH_16 is not set
+
+#
+# AT91 Feature Selections
+#
+# CONFIG_AT91_PROGRAMMABLE_CLOCKS is not set
+
+#
+# Processor Type
+#
+CONFIG_CPU_32=y
+CONFIG_CPU_ARM926T=y
+CONFIG_CPU_32v5=y
+CONFIG_CPU_ABRT_EV5TJ=y
+CONFIG_CPU_CACHE_VIVT=y
+CONFIG_CPU_COPY_V4WB=y
+CONFIG_CPU_TLB_V4WBI=y
+CONFIG_CPU_CP15=y
+CONFIG_CPU_CP15_MMU=y
+
+#
+# Processor Features
+#
+# CONFIG_ARM_THUMB is not set
+# CONFIG_CPU_ICACHE_DISABLE is not set
+# CONFIG_CPU_DCACHE_DISABLE is not set
+# CONFIG_CPU_DCACHE_WRITETHROUGH is not set
+# CONFIG_CPU_CACHE_ROUND_ROBIN is not set
+
+#
+# Bus support
+#
+
+#
+# PCCARD (PCMCIA/CardBus) support
+#
+# CONFIG_PCCARD is not set
+
+#
+# Kernel Features
+#
+# CONFIG_PREEMPT is not set
+# CONFIG_NO_IDLE_HZ is not set
+CONFIG_HZ=100
+# CONFIG_AEABI is not set
+# CONFIG_ARCH_DISCONTIGMEM_ENABLE is not set
+CONFIG_SELECT_MEMORY_MODEL=y
+CONFIG_FLATMEM_MANUAL=y
+# CONFIG_DISCONTIGMEM_MANUAL is not set
+# CONFIG_SPARSEMEM_MANUAL is not set
+CONFIG_FLATMEM=y
+CONFIG_FLAT_NODE_MEM_MAP=y
+# CONFIG_SPARSEMEM_STATIC is not set
+CONFIG_SPLIT_PTLOCK_CPUS=4096
+# CONFIG_RESOURCES_64BIT is not set
+# CONFIG_LEDS is not set
+CONFIG_ALIGNMENT_TRAP=y
+
+#
+# Boot options
+#
+CONFIG_ZBOOT_ROM_TEXT=0x0
+CONFIG_ZBOOT_ROM_BSS=0x0
+CONFIG_CMDLINE="mem=64M console=ttyS0,115200 initrd=0x21100000,3145728 root=/dev/ram0 rw"
+# CONFIG_XIP_KERNEL is not set
+
+#
+# Floating point emulation
+#
+
+#
+# At least one emulation must be selected
+#
+CONFIG_FPE_NWFPE=y
+# CONFIG_FPE_NWFPE_XP is not set
+# CONFIG_FPE_FASTFPE is not set
+# CONFIG_VFP is not set
+
+#
+# Userspace binary formats
+#
+CONFIG_BINFMT_ELF=y
+# CONFIG_BINFMT_AOUT is not set
+# CONFIG_BINFMT_MISC is not set
+# CONFIG_ARTHUR is not set
+
+#
+# Power management options
+#
+# CONFIG_PM is not set
+# CONFIG_APM is not set
+
+#
+# Networking
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+# CONFIG_NETDEBUG is not set
+CONFIG_PACKET=y
+# CONFIG_PACKET_MMAP is not set
+CONFIG_UNIX=y
+# CONFIG_NET_KEY is not set
+CONFIG_INET=y
+# CONFIG_IP_MULTICAST is not set
+# CONFIG_IP_ADVANCED_ROUTER is not set
+CONFIG_IP_FIB_HASH=y
+CONFIG_IP_PNP=y
+# CONFIG_IP_PNP_DHCP is not set
+CONFIG_IP_PNP_BOOTP=y
+CONFIG_IP_PNP_RARP=y
+# CONFIG_NET_IPIP is not set
+# CONFIG_NET_IPGRE is not set
+# CONFIG_ARPD is not set
+# CONFIG_SYN_COOKIES is not set
+# CONFIG_INET_AH is not set
+# CONFIG_INET_ESP is not set
+# CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_XFRM_TUNNEL is not set
+# CONFIG_INET_TUNNEL is not set
+# CONFIG_INET_XFRM_MODE_TRANSPORT is not set
+# CONFIG_INET_XFRM_MODE_TUNNEL is not set
+# CONFIG_INET_XFRM_MODE_BEET is not set
+# CONFIG_INET_DIAG is not set
+# CONFIG_TCP_CONG_ADVANCED is not set
+CONFIG_TCP_CONG_CUBIC=y
+CONFIG_DEFAULT_TCP_CONG="cubic"
+# CONFIG_TCP_MD5SIG is not set
+# CONFIG_IPV6 is not set
+# CONFIG_INET6_XFRM_TUNNEL is not set
+# CONFIG_INET6_TUNNEL is not set
+# CONFIG_NETWORK_SECMARK is not set
+# CONFIG_NETFILTER is not set
+
+#
+# DCCP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_DCCP is not set
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_SCTP is not set
+
+#
+# TIPC Configuration (EXPERIMENTAL)
+#
+# CONFIG_TIPC is not set
+# CONFIG_ATM is not set
+# CONFIG_BRIDGE is not set
+# CONFIG_VLAN_8021Q is not set
+# CONFIG_DECNET is not set
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_ATALK is not set
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+
+#
+# QoS and/or fair queueing
+#
+# CONFIG_NET_SCHED is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+# CONFIG_HAMRADIO is not set
+# CONFIG_IRDA is not set
+# CONFIG_BT is not set
+# CONFIG_IEEE80211 is not set
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+# CONFIG_FW_LOADER is not set
+# CONFIG_DEBUG_DRIVER is not set
+# CONFIG_SYS_HYPERVISOR is not set
+
+#
+# Connector - unified userspace <-> kernelspace linker
+#
+# CONFIG_CONNECTOR is not set
+
+#
+# Memory Technology Devices (MTD)
+#
+CONFIG_MTD=y
+# CONFIG_MTD_DEBUG is not set
+# CONFIG_MTD_CONCAT is not set
+CONFIG_MTD_PARTITIONS=y
+# CONFIG_MTD_REDBOOT_PARTS is not set
+CONFIG_MTD_CMDLINE_PARTS=y
+# CONFIG_MTD_AFS_PARTS is not set
+
+#
+# User Modules And Translation Layers
+#
+CONFIG_MTD_CHAR=y
+CONFIG_MTD_BLKDEVS=y
+CONFIG_MTD_BLOCK=y
+# CONFIG_FTL is not set
+# CONFIG_NFTL is not set
+# CONFIG_INFTL is not set
+# CONFIG_RFD_FTL is not set
+# CONFIG_SSFDC is not set
+
+#
+# RAM/ROM/Flash chip drivers
+#
+# CONFIG_MTD_CFI is not set
+# CONFIG_MTD_JEDECPROBE is not set
+CONFIG_MTD_MAP_BANK_WIDTH_1=y
+CONFIG_MTD_MAP_BANK_WIDTH_2=y
+CONFIG_MTD_MAP_BANK_WIDTH_4=y
+# CONFIG_MTD_MAP_BANK_WIDTH_8 is not set
+# CONFIG_MTD_MAP_BANK_WIDTH_16 is not set
+# CONFIG_MTD_MAP_BANK_WIDTH_32 is not set
+CONFIG_MTD_CFI_I1=y
+CONFIG_MTD_CFI_I2=y
+# CONFIG_MTD_CFI_I4 is not set
+# CONFIG_MTD_CFI_I8 is not set
+# CONFIG_MTD_RAM is not set
+# CONFIG_MTD_ROM is not set
+# CONFIG_MTD_ABSENT is not set
+# CONFIG_MTD_OBSOLETE_CHIPS is not set
+
+#
+# Mapping drivers for chip access
+#
+# CONFIG_MTD_COMPLEX_MAPPINGS is not set
+# CONFIG_MTD_PLATRAM is not set
+
+#
+# Self-contained MTD device drivers
+#
+CONFIG_MTD_DATAFLASH=y
+# CONFIG_MTD_M25P80 is not set
+# CONFIG_MTD_SLRAM is not set
+# CONFIG_MTD_PHRAM is not set
+# CONFIG_MTD_MTDRAM is not set
+# CONFIG_MTD_BLOCK2MTD is not set
+
+#
+# Disk-On-Chip Device Drivers
+#
+# CONFIG_MTD_DOC2000 is not set
+# CONFIG_MTD_DOC2001 is not set
+# CONFIG_MTD_DOC2001PLUS is not set
+
+#
+# NAND Flash Device Drivers
+#
+CONFIG_MTD_NAND=y
+# CONFIG_MTD_NAND_VERIFY_WRITE is not set
+# CONFIG_MTD_NAND_ECC_SMC is not set
+CONFIG_MTD_NAND_IDS=y
+# CONFIG_MTD_NAND_DISKONCHIP is not set
+CONFIG_MTD_NAND_AT91=y
+# CONFIG_MTD_NAND_NANDSIM is not set
+
+#
+# OneNAND Flash Device Drivers
+#
+# CONFIG_MTD_ONENAND is not set
+
+#
+# Parallel port support
+#
+# CONFIG_PARPORT is not set
+
+#
+# Plug and Play support
+#
+
+#
+# Block devices
+#
+# CONFIG_BLK_DEV_COW_COMMON is not set
+CONFIG_BLK_DEV_LOOP=y
+# CONFIG_BLK_DEV_CRYPTOLOOP is not set
+# CONFIG_BLK_DEV_NBD is not set
+# CONFIG_BLK_DEV_UB is not set
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_COUNT=16
+CONFIG_BLK_DEV_RAM_SIZE=8192
+CONFIG_BLK_DEV_RAM_BLOCKSIZE=1024
+CONFIG_BLK_DEV_INITRD=y
+# CONFIG_CDROM_PKTCDVD is not set
+# CONFIG_ATA_OVER_ETH is not set
+
+#
+# SCSI device support
+#
+# CONFIG_RAID_ATTRS is not set
+CONFIG_SCSI=y
+# CONFIG_SCSI_TGT is not set
+# CONFIG_SCSI_NETLINK is not set
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=y
+# CONFIG_CHR_DEV_ST is not set
+# CONFIG_CHR_DEV_OSST is not set
+# CONFIG_BLK_DEV_SR is not set
+# CONFIG_CHR_DEV_SG is not set
+# CONFIG_CHR_DEV_SCH is not set
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+CONFIG_SCSI_MULTI_LUN=y
+# CONFIG_SCSI_CONSTANTS is not set
+# CONFIG_SCSI_LOGGING is not set
+# CONFIG_SCSI_SCAN_ASYNC is not set
+
+#
+# SCSI Transports
+#
+# CONFIG_SCSI_SPI_ATTRS is not set
+# CONFIG_SCSI_FC_ATTRS is not set
+# CONFIG_SCSI_ISCSI_ATTRS is not set
+# CONFIG_SCSI_SAS_ATTRS is not set
+# CONFIG_SCSI_SAS_LIBSAS is not set
+
+#
+# SCSI low-level drivers
+#
+# CONFIG_ISCSI_TCP is not set
+# CONFIG_SCSI_DEBUG is not set
+
+#
+# Serial ATA (prod) and Parallel ATA (experimental) drivers
+#
+# CONFIG_ATA is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+# CONFIG_MD is not set
+
+#
+# Fusion MPT device support
+#
+# CONFIG_FUSION is not set
+
+#
+# IEEE 1394 (FireWire) support
+#
+
+#
+# I2O device support
+#
+
+#
+# Network device support
+#
+CONFIG_NETDEVICES=y
+# CONFIG_DUMMY is not set
+# CONFIG_BONDING is not set
+# CONFIG_EQUALIZER is not set
+# CONFIG_TUN is not set
+
+#
+# PHY device support
+#
+# CONFIG_PHYLIB is not set
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=y
+# CONFIG_SMC91X is not set
+# CONFIG_DM9000 is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+
+#
+# Ethernet (10000 Mbit)
+#
+
+#
+# Token Ring devices
+#
+
+#
+# Wireless LAN (non-hamradio)
+#
+# CONFIG_NET_RADIO is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+# CONFIG_PPP is not set
+# CONFIG_SLIP is not set
+# CONFIG_SHAPER is not set
+# CONFIG_NETCONSOLE is not set
+# CONFIG_NETPOLL is not set
+# CONFIG_NET_POLL_CONTROLLER is not set
+
+#
+# ISDN subsystem
+#
+# CONFIG_ISDN is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+# CONFIG_INPUT_FF_MEMLESS is not set
+
+#
+# Userland interfaces
+#
+CONFIG_INPUT_MOUSEDEV=y
+# CONFIG_INPUT_MOUSEDEV_PSAUX is not set
+CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024
+CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768
+# CONFIG_INPUT_JOYDEV is not set
+CONFIG_INPUT_TSDEV=y
+CONFIG_INPUT_TSDEV_SCREEN_X=240
+CONFIG_INPUT_TSDEV_SCREEN_Y=320
+CONFIG_INPUT_EVDEV=y
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input Device Drivers
+#
+# CONFIG_INPUT_KEYBOARD is not set
+# CONFIG_INPUT_MOUSE is not set
+# CONFIG_INPUT_JOYSTICK is not set
+CONFIG_INPUT_TOUCHSCREEN=y
+CONFIG_TOUCHSCREEN_ADS7846=y
+# CONFIG_TOUCHSCREEN_GUNZE is not set
+# CONFIG_TOUCHSCREEN_ELO is not set
+# CONFIG_TOUCHSCREEN_MTOUCH is not set
+# CONFIG_TOUCHSCREEN_MK712 is not set
+# CONFIG_TOUCHSCREEN_PENMOUNT is not set
+# CONFIG_TOUCHSCREEN_TOUCHRIGHT is not set
+# CONFIG_TOUCHSCREEN_TOUCHWIN is not set
+# CONFIG_TOUCHSCREEN_UCB1400 is not set
+# CONFIG_INPUT_MISC is not set
+
+#
+# Hardware I/O ports
+#
+# CONFIG_SERIO is not set
+# CONFIG_GAMEPORT is not set
+
+#
+# Character devices
+#
+CONFIG_VT=y
+CONFIG_VT_CONSOLE=y
+CONFIG_HW_CONSOLE=y
+# CONFIG_VT_HW_CONSOLE_BINDING is not set
+# CONFIG_SERIAL_NONSTANDARD is not set
+
+#
+# Serial drivers
+#
+# CONFIG_SERIAL_8250 is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_ATMEL=y
+CONFIG_SERIAL_ATMEL_CONSOLE=y
+# CONFIG_SERIAL_ATMEL_TTYAT is not set
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+CONFIG_UNIX98_PTYS=y
+CONFIG_LEGACY_PTYS=y
+CONFIG_LEGACY_PTY_COUNT=256
+
+#
+# IPMI
+#
+# CONFIG_IPMI_HANDLER is not set
+
+#
+# Watchdog Cards
+#
+CONFIG_WATCHDOG=y
+CONFIG_WATCHDOG_NOWAYOUT=y
+
+#
+# Watchdog Device Drivers
+#
+# CONFIG_SOFT_WATCHDOG is not set
+
+#
+# USB-based Watchdog Cards
+#
+# CONFIG_USBPCWATCHDOG is not set
+CONFIG_HW_RANDOM=y
+# CONFIG_NVRAM is not set
+# CONFIG_DTLK is not set
+# CONFIG_R3964 is not set
+# CONFIG_RAW_DRIVER is not set
+
+#
+# TPM devices
+#
+# CONFIG_TCG_TPM is not set
+
+#
+# I2C support
+#
+CONFIG_I2C=y
+CONFIG_I2C_CHARDEV=y
+
+#
+# I2C Algorithms
+#
+# CONFIG_I2C_ALGOBIT is not set
+# CONFIG_I2C_ALGOPCF is not set
+# CONFIG_I2C_ALGOPCA is not set
+
+#
+# I2C Hardware Bus support
+#
+CONFIG_I2C_AT91=y
+# CONFIG_I2C_OCORES is not set
+# CONFIG_I2C_PARPORT_LIGHT is not set
+# CONFIG_I2C_STUB is not set
+# CONFIG_I2C_PCA is not set
+# CONFIG_I2C_PCA_ISA is not set
+
+#
+# Miscellaneous I2C Chip support
+#
+# CONFIG_SENSORS_DS1337 is not set
+# CONFIG_SENSORS_DS1374 is not set
+# CONFIG_SENSORS_EEPROM is not set
+# CONFIG_SENSORS_PCF8574 is not set
+# CONFIG_SENSORS_PCA9539 is not set
+# CONFIG_SENSORS_PCF8591 is not set
+# CONFIG_SENSORS_MAX6875 is not set
+# CONFIG_I2C_DEBUG_CORE is not set
+# CONFIG_I2C_DEBUG_ALGO is not set
+# CONFIG_I2C_DEBUG_BUS is not set
+# CONFIG_I2C_DEBUG_CHIP is not set
+
+#
+# SPI support
+#
+CONFIG_SPI=y
+# CONFIG_SPI_DEBUG is not set
+CONFIG_SPI_MASTER=y
+
+#
+# SPI Master Controller Drivers
+#
+CONFIG_SPI_ATMEL=y
+# CONFIG_SPI_BITBANG is not set
+
+#
+# SPI Protocol Masters
+#
+
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
+#
+# Hardware Monitoring support
+#
+# CONFIG_HWMON is not set
+# CONFIG_HWMON_VID is not set
+
+#
+# Misc devices
+#
+# CONFIG_TIFM_CORE is not set
+
+#
+# LED devices
+#
+# CONFIG_NEW_LEDS is not set
+
+#
+# LED drivers
+#
+
+#
+# LED Triggers
+#
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+# CONFIG_USB_DABUSB is not set
+
+#
+# Graphics support
+#
+# CONFIG_FIRMWARE_EDID is not set
+CONFIG_FB=y
+# CONFIG_FB_CFB_FILLRECT is not set
+# CONFIG_FB_CFB_COPYAREA is not set
+# CONFIG_FB_CFB_IMAGEBLIT is not set
+# CONFIG_FB_MACMODES is not set
+# CONFIG_FB_BACKLIGHT is not set
+# CONFIG_FB_MODE_HELPERS is not set
+# CONFIG_FB_TILEBLITTING is not set
+# CONFIG_FB_S1D13XXX is not set
+# CONFIG_FB_VIRTUAL is not set
+
+#
+# Console display driver support
+#
+# CONFIG_VGA_CONSOLE is not set
+CONFIG_DUMMY_CONSOLE=y
+# CONFIG_FRAMEBUFFER_CONSOLE is not set
+
+#
+# Logo configuration
+#
+# CONFIG_LOGO is not set
+# CONFIG_BACKLIGHT_LCD_SUPPORT is not set
+
+#
+# Sound
+#
+# CONFIG_SOUND is not set
+
+#
+# HID Devices
+#
+CONFIG_HID=y
+
+#
+# USB support
+#
+CONFIG_USB_ARCH_HAS_HCD=y
+CONFIG_USB_ARCH_HAS_OHCI=y
+# CONFIG_USB_ARCH_HAS_EHCI is not set
+CONFIG_USB=y
+# CONFIG_USB_DEBUG is not set
+
+#
+# Miscellaneous USB options
+#
+CONFIG_USB_DEVICEFS=y
+# CONFIG_USB_BANDWIDTH is not set
+# CONFIG_USB_DYNAMIC_MINORS is not set
+# CONFIG_USB_MULTITHREAD_PROBE is not set
+# CONFIG_USB_OTG is not set
+
+#
+# USB Host Controller Drivers
+#
+# CONFIG_USB_ISP116X_HCD is not set
+CONFIG_USB_OHCI_HCD=y
+# CONFIG_USB_OHCI_BIG_ENDIAN is not set
+CONFIG_USB_OHCI_LITTLE_ENDIAN=y
+# CONFIG_USB_SL811_HCD is not set
+
+#
+# USB Device Class drivers
+#
+# CONFIG_USB_ACM is not set
+# CONFIG_USB_PRINTER is not set
+
+#
+# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support'
+#
+
+#
+# may also be needed; see USB_STORAGE Help for more information
+#
+CONFIG_USB_STORAGE=y
+# CONFIG_USB_STORAGE_DEBUG is not set
+# CONFIG_USB_STORAGE_DATAFAB is not set
+# CONFIG_USB_STORAGE_FREECOM is not set
+# CONFIG_USB_STORAGE_DPCM is not set
+# CONFIG_USB_STORAGE_USBAT is not set
+# CONFIG_USB_STORAGE_SDDR09 is not set
+# CONFIG_USB_STORAGE_SDDR55 is not set
+# CONFIG_USB_STORAGE_JUMPSHOT is not set
+# CONFIG_USB_STORAGE_ALAUDA is not set
+# CONFIG_USB_STORAGE_ONETOUCH is not set
+# CONFIG_USB_STORAGE_KARMA is not set
+# CONFIG_USB_LIBUSUAL is not set
+
+#
+# USB Input Devices
+#
+# CONFIG_USB_HID is not set
+
+#
+# USB HID Boot Protocol drivers
+#
+# CONFIG_USB_KBD is not set
+# CONFIG_USB_MOUSE is not set
+# CONFIG_USB_AIPTEK is not set
+# CONFIG_USB_WACOM is not set
+# CONFIG_USB_ACECAD is not set
+# CONFIG_USB_KBTAB is not set
+# CONFIG_USB_POWERMATE is not set
+# CONFIG_USB_TOUCHSCREEN is not set
+# CONFIG_USB_YEALINK is not set
+# CONFIG_USB_XPAD is not set
+# CONFIG_USB_ATI_REMOTE is not set
+# CONFIG_USB_ATI_REMOTE2 is not set
+# CONFIG_USB_KEYSPAN_REMOTE is not set
+# CONFIG_USB_APPLETOUCH is not set
+
+#
+# USB Imaging devices
+#
+# CONFIG_USB_MDC800 is not set
+# CONFIG_USB_MICROTEK is not set
+
+#
+# USB Network Adapters
+#
+# CONFIG_USB_CATC is not set
+# CONFIG_USB_KAWETH is not set
+# CONFIG_USB_PEGASUS is not set
+# CONFIG_USB_RTL8150 is not set
+# CONFIG_USB_USBNET_MII is not set
+# CONFIG_USB_USBNET is not set
+CONFIG_USB_MON=y
+
+#
+# USB port drivers
+#
+
+#
+# USB Serial Converter support
+#
+# CONFIG_USB_SERIAL is not set
+
+#
+# USB Miscellaneous drivers
+#
+# CONFIG_USB_EMI62 is not set
+# CONFIG_USB_EMI26 is not set
+# CONFIG_USB_ADUTUX is not set
+# CONFIG_USB_AUERSWALD is not set
+# CONFIG_USB_RIO500 is not set
+# CONFIG_USB_LEGOTOWER is not set
+# CONFIG_USB_LCD is not set
+# CONFIG_USB_LED is not set
+# CONFIG_USB_CYPRESS_CY7C63 is not set
+# CONFIG_USB_CYTHERM is not set
+# CONFIG_USB_PHIDGET is not set
+# CONFIG_USB_IDMOUSE is not set
+# CONFIG_USB_FTDI_ELAN is not set
+# CONFIG_USB_APPLEDISPLAY is not set
+# CONFIG_USB_LD is not set
+# CONFIG_USB_TRANCEVIBRATOR is not set
+# CONFIG_USB_TEST is not set
+
+#
+# USB DSL modem support
+#
+
+#
+# USB Gadget Support
+#
+CONFIG_USB_GADGET=y
+# CONFIG_USB_GADGET_DEBUG_FILES is not set
+CONFIG_USB_GADGET_SELECTED=y
+# CONFIG_USB_GADGET_NET2280 is not set
+# CONFIG_USB_GADGET_PXA2XX is not set
+# CONFIG_USB_GADGET_GOKU is not set
+# CONFIG_USB_GADGET_LH7A40X is not set
+# CONFIG_USB_GADGET_OMAP is not set
+CONFIG_USB_GADGET_AT91=y
+CONFIG_USB_AT91=y
+# CONFIG_USB_GADGET_DUMMY_HCD is not set
+# CONFIG_USB_GADGET_DUALSPEED is not set
+CONFIG_USB_ZERO=m
+# CONFIG_USB_ETH is not set
+CONFIG_USB_GADGETFS=m
+CONFIG_USB_FILE_STORAGE=m
+# CONFIG_USB_FILE_STORAGE_TEST is not set
+CONFIG_USB_G_SERIAL=m
+# CONFIG_USB_MIDI_GADGET is not set
+
+#
+# MMC/SD Card support
+#
+CONFIG_MMC=y
+# CONFIG_MMC_DEBUG is not set
+CONFIG_MMC_BLOCK=y
+CONFIG_MMC_AT91=m
+# CONFIG_MMC_TIFM_SD is not set
+
+#
+# Real Time Clock
+#
+CONFIG_RTC_LIB=y
+# CONFIG_RTC_CLASS is not set
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+# CONFIG_EXT2_FS_XATTR is not set
+# CONFIG_EXT2_FS_XIP is not set
+# CONFIG_EXT3_FS is not set
+# CONFIG_EXT4DEV_FS is not set
+# CONFIG_REISERFS_FS is not set
+# CONFIG_JFS_FS is not set
+# CONFIG_FS_POSIX_ACL is not set
+# CONFIG_XFS_FS is not set
+# CONFIG_GFS2_FS is not set
+# CONFIG_OCFS2_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_INOTIFY=y
+CONFIG_INOTIFY_USER=y
+# CONFIG_QUOTA is not set
+CONFIG_DNOTIFY=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_AUTOFS4_FS is not set
+# CONFIG_FUSE_FS is not set
+
+#
+# CD-ROM/DVD Filesystems
+#
+# CONFIG_ISO9660_FS is not set
+# CONFIG_UDF_FS is not set
+
+#
+# DOS/FAT/NT Filesystems
+#
+CONFIG_FAT_FS=y
+# CONFIG_MSDOS_FS is not set
+CONFIG_VFAT_FS=y
+CONFIG_FAT_DEFAULT_CODEPAGE=437
+CONFIG_FAT_DEFAULT_IOCHARSET="iso8859-1"
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_SYSCTL=y
+CONFIG_SYSFS=y
+CONFIG_TMPFS=y
+# CONFIG_TMPFS_POSIX_ACL is not set
+# CONFIG_HUGETLB_PAGE is not set
+CONFIG_RAMFS=y
+# CONFIG_CONFIGFS_FS is not set
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_HFS_FS is not set
+# CONFIG_HFSPLUS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+CONFIG_JFFS2_FS=y
+CONFIG_JFFS2_FS_DEBUG=0
+CONFIG_JFFS2_FS_WRITEBUFFER=y
+# CONFIG_JFFS2_SUMMARY is not set
+# CONFIG_JFFS2_FS_XATTR is not set
+# CONFIG_JFFS2_COMPRESSION_OPTIONS is not set
+CONFIG_JFFS2_ZLIB=y
+CONFIG_JFFS2_RTIME=y
+# CONFIG_JFFS2_RUBIN is not set
+CONFIG_CRAMFS=y
+# CONFIG_VXFS_FS is not set
+# CONFIG_HPFS_FS is not set
+# CONFIG_QNX4FS_FS is not set
+# CONFIG_SYSV_FS is not set
+# CONFIG_UFS_FS is not set
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=y
+# CONFIG_NFS_V3 is not set
+# CONFIG_NFS_V4 is not set
+# CONFIG_NFS_DIRECTIO is not set
+# CONFIG_NFSD is not set
+CONFIG_ROOT_NFS=y
+CONFIG_LOCKD=y
+CONFIG_NFS_COMMON=y
+CONFIG_SUNRPC=y
+# CONFIG_RPCSEC_GSS_KRB5 is not set
+# CONFIG_RPCSEC_GSS_SPKM3 is not set
+# CONFIG_SMB_FS is not set
+# CONFIG_CIFS is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+# CONFIG_9P_FS is not set
+
+#
+# Partition Types
+#
+# CONFIG_PARTITION_ADVANCED is not set
+CONFIG_MSDOS_PARTITION=y
+
+#
+# Native Language Support
+#
+CONFIG_NLS=y
+CONFIG_NLS_DEFAULT="iso8859-1"
+CONFIG_NLS_CODEPAGE_437=y
+# CONFIG_NLS_CODEPAGE_737 is not set
+# CONFIG_NLS_CODEPAGE_775 is not set
+CONFIG_NLS_CODEPAGE_850=y
+# CONFIG_NLS_CODEPAGE_852 is not set
+# CONFIG_NLS_CODEPAGE_855 is not set
+# CONFIG_NLS_CODEPAGE_857 is not set
+# CONFIG_NLS_CODEPAGE_860 is not set
+# CONFIG_NLS_CODEPAGE_861 is not set
+# CONFIG_NLS_CODEPAGE_862 is not set
+# CONFIG_NLS_CODEPAGE_863 is not set
+# CONFIG_NLS_CODEPAGE_864 is not set
+# CONFIG_NLS_CODEPAGE_865 is not set
+# CONFIG_NLS_CODEPAGE_866 is not set
+# CONFIG_NLS_CODEPAGE_869 is not set
+# CONFIG_NLS_CODEPAGE_936 is not set
+# CONFIG_NLS_CODEPAGE_950 is not set
+# CONFIG_NLS_CODEPAGE_932 is not set
+# CONFIG_NLS_CODEPAGE_949 is not set
+# CONFIG_NLS_CODEPAGE_874 is not set
+# CONFIG_NLS_ISO8859_8 is not set
+# CONFIG_NLS_CODEPAGE_1250 is not set
+# CONFIG_NLS_CODEPAGE_1251 is not set
+# CONFIG_NLS_ASCII is not set
+CONFIG_NLS_ISO8859_1=y
+# CONFIG_NLS_ISO8859_2 is not set
+# CONFIG_NLS_ISO8859_3 is not set
+# CONFIG_NLS_ISO8859_4 is not set
+# CONFIG_NLS_ISO8859_5 is not set
+# CONFIG_NLS_ISO8859_6 is not set
+# CONFIG_NLS_ISO8859_7 is not set
+# CONFIG_NLS_ISO8859_9 is not set
+# CONFIG_NLS_ISO8859_13 is not set
+# CONFIG_NLS_ISO8859_14 is not set
+# CONFIG_NLS_ISO8859_15 is not set
+# CONFIG_NLS_KOI8_R is not set
+# CONFIG_NLS_KOI8_U is not set
+# CONFIG_NLS_UTF8 is not set
+
+#
+# Distributed Lock Manager
+#
+# CONFIG_DLM is not set
+
+#
+# Profiling support
+#
+# CONFIG_PROFILING is not set
+
+#
+# Kernel hacking
+#
+# CONFIG_PRINTK_TIME is not set
+CONFIG_ENABLE_MUST_CHECK=y
+# CONFIG_MAGIC_SYSRQ is not set
+# CONFIG_UNUSED_SYMBOLS is not set
+# CONFIG_DEBUG_FS is not set
+# CONFIG_HEADERS_CHECK is not set
+CONFIG_DEBUG_KERNEL=y
+CONFIG_LOG_BUF_SHIFT=14
+CONFIG_DETECT_SOFTLOCKUP=y
+# CONFIG_SCHEDSTATS is not set
+# CONFIG_DEBUG_SLAB is not set
+# CONFIG_DEBUG_RT_MUTEXES is not set
+# CONFIG_RT_MUTEX_TESTER is not set
+# CONFIG_DEBUG_SPINLOCK is not set
+# CONFIG_DEBUG_MUTEXES is not set
+# CONFIG_DEBUG_RWSEMS is not set
+# CONFIG_DEBUG_SPINLOCK_SLEEP is not set
+# CONFIG_DEBUG_LOCKING_API_SELFTESTS is not set
+# CONFIG_DEBUG_KOBJECT is not set
+CONFIG_DEBUG_BUGVERBOSE=y
+# CONFIG_DEBUG_INFO is not set
+# CONFIG_DEBUG_VM is not set
+# CONFIG_DEBUG_LIST is not set
+CONFIG_FRAME_POINTER=y
+CONFIG_FORCED_INLINING=y
+# CONFIG_RCU_TORTURE_TEST is not set
+CONFIG_DEBUG_USER=y
+# CONFIG_DEBUG_ERRORS is not set
+CONFIG_DEBUG_LL=y
+# CONFIG_DEBUG_ICEDCC is not set
+
+#
+# Security options
+#
+# CONFIG_KEYS is not set
+# CONFIG_SECURITY is not set
+
+#
+# Cryptographic options
+#
+# CONFIG_CRYPTO is not set
+
+#
+# Library routines
+#
+CONFIG_BITREVERSE=y
+# CONFIG_CRC_CCITT is not set
+# CONFIG_CRC16 is not set
+CONFIG_CRC32=y
+# CONFIG_LIBCRC32C is not set
+CONFIG_ZLIB_INFLATE=y
+CONFIG_PLIST=y
+CONFIG_IOMAP_COPY=y
diff --git a/arch/arm/configs/ateb9200_defconfig b/arch/arm/configs/ateb9200_defconfig
index 3de5c643848c..baa97698c744 100644
--- a/arch/arm/configs/ateb9200_defconfig
+++ b/arch/arm/configs/ateb9200_defconfig
@@ -1066,7 +1066,7 @@ CONFIG_RTC_INTF_DEV=y
# CONFIG_RTC_DRV_PCF8563 is not set
# CONFIG_RTC_DRV_RS5C372 is not set
# CONFIG_RTC_DRV_M48T86 is not set
-CONFIG_RTC_DRV_AT91=y
+CONFIG_RTC_DRV_AT91RM9200=y
# CONFIG_RTC_DRV_TEST is not set
#
diff --git a/arch/arm/configs/csb337_defconfig b/arch/arm/configs/csb337_defconfig
index 2cadd51506bb..88e5d28aeec7 100644
--- a/arch/arm/configs/csb337_defconfig
+++ b/arch/arm/configs/csb337_defconfig
@@ -355,10 +355,12 @@ CONFIG_MTD_CFI_UTIL=y
# Mapping drivers for chip access
#
# CONFIG_MTD_COMPLEX_MAPPINGS is not set
-# CONFIG_MTD_PHYSMAP is not set
+CONFIG_MTD_PHYSMAP=y
+CONFIG_MTD_PHYSMAP_START=0
+CONFIG_MTD_PHYSMAP_LEN=0
+CONFIG_MTD_PHYSMAP_BANKWIDTH=0
# CONFIG_MTD_ARM_INTEGRATOR is not set
# CONFIG_MTD_PLATRAM is not set
-CONFIG_MTD_CSB337=y
#
# Self-contained MTD device drivers
@@ -986,7 +988,7 @@ CONFIG_RTC_DRV_DS1307=y
# CONFIG_RTC_DRV_PCF8583 is not set
# CONFIG_RTC_DRV_RS5C372 is not set
# CONFIG_RTC_DRV_M48T86 is not set
-CONFIG_RTC_DRV_AT91=y
+CONFIG_RTC_DRV_AT91RM9200=y
# CONFIG_RTC_DRV_TEST is not set
# CONFIG_RTC_DRV_V3020 is not set
diff --git a/arch/arm/configs/csb637_defconfig b/arch/arm/configs/csb637_defconfig
index 94908c1df4cf..669f035896f9 100644
--- a/arch/arm/configs/csb637_defconfig
+++ b/arch/arm/configs/csb637_defconfig
@@ -355,10 +355,12 @@ CONFIG_MTD_CFI_UTIL=y
# Mapping drivers for chip access
#
# CONFIG_MTD_COMPLEX_MAPPINGS is not set
-# CONFIG_MTD_PHYSMAP is not set
+CONFIG_MTD_PHYSMAP=y
+CONFIG_MTD_PHYSMAP_START=0
+CONFIG_MTD_PHYSMAP_LEN=0
+CONFIG_MTD_PHYSMAP_BANKWIDTH=0
# CONFIG_MTD_ARM_INTEGRATOR is not set
# CONFIG_MTD_PLATRAM is not set
-CONFIG_MTD_CSB637=y
#
# Self-contained MTD device drivers
diff --git a/arch/arm/configs/kafa_defconfig b/arch/arm/configs/kafa_defconfig
index a4cdafc1548a..a0f48d54fbcc 100644
--- a/arch/arm/configs/kafa_defconfig
+++ b/arch/arm/configs/kafa_defconfig
@@ -718,7 +718,7 @@ CONFIG_RTC_INTF_DEV=y
# CONFIG_RTC_DRV_PCF8563 is not set
# CONFIG_RTC_DRV_RS5C372 is not set
# CONFIG_RTC_DRV_M48T86 is not set
-CONFIG_RTC_DRV_AT91=y
+CONFIG_RTC_DRV_AT91RM9200=y
# CONFIG_RTC_DRV_TEST is not set
#
diff --git a/arch/arm/configs/s3c2410_defconfig b/arch/arm/configs/s3c2410_defconfig
index 3b31a33d0080..df19e3632038 100644
--- a/arch/arm/configs/s3c2410_defconfig
+++ b/arch/arm/configs/s3c2410_defconfig
@@ -1,7 +1,7 @@
#
# Automatically generated make config: don't edit
-# Linux kernel version: 2.6.19-rc4
-# Fri Nov 3 17:41:31 2006
+# Linux kernel version: 2.6.20
+# Thu Feb 15 11:26:24 2007
#
CONFIG_ARM=y
# CONFIG_GENERIC_TIME is not set
@@ -11,6 +11,8 @@ CONFIG_TRACE_IRQFLAGS_SUPPORT=y
CONFIG_HARDIRQS_SW_RESEND=y
CONFIG_GENERIC_IRQ_PROBE=y
CONFIG_RWSEM_GENERIC_SPINLOCK=y
+# CONFIG_ARCH_HAS_ILOG2_U32 is not set
+# CONFIG_ARCH_HAS_ILOG2_U64 is not set
CONFIG_GENERIC_HWEIGHT=y
CONFIG_GENERIC_CALIBRATE_DELAY=y
CONFIG_VECTORS_BASE=0xffff0000
@@ -37,13 +39,14 @@ CONFIG_SYSVIPC=y
# CONFIG_UTS_NS is not set
# CONFIG_AUDIT is not set
# CONFIG_IKCONFIG is not set
+CONFIG_SYSFS_DEPRECATED=y
# CONFIG_RELAY is not set
CONFIG_INITRAMFS_SOURCE=""
CONFIG_CC_OPTIMIZE_FOR_SIZE=y
CONFIG_SYSCTL=y
# CONFIG_EMBEDDED is not set
CONFIG_UID16=y
-# CONFIG_SYSCTL_SYSCALL is not set
+CONFIG_SYSCTL_SYSCALL=y
CONFIG_KALLSYMS=y
# CONFIG_KALLSYMS_ALL is not set
# CONFIG_KALLSYMS_EXTRA_PASS is not set
@@ -76,7 +79,9 @@ CONFIG_KMOD=y
# Block layer
#
CONFIG_BLOCK=y
+# CONFIG_LBD is not set
# CONFIG_BLK_DEV_IO_TRACE is not set
+# CONFIG_LSF is not set
#
# IO Schedulers
@@ -110,6 +115,7 @@ CONFIG_DEFAULT_IOSCHED="anticipatory"
# CONFIG_ARCH_IMX is not set
# CONFIG_ARCH_IOP32X is not set
# CONFIG_ARCH_IOP33X is not set
+# CONFIG_ARCH_IOP13XX is not set
# CONFIG_ARCH_IXP4XX is not set
# CONFIG_ARCH_IXP2000 is not set
# CONFIG_ARCH_IXP23XX is not set
@@ -122,54 +128,73 @@ CONFIG_ARCH_S3C2410=y
# CONFIG_ARCH_SHARK is not set
# CONFIG_ARCH_LH7A40X is not set
# CONFIG_ARCH_OMAP is not set
+CONFIG_PLAT_S3C24XX=y
+CONFIG_CPU_S3C244X=y
+CONFIG_PM_SIMTEC=y
+# CONFIG_S3C2410_BOOT_WATCHDOG is not set
+# CONFIG_S3C2410_BOOT_ERROR_RESET is not set
+# CONFIG_S3C2410_PM_DEBUG is not set
+# CONFIG_S3C2410_PM_CHECK is not set
+CONFIG_S3C2410_LOWLEVEL_UART_PORT=0
+CONFIG_S3C2410_DMA=y
+# CONFIG_S3C2410_DMA_DEBUG is not set
+CONFIG_MACH_SMDK=y
#
-# S3C24XX Implementations
+# S3C2400 Machines
+#
+CONFIG_CPU_S3C2410=y
+CONFIG_CPU_S3C2410_DMA=y
+CONFIG_S3C2410_PM=y
+CONFIG_S3C2410_GPIO=y
+CONFIG_S3C2410_CLOCK=y
+
+#
+# S3C2410 Machines
+#
+CONFIG_ARCH_SMDK2410=y
+CONFIG_ARCH_H1940=y
+CONFIG_PM_H1940=y
+CONFIG_MACH_N30=y
+CONFIG_ARCH_BAST=y
+CONFIG_MACH_OTOM=y
+CONFIG_MACH_AML_M5900=y
+CONFIG_BAST_PC104_IRQ=y
+CONFIG_MACH_VR1000=y
+CONFIG_CPU_S3C2412=y
+CONFIG_S3C2412_DMA=y
+CONFIG_S3C2412_PM=y
+
+#
+# S3C2412 Machines
+#
+CONFIG_MACH_SMDK2413=y
+CONFIG_MACH_S3C2413=y
+CONFIG_MACH_VSTMS=y
+CONFIG_CPU_S3C2440=y
+CONFIG_S3C2440_DMA=y
+
+#
+# S3C2440 Machines
#
-# CONFIG_MACH_AML_M5900 is not set
CONFIG_MACH_ANUBIS=y
CONFIG_MACH_OSIRIS=y
-CONFIG_ARCH_BAST=y
-CONFIG_BAST_PC104_IRQ=y
-CONFIG_ARCH_H1940=y
-CONFIG_MACH_N30=y
-CONFIG_MACH_SMDK=y
-CONFIG_ARCH_SMDK2410=y
-CONFIG_ARCH_S3C2440=y
-CONFIG_SMDK2440_CPU2440=y
-CONFIG_SMDK2440_CPU2442=y
-CONFIG_MACH_S3C2413=y
-CONFIG_MACH_SMDK2413=y
-CONFIG_MACH_VR1000=y
CONFIG_MACH_RX3715=y
-CONFIG_MACH_OTOM=y
+CONFIG_ARCH_S3C2440=y
CONFIG_MACH_NEXCODER_2440=y
-CONFIG_MACH_VSTMS=y
-CONFIG_S3C2410_CLOCK=y
-CONFIG_S3C2410_PM=y
-CONFIG_CPU_S3C2410_DMA=y
-CONFIG_CPU_S3C2410=y
-CONFIG_S3C2412_PM=y
-CONFIG_CPU_S3C2412=y
-CONFIG_CPU_S3C244X=y
-CONFIG_CPU_S3C2440=y
+CONFIG_SMDK2440_CPU2440=y
CONFIG_CPU_S3C2442=y
#
-# S3C2410 Boot
+# S3C2442 Machines
#
-# CONFIG_S3C2410_BOOT_WATCHDOG is not set
-# CONFIG_S3C2410_BOOT_ERROR_RESET is not set
+CONFIG_SMDK2440_CPU2442=y
+CONFIG_CPU_S3C2443=y
#
-# S3C2410 Setup
+# S3C2443 Machines
#
-CONFIG_S3C2410_DMA=y
-# CONFIG_S3C2410_DMA_DEBUG is not set
-# CONFIG_S3C2410_PM_DEBUG is not set
-# CONFIG_S3C2410_PM_CHECK is not set
-CONFIG_PM_SIMTEC=y
-CONFIG_S3C2410_LOWLEVEL_UART_PORT=0
+CONFIG_MACH_SMDK2443=y
#
# Processor Type
@@ -196,6 +221,7 @@ CONFIG_CPU_CP15_MMU=y
# CONFIG_CPU_DCACHE_DISABLE is not set
# CONFIG_CPU_DCACHE_WRITETHROUGH is not set
# CONFIG_CPU_CACHE_ROUND_ROBIN is not set
+# CONFIG_OUTER_CACHE is not set
#
# Bus support
@@ -303,6 +329,7 @@ CONFIG_INET_TCP_DIAG=y
# CONFIG_TCP_CONG_ADVANCED is not set
CONFIG_TCP_CONG_CUBIC=y
CONFIG_DEFAULT_TCP_CONG="cubic"
+# CONFIG_TCP_MD5SIG is not set
# CONFIG_IPV6 is not set
# CONFIG_INET6_XFRM_TUNNEL is not set
# CONFIG_INET6_TUNNEL is not set
@@ -385,6 +412,7 @@ CONFIG_MTD_CMDLINE_PARTS=y
# User Modules And Translation Layers
#
CONFIG_MTD_CHAR=y
+CONFIG_MTD_BLKDEVS=y
CONFIG_MTD_BLOCK=y
# CONFIG_FTL is not set
# CONFIG_NFTL is not set
@@ -530,6 +558,11 @@ CONFIG_BLK_DEV_IDE_BAST=y
# CONFIG_SCSI is not set
# CONFIG_SCSI_NETLINK is not set
+#
+# Serial ATA (prod) and Parallel ATA (experimental) drivers
+#
+# CONFIG_ATA is not set
+
#
# Multi-device support (RAID and LVM)
#
@@ -682,7 +715,7 @@ CONFIG_SERIAL_NONSTANDARD=y
# CONFIG_DIGIEPCA is not set
# CONFIG_MOXA_INTELLIO is not set
# CONFIG_MOXA_SMARTIO is not set
-# CONFIG_ISI is not set
+# CONFIG_MOXA_SMARTIO_NEW is not set
# CONFIG_SYNCLINKMP is not set
# CONFIG_N_HDLC is not set
# CONFIG_RISCOM8 is not set
@@ -700,13 +733,14 @@ CONFIG_SERIAL_8250_NR_UARTS=8
CONFIG_SERIAL_8250_RUNTIME_UARTS=4
CONFIG_SERIAL_8250_EXTENDED=y
CONFIG_SERIAL_8250_MANY_PORTS=y
-CONFIG_SERIAL_8250_SHARE_IRQ=y
-# CONFIG_SERIAL_8250_DETECT_IRQ is not set
-# CONFIG_SERIAL_8250_RSA is not set
# CONFIG_SERIAL_8250_FOURPORT is not set
# CONFIG_SERIAL_8250_ACCENT is not set
# CONFIG_SERIAL_8250_BOCA is not set
+# CONFIG_SERIAL_8250_EXAR_ST16C554 is not set
# CONFIG_SERIAL_8250_HUB6 is not set
+CONFIG_SERIAL_8250_SHARE_IRQ=y
+# CONFIG_SERIAL_8250_DETECT_IRQ is not set
+# CONFIG_SERIAL_8250_RSA is not set
#
# Non-8250 serial port support
@@ -755,10 +789,6 @@ CONFIG_HW_RANDOM=y
# CONFIG_NVRAM is not set
# CONFIG_DTLK is not set
# CONFIG_R3964 is not set
-
-#
-# Ftape, the floppy tape device driver
-#
# CONFIG_RAW_DRIVER is not set
#
@@ -863,6 +893,7 @@ CONFIG_SENSORS_LM85=m
# CONFIG_SENSORS_LM92 is not set
# CONFIG_SENSORS_MAX1619 is not set
# CONFIG_SENSORS_PC87360 is not set
+# CONFIG_SENSORS_PC87427 is not set
# CONFIG_SENSORS_SMSC47M1 is not set
# CONFIG_SENSORS_SMSC47M192 is not set
# CONFIG_SENSORS_SMSC47B397 is not set
@@ -870,6 +901,7 @@ CONFIG_SENSORS_LM85=m
# CONFIG_SENSORS_W83781D is not set
# CONFIG_SENSORS_W83791D is not set
# CONFIG_SENSORS_W83792D is not set
+# CONFIG_SENSORS_W83793 is not set
# CONFIG_SENSORS_W83L785TS is not set
# CONFIG_SENSORS_W83627HF is not set
# CONFIG_SENSORS_W83627EHF is not set
@@ -951,6 +983,11 @@ CONFIG_FONT_8x16=y
#
# CONFIG_SOUND is not set
+#
+# HID Devices
+#
+CONFIG_HID=y
+
#
# USB support
#
@@ -1028,6 +1065,7 @@ CONFIG_USB_OHCI_LITTLE_ENDIAN=y
# CONFIG_USB_KAWETH is not set
# CONFIG_USB_PEGASUS is not set
# CONFIG_USB_RTL8150 is not set
+# CONFIG_USB_USBNET_MII is not set
# CONFIG_USB_USBNET is not set
CONFIG_USB_MON=y
@@ -1179,9 +1217,6 @@ CONFIG_RAMFS=y
# CONFIG_BEFS_FS is not set
# CONFIG_BFS_FS is not set
# CONFIG_EFS_FS is not set
-CONFIG_JFFS_FS=y
-CONFIG_JFFS_FS_VERBOSE=0
-# CONFIG_JFFS_PROC_FS is not set
CONFIG_JFFS2_FS=y
CONFIG_JFFS2_FS_DEBUG=0
CONFIG_JFFS2_FS_WRITEBUFFER=y
@@ -1191,7 +1226,7 @@ CONFIG_JFFS2_FS_WRITEBUFFER=y
CONFIG_JFFS2_ZLIB=y
CONFIG_JFFS2_RTIME=y
# CONFIG_JFFS2_RUBIN is not set
-# CONFIG_CRAMFS is not set
+CONFIG_CRAMFS=y
# CONFIG_VXFS_FS is not set
# CONFIG_HPFS_FS is not set
# CONFIG_QNX4FS_FS is not set
@@ -1284,6 +1319,11 @@ CONFIG_NLS_DEFAULT="iso8859-1"
# CONFIG_NLS_KOI8_U is not set
# CONFIG_NLS_UTF8 is not set
+#
+# Distributed Lock Manager
+#
+# CONFIG_DLM is not set
+
#
# Profiling support
#
@@ -1296,6 +1336,8 @@ CONFIG_NLS_DEFAULT="iso8859-1"
CONFIG_ENABLE_MUST_CHECK=y
CONFIG_MAGIC_SYSRQ=y
# CONFIG_UNUSED_SYMBOLS is not set
+# CONFIG_DEBUG_FS is not set
+# CONFIG_HEADERS_CHECK is not set
CONFIG_DEBUG_KERNEL=y
CONFIG_LOG_BUF_SHIFT=16
CONFIG_DETECT_SOFTLOCKUP=y
@@ -1311,12 +1353,10 @@ CONFIG_DEBUG_MUTEXES=y
# CONFIG_DEBUG_KOBJECT is not set
CONFIG_DEBUG_BUGVERBOSE=y
CONFIG_DEBUG_INFO=y
-# CONFIG_DEBUG_FS is not set
# CONFIG_DEBUG_VM is not set
# CONFIG_DEBUG_LIST is not set
CONFIG_FRAME_POINTER=y
CONFIG_FORCED_INLINING=y
-# CONFIG_HEADERS_CHECK is not set
# CONFIG_RCU_TORTURE_TEST is not set
CONFIG_DEBUG_USER=y
# CONFIG_DEBUG_ERRORS is not set
@@ -1339,6 +1379,7 @@ CONFIG_DEBUG_S3C2410_UART=0
#
# Library routines
#
+CONFIG_BITREVERSE=y
# CONFIG_CRC_CCITT is not set
# CONFIG_CRC16 is not set
CONFIG_CRC32=y
@@ -1346,3 +1387,4 @@ CONFIG_CRC32=y
CONFIG_ZLIB_INFLATE=y
CONFIG_ZLIB_DEFLATE=y
CONFIG_PLIST=y
+CONFIG_IOMAP_COPY=y
diff --git a/arch/arm/kernel/crunch.c b/arch/arm/kernel/crunch.c
index cec83783206e..627d79414c9d 100644
--- a/arch/arm/kernel/crunch.c
+++ b/arch/arm/kernel/crunch.c
@@ -75,6 +75,7 @@ static struct notifier_block crunch_notifier_block = {
static int __init crunch_init(void)
{
thread_register_notifier(&crunch_notifier_block);
+ elf_hwcap |= HWCAP_CRUNCH;
return 0;
}
diff --git a/arch/arm/kernel/setup.c b/arch/arm/kernel/setup.c
index bbab134cd82d..243aea458057 100644
--- a/arch/arm/kernel/setup.c
+++ b/arch/arm/kernel/setup.c
@@ -88,6 +88,9 @@ struct cpu_user_fns cpu_user;
#ifdef MULTI_CACHE
struct cpu_cache_fns cpu_cache;
#endif
+#ifdef CONFIG_OUTER_CACHE
+struct outer_cache_fns outer_cache;
+#endif
struct stack {
u32 irq[3];
diff --git a/arch/arm/mach-at91rm9200/Kconfig b/arch/arm/mach-at91/Kconfig
similarity index 76%
rename from arch/arm/mach-at91rm9200/Kconfig
rename to arch/arm/mach-at91/Kconfig
index 9f11db8af233..bf0d96272e3a 100644
--- a/arch/arm/mach-at91rm9200/Kconfig
+++ b/arch/arm/mach-at91/Kconfig
@@ -9,11 +9,14 @@ config ARCH_AT91RM9200
bool "AT91RM9200"
config ARCH_AT91SAM9260
- bool "AT91SAM9260"
+ bool "AT91SAM9260 or AT91SAM9XE"
config ARCH_AT91SAM9261
bool "AT91SAM9261"
+config ARCH_AT91SAM9263
+ bool "AT91SAM9263"
+
endchoice
# ----------------------------------------------------------
@@ -90,13 +93,22 @@ endif
if ARCH_AT91SAM9260
-comment "AT91SAM9260 Board Type"
+comment "AT91SAM9260 Variants"
-config MACH_AT91SAM9260EK
- bool "Atmel AT91SAM9260-EK Evaluation Kit"
+config ARCH_AT91SAM9260_SAM9XE
+ bool "AT91SAM9XE"
depends on ARCH_AT91SAM9260
help
- Select this if you are using Atmel's AT91SAM9260-EK Evaluation Kit.
+ Select this if you are using Atmel's AT91SAM9XE System-on-Chip.
+ They are basicaly AT91SAM9260s with various sizes of embedded Flash.
+
+comment "AT91SAM9260 / AT91SAM9XE Board Type"
+
+config MACH_AT91SAM9260EK
+ bool "Atmel AT91SAM9260-EK / AT91SAM9XE Evaluation Kit"
+ depends on ARCH_AT91SAM9260
+ help
+ Select this if you are using Atmel's AT91SAM9260-EK or AT91SAM9XE Evaluation Kit
endif
@@ -118,17 +130,32 @@ endif
# ----------------------------------------------------------
+if ARCH_AT91SAM9263
+
+comment "AT91SAM9263 Board Type"
+
+config MACH_AT91SAM9263EK
+ bool "Atmel AT91SAM9263-EK Evaluation Kit"
+ depends on ARCH_AT91SAM9263
+ help
+ Select this if you are using Atmel's AT91SAM9263-EK Evaluation Kit.
+
+
+endif
+
+# ----------------------------------------------------------
+
comment "AT91 Board Options"
config MTD_AT91_DATAFLASH_CARD
bool "Enable DataFlash Card support"
- depends on (ARCH_AT91RM9200DK || MACH_AT91RM9200EK || MACH_AT91SAM9260EK || MACH_AT91SAM9261EK)
+ depends on (ARCH_AT91RM9200DK || MACH_AT91RM9200EK || MACH_AT91SAM9260EK || MACH_AT91SAM9261EK || MACH_AT91SAM9263EK)
help
Enable support for the DataFlash card.
config MTD_NAND_AT91_BUSWIDTH_16
bool "Enable 16-bit data bus interface to NAND flash"
- depends on (MACH_AT91SAM9261EK || MACH_AT91SAM9260EK)
+ depends on (MACH_AT91SAM9260EK || MACH_AT91SAM9261EK || MACH_AT91SAM9263EK)
help
On AT91SAM926x boards both types of NAND flash can be present
(8 and 16 bit data bus width).
diff --git a/arch/arm/mach-at91rm9200/Makefile b/arch/arm/mach-at91/Makefile
similarity index 88%
rename from arch/arm/mach-at91rm9200/Makefile
rename to arch/arm/mach-at91/Makefile
index cf777007847a..05de6cdc88f1 100644
--- a/arch/arm/mach-at91rm9200/Makefile
+++ b/arch/arm/mach-at91/Makefile
@@ -13,6 +13,7 @@ obj-$(CONFIG_PM) += pm.o
obj-$(CONFIG_ARCH_AT91RM9200) += at91rm9200.o at91rm9200_time.o at91rm9200_devices.o
obj-$(CONFIG_ARCH_AT91SAM9260) += at91sam9260.o at91sam926x_time.o at91sam9260_devices.o
obj-$(CONFIG_ARCH_AT91SAM9261) += at91sam9261.o at91sam926x_time.o at91sam9261_devices.o
+obj-$(CONFIG_ARCH_AT91SAM9263) += at91sam9263.o at91sam926x_time.o at91sam9263_devices.o
# AT91RM9200 board-specific support
obj-$(CONFIG_MACH_ONEARM) += board-1arm.o
@@ -31,6 +32,9 @@ obj-$(CONFIG_MACH_AT91SAM9260EK) += board-sam9260ek.o
# AT91SAM9261 board-specific support
obj-$(CONFIG_MACH_AT91SAM9261EK) += board-sam9261ek.o
+# AT91SAM9263 board-specific support
+obj-$(CONFIG_MACH_AT91SAM9263EK) += board-sam9263ek.o
+
# LEDs support
led-$(CONFIG_ARCH_AT91RM9200DK) += leds.o
led-$(CONFIG_MACH_AT91RM9200EK) += leds.o
diff --git a/arch/arm/mach-at91rm9200/Makefile.boot b/arch/arm/mach-at91/Makefile.boot
similarity index 100%
rename from arch/arm/mach-at91rm9200/Makefile.boot
rename to arch/arm/mach-at91/Makefile.boot
diff --git a/arch/arm/mach-at91rm9200/at91rm9200.c b/arch/arm/mach-at91/at91rm9200.c
similarity index 89%
rename from arch/arm/mach-at91rm9200/at91rm9200.c
rename to arch/arm/mach-at91/at91rm9200.c
index a92e9a495b07..2ddcdd69df7d 100644
--- a/arch/arm/mach-at91rm9200/at91rm9200.c
+++ b/arch/arm/mach-at91/at91rm9200.c
@@ -1,5 +1,5 @@
/*
- * arch/arm/mach-at91rm9200/at91rm9200.c
+ * arch/arm/mach-at91/at91rm9200.c
*
* Copyright (C) 2005 SAN People
*
@@ -117,6 +117,36 @@ static struct clk pioD_clk = {
.pmc_mask = 1 << AT91RM9200_ID_PIOD,
.type = CLK_TYPE_PERIPHERAL,
};
+static struct clk tc0_clk = {
+ .name = "tc0_clk",
+ .pmc_mask = 1 << AT91RM9200_ID_TC0,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc1_clk = {
+ .name = "tc1_clk",
+ .pmc_mask = 1 << AT91RM9200_ID_TC1,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc2_clk = {
+ .name = "tc2_clk",
+ .pmc_mask = 1 << AT91RM9200_ID_TC2,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc3_clk = {
+ .name = "tc3_clk",
+ .pmc_mask = 1 << AT91RM9200_ID_TC3,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc4_clk = {
+ .name = "tc4_clk",
+ .pmc_mask = 1 << AT91RM9200_ID_TC4,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc5_clk = {
+ .name = "tc5_clk",
+ .pmc_mask = 1 << AT91RM9200_ID_TC5,
+ .type = CLK_TYPE_PERIPHERAL,
+};
static struct clk *periph_clocks[] __initdata = {
&pioA_clk,
@@ -132,7 +162,12 @@ static struct clk *periph_clocks[] __initdata = {
&twi_clk,
&spi_clk,
// ssc 0 .. ssc2
- // tc0 .. tc5
+ &tc0_clk,
+ &tc1_clk,
+ &tc2_clk,
+ &tc3_clk,
+ &tc4_clk,
+ &tc5_clk,
&ohci_clk,
ðer_clk,
// irq0 .. irq6
diff --git a/arch/arm/mach-at91rm9200/at91rm9200_devices.c b/arch/arm/mach-at91/at91rm9200_devices.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/at91rm9200_devices.c
rename to arch/arm/mach-at91/at91rm9200_devices.c
index 57fac7203fe4..2624a4f22d61 100644
--- a/arch/arm/mach-at91rm9200/at91rm9200_devices.c
+++ b/arch/arm/mach-at91/at91rm9200_devices.c
@@ -1,5 +1,5 @@
/*
- * arch/arm/mach-at91rm9200/at91rm9200_devices.c
+ * arch/arm/mach-at91/at91rm9200_devices.c
*
* Copyright (C) 2005 Thibaut VARENE
* Copyright (C) 2005 David Brownell
@@ -315,7 +315,7 @@ static struct platform_device at91rm9200_mmc_device = {
.num_resources = ARRAY_SIZE(mmc_resources),
};
-void __init at91_add_device_mmc(struct at91_mmc_data *data)
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data)
{
if (!data)
return;
@@ -361,7 +361,7 @@ void __init at91_add_device_mmc(struct at91_mmc_data *data)
platform_device_register(&at91rm9200_mmc_device);
}
#else
-void __init at91_add_device_mmc(struct at91_mmc_data *data) {}
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data) {}
#endif
@@ -594,6 +594,10 @@ u8 at91_leds_timer;
void __init at91_init_leds(u8 cpu_led, u8 timer_led)
{
+ /* Enable GPIO to access the LEDs */
+ at91_set_gpio_output(cpu_led, 1);
+ at91_set_gpio_output(timer_led, 1);
+
at91_leds_cpu = cpu_led;
at91_leds_timer = timer_led;
}
diff --git a/arch/arm/mach-at91rm9200/at91rm9200_time.c b/arch/arm/mach-at91/at91rm9200_time.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/at91rm9200_time.c
rename to arch/arm/mach-at91/at91rm9200_time.c
index b999e192a7e9..949199a244c7 100644
--- a/arch/arm/mach-at91rm9200/at91rm9200_time.c
+++ b/arch/arm/mach-at91/at91rm9200_time.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/at91rm9200_time.c
+ * linux/arch/arm/mach-at91/at91rm9200_time.c
*
* Copyright (C) 2003 SAN People
* Copyright (C) 2003 ATMEL
diff --git a/arch/arm/mach-at91rm9200/at91sam9260.c b/arch/arm/mach-at91/at91sam9260.c
similarity index 79%
rename from arch/arm/mach-at91rm9200/at91sam9260.c
rename to arch/arm/mach-at91/at91sam9260.c
index b14871adc300..6ea41d8266cb 100644
--- a/arch/arm/mach-at91rm9200/at91sam9260.c
+++ b/arch/arm/mach-at91/at91sam9260.c
@@ -1,5 +1,5 @@
/*
- * arch/arm/mach-at91rm9200/at91sam9260.c
+ * arch/arm/mach-at91/at91sam9260.c
*
* Copyright (C) 2006 SAN People
*
@@ -14,6 +14,7 @@
#include
#include
+#include
#include
#include
#include
@@ -27,7 +28,11 @@ static struct map_desc at91sam9260_io_desc[] __initdata = {
.pfn = __phys_to_pfn(AT91_BASE_SYS),
.length = SZ_16K,
.type = MT_DEVICE,
- }, {
+ }
+};
+
+static struct map_desc at91sam9260_sram_desc[] __initdata = {
+ {
.virtual = AT91_IO_VIRT_BASE - AT91SAM9260_SRAM0_SIZE,
.pfn = __phys_to_pfn(AT91SAM9260_SRAM0_BASE),
.length = AT91SAM9260_SRAM0_SIZE,
@@ -37,7 +42,14 @@ static struct map_desc at91sam9260_io_desc[] __initdata = {
.pfn = __phys_to_pfn(AT91SAM9260_SRAM1_BASE),
.length = AT91SAM9260_SRAM1_SIZE,
.type = MT_DEVICE,
- },
+ }
+};
+
+static struct map_desc at91sam9xe_sram_desc[] __initdata = {
+ {
+ .pfn = __phys_to_pfn(AT91SAM9XE_SRAM_BASE),
+ .type = MT_DEVICE,
+ }
};
/* --------------------------------------------------------------------
@@ -107,13 +119,28 @@ static struct clk spi1_clk = {
.pmc_mask = 1 << AT91SAM9260_ID_SPI1,
.type = CLK_TYPE_PERIPHERAL,
};
+static struct clk tc0_clk = {
+ .name = "tc0_clk",
+ .pmc_mask = 1 << AT91SAM9260_ID_TC0,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc1_clk = {
+ .name = "tc1_clk",
+ .pmc_mask = 1 << AT91SAM9260_ID_TC1,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc2_clk = {
+ .name = "tc2_clk",
+ .pmc_mask = 1 << AT91SAM9260_ID_TC2,
+ .type = CLK_TYPE_PERIPHERAL,
+};
static struct clk ohci_clk = {
.name = "ohci_clk",
.pmc_mask = 1 << AT91SAM9260_ID_UHP,
.type = CLK_TYPE_PERIPHERAL,
};
-static struct clk ether_clk = {
- .name = "ether_clk",
+static struct clk macb_clk = {
+ .name = "macb_clk",
.pmc_mask = 1 << AT91SAM9260_ID_EMAC,
.type = CLK_TYPE_PERIPHERAL,
};
@@ -137,6 +164,21 @@ static struct clk usart5_clk = {
.pmc_mask = 1 << AT91SAM9260_ID_US5,
.type = CLK_TYPE_PERIPHERAL,
};
+static struct clk tc3_clk = {
+ .name = "tc3_clk",
+ .pmc_mask = 1 << AT91SAM9260_ID_TC3,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc4_clk = {
+ .name = "tc4_clk",
+ .pmc_mask = 1 << AT91SAM9260_ID_TC4,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc5_clk = {
+ .name = "tc5_clk",
+ .pmc_mask = 1 << AT91SAM9260_ID_TC5,
+ .type = CLK_TYPE_PERIPHERAL,
+};
static struct clk *periph_clocks[] __initdata = {
&pioA_clk,
@@ -152,14 +194,18 @@ static struct clk *periph_clocks[] __initdata = {
&spi0_clk,
&spi1_clk,
// ssc
- // tc0 .. tc2
+ &tc0_clk,
+ &tc1_clk,
+ &tc2_clk,
&ohci_clk,
- ðer_clk,
+ &macb_clk,
&isi_clk,
&usart3_clk,
&usart4_clk,
&usart5_clk,
- // tc3 .. tc5
+ &tc3_clk,
+ &tc4_clk,
+ &tc5_clk,
// irq0 .. irq2
};
@@ -213,7 +259,7 @@ static struct at91_gpio_bank at91sam9260_gpio[] = {
static void at91sam9260_reset(void)
{
- at91_sys_write(AT91_RSTC_CR, (0xA5 << 24) | AT91_RSTC_PROCRST | AT91_RSTC_PERRST);
+ at91_sys_write(AT91_RSTC_CR, AT91_RSTC_KEY | AT91_RSTC_PROCRST | AT91_RSTC_PERRST);
}
@@ -221,11 +267,37 @@ static void at91sam9260_reset(void)
* AT91SAM9260 processor initialization
* -------------------------------------------------------------------- */
+static void __init at91sam9xe_initialize(void)
+{
+ unsigned long cidr, sram_size;
+
+ cidr = at91_sys_read(AT91_DBGU_CIDR);
+
+ switch (cidr & AT91_CIDR_SRAMSIZ) {
+ case AT91_CIDR_SRAMSIZ_32K:
+ sram_size = 2 * SZ_16K;
+ break;
+ case AT91_CIDR_SRAMSIZ_16K:
+ default:
+ sram_size = SZ_16K;
+ }
+
+ at91sam9xe_sram_desc->virtual = AT91_IO_VIRT_BASE - sram_size;
+ at91sam9xe_sram_desc->length = sram_size;
+
+ iotable_init(at91sam9xe_sram_desc, ARRAY_SIZE(at91sam9xe_sram_desc));
+}
+
void __init at91sam9260_initialize(unsigned long main_clock)
{
/* Map peripherals */
iotable_init(at91sam9260_io_desc, ARRAY_SIZE(at91sam9260_io_desc));
+ if (cpu_is_at91sam9xe())
+ at91sam9xe_initialize();
+ else
+ iotable_init(at91sam9260_sram_desc, ARRAY_SIZE(at91sam9260_sram_desc));
+
at91_arch_reset = at91sam9260_reset;
at91_extern_irq = (1 << AT91SAM9260_ID_IRQ0) | (1 << AT91SAM9260_ID_IRQ1)
| (1 << AT91SAM9260_ID_IRQ2);
diff --git a/arch/arm/mach-at91rm9200/at91sam9260_devices.c b/arch/arm/mach-at91/at91sam9260_devices.c
similarity index 97%
rename from arch/arm/mach-at91rm9200/at91sam9260_devices.c
rename to arch/arm/mach-at91/at91sam9260_devices.c
index f42d3a40ec3c..f7d342ccbebf 100644
--- a/arch/arm/mach-at91rm9200/at91sam9260_devices.c
+++ b/arch/arm/mach-at91/at91sam9260_devices.c
@@ -1,5 +1,5 @@
/*
- * arch/arm/mach-at91rm9200/at91sam9260_devices.c
+ * arch/arm/mach-at91/at91sam9260_devices.c
*
* Copyright (C) 2006 Atmel
*
@@ -128,7 +128,7 @@ void __init at91_add_device_udc(struct at91_udc_data *data) {}
#if defined(CONFIG_MACB) || defined(CONFIG_MACB_MODULE)
static u64 eth_dmamask = 0xffffffffUL;
-static struct eth_platform_data eth_data;
+static struct at91_eth_data eth_data;
static struct resource eth_resources[] = {
[0] = {
@@ -155,7 +155,7 @@ static struct platform_device at91sam9260_eth_device = {
.num_resources = ARRAY_SIZE(eth_resources),
};
-void __init at91_add_device_eth(struct eth_platform_data *data)
+void __init at91_add_device_eth(struct at91_eth_data *data)
{
if (!data)
return;
@@ -192,7 +192,7 @@ void __init at91_add_device_eth(struct eth_platform_data *data)
platform_device_register(&at91sam9260_eth_device);
}
#else
-void __init at91_add_device_eth(struct eth_platform_data *data) {}
+void __init at91_add_device_eth(struct at91_eth_data *data) {}
#endif
@@ -229,7 +229,7 @@ static struct platform_device at91sam9260_mmc_device = {
.num_resources = ARRAY_SIZE(mmc_resources),
};
-void __init at91_add_device_mmc(struct at91_mmc_data *data)
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data)
{
if (!data)
return;
@@ -275,7 +275,7 @@ void __init at91_add_device_mmc(struct at91_mmc_data *data)
platform_device_register(&at91sam9260_mmc_device);
}
#else
-void __init at91_add_device_mmc(struct at91_mmc_data *data) {}
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data) {}
#endif
@@ -515,6 +515,10 @@ u8 at91_leds_timer;
void __init at91_init_leds(u8 cpu_led, u8 timer_led)
{
+ /* Enable GPIO to access the LEDs */
+ at91_set_gpio_output(cpu_led, 1);
+ at91_set_gpio_output(timer_led, 1);
+
at91_leds_cpu = cpu_led;
at91_leds_timer = timer_led;
}
diff --git a/arch/arm/mach-at91rm9200/at91sam9261.c b/arch/arm/mach-at91/at91sam9261.c
similarity index 92%
rename from arch/arm/mach-at91rm9200/at91sam9261.c
rename to arch/arm/mach-at91/at91sam9261.c
index d242bb885c6d..784d1e682d6d 100644
--- a/arch/arm/mach-at91rm9200/at91sam9261.c
+++ b/arch/arm/mach-at91/at91sam9261.c
@@ -1,5 +1,5 @@
/*
- * arch/arm/mach-at91rm9200/at91sam9261.c
+ * arch/arm/mach-at91/at91sam9261.c
*
* Copyright (C) 2005 SAN People
*
@@ -97,6 +97,21 @@ static struct clk spi1_clk = {
.pmc_mask = 1 << AT91SAM9261_ID_SPI1,
.type = CLK_TYPE_PERIPHERAL,
};
+static struct clk tc0_clk = {
+ .name = "tc0_clk",
+ .pmc_mask = 1 << AT91SAM9261_ID_TC0,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc1_clk = {
+ .name = "tc1_clk",
+ .pmc_mask = 1 << AT91SAM9261_ID_TC1,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tc2_clk = {
+ .name = "tc2_clk",
+ .pmc_mask = 1 << AT91SAM9261_ID_TC2,
+ .type = CLK_TYPE_PERIPHERAL,
+};
static struct clk ohci_clk = {
.name = "ohci_clk",
.pmc_mask = 1 << AT91SAM9261_ID_UHP,
@@ -121,7 +136,9 @@ static struct clk *periph_clocks[] __initdata = {
&spi0_clk,
&spi1_clk,
// ssc 0 .. ssc2
- // tc0 .. tc2
+ &tc0_clk,
+ &tc1_clk,
+ &tc2_clk,
&ohci_clk,
&lcdc_clk,
// irq0 .. irq2
@@ -208,7 +225,7 @@ static struct at91_gpio_bank at91sam9261_gpio[] = {
static void at91sam9261_reset(void)
{
- at91_sys_write(AT91_RSTC_CR, (0xA5 << 24) | AT91_RSTC_PROCRST | AT91_RSTC_PERRST);
+ at91_sys_write(AT91_RSTC_CR, AT91_RSTC_KEY | AT91_RSTC_PROCRST | AT91_RSTC_PERRST);
}
diff --git a/arch/arm/mach-at91rm9200/at91sam9261_devices.c b/arch/arm/mach-at91/at91sam9261_devices.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/at91sam9261_devices.c
rename to arch/arm/mach-at91/at91sam9261_devices.c
index ed1d79081b35..e1504766fd64 100644
--- a/arch/arm/mach-at91rm9200/at91sam9261_devices.c
+++ b/arch/arm/mach-at91/at91sam9261_devices.c
@@ -1,5 +1,5 @@
/*
- * arch/arm/mach-at91rm9200/at91sam9261_devices.c
+ * arch/arm/mach-at91/at91sam9261_devices.c
*
* Copyright (C) 2005 Thibaut VARENE
* Copyright (C) 2005 David Brownell
@@ -159,7 +159,7 @@ static struct platform_device at91sam9261_mmc_device = {
.num_resources = ARRAY_SIZE(mmc_resources),
};
-void __init at91_add_device_mmc(struct at91_mmc_data *data)
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data)
{
if (!data)
return;
@@ -192,7 +192,7 @@ void __init at91_add_device_mmc(struct at91_mmc_data *data)
platform_device_register(&at91sam9261_mmc_device);
}
#else
-void __init at91_add_device_mmc(struct at91_mmc_data *data) {}
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data) {}
#endif
@@ -513,6 +513,10 @@ u8 at91_leds_timer;
void __init at91_init_leds(u8 cpu_led, u8 timer_led)
{
+ /* Enable GPIO to access the LEDs */
+ at91_set_gpio_output(cpu_led, 1);
+ at91_set_gpio_output(timer_led, 1);
+
at91_leds_cpu = cpu_led;
at91_leds_timer = timer_led;
}
diff --git a/arch/arm/mach-at91/at91sam9263.c b/arch/arm/mach-at91/at91sam9263.c
new file mode 100644
index 000000000000..6aa342e8f1b1
--- /dev/null
+++ b/arch/arm/mach-at91/at91sam9263.c
@@ -0,0 +1,313 @@
+/*
+ * arch/arm/mach-at91/at91sam9263.c
+ *
+ * Copyright (C) 2007 Atmel Corporation.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ */
+
+#include
+
+#include
+#include
+#include
+#include
+#include
+
+#include "generic.h"
+#include "clock.h"
+
+static struct map_desc at91sam9263_io_desc[] __initdata = {
+ {
+ .virtual = AT91_VA_BASE_SYS,
+ .pfn = __phys_to_pfn(AT91_BASE_SYS),
+ .length = SZ_16K,
+ .type = MT_DEVICE,
+ }, {
+ .virtual = AT91_IO_VIRT_BASE - AT91SAM9263_SRAM0_SIZE,
+ .pfn = __phys_to_pfn(AT91SAM9263_SRAM0_BASE),
+ .length = AT91SAM9263_SRAM0_SIZE,
+ .type = MT_DEVICE,
+ }, {
+ .virtual = AT91_IO_VIRT_BASE - AT91SAM9263_SRAM0_SIZE - AT91SAM9263_SRAM1_SIZE,
+ .pfn = __phys_to_pfn(AT91SAM9263_SRAM1_BASE),
+ .length = AT91SAM9263_SRAM1_SIZE,
+ .type = MT_DEVICE,
+ },
+};
+
+/* --------------------------------------------------------------------
+ * Clocks
+ * -------------------------------------------------------------------- */
+
+/*
+ * The peripheral clocks.
+ */
+static struct clk pioA_clk = {
+ .name = "pioA_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_PIOA,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk pioB_clk = {
+ .name = "pioB_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_PIOB,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk pioCDE_clk = {
+ .name = "pioCDE_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_PIOCDE,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk usart0_clk = {
+ .name = "usart0_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_US0,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk usart1_clk = {
+ .name = "usart1_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_US1,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk usart2_clk = {
+ .name = "usart2_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_US2,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk mmc0_clk = {
+ .name = "mci0_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_MCI0,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk mmc1_clk = {
+ .name = "mci1_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_MCI1,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk twi_clk = {
+ .name = "twi_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_TWI,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk spi0_clk = {
+ .name = "spi0_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_SPI0,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk spi1_clk = {
+ .name = "spi1_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_SPI1,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk tcb_clk = {
+ .name = "tcb_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_TCB,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk macb_clk = {
+ .name = "macb_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_EMAC,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk udc_clk = {
+ .name = "udc_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_UDP,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk isi_clk = {
+ .name = "isi_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_ISI,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk lcdc_clk = {
+ .name = "lcdc_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_ISI,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+static struct clk ohci_clk = {
+ .name = "ohci_clk",
+ .pmc_mask = 1 << AT91SAM9263_ID_UHP,
+ .type = CLK_TYPE_PERIPHERAL,
+};
+
+static struct clk *periph_clocks[] __initdata = {
+ &pioA_clk,
+ &pioB_clk,
+ &pioCDE_clk,
+ &usart0_clk,
+ &usart1_clk,
+ &usart2_clk,
+ &mmc0_clk,
+ &mmc1_clk,
+ // can
+ &twi_clk,
+ &spi0_clk,
+ &spi1_clk,
+ // ssc0 .. ssc1
+ // ac97
+ &tcb_clk,
+ // pwmc
+ &macb_clk,
+ // 2dge
+ &udc_clk,
+ &isi_clk,
+ &lcdc_clk,
+ // dma
+ &ohci_clk,
+ // irq0 .. irq1
+};
+
+/*
+ * The four programmable clocks.
+ * You must configure pin multiplexing to bring these signals out.
+ */
+static struct clk pck0 = {
+ .name = "pck0",
+ .pmc_mask = AT91_PMC_PCK0,
+ .type = CLK_TYPE_PROGRAMMABLE,
+ .id = 0,
+};
+static struct clk pck1 = {
+ .name = "pck1",
+ .pmc_mask = AT91_PMC_PCK1,
+ .type = CLK_TYPE_PROGRAMMABLE,
+ .id = 1,
+};
+static struct clk pck2 = {
+ .name = "pck2",
+ .pmc_mask = AT91_PMC_PCK2,
+ .type = CLK_TYPE_PROGRAMMABLE,
+ .id = 2,
+};
+static struct clk pck3 = {
+ .name = "pck3",
+ .pmc_mask = AT91_PMC_PCK3,
+ .type = CLK_TYPE_PROGRAMMABLE,
+ .id = 3,
+};
+
+static void __init at91sam9263_register_clocks(void)
+{
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(periph_clocks); i++)
+ clk_register(periph_clocks[i]);
+
+ clk_register(&pck0);
+ clk_register(&pck1);
+ clk_register(&pck2);
+ clk_register(&pck3);
+}
+
+/* --------------------------------------------------------------------
+ * GPIO
+ * -------------------------------------------------------------------- */
+
+static struct at91_gpio_bank at91sam9263_gpio[] = {
+ {
+ .id = AT91SAM9263_ID_PIOA,
+ .offset = AT91_PIOA,
+ .clock = &pioA_clk,
+ }, {
+ .id = AT91SAM9263_ID_PIOB,
+ .offset = AT91_PIOB,
+ .clock = &pioB_clk,
+ }, {
+ .id = AT91SAM9263_ID_PIOCDE,
+ .offset = AT91_PIOC,
+ .clock = &pioCDE_clk,
+ }, {
+ .id = AT91SAM9263_ID_PIOCDE,
+ .offset = AT91_PIOD,
+ .clock = &pioCDE_clk,
+ }, {
+ .id = AT91SAM9263_ID_PIOCDE,
+ .offset = AT91_PIOE,
+ .clock = &pioCDE_clk,
+ }
+};
+
+static void at91sam9263_reset(void)
+{
+ at91_sys_write(AT91_RSTC_CR, AT91_RSTC_KEY | AT91_RSTC_PROCRST | AT91_RSTC_PERRST);
+}
+
+
+/* --------------------------------------------------------------------
+ * AT91SAM9263 processor initialization
+ * -------------------------------------------------------------------- */
+
+void __init at91sam9263_initialize(unsigned long main_clock)
+{
+ /* Map peripherals */
+ iotable_init(at91sam9263_io_desc, ARRAY_SIZE(at91sam9263_io_desc));
+
+ at91_arch_reset = at91sam9263_reset;
+ at91_extern_irq = (1 << AT91SAM9263_ID_IRQ0) | (1 << AT91SAM9263_ID_IRQ1);
+
+ /* Init clock subsystem */
+ at91_clock_init(main_clock);
+
+ /* Register the processor-specific clocks */
+ at91sam9263_register_clocks();
+
+ /* Register GPIO subsystem */
+ at91_gpio_init(at91sam9263_gpio, 5);
+}
+
+/* --------------------------------------------------------------------
+ * Interrupt initialization
+ * -------------------------------------------------------------------- */
+
+/*
+ * The default interrupt priority levels (0 = lowest, 7 = highest).
+ */
+static unsigned int at91sam9263_default_irq_priority[NR_AIC_IRQS] __initdata = {
+ 7, /* Advanced Interrupt Controller (FIQ) */
+ 7, /* System Peripherals */
+ 0, /* Parallel IO Controller A */
+ 0, /* Parallel IO Controller B */
+ 0, /* Parallel IO Controller C, D and E */
+ 0,
+ 0,
+ 6, /* USART 0 */
+ 6, /* USART 1 */
+ 6, /* USART 2 */
+ 0, /* Multimedia Card Interface 0 */
+ 0, /* Multimedia Card Interface 1 */
+ 4, /* CAN */
+ 0, /* Two-Wire Interface */
+ 6, /* Serial Peripheral Interface 0 */
+ 6, /* Serial Peripheral Interface 1 */
+ 5, /* Serial Synchronous Controller 0 */
+ 5, /* Serial Synchronous Controller 1 */
+ 6, /* AC97 Controller */
+ 0, /* Timer Counter 0, 1 and 2 */
+ 0, /* Pulse Width Modulation Controller */
+ 3, /* Ethernet */
+ 0,
+ 0, /* 2D Graphic Engine */
+ 3, /* USB Device Port */
+ 0, /* Image Sensor Interface */
+ 3, /* LDC Controller */
+ 0, /* DMA Controller */
+ 0,
+ 3, /* USB Host port */
+ 0, /* Advanced Interrupt Controller (IRQ0) */
+ 0, /* Advanced Interrupt Controller (IRQ1) */
+};
+
+void __init at91sam9263_init_interrupts(unsigned int priority[NR_AIC_IRQS])
+{
+ if (!priority)
+ priority = at91sam9263_default_irq_priority;
+
+ /* Initialize the AIC interrupt controller */
+ at91_aic_init(priority);
+
+ /* Enable GPIO interrupts */
+ at91_gpio_irq_setup();
+}
diff --git a/arch/arm/mach-at91/at91sam9263_devices.c b/arch/arm/mach-at91/at91sam9263_devices.c
new file mode 100644
index 000000000000..d9af7ca58bce
--- /dev/null
+++ b/arch/arm/mach-at91/at91sam9263_devices.c
@@ -0,0 +1,818 @@
+/*
+ * arch/arm/mach-at91/at91sam9263_devices.c
+ *
+ * Copyright (C) 2007 Atmel Corporation.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ */
+#include
+#include
+
+#include
+
+#include
+#include
+#include
+#include
+#include
+
+#include "generic.h"
+
+#define SZ_512 0x00000200
+#define SZ_256 0x00000100
+#define SZ_16 0x00000010
+
+/* --------------------------------------------------------------------
+ * USB Host
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_USB_OHCI_HCD) || defined(CONFIG_USB_OHCI_HCD_MODULE)
+static u64 ohci_dmamask = 0xffffffffUL;
+static struct at91_usbh_data usbh_data;
+
+static struct resource usbh_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_UHP_BASE,
+ .end = AT91SAM9263_UHP_BASE + SZ_1M - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_UHP,
+ .end = AT91SAM9263_ID_UHP,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91_usbh_device = {
+ .name = "at91_ohci",
+ .id = -1,
+ .dev = {
+ .dma_mask = &ohci_dmamask,
+ .coherent_dma_mask = 0xffffffff,
+ .platform_data = &usbh_data,
+ },
+ .resource = usbh_resources,
+ .num_resources = ARRAY_SIZE(usbh_resources),
+};
+
+void __init at91_add_device_usbh(struct at91_usbh_data *data)
+{
+ int i;
+
+ if (!data)
+ return;
+
+ /* Enable VBus control for UHP ports */
+ for (i = 0; i < data->ports; i++) {
+ if (data->vbus_pin[i])
+ at91_set_gpio_output(data->vbus_pin[i], 0);
+ }
+
+ usbh_data = *data;
+ platform_device_register(&at91_usbh_device);
+}
+#else
+void __init at91_add_device_usbh(struct at91_usbh_data *data) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * USB Device (Gadget)
+ * -------------------------------------------------------------------- */
+
+#ifdef CONFIG_USB_GADGET_AT91
+static struct at91_udc_data udc_data;
+
+static struct resource udc_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_UDP,
+ .end = AT91SAM9263_BASE_UDP + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_UDP,
+ .end = AT91SAM9263_ID_UDP,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91_udc_device = {
+ .name = "at91_udc",
+ .id = -1,
+ .dev = {
+ .platform_data = &udc_data,
+ },
+ .resource = udc_resources,
+ .num_resources = ARRAY_SIZE(udc_resources),
+};
+
+void __init at91_add_device_udc(struct at91_udc_data *data)
+{
+ if (!data)
+ return;
+
+ if (data->vbus_pin) {
+ at91_set_gpio_input(data->vbus_pin, 0);
+ at91_set_deglitch(data->vbus_pin, 1);
+ }
+
+ /* Pullup pin is handled internally by USB device peripheral */
+
+ udc_data = *data;
+ platform_device_register(&at91_udc_device);
+}
+#else
+void __init at91_add_device_udc(struct at91_udc_data *data) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * Ethernet
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_MACB) || defined(CONFIG_MACB_MODULE)
+static u64 eth_dmamask = 0xffffffffUL;
+static struct at91_eth_data eth_data;
+
+static struct resource eth_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_EMAC,
+ .end = AT91SAM9263_BASE_EMAC + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_EMAC,
+ .end = AT91SAM9263_ID_EMAC,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91sam9263_eth_device = {
+ .name = "macb",
+ .id = -1,
+ .dev = {
+ .dma_mask = ð_dmamask,
+ .coherent_dma_mask = 0xffffffff,
+ .platform_data = ð_data,
+ },
+ .resource = eth_resources,
+ .num_resources = ARRAY_SIZE(eth_resources),
+};
+
+void __init at91_add_device_eth(struct at91_eth_data *data)
+{
+ if (!data)
+ return;
+
+ if (data->phy_irq_pin) {
+ at91_set_gpio_input(data->phy_irq_pin, 0);
+ at91_set_deglitch(data->phy_irq_pin, 1);
+ }
+
+ /* Pins used for MII and RMII */
+ at91_set_A_periph(AT91_PIN_PE21, 0); /* ETXCK_EREFCK */
+ at91_set_B_periph(AT91_PIN_PC25, 0); /* ERXDV */
+ at91_set_A_periph(AT91_PIN_PE25, 0); /* ERX0 */
+ at91_set_A_periph(AT91_PIN_PE26, 0); /* ERX1 */
+ at91_set_A_periph(AT91_PIN_PE27, 0); /* ERXER */
+ at91_set_A_periph(AT91_PIN_PE28, 0); /* ETXEN */
+ at91_set_A_periph(AT91_PIN_PE23, 0); /* ETX0 */
+ at91_set_A_periph(AT91_PIN_PE24, 0); /* ETX1 */
+ at91_set_A_periph(AT91_PIN_PE30, 0); /* EMDIO */
+ at91_set_A_periph(AT91_PIN_PE29, 0); /* EMDC */
+
+ if (!data->is_rmii) {
+ at91_set_A_periph(AT91_PIN_PE22, 0); /* ECRS */
+ at91_set_B_periph(AT91_PIN_PC26, 0); /* ECOL */
+ at91_set_B_periph(AT91_PIN_PC22, 0); /* ERX2 */
+ at91_set_B_periph(AT91_PIN_PC23, 0); /* ERX3 */
+ at91_set_B_periph(AT91_PIN_PC27, 0); /* ERXCK */
+ at91_set_B_periph(AT91_PIN_PC20, 0); /* ETX2 */
+ at91_set_B_periph(AT91_PIN_PC21, 0); /* ETX3 */
+ at91_set_B_periph(AT91_PIN_PC24, 0); /* ETXER */
+ }
+
+ eth_data = *data;
+ platform_device_register(&at91sam9263_eth_device);
+}
+#else
+void __init at91_add_device_eth(struct at91_eth_data *data) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * MMC / SD
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_MMC_AT91) || defined(CONFIG_MMC_AT91_MODULE)
+static u64 mmc_dmamask = 0xffffffffUL;
+static struct at91_mmc_data mmc0_data, mmc1_data;
+
+static struct resource mmc0_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_MCI0,
+ .end = AT91SAM9263_BASE_MCI0 + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_MCI0,
+ .end = AT91SAM9263_ID_MCI0,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91sam9263_mmc0_device = {
+ .name = "at91_mci",
+ .id = 0,
+ .dev = {
+ .dma_mask = &mmc_dmamask,
+ .coherent_dma_mask = 0xffffffff,
+ .platform_data = &mmc0_data,
+ },
+ .resource = mmc0_resources,
+ .num_resources = ARRAY_SIZE(mmc0_resources),
+};
+
+static struct resource mmc1_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_MCI1,
+ .end = AT91SAM9263_BASE_MCI1 + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_MCI1,
+ .end = AT91SAM9263_ID_MCI1,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91sam9263_mmc1_device = {
+ .name = "at91_mci",
+ .id = 1,
+ .dev = {
+ .dma_mask = &mmc_dmamask,
+ .coherent_dma_mask = 0xffffffff,
+ .platform_data = &mmc1_data,
+ },
+ .resource = mmc1_resources,
+ .num_resources = ARRAY_SIZE(mmc1_resources),
+};
+
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data)
+{
+ if (!data)
+ return;
+
+ /* input/irq */
+ if (data->det_pin) {
+ at91_set_gpio_input(data->det_pin, 1);
+ at91_set_deglitch(data->det_pin, 1);
+ }
+ if (data->wp_pin)
+ at91_set_gpio_input(data->wp_pin, 1);
+ if (data->vcc_pin)
+ at91_set_gpio_output(data->vcc_pin, 0);
+
+ if (mmc_id == 0) { /* MCI0 */
+ /* CLK */
+ at91_set_A_periph(AT91_PIN_PA12, 0);
+
+ if (data->slot_b) {
+ /* CMD */
+ at91_set_A_periph(AT91_PIN_PA16, 1);
+
+ /* DAT0, maybe DAT1..DAT3 */
+ at91_set_A_periph(AT91_PIN_PA17, 1);
+ if (data->wire4) {
+ at91_set_A_periph(AT91_PIN_PA18, 1);
+ at91_set_A_periph(AT91_PIN_PA19, 1);
+ at91_set_A_periph(AT91_PIN_PA20, 1);
+ }
+ } else {
+ /* CMD */
+ at91_set_A_periph(AT91_PIN_PA1, 1);
+
+ /* DAT0, maybe DAT1..DAT3 */
+ at91_set_A_periph(AT91_PIN_PA0, 1);
+ if (data->wire4) {
+ at91_set_A_periph(AT91_PIN_PA3, 1);
+ at91_set_A_periph(AT91_PIN_PA4, 1);
+ at91_set_A_periph(AT91_PIN_PA5, 1);
+ }
+ }
+
+ mmc0_data = *data;
+ at91_clock_associate("mci0_clk", &at91sam9263_mmc1_device.dev, "mci_clk");
+ platform_device_register(&at91sam9263_mmc0_device);
+ } else { /* MCI1 */
+ /* CLK */
+ at91_set_A_periph(AT91_PIN_PA6, 0);
+
+ if (data->slot_b) {
+ /* CMD */
+ at91_set_A_periph(AT91_PIN_PA21, 1);
+
+ /* DAT0, maybe DAT1..DAT3 */
+ at91_set_A_periph(AT91_PIN_PA22, 1);
+ if (data->wire4) {
+ at91_set_A_periph(AT91_PIN_PA23, 1);
+ at91_set_A_periph(AT91_PIN_PA24, 1);
+ at91_set_A_periph(AT91_PIN_PA25, 1);
+ }
+ } else {
+ /* CMD */
+ at91_set_A_periph(AT91_PIN_PA7, 1);
+
+ /* DAT0, maybe DAT1..DAT3 */
+ at91_set_A_periph(AT91_PIN_PA8, 1);
+ if (data->wire4) {
+ at91_set_A_periph(AT91_PIN_PA9, 1);
+ at91_set_A_periph(AT91_PIN_PA10, 1);
+ at91_set_A_periph(AT91_PIN_PA11, 1);
+ }
+ }
+
+ mmc1_data = *data;
+ at91_clock_associate("mci1_clk", &at91sam9263_mmc1_device.dev, "mci_clk");
+ platform_device_register(&at91sam9263_mmc1_device);
+ }
+}
+#else
+void __init at91_add_device_mmc(short mmc_id, struct at91_mmc_data *data) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * NAND / SmartMedia
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_MTD_NAND_AT91) || defined(CONFIG_MTD_NAND_AT91_MODULE)
+static struct at91_nand_data nand_data;
+
+#define NAND_BASE AT91_CHIPSELECT_3
+
+static struct resource nand_resources[] = {
+ {
+ .start = NAND_BASE,
+ .end = NAND_BASE + SZ_256M - 1,
+ .flags = IORESOURCE_MEM,
+ }
+};
+
+static struct platform_device at91sam9263_nand_device = {
+ .name = "at91_nand",
+ .id = -1,
+ .dev = {
+ .platform_data = &nand_data,
+ },
+ .resource = nand_resources,
+ .num_resources = ARRAY_SIZE(nand_resources),
+};
+
+void __init at91_add_device_nand(struct at91_nand_data *data)
+{
+ unsigned long csa, mode;
+
+ if (!data)
+ return;
+
+ csa = at91_sys_read(AT91_MATRIX_EBI0CSA);
+ at91_sys_write(AT91_MATRIX_EBI0CSA, csa | AT91_MATRIX_EBI0_CS3A_SMC);
+
+ /* set the bus interface characteristics */
+ at91_sys_write(AT91_SMC_SETUP(3), AT91_SMC_NWESETUP_(0) | AT91_SMC_NCS_WRSETUP_(0)
+ | AT91_SMC_NRDSETUP_(0) | AT91_SMC_NCS_RDSETUP_(0));
+
+ at91_sys_write(AT91_SMC_PULSE(3), AT91_SMC_NWEPULSE_(3) | AT91_SMC_NCS_WRPULSE_(3)
+ | AT91_SMC_NRDPULSE_(3) | AT91_SMC_NCS_RDPULSE_(3));
+
+ at91_sys_write(AT91_SMC_CYCLE(3), AT91_SMC_NWECYCLE_(5) | AT91_SMC_NRDCYCLE_(5));
+
+ if (data->bus_width_16)
+ mode = AT91_SMC_DBW_16;
+ else
+ mode = AT91_SMC_DBW_8;
+ at91_sys_write(AT91_SMC_MODE(3), mode | AT91_SMC_READMODE | AT91_SMC_WRITEMODE | AT91_SMC_EXNWMODE_DISABLE | AT91_SMC_TDF_(2));
+
+ /* enable pin */
+ if (data->enable_pin)
+ at91_set_gpio_output(data->enable_pin, 1);
+
+ /* ready/busy pin */
+ if (data->rdy_pin)
+ at91_set_gpio_input(data->rdy_pin, 1);
+
+ /* card detect pin */
+ if (data->det_pin)
+ at91_set_gpio_input(data->det_pin, 1);
+
+ nand_data = *data;
+ platform_device_register(&at91sam9263_nand_device);
+}
+#else
+void __init at91_add_device_nand(struct at91_nand_data *data) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * TWI (i2c)
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_I2C_AT91) || defined(CONFIG_I2C_AT91_MODULE)
+
+static struct resource twi_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_TWI,
+ .end = AT91SAM9263_BASE_TWI + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_TWI,
+ .end = AT91SAM9263_ID_TWI,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91sam9263_twi_device = {
+ .name = "at91_i2c",
+ .id = -1,
+ .resource = twi_resources,
+ .num_resources = ARRAY_SIZE(twi_resources),
+};
+
+void __init at91_add_device_i2c(void)
+{
+ /* pins used for TWI interface */
+ at91_set_A_periph(AT91_PIN_PB4, 0); /* TWD */
+ at91_set_multi_drive(AT91_PIN_PB4, 1);
+
+ at91_set_A_periph(AT91_PIN_PB5, 0); /* TWCK */
+ at91_set_multi_drive(AT91_PIN_PB5, 1);
+
+ platform_device_register(&at91sam9263_twi_device);
+}
+#else
+void __init at91_add_device_i2c(void) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * SPI
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_SPI_ATMEL) || defined(CONFIG_SPI_ATMEL_MODULE)
+static u64 spi_dmamask = 0xffffffffUL;
+
+static struct resource spi0_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_SPI0,
+ .end = AT91SAM9263_BASE_SPI0 + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_SPI0,
+ .end = AT91SAM9263_ID_SPI0,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91sam9263_spi0_device = {
+ .name = "atmel_spi",
+ .id = 0,
+ .dev = {
+ .dma_mask = &spi_dmamask,
+ .coherent_dma_mask = 0xffffffff,
+ },
+ .resource = spi0_resources,
+ .num_resources = ARRAY_SIZE(spi0_resources),
+};
+
+static const unsigned spi0_standard_cs[4] = { AT91_PIN_PA5, AT91_PIN_PA3, AT91_PIN_PA4, AT91_PIN_PB11 };
+
+static struct resource spi1_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_SPI1,
+ .end = AT91SAM9263_BASE_SPI1 + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_SPI1,
+ .end = AT91SAM9263_ID_SPI1,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device at91sam9263_spi1_device = {
+ .name = "atmel_spi",
+ .id = 1,
+ .dev = {
+ .dma_mask = &spi_dmamask,
+ .coherent_dma_mask = 0xffffffff,
+ },
+ .resource = spi1_resources,
+ .num_resources = ARRAY_SIZE(spi1_resources),
+};
+
+static const unsigned spi1_standard_cs[4] = { AT91_PIN_PB15, AT91_PIN_PB16, AT91_PIN_PB17, AT91_PIN_PB18 };
+
+void __init at91_add_device_spi(struct spi_board_info *devices, int nr_devices)
+{
+ int i;
+ unsigned long cs_pin;
+ short enable_spi0 = 0;
+ short enable_spi1 = 0;
+
+ /* Choose SPI chip-selects */
+ for (i = 0; i < nr_devices; i++) {
+ if (devices[i].controller_data)
+ cs_pin = (unsigned long) devices[i].controller_data;
+ else if (devices[i].bus_num == 0)
+ cs_pin = spi0_standard_cs[devices[i].chip_select];
+ else
+ cs_pin = spi1_standard_cs[devices[i].chip_select];
+
+ if (devices[i].bus_num == 0)
+ enable_spi0 = 1;
+ else
+ enable_spi1 = 1;
+
+ /* enable chip-select pin */
+ at91_set_gpio_output(cs_pin, 1);
+
+ /* pass chip-select pin to driver */
+ devices[i].controller_data = (void *) cs_pin;
+ }
+
+ spi_register_board_info(devices, nr_devices);
+
+ /* Configure SPI bus(es) */
+ if (enable_spi0) {
+ at91_set_B_periph(AT91_PIN_PA0, 0); /* SPI0_MISO */
+ at91_set_B_periph(AT91_PIN_PA1, 0); /* SPI0_MOSI */
+ at91_set_B_periph(AT91_PIN_PA2, 0); /* SPI1_SPCK */
+
+ at91_clock_associate("spi0_clk", &at91sam9263_spi0_device.dev, "spi_clk");
+ platform_device_register(&at91sam9263_spi0_device);
+ }
+ if (enable_spi1) {
+ at91_set_A_periph(AT91_PIN_PB12, 0); /* SPI1_MISO */
+ at91_set_A_periph(AT91_PIN_PB13, 0); /* SPI1_MOSI */
+ at91_set_A_periph(AT91_PIN_PB14, 0); /* SPI1_SPCK */
+
+ at91_clock_associate("spi1_clk", &at91sam9263_spi1_device.dev, "spi_clk");
+ platform_device_register(&at91sam9263_spi1_device);
+ }
+}
+#else
+void __init at91_add_device_spi(struct spi_board_info *devices, int nr_devices) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * LEDs
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_LEDS)
+u8 at91_leds_cpu;
+u8 at91_leds_timer;
+
+void __init at91_init_leds(u8 cpu_led, u8 timer_led)
+{
+ /* Enable GPIO to access the LEDs */
+ at91_set_gpio_output(cpu_led, 1);
+ at91_set_gpio_output(timer_led, 1);
+
+ at91_leds_cpu = cpu_led;
+ at91_leds_timer = timer_led;
+}
+#else
+void __init at91_init_leds(u8 cpu_led, u8 timer_led) {}
+#endif
+
+
+/* --------------------------------------------------------------------
+ * UART
+ * -------------------------------------------------------------------- */
+
+#if defined(CONFIG_SERIAL_ATMEL)
+
+static struct resource dbgu_resources[] = {
+ [0] = {
+ .start = AT91_VA_BASE_SYS + AT91_DBGU,
+ .end = AT91_VA_BASE_SYS + AT91_DBGU + SZ_512 - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91_ID_SYS,
+ .end = AT91_ID_SYS,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct atmel_uart_data dbgu_data = {
+ .use_dma_tx = 0,
+ .use_dma_rx = 0, /* DBGU not capable of receive DMA */
+ .regs = (void __iomem *)(AT91_VA_BASE_SYS + AT91_DBGU),
+};
+
+static struct platform_device at91sam9263_dbgu_device = {
+ .name = "atmel_usart",
+ .id = 0,
+ .dev = {
+ .platform_data = &dbgu_data,
+ .coherent_dma_mask = 0xffffffff,
+ },
+ .resource = dbgu_resources,
+ .num_resources = ARRAY_SIZE(dbgu_resources),
+};
+
+static inline void configure_dbgu_pins(void)
+{
+ at91_set_A_periph(AT91_PIN_PC30, 0); /* DRXD */
+ at91_set_A_periph(AT91_PIN_PC31, 1); /* DTXD */
+}
+
+static struct resource uart0_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_US0,
+ .end = AT91SAM9263_BASE_US0 + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_US0,
+ .end = AT91SAM9263_ID_US0,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct atmel_uart_data uart0_data = {
+ .use_dma_tx = 1,
+ .use_dma_rx = 1,
+};
+
+static struct platform_device at91sam9263_uart0_device = {
+ .name = "atmel_usart",
+ .id = 1,
+ .dev = {
+ .platform_data = &uart0_data,
+ .coherent_dma_mask = 0xffffffff,
+ },
+ .resource = uart0_resources,
+ .num_resources = ARRAY_SIZE(uart0_resources),
+};
+
+static inline void configure_usart0_pins(void)
+{
+ at91_set_A_periph(AT91_PIN_PA26, 1); /* TXD0 */
+ at91_set_A_periph(AT91_PIN_PA27, 0); /* RXD0 */
+ at91_set_A_periph(AT91_PIN_PA28, 0); /* RTS0 */
+ at91_set_A_periph(AT91_PIN_PA29, 0); /* CTS0 */
+}
+
+static struct resource uart1_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_US1,
+ .end = AT91SAM9263_BASE_US1 + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_US1,
+ .end = AT91SAM9263_ID_US1,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct atmel_uart_data uart1_data = {
+ .use_dma_tx = 1,
+ .use_dma_rx = 1,
+};
+
+static struct platform_device at91sam9263_uart1_device = {
+ .name = "atmel_usart",
+ .id = 2,
+ .dev = {
+ .platform_data = &uart1_data,
+ .coherent_dma_mask = 0xffffffff,
+ },
+ .resource = uart1_resources,
+ .num_resources = ARRAY_SIZE(uart1_resources),
+};
+
+static inline void configure_usart1_pins(void)
+{
+ at91_set_A_periph(AT91_PIN_PD0, 1); /* TXD1 */
+ at91_set_A_periph(AT91_PIN_PD1, 0); /* RXD1 */
+ at91_set_B_periph(AT91_PIN_PD7, 0); /* RTS1 */
+ at91_set_B_periph(AT91_PIN_PD8, 0); /* CTS1 */
+}
+
+static struct resource uart2_resources[] = {
+ [0] = {
+ .start = AT91SAM9263_BASE_US2,
+ .end = AT91SAM9263_BASE_US2 + SZ_16K - 1,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = AT91SAM9263_ID_US2,
+ .end = AT91SAM9263_ID_US2,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct atmel_uart_data uart2_data = {
+ .use_dma_tx = 1,
+ .use_dma_rx = 1,
+};
+
+static struct platform_device at91sam9263_uart2_device = {
+ .name = "atmel_usart",
+ .id = 3,
+ .dev = {
+ .platform_data = &uart2_data,
+ .coherent_dma_mask = 0xffffffff,
+ },
+ .resource = uart2_resources,
+ .num_resources = ARRAY_SIZE(uart2_resources),
+};
+
+static inline void configure_usart2_pins(void)
+{
+ at91_set_A_periph(AT91_PIN_PD2, 1); /* TXD2 */
+ at91_set_A_periph(AT91_PIN_PD3, 0); /* RXD2 */
+ at91_set_B_periph(AT91_PIN_PD5, 0); /* RTS2 */
+ at91_set_B_periph(AT91_PIN_PD6, 0); /* CTS2 */
+}
+
+struct platform_device *at91_uarts[ATMEL_MAX_UART]; /* the UARTs to use */
+struct platform_device *atmel_default_console_device; /* the serial console device */
+
+void __init at91_init_serial(struct at91_uart_config *config)
+{
+ int i;
+
+ /* Fill in list of supported UARTs */
+ for (i = 0; i < config->nr_tty; i++) {
+ switch (config->tty_map[i]) {
+ case 0:
+ configure_usart0_pins();
+ at91_uarts[i] = &at91sam9263_uart0_device;
+ at91_clock_associate("usart0_clk", &at91sam9263_uart0_device.dev, "usart");
+ break;
+ case 1:
+ configure_usart1_pins();
+ at91_uarts[i] = &at91sam9263_uart1_device;
+ at91_clock_associate("usart1_clk", &at91sam9263_uart1_device.dev, "usart");
+ break;
+ case 2:
+ configure_usart2_pins();
+ at91_uarts[i] = &at91sam9263_uart2_device;
+ at91_clock_associate("usart2_clk", &at91sam9263_uart2_device.dev, "usart");
+ break;
+ case 3:
+ configure_dbgu_pins();
+ at91_uarts[i] = &at91sam9263_dbgu_device;
+ at91_clock_associate("mck", &at91sam9263_dbgu_device.dev, "usart");
+ break;
+ default:
+ continue;
+ }
+ at91_uarts[i]->id = i; /* update ID number to mapped ID */
+ }
+
+ /* Set serial console device */
+ if (config->console_tty < ATMEL_MAX_UART)
+ atmel_default_console_device = at91_uarts[config->console_tty];
+ if (!atmel_default_console_device)
+ printk(KERN_INFO "AT91: No default serial console defined.\n");
+}
+
+void __init at91_add_device_serial(void)
+{
+ int i;
+
+ for (i = 0; i < ATMEL_MAX_UART; i++) {
+ if (at91_uarts[i])
+ platform_device_register(at91_uarts[i]);
+ }
+}
+#else
+void __init at91_init_serial(struct at91_uart_config *config) {}
+void __init at91_add_device_serial(void) {}
+#endif
+
+
+/* -------------------------------------------------------------------- */
+/*
+ * These devices are always present and don't need any board-specific
+ * setup.
+ */
+static int __init at91_add_standard_devices(void)
+{
+ return 0;
+}
+
+arch_initcall(at91_add_standard_devices);
diff --git a/arch/arm/mach-at91rm9200/at91sam926x_time.c b/arch/arm/mach-at91/at91sam926x_time.c
similarity index 94%
rename from arch/arm/mach-at91rm9200/at91sam926x_time.c
rename to arch/arm/mach-at91/at91sam926x_time.c
index 99df5f6ee42e..a4dded27fa16 100644
--- a/arch/arm/mach-at91rm9200/at91sam926x_time.c
+++ b/arch/arm/mach-at91/at91sam926x_time.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/at91sam926x_time.c
+ * linux/arch/arm/mach-at91/at91sam926x_time.c
*
* Copyright (C) 2005-2006 M. Amine SAYA, ATMEL Rousset, France
* Revision 2005 M. Nicolas Diremdjian, ATMEL Rousset, France
@@ -30,7 +30,6 @@
* Returns number of microseconds since last timer interrupt. Note that interrupts
* will have been disabled by do_gettimeofday()
* 'LATCH' is hwclock ticks (see CLOCK_TICK_RATE in timex.h) per jiffy.
- * 'tick' is usecs per jiffy (linux/timex.h).
*/
static unsigned long at91sam926x_gettimeoffset(void)
{
@@ -39,7 +38,7 @@ static unsigned long at91sam926x_gettimeoffset(void)
elapsed = (PIT_PICNT(t) * LATCH) + PIT_CPIV(t); /* hardware clock cycles */
- return (unsigned long)(elapsed * 1000000) / LATCH;
+ return (unsigned long)(elapsed * jiffies_to_usecs(1)) / LATCH;
}
/*
diff --git a/arch/arm/mach-at91rm9200/board-1arm.c b/arch/arm/mach-at91/board-1arm.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/board-1arm.c
rename to arch/arm/mach-at91/board-1arm.c
index 971c3e2d8e36..2d3d4b6f7b02 100644
--- a/arch/arm/mach-at91rm9200/board-1arm.c
+++ b/arch/arm/mach-at91/board-1arm.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-1arm.c
+ * linux/arch/arm/mach-at91/board-1arm.c
*
* Copyright (C) 2005 SAN People
*
diff --git a/arch/arm/mach-at91rm9200/board-carmeva.c b/arch/arm/mach-at91/board-carmeva.c
similarity index 97%
rename from arch/arm/mach-at91rm9200/board-carmeva.c
rename to arch/arm/mach-at91/board-carmeva.c
index 654f0379550a..b4518619063a 100644
--- a/arch/arm/mach-at91rm9200/board-carmeva.c
+++ b/arch/arm/mach-at91/board-carmeva.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-carmeva.c
+ * linux/arch/arm/mach-at91/board-carmeva.c
*
* Copyright (c) 2005 Peer Georgi
* Conitec Datasystems
@@ -134,7 +134,7 @@ static void __init carmeva_board_init(void)
/* Compact Flash */
// at91_add_device_cf(&carmeva_cf_data);
/* MMC */
- at91_add_device_mmc(&carmeva_mmc_data);
+ at91_add_device_mmc(0, &carmeva_mmc_data);
}
MACHINE_START(CARMEVA, "Carmeva")
diff --git a/arch/arm/mach-at91rm9200/board-csb337.c b/arch/arm/mach-at91/board-csb337.c
similarity index 78%
rename from arch/arm/mach-at91rm9200/board-csb337.c
rename to arch/arm/mach-at91/board-csb337.c
index b8bb8052607a..e18a41e61f0c 100644
--- a/arch/arm/mach-at91rm9200/board-csb337.c
+++ b/arch/arm/mach-at91/board-csb337.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-csb337.c
+ * linux/arch/arm/mach-at91/board-csb337.c
*
* Copyright (C) 2005 SAN People
*
@@ -24,6 +24,7 @@
#include
#include
#include
+#include
#include
#include
@@ -112,6 +113,42 @@ static struct spi_board_info csb337_spi_devices[] = {
},
};
+#define CSB_FLASH_BASE AT91_CHIPSELECT_0
+#define CSB_FLASH_SIZE 0x800000
+
+static struct mtd_partition csb_flash_partitions[] = {
+ {
+ .name = "uMON flash",
+ .offset = 0,
+ .size = MTDPART_SIZ_FULL,
+ .mask_flags = MTD_WRITEABLE, /* read only */
+ }
+};
+
+static struct physmap_flash_data csb_flash_data = {
+ .width = 2,
+ .parts = csb_flash_partitions,
+ .nr_parts = ARRAY_SIZE(csb_flash_partitions),
+};
+
+static struct resource csb_flash_resources[] = {
+ {
+ .start = CSB_FLASH_BASE,
+ .end = CSB_FLASH_BASE + CSB_FLASH_SIZE - 1,
+ .flags = IORESOURCE_MEM,
+ }
+};
+
+static struct platform_device csb_flash = {
+ .name = "physmap-flash",
+ .id = 0,
+ .dev = {
+ .platform_data = &csb_flash_data,
+ },
+ .resource = csb_flash_resources,
+ .num_resources = ARRAY_SIZE(csb_flash_resources),
+};
+
static void __init csb337_board_init(void)
{
/* Serial */
@@ -130,7 +167,9 @@ static void __init csb337_board_init(void)
/* SPI */
at91_add_device_spi(csb337_spi_devices, ARRAY_SIZE(csb337_spi_devices));
/* MMC */
- at91_add_device_mmc(&csb337_mmc_data);
+ at91_add_device_mmc(0, &csb337_mmc_data);
+ /* NOR flash */
+ platform_device_register(&csb_flash);
}
MACHINE_START(CSB337, "Cogent CSB337")
diff --git a/arch/arm/mach-at91rm9200/board-csb637.c b/arch/arm/mach-at91/board-csb637.c
similarity index 75%
rename from arch/arm/mach-at91rm9200/board-csb637.c
rename to arch/arm/mach-at91/board-csb637.c
index a29fa0e822ce..77f04b935b3a 100644
--- a/arch/arm/mach-at91rm9200/board-csb637.c
+++ b/arch/arm/mach-at91/board-csb637.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-csb637.c
+ * linux/arch/arm/mach-at91/board-csb637.c
*
* Copyright (C) 2005 SAN People
*
@@ -23,6 +23,7 @@
#include
#include
#include
+#include
#include
#include
@@ -81,6 +82,42 @@ static struct at91_udc_data __initdata csb637_udc_data = {
.pullup_pin = AT91_PIN_PB1,
};
+#define CSB_FLASH_BASE AT91_CHIPSELECT_0
+#define CSB_FLASH_SIZE 0x1000000
+
+static struct mtd_partition csb_flash_partitions[] = {
+ {
+ .name = "uMON flash",
+ .offset = 0,
+ .size = MTDPART_SIZ_FULL,
+ .mask_flags = MTD_WRITEABLE, /* read only */
+ }
+};
+
+static struct physmap_flash_data csb_flash_data = {
+ .width = 2,
+ .parts = csb_flash_partitions,
+ .nr_parts = ARRAY_SIZE(csb_flash_partitions),
+};
+
+static struct resource csb_flash_resources[] = {
+ {
+ .start = CSB_FLASH_BASE,
+ .end = CSB_FLASH_BASE + CSB_FLASH_SIZE - 1,
+ .flags = IORESOURCE_MEM,
+ }
+};
+
+static struct platform_device csb_flash = {
+ .name = "physmap-flash",
+ .id = 0,
+ .dev = {
+ .platform_data = &csb_flash_data,
+ },
+ .resource = csb_flash_resources,
+ .num_resources = ARRAY_SIZE(csb_flash_resources),
+};
+
static void __init csb637_board_init(void)
{
/* Serial */
@@ -95,6 +132,8 @@ static void __init csb637_board_init(void)
at91_add_device_i2c();
/* SPI */
at91_add_device_spi(NULL, 0);
+ /* NOR flash */
+ platform_device_register(&csb_flash);
}
MACHINE_START(CSB637, "Cogent CSB637")
diff --git a/arch/arm/mach-at91rm9200/board-dk.c b/arch/arm/mach-at91/board-dk.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/board-dk.c
rename to arch/arm/mach-at91/board-dk.c
index 7522bf91bce8..6043c38c0a9e 100644
--- a/arch/arm/mach-at91rm9200/board-dk.c
+++ b/arch/arm/mach-at91/board-dk.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-dk.c
+ * linux/arch/arm/mach-at91/board-dk.c
*
* Copyright (C) 2005 SAN People
*
@@ -194,7 +194,7 @@ static void __init dk_board_init(void)
#else
/* MMC */
at91_set_gpio_output(AT91_PIN_PB7, 1); /* this MMC card slot can optionally use SPI signaling (CS3). */
- at91_add_device_mmc(&dk_mmc_data);
+ at91_add_device_mmc(0, &dk_mmc_data);
#endif
/* NAND */
at91_add_device_nand(&dk_nand_data);
diff --git a/arch/arm/mach-at91rm9200/board-eb9200.c b/arch/arm/mach-at91/board-eb9200.c
similarity index 97%
rename from arch/arm/mach-at91rm9200/board-eb9200.c
rename to arch/arm/mach-at91/board-eb9200.c
index 80b72cf7264c..20458b5548f0 100644
--- a/arch/arm/mach-at91rm9200/board-eb9200.c
+++ b/arch/arm/mach-at91/board-eb9200.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-eb9200.c
+ * linux/arch/arm/mach-at91/board-eb9200.c
*
* Copyright (C) 2005 SAN People, adapted for ATEB9200 from Embest
* by Andrew Patrikalakis
@@ -109,7 +109,7 @@ static void __init eb9200_board_init(void)
at91_add_device_spi(NULL, 0);
/* MMC */
/* only supports 1 or 4 bit interface, not wired through to SPI */
- at91_add_device_mmc(&eb9200_mmc_data);
+ at91_add_device_mmc(0, &eb9200_mmc_data);
}
MACHINE_START(ATEB9200, "Embest ATEB9200")
diff --git a/arch/arm/mach-at91rm9200/board-ek.c b/arch/arm/mach-at91/board-ek.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/board-ek.c
rename to arch/arm/mach-at91/board-ek.c
index c4fdb415f20e..322fdd75a1e4 100644
--- a/arch/arm/mach-at91rm9200/board-ek.c
+++ b/arch/arm/mach-at91/board-ek.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-ek.c
+ * linux/arch/arm/mach-at91/board-ek.c
*
* Copyright (C) 2005 SAN People
*
@@ -154,7 +154,7 @@ static void __init ek_board_init(void)
#else
/* MMC */
at91_set_gpio_output(AT91_PIN_PB22, 1); /* this MMC card slot can optionally use SPI signaling (CS3). */
- at91_add_device_mmc(&ek_mmc_data);
+ at91_add_device_mmc(0, &ek_mmc_data);
#endif
/* NOR Flash */
platform_device_register(&ek_flash);
diff --git a/arch/arm/mach-at91rm9200/board-kafa.c b/arch/arm/mach-at91/board-kafa.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/board-kafa.c
rename to arch/arm/mach-at91/board-kafa.c
index 6ef3c4879829..c77d84ce9cae 100644
--- a/arch/arm/mach-at91rm9200/board-kafa.c
+++ b/arch/arm/mach-at91/board-kafa.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-kafa.c
+ * linux/arch/arm/mach-at91/board-kafa.c
*
* Copyright (C) 2006 Sperry-Sun
*
diff --git a/arch/arm/mach-at91rm9200/board-kb9202.c b/arch/arm/mach-at91/board-kb9202.c
similarity index 97%
rename from arch/arm/mach-at91rm9200/board-kb9202.c
rename to arch/arm/mach-at91/board-kb9202.c
index 759d8191854f..76f6e1e553ea 100644
--- a/arch/arm/mach-at91rm9200/board-kb9202.c
+++ b/arch/arm/mach-at91/board-kb9202.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-kb9202.c
+ * linux/arch/arm/mach-at91/board-kb9202.c
*
* Copyright (c) 2005 kb_admin
* KwikByte, Inc.
@@ -122,7 +122,7 @@ static void __init kb9202_board_init(void)
/* USB Device */
at91_add_device_udc(&kb9202_udc_data);
/* MMC */
- at91_add_device_mmc(&kb9202_mmc_data);
+ at91_add_device_mmc(0, &kb9202_mmc_data);
/* I2C */
at91_add_device_i2c();
/* SPI */
diff --git a/arch/arm/mach-at91rm9200/board-sam9260ek.c b/arch/arm/mach-at91/board-sam9260ek.c
similarity index 96%
rename from arch/arm/mach-at91rm9200/board-sam9260ek.c
rename to arch/arm/mach-at91/board-sam9260ek.c
index da5d58ac870b..57fb4499d969 100644
--- a/arch/arm/mach-at91rm9200/board-sam9260ek.c
+++ b/arch/arm/mach-at91/board-sam9260ek.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-ek.c
+ * linux/arch/arm/mach-at91/board-sam9260ek.c
*
* Copyright (C) 2005 SAN People
* Copyright (C) 2006 Atmel
@@ -118,7 +118,7 @@ static struct spi_board_info ek_spi_devices[] = {
/*
* MACB Ethernet device
*/
-static struct __initdata eth_platform_data ek_macb_data = {
+static struct __initdata at91_eth_data ek_macb_data = {
.phy_irq_pin = AT91_PIN_PA7,
.is_rmii = 1,
};
@@ -187,7 +187,7 @@ static void __init ek_board_init(void)
/* Ethernet */
at91_add_device_eth(&ek_macb_data);
/* MMC */
- at91_add_device_mmc(&ek_mmc_data);
+ at91_add_device_mmc(0, &ek_mmc_data);
}
MACHINE_START(AT91SAM9260EK, "Atmel AT91SAM9260-EK")
diff --git a/arch/arm/mach-at91rm9200/board-sam9261ek.c b/arch/arm/mach-at91/board-sam9261ek.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/board-sam9261ek.c
rename to arch/arm/mach-at91/board-sam9261ek.c
index 30b490d8886b..b7e772467cf6 100644
--- a/arch/arm/mach-at91rm9200/board-sam9261ek.c
+++ b/arch/arm/mach-at91/board-sam9261ek.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/board-ek.c
+ * linux/arch/arm/mach-at91/board-sam9261ek.c
*
* Copyright (C) 2005 SAN People
* Copyright (C) 2006 Atmel
@@ -243,7 +243,7 @@ static void __init ek_board_init(void)
at91_add_device_spi(ek_spi_devices, ARRAY_SIZE(ek_spi_devices));
#else
/* MMC */
- at91_add_device_mmc(&ek_mmc_data);
+ at91_add_device_mmc(0, &ek_mmc_data);
#endif
}
diff --git a/arch/arm/mach-at91/board-sam9263ek.c b/arch/arm/mach-at91/board-sam9263ek.c
new file mode 100644
index 000000000000..8fdce11a880c
--- /dev/null
+++ b/arch/arm/mach-at91/board-sam9263ek.c
@@ -0,0 +1,176 @@
+/*
+ * linux/arch/arm/mach-at91/board-sam9263ek.c
+ *
+ * Copyright (C) 2005 SAN People
+ * Copyright (C) 2007 Atmel Corporation.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+ */
+
+#include
+#include
+#include
+#include
+#include
+#include
+
+#include
+#include
+#include
+#include
+
+#include
+#include
+#include
+
+#include
+#include
+#include
+
+#include "generic.h"
+
+
+/*
+ * Serial port configuration.
+ * 0 .. 2 = USART0 .. USART2
+ * 3 = DBGU
+ */
+static struct at91_uart_config __initdata ek_uart_config = {
+ .console_tty = 0, /* ttyS0 */
+ .nr_tty = 2,
+ .tty_map = { 3, 0, -1, -1, } /* ttyS0, ..., ttyS3 */
+};
+
+static void __init ek_map_io(void)
+{
+ /* Initialize processor: 16.367 MHz crystal */
+ at91sam9263_initialize(16367660);
+
+ /* Setup the serial ports and console */
+ at91_init_serial(&ek_uart_config);
+}
+
+static void __init ek_init_irq(void)
+{
+ at91sam9263_init_interrupts(NULL);
+}
+
+
+/*
+ * USB Host port
+ */
+static struct at91_usbh_data __initdata ek_usbh_data = {
+ .ports = 2,
+ .vbus_pin = { AT91_PIN_PA24, AT91_PIN_PA21 },
+};
+
+/*
+ * USB Device port
+ */
+static struct at91_udc_data __initdata ek_udc_data = {
+ .vbus_pin = AT91_PIN_PA25,
+ .pullup_pin = 0, /* pull-up driven by UDC */
+};
+
+
+/*
+ * SPI devices.
+ */
+static struct spi_board_info ek_spi_devices[] = {
+#if defined(CONFIG_MTD_AT91_DATAFLASH_CARD)
+ { /* DataFlash card */
+ .modalias = "mtd_dataflash",
+ .chip_select = 0,
+ .max_speed_hz = 15 * 1000 * 1000,
+ .bus_num = 0,
+ },
+#endif
+};
+
+
+/*
+ * MCI (SD/MMC)
+ */
+static struct at91_mmc_data __initdata ek_mmc_data = {
+ .wire4 = 1,
+ .det_pin = AT91_PIN_PE18,
+ .wp_pin = AT91_PIN_PE19,
+// .vcc_pin = ... not connected
+};
+
+
+/*
+ * NAND flash
+ */
+static struct mtd_partition __initdata ek_nand_partition[] = {
+ {
+ .name = "Partition 1",
+ .offset = 0,
+ .size = 64 * 1024 * 1024,
+ },
+ {
+ .name = "Partition 2",
+ .offset = 64 * 1024 * 1024,
+ .size = MTDPART_SIZ_FULL,
+ },
+};
+
+static struct mtd_partition *nand_partitions(int size, int *num_partitions)
+{
+ *num_partitions = ARRAY_SIZE(ek_nand_partition);
+ return ek_nand_partition;
+}
+
+static struct at91_nand_data __initdata ek_nand_data = {
+ .ale = 21,
+ .cle = 22,
+// .det_pin = ... not connected
+ .rdy_pin = AT91_PIN_PA22,
+ .enable_pin = AT91_PIN_PD15,
+ .partition_info = nand_partitions,
+#if defined(CONFIG_MTD_NAND_AT91_BUSWIDTH_16)
+ .bus_width_16 = 1,
+#else
+ .bus_width_16 = 0,
+#endif
+};
+
+
+static void __init ek_board_init(void)
+{
+ /* Serial */
+ at91_add_device_serial();
+ /* USB Host */
+ at91_add_device_usbh(&ek_usbh_data);
+ /* USB Device */
+ at91_add_device_udc(&ek_udc_data);
+ /* SPI */
+ at91_add_device_spi(ek_spi_devices, ARRAY_SIZE(ek_spi_devices));
+ /* MMC */
+ at91_add_device_mmc(1, &ek_mmc_data);
+ /* NAND */
+ at91_add_device_nand(&ek_nand_data);
+}
+
+MACHINE_START(AT91SAM9263EK, "Atmel AT91SAM9263-EK")
+ /* Maintainer: Atmel */
+ .phys_io = AT91_BASE_SYS,
+ .io_pg_offst = (AT91_VA_BASE_SYS >> 18) & 0xfffc,
+ .boot_params = AT91_SDRAM_BASE + 0x100,
+ .timer = &at91sam926x_timer,
+ .map_io = ek_map_io,
+ .init_irq = ek_init_irq,
+ .init_machine = ek_board_init,
+MACHINE_END
diff --git a/arch/arm/mach-at91rm9200/clock.c b/arch/arm/mach-at91/clock.c
similarity index 94%
rename from arch/arm/mach-at91rm9200/clock.c
rename to arch/arm/mach-at91/clock.c
index 4dee21fefe5a..f6cb74806043 100644
--- a/arch/arm/mach-at91rm9200/clock.c
+++ b/arch/arm/mach-at91/clock.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/clock.c
+ * linux/arch/arm/mach-at91/clock.c
*
* Copyright (C) 2005 David Brownell
* Copyright (C) 2005 Ivan Kokshaysky
@@ -525,27 +525,6 @@ fail:
return 0;
}
-/*
- * Several unused clocks may be active. Turn them off.
- */
-static void __init at91_periphclk_reset(void)
-{
- unsigned long reg;
- struct clk *clk;
-
- reg = at91_sys_read(AT91_PMC_PCSR);
-
- list_for_each_entry(clk, &clocks, node) {
- if (clk->mode != pmc_periph_mode)
- continue;
-
- if (clk->users > 0)
- reg &= ~clk->pmc_mask;
- }
-
- at91_sys_write(AT91_PMC_PCDR, reg);
-}
-
static struct clk *const standard_pmc_clocks[] __initdata = {
/* four primary clocks */
&clk32k,
@@ -586,7 +565,7 @@ int __init at91_clock_init(unsigned long main_clock)
pr_info("Clocks: PLLA overclocked, %ld MHz\n", plla.rate_hz / 1000000);
/*
- * USB clock init: choose 48 MHz PLLB value, turn all clocks off,
+ * USB clock init: choose 48 MHz PLLB value,
* disable 48MHz clock during usb peripheral suspend.
*
* REVISIT: assumes MCK doesn't derive from PLLB!
@@ -596,16 +575,10 @@ int __init at91_clock_init(unsigned long main_clock)
if (cpu_is_at91rm9200()) {
uhpck.pmc_mask = AT91RM9200_PMC_UHP;
udpck.pmc_mask = AT91RM9200_PMC_UDP;
- at91_sys_write(AT91_PMC_SCDR, AT91RM9200_PMC_UHP | AT91RM9200_PMC_UDP);
at91_sys_write(AT91_PMC_SCER, AT91RM9200_PMC_MCKUDP);
- } else if (cpu_is_at91sam9260()) {
+ } else if (cpu_is_at91sam9260() || cpu_is_at91sam9261() || cpu_is_at91sam9263()) {
uhpck.pmc_mask = AT91SAM926x_PMC_UHP;
udpck.pmc_mask = AT91SAM926x_PMC_UDP;
- at91_sys_write(AT91_PMC_SCDR, AT91SAM926x_PMC_UHP | AT91SAM926x_PMC_UDP);
- } else if (cpu_is_at91sam9261()) {
- uhpck.pmc_mask = (AT91SAM926x_PMC_UHP | AT91_PMC_HCK0);
- udpck.pmc_mask = AT91SAM926x_PMC_UDP;
- at91_sys_write(AT91_PMC_SCDR, AT91SAM926x_PMC_UHP | AT91_PMC_HCK0 | AT91SAM926x_PMC_UDP);
}
at91_sys_write(AT91_CKGR_PLLBR, 0);
@@ -634,11 +607,34 @@ int __init at91_clock_init(unsigned long main_clock)
(unsigned) main_clock / 1000000,
((unsigned) main_clock % 1000000) / 1000);
- /* disable all programmable clocks */
- at91_sys_write(AT91_PMC_SCDR, AT91_PMC_PCK0 | AT91_PMC_PCK1 | AT91_PMC_PCK2 | AT91_PMC_PCK3);
+ return 0;
+}
- /* disable all other unused peripheral clocks */
- at91_periphclk_reset();
+/*
+ * Several unused clocks may be active. Turn them off.
+ */
+static int __init at91_clock_reset(void)
+{
+ unsigned long pcdr = 0;
+ unsigned long scdr = 0;
+ struct clk *clk;
+
+ list_for_each_entry(clk, &clocks, node) {
+ if (clk->users > 0)
+ continue;
+
+ if (clk->mode == pmc_periph_mode)
+ pcdr |= clk->pmc_mask;
+
+ if (clk->mode == pmc_sys_mode)
+ scdr |= clk->pmc_mask;
+
+ pr_debug("Clocks: disable unused %s\n", clk->name);
+ }
+
+ at91_sys_write(AT91_PMC_PCDR, pcdr);
+ at91_sys_write(AT91_PMC_SCDR, scdr);
return 0;
}
+late_initcall(at91_clock_reset);
diff --git a/arch/arm/mach-at91rm9200/clock.h b/arch/arm/mach-at91/clock.h
similarity index 94%
rename from arch/arm/mach-at91rm9200/clock.h
rename to arch/arm/mach-at91/clock.h
index b5c7a2eb2d1d..1ba3b95ff359 100644
--- a/arch/arm/mach-at91rm9200/clock.h
+++ b/arch/arm/mach-at91/clock.h
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/clock.h
+ * linux/arch/arm/mach-at91/clock.h
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
diff --git a/arch/arm/mach-at91rm9200/generic.h b/arch/arm/mach-at91/generic.h
similarity index 90%
rename from arch/arm/mach-at91rm9200/generic.h
rename to arch/arm/mach-at91/generic.h
index 8c4d5a77d485..bda26221c522 100644
--- a/arch/arm/mach-at91rm9200/generic.h
+++ b/arch/arm/mach-at91/generic.h
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/generic.h
+ * linux/arch/arm/mach-at91/generic.h
*
* Copyright (C) 2005 David Brownell
*
@@ -12,11 +12,13 @@
extern void __init at91rm9200_initialize(unsigned long main_clock, unsigned short banks);
extern void __init at91sam9260_initialize(unsigned long main_clock);
extern void __init at91sam9261_initialize(unsigned long main_clock);
+extern void __init at91sam9263_initialize(unsigned long main_clock);
/* Interrupts */
extern void __init at91rm9200_init_interrupts(unsigned int priority[]);
extern void __init at91sam9260_init_interrupts(unsigned int priority[]);
extern void __init at91sam9261_init_interrupts(unsigned int priority[]);
+extern void __init at91sam9263_init_interrupts(unsigned int priority[]);
extern void __init at91_aic_init(unsigned int priority[]);
/* Timer */
diff --git a/arch/arm/mach-at91rm9200/gpio.c b/arch/arm/mach-at91/gpio.c
similarity index 99%
rename from arch/arm/mach-at91rm9200/gpio.c
rename to arch/arm/mach-at91/gpio.c
index af22659c8a28..9b7495cd555d 100644
--- a/arch/arm/mach-at91rm9200/gpio.c
+++ b/arch/arm/mach-at91/gpio.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/gpio.c
+ * linux/arch/arm/mach-at91/gpio.c
*
* Copyright (C) 2005 HP Labs
*
diff --git a/arch/arm/mach-at91rm9200/irq.c b/arch/arm/mach-at91/irq.c
similarity index 99%
rename from arch/arm/mach-at91rm9200/irq.c
rename to arch/arm/mach-at91/irq.c
index 2148daafd29c..78a5cdb746dc 100644
--- a/arch/arm/mach-at91rm9200/irq.c
+++ b/arch/arm/mach-at91/irq.c
@@ -1,5 +1,5 @@
/*
- * linux/arch/arm/mach-at91rm9200/irq.c
+ * linux/arch/arm/mach-at91/irq.c
*
* Copyright (C) 2004 SAN People
* Copyright (C) 2004 ATMEL
diff --git a/arch/arm/mach-at91rm9200/leds.c b/arch/arm/mach-at91/leds.c
similarity index 93%
rename from arch/arm/mach-at91rm9200/leds.c
rename to arch/arm/mach-at91/leds.c
index 1a333730466e..0d5144973988 100644
--- a/arch/arm/mach-at91rm9200/leds.c
+++ b/arch/arm/mach-at91/leds.c
@@ -86,10 +86,6 @@ static int __init leds_init(void)
if (!at91_leds_timer || !at91_leds_cpu)
return -ENODEV;
- /* Enable PIO to access the LEDs */
- at91_set_gpio_output(at91_leds_timer, 1);
- at91_set_gpio_output(at91_leds_cpu, 1);
-
leds_event = at91_leds_event;
leds_event(led_start);
diff --git a/arch/arm/mach-at91rm9200/pm.c b/arch/arm/mach-at91/pm.c
similarity index 98%
rename from arch/arm/mach-at91rm9200/pm.c
rename to arch/arm/mach-at91/pm.c
index 67aa5572a3ea..b49bfda53d7f 100644
--- a/arch/arm/mach-at91rm9200/pm.c
+++ b/arch/arm/mach-at91/pm.c
@@ -1,5 +1,5 @@
/*
- * arch/arm/mach-at91rm9200/pm.c
+ * arch/arm/mach-at91/pm.c
* AT91 Power Management
*
* Copyright (C) 2005 David Brownell
@@ -80,6 +80,8 @@ static int at91_pm_verify_clocks(void)
#warning "Check SAM9260 USB clocks"
} else if (cpu_is_at91sam9261()) {
#warning "Check SAM9261 USB clocks"
+ } else if (cpu_is_at91sam9263()) {
+#warning "Check SAM9263 USB clocks"
}
#ifdef CONFIG_AT91_PROGRAMMABLE_CLOCKS
diff --git a/arch/arm/mach-ep93xx/clock.c b/arch/arm/mach-ep93xx/clock.c
index 08ad782c1649..f174d1a3b11c 100644
--- a/arch/arm/mach-ep93xx/clock.c
+++ b/arch/arm/mach-ep93xx/clock.c
@@ -13,6 +13,7 @@
#include
#include
#include
+#include
#include
#include
#include
@@ -124,7 +125,7 @@ static unsigned long calc_pll_rate(u32 config_word)
return (unsigned long)rate;
}
-void ep93xx_clock_init(void)
+static int __init ep93xx_clock_init(void)
{
u32 value;
@@ -153,4 +154,7 @@ void ep93xx_clock_init(void)
printk(KERN_INFO "ep93xx: FCLK %ld MHz, HCLK %ld MHz, PCLK %ld MHz\n",
clk_f.rate / 1000000, clk_h.rate / 1000000,
clk_p.rate / 1000000);
+
+ return 0;
}
+arch_initcall(ep93xx_clock_init);
diff --git a/arch/arm/mach-ep93xx/core.c b/arch/arm/mach-ep93xx/core.c
index 6b26346191c0..829aed696d98 100644
--- a/arch/arm/mach-ep93xx/core.c
+++ b/arch/arm/mach-ep93xx/core.c
@@ -152,22 +152,30 @@ struct sys_timer ep93xx_timer = {
/*************************************************************************
* GPIO handling for EP93xx
*************************************************************************/
-static unsigned char gpio_int_enable[2];
-static unsigned char gpio_int_type1[2];
-static unsigned char gpio_int_type2[2];
+static unsigned char gpio_int_unmasked[3];
+static unsigned char gpio_int_enabled[3];
+static unsigned char gpio_int_type1[3];
+static unsigned char gpio_int_type2[3];
-static void update_gpio_ab_int_params(int port)
+static void update_gpio_int_params(int abf)
{
- if (port == 0) {
+ if (abf == 0) {
__raw_writeb(0, EP93XX_GPIO_A_INT_ENABLE);
__raw_writeb(gpio_int_type2[0], EP93XX_GPIO_A_INT_TYPE2);
__raw_writeb(gpio_int_type1[0], EP93XX_GPIO_A_INT_TYPE1);
- __raw_writeb(gpio_int_enable[0], EP93XX_GPIO_A_INT_ENABLE);
- } else if (port == 1) {
+ __raw_writeb(gpio_int_unmasked[0] & gpio_int_enabled[0], EP93XX_GPIO_A_INT_ENABLE);
+ } else if (abf == 1) {
__raw_writeb(0, EP93XX_GPIO_B_INT_ENABLE);
__raw_writeb(gpio_int_type2[1], EP93XX_GPIO_B_INT_TYPE2);
__raw_writeb(gpio_int_type1[1], EP93XX_GPIO_B_INT_TYPE1);
- __raw_writeb(gpio_int_enable[1], EP93XX_GPIO_B_INT_ENABLE);
+ __raw_writeb(gpio_int_unmasked[1] & gpio_int_enabled[1], EP93XX_GPIO_B_INT_ENABLE);
+ } else if (abf == 2) {
+ __raw_writeb(0, EP93XX_GPIO_F_INT_ENABLE);
+ __raw_writeb(gpio_int_type2[2], EP93XX_GPIO_F_INT_TYPE2);
+ __raw_writeb(gpio_int_type1[2], EP93XX_GPIO_F_INT_TYPE1);
+ __raw_writeb(gpio_int_unmasked[2] & gpio_int_enabled[2], EP93XX_GPIO_F_INT_ENABLE);
+ } else {
+ BUG();
}
}
@@ -192,8 +200,13 @@ void gpio_line_config(int line, int direction)
local_irq_save(flags);
if (direction == GPIO_OUT) {
if (line >= 0 && line < 16) {
- gpio_int_enable[line >> 3] &= ~(1 << (line & 7));
- update_gpio_ab_int_params(line >> 3);
+ /* Port A/B. */
+ gpio_int_unmasked[line >> 3] &= ~(1 << (line & 7));
+ update_gpio_int_params(line >> 3);
+ } else if (line >= 40 && line < 48) {
+ /* Port F. */
+ gpio_int_unmasked[2] &= ~(1 << (line & 7));
+ update_gpio_int_params(2);
}
v = __raw_readb(data_direction_register);
@@ -244,8 +257,7 @@ EXPORT_SYMBOL(gpio_line_set);
/*************************************************************************
* EP93xx IRQ handling
*************************************************************************/
-static void ep93xx_gpio_ab_irq_handler(unsigned int irq,
- struct irq_desc *desc)
+static void ep93xx_gpio_ab_irq_handler(unsigned int irq, struct irq_desc *desc)
{
unsigned char status;
int i;
@@ -267,37 +279,46 @@ static void ep93xx_gpio_ab_irq_handler(unsigned int irq,
}
}
-static void ep93xx_gpio_ab_irq_mask_ack(unsigned int irq)
+static void ep93xx_gpio_f_irq_handler(unsigned int irq, struct irq_desc *desc)
+{
+ int gpio_irq = IRQ_EP93XX_GPIO(16) + (((irq + 1) & 7) ^ 4);
+
+ desc_handle_irq(gpio_irq, irq_desc + gpio_irq);
+}
+
+static void ep93xx_gpio_irq_mask_ack(unsigned int irq)
{
int line = irq - IRQ_EP93XX_GPIO(0);
int port = line >> 3;
- gpio_int_enable[port] &= ~(1 << (line & 7));
- update_gpio_ab_int_params(port);
+ gpio_int_unmasked[port] &= ~(1 << (line & 7));
+ update_gpio_int_params(port);
- if (line >> 3) {
- __raw_writel(1 << (line & 7), EP93XX_GPIO_B_INT_ACK);
- } else {
+ if (port == 0) {
__raw_writel(1 << (line & 7), EP93XX_GPIO_A_INT_ACK);
+ } else if (port == 1) {
+ __raw_writel(1 << (line & 7), EP93XX_GPIO_B_INT_ACK);
+ } else if (port == 2) {
+ __raw_writel(1 << (line & 7), EP93XX_GPIO_F_INT_ACK);
}
}
-static void ep93xx_gpio_ab_irq_mask(unsigned int irq)
+static void ep93xx_gpio_irq_mask(unsigned int irq)
{
int line = irq - IRQ_EP93XX_GPIO(0);
int port = line >> 3;
- gpio_int_enable[port] &= ~(1 << (line & 7));
- update_gpio_ab_int_params(port);
+ gpio_int_unmasked[port] &= ~(1 << (line & 7));
+ update_gpio_int_params(port);
}
-static void ep93xx_gpio_ab_irq_unmask(unsigned int irq)
+static void ep93xx_gpio_irq_unmask(unsigned int irq)
{
int line = irq - IRQ_EP93XX_GPIO(0);
int port = line >> 3;
- gpio_int_enable[port] |= 1 << (line & 7);
- update_gpio_ab_int_params(port);
+ gpio_int_unmasked[port] |= 1 << (line & 7);
+ update_gpio_int_params(port);
}
@@ -306,40 +327,51 @@ static void ep93xx_gpio_ab_irq_unmask(unsigned int irq)
* edge (1) triggered, while gpio_int_type2 controls whether it
* triggers on low/falling (0) or high/rising (1).
*/
-static int ep93xx_gpio_ab_irq_type(unsigned int irq, unsigned int type)
+static int ep93xx_gpio_irq_type(unsigned int irq, unsigned int type)
{
int port;
int line;
line = irq - IRQ_EP93XX_GPIO(0);
- gpio_line_config(line, GPIO_IN);
+ if (line >= 0 && line < 16) {
+ gpio_line_config(line, GPIO_IN);
+ } else {
+ gpio_line_config(EP93XX_GPIO_LINE_F(line), GPIO_IN);
+ }
port = line >> 3;
line &= 7;
if (type & IRQT_RISING) {
+ gpio_int_enabled[port] |= 1 << line;
gpio_int_type1[port] |= 1 << line;
gpio_int_type2[port] |= 1 << line;
} else if (type & IRQT_FALLING) {
+ gpio_int_enabled[port] |= 1 << line;
gpio_int_type1[port] |= 1 << line;
gpio_int_type2[port] &= ~(1 << line);
} else if (type & IRQT_HIGH) {
+ gpio_int_enabled[port] |= 1 << line;
gpio_int_type1[port] &= ~(1 << line);
gpio_int_type2[port] |= 1 << line;
} else if (type & IRQT_LOW) {
+ gpio_int_enabled[port] |= 1 << line;
gpio_int_type1[port] &= ~(1 << line);
gpio_int_type2[port] &= ~(1 << line);
+ } else {
+ gpio_int_enabled[port] &= ~(1 << line);
}
- update_gpio_ab_int_params(port);
+ update_gpio_int_params(port);
return 0;
}
-static struct irq_chip ep93xx_gpio_ab_irq_chip = {
- .ack = ep93xx_gpio_ab_irq_mask_ack,
- .mask = ep93xx_gpio_ab_irq_mask,
- .unmask = ep93xx_gpio_ab_irq_unmask,
- .set_type = ep93xx_gpio_ab_irq_type,
+static struct irq_chip ep93xx_gpio_irq_chip = {
+ .name = "GPIO",
+ .ack = ep93xx_gpio_irq_mask_ack,
+ .mask = ep93xx_gpio_irq_mask,
+ .unmask = ep93xx_gpio_irq_unmask,
+ .set_type = ep93xx_gpio_irq_type,
};
@@ -350,12 +382,21 @@ void __init ep93xx_init_irq(void)
vic_init((void *)EP93XX_VIC1_BASE, 0, EP93XX_VIC1_VALID_IRQ_MASK);
vic_init((void *)EP93XX_VIC2_BASE, 32, EP93XX_VIC2_VALID_IRQ_MASK);
- for (irq = IRQ_EP93XX_GPIO(0) ; irq <= IRQ_EP93XX_GPIO(15); irq++) {
- set_irq_chip(irq, &ep93xx_gpio_ab_irq_chip);
+ for (irq = IRQ_EP93XX_GPIO(0); irq <= IRQ_EP93XX_GPIO(23); irq++) {
+ set_irq_chip(irq, &ep93xx_gpio_irq_chip);
set_irq_handler(irq, handle_level_irq);
set_irq_flags(irq, IRQF_VALID);
}
+
set_irq_chained_handler(IRQ_EP93XX_GPIO_AB, ep93xx_gpio_ab_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO0MUX, ep93xx_gpio_f_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO1MUX, ep93xx_gpio_f_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO2MUX, ep93xx_gpio_f_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO3MUX, ep93xx_gpio_f_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO4MUX, ep93xx_gpio_f_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO5MUX, ep93xx_gpio_f_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO6MUX, ep93xx_gpio_f_irq_handler);
+ set_irq_chained_handler(IRQ_EP93XX_GPIO7MUX, ep93xx_gpio_f_irq_handler);
}
@@ -461,8 +502,6 @@ void __init ep93xx_init_devices(void)
{
unsigned int v;
- ep93xx_clock_init();
-
/*
* Disallow access to MaverickCrunch initially.
*/
@@ -477,8 +516,4 @@ void __init ep93xx_init_devices(void)
platform_device_register(&ep93xx_rtc_device);
platform_device_register(&ep93xx_ohci_device);
-
-#ifdef CONFIG_CRUNCH
- elf_hwcap |= HWCAP_CRUNCH;
-#endif
}
diff --git a/arch/arm/mach-pxa/generic.c b/arch/arm/mach-pxa/generic.c
index 9de1278d234f..390524c4710f 100644
--- a/arch/arm/mach-pxa/generic.c
+++ b/arch/arm/mach-pxa/generic.c
@@ -338,6 +338,27 @@ static struct platform_device i2c_device = {
.num_resources = ARRAY_SIZE(i2c_resources),
};
+#ifdef CONFIG_PXA27x
+static struct resource i2c_power_resources[] = {
+ {
+ .start = 0x40f00180,
+ .end = 0x40f001a3,
+ .flags = IORESOURCE_MEM,
+ }, {
+ .start = IRQ_PWRI2C,
+ .end = IRQ_PWRI2C,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device i2c_power_device = {
+ .name = "pxa2xx-i2c",
+ .id = 1,
+ .resource = i2c_power_resources,
+ .num_resources = ARRAY_SIZE(i2c_resources),
+};
+#endif
+
void __init pxa_set_i2c_info(struct i2c_pxa_platform_data *info)
{
i2c_device.dev.platform_data = info;
@@ -392,6 +413,9 @@ static struct platform_device *devices[] __initdata = {
&stuart_device,
&pxaficp_device,
&i2c_device,
+#ifdef CONFIG_PXA27x
+ &i2c_power_device,
+#endif
&i2s_device,
&pxartc_device,
};
diff --git a/arch/arm/mach-realview/Kconfig b/arch/arm/mach-realview/Kconfig
index 17f5f4439fe7..35156ca39df7 100644
--- a/arch/arm/mach-realview/Kconfig
+++ b/arch/arm/mach-realview/Kconfig
@@ -10,10 +10,21 @@ config MACH_REALVIEW_EB
config REALVIEW_MPCORE
bool "Support MPcore tile"
depends on MACH_REALVIEW_EB
+ select CACHE_L2X0
help
Enable support for the MPCore tile on the Realview platform.
Since there are device address and interrupt differences, a
kernel built with this option enabled is not compatible with
other tiles.
+config REALVIEW_MPCORE_REVB
+ bool "Support MPcore RevB tile"
+ depends on REALVIEW_MPCORE
+ default n
+ help
+ Enable support for the MPCore RevB tile on the Realview platform.
+ Since there are device address differences, a
+ kernel built with this option enabled is not compatible with
+ other tiles.
+
endmenu
diff --git a/arch/arm/mach-realview/platsmp.c b/arch/arm/mach-realview/platsmp.c
index b8484e15dacb..fce3596f9950 100644
--- a/arch/arm/mach-realview/platsmp.c
+++ b/arch/arm/mach-realview/platsmp.c
@@ -52,13 +52,14 @@ void __cpuinit platform_secondary_init(unsigned int cpu)
* core (e.g. timer irq), then they will not have been enabled
* for us: do so
*/
- gic_cpu_init(__io_address(REALVIEW_GIC_CPU_BASE));
+ gic_cpu_init(0, __io_address(REALVIEW_GIC_CPU_BASE));
/*
* let the primary processor know we're out of the
* pen, then head off into the C entry point
*/
pen_release = -1;
+ smp_wmb();
/*
* Synchronise with the boot thread.
@@ -102,6 +103,7 @@ int __cpuinit boot_secondary(unsigned int cpu, struct task_struct *idle)
timeout = jiffies + (1 * HZ);
while (time_before(jiffies, timeout)) {
+ smp_rmb();
if (pen_release == -1)
break;
diff --git a/arch/arm/mach-realview/realview_eb.c b/arch/arm/mach-realview/realview_eb.c
index 9741b4d3c9cf..3dba666151db 100644
--- a/arch/arm/mach-realview/realview_eb.c
+++ b/arch/arm/mach-realview/realview_eb.c
@@ -31,6 +31,7 @@
#include
#include
#include
+#include
#include
#include
@@ -57,7 +58,26 @@ static struct map_desc realview_eb_io_desc[] __initdata = {
.pfn = __phys_to_pfn(REALVIEW_GIC_DIST_BASE),
.length = SZ_4K,
.type = MT_DEVICE,
+ },
+#ifdef CONFIG_REALVIEW_MPCORE
+ {
+ .virtual = IO_ADDRESS(REALVIEW_GIC1_CPU_BASE),
+ .pfn = __phys_to_pfn(REALVIEW_GIC1_CPU_BASE),
+ .length = SZ_4K,
+ .type = MT_DEVICE,
}, {
+ .virtual = IO_ADDRESS(REALVIEW_GIC1_DIST_BASE),
+ .pfn = __phys_to_pfn(REALVIEW_GIC1_DIST_BASE),
+ .length = SZ_4K,
+ .type = MT_DEVICE,
+ }, {
+ .virtual = IO_ADDRESS(REALVIEW_MPCORE_L220_BASE),
+ .pfn = __phys_to_pfn(REALVIEW_MPCORE_L220_BASE),
+ .length = SZ_8K,
+ .type = MT_DEVICE,
+ },
+#endif
+ {
.virtual = IO_ADDRESS(REALVIEW_SCTL_BASE),
.pfn = __phys_to_pfn(REALVIEW_SCTL_BASE),
.length = SZ_4K,
@@ -138,19 +158,29 @@ static void __init gic_init_irq(void)
#ifdef CONFIG_REALVIEW_MPCORE
unsigned int pldctrl;
writel(0x0000a05f, __io_address(REALVIEW_SYS_LOCK));
- pldctrl = readl(__io_address(REALVIEW_SYS_BASE) + 0xd8);
+ pldctrl = readl(__io_address(REALVIEW_SYS_BASE) + REALVIEW_MPCORE_SYS_PLD_CTRL1);
pldctrl |= 0x00800000; /* New irq mode */
- writel(pldctrl, __io_address(REALVIEW_SYS_BASE) + 0xd8);
+ writel(pldctrl, __io_address(REALVIEW_SYS_BASE) + REALVIEW_MPCORE_SYS_PLD_CTRL1);
writel(0x00000000, __io_address(REALVIEW_SYS_LOCK));
#endif
- gic_dist_init(__io_address(REALVIEW_GIC_DIST_BASE));
- gic_cpu_init(__io_address(REALVIEW_GIC_CPU_BASE));
+ gic_dist_init(0, __io_address(REALVIEW_GIC_DIST_BASE), 29);
+ gic_cpu_init(0, __io_address(REALVIEW_GIC_CPU_BASE));
+#ifdef CONFIG_REALVIEW_MPCORE
+ gic_dist_init(1, __io_address(REALVIEW_GIC1_DIST_BASE), 64);
+ gic_cpu_init(1, __io_address(REALVIEW_GIC1_CPU_BASE));
+ gic_cascade_irq(1, IRQ_EB_IRQ1);
+#endif
}
static void __init realview_eb_init(void)
{
int i;
+#ifdef CONFIG_REALVIEW_MPCORE
+ /* 1MB (128KB/way), 8-way associativity, evmon/parity/share enabled
+ * Bits: .... ...0 0111 1001 0000 .... .... .... */
+ l2x0_init(__io_address(REALVIEW_MPCORE_L220_BASE), 0x00790000, 0xfe000fff);
+#endif
clk_register(&realview_clcd_clk);
platform_device_register(&realview_flash_device);
diff --git a/arch/arm/mach-s3c2400/Kconfig b/arch/arm/mach-s3c2400/Kconfig
new file mode 100644
index 000000000000..deab0722836e
--- /dev/null
+++ b/arch/arm/mach-s3c2400/Kconfig
@@ -0,0 +1,13 @@
+# arch/arm/mach-s3c2400/Kconfig
+#
+# Copyright 2007 Simtec Electronics
+#
+# Licensed under GPLv2
+
+
+
+menu "S3C2400 Machines"
+
+
+endmenu
+
diff --git a/arch/arm/mach-s3c2400/Makefile b/arch/arm/mach-s3c2400/Makefile
new file mode 100644
index 000000000000..7e23f4e13766
--- /dev/null
+++ b/arch/arm/mach-s3c2400/Makefile
@@ -0,0 +1,15 @@
+# arch/arm/mach-s3c2400/Makefile
+#
+# Copyright 2007 Simtec Electronics
+#
+# Licensed under GPLv2
+
+obj-y :=
+obj-m :=
+obj-n :=
+obj- :=
+
+obj-$(CONFIG_CPU_S3C2400) += gpio.o
+
+# Machine support
+
diff --git a/arch/arm/mach-s3c2410/s3c2400-gpio.c b/arch/arm/mach-s3c2400/gpio.c
similarity index 96%
rename from arch/arm/mach-s3c2410/s3c2400-gpio.c
rename to arch/arm/mach-s3c2400/gpio.c
index 1576d01d5f82..758e160410e9 100644
--- a/arch/arm/mach-s3c2410/s3c2400-gpio.c
+++ b/arch/arm/mach-s3c2400/gpio.c
@@ -1,4 +1,4 @@
-/* linux/arch/arm/mach-s3c2410/s3c2400-gpio.c
+/* linux/arch/arm/mach-s3c2400/gpio.c
*
* Copyright (c) 2006 Lucas Correia Villa Real
*
diff --git a/arch/arm/mach-s3c2410/Kconfig b/arch/arm/mach-s3c2410/Kconfig
index eb4ec411312b..d4b013b283c3 100644
--- a/arch/arm/mach-s3c2410/Kconfig
+++ b/arch/arm/mach-s3c2410/Kconfig
@@ -1,30 +1,69 @@
-if ARCH_S3C2410
+# arch/arm/mach-s3c2410/Kconfig
+#
+# Copyright 2007 Simtec Electronics
+#
+# Licensed under GPLv2
-menu "S3C24XX Implementations"
+config CPU_S3C2410
+ bool
+ depends on ARCH_S3C2410
+ select S3C2410_CLOCK
+ select S3C2410_GPIO
+ select S3C2410_PM if PM
+ help
+ Support for S3C2410 and S3C2410A family from the S3C24XX line
+ of Samsung Mobile CPUs.
-config MACH_AML_M5900
- bool "AML M5900 Series"
+config CPU_S3C2410_DMA
+ bool
+ depends on S3C2410_DMA && (CPU_S3C2410 || CPU_S3C2442)
+ default y if CPU_S3C2410 || CPU_S3C2442
+ help
+ DMA device selection for S3C2410 and compatible CPUs
+
+config S3C2410_PM
+ bool
+ help
+ Power Management code common to S3C2410 and better
+
+config S3C2410_GPIO
+ bool
+ help
+ GPIO code for S3C2410 and similar processors
+
+config S3C2410_CLOCK
+ bool
+ help
+ Clock code for the S3C2410, and similar processors
+
+
+menu "S3C2410 Machines"
+
+config ARCH_SMDK2410
+ bool "SMDK2410/A9M2410"
select CPU_S3C2410
- select PM_SIMTEC if PM
+ select MACH_SMDK
help
- Say Y here if you are using the American Microsystems M5900 Series
-
+ Say Y here if you are using the SMDK2410 or the derived module A9M2410
+
-config MACH_ANUBIS
- bool "Simtec Electronics ANUBIS"
- select CPU_S3C2440
- select PM_SIMTEC if PM
+config ARCH_H1940
+ bool "IPAQ H1940"
+ select CPU_S3C2410
+ select PM_H1940 if PM
help
- Say Y here if you are using the Simtec Electronics ANUBIS
- development system
+ Say Y here if you are using the HP IPAQ H1940
-config MACH_OSIRIS
- bool "Simtec IM2440D20 (OSIRIS) module"
- select CPU_S3C2440
- select PM_SIMTEC if PM
+config PM_H1940
+ bool
help
- Say Y here if you are using the Simtec IM2440D20 module, also
- known as the Osiris.
+ Internal node for H1940 and related PM
+
+config MACH_N30
+ bool "Acer N30"
+ select CPU_S3C2410
+ help
+ Say Y here if you are using the Acer N30
config ARCH_BAST
bool "Simtec Electronics BAST (EB2410ITX)"
@@ -35,7 +74,19 @@ config ARCH_BAST
Say Y here if you are using the Simtec Electronics EB2410ITX
development board (also known as BAST)
- Product page: .
+config MACH_OTOM
+ bool "NexVision OTOM Board"
+ select CPU_S3C2410
+ help
+ Say Y here if you are using the Nex Vision OTOM board
+
+config MACH_AML_M5900
+ bool "AML M5900 Series"
+ select CPU_S3C2410
+ select PM_SIMTEC if PM
+ help
+ Say Y here if you are using the American Microsystems M5900 Series
+
config BAST_PC104_IRQ
bool "BAST PC104 IRQ support"
@@ -45,74 +96,6 @@ config BAST_PC104_IRQ
Say Y here to enable the PC104 IRQ routing on the
Simtec BAST (EB2410ITX)
-config PM_H1940
- bool
- help
- Internal node for H1940 and related PM
-
-config ARCH_H1940
- bool "IPAQ H1940"
- select CPU_S3C2410
- select PM_H1940 if PM
- help
- Say Y here if you are using the HP IPAQ H1940
-
- .
-
-config MACH_N30
- bool "Acer N30"
- select CPU_S3C2410
- help
- Say Y here if you are using the Acer N30
-
- .
-
-config MACH_SMDK
- bool
- help
- Common machine code for SMDK2410 and SMDK2440
-
-config ARCH_SMDK2410
- bool "SMDK2410/A9M2410"
- select CPU_S3C2410
- select MACH_SMDK
- help
- Say Y here if you are using the SMDK2410 or the derived module A9M2410
-
-
-config ARCH_S3C2440
- bool "SMDK2440"
- select CPU_S3C2440
- select MACH_SMDK
- help
- Say Y here if you are using the SMDK2440.
-
-config SMDK2440_CPU2440
- bool "SMDK2440 with S3C2440 CPU module"
- depends on ARCH_S3C2440
- default y if ARCH_S3C2440
- select CPU_S3C2440
-
-config SMDK2440_CPU2442
- bool "SMDM2440 with S3C2442 CPU module"
- depends on ARCH_S3C2440
- select CPU_S3C2442
-
-config MACH_S3C2413
- bool
- help
- Internal node for S3C2413 version of SMDK2413, so that
- machine_is_s3c2413() will work when MACH_SMDK2413 is
- selected
-
-config MACH_SMDK2413
- bool "SMDK2413"
- select CPU_S3C2412
- select MACH_S3C2413
- select MACH_SMDK
- help
- Say Y here if you are using an SMDK2413
-
config MACH_VR1000
bool "Thorcom VR1000"
select PM_SIMTEC if PM
@@ -120,202 +103,11 @@ config MACH_VR1000
help
Say Y here if you are using the Thorcom VR1000 board.
- This linux port is currently being maintained by Simtec, on behalf
- of Thorcom. Any queries, please contact Thorcom first.
-
-config MACH_RX3715
- bool "HP iPAQ rx3715"
- select CPU_S3C2440
- select PM_H1940 if PM
+config MACH_QT2410
+ bool "QT2410"
+ select CPU_S3C2410
help
- Say Y here if you are using the HP iPAQ rx3715.
-
- See for more
- information on this project
-
-config MACH_OTOM
- bool "NexVision OTOM Board"
- select CPU_S3C2410
- help
- Say Y here if you are using the Nex Vision OTOM board
-
-config MACH_NEXCODER_2440
- bool "NexVision NEXCODER 2440 Light Board"
- select CPU_S3C2440
- help
- Say Y here if you are using the Nex Vision NEXCODER 2440 Light Board
-
-config MACH_VSTMS
- bool "VMSTMS"
- select CPU_S3C2412
- help
- Say Y here if you are using an VSTMS board
+ Say Y here if you are using the Armzone QT2410
endmenu
-config S3C2410_CLOCK
- bool
- help
- Clock code for the S3C2410, and similar processors
-
-config S3C2410_PM
- bool
- help
- Power Management code common to S3C2410 and better
-
-config CPU_S3C2410_DMA
- bool
- depends on S3C2410_DMA && (CPU_S3C2410 || CPU_S3C2442)
- default y if CPU_S3C2410 || CPU_S3C2442
- help
- DMA device selection for S3C2410 and compatible CPUs
-
-config CPU_S3C2410
- bool
- depends on ARCH_S3C2410
- select S3C2410_CLOCK
- select S3C2410_PM if PM
- help
- Support for S3C2410 and S3C2410A family from the S3C24XX line
- of Samsung Mobile CPUs.
-
-# internal node to signify if we are only dealing with an S3C2412
-
-config CPU_S3C2412_ONLY
- bool
- depends on ARCH_S3C2410 && !CPU_S3C2400 && !CPU_S3C2410 && \
- !CPU_S3C2440 && !CPU_S3C2442 && CPU_S3C2412
- default y if CPU_S3C2412
-
-config S3C2412_PM
- bool
- help
- Internal config node to apply S3C2412 power management
-
-config CPU_S3C2412
- bool
- depends on ARCH_S3C2410
- select S3C2412_PM if PM
- help
- Support for the S3C2412 and S3C2413 SoCs from the S3C24XX line
-
-config CPU_S3C244X
- bool
- depends on ARCH_S3C2410 && (CPU_S3C2440 || CPU_S3C2442)
- help
- Support for S3C2440 and S3C2442 Samsung Mobile CPU based systems.
-
-config CPU_S3C2440
- bool
- depends on ARCH_S3C2410
- select S3C2410_CLOCK
- select S3C2410_PM if PM
- select CPU_S3C244X
- help
- Support for S3C2440 Samsung Mobile CPU based systems.
-
-config CPU_S3C2442
- bool
- depends on ARCH_S3C2420
- select S3C2410_CLOCK
- select S3C2410_PM if PM
- select CPU_S3C244X
- help
- Support for S3C2442 Samsung Mobile CPU based systems.
-
-comment "S3C2410 Boot"
-
-config S3C2410_BOOT_WATCHDOG
- bool "S3C2410 Initialisation watchdog"
- depends on ARCH_S3C2410 && S3C2410_WATCHDOG
- help
- Say y to enable the watchdog during the kernel decompression
- stage. If the kernel fails to uncompress, then the watchdog
- will trigger a reset and the system should restart.
-
- Although this uses the same hardware unit as the kernel watchdog
- driver, it is not a replacement for it. If you use this option,
- you will have to use the watchdg driver to either stop the timeout
- or restart it. If you do not, then your kernel will reboot after
- startup.
-
- The driver uses a fixed timeout value, so the exact time till the
- system resets depends on the value of PCLK. The timeout on an
- 200MHz s3c2410 should be about 30 seconds.
-
-config S3C2410_BOOT_ERROR_RESET
- bool "S3C2410 Reboot on decompression error"
- depends on ARCH_S3C2410
- help
- Say y here to use the watchdog to reset the system if the
- kernel decompressor detects an error during decompression.
-
-
-comment "S3C2410 Setup"
-
-config S3C2410_DMA
- bool "S3C2410 DMA support"
- depends on ARCH_S3C2410
- help
- S3C2410 DMA support. This is needed for drivers like sound which
- use the S3C2410's DMA system to move data to and from the
- peripheral blocks.
-
-config S3C2410_DMA_DEBUG
- bool "S3C2410 DMA support debug"
- depends on ARCH_S3C2410 && S3C2410_DMA
- help
- Enable debugging output for the DMA code. This option sends info
- to the kernel log, at priority KERN_DEBUG.
-
- Note, it is easy to create and fill the log buffer in a small
- amount of time, as well as using an significant percentage of
- the CPU time doing so.
-
-
-config S3C2410_PM_DEBUG
- bool "S3C2410 PM Suspend debug"
- depends on ARCH_S3C2410 && PM
- help
- Say Y here if you want verbose debugging from the PM Suspend and
- Resume code. See
- for more information.
-
-config S3C2410_PM_CHECK
- bool "S3C2410 PM Suspend Memory CRC"
- depends on ARCH_S3C2410 && PM && CRC32
- help
- Enable the PM code's memory area checksum over sleep. This option
- will generate CRCs of all blocks of memory, and store them before
- going to sleep. The blocks are then checked on resume for any
- errors.
-
-config S3C2410_PM_CHECK_CHUNKSIZE
- int "S3C2410 PM Suspend CRC Chunksize (KiB)"
- depends on ARCH_S3C2410 && PM && S3C2410_PM_CHECK
- default 64
- help
- Set the chunksize in Kilobytes of the CRC for checking memory
- corruption over suspend and resume. A smaller value will mean that
- the CRC data block will take more memory, but wil identify any
- faults with better precision.
-
-config PM_SIMTEC
- bool
- help
- Common power management code for systems that are
- compatible with the Simtec style of power management
-
-config S3C2410_LOWLEVEL_UART_PORT
- int "S3C2410 UART to use for low-level messages"
- default 0
- help
- Choice of which UART port to use for the low-level messages,
- such as the `Uncompressing...` at start time. The value of
- this configuration should be between zero and two. The port
- must have been initialised by the boot-loader before use.
-
- Note, this does not affect the port used by the debug messages,
- which is a separate configuration.
-
-endif
diff --git a/arch/arm/mach-s3c2410/Makefile b/arch/arm/mach-s3c2410/Makefile
index 27663e28cc88..9a3d3d24c084 100644
--- a/arch/arm/mach-s3c2410/Makefile
+++ b/arch/arm/mach-s3c2410/Makefile
@@ -1,92 +1,31 @@
-
+# arch/arm/mach-s3c2410/Makefile
#
-# Makefile for the linux kernel.
+# Copyright 2007 Simtec Electronics
#
+# Licensed under GPLv2
-# Object file lists.
-
-obj-y := cpu.o irq.o time.o gpio.o clock.o devs.o
-obj-m :=
-obj-n :=
-obj- :=
-obj-dma-y :=
-obj-dma-n :=
-
-# DMA
-obj-$(CONFIG_S3C2410_DMA) += dma.o
-
-# S3C2400 support files
-obj-$(CONFIG_CPU_S3C2400) += s3c2400-gpio.o
-
-# S3C2410 support files
+obj-y :=
+obj-m :=
+obj-n :=
+obj- :=
obj-$(CONFIG_CPU_S3C2410) += s3c2410.o
-obj-$(CONFIG_CPU_S3C2410) += s3c2410-gpio.o
-obj-$(CONFIG_CPU_S3C2410) += s3c2410-irq.o
+obj-$(CONFIG_CPU_S3C2410) += irq.o
+obj-$(CONFIG_CPU_S3C2410_DMA) += dma.o
+obj-$(CONFIG_CPU_S3C2410_DMA) += dma.o
+obj-$(CONFIG_S3C2410_PM) += pm.o sleep.o
+obj-$(CONFIG_S3C2410_GPIO) += gpio.o
+obj-$(CONFIG_S3C2410_CLOCK) += clock.o
-obj-$(CONFIG_S3C2410_PM) += s3c2410-pm.o s3c2410-sleep.o
-obj-$(CONFIG_CPU_S3C2410_DMA) += s3c2410-dma.o
+# Machine support
-# Power Management support
-
-obj-$(CONFIG_PM) += pm.o sleep.o
-obj-$(CONFIG_PM_SIMTEC) += pm-simtec.o
-obj-$(CONFIG_PM_H1940) += pm-h1940.o
-
-# S3C2412 support
-obj-$(CONFIG_CPU_S3C2412) += s3c2412.o
-obj-$(CONFIG_CPU_S3C2412) += s3c2412-irq.o
-obj-$(CONFIG_CPU_S3C2412) += s3c2412-clock.o
-obj-dma-$(CONFIG_CPU_S3C2412) += s3c2412-dma.o
-
-obj-$(CONFIG_S3C2412_PM) += s3c2412-pm.o
-
-#
-# S3C244X support
-
-obj-$(CONFIG_CPU_S3C244X) += s3c244x.o
-obj-$(CONFIG_CPU_S3C244X) += s3c244x-irq.o
-
-# Clock control
-
-obj-$(CONFIG_S3C2410_CLOCK) += s3c2410-clock.o
-
-# S3C2440 support
-
-obj-$(CONFIG_CPU_S3C2440) += s3c2440.o s3c2440-dsc.o
-obj-$(CONFIG_CPU_S3C2440) += s3c2440-irq.o
-obj-$(CONFIG_CPU_S3C2440) += s3c2440-clock.o
-obj-$(CONFIG_CPU_S3C2440) += s3c2410-gpio.o
-obj-dma-$(CONFIG_CPU_S3C2440) += s3c2440-dma.o
-
-# S3C2442 support
-
-obj-$(CONFIG_CPU_S3C2442) += s3c2442.o
-obj-$(CONFIG_CPU_S3C2442) += s3c2442-clock.o
-
-# bast extras
-
-obj-$(CONFIG_BAST_PC104_IRQ) += bast-irq.o
-
-# merge in dma objects
-
-obj-y += $(obj-dma-y)
-
-# machine specific support
-
-obj-$(CONFIG_MACH_AML_M5900) += mach-amlm5900.o
-obj-$(CONFIG_MACH_ANUBIS) += mach-anubis.o
-obj-$(CONFIG_MACH_OSIRIS) += mach-osiris.o
-obj-$(CONFIG_ARCH_BAST) += mach-bast.o usb-simtec.o
-obj-$(CONFIG_ARCH_H1940) += mach-h1940.o
-obj-$(CONFIG_MACH_N30) += mach-n30.o
obj-$(CONFIG_ARCH_SMDK2410) += mach-smdk2410.o
-obj-$(CONFIG_MACH_SMDK2413) += mach-smdk2413.o
-obj-$(CONFIG_ARCH_S3C2440) += mach-smdk2440.o
-obj-$(CONFIG_MACH_VR1000) += mach-vr1000.o usb-simtec.o
-obj-$(CONFIG_MACH_RX3715) += mach-rx3715.o
+obj-$(CONFIG_ARCH_H1940) += mach-h1940.o
+obj-$(CONFIG_PM_H1940) += pm-h1940.o
+obj-$(CONFIG_MACH_N30) += mach-n30.o
+obj-$(CONFIG_ARCH_BAST) += mach-bast.o usb-simtec.o
obj-$(CONFIG_MACH_OTOM) += mach-otom.o
-obj-$(CONFIG_MACH_NEXCODER_2440) += mach-nexcoder.o
-obj-$(CONFIG_MACH_VSTMS) += mach-vstms.o
-
-obj-$(CONFIG_MACH_SMDK) += common-smdk.o
\ No newline at end of file
+obj-$(CONFIG_MACH_AML_M5900) += mach-amlm5900.o
+obj-$(CONFIG_BAST_PC104_IRQ) += bast-irq.o
+obj-$(CONFIG_MACH_VR1000) += mach-vr1000.o usb-simtec.o
+obj-$(CONFIG_MACH_QT2410) += mach-qt2410.o
diff --git a/arch/arm/mach-s3c2410/bast-irq.c b/arch/arm/mach-s3c2410/bast-irq.c
index 379efe70778c..daeba427d781 100644
--- a/arch/arm/mach-s3c2410/bast-irq.c
+++ b/arch/arm/mach-s3c2410/bast-irq.c
@@ -39,7 +39,7 @@
#include
#include
-#include "irq.h"
+#include
#if 0
#include
diff --git a/arch/arm/mach-s3c2410/bast.h b/arch/arm/mach-s3c2410/bast.h
index e5d03311752c..e98543742eb9 100644
--- a/arch/arm/mach-s3c2410/bast.h
+++ b/arch/arm/mach-s3c2410/bast.h
@@ -1,2 +1,2 @@
-
+/* linux/arch/arm/mach-s3c2410/bast.h
extern void bast_init_irq(void);
diff --git a/arch/arm/mach-s3c2410/clock.c b/arch/arm/mach-s3c2410/clock.c
index e13fb6778890..5b4831c4c1d8 100644
--- a/arch/arm/mach-s3c2410/clock.c
+++ b/arch/arm/mach-s3c2410/clock.c
@@ -1,15 +1,9 @@
/* linux/arch/arm/mach-s3c2410/clock.c
*
- * Copyright (c) 2004-2005 Simtec Electronics
+ * Copyright (c) 2006 Simtec Electronics
* Ben Dooks
*
- * S3C24XX Core clock control support
- *
- * Based on, and code from linux/arch/arm/mach-versatile/clock.c
- **
- ** Copyright (C) 2004 ARM Limited.
- ** Written by Deep Blue Solutions Limited.
- *
+ * S3C2410,S3C2440,S3C2442 Clock control support
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -32,418 +26,251 @@
#include
#include
#include
-#include
#include
-#include
-#include
#include
#include
#include
+#include
+
+#include
#include
-#include
#include
+#include
#include
#include
-#include "clock.h"
-#include "cpu.h"
+#include
+#include
+#include
-/* clock information */
-
-static LIST_HEAD(clocks);
-
-DEFINE_MUTEX(clocks_mutex);
-
-/* enable and disable calls for use with the clk struct */
-
-static int clk_null_enable(struct clk *clk, int enable)
+int s3c2410_clkcon_enable(struct clk *clk, int enable)
{
- return 0;
-}
+ unsigned int clocks = clk->ctrlbit;
+ unsigned long clkcon;
-/* Clock API calls */
-
-struct clk *clk_get(struct device *dev, const char *id)
-{
- struct clk *p;
- struct clk *clk = ERR_PTR(-ENOENT);
- int idno;
-
- if (dev == NULL || dev->bus != &platform_bus_type)
- idno = -1;
- else
- idno = to_platform_device(dev)->id;
-
- mutex_lock(&clocks_mutex);
-
- list_for_each_entry(p, &clocks, list) {
- if (p->id == idno &&
- strcmp(id, p->name) == 0 &&
- try_module_get(p->owner)) {
- clk = p;
- break;
- }
- }
-
- /* check for the case where a device was supplied, but the
- * clock that was being searched for is not device specific */
-
- if (IS_ERR(clk)) {
- list_for_each_entry(p, &clocks, list) {
- if (p->id == -1 && strcmp(id, p->name) == 0 &&
- try_module_get(p->owner)) {
- clk = p;
- break;
- }
- }
- }
-
- mutex_unlock(&clocks_mutex);
- return clk;
-}
-
-void clk_put(struct clk *clk)
-{
- module_put(clk->owner);
-}
-
-int clk_enable(struct clk *clk)
-{
- if (IS_ERR(clk) || clk == NULL)
- return -EINVAL;
-
- clk_enable(clk->parent);
-
- mutex_lock(&clocks_mutex);
-
- if ((clk->usage++) == 0)
- (clk->enable)(clk, 1);
-
- mutex_unlock(&clocks_mutex);
- return 0;
-}
-
-void clk_disable(struct clk *clk)
-{
- if (IS_ERR(clk) || clk == NULL)
- return;
-
- mutex_lock(&clocks_mutex);
-
- if ((--clk->usage) == 0)
- (clk->enable)(clk, 0);
-
- mutex_unlock(&clocks_mutex);
- clk_disable(clk->parent);
-}
-
-
-unsigned long clk_get_rate(struct clk *clk)
-{
- if (IS_ERR(clk))
- return 0;
-
- if (clk->rate != 0)
- return clk->rate;
-
- if (clk->get_rate != NULL)
- return (clk->get_rate)(clk);
-
- if (clk->parent != NULL)
- return clk_get_rate(clk->parent);
-
- return clk->rate;
-}
-
-long clk_round_rate(struct clk *clk, unsigned long rate)
-{
- if (!IS_ERR(clk) && clk->round_rate)
- return (clk->round_rate)(clk, rate);
-
- return rate;
-}
-
-int clk_set_rate(struct clk *clk, unsigned long rate)
-{
- int ret;
-
- if (IS_ERR(clk))
- return -EINVAL;
-
- mutex_lock(&clocks_mutex);
- ret = (clk->set_rate)(clk, rate);
- mutex_unlock(&clocks_mutex);
-
- return ret;
-}
-
-struct clk *clk_get_parent(struct clk *clk)
-{
- return clk->parent;
-}
-
-int clk_set_parent(struct clk *clk, struct clk *parent)
-{
- int ret = 0;
-
- if (IS_ERR(clk))
- return -EINVAL;
-
- mutex_lock(&clocks_mutex);
-
- if (clk->set_parent)
- ret = (clk->set_parent)(clk, parent);
-
- mutex_unlock(&clocks_mutex);
-
- return ret;
-}
-
-EXPORT_SYMBOL(clk_get);
-EXPORT_SYMBOL(clk_put);
-EXPORT_SYMBOL(clk_enable);
-EXPORT_SYMBOL(clk_disable);
-EXPORT_SYMBOL(clk_get_rate);
-EXPORT_SYMBOL(clk_round_rate);
-EXPORT_SYMBOL(clk_set_rate);
-EXPORT_SYMBOL(clk_get_parent);
-EXPORT_SYMBOL(clk_set_parent);
-
-/* base clocks */
-
-struct clk clk_xtal = {
- .name = "xtal",
- .id = -1,
- .rate = 0,
- .parent = NULL,
- .ctrlbit = 0,
-};
-
-struct clk clk_mpll = {
- .name = "mpll",
- .id = -1,
-};
-
-struct clk clk_upll = {
- .name = "upll",
- .id = -1,
- .parent = NULL,
- .ctrlbit = 0,
-};
-
-struct clk clk_f = {
- .name = "fclk",
- .id = -1,
- .rate = 0,
- .parent = &clk_mpll,
- .ctrlbit = 0,
-};
-
-struct clk clk_h = {
- .name = "hclk",
- .id = -1,
- .rate = 0,
- .parent = NULL,
- .ctrlbit = 0,
-};
-
-struct clk clk_p = {
- .name = "pclk",
- .id = -1,
- .rate = 0,
- .parent = NULL,
- .ctrlbit = 0,
-};
-
-struct clk clk_usb_bus = {
- .name = "usb-bus",
- .id = -1,
- .rate = 0,
- .parent = &clk_upll,
-};
-
-/* clocks that could be registered by external code */
-
-static int s3c24xx_dclk_enable(struct clk *clk, int enable)
-{
- unsigned long dclkcon = __raw_readl(S3C24XX_DCLKCON);
+ clkcon = __raw_readl(S3C2410_CLKCON);
if (enable)
- dclkcon |= clk->ctrlbit;
+ clkcon |= clocks;
else
- dclkcon &= ~clk->ctrlbit;
+ clkcon &= ~clocks;
- __raw_writel(dclkcon, S3C24XX_DCLKCON);
+ /* ensure none of the special function bits set */
+ clkcon &= ~(S3C2410_CLKCON_IDLE|S3C2410_CLKCON_POWER);
+
+ __raw_writel(clkcon, S3C2410_CLKCON);
return 0;
}
-static int s3c24xx_dclk_setparent(struct clk *clk, struct clk *parent)
+static int s3c2410_upll_enable(struct clk *clk, int enable)
{
- unsigned long dclkcon;
- unsigned int uclk;
+ unsigned long clkslow = __raw_readl(S3C2410_CLKSLOW);
+ unsigned long orig = clkslow;
- if (parent == &clk_upll)
- uclk = 1;
- else if (parent == &clk_p)
- uclk = 0;
+ if (enable)
+ clkslow &= ~S3C2410_CLKSLOW_UCLK_OFF;
else
- return -EINVAL;
+ clkslow |= S3C2410_CLKSLOW_UCLK_OFF;
- clk->parent = parent;
+ __raw_writel(clkslow, S3C2410_CLKSLOW);
- dclkcon = __raw_readl(S3C24XX_DCLKCON);
+ /* if we started the UPLL, then allow to settle */
- if (clk->ctrlbit == S3C2410_DCLKCON_DCLK0EN) {
- if (uclk)
- dclkcon |= S3C2410_DCLKCON_DCLK0_UCLK;
- else
- dclkcon &= ~S3C2410_DCLKCON_DCLK0_UCLK;
- } else {
- if (uclk)
- dclkcon |= S3C2410_DCLKCON_DCLK1_UCLK;
- else
- dclkcon &= ~S3C2410_DCLKCON_DCLK1_UCLK;
+ if (enable && (orig & S3C2410_CLKSLOW_UCLK_OFF))
+ udelay(200);
+
+ return 0;
+}
+
+/* standard clock definitions */
+
+static struct clk init_clocks_disable[] = {
+ {
+ .name = "nand",
+ .id = -1,
+ .parent = &clk_h,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_NAND,
+ }, {
+ .name = "sdi",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_SDI,
+ }, {
+ .name = "adc",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_ADC,
+ }, {
+ .name = "i2c",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_IIC,
+ }, {
+ .name = "iis",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_IIS,
+ }, {
+ .name = "spi",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_SPI,
+ }
+};
+
+static struct clk init_clocks[] = {
+ {
+ .name = "lcd",
+ .id = -1,
+ .parent = &clk_h,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_LCDC,
+ }, {
+ .name = "gpio",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_GPIO,
+ }, {
+ .name = "usb-host",
+ .id = -1,
+ .parent = &clk_h,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_USBH,
+ }, {
+ .name = "usb-device",
+ .id = -1,
+ .parent = &clk_h,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_USBD,
+ }, {
+ .name = "timers",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_PWMT,
+ }, {
+ .name = "uart",
+ .id = 0,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_UART0,
+ }, {
+ .name = "uart",
+ .id = 1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_UART1,
+ }, {
+ .name = "uart",
+ .id = 2,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_UART2,
+ }, {
+ .name = "rtc",
+ .id = -1,
+ .parent = &clk_p,
+ .enable = s3c2410_clkcon_enable,
+ .ctrlbit = S3C2410_CLKCON_RTC,
+ }, {
+ .name = "watchdog",
+ .id = -1,
+ .parent = &clk_p,
+ .ctrlbit = 0,
+ }, {
+ .name = "usb-bus-host",
+ .id = -1,
+ .parent = &clk_usb_bus,
+ }, {
+ .name = "usb-bus-gadget",
+ .id = -1,
+ .parent = &clk_usb_bus,
+ },
+};
+
+/* s3c2410_baseclk_add()
+ *
+ * Add all the clocks used by the s3c2410 or compatible CPUs
+ * such as the S3C2440 and S3C2442.
+ *
+ * We cannot use a system device as we are needed before any
+ * of the init-calls that initialise the devices are actually
+ * done.
+*/
+
+int __init s3c2410_baseclk_add(void)
+{
+ unsigned long clkslow = __raw_readl(S3C2410_CLKSLOW);
+ unsigned long clkcon = __raw_readl(S3C2410_CLKCON);
+ struct clk *clkp;
+ struct clk *xtal;
+ int ret;
+ int ptr;
+
+ clk_upll.enable = s3c2410_upll_enable;
+
+ if (s3c24xx_register_clock(&clk_usb_bus) < 0)
+ printk(KERN_ERR "failed to register usb bus clock\n");
+
+ /* register clocks from clock array */
+
+ clkp = init_clocks;
+ for (ptr = 0; ptr < ARRAY_SIZE(init_clocks); ptr++, clkp++) {
+ /* ensure that we note the clock state */
+
+ clkp->usage = clkcon & clkp->ctrlbit ? 1 : 0;
+
+ ret = s3c24xx_register_clock(clkp);
+ if (ret < 0) {
+ printk(KERN_ERR "Failed to register clock %s (%d)\n",
+ clkp->name, ret);
+ }
}
- __raw_writel(dclkcon, S3C24XX_DCLKCON);
+ /* We must be careful disabling the clocks we are not intending to
+ * be using at boot time, as subsytems such as the LCD which do
+ * their own DMA requests to the bus can cause the system to lockup
+ * if they where in the middle of requesting bus access.
+ *
+ * Disabling the LCD clock if the LCD is active is very dangerous,
+ * and therefore the bootloader should be careful to not enable
+ * the LCD clock if it is not needed.
+ */
- return 0;
-}
+ /* install (and disable) the clocks we do not need immediately */
+ clkp = init_clocks_disable;
+ for (ptr = 0; ptr < ARRAY_SIZE(init_clocks_disable); ptr++, clkp++) {
-static int s3c24xx_clkout_setparent(struct clk *clk, struct clk *parent)
-{
- unsigned long mask;
- unsigned long source;
+ ret = s3c24xx_register_clock(clkp);
+ if (ret < 0) {
+ printk(KERN_ERR "Failed to register clock %s (%d)\n",
+ clkp->name, ret);
+ }
- /* calculate the MISCCR setting for the clock */
-
- if (parent == &clk_xtal)
- source = S3C2410_MISCCR_CLK0_MPLL;
- else if (parent == &clk_upll)
- source = S3C2410_MISCCR_CLK0_UPLL;
- else if (parent == &clk_f)
- source = S3C2410_MISCCR_CLK0_FCLK;
- else if (parent == &clk_h)
- source = S3C2410_MISCCR_CLK0_HCLK;
- else if (parent == &clk_p)
- source = S3C2410_MISCCR_CLK0_PCLK;
- else if (clk == &s3c24xx_clkout0 && parent == &s3c24xx_dclk0)
- source = S3C2410_MISCCR_CLK0_DCLK0;
- else if (clk == &s3c24xx_clkout1 && parent == &s3c24xx_dclk1)
- source = S3C2410_MISCCR_CLK0_DCLK0;
- else
- return -EINVAL;
-
- clk->parent = parent;
-
- if (clk == &s3c24xx_dclk0)
- mask = S3C2410_MISCCR_CLK0_MASK;
- else {
- source <<= 4;
- mask = S3C2410_MISCCR_CLK1_MASK;
+ s3c2410_clkcon_enable(clkp, 0);
}
- s3c2410_modify_misccr(mask, source);
- return 0;
-}
+ /* show the clock-slow value */
-/* external clock definitions */
+ xtal = clk_get(NULL, "xtal");
-struct clk s3c24xx_dclk0 = {
- .name = "dclk0",
- .id = -1,
- .ctrlbit = S3C2410_DCLKCON_DCLK0EN,
- .enable = s3c24xx_dclk_enable,
- .set_parent = s3c24xx_dclk_setparent,
-};
-
-struct clk s3c24xx_dclk1 = {
- .name = "dclk1",
- .id = -1,
- .ctrlbit = S3C2410_DCLKCON_DCLK0EN,
- .enable = s3c24xx_dclk_enable,
- .set_parent = s3c24xx_dclk_setparent,
-};
-
-struct clk s3c24xx_clkout0 = {
- .name = "clkout0",
- .id = -1,
- .set_parent = s3c24xx_clkout_setparent,
-};
-
-struct clk s3c24xx_clkout1 = {
- .name = "clkout1",
- .id = -1,
- .set_parent = s3c24xx_clkout_setparent,
-};
-
-struct clk s3c24xx_uclk = {
- .name = "uclk",
- .id = -1,
-};
-
-/* initialise the clock system */
-
-int s3c24xx_register_clock(struct clk *clk)
-{
- clk->owner = THIS_MODULE;
-
- if (clk->enable == NULL)
- clk->enable = clk_null_enable;
-
- /* add to the list of available clocks */
-
- mutex_lock(&clocks_mutex);
- list_add(&clk->list, &clocks);
- mutex_unlock(&clocks_mutex);
-
- return 0;
-}
-
-/* initalise all the clocks */
-
-int __init s3c24xx_setup_clocks(unsigned long xtal,
- unsigned long fclk,
- unsigned long hclk,
- unsigned long pclk)
-{
- printk(KERN_INFO "S3C24XX Clocks, (c) 2004 Simtec Electronics\n");
-
- /* initialise the main system clocks */
-
- clk_xtal.rate = xtal;
- clk_upll.rate = s3c2410_get_pll(__raw_readl(S3C2410_UPLLCON), xtal);
-
- clk_mpll.rate = fclk;
- clk_h.rate = hclk;
- clk_p.rate = pclk;
- clk_f.rate = fclk;
-
- /* assume uart clocks are correctly setup */
-
- /* register our clocks */
-
- if (s3c24xx_register_clock(&clk_xtal) < 0)
- printk(KERN_ERR "failed to register master xtal\n");
-
- if (s3c24xx_register_clock(&clk_mpll) < 0)
- printk(KERN_ERR "failed to register mpll clock\n");
-
- if (s3c24xx_register_clock(&clk_upll) < 0)
- printk(KERN_ERR "failed to register upll clock\n");
-
- if (s3c24xx_register_clock(&clk_f) < 0)
- printk(KERN_ERR "failed to register cpu fclk\n");
-
- if (s3c24xx_register_clock(&clk_h) < 0)
- printk(KERN_ERR "failed to register cpu hclk\n");
-
- if (s3c24xx_register_clock(&clk_p) < 0)
- printk(KERN_ERR "failed to register cpu pclk\n");
+ printk("CLOCK: Slow mode (%ld.%ld MHz), %s, MPLL %s, UPLL %s\n",
+ print_mhz(clk_get_rate(xtal) /
+ ( 2 * S3C2410_CLKSLOW_GET_SLOWVAL(clkslow))),
+ (clkslow & S3C2410_CLKSLOW_SLOW) ? "slow" : "fast",
+ (clkslow & S3C2410_CLKSLOW_MPLL_OFF) ? "off" : "on",
+ (clkslow & S3C2410_CLKSLOW_UCLK_OFF) ? "off" : "on");
return 0;
}
diff --git a/arch/arm/mach-s3c2410/dma.c b/arch/arm/mach-s3c2410/dma.c
index fa860e716b4f..67d1ad363973 100644
--- a/arch/arm/mach-s3c2410/dma.c
+++ b/arch/arm/mach-s3c2410/dma.c
@@ -1,9 +1,9 @@
/* linux/arch/arm/mach-s3c2410/dma.c
*
- * Copyright (c) 2003-2005,2006 Simtec Electronics
+ * Copyright (c) 2006 Simtec Electronics
* Ben Dooks
*
- * S3C2410 DMA core
+ * S3C2410 DMA selection
*
* http://armlinux.simtec.co.uk/
*
@@ -12,1430 +12,170 @@
* published by the Free Software Foundation.
*/
-
-#ifdef CONFIG_S3C2410_DMA_DEBUG
-#define DEBUG
-#endif
-
-#include
+#include
#include
-#include
-#include
-#include
#include
-#include
-#include
-#include
+#include
-#include
-#include
-#include
-#include
#include
+#include
-#include
-#include
+#include
+#include
-#include "dma.h"
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
-/* io map for dma */
-static void __iomem *dma_base;
-static struct kmem_cache *dma_kmem;
-
-struct s3c24xx_dma_selection dma_sel;
-
-/* dma channel state information */
-struct s3c2410_dma_chan s3c2410_chans[S3C2410_DMA_CHANNELS];
-
-/* debugging functions */
-
-#define BUF_MAGIC (0xcafebabe)
-
-#define dmawarn(fmt...) printk(KERN_DEBUG fmt)
-
-#define dma_regaddr(chan, reg) ((chan)->regs + (reg))
-
-#if 1
-#define dma_wrreg(chan, reg, val) writel((val), (chan)->regs + (reg))
-#else
-static inline void
-dma_wrreg(struct s3c2410_dma_chan *chan, int reg, unsigned long val)
-{
- pr_debug("writing %08x to register %08x\n",(unsigned int)val,reg);
- writel(val, dma_regaddr(chan, reg));
-}
-#endif
-
-#define dma_rdreg(chan, reg) readl((chan)->regs + (reg))
-
-/* captured register state for debug */
-
-struct s3c2410_dma_regstate {
- unsigned long dcsrc;
- unsigned long disrc;
- unsigned long dstat;
- unsigned long dcon;
- unsigned long dmsktrig;
+static struct s3c24xx_dma_map __initdata s3c2410_dma_mappings[] = {
+ [DMACH_XD0] = {
+ .name = "xdreq0",
+ .channels[0] = S3C2410_DCON_CH0_XDREQ0 | DMA_CH_VALID,
+ },
+ [DMACH_XD1] = {
+ .name = "xdreq1",
+ .channels[1] = S3C2410_DCON_CH1_XDREQ1 | DMA_CH_VALID,
+ },
+ [DMACH_SDI] = {
+ .name = "sdi",
+ .channels[0] = S3C2410_DCON_CH0_SDI | DMA_CH_VALID,
+ .channels[2] = S3C2410_DCON_CH2_SDI | DMA_CH_VALID,
+ .channels[3] = S3C2410_DCON_CH3_SDI | DMA_CH_VALID,
+ .hw_addr.to = S3C2410_PA_IIS + S3C2410_IISFIFO,
+ .hw_addr.from = S3C2410_PA_IIS + S3C2410_IISFIFO,
+ },
+ [DMACH_SPI0] = {
+ .name = "spi0",
+ .channels[1] = S3C2410_DCON_CH1_SPI | DMA_CH_VALID,
+ .hw_addr.to = S3C2410_PA_SPI + S3C2410_SPTDAT,
+ .hw_addr.from = S3C2410_PA_SPI + S3C2410_SPRDAT,
+ },
+ [DMACH_SPI1] = {
+ .name = "spi1",
+ .channels[3] = S3C2410_DCON_CH3_SPI | DMA_CH_VALID,
+ .hw_addr.to = S3C2410_PA_SPI + 0x20 + S3C2410_SPTDAT,
+ .hw_addr.from = S3C2410_PA_SPI + 0x20 + S3C2410_SPRDAT,
+ },
+ [DMACH_UART0] = {
+ .name = "uart0",
+ .channels[0] = S3C2410_DCON_CH0_UART0 | DMA_CH_VALID,
+ .hw_addr.to = S3C2410_PA_UART0 + S3C2410_UTXH,
+ .hw_addr.from = S3C2410_PA_UART0 + S3C2410_URXH,
+ },
+ [DMACH_UART1] = {
+ .name = "uart1",
+ .channels[1] = S3C2410_DCON_CH1_UART1 | DMA_CH_VALID,
+ .hw_addr.to = S3C2410_PA_UART1 + S3C2410_UTXH,
+ .hw_addr.from = S3C2410_PA_UART1 + S3C2410_URXH,
+ },
+ [DMACH_UART2] = {
+ .name = "uart2",
+ .channels[3] = S3C2410_DCON_CH3_UART2 | DMA_CH_VALID,
+ .hw_addr.to = S3C2410_PA_UART2 + S3C2410_UTXH,
+ .hw_addr.from = S3C2410_PA_UART2 + S3C2410_URXH,
+ },
+ [DMACH_TIMER] = {
+ .name = "timer",
+ .channels[0] = S3C2410_DCON_CH0_TIMER | DMA_CH_VALID,
+ .channels[2] = S3C2410_DCON_CH2_TIMER | DMA_CH_VALID,
+ .channels[3] = S3C2410_DCON_CH3_TIMER | DMA_CH_VALID,
+ },
+ [DMACH_I2S_IN] = {
+ .name = "i2s-sdi",
+ .channels[1] = S3C2410_DCON_CH1_I2SSDI | DMA_CH_VALID,
+ .channels[2] = S3C2410_DCON_CH2_I2SSDI | DMA_CH_VALID,
+ .hw_addr.from = S3C2410_PA_IIS + S3C2410_IISFIFO,
+ },
+ [DMACH_I2S_OUT] = {
+ .name = "i2s-sdo",
+ .channels[2] = S3C2410_DCON_CH2_I2SSDO | DMA_CH_VALID,
+ .hw_addr.to = S3C2410_PA_IIS + S3C2410_IISFIFO,
+ },
+ [DMACH_USB_EP1] = {
+ .name = "usb-ep1",
+ .channels[0] = S3C2410_DCON_CH0_USBEP1 | DMA_CH_VALID,
+ },
+ [DMACH_USB_EP2] = {
+ .name = "usb-ep2",
+ .channels[1] = S3C2410_DCON_CH1_USBEP2 | DMA_CH_VALID,
+ },
+ [DMACH_USB_EP3] = {
+ .name = "usb-ep3",
+ .channels[2] = S3C2410_DCON_CH2_USBEP3 | DMA_CH_VALID,
+ },
+ [DMACH_USB_EP4] = {
+ .name = "usb-ep4",
+ .channels[3] =S3C2410_DCON_CH3_USBEP4 | DMA_CH_VALID,
+ },
};
-#ifdef CONFIG_S3C2410_DMA_DEBUG
-
-/* dmadbg_showregs
- *
- * simple debug routine to print the current state of the dma registers
-*/
-
-static void
-dmadbg_capture(struct s3c2410_dma_chan *chan, struct s3c2410_dma_regstate *regs)
+static void s3c2410_dma_select(struct s3c2410_dma_chan *chan,
+ struct s3c24xx_dma_map *map)
{
- regs->dcsrc = dma_rdreg(chan, S3C2410_DMA_DCSRC);
- regs->disrc = dma_rdreg(chan, S3C2410_DMA_DISRC);
- regs->dstat = dma_rdreg(chan, S3C2410_DMA_DSTAT);
- regs->dcon = dma_rdreg(chan, S3C2410_DMA_DCON);
- regs->dmsktrig = dma_rdreg(chan, S3C2410_DMA_DMASKTRIG);
+ chan->dcon = map->channels[chan->number] & ~DMA_CH_VALID;
}
-static void
-dmadbg_dumpregs(const char *fname, int line, struct s3c2410_dma_chan *chan,
- struct s3c2410_dma_regstate *regs)
-{
- printk(KERN_DEBUG "dma%d: %s:%d: DCSRC=%08lx, DISRC=%08lx, DSTAT=%08lx DMT=%02lx, DCON=%08lx\n",
- chan->number, fname, line,
- regs->dcsrc, regs->disrc, regs->dstat, regs->dmsktrig,
- regs->dcon);
-}
-
-static void
-dmadbg_showchan(const char *fname, int line, struct s3c2410_dma_chan *chan)
-{
- struct s3c2410_dma_regstate state;
-
- dmadbg_capture(chan, &state);
-
- printk(KERN_DEBUG "dma%d: %s:%d: ls=%d, cur=%p, %p %p\n",
- chan->number, fname, line, chan->load_state,
- chan->curr, chan->next, chan->end);
-
- dmadbg_dumpregs(fname, line, chan, &state);
-}
-
-static void
-dmadbg_showregs(const char *fname, int line, struct s3c2410_dma_chan *chan)
-{
- struct s3c2410_dma_regstate state;
-
- dmadbg_capture(chan, &state);
- dmadbg_dumpregs(fname, line, chan, &state);
-}
-
-#define dbg_showregs(chan) dmadbg_showregs(__FUNCTION__, __LINE__, (chan))
-#define dbg_showchan(chan) dmadbg_showchan(__FUNCTION__, __LINE__, (chan))
-#else
-#define dbg_showregs(chan) do { } while(0)
-#define dbg_showchan(chan) do { } while(0)
-#endif /* CONFIG_S3C2410_DMA_DEBUG */
-
-static struct s3c2410_dma_chan *dma_chan_map[DMACH_MAX];
-
-/* lookup_dma_channel
- *
- * change the dma channel number given into a real dma channel id
-*/
-
-static struct s3c2410_dma_chan *lookup_dma_channel(unsigned int channel)
-{
- if (channel & DMACH_LOW_LEVEL)
- return &s3c2410_chans[channel & ~DMACH_LOW_LEVEL];
- else
- return dma_chan_map[channel];
-}
-
-/* s3c2410_dma_stats_timeout
- *
- * Update DMA stats from timeout info
-*/
-
-static void
-s3c2410_dma_stats_timeout(struct s3c2410_dma_stats *stats, int val)
-{
- if (stats == NULL)
- return;
-
- if (val > stats->timeout_longest)
- stats->timeout_longest = val;
- if (val < stats->timeout_shortest)
- stats->timeout_shortest = val;
-
- stats->timeout_avg += val;
-}
-
-/* s3c2410_dma_waitforload
- *
- * wait for the DMA engine to load a buffer, and update the state accordingly
-*/
-
-static int
-s3c2410_dma_waitforload(struct s3c2410_dma_chan *chan, int line)
-{
- int timeout = chan->load_timeout;
- int took;
-
- if (chan->load_state != S3C2410_DMALOAD_1LOADED) {
- printk(KERN_ERR "dma%d: s3c2410_dma_waitforload() called in loadstate %d from line %d\n", chan->number, chan->load_state, line);
- return 0;
- }
-
- if (chan->stats != NULL)
- chan->stats->loads++;
-
- while (--timeout > 0) {
- if ((dma_rdreg(chan, S3C2410_DMA_DSTAT) << (32-20)) != 0) {
- took = chan->load_timeout - timeout;
-
- s3c2410_dma_stats_timeout(chan->stats, took);
-
- switch (chan->load_state) {
- case S3C2410_DMALOAD_1LOADED:
- chan->load_state = S3C2410_DMALOAD_1RUNNING;
- break;
-
- default:
- printk(KERN_ERR "dma%d: unknown load_state in s3c2410_dma_waitforload() %d\n", chan->number, chan->load_state);
- }
-
- return 1;
- }
- }
-
- if (chan->stats != NULL) {
- chan->stats->timeout_failed++;
- }
-
- return 0;
-}
-
-
-
-/* s3c2410_dma_loadbuffer
- *
- * load a buffer, and update the channel state
-*/
-
-static inline int
-s3c2410_dma_loadbuffer(struct s3c2410_dma_chan *chan,
- struct s3c2410_dma_buf *buf)
-{
- unsigned long reload;
-
- pr_debug("s3c2410_chan_loadbuffer: loading buff %p (0x%08lx,0x%06x)\n",
- buf, (unsigned long)buf->data, buf->size);
-
- if (buf == NULL) {
- dmawarn("buffer is NULL\n");
- return -EINVAL;
- }
-
- /* check the state of the channel before we do anything */
-
- if (chan->load_state == S3C2410_DMALOAD_1LOADED) {
- dmawarn("load_state is S3C2410_DMALOAD_1LOADED\n");
- }
-
- if (chan->load_state == S3C2410_DMALOAD_1LOADED_1RUNNING) {
- dmawarn("state is S3C2410_DMALOAD_1LOADED_1RUNNING\n");
- }
-
- /* it would seem sensible if we are the last buffer to not bother
- * with the auto-reload bit, so that the DMA engine will not try
- * and load another transfer after this one has finished...
- */
- if (chan->load_state == S3C2410_DMALOAD_NONE) {
- pr_debug("load_state is none, checking for noreload (next=%p)\n",
- buf->next);
- reload = (buf->next == NULL) ? S3C2410_DCON_NORELOAD : 0;
- } else {
- //pr_debug("load_state is %d => autoreload\n", chan->load_state);
- reload = S3C2410_DCON_AUTORELOAD;
- }
-
- if ((buf->data & 0xf0000000) != 0x30000000) {
- dmawarn("dmaload: buffer is %p\n", (void *)buf->data);
- }
-
- writel(buf->data, chan->addr_reg);
-
- dma_wrreg(chan, S3C2410_DMA_DCON,
- chan->dcon | reload | (buf->size/chan->xfer_unit));
-
- chan->next = buf->next;
-
- /* update the state of the channel */
-
- switch (chan->load_state) {
- case S3C2410_DMALOAD_NONE:
- chan->load_state = S3C2410_DMALOAD_1LOADED;
- break;
-
- case S3C2410_DMALOAD_1RUNNING:
- chan->load_state = S3C2410_DMALOAD_1LOADED_1RUNNING;
- break;
-
- default:
- dmawarn("dmaload: unknown state %d in loadbuffer\n",
- chan->load_state);
- break;
- }
-
- return 0;
-}
-
-/* s3c2410_dma_call_op
- *
- * small routine to call the op routine with the given op if it has been
- * registered
-*/
-
-static void
-s3c2410_dma_call_op(struct s3c2410_dma_chan *chan, enum s3c2410_chan_op op)
-{
- if (chan->op_fn != NULL) {
- (chan->op_fn)(chan, op);
- }
-}
-
-/* s3c2410_dma_buffdone
- *
- * small wrapper to check if callback routine needs to be called, and
- * if so, call it
-*/
-
-static inline void
-s3c2410_dma_buffdone(struct s3c2410_dma_chan *chan, struct s3c2410_dma_buf *buf,
- enum s3c2410_dma_buffresult result)
-{
-#if 0
- pr_debug("callback_fn=%p, buf=%p, id=%p, size=%d, result=%d\n",
- chan->callback_fn, buf, buf->id, buf->size, result);
-#endif
-
- if (chan->callback_fn != NULL) {
- (chan->callback_fn)(chan, buf->id, buf->size, result);
- }
-}
-
-/* s3c2410_dma_start
- *
- * start a dma channel going
-*/
-
-static int s3c2410_dma_start(struct s3c2410_dma_chan *chan)
-{
- unsigned long tmp;
- unsigned long flags;
-
- pr_debug("s3c2410_start_dma: channel=%d\n", chan->number);
-
- local_irq_save(flags);
-
- if (chan->state == S3C2410_DMA_RUNNING) {
- pr_debug("s3c2410_start_dma: already running (%d)\n", chan->state);
- local_irq_restore(flags);
- return 0;
- }
-
- chan->state = S3C2410_DMA_RUNNING;
-
- /* check wether there is anything to load, and if not, see
- * if we can find anything to load
- */
-
- if (chan->load_state == S3C2410_DMALOAD_NONE) {
- if (chan->next == NULL) {
- printk(KERN_ERR "dma%d: channel has nothing loaded\n",
- chan->number);
- chan->state = S3C2410_DMA_IDLE;
- local_irq_restore(flags);
- return -EINVAL;
- }
-
- s3c2410_dma_loadbuffer(chan, chan->next);
- }
-
- dbg_showchan(chan);
-
- /* enable the channel */
-
- if (!chan->irq_enabled) {
- enable_irq(chan->irq);
- chan->irq_enabled = 1;
- }
-
- /* start the channel going */
-
- tmp = dma_rdreg(chan, S3C2410_DMA_DMASKTRIG);
- tmp &= ~S3C2410_DMASKTRIG_STOP;
- tmp |= S3C2410_DMASKTRIG_ON;
- dma_wrreg(chan, S3C2410_DMA_DMASKTRIG, tmp);
-
- pr_debug("dma%d: %08lx to DMASKTRIG\n", chan->number, tmp);
-
-#if 0
- /* the dma buffer loads should take care of clearing the AUTO
- * reloading feature */
- tmp = dma_rdreg(chan, S3C2410_DMA_DCON);
- tmp &= ~S3C2410_DCON_NORELOAD;
- dma_wrreg(chan, S3C2410_DMA_DCON, tmp);
-#endif
-
- s3c2410_dma_call_op(chan, S3C2410_DMAOP_START);
-
- dbg_showchan(chan);
-
- /* if we've only loaded one buffer onto the channel, then chec
- * to see if we have another, and if so, try and load it so when
- * the first buffer is finished, the new one will be loaded onto
- * the channel */
-
- if (chan->next != NULL) {
- if (chan->load_state == S3C2410_DMALOAD_1LOADED) {
-
- if (s3c2410_dma_waitforload(chan, __LINE__) == 0) {
- pr_debug("%s: buff not yet loaded, no more todo\n",
- __FUNCTION__);
- } else {
- chan->load_state = S3C2410_DMALOAD_1RUNNING;
- s3c2410_dma_loadbuffer(chan, chan->next);
- }
-
- } else if (chan->load_state == S3C2410_DMALOAD_1RUNNING) {
- s3c2410_dma_loadbuffer(chan, chan->next);
- }
- }
-
-
- local_irq_restore(flags);
-
- return 0;
-}
-
-/* s3c2410_dma_canload
- *
- * work out if we can queue another buffer into the DMA engine
-*/
-
-static int
-s3c2410_dma_canload(struct s3c2410_dma_chan *chan)
-{
- if (chan->load_state == S3C2410_DMALOAD_NONE ||
- chan->load_state == S3C2410_DMALOAD_1RUNNING)
- return 1;
-
- return 0;
-}
-
-/* s3c2410_dma_enqueue
- *
- * queue an given buffer for dma transfer.
- *
- * id the device driver's id information for this buffer
- * data the physical address of the buffer data
- * size the size of the buffer in bytes
- *
- * If the channel is not running, then the flag S3C2410_DMAF_AUTOSTART
- * is checked, and if set, the channel is started. If this flag isn't set,
- * then an error will be returned.
- *
- * It is possible to queue more than one DMA buffer onto a channel at
- * once, and the code will deal with the re-loading of the next buffer
- * when necessary.
-*/
-
-int s3c2410_dma_enqueue(unsigned int channel, void *id,
- dma_addr_t data, int size)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
- struct s3c2410_dma_buf *buf;
- unsigned long flags;
-
- if (chan == NULL)
- return -EINVAL;
-
- pr_debug("%s: id=%p, data=%08x, size=%d\n",
- __FUNCTION__, id, (unsigned int)data, size);
-
- buf = kmem_cache_alloc(dma_kmem, GFP_ATOMIC);
- if (buf == NULL) {
- pr_debug("%s: out of memory (%ld alloc)\n",
- __FUNCTION__, (long)sizeof(*buf));
- return -ENOMEM;
- }
-
- //pr_debug("%s: new buffer %p\n", __FUNCTION__, buf);
- //dbg_showchan(chan);
-
- buf->next = NULL;
- buf->data = buf->ptr = data;
- buf->size = size;
- buf->id = id;
- buf->magic = BUF_MAGIC;
-
- local_irq_save(flags);
-
- if (chan->curr == NULL) {
- /* we've got nothing loaded... */
- pr_debug("%s: buffer %p queued onto empty channel\n",
- __FUNCTION__, buf);
-
- chan->curr = buf;
- chan->end = buf;
- chan->next = NULL;
- } else {
- pr_debug("dma%d: %s: buffer %p queued onto non-empty channel\n",
- chan->number, __FUNCTION__, buf);
-
- if (chan->end == NULL)
- pr_debug("dma%d: %s: %p not empty, and chan->end==NULL?\n",
- chan->number, __FUNCTION__, chan);
-
- chan->end->next = buf;
- chan->end = buf;
- }
-
- /* if necessary, update the next buffer field */
- if (chan->next == NULL)
- chan->next = buf;
-
- /* check to see if we can load a buffer */
- if (chan->state == S3C2410_DMA_RUNNING) {
- if (chan->load_state == S3C2410_DMALOAD_1LOADED && 1) {
- if (s3c2410_dma_waitforload(chan, __LINE__) == 0) {
- printk(KERN_ERR "dma%d: loadbuffer:"
- "timeout loading buffer\n",
- chan->number);
- dbg_showchan(chan);
- local_irq_restore(flags);
- return -EINVAL;
- }
- }
-
- while (s3c2410_dma_canload(chan) && chan->next != NULL) {
- s3c2410_dma_loadbuffer(chan, chan->next);
- }
- } else if (chan->state == S3C2410_DMA_IDLE) {
- if (chan->flags & S3C2410_DMAF_AUTOSTART) {
- s3c2410_dma_ctrl(chan->number, S3C2410_DMAOP_START);
- }
- }
-
- local_irq_restore(flags);
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_enqueue);
-
-static inline void
-s3c2410_dma_freebuf(struct s3c2410_dma_buf *buf)
-{
- int magicok = (buf->magic == BUF_MAGIC);
-
- buf->magic = -1;
-
- if (magicok) {
- kmem_cache_free(dma_kmem, buf);
- } else {
- printk("s3c2410_dma_freebuf: buff %p with bad magic\n", buf);
- }
-}
-
-/* s3c2410_dma_lastxfer
- *
- * called when the system is out of buffers, to ensure that the channel
- * is prepared for shutdown.
-*/
-
-static inline void
-s3c2410_dma_lastxfer(struct s3c2410_dma_chan *chan)
-{
-#if 0
- pr_debug("dma%d: s3c2410_dma_lastxfer: load_state %d\n",
- chan->number, chan->load_state);
-#endif
-
- switch (chan->load_state) {
- case S3C2410_DMALOAD_NONE:
- break;
-
- case S3C2410_DMALOAD_1LOADED:
- if (s3c2410_dma_waitforload(chan, __LINE__) == 0) {
- /* flag error? */
- printk(KERN_ERR "dma%d: timeout waiting for load (%s)\n",
- chan->number, __FUNCTION__);
- return;
- }
- break;
-
- case S3C2410_DMALOAD_1LOADED_1RUNNING:
- /* I belive in this case we do not have anything to do
- * until the next buffer comes along, and we turn off the
- * reload */
- return;
-
- default:
- pr_debug("dma%d: lastxfer: unhandled load_state %d with no next\n",
- chan->number, chan->load_state);
- return;
-
- }
-
- /* hopefully this'll shut the damned thing up after the transfer... */
- dma_wrreg(chan, S3C2410_DMA_DCON, chan->dcon | S3C2410_DCON_NORELOAD);
-}
-
-
-#define dmadbg2(x...)
-
-static irqreturn_t
-s3c2410_dma_irq(int irq, void *devpw)
-{
- struct s3c2410_dma_chan *chan = (struct s3c2410_dma_chan *)devpw;
- struct s3c2410_dma_buf *buf;
-
- buf = chan->curr;
-
- dbg_showchan(chan);
-
- /* modify the channel state */
-
- switch (chan->load_state) {
- case S3C2410_DMALOAD_1RUNNING:
- /* TODO - if we are running only one buffer, we probably
- * want to reload here, and then worry about the buffer
- * callback */
-
- chan->load_state = S3C2410_DMALOAD_NONE;
- break;
-
- case S3C2410_DMALOAD_1LOADED:
- /* iirc, we should go back to NONE loaded here, we
- * had a buffer, and it was never verified as being
- * loaded.
- */
-
- chan->load_state = S3C2410_DMALOAD_NONE;
- break;
-
- case S3C2410_DMALOAD_1LOADED_1RUNNING:
- /* we'll worry about checking to see if another buffer is
- * ready after we've called back the owner. This should
- * ensure we do not wait around too long for the DMA
- * engine to start the next transfer
- */
-
- chan->load_state = S3C2410_DMALOAD_1LOADED;
- break;
-
- case S3C2410_DMALOAD_NONE:
- printk(KERN_ERR "dma%d: IRQ with no loaded buffer?\n",
- chan->number);
- break;
-
- default:
- printk(KERN_ERR "dma%d: IRQ in invalid load_state %d\n",
- chan->number, chan->load_state);
- break;
- }
-
- if (buf != NULL) {
- /* update the chain to make sure that if we load any more
- * buffers when we call the callback function, things should
- * work properly */
-
- chan->curr = buf->next;
- buf->next = NULL;
-
- if (buf->magic != BUF_MAGIC) {
- printk(KERN_ERR "dma%d: %s: buf %p incorrect magic\n",
- chan->number, __FUNCTION__, buf);
- return IRQ_HANDLED;
- }
-
- s3c2410_dma_buffdone(chan, buf, S3C2410_RES_OK);
-
- /* free resouces */
- s3c2410_dma_freebuf(buf);
- } else {
- }
-
- /* only reload if the channel is still running... our buffer done
- * routine may have altered the state by requesting the dma channel
- * to stop or shutdown... */
-
- /* todo: check that when the channel is shut-down from inside this
- * function, we cope with unsetting reload, etc */
-
- if (chan->next != NULL && chan->state != S3C2410_DMA_IDLE) {
- unsigned long flags;
-
- switch (chan->load_state) {
- case S3C2410_DMALOAD_1RUNNING:
- /* don't need to do anything for this state */
- break;
-
- case S3C2410_DMALOAD_NONE:
- /* can load buffer immediately */
- break;
-
- case S3C2410_DMALOAD_1LOADED:
- if (s3c2410_dma_waitforload(chan, __LINE__) == 0) {
- /* flag error? */
- printk(KERN_ERR "dma%d: timeout waiting for load (%s)\n",
- chan->number, __FUNCTION__);
- return IRQ_HANDLED;
- }
-
- break;
-
- case S3C2410_DMALOAD_1LOADED_1RUNNING:
- goto no_load;
-
- default:
- printk(KERN_ERR "dma%d: unknown load_state in irq, %d\n",
- chan->number, chan->load_state);
- return IRQ_HANDLED;
- }
-
- local_irq_save(flags);
- s3c2410_dma_loadbuffer(chan, chan->next);
- local_irq_restore(flags);
- } else {
- s3c2410_dma_lastxfer(chan);
-
- /* see if we can stop this channel.. */
- if (chan->load_state == S3C2410_DMALOAD_NONE) {
- pr_debug("dma%d: end of transfer, stopping channel (%ld)\n",
- chan->number, jiffies);
- s3c2410_dma_ctrl(chan->number | DMACH_LOW_LEVEL,
- S3C2410_DMAOP_STOP);
- }
- }
-
- no_load:
- return IRQ_HANDLED;
-}
-
-static struct s3c2410_dma_chan *s3c2410_dma_map_channel(int channel);
-
-/* s3c2410_request_dma
- *
- * get control of an dma channel
-*/
-
-int s3c2410_dma_request(unsigned int channel,
- struct s3c2410_dma_client *client,
- void *dev)
-{
- struct s3c2410_dma_chan *chan;
- unsigned long flags;
- int err;
-
- pr_debug("dma%d: s3c2410_request_dma: client=%s, dev=%p\n",
- channel, client->name, dev);
-
- local_irq_save(flags);
-
- chan = s3c2410_dma_map_channel(channel);
- if (chan == NULL) {
- local_irq_restore(flags);
- return -EBUSY;
- }
-
- dbg_showchan(chan);
-
- chan->client = client;
- chan->in_use = 1;
-
- if (!chan->irq_claimed) {
- pr_debug("dma%d: %s : requesting irq %d\n",
- channel, __FUNCTION__, chan->irq);
-
- chan->irq_claimed = 1;
- local_irq_restore(flags);
-
- err = request_irq(chan->irq, s3c2410_dma_irq, IRQF_DISABLED,
- client->name, (void *)chan);
-
- local_irq_save(flags);
-
- if (err) {
- chan->in_use = 0;
- chan->irq_claimed = 0;
- local_irq_restore(flags);
-
- printk(KERN_ERR "%s: cannot get IRQ %d for DMA %d\n",
- client->name, chan->irq, chan->number);
- return err;
- }
-
- chan->irq_enabled = 1;
- }
-
- local_irq_restore(flags);
-
- /* need to setup */
-
- pr_debug("%s: channel initialised, %p\n", __FUNCTION__, chan);
-
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_request);
-
-/* s3c2410_dma_free
- *
- * release the given channel back to the system, will stop and flush
- * any outstanding transfers, and ensure the channel is ready for the
- * next claimant.
- *
- * Note, although a warning is currently printed if the freeing client
- * info is not the same as the registrant's client info, the free is still
- * allowed to go through.
-*/
-
-int s3c2410_dma_free(dmach_t channel, struct s3c2410_dma_client *client)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
- unsigned long flags;
-
- if (chan == NULL)
- return -EINVAL;
-
- local_irq_save(flags);
-
- if (chan->client != client) {
- printk(KERN_WARNING "dma%d: possible free from different client (channel %p, passed %p)\n",
- channel, chan->client, client);
- }
-
- /* sort out stopping and freeing the channel */
-
- if (chan->state != S3C2410_DMA_IDLE) {
- pr_debug("%s: need to stop dma channel %p\n",
- __FUNCTION__, chan);
-
- /* possibly flush the channel */
- s3c2410_dma_ctrl(channel, S3C2410_DMAOP_STOP);
- }
-
- chan->client = NULL;
- chan->in_use = 0;
-
- if (chan->irq_claimed)
- free_irq(chan->irq, (void *)chan);
-
- chan->irq_claimed = 0;
-
- if (!(channel & DMACH_LOW_LEVEL))
- dma_chan_map[channel] = NULL;
-
- local_irq_restore(flags);
-
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_free);
-
-static int s3c2410_dma_dostop(struct s3c2410_dma_chan *chan)
-{
- unsigned long flags;
- unsigned long tmp;
-
- pr_debug("%s:\n", __FUNCTION__);
-
- dbg_showchan(chan);
-
- local_irq_save(flags);
-
- s3c2410_dma_call_op(chan, S3C2410_DMAOP_STOP);
-
- tmp = dma_rdreg(chan, S3C2410_DMA_DMASKTRIG);
- tmp |= S3C2410_DMASKTRIG_STOP;
- //tmp &= ~S3C2410_DMASKTRIG_ON;
- dma_wrreg(chan, S3C2410_DMA_DMASKTRIG, tmp);
-
-#if 0
- /* should also clear interrupts, according to WinCE BSP */
- tmp = dma_rdreg(chan, S3C2410_DMA_DCON);
- tmp |= S3C2410_DCON_NORELOAD;
- dma_wrreg(chan, S3C2410_DMA_DCON, tmp);
-#endif
-
- /* should stop do this, or should we wait for flush? */
- chan->state = S3C2410_DMA_IDLE;
- chan->load_state = S3C2410_DMALOAD_NONE;
-
- local_irq_restore(flags);
-
- return 0;
-}
-
-void s3c2410_dma_waitforstop(struct s3c2410_dma_chan *chan)
-{
- unsigned long tmp;
- unsigned int timeout = 0x10000;
-
- while (timeout-- > 0) {
- tmp = dma_rdreg(chan, S3C2410_DMA_DMASKTRIG);
-
- if (!(tmp & S3C2410_DMASKTRIG_ON))
- return;
- }
-
- pr_debug("dma%d: failed to stop?\n", chan->number);
-}
-
-
-/* s3c2410_dma_flush
- *
- * stop the channel, and remove all current and pending transfers
-*/
-
-static int s3c2410_dma_flush(struct s3c2410_dma_chan *chan)
-{
- struct s3c2410_dma_buf *buf, *next;
- unsigned long flags;
-
- pr_debug("%s: chan %p (%d)\n", __FUNCTION__, chan, chan->number);
-
- dbg_showchan(chan);
-
- local_irq_save(flags);
-
- if (chan->state != S3C2410_DMA_IDLE) {
- pr_debug("%s: stopping channel...\n", __FUNCTION__ );
- s3c2410_dma_ctrl(chan->number, S3C2410_DMAOP_STOP);
- }
-
- buf = chan->curr;
- if (buf == NULL)
- buf = chan->next;
-
- chan->curr = chan->next = chan->end = NULL;
-
- if (buf != NULL) {
- for ( ; buf != NULL; buf = next) {
- next = buf->next;
-
- pr_debug("%s: free buffer %p, next %p\n",
- __FUNCTION__, buf, buf->next);
-
- s3c2410_dma_buffdone(chan, buf, S3C2410_RES_ABORT);
- s3c2410_dma_freebuf(buf);
- }
- }
-
- dbg_showregs(chan);
-
- s3c2410_dma_waitforstop(chan);
-
-#if 0
- /* should also clear interrupts, according to WinCE BSP */
- {
- unsigned long tmp;
-
- tmp = dma_rdreg(chan, S3C2410_DMA_DCON);
- tmp |= S3C2410_DCON_NORELOAD;
- dma_wrreg(chan, S3C2410_DMA_DCON, tmp);
- }
-#endif
-
- dbg_showregs(chan);
-
- local_irq_restore(flags);
-
- return 0;
-}
-
-int
-s3c2410_dma_started(struct s3c2410_dma_chan *chan)
-{
- unsigned long flags;
-
- local_irq_save(flags);
-
- dbg_showchan(chan);
-
- /* if we've only loaded one buffer onto the channel, then chec
- * to see if we have another, and if so, try and load it so when
- * the first buffer is finished, the new one will be loaded onto
- * the channel */
-
- if (chan->next != NULL) {
- if (chan->load_state == S3C2410_DMALOAD_1LOADED) {
-
- if (s3c2410_dma_waitforload(chan, __LINE__) == 0) {
- pr_debug("%s: buff not yet loaded, no more todo\n",
- __FUNCTION__);
- } else {
- chan->load_state = S3C2410_DMALOAD_1RUNNING;
- s3c2410_dma_loadbuffer(chan, chan->next);
- }
-
- } else if (chan->load_state == S3C2410_DMALOAD_1RUNNING) {
- s3c2410_dma_loadbuffer(chan, chan->next);
- }
- }
-
-
- local_irq_restore(flags);
-
- return 0;
-
-}
-
-int
-s3c2410_dma_ctrl(dmach_t channel, enum s3c2410_chan_op op)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
-
- if (chan == NULL)
- return -EINVAL;
-
- switch (op) {
- case S3C2410_DMAOP_START:
- return s3c2410_dma_start(chan);
-
- case S3C2410_DMAOP_STOP:
- return s3c2410_dma_dostop(chan);
-
- case S3C2410_DMAOP_PAUSE:
- case S3C2410_DMAOP_RESUME:
- return -ENOENT;
-
- case S3C2410_DMAOP_FLUSH:
- return s3c2410_dma_flush(chan);
-
- case S3C2410_DMAOP_STARTED:
- return s3c2410_dma_started(chan);
-
- case S3C2410_DMAOP_TIMEOUT:
- return 0;
-
- }
-
- return -ENOENT; /* unknown, don't bother */
-}
-
-EXPORT_SYMBOL(s3c2410_dma_ctrl);
-
-/* DMA configuration for each channel
- *
- * DISRCC -> source of the DMA (AHB,APB)
- * DISRC -> source address of the DMA
- * DIDSTC -> destination of the DMA (AHB,APD)
- * DIDST -> destination address of the DMA
-*/
-
-/* s3c2410_dma_config
- *
- * xfersize: size of unit in bytes (1,2,4)
- * dcon: base value of the DCONx register
-*/
-
-int s3c2410_dma_config(dmach_t channel,
- int xferunit,
- int dcon)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
-
- pr_debug("%s: chan=%d, xfer_unit=%d, dcon=%08x\n",
- __FUNCTION__, channel, xferunit, dcon);
-
- if (chan == NULL)
- return -EINVAL;
-
- pr_debug("%s: Initial dcon is %08x\n", __FUNCTION__, dcon);
-
- dcon |= chan->dcon & dma_sel.dcon_mask;
-
- pr_debug("%s: New dcon is %08x\n", __FUNCTION__, dcon);
-
- switch (xferunit) {
- case 1:
- dcon |= S3C2410_DCON_BYTE;
- break;
-
- case 2:
- dcon |= S3C2410_DCON_HALFWORD;
- break;
-
- case 4:
- dcon |= S3C2410_DCON_WORD;
- break;
-
- default:
- pr_debug("%s: bad transfer size %d\n", __FUNCTION__, xferunit);
- return -EINVAL;
- }
-
- dcon |= S3C2410_DCON_HWTRIG;
- dcon |= S3C2410_DCON_INTREQ;
-
- pr_debug("%s: dcon now %08x\n", __FUNCTION__, dcon);
-
- chan->dcon = dcon;
- chan->xfer_unit = xferunit;
-
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_config);
-
-int s3c2410_dma_setflags(dmach_t channel, unsigned int flags)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
-
- if (chan == NULL)
- return -EINVAL;
-
- pr_debug("%s: chan=%p, flags=%08x\n", __FUNCTION__, chan, flags);
-
- chan->flags = flags;
-
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_setflags);
-
-
-/* do we need to protect the settings of the fields from
- * irq?
-*/
-
-int s3c2410_dma_set_opfn(dmach_t channel, s3c2410_dma_opfn_t rtn)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
-
- if (chan == NULL)
- return -EINVAL;
-
- pr_debug("%s: chan=%p, op rtn=%p\n", __FUNCTION__, chan, rtn);
-
- chan->op_fn = rtn;
-
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_set_opfn);
-
-int s3c2410_dma_set_buffdone_fn(dmach_t channel, s3c2410_dma_cbfn_t rtn)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
-
- if (chan == NULL)
- return -EINVAL;
-
- pr_debug("%s: chan=%p, callback rtn=%p\n", __FUNCTION__, chan, rtn);
-
- chan->callback_fn = rtn;
-
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_set_buffdone_fn);
-
-/* s3c2410_dma_devconfig
- *
- * configure the dma source/destination hardware type and address
- *
- * source: S3C2410_DMASRC_HW: source is hardware
- * S3C2410_DMASRC_MEM: source is memory
- *
- * hwcfg: the value for xxxSTCn register,
- * bit 0: 0=increment pointer, 1=leave pointer
- * bit 1: 0=soucre is AHB, 1=soucre is APB
- *
- * devaddr: physical address of the source
-*/
-
-int s3c2410_dma_devconfig(int channel,
- enum s3c2410_dmasrc source,
- int hwcfg,
- unsigned long devaddr)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
-
- if (chan == NULL)
- return -EINVAL;
-
- pr_debug("%s: source=%d, hwcfg=%08x, devaddr=%08lx\n",
- __FUNCTION__, (int)source, hwcfg, devaddr);
-
- chan->source = source;
- chan->dev_addr = devaddr;
-
- switch (source) {
- case S3C2410_DMASRC_HW:
- /* source is hardware */
- pr_debug("%s: hw source, devaddr=%08lx, hwcfg=%d\n",
- __FUNCTION__, devaddr, hwcfg);
- dma_wrreg(chan, S3C2410_DMA_DISRCC, hwcfg & 3);
- dma_wrreg(chan, S3C2410_DMA_DISRC, devaddr);
- dma_wrreg(chan, S3C2410_DMA_DIDSTC, (0<<1) | (0<<0));
-
- chan->addr_reg = dma_regaddr(chan, S3C2410_DMA_DIDST);
- return 0;
-
- case S3C2410_DMASRC_MEM:
- /* source is memory */
- pr_debug( "%s: mem source, devaddr=%08lx, hwcfg=%d\n",
- __FUNCTION__, devaddr, hwcfg);
- dma_wrreg(chan, S3C2410_DMA_DISRCC, (0<<1) | (0<<0));
- dma_wrreg(chan, S3C2410_DMA_DIDST, devaddr);
- dma_wrreg(chan, S3C2410_DMA_DIDSTC, hwcfg & 3);
-
- chan->addr_reg = dma_regaddr(chan, S3C2410_DMA_DISRC);
- return 0;
- }
-
- printk(KERN_ERR "dma%d: invalid source type (%d)\n", channel, source);
- return -EINVAL;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_devconfig);
-
-/* s3c2410_dma_getposition
- *
- * returns the current transfer points for the dma source and destination
-*/
-
-int s3c2410_dma_getposition(dmach_t channel, dma_addr_t *src, dma_addr_t *dst)
-{
- struct s3c2410_dma_chan *chan = lookup_dma_channel(channel);
-
- if (chan == NULL)
- return -EINVAL;
-
- if (src != NULL)
- *src = dma_rdreg(chan, S3C2410_DMA_DCSRC);
-
- if (dst != NULL)
- *dst = dma_rdreg(chan, S3C2410_DMA_DCDST);
-
- return 0;
-}
-
-EXPORT_SYMBOL(s3c2410_dma_getposition);
-
-
-/* system device class */
-
-#ifdef CONFIG_PM
-
-static int s3c2410_dma_suspend(struct sys_device *dev, pm_message_t state)
-{
- struct s3c2410_dma_chan *cp = container_of(dev, struct s3c2410_dma_chan, dev);
-
- printk(KERN_DEBUG "suspending dma channel %d\n", cp->number);
-
- if (dma_rdreg(cp, S3C2410_DMA_DMASKTRIG) & S3C2410_DMASKTRIG_ON) {
- /* the dma channel is still working, which is probably
- * a bad thing to do over suspend/resume. We stop the
- * channel and assume that the client is either going to
- * retry after resume, or that it is broken.
- */
-
- printk(KERN_INFO "dma: stopping channel %d due to suspend\n",
- cp->number);
-
- s3c2410_dma_dostop(cp);
- }
-
- return 0;
-}
-
-static int s3c2410_dma_resume(struct sys_device *dev)
-{
- return 0;
-}
-
-#else
-#define s3c2410_dma_suspend NULL
-#define s3c2410_dma_resume NULL
-#endif /* CONFIG_PM */
-
-struct sysdev_class dma_sysclass = {
- set_kset_name("s3c24xx-dma"),
- .suspend = s3c2410_dma_suspend,
- .resume = s3c2410_dma_resume,
+static struct s3c24xx_dma_selection __initdata s3c2410_dma_sel = {
+ .select = s3c2410_dma_select,
+ .dcon_mask = 7 << 24,
+ .map = s3c2410_dma_mappings,
+ .map_size = ARRAY_SIZE(s3c2410_dma_mappings),
};
-/* kmem cache implementation */
+static struct s3c24xx_dma_order __initdata s3c2410_dma_order = {
+ .channels = {
+ [DMACH_SDI] = {
+ .list = {
+ [0] = 3 | DMA_CH_VALID,
+ [1] = 2 | DMA_CH_VALID,
+ [2] = 0 | DMA_CH_VALID,
+ },
+ },
+ [DMACH_I2S_IN] = {
+ .list = {
+ [0] = 1 | DMA_CH_VALID,
+ [1] = 2 | DMA_CH_VALID,
+ },
+ },
+ },
+};
-static void s3c2410_dma_cache_ctor(void *p, struct kmem_cache *c, unsigned long f)
+static int s3c2410_dma_add(struct sys_device *sysdev)
{
- memset(p, 0, sizeof(struct s3c2410_dma_buf));
+ s3c2410_dma_init();
+ s3c24xx_dma_order_set(&s3c2410_dma_order);
+ return s3c24xx_dma_init_map(&s3c2410_dma_sel);
}
-/* initialisation code */
+#if defined(CONFIG_CPU_S3C2410)
+static struct sysdev_driver s3c2410_dma_driver = {
+ .add = s3c2410_dma_add,
+};
-static int __init s3c2410_init_dma(void)
+static int __init s3c2410_dma_drvinit(void)
{
- struct s3c2410_dma_chan *cp;
- int channel;
- int ret;
-
- printk("S3C24XX DMA Driver, (c) 2003-2004,2006 Simtec Electronics\n");
-
- dma_base = ioremap(S3C24XX_PA_DMA, 0x200);
- if (dma_base == NULL) {
- printk(KERN_ERR "dma failed to remap register block\n");
- return -ENOMEM;
- }
-
- printk("Registering sysclass\n");
-
- ret = sysdev_class_register(&dma_sysclass);
- if (ret != 0) {
- printk(KERN_ERR "dma sysclass registration failed\n");
- goto err;
- }
-
- dma_kmem = kmem_cache_create("dma_desc", sizeof(struct s3c2410_dma_buf), 0,
- SLAB_HWCACHE_ALIGN,
- s3c2410_dma_cache_ctor, NULL);
-
- if (dma_kmem == NULL) {
- printk(KERN_ERR "dma failed to make kmem cache\n");
- ret = -ENOMEM;
- goto err;
- }
-
- for (channel = 0; channel < S3C2410_DMA_CHANNELS; channel++) {
- cp = &s3c2410_chans[channel];
-
- memset(cp, 0, sizeof(struct s3c2410_dma_chan));
-
- /* dma channel irqs are in order.. */
- cp->number = channel;
- cp->irq = channel + IRQ_DMA0;
- cp->regs = dma_base + (channel*0x40);
-
- /* point current stats somewhere */
- cp->stats = &cp->stats_store;
- cp->stats_store.timeout_shortest = LONG_MAX;
-
- /* basic channel configuration */
-
- cp->load_timeout = 1<<18;
-
- /* register system device */
-
- cp->dev.cls = &dma_sysclass;
- cp->dev.id = channel;
- ret = sysdev_register(&cp->dev);
-
- printk("DMA channel %d at %p, irq %d\n",
- cp->number, cp->regs, cp->irq);
- }
-
- return 0;
-
- err:
- kmem_cache_destroy(dma_kmem);
- iounmap(dma_base);
- dma_base = NULL;
- return ret;
+ return sysdev_driver_register(&s3c2410_sysclass, &s3c2410_dma_driver);
}
-core_initcall(s3c2410_init_dma);
+arch_initcall(s3c2410_dma_drvinit);
+#endif
-static inline int is_channel_valid(unsigned int channel)
+#if defined(CONFIG_CPU_S3C2442)
+/* S3C2442 DMA contains the same selection table as the S3C2410 */
+static struct sysdev_driver s3c2442_dma_driver = {
+ .add = s3c2410_dma_add,
+};
+
+static int __init s3c2442_dma_drvinit(void)
{
- return (channel & DMA_CH_VALID);
+ return sysdev_driver_register(&s3c2442_sysclass, &s3c2442_dma_driver);
}
-/* s3c2410_dma_map_channel()
- *
- * turn the virtual channel number into a real, and un-used hardware
- * channel.
- *
- * currently this code uses first-free channel from the specified harware
- * map, not taking into account anything that the board setup code may
- * have to say about the likely peripheral set to be in use.
-*/
+arch_initcall(s3c2442_dma_drvinit);
+#endif
-struct s3c2410_dma_chan *s3c2410_dma_map_channel(int channel)
-{
- struct s3c24xx_dma_map *ch_map;
- struct s3c2410_dma_chan *dmach;
- int ch;
-
- if (dma_sel.map == NULL || channel > dma_sel.map_size)
- return NULL;
-
- ch_map = dma_sel.map + channel;
-
- for (ch = 0; ch < S3C2410_DMA_CHANNELS; ch++) {
- if (!is_channel_valid(ch_map->channels[ch]))
- continue;
-
- if (s3c2410_chans[ch].in_use == 0) {
- printk("mapped channel %d to %d\n", channel, ch);
- break;
- }
- }
-
- if (ch >= S3C2410_DMA_CHANNELS)
- return NULL;
-
- /* update our channel mapping */
-
- dmach = &s3c2410_chans[ch];
- dma_chan_map[channel] = dmach;
-
- /* select the channel */
-
- (dma_sel.select)(dmach, ch_map);
-
- return dmach;
-}
-
-static void s3c24xx_dma_show_ch(struct s3c24xx_dma_map *map, int ch)
-{
- /* show the channel configuration */
-
- printk("%2d: %20s, channels %c%c%c%c\n", ch, map->name,
- (is_channel_valid(map->channels[0]) ? '0' : '-'),
- (is_channel_valid(map->channels[1]) ? '1' : '-'),
- (is_channel_valid(map->channels[2]) ? '2' : '-'),
- (is_channel_valid(map->channels[3]) ? '3' : '-'));
-}
-
-static int s3c24xx_dma_check_entry(struct s3c24xx_dma_map *map, int ch)
-{
- if (1)
- s3c24xx_dma_show_ch(map, ch);
-
- return 0;
-}
-
-int __init s3c24xx_dma_init_map(struct s3c24xx_dma_selection *sel)
-{
- struct s3c24xx_dma_map *nmap;
- size_t map_sz = sizeof(*nmap) * sel->map_size;
- int ptr;
-
- nmap = kmalloc(map_sz, GFP_KERNEL);
- if (nmap == NULL)
- return -ENOMEM;
-
- memcpy(nmap, sel->map, map_sz);
- memcpy(&dma_sel, sel, sizeof(*sel));
-
- dma_sel.map = nmap;
-
- for (ptr = 0; ptr < sel->map_size; ptr++)
- s3c24xx_dma_check_entry(nmap+ptr, ptr);
-
- return 0;
-}
diff --git a/arch/arm/mach-s3c2410/gpio.c b/arch/arm/mach-s3c2410/gpio.c
index f6fb215bb48c..01e795d1146e 100644
--- a/arch/arm/mach-s3c2410/gpio.c
+++ b/arch/arm/mach-s3c2410/gpio.c
@@ -1,9 +1,9 @@
/* linux/arch/arm/mach-s3c2410/gpio.c
*
- * Copyright (c) 2004-2005 Simtec Electronics
+ * Copyright (c) 2004-2006 Simtec Electronics
* Ben Dooks
*
- * S3C24XX GPIO support
+ * S3C2410 GPIO support
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -18,8 +18,7 @@
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
-*/
-
+ */
#include
#include
@@ -33,156 +32,40 @@
#include
-void s3c2410_gpio_cfgpin(unsigned int pin, unsigned int function)
+int s3c2410_gpio_irqfilter(unsigned int pin, unsigned int on,
+ unsigned int config)
{
- void __iomem *base = S3C24XX_GPIO_BASE(pin);
- unsigned long mask;
- unsigned long con;
+ void __iomem *reg = S3C24XX_EINFLT0;
unsigned long flags;
+ unsigned long val;
- if (pin < S3C2410_GPIO_BANKB) {
- mask = 1 << S3C2410_GPIO_OFFSET(pin);
- } else {
- mask = 3 << S3C2410_GPIO_OFFSET(pin)*2;
- }
+ if (pin < S3C2410_GPG8 || pin > S3C2410_GPG15)
+ return -1;
- switch (function) {
- case S3C2410_GPIO_LEAVE:
- mask = 0;
- function = 0;
- break;
+ config &= 0xff;
- case S3C2410_GPIO_INPUT:
- case S3C2410_GPIO_OUTPUT:
- case S3C2410_GPIO_SFN2:
- case S3C2410_GPIO_SFN3:
- if (pin < S3C2410_GPIO_BANKB) {
- function -= 1;
- function &= 1;
- function <<= S3C2410_GPIO_OFFSET(pin);
- } else {
- function &= 3;
- function <<= S3C2410_GPIO_OFFSET(pin)*2;
- }
- }
-
- /* modify the specified register wwith IRQs off */
+ pin -= S3C2410_GPG8;
+ reg += pin & ~3;
local_irq_save(flags);
- con = __raw_readl(base + 0x00);
- con &= ~mask;
- con |= function;
+ /* update filter width and clock source */
- __raw_writel(con, base + 0x00);
+ val = __raw_readl(reg);
+ val &= ~(0xff << ((pin & 3) * 8));
+ val |= config << ((pin & 3) * 8);
+ __raw_writel(val, reg);
+
+ /* update filter enable */
+
+ val = __raw_readl(S3C24XX_EXTINT2);
+ val &= ~(1 << ((pin * 4) + 3));
+ val |= on << ((pin * 4) + 3);
+ __raw_writel(val, S3C24XX_EXTINT2);
local_irq_restore(flags);
+
+ return 0;
}
-EXPORT_SYMBOL(s3c2410_gpio_cfgpin);
-
-unsigned int s3c2410_gpio_getcfg(unsigned int pin)
-{
- void __iomem *base = S3C24XX_GPIO_BASE(pin);
- unsigned long val = __raw_readl(base);
-
- if (pin < S3C2410_GPIO_BANKB) {
- val >>= S3C2410_GPIO_OFFSET(pin);
- val &= 1;
- val += 1;
- } else {
- val >>= S3C2410_GPIO_OFFSET(pin)*2;
- val &= 3;
- }
-
- return val | S3C2410_GPIO_INPUT;
-}
-
-EXPORT_SYMBOL(s3c2410_gpio_getcfg);
-
-void s3c2410_gpio_pullup(unsigned int pin, unsigned int to)
-{
- void __iomem *base = S3C24XX_GPIO_BASE(pin);
- unsigned long offs = S3C2410_GPIO_OFFSET(pin);
- unsigned long flags;
- unsigned long up;
-
- if (pin < S3C2410_GPIO_BANKB)
- return;
-
- local_irq_save(flags);
-
- up = __raw_readl(base + 0x08);
- up &= ~(1L << offs);
- up |= to << offs;
- __raw_writel(up, base + 0x08);
-
- local_irq_restore(flags);
-}
-
-EXPORT_SYMBOL(s3c2410_gpio_pullup);
-
-void s3c2410_gpio_setpin(unsigned int pin, unsigned int to)
-{
- void __iomem *base = S3C24XX_GPIO_BASE(pin);
- unsigned long offs = S3C2410_GPIO_OFFSET(pin);
- unsigned long flags;
- unsigned long dat;
-
- local_irq_save(flags);
-
- dat = __raw_readl(base + 0x04);
- dat &= ~(1 << offs);
- dat |= to << offs;
- __raw_writel(dat, base + 0x04);
-
- local_irq_restore(flags);
-}
-
-EXPORT_SYMBOL(s3c2410_gpio_setpin);
-
-unsigned int s3c2410_gpio_getpin(unsigned int pin)
-{
- void __iomem *base = S3C24XX_GPIO_BASE(pin);
- unsigned long offs = S3C2410_GPIO_OFFSET(pin);
-
- return __raw_readl(base + 0x04) & (1<< offs);
-}
-
-EXPORT_SYMBOL(s3c2410_gpio_getpin);
-
-unsigned int s3c2410_modify_misccr(unsigned int clear, unsigned int change)
-{
- unsigned long flags;
- unsigned long misccr;
-
- local_irq_save(flags);
- misccr = __raw_readl(S3C24XX_MISCCR);
- misccr &= ~clear;
- misccr ^= change;
- __raw_writel(misccr, S3C24XX_MISCCR);
- local_irq_restore(flags);
-
- return misccr;
-}
-
-EXPORT_SYMBOL(s3c2410_modify_misccr);
-
-int s3c2410_gpio_getirq(unsigned int pin)
-{
- if (pin < S3C2410_GPF0 || pin > S3C2410_GPG15)
- return -1; /* not valid interrupts */
-
- if (pin < S3C2410_GPG0 && pin > S3C2410_GPF7)
- return -1; /* not valid pin */
-
- if (pin < S3C2410_GPF4)
- return (pin - S3C2410_GPF0) + IRQ_EINT0;
-
- if (pin < S3C2410_GPG0)
- return (pin - S3C2410_GPF4) + IRQ_EINT4;
-
- return (pin - S3C2410_GPG0) + IRQ_EINT8;
-}
-
-EXPORT_SYMBOL(s3c2410_gpio_getirq);
+EXPORT_SYMBOL(s3c2410_gpio_irqfilter);
diff --git a/arch/arm/mach-s3c2410/irq.c b/arch/arm/mach-s3c2410/irq.c
index 3c0ed7871c55..53cbdaa43ac6 100644
--- a/arch/arm/mach-s3c2410/irq.c
+++ b/arch/arm/mach-s3c2410/irq.c
@@ -1,6 +1,6 @@
/* linux/arch/arm/mach-s3c2410/irq.c
*
- * Copyright (c) 2003,2004 Simtec Electronics
+ * Copyright (c) 2006 Simtec Electronics
* Ben Dooks
*
* This program is free software; you can redistribute it and/or modify
@@ -17,37 +17,6 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
*
- * Changelog:
- *
- * 22-Jul-2004 Ben Dooks
- * Fixed compile warnings
- *
- * 22-Jul-2004 Roc Wu
- * Fixed s3c_extirq_type
- *
- * 21-Jul-2004 Arnaud Patard (Rtp)
- * Addition of ADC/TC demux
- *
- * 04-Oct-2004 Klaus Fetscher
- * Fix for set_irq_type() on low EINT numbers
- *
- * 05-Oct-2004 Ben Dooks
- * Tidy up KF's patch and sort out new release
- *
- * 05-Oct-2004 Ben Dooks
- * Add support for power management controls
- *
- * 04-Nov-2004 Ben Dooks
- * Fix standard IRQ wake for EINT0..4 and RTC
- *
- * 22-Feb-2005 Ben Dooks
- * Fixed edge-triggering on ADC IRQ
- *
- * 28-Jun-2005 Ben Dooks
- * Mark IRQ_LCD valid
- *
- * 25-Jul-2005 Ben Dooks
- * Split the S3C2440 IRQ code to seperate file
*/
#include
@@ -57,745 +26,23 @@
#include
#include
-#include
-#include
-#include
+#include
+#include
-#include
-
-#include
-#include
-
-#include "cpu.h"
-#include "pm.h"
-#include "irq.h"
-
-/* wakeup irq control */
-
-#ifdef CONFIG_PM
-
-/* state for IRQs over sleep */
-
-/* default is to allow for EINT0..EINT15, and IRQ_RTC as wakeup sources
- *
- * set bit to 1 in allow bitfield to enable the wakeup settings on it
-*/
-
-unsigned long s3c_irqwake_intallow = 1L << (IRQ_RTC - IRQ_EINT0) | 0xfL;
-unsigned long s3c_irqwake_intmask = 0xffffffffL;
-unsigned long s3c_irqwake_eintallow = 0x0000fff0L;
-unsigned long s3c_irqwake_eintmask = 0xffffffffL;
-
-int
-s3c_irq_wake(unsigned int irqno, unsigned int state)
+static int s3c2410_irq_add(struct sys_device *sysdev)
{
- unsigned long irqbit = 1 << (irqno - IRQ_EINT0);
-
- if (!(s3c_irqwake_intallow & irqbit))
- return -ENOENT;
-
- printk(KERN_INFO "wake %s for irq %d\n",
- state ? "enabled" : "disabled", irqno);
-
- if (!state)
- s3c_irqwake_intmask |= irqbit;
- else
- s3c_irqwake_intmask &= ~irqbit;
-
return 0;
}
-static int
-s3c_irqext_wake(unsigned int irqno, unsigned int state)
-{
- unsigned long bit = 1L << (irqno - EXTINT_OFF);
-
- if (!(s3c_irqwake_eintallow & bit))
- return -ENOENT;
-
- printk(KERN_INFO "wake %s for irq %d\n",
- state ? "enabled" : "disabled", irqno);
-
- if (!state)
- s3c_irqwake_eintmask |= bit;
- else
- s3c_irqwake_eintmask &= ~bit;
-
- return 0;
-}
-
-#else
-#define s3c_irqext_wake NULL
-#define s3c_irq_wake NULL
-#endif
-
-
-static void
-s3c_irq_mask(unsigned int irqno)
-{
- unsigned long mask;
-
- irqno -= IRQ_EINT0;
-
- mask = __raw_readl(S3C2410_INTMSK);
- mask |= 1UL << irqno;
- __raw_writel(mask, S3C2410_INTMSK);
-}
-
-static inline void
-s3c_irq_ack(unsigned int irqno)
-{
- unsigned long bitval = 1UL << (irqno - IRQ_EINT0);
-
- __raw_writel(bitval, S3C2410_SRCPND);
- __raw_writel(bitval, S3C2410_INTPND);
-}
-
-static inline void
-s3c_irq_maskack(unsigned int irqno)
-{
- unsigned long bitval = 1UL << (irqno - IRQ_EINT0);
- unsigned long mask;
-
- mask = __raw_readl(S3C2410_INTMSK);
- __raw_writel(mask|bitval, S3C2410_INTMSK);
-
- __raw_writel(bitval, S3C2410_SRCPND);
- __raw_writel(bitval, S3C2410_INTPND);
-}
-
-
-static void
-s3c_irq_unmask(unsigned int irqno)
-{
- unsigned long mask;
-
- if (irqno != IRQ_TIMER4 && irqno != IRQ_EINT8t23)
- irqdbf2("s3c_irq_unmask %d\n", irqno);
-
- irqno -= IRQ_EINT0;
-
- mask = __raw_readl(S3C2410_INTMSK);
- mask &= ~(1UL << irqno);
- __raw_writel(mask, S3C2410_INTMSK);
-}
-
-struct irq_chip s3c_irq_level_chip = {
- .name = "s3c-level",
- .ack = s3c_irq_maskack,
- .mask = s3c_irq_mask,
- .unmask = s3c_irq_unmask,
- .set_wake = s3c_irq_wake
+static struct sysdev_driver s3c2410_irq_driver = {
+ .add = s3c2410_irq_add,
+ .suspend = s3c24xx_irq_suspend,
+ .resume = s3c24xx_irq_resume,
};
-static struct irq_chip s3c_irq_chip = {
- .name = "s3c",
- .ack = s3c_irq_ack,
- .mask = s3c_irq_mask,
- .unmask = s3c_irq_unmask,
- .set_wake = s3c_irq_wake
-};
-
-static void
-s3c_irqext_mask(unsigned int irqno)
+static int s3c2410_irq_init(void)
{
- unsigned long mask;
-
- irqno -= EXTINT_OFF;
-
- mask = __raw_readl(S3C24XX_EINTMASK);
- mask |= ( 1UL << irqno);
- __raw_writel(mask, S3C24XX_EINTMASK);
+ return sysdev_driver_register(&s3c2410_sysclass, &s3c2410_irq_driver);
}
-static void
-s3c_irqext_ack(unsigned int irqno)
-{
- unsigned long req;
- unsigned long bit;
- unsigned long mask;
-
- bit = 1UL << (irqno - EXTINT_OFF);
-
- mask = __raw_readl(S3C24XX_EINTMASK);
-
- __raw_writel(bit, S3C24XX_EINTPEND);
-
- req = __raw_readl(S3C24XX_EINTPEND);
- req &= ~mask;
-
- /* not sure if we should be acking the parent irq... */
-
- if (irqno <= IRQ_EINT7 ) {
- if ((req & 0xf0) == 0)
- s3c_irq_ack(IRQ_EINT4t7);
- } else {
- if ((req >> 8) == 0)
- s3c_irq_ack(IRQ_EINT8t23);
- }
-}
-
-static void
-s3c_irqext_unmask(unsigned int irqno)
-{
- unsigned long mask;
-
- irqno -= EXTINT_OFF;
-
- mask = __raw_readl(S3C24XX_EINTMASK);
- mask &= ~( 1UL << irqno);
- __raw_writel(mask, S3C24XX_EINTMASK);
-}
-
-int
-s3c_irqext_type(unsigned int irq, unsigned int type)
-{
- void __iomem *extint_reg;
- void __iomem *gpcon_reg;
- unsigned long gpcon_offset, extint_offset;
- unsigned long newvalue = 0, value;
-
- if ((irq >= IRQ_EINT0) && (irq <= IRQ_EINT3))
- {
- gpcon_reg = S3C2410_GPFCON;
- extint_reg = S3C24XX_EXTINT0;
- gpcon_offset = (irq - IRQ_EINT0) * 2;
- extint_offset = (irq - IRQ_EINT0) * 4;
- }
- else if ((irq >= IRQ_EINT4) && (irq <= IRQ_EINT7))
- {
- gpcon_reg = S3C2410_GPFCON;
- extint_reg = S3C24XX_EXTINT0;
- gpcon_offset = (irq - (EXTINT_OFF)) * 2;
- extint_offset = (irq - (EXTINT_OFF)) * 4;
- }
- else if ((irq >= IRQ_EINT8) && (irq <= IRQ_EINT15))
- {
- gpcon_reg = S3C2410_GPGCON;
- extint_reg = S3C24XX_EXTINT1;
- gpcon_offset = (irq - IRQ_EINT8) * 2;
- extint_offset = (irq - IRQ_EINT8) * 4;
- }
- else if ((irq >= IRQ_EINT16) && (irq <= IRQ_EINT23))
- {
- gpcon_reg = S3C2410_GPGCON;
- extint_reg = S3C24XX_EXTINT2;
- gpcon_offset = (irq - IRQ_EINT8) * 2;
- extint_offset = (irq - IRQ_EINT16) * 4;
- } else
- return -1;
-
- /* Set the GPIO to external interrupt mode */
- value = __raw_readl(gpcon_reg);
- value = (value & ~(3 << gpcon_offset)) | (0x02 << gpcon_offset);
- __raw_writel(value, gpcon_reg);
-
- /* Set the external interrupt to pointed trigger type */
- switch (type)
- {
- case IRQT_NOEDGE:
- printk(KERN_WARNING "No edge setting!\n");
- break;
-
- case IRQT_RISING:
- newvalue = S3C2410_EXTINT_RISEEDGE;
- break;
-
- case IRQT_FALLING:
- newvalue = S3C2410_EXTINT_FALLEDGE;
- break;
-
- case IRQT_BOTHEDGE:
- newvalue = S3C2410_EXTINT_BOTHEDGE;
- break;
-
- case IRQT_LOW:
- newvalue = S3C2410_EXTINT_LOWLEV;
- break;
-
- case IRQT_HIGH:
- newvalue = S3C2410_EXTINT_HILEV;
- break;
-
- default:
- printk(KERN_ERR "No such irq type %d", type);
- return -1;
- }
-
- value = __raw_readl(extint_reg);
- value = (value & ~(7 << extint_offset)) | (newvalue << extint_offset);
- __raw_writel(value, extint_reg);
-
- return 0;
-}
-
-static struct irq_chip s3c_irqext_chip = {
- .name = "s3c-ext",
- .mask = s3c_irqext_mask,
- .unmask = s3c_irqext_unmask,
- .ack = s3c_irqext_ack,
- .set_type = s3c_irqext_type,
- .set_wake = s3c_irqext_wake
-};
-
-static struct irq_chip s3c_irq_eint0t4 = {
- .name = "s3c-ext0",
- .ack = s3c_irq_ack,
- .mask = s3c_irq_mask,
- .unmask = s3c_irq_unmask,
- .set_wake = s3c_irq_wake,
- .set_type = s3c_irqext_type,
-};
-
-/* mask values for the parent registers for each of the interrupt types */
-
-#define INTMSK_UART0 (1UL << (IRQ_UART0 - IRQ_EINT0))
-#define INTMSK_UART1 (1UL << (IRQ_UART1 - IRQ_EINT0))
-#define INTMSK_UART2 (1UL << (IRQ_UART2 - IRQ_EINT0))
-#define INTMSK_ADCPARENT (1UL << (IRQ_ADCPARENT - IRQ_EINT0))
-
-
-/* UART0 */
-
-static void
-s3c_irq_uart0_mask(unsigned int irqno)
-{
- s3c_irqsub_mask(irqno, INTMSK_UART0, 7);
-}
-
-static void
-s3c_irq_uart0_unmask(unsigned int irqno)
-{
- s3c_irqsub_unmask(irqno, INTMSK_UART0);
-}
-
-static void
-s3c_irq_uart0_ack(unsigned int irqno)
-{
- s3c_irqsub_maskack(irqno, INTMSK_UART0, 7);
-}
-
-static struct irq_chip s3c_irq_uart0 = {
- .name = "s3c-uart0",
- .mask = s3c_irq_uart0_mask,
- .unmask = s3c_irq_uart0_unmask,
- .ack = s3c_irq_uart0_ack,
-};
-
-/* UART1 */
-
-static void
-s3c_irq_uart1_mask(unsigned int irqno)
-{
- s3c_irqsub_mask(irqno, INTMSK_UART1, 7 << 3);
-}
-
-static void
-s3c_irq_uart1_unmask(unsigned int irqno)
-{
- s3c_irqsub_unmask(irqno, INTMSK_UART1);
-}
-
-static void
-s3c_irq_uart1_ack(unsigned int irqno)
-{
- s3c_irqsub_maskack(irqno, INTMSK_UART1, 7 << 3);
-}
-
-static struct irq_chip s3c_irq_uart1 = {
- .name = "s3c-uart1",
- .mask = s3c_irq_uart1_mask,
- .unmask = s3c_irq_uart1_unmask,
- .ack = s3c_irq_uart1_ack,
-};
-
-/* UART2 */
-
-static void
-s3c_irq_uart2_mask(unsigned int irqno)
-{
- s3c_irqsub_mask(irqno, INTMSK_UART2, 7 << 6);
-}
-
-static void
-s3c_irq_uart2_unmask(unsigned int irqno)
-{
- s3c_irqsub_unmask(irqno, INTMSK_UART2);
-}
-
-static void
-s3c_irq_uart2_ack(unsigned int irqno)
-{
- s3c_irqsub_maskack(irqno, INTMSK_UART2, 7 << 6);
-}
-
-static struct irq_chip s3c_irq_uart2 = {
- .name = "s3c-uart2",
- .mask = s3c_irq_uart2_mask,
- .unmask = s3c_irq_uart2_unmask,
- .ack = s3c_irq_uart2_ack,
-};
-
-/* ADC and Touchscreen */
-
-static void
-s3c_irq_adc_mask(unsigned int irqno)
-{
- s3c_irqsub_mask(irqno, INTMSK_ADCPARENT, 3 << 9);
-}
-
-static void
-s3c_irq_adc_unmask(unsigned int irqno)
-{
- s3c_irqsub_unmask(irqno, INTMSK_ADCPARENT);
-}
-
-static void
-s3c_irq_adc_ack(unsigned int irqno)
-{
- s3c_irqsub_ack(irqno, INTMSK_ADCPARENT, 3 << 9);
-}
-
-static struct irq_chip s3c_irq_adc = {
- .name = "s3c-adc",
- .mask = s3c_irq_adc_mask,
- .unmask = s3c_irq_adc_unmask,
- .ack = s3c_irq_adc_ack,
-};
-
-/* irq demux for adc */
-static void s3c_irq_demux_adc(unsigned int irq,
- struct irq_desc *desc)
-{
- unsigned int subsrc, submsk;
- unsigned int offset = 9;
- struct irq_desc *mydesc;
-
- /* read the current pending interrupts, and the mask
- * for what it is available */
-
- subsrc = __raw_readl(S3C2410_SUBSRCPND);
- submsk = __raw_readl(S3C2410_INTSUBMSK);
-
- subsrc &= ~submsk;
- subsrc >>= offset;
- subsrc &= 3;
-
- if (subsrc != 0) {
- if (subsrc & 1) {
- mydesc = irq_desc + IRQ_TC;
- desc_handle_irq(IRQ_TC, mydesc);
- }
- if (subsrc & 2) {
- mydesc = irq_desc + IRQ_ADC;
- desc_handle_irq(IRQ_ADC, mydesc);
- }
- }
-}
-
-static void s3c_irq_demux_uart(unsigned int start)
-{
- unsigned int subsrc, submsk;
- unsigned int offset = start - IRQ_S3CUART_RX0;
- struct irq_desc *desc;
-
- /* read the current pending interrupts, and the mask
- * for what it is available */
-
- subsrc = __raw_readl(S3C2410_SUBSRCPND);
- submsk = __raw_readl(S3C2410_INTSUBMSK);
-
- irqdbf2("s3c_irq_demux_uart: start=%d (%d), subsrc=0x%08x,0x%08x\n",
- start, offset, subsrc, submsk);
-
- subsrc &= ~submsk;
- subsrc >>= offset;
- subsrc &= 7;
-
- if (subsrc != 0) {
- desc = irq_desc + start;
-
- if (subsrc & 1)
- desc_handle_irq(start, desc);
-
- desc++;
-
- if (subsrc & 2)
- desc_handle_irq(start+1, desc);
-
- desc++;
-
- if (subsrc & 4)
- desc_handle_irq(start+2, desc);
- }
-}
-
-/* uart demux entry points */
-
-static void
-s3c_irq_demux_uart0(unsigned int irq,
- struct irq_desc *desc)
-{
- irq = irq;
- s3c_irq_demux_uart(IRQ_S3CUART_RX0);
-}
-
-static void
-s3c_irq_demux_uart1(unsigned int irq,
- struct irq_desc *desc)
-{
- irq = irq;
- s3c_irq_demux_uart(IRQ_S3CUART_RX1);
-}
-
-static void
-s3c_irq_demux_uart2(unsigned int irq,
- struct irq_desc *desc)
-{
- irq = irq;
- s3c_irq_demux_uart(IRQ_S3CUART_RX2);
-}
-
-static void
-s3c_irq_demux_extint8(unsigned int irq,
- struct irq_desc *desc)
-{
- unsigned long eintpnd = __raw_readl(S3C24XX_EINTPEND);
- unsigned long eintmsk = __raw_readl(S3C24XX_EINTMASK);
-
- eintpnd &= ~eintmsk;
- eintpnd &= ~0xff; /* ignore lower irqs */
-
- /* we may as well handle all the pending IRQs here */
-
- while (eintpnd) {
- irq = __ffs(eintpnd);
- eintpnd &= ~(1<
#include
#include
-
+#include
#include
#include
@@ -52,8 +52,8 @@
#include
#include
-#include "devs.h"
-#include "cpu.h"
+#include
+#include
#ifdef CONFIG_MTD_PARTITIONS
@@ -113,12 +113,6 @@ static struct platform_device amlm5900_device_nor = {
#endif
static struct map_desc amlm5900_iodesc[] __initdata = {
- {
- .virtual = (u32)S3C24XX_VA_SPI,
- .pfn = __phys_to_pfn(S3C2410_PA_SPI),
- .length = SZ_1M,
- .type = MT_DEVICE
- }
};
#define UCON S3C2410_UCON_DEFAULT
diff --git a/arch/arm/mach-s3c2410/mach-bast.c b/arch/arm/mach-s3c2410/mach-bast.c
index b8b76757ec54..7b81296427eb 100644
--- a/arch/arm/mach-s3c2410/mach-bast.c
+++ b/arch/arm/mach-s3c2410/mach-bast.c
@@ -50,9 +50,9 @@
#include
-#include "clock.h"
-#include "devs.h"
-#include "cpu.h"
+#include
+#include
+#include
#include "usb-simtec.h"
#define COPYRIGHT ", (c) 2004-2005 Simtec Electronics"
diff --git a/arch/arm/mach-s3c2410/mach-h1940.c b/arch/arm/mach-s3c2410/mach-h1940.c
index 15b625eae499..01c60d0923cd 100644
--- a/arch/arm/mach-s3c2410/mach-h1940.c
+++ b/arch/arm/mach-s3c2410/mach-h1940.c
@@ -25,23 +25,24 @@
#include
#include
-#include
#include
#include
#include
-
#include
#include
+#include
+#include
#include
#include
#include
+#include
-#include "clock.h"
-#include "devs.h"
-#include "cpu.h"
-#include "pm.h"
+#include
+#include
+#include
+#include
static struct map_desc h1940_iodesc[] __initdata = {
[0] = {
@@ -102,6 +103,32 @@ void h1940_latch_control(unsigned int clear, unsigned int set)
EXPORT_SYMBOL_GPL(h1940_latch_control);
+static void h1940_udc_pullup(enum s3c2410_udc_cmd_e cmd)
+{
+ printk(KERN_DEBUG "udc: pullup(%d)\n",cmd);
+
+ switch (cmd)
+ {
+ case S3C2410_UDC_P_ENABLE :
+ h1940_latch_control(0, H1940_LATCH_USB_DP);
+ break;
+ case S3C2410_UDC_P_DISABLE :
+ h1940_latch_control(H1940_LATCH_USB_DP, 0);
+ break;
+ case S3C2410_UDC_P_RESET :
+ break;
+ default:
+ break;
+ }
+}
+
+static struct s3c2410_udc_mach_info h1940_udc_cfg __initdata = {
+ .udc_command = h1940_udc_pullup,
+ .vbus_pin = S3C2410_GPG5,
+ .vbus_pin_inverted = 1,
+};
+
+
/**
* Set lcd on or off
@@ -146,12 +173,19 @@ static struct s3c2410fb_mach_info h1940_lcdcfg __initdata = {
.bpp= {16,16,16},
};
+static struct platform_device s3c_device_leds = {
+ .name = "h1940-leds",
+ .id = -1,
+};
+
static struct platform_device *h1940_devices[] __initdata = {
&s3c_device_usb,
&s3c_device_lcd,
&s3c_device_wdt,
&s3c_device_i2c,
&s3c_device_iis,
+ &s3c_device_usbgadget,
+ &s3c_device_leds,
};
static struct s3c24xx_board h1940_board __initdata = {
@@ -179,7 +213,23 @@ static void __init h1940_init_irq(void)
static void __init h1940_init(void)
{
+ u32 tmp;
+
s3c24xx_fb_set_platdata(&h1940_lcdcfg);
+ s3c24xx_udc_set_platdata(&h1940_udc_cfg);
+
+ /* Turn off suspend on both USB ports, and switch the
+ * selectable USB port to USB device mode. */
+
+ s3c2410_modify_misccr(S3C2410_MISCCR_USBHOST |
+ S3C2410_MISCCR_USBSUSPND0 |
+ S3C2410_MISCCR_USBSUSPND1, 0x0);
+
+ tmp = (
+ 0x78 << S3C2410_PLLCON_MDIVSHIFT)
+ | (0x02 << S3C2410_PLLCON_PDIVSHIFT)
+ | (0x03 << S3C2410_PLLCON_SDIVSHIFT);
+ writel(tmp, S3C2410_UPLLCON);
}
MACHINE_START(H1940, "IPAQ-H1940")
@@ -189,6 +239,6 @@ MACHINE_START(H1940, "IPAQ-H1940")
.boot_params = S3C2410_SDRAM_PA + 0x100,
.map_io = h1940_map_io,
.init_irq = h1940_init_irq,
- .init_machine = h1940_init,
+ .init_machine = h1940_init,
.timer = &s3c24xx_timer,
MACHINE_END
diff --git a/arch/arm/mach-s3c2410/mach-n30.c b/arch/arm/mach-s3c2410/mach-n30.c
index 0411e9adb54d..261aa4cc0770 100644
--- a/arch/arm/mach-s3c2410/mach-n30.c
+++ b/arch/arm/mach-s3c2410/mach-n30.c
@@ -29,7 +29,6 @@
#include
#include
-#include
#include
#include
#include
@@ -38,10 +37,10 @@
#include
#include
-#include "s3c2410.h"
-#include "clock.h"
-#include "devs.h"
-#include "cpu.h"
+#include
+#include
+#include
+#include
static struct map_desc n30_iodesc[] __initdata = {
/* nothing here yet */
diff --git a/arch/arm/mach-s3c2410/mach-otom.c b/arch/arm/mach-s3c2410/mach-otom.c
index 2c738b375e4d..c78ab75b44f3 100644
--- a/arch/arm/mach-s3c2410/mach-otom.c
+++ b/arch/arm/mach-s3c2410/mach-otom.c
@@ -32,10 +32,10 @@
#include
#include
-#include "s3c2410.h"
-#include "clock.h"
-#include "devs.h"
-#include "cpu.h"
+#include
+#include
+#include
+#include
static struct map_desc otom11_iodesc[] __initdata = {
/* Device area */
diff --git a/arch/arm/mach-s3c2410/mach-qt2410.c b/arch/arm/mach-s3c2410/mach-qt2410.c
new file mode 100644
index 000000000000..c6a41593de21
--- /dev/null
+++ b/arch/arm/mach-s3c2410/mach-qt2410.c
@@ -0,0 +1,448 @@
+/* linux/arch/arm/mach-s3c2410/mach-qt2410.c
+ *
+ * Copyright (C) 2006 by OpenMoko, Inc.
+ * Author: Harald Welte
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as
+ * published by the Free Software Foundation; either version 2 of
+ * the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
+ * MA 02111-1307 USA
+ *
+ */
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+#include
+#include
+#include
+#include
+
+#include
+#include
+#include
+
+#include
+#include
+#include
+#include
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+#include
+#include
+#include
+#include
+
+static struct map_desc qt2410_iodesc[] __initdata = {
+ { 0xe0000000, __phys_to_pfn(S3C2410_CS3+0x01000000), SZ_1M, MT_DEVICE }
+};
+
+#define UCON S3C2410_UCON_DEFAULT
+#define ULCON S3C2410_LCON_CS8 | S3C2410_LCON_PNONE | S3C2410_LCON_STOPB
+#define UFCON S3C2410_UFCON_RXTRIG8 | S3C2410_UFCON_FIFOMODE
+
+static struct s3c2410_uartcfg smdk2410_uartcfgs[] = {
+ [0] = {
+ .hwport = 0,
+ .flags = 0,
+ .ucon = UCON,
+ .ulcon = ULCON,
+ .ufcon = UFCON,
+ },
+ [1] = {
+ .hwport = 1,
+ .flags = 0,
+ .ucon = UCON,
+ .ulcon = ULCON,
+ .ufcon = UFCON,
+ },
+ [2] = {
+ .hwport = 2,
+ .flags = 0,
+ .ucon = UCON,
+ .ulcon = ULCON,
+ .ufcon = UFCON,
+ }
+};
+
+/* LCD driver info */
+
+/* Configuration for 640x480 SHARP LQ080V3DG01 */
+static struct s3c2410fb_mach_info qt2410_biglcd_cfg __initdata = {
+ .regs = {
+
+ .lcdcon1 = S3C2410_LCDCON1_TFT16BPP |
+ S3C2410_LCDCON1_TFT |
+ S3C2410_LCDCON1_CLKVAL(0x01), /* HCLK/4 */
+
+ .lcdcon2 = S3C2410_LCDCON2_VBPD(18) | /* 19 */
+ S3C2410_LCDCON2_LINEVAL(479) |
+ S3C2410_LCDCON2_VFPD(10) | /* 11 */
+ S3C2410_LCDCON2_VSPW(14), /* 15 */
+
+ .lcdcon3 = S3C2410_LCDCON3_HBPD(43) | /* 44 */
+ S3C2410_LCDCON3_HOZVAL(639) | /* 640 */
+ S3C2410_LCDCON3_HFPD(115), /* 116 */
+
+ .lcdcon4 = S3C2410_LCDCON4_MVAL(0) |
+ S3C2410_LCDCON4_HSPW(95), /* 96 */
+
+ .lcdcon5 = S3C2410_LCDCON5_FRM565 |
+ S3C2410_LCDCON5_INVVLINE |
+ S3C2410_LCDCON5_INVVFRAME |
+ S3C2410_LCDCON5_PWREN |
+ S3C2410_LCDCON5_HWSWP,
+ },
+
+ .lpcsel = ((0xCE6) & ~7) | 1<<4,
+
+ .width = 640,
+ .height = 480,
+
+ .xres = {
+ .min = 640,
+ .max = 640,
+ .defval = 640,
+ },
+
+ .yres = {
+ .min = 480,
+ .max = 480,
+ .defval = 480,
+ },
+
+ .bpp = {
+ .min = 16,
+ .max = 16,
+ .defval = 16,
+ },
+};
+
+/* Configuration for 480x640 toppoly TD028TTEC1 */
+static struct s3c2410fb_mach_info qt2410_prodlcd_cfg __initdata = {
+ .regs = {
+
+ .lcdcon1 = S3C2410_LCDCON1_TFT16BPP |
+ S3C2410_LCDCON1_TFT |
+ S3C2410_LCDCON1_CLKVAL(0x01), /* HCLK/4 */
+
+ .lcdcon2 = S3C2410_LCDCON2_VBPD(1) | /* 2 */
+ S3C2410_LCDCON2_LINEVAL(639) |/* 640 */
+ S3C2410_LCDCON2_VFPD(3) | /* 4 */
+ S3C2410_LCDCON2_VSPW(1), /* 2 */
+
+ .lcdcon3 = S3C2410_LCDCON3_HBPD(7) | /* 8 */
+ S3C2410_LCDCON3_HOZVAL(479) | /* 479 */
+ S3C2410_LCDCON3_HFPD(23), /* 24 */
+
+ .lcdcon4 = S3C2410_LCDCON4_MVAL(0) |
+ S3C2410_LCDCON4_HSPW(7), /* 8 */
+
+ .lcdcon5 = S3C2410_LCDCON5_FRM565 |
+ S3C2410_LCDCON5_INVVLINE |
+ S3C2410_LCDCON5_INVVFRAME |
+ S3C2410_LCDCON5_PWREN |
+ S3C2410_LCDCON5_HWSWP,
+ },
+
+ .lpcsel = ((0xCE6) & ~7) | 1<<4,
+
+ .width = 480,
+ .height = 640,
+
+ .xres = {
+ .min = 480,
+ .max = 480,
+ .defval = 480,
+ },
+
+ .yres = {
+ .min = 640,
+ .max = 640,
+ .defval = 640,
+ },
+
+ .bpp = {
+ .min = 16,
+ .max = 16,
+ .defval = 16,
+ },
+};
+
+/* Config for 240x320 LCD */
+static struct s3c2410fb_mach_info qt2410_lcd_cfg __initdata = {
+ .regs = {
+
+ .lcdcon1 = S3C2410_LCDCON1_TFT16BPP |
+ S3C2410_LCDCON1_TFT |
+ S3C2410_LCDCON1_CLKVAL(0x04),
+
+ .lcdcon2 = S3C2410_LCDCON2_VBPD(1) |
+ S3C2410_LCDCON2_LINEVAL(319) |
+ S3C2410_LCDCON2_VFPD(6) |
+ S3C2410_LCDCON2_VSPW(3),
+
+ .lcdcon3 = S3C2410_LCDCON3_HBPD(12) |
+ S3C2410_LCDCON3_HOZVAL(239) |
+ S3C2410_LCDCON3_HFPD(7),
+
+ .lcdcon4 = S3C2410_LCDCON4_MVAL(0) |
+ S3C2410_LCDCON4_HSPW(3),
+
+ .lcdcon5 = S3C2410_LCDCON5_FRM565 |
+ S3C2410_LCDCON5_INVVLINE |
+ S3C2410_LCDCON5_INVVFRAME |
+ S3C2410_LCDCON5_PWREN |
+ S3C2410_LCDCON5_HWSWP,
+ },
+
+ .lpcsel = ((0xCE6) & ~7) | 1<<4,
+
+ .width = 240,
+ .height = 320,
+
+ .xres = {
+ .min = 240,
+ .max = 240,
+ .defval = 240,
+ },
+
+ .yres = {
+ .min = 320,
+ .max = 320,
+ .defval = 320,
+ },
+
+ .bpp = {
+ .min = 16,
+ .max = 16,
+ .defval = 16,
+ },
+};
+
+/* CS8900 */
+
+static struct resource qt2410_cs89x0_resources[] = {
+ [0] = {
+ .start = 0x19000000,
+ .end = 0x19000000 + 16,
+ .flags = IORESOURCE_MEM,
+ },
+ [1] = {
+ .start = IRQ_EINT9,
+ .end = IRQ_EINT9,
+ .flags = IORESOURCE_IRQ,
+ },
+};
+
+static struct platform_device qt2410_cs89x0 = {
+ .name = "cirrus-cs89x0",
+ .num_resources = ARRAY_SIZE(qt2410_cs89x0_resources),
+ .resource = qt2410_cs89x0_resources,
+};
+
+/* LED */
+
+static struct s3c24xx_led_platdata qt2410_pdata_led = {
+ .gpio = S3C2410_GPB0,
+ .flags = S3C24XX_LEDF_ACTLOW | S3C24XX_LEDF_TRISTATE,
+ .name = "led",
+ .def_trigger = "timer",
+};
+
+static struct platform_device qt2410_led = {
+ .name = "s3c24xx_led",
+ .id = 0,
+ .dev = {
+ .platform_data = &qt2410_pdata_led,
+ },
+};
+
+/* SPI */
+
+static void spi_gpio_cs(struct s3c2410_spigpio_info *spi, int cs)
+{
+ switch (cs) {
+ case BITBANG_CS_ACTIVE:
+ s3c2410_gpio_setpin(S3C2410_GPB5, 0);
+ break;
+ case BITBANG_CS_INACTIVE:
+ s3c2410_gpio_setpin(S3C2410_GPB5, 1);
+ break;
+ }
+}
+
+static struct s3c2410_spigpio_info spi_gpio_cfg = {
+ .pin_clk = S3C2410_GPG7,
+ .pin_mosi = S3C2410_GPG6,
+ .pin_miso = S3C2410_GPG5,
+ .chip_select = &spi_gpio_cs,
+};
+
+
+static struct platform_device qt2410_spi = {
+ .name = "s3c24xx-spi-gpio",
+ .id = 1,
+ .dev = {
+ .platform_data = &spi_gpio_cfg,
+ },
+};
+
+/* Board devices */
+
+static struct platform_device *qt2410_devices[] __initdata = {
+ &s3c_device_usb,
+ &s3c_device_lcd,
+ &s3c_device_wdt,
+ &s3c_device_i2c,
+ &s3c_device_iis,
+ &s3c_device_sdi,
+ &s3c_device_usbgadget,
+ &qt2410_spi,
+ &qt2410_cs89x0,
+ &qt2410_led,
+};
+
+static struct s3c24xx_board qt2410_board __initdata = {
+ .devices = qt2410_devices,
+ .devices_count = ARRAY_SIZE(qt2410_devices)
+};
+
+static struct mtd_partition qt2410_nand_part[] = {
+ [0] = {
+ .name = "U-Boot",
+ .size = 0x30000,
+ .offset = 0,
+ },
+ [1] = {
+ .name = "U-Boot environment",
+ .offset = 0x30000,
+ .size = 0x4000,
+ },
+ [2] = {
+ .name = "kernel",
+ .offset = 0x34000,
+ .size = SZ_2M,
+ },
+ [3] = {
+ .name = "initrd",
+ .offset = 0x234000,
+ .size = SZ_4M,
+ },
+ [4] = {
+ .name = "jffs2",
+ .offset = 0x634000,
+ .size = 0x39cc000,
+ },
+};
+
+static struct s3c2410_nand_set qt2410_nand_sets[] = {
+ [0] = {
+ .name = "NAND",
+ .nr_chips = 1,
+ .nr_partitions = ARRAY_SIZE(qt2410_nand_part),
+ .partitions = qt2410_nand_part,
+ },
+};
+
+/* choose a set of timings which should suit most 512Mbit
+ * chips and beyond.
+ */
+
+static struct s3c2410_platform_nand qt2410_nand_info = {
+ .tacls = 20,
+ .twrph0 = 60,
+ .twrph1 = 20,
+ .nr_sets = ARRAY_SIZE(qt2410_nand_sets),
+ .sets = qt2410_nand_sets,
+};
+
+/* UDC */
+
+static struct s3c2410_udc_mach_info qt2410_udc_cfg = {
+};
+
+static char tft_type = 's';
+
+static int __init qt2410_tft_setup(char *str)
+{
+ tft_type = str[0];
+ return 1;
+}
+
+__setup("tft=", qt2410_tft_setup);
+
+static void __init qt2410_map_io(void)
+{
+ s3c24xx_init_io(qt2410_iodesc, ARRAY_SIZE(qt2410_iodesc));
+ s3c24xx_init_clocks(12*1000*1000);
+ s3c24xx_init_uarts(smdk2410_uartcfgs, ARRAY_SIZE(smdk2410_uartcfgs));
+ s3c24xx_set_board(&qt2410_board);
+}
+
+static void __init qt2410_machine_init(void)
+{
+ s3c_device_nand.dev.platform_data = &qt2410_nand_info;
+
+ switch (tft_type) {
+ case 'p': /* production */
+ s3c24xx_fb_set_platdata(&qt2410_prodlcd_cfg);
+ break;
+ case 'b': /* big */
+ s3c24xx_fb_set_platdata(&qt2410_biglcd_cfg);
+ break;
+ case 's': /* small */
+ default:
+ s3c24xx_fb_set_platdata(&qt2410_lcd_cfg);
+ break;
+ }
+
+ s3c2410_gpio_cfgpin(S3C2410_GPB0, S3C2410_GPIO_OUTPUT);
+ s3c2410_gpio_setpin(S3C2410_GPB0, 1);
+
+ s3c24xx_udc_set_platdata(&qt2410_udc_cfg);
+
+ s3c2410_gpio_cfgpin(S3C2410_GPB5, S3C2410_GPIO_OUTPUT);
+
+ s3c2410_pm_init();
+}
+
+MACHINE_START(QT2410, "QT2410")
+ .phys_io = S3C2410_PA_UART,
+ .io_pg_offst = (((u32)S3C24XX_VA_UART) >> 18) & 0xfffc,
+ .boot_params = S3C2410_SDRAM_PA + 0x100,
+ .map_io = qt2410_map_io,
+ .init_irq = s3c24xx_init_irq,
+ .init_machine = qt2410_machine_init,
+ .timer = &s3c24xx_timer,
+MACHINE_END
+
+
diff --git a/arch/arm/mach-s3c2410/mach-smdk2410.c b/arch/arm/mach-s3c2410/mach-smdk2410.c
index 01c0c986d827..57b8a80f33d0 100644
--- a/arch/arm/mach-s3c2410/mach-smdk2410.c
+++ b/arch/arm/mach-s3c2410/mach-smdk2410.c
@@ -1,4 +1,4 @@
-/***********************************************************************
+/* linux/arch/arm/mach-s3c2410/mach-smdk2410.c
*
* linux/arch/arm/mach-s3c2410/mach-smdk2410.c
*
@@ -49,10 +49,10 @@
#include
-#include "devs.h"
-#include "cpu.h"
+#include
+#include
-#include "common-smdk.h"
+#include
static struct map_desc smdk2410_iodesc[] __initdata = {
/* nothing here yet */
diff --git a/arch/arm/mach-s3c2410/mach-vr1000.c b/arch/arm/mach-s3c2410/mach-vr1000.c
index a382fc095110..c947c75bcbf0 100644
--- a/arch/arm/mach-s3c2410/mach-vr1000.c
+++ b/arch/arm/mach-s3c2410/mach-vr1000.c
@@ -43,9 +43,9 @@
#include
#include
-#include "clock.h"
-#include "devs.h"
-#include "cpu.h"
+#include
+#include
+#include
#include "usb-simtec.h"
/* macros for virtual address mods for the io space entries */
diff --git a/arch/arm/mach-s3c2410/pm.c b/arch/arm/mach-s3c2410/pm.c
index ebf294dd31da..3b3a7db4e0dd 100644
--- a/arch/arm/mach-s3c2410/pm.c
+++ b/arch/arm/mach-s3c2410/pm.c
@@ -1,11 +1,9 @@
/* linux/arch/arm/mach-s3c2410/pm.c
*
- * Copyright (c) 2004,2006 Simtec Electronics
+ * Copyright (c) 2006 Simtec Electronics
* Ben Dooks
*
- * S3C24XX Power Manager (Suspend-To-RAM) support
- *
- * See Documentation/arm/Samsung-S3C24XX/Suspend.txt for more information
+ * S3C2410 (and compatible) Power Manager (Suspend-To-RAM) support
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -20,640 +18,139 @@
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
- *
- * Parts based on arch/arm/mach-pxa/pm.c
- *
- * Thanks to Dimitry Andric for debugging
*/
#include
#include
#include
#include
-#include
-#include