diff -Nur linux-2.6.4-rc2.org/arch/arm/Kconfig linux-2.6.4-rc2/arch/arm/Kconfig --- linux-2.6.4-rc2.org/arch/arm/Kconfig 2004-03-04 06:16:47.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/Kconfig 2004-03-09 13:25:56.000000000 +0000 @@ -145,6 +145,14 @@ If you have any questions or comments about the Linux kernel port to this board, send e-mail to sjhill@cotw.com. +config ARCH_PSIONW + bool "Psion Windermere" + help + Say Y here if you want to run this kernel on Psion Windermere + systems with NEC 710T processor. Psion Windermere architecture + covers Psion 5MX, 5MX Pro and Revo. It does not work on older + Psion 5. + config ARCH_RPC bool "RiscPC" help @@ -169,6 +177,8 @@ source "arch/arm/mach-iop3xx/Kconfig" +source "arch/arm/mach-psionw/Kconfig" + source "arch/arm/mach-pxa/Kconfig" source "arch/arm/mach-sa1100/Kconfig" @@ -229,7 +239,7 @@ # Select various configuration options depending on the machine type config DISCONTIGMEM bool - depends on ARCH_EDB7211 || ARCH_SA1100 + depends on ARCH_EDB7211 || ARCH_PSIONW || ARCH_SA1100 default y help Say Y to upport efficient handling of discontiguous physical memory, diff -Nur linux-2.6.4-rc2.org/arch/arm/Makefile linux-2.6.4-rc2/arch/arm/Makefile --- linux-2.6.4-rc2.org/arch/arm/Makefile 2004-03-09 13:22:59.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/Makefile 2004-03-09 13:25:56.000000000 +0000 @@ -99,6 +99,8 @@ machine-$(CONFIG_ARCH_ANAKIN) := anakin machine-$(CONFIG_ARCH_IOP3XX) := iop3xx machine-$(CONFIG_ARCH_ADIFCC) := adifcc +textaddr-$(CONFIG_ARCH_PSIONW) := 0xc0048000 + machine-$(CONFIG_ARCH_PSIONW) := psionw MACHINE := $(machine-y) TEXTADDR := $(textaddr-y) diff -Nur linux-2.6.4-rc2.org/arch/arm/configs/psionw_defconfig linux-2.6.4-rc2/arch/arm/configs/psionw_defconfig --- linux-2.6.4-rc2.org/arch/arm/configs/psionw_defconfig 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/configs/psionw_defconfig 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,469 @@ +# +# Automatically generated make config: don't edit +# +CONFIG_ARM=y +CONFIG_MMU=y +CONFIG_UID16=y +CONFIG_RWSEM_GENERIC_SPINLOCK=y + +# +# Code maturity level options +# +CONFIG_EXPERIMENTAL=y +CONFIG_CLEAN_COMPILE=y +CONFIG_STANDALONE=y +CONFIG_BROKEN_ON_SMP=y + +# +# General setup +# +CONFIG_SWAP=y +CONFIG_SYSVIPC=y +# CONFIG_BSD_PROCESS_ACCT is not set +CONFIG_SYSCTL=y +CONFIG_LOG_BUF_SHIFT=14 +# CONFIG_IKCONFIG is not set +# CONFIG_EMBEDDED is not set +CONFIG_KALLSYMS=y +CONFIG_FUTEX=y +CONFIG_EPOLL=y +CONFIG_IOSCHED_NOOP=y +CONFIG_IOSCHED_AS=y +CONFIG_IOSCHED_DEADLINE=y + +# +# Loadable module support +# +# CONFIG_MODULES is not set + +# +# System Type +# +# CONFIG_ARCH_ADIFCC is not set +# CONFIG_ARCH_ANAKIN is not set +# CONFIG_ARCH_CLPS7500 is not set +# CONFIG_ARCH_CLPS711X is not set +# CONFIG_ARCH_CO285 is not set +# CONFIG_ARCH_PXA is not set +# CONFIG_ARCH_EBSA110 is not set +# CONFIG_ARCH_CAMELOT is not set +# CONFIG_ARCH_FOOTBRIDGE is not set +# CONFIG_ARCH_INTEGRATOR is not set +# CONFIG_ARCH_IOP3XX is not set +# CONFIG_ARCH_L7200 is not set +CONFIG_ARCH_PSIONW=y +# CONFIG_ARCH_RPC is not set +# CONFIG_ARCH_SA1100 is not set +# CONFIG_ARCH_SHARK is not set + +# +# CLPS711X/EP721X Implementations +# + +# +# Epxa10db +# + +# +# Footbridge Implementations +# + +# +# IOP3xx Implementation Options +# +# CONFIG_ARCH_IOP310 is not set +# CONFIG_ARCH_IOP321 is not set + +# +# IOP3xx Chipset Features +# + +# +# Psion Implementations +# +# CONFIG_PSIONW_5MX is not set +# CONFIG_PSIONW_5MXPRO24MB is not set +CONFIG_PSIONW_5MXPRO32MB=y +# CONFIG_PSIONW_REVO is not set +# CONFIG_PSIONW_REVOPLUS is not set + +# +# Intel PXA250/210 Implementations +# + +# +# SA11x0 Implementations +# + +# +# Processor Type +# +CONFIG_CPU_32=y +CONFIG_CPU_ARM720T=y +CONFIG_CPU_32v4=y +CONFIG_CPU_ABRT_LV4T=y +CONFIG_CPU_CACHE_V4=y +CONFIG_CPU_COPY_V4WT=y +CONFIG_CPU_TLB_V4WT=y + +# +# Processor Features +# +# CONFIG_ARM_THUMB is not set + +# +# General setup +# +CONFIG_DISCONTIGMEM=y +# CONFIG_ZBOOT_ROM is not set +CONFIG_ZBOOT_ROM_TEXT=0x0 +CONFIG_ZBOOT_ROM_BSS=0x0 +CONFIG_HOTPLUG=y + +# +# PCMCIA/CardBus support +# +# CONFIG_PCMCIA is not set +# CONFIG_PCMCIA_DEBUG is not set + +# +# At least one math emulation must be selected +# +CONFIG_FPE_NWFPE=y +# CONFIG_FPE_NWFPE_XP is not set +# CONFIG_FPE_FASTFPE is not set +CONFIG_BINFMT_ELF=y +# CONFIG_BINFMT_AOUT is not set +# CONFIG_BINFMT_MISC is not set + +# +# Generic Driver Options +# +# CONFIG_FW_LOADER is not set +# CONFIG_PM is not set +# CONFIG_PREEMPT is not set +# CONFIG_ARTHUR is not set +CONFIG_CMDLINE="" +CONFIG_ALIGNMENT_TRAP=y + +# +# Parallel port support +# +# CONFIG_PARPORT is not set + +# +# Memory Technology Devices (MTD) +# +# CONFIG_MTD is not set + +# +# Plug and Play support +# +# CONFIG_PNP is not set + +# +# Block devices +# +# CONFIG_BLK_DEV_FD is not set +# CONFIG_BLK_DEV_LOOP is not set +CONFIG_BLK_DEV_RAM=y +CONFIG_BLK_DEV_RAM_SIZE=4096 +CONFIG_BLK_DEV_INITRD=y + +# +# Multi-device support (RAID and LVM) +# +# CONFIG_MD is not set + +# +# Networking support +# +# CONFIG_NET is not set + +# +# Amateur Radio support +# +# CONFIG_HAMRADIO is not set + +# +# ATA/ATAPI/MFM/RLL support +# +# CONFIG_IDE is not set + +# +# SCSI device support +# +# CONFIG_SCSI is not set + +# +# I2O device support +# + +# +# ISDN subsystem +# + +# +# Input device support +# +CONFIG_INPUT=y + +# +# Userland interfaces +# +CONFIG_INPUT_MOUSEDEV=y +CONFIG_INPUT_MOUSEDEV_PSAUX=y +CONFIG_INPUT_MOUSEDEV_SCREEN_X=1024 +CONFIG_INPUT_MOUSEDEV_SCREEN_Y=768 +# CONFIG_INPUT_JOYDEV is not set +# CONFIG_INPUT_TSDEV is not set +# CONFIG_INPUT_TSLIBDEV is not set +# CONFIG_INPUT_EVDEV is not set +# CONFIG_INPUT_EVBUG is not set + +# +# Input I/O drivers +# +# CONFIG_GAMEPORT is not set +CONFIG_SOUND_GAMEPORT=y +CONFIG_SERIO=y +# CONFIG_SERIO_I8042 is not set +# CONFIG_SERIO_SERPORT is not set +# CONFIG_SERIO_CT82C710 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 is not set +# CONFIG_INPUT_MISC is not set + +# +# Character devices +# +CONFIG_VT=y +CONFIG_VT_CONSOLE=y +CONFIG_HW_CONSOLE=y +# CONFIG_SERIAL_NONSTANDARD is not set + +# +# Serial drivers +# +# CONFIG_SERIAL_8250 is not set + +# +# Non-8250 serial port support +# +CONFIG_SERIAL_PSIONW=y +CONFIG_SERIAL_PSIONW_CONSOLE=y +# CONFIG_SERIAL_DZ is not set +CONFIG_SERIAL_CORE=y +CONFIG_SERIAL_CORE_CONSOLE=y +CONFIG_UNIX98_PTYS=y +CONFIG_UNIX98_PTY_COUNT=256 + +# +# I2C support +# +# CONFIG_I2C is not set + +# +# I2C Algorithms +# + +# +# I2C Hardware Bus support +# + +# +# I2C Hardware Sensors Chip support +# +# CONFIG_I2C_SENSOR is not set + +# +# L3 serial bus support +# +# CONFIG_L3 is not set + +# +# Mice +# +# CONFIG_BUSMOUSE is not set +# CONFIG_QIC02_TAPE is not set + +# +# IPMI +# +# CONFIG_IPMI_HANDLER is not set + +# +# Watchdog Cards +# +# CONFIG_WATCHDOG is not set +# CONFIG_NVRAM is not set +# CONFIG_RTC is not set +# CONFIG_GEN_RTC is not set +# CONFIG_DTLK is not set +# CONFIG_R3964 is not set +# CONFIG_APPLICOM is not set + +# +# Ftape, the floppy tape device driver +# +# CONFIG_FTAPE is not set +# CONFIG_AGP is not set +# CONFIG_DRM is not set +# CONFIG_RAW_DRIVER is not set + +# +# Multimedia devices +# +# CONFIG_VIDEO_DEV is not set + +# +# Digital Video Broadcasting Devices +# + +# +# MMC/SD Card support +# +# CONFIG_MMC is not set + +# +# File systems +# +CONFIG_EXT2_FS=y +# CONFIG_EXT2_FS_XATTR is not set +# CONFIG_EXT3_FS is not set +# CONFIG_JBD is not set +# CONFIG_REISERFS_FS is not set +# CONFIG_JFS_FS is not set +# CONFIG_XFS_FS is not set +CONFIG_MINIX_FS=y +# CONFIG_ROMFS_FS is not set +# CONFIG_QUOTA is not set +# CONFIG_AUTOFS_FS is not set +# CONFIG_AUTOFS4_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 is not set +# CONFIG_NTFS_FS is not set + +# +# Pseudo filesystems +# +CONFIG_PROC_FS=y +# CONFIG_DEVFS_FS is not set +CONFIG_DEVPTS_FS=y +# CONFIG_DEVPTS_FS_XATTR is not set +# CONFIG_TMPFS is not set +# CONFIG_HUGETLB_PAGE is not set +CONFIG_RAMFS=y + +# +# Miscellaneous filesystems +# +# CONFIG_ADFS_FS is not set +# CONFIG_AFFS_FS is not set +# CONFIG_HFS_FS is not set +# CONFIG_BEFS_FS is not set +# CONFIG_BFS_FS is not set +# CONFIG_EFS_FS is not set +# CONFIG_CRAMFS is not set +# 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 + +# +# Partition Types +# +CONFIG_PARTITION_ADVANCED=y +# CONFIG_ACORN_PARTITION is not set +# CONFIG_OSF_PARTITION is not set +# CONFIG_AMIGA_PARTITION is not set +# CONFIG_ATARI_PARTITION is not set +# CONFIG_MAC_PARTITION is not set +CONFIG_MSDOS_PARTITION=y +# CONFIG_BSD_DISKLABEL is not set +# CONFIG_MINIX_SUBPARTITION is not set +# CONFIG_SOLARIS_X86_PARTITION is not set +# CONFIG_UNIXWARE_DISKLABEL is not set +# CONFIG_LDM_PARTITION is not set +# CONFIG_NEC98_PARTITION is not set +# CONFIG_SGI_PARTITION is not set +# CONFIG_ULTRIX_PARTITION is not set +# CONFIG_SUN_PARTITION is not set +# CONFIG_EFI_PARTITION is not set + +# +# Graphics support +# +# CONFIG_FB is not set + +# +# Console display driver support +# +# CONFIG_VGA_CONSOLE is not set +# CONFIG_MDA_CONSOLE is not set +CONFIG_DUMMY_CONSOLE=y + +# +# Misc devices +# + +# +# Multimedia Capabilities Port drivers +# +# CONFIG_MCP is not set + +# +# Console Switches +# +# CONFIG_SWITCHES is not set + +# +# USB support +# +# CONFIG_USB_GADGET is not set + +# +# Kernel hacking +# +CONFIG_FRAME_POINTER=y +CONFIG_DEBUG_USER=y +# CONFIG_DEBUG_INFO is not set +CONFIG_DEBUG_KERNEL=y +# CONFIG_DEBUG_SLAB is not set +CONFIG_MAGIC_SYSRQ=y +# CONFIG_DEBUG_SPINLOCK is not set +# CONFIG_DEBUG_WAITQ is not set +# CONFIG_DEBUG_BUGVERBOSE is not set +# CONFIG_DEBUG_ERRORS is not set +CONFIG_DEBUG_LL=y + +# +# Security options +# +# CONFIG_SECURITY is not set + +# +# Cryptographic options +# +# CONFIG_CRYPTO is not set + +# +# Library routines +# +# CONFIG_CRC32 is not set diff -Nur linux-2.6.4-rc2.org/arch/arm/kernel/debug.S linux-2.6.4-rc2/arch/arm/kernel/debug.S --- linux-2.6.4-rc2.org/arch/arm/kernel/debug.S 2004-03-04 06:16:41.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/kernel/debug.S 2004-03-09 13:25:56.000000000 +0000 @@ -348,6 +348,37 @@ 1002: .endm +#elif defined(CONFIG_ARCH_PSIONW) + +#include + + .macro addruart,rx + mrc p15, 0, \rx, c1, c0 + tst \rx, #1 @ MMU enabled? + moveq \rx, #PSIONW_PHYS_BASE + movne \rx, #PSIONW_VIRT_BASE + orr \rx, \rx, #0x0700 @ UART2 + .endm + + .macro senduart,rd,rx + str \rd, [\rx] @ UARTDR + .endm + + .macro waituart,rd,rx +1001: ldr \rd, [\rx, #0x0010] @ SYSFLGx + tst \rd, #1 << 3 @ UBUSYx + bne 1001b + .endm + + .macro busyuart,rd,rx + tst \rx, #0x0000 @ UART2 does not have CTS here + bne 1002f +1001: ldr \rd, [\rx, #0x0010] @ SYSFLGx + tst \rd, #1 << 0 @ CTS + bne 1001b +1002: + .endm + #elif defined(CONFIG_ARCH_ANAKIN) //#//include diff -Nur linux-2.6.4-rc2.org/arch/arm/kernel/entry-armv.S linux-2.6.4-rc2/arch/arm/kernel/entry-armv.S --- linux-2.6.4-rc2.org/arch/arm/kernel/entry-armv.S 2004-03-04 06:16:41.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/kernel/entry-armv.S 2004-03-09 13:25:56.000000000 +0000 @@ -508,6 +508,41 @@ .macro irq_prio_table .endm + +#elif defined(CONFIG_ARCH_PSIONW) + +#include + + .macro disable_fiq + .endm + + .macro get_irqnr_and_base, irqnr, stat, base, mask + mov \base, #PSIONW_BASE + ldr \stat, [\base, #INTRSR] + ldr \mask, [\base, #INTENS] + mov \irqnr, #4 + mov \mask, \mask, lsl #16 + and \stat, \stat, \mask, lsr #16 + movs \stat, \stat, lsr #4 + bne 1001f + +1001: tst \stat, #255 + addeq \irqnr, \irqnr, #8 + moveq \stat, \stat, lsr #8 + tst \stat, #15 + addeq \irqnr, \irqnr, #4 + moveq \stat, \stat, lsr #4 + tst \stat, #3 + addeq \irqnr, \irqnr, #2 + moveq \stat, \stat, lsr #2 + tst \stat, #1 + addeq \irqnr, \irqnr, #1 + moveq \stat, \stat, lsr #1 + tst \stat, #1 @ bit 0 should be set + .endm + + .macro irq_prio_table + .endm #elif defined (CONFIG_ARCH_CAMELOT) #include diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/Kconfig linux-2.6.4-rc2/arch/arm/mach-psionw/Kconfig --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/Kconfig 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/Kconfig 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,40 @@ + +menu "Psion Implementations" + +choice + prompt "Psion Model" + depends on ARCH_PSIONW + default PSIONW_5MX + +config PSIONW_5MX + bool "Psion 5MX with 16MB of memory" + help + Say Y if you intend to run the kernel on Psion 5MX machine. + +config PSIONW_5MXPRO24MB + bool "Psion 5MX Pro with 24MB of memory" + help + Say Y if you intend to run the kernel on Psion 5MX Pro 24 + machine. + +config PSIONW_5MXPRO32MB + bool "Psion 5MX Pro with 32MB of memory" + help + Say Y if you intend to run the kernel on Psion 5MX Pro 32 + machine. + +config PSIONW_REVO + bool "Psion Revo with 8MB of memory" + help + Say Y if you intend to run the kernel on Psion Revo machine. + +config PSIONW_REVOPLUS + bool "Psion Revo Plus with 16MB of memory" + help + Say Y if you intend to run the kernel on Psion Revo Plus + machine. + +endchoice + +endmenu + diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/Makefile linux-2.6.4-rc2/arch/arm/mach-psionw/Makefile --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/Makefile 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/Makefile 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,16 @@ +# +# Makefile for the linux kernel. +# + +# Object file lists. + +obj-y := irq.o mm.o psionw-arch.o psionw-hardware.o psionw-time.o serial-debug.o +#obj-y := psionw-power.o +obj-m := +obj-n := +obj- := + +#obj-$(CONFIG_ARCH_PSIONW) += psionw-time.o psionw-leds.o psionw-power.o serial-debug.o +#leds-$(CONFIG_ARCH_PSIONW) += psionw-leds.o +obj-$(CONFIG_LEDS) += $(leds-y) + diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/irq.c linux-2.6.4-rc2/arch/arm/mach-psionw/irq.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/irq.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/irq.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,117 @@ +/* + * linux/arch/arm/mach-psionw/irq.c + * + * Copyright (C) 2001 Yuji Shinokawa + * Copyright (C) 2001 Tony Lindgren + * + * 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 + +static void int_mask(unsigned int irq) +{ + u32 intmr; + + intmr = (1 << irq); + psionw_writel(intmr, INTENC); +} + +static void int_ack(unsigned int irq) +{ + u32 intmr; + + intmr = (1 << irq); + psionw_writel(intmr, INTENC); + + switch (irq) { + case IRQ_CSINT: + psionw_writel(1, COEOI); + printk("Received and cleared CSINT irq %d\n", irq); + break; + case IRQ_EINT2: + psionw_writel(1, E2EOI); + printk("Received and cleared EINT2 irq %d\n", irq); + break; + case IRQ_TC1OI: + psionw_writel(1, TC1EOI); /* Cleared here, handled in rtc */ + break; + case IRQ_TC2OI: + psionw_writel(1, TC2EOI); /* Cleared here, handled in timer */ + break; + case IRQ_RTCMI: + psionw_writel(1, RTCEOI); /* Cleared here, handled in rtc*/ + break; + case IRQ_TINT: + psionw_writel(1, TEOI); + printk("Received and cleared TINT irq %d\n", irq); + break; + } +} + +static void int_unmask(unsigned int irq) +{ + u32 intmr; + intmr = (1 << irq); + psionw_writel(intmr, INTENS); +} + +static struct irqchip int_chip = { + .ack = int_ack, + .mask = int_mask, + .unmask = int_unmask, +}; + +void __init +psionw_init_irq(void) +{ + unsigned int i, ret; + + for (i = 0; i < NR_IRQS; i++) { + if (INT1_IRQS & (1 << i)) { + set_irq_handler(i, do_level_IRQ); + set_irq_chip(i, &int_chip); + set_irq_flags(i, IRQF_VALID | IRQF_PROBE); + } + } + + /* + * Disable interrupts + */ + psionw_writel(0xffffffff, INTENC); + + /* + * Clear down any pending interrupts + */ + psionw_writel(1, MCEOI); + psionw_writel(1, BLEOI); + psionw_writel(1, COEOI); + psionw_writel(1, TC1EOI); + psionw_writel(1, TC2EOI); + psionw_writel(1, RTCEOI); + psionw_writel(1, TEOI); + psionw_writel(1, UMSEOI); + psionw_writel(1, SSCR0); + + //init_FIQ(); +} diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/mm.c linux-2.6.4-rc2/arch/arm/mach-psionw/mm.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/mm.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/mm.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,45 @@ +/* + * linux/arch/arm/mach-psionw/mm.c + * + * Copyright (C) 2000 Tony Lindgren + * + * 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 + +/* + * Logical Physical + */ +static struct map_desc psionw_io_desc[] __initdata = { + {PSIONW_VIRT_BASE, PSIONW_PHYS_BASE, 0x10000, MT_DEVICE}, + {ETNA_V_BASE, ETNA_P_BASE, ETNA_SIZE, MT_DEVICE}, + {CF1_V_BASE, CF1_P_BASE, CF_SIZE, MT_DEVICE}, + {PSION_V_BR, PSION_P_BR, PSION_BR_SIZE, MT_DEVICE}, + {PSION_V_BF, PSION_P_BF, PSION_BF_SIZE, MT_DEVICE}, +}; + +void __init psionw_map_io(void) +{ + iotable_init(psionw_io_desc, ARRAY_SIZE(psionw_io_desc)); +} diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-arch.c linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-arch.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-arch.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-arch.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,121 @@ +/* + * linux/arch/arm/mach-psionw/psionw.c + * + * Copyright (C) 2001 Tony Lindgren + * + * Based on the mach-sa1100 code, some portions of the code + * Copyright (C) 2000 Nicolas Pitre . + * + * 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 + +extern void psionw_init_irq(void); +extern void psionw_map_io(void); + +#define SET_BANK(__nr,__start,__size) \ + mi->bank[__nr].start = (__start), \ + mi->bank[__nr].size = (__size), \ + mi->bank[__nr].node = (((unsigned)(__start) - PHYS_OFFSET) >> 27) + +static void __init +fixup_psionw(struct machine_desc *desc, struct tag *tag, + char **cmdline, struct meminfo *mi) +{ +#if defined(CONFIG_PSIONW_5MX) + SET_BANK(0, 0xc0000000, 8 * 1024 * 1024); + SET_BANK(1, 0xc1000000, 8 * 1024 * 1024); + mi->nr_banks = 2; +#elif defined(CONFIG_PSIONW_5MXPRO24MB) + /* Chris Halls */ + SET_BANK(0, 0xc0000000, 8 * 1024 * 1024); + SET_BANK(1, 0xc1000000, 8 * 1024 * 1024); + SET_BANK(2, 0xd0000000, 4 * 1024 * 1024); + SET_BANK(3, 0xd0800000, 4 * 1024 * 1024); + mi->nr_banks = 4; +#elif defined(CONFIG_PSIONW_5MXPRO32MB) + /* Provided by Thilo Hille */ + SET_BANK(0, 0xc0000000, 8 * 1024 * 1024); + SET_BANK(1, 0xc1000000, 8 * 1024 * 1024); + SET_BANK(2, 0xd0000000, 8 * 1024 * 1024); + SET_BANK(3, 0xd1000000, 8 * 1024 * 1024); + mi->nr_banks = 4; +#elif defined(CONFIG_PSIONW_REVO) + /* This seems to be correct */ + SET_BANK(0, 0xc0000000, 4 * 1024 * 1024); + SET_BANK(1, 0xc0800000, 4 * 1024 * 1024); + mi->nr_banks = 2; +#elif defined(CONFIG_PSIONW_REVOPLUS) + /* Provided by Ilmar Kotte */ + SET_BANK(0, 0xc0000000, 4 * 1024 * 1024); + SET_BANK(1, 0xc0800000, 4 * 1024 * 1024); + SET_BANK(2, 0xd0000000, 4 * 1024 * 1024); + SET_BANK(3, 0xd0800000, 4 * 1024 * 1024); + mi->nr_banks = 4; +#else +#error Unknown machine type! +#endif + +#if 0 + ROOT_DEV = MKDEV(RAMDISK_MAJOR, 0); + + /* Merge the command line options from kernel and boot loader */ + strcat(*cmdline, " "); + strcat(*cmdline, tag->commandline); + strcpy(tag->commandline, *cmdline); +#endif +} + +MACHINE_START(PSIONW, "Psion Windermere NEC ARM710T") +MAINTAINER("Tony Lindgren") +BOOT_MEM(0xc0000000, 0x80000000, 0xff000000) + +/* + * VIDEO() does not poke a hole to bootmem. + * See arch/arm/arm/mm/init.c. + */ +//VIDEO(0xc000d000, 0xc000d000 + (PSION_LCD_W * PSION_LCD_H * 4 / 8)) + +/* Must sync with TEXTADDR */ +BOOT_PARAMS(0xc0048000 - (128 * 1024)) + +FIXUP(fixup_psionw) +MAPIO(psionw_map_io) +INITIRQ(psionw_init_irq) +MACHINE_END + +static int psionw_hw_init(void) +{ + printk("XXX in psionw_hw_init\n"); + + return 0; +} + +__initcall(psionw_hw_init); diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-hardware.c linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-hardware.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-hardware.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-hardware.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,45 @@ +/* + * linux/arch/arm/mach-psionw/hardware.c + * + * Copyright (C) 2000 Deep Blue Solutions Ltd + * + * 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 + +/* + * Shut down all unnecessary hardware + */ +static int +psionw_hw_init(void) +{ + if (psionw_readb(PCDR) & PCDR_UART1) { + psionw_writeb(psionw_readb(PCDR) & ~PCDR_UART1, PCDR); + } + + if (psionw_readb(PCDR) & PCDR_UART2) { + //psionw_writeb(psionw_readb(PCDR) & ~PCDR_UART2, PCDR); + } + + return 0; +} + +__initcall(psionw_hw_init); diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-leds.c linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-leds.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-leds.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-leds.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,74 @@ +/* + * linux/arch/arm/mach-psionw/leds.c + * + * Psionw LED control routines + * + * Copyright (C) 2000 Deep Blue Solutions Ltd + * + * 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 + +static void psionw_leds_event(led_event_t ledevt) +{ + unsigned long flags; + u32 port; + + local_irq_save(flags); + switch(ledevt) { + case led_idle_start: + /* + * Turn off red front led when entering idle. + * The led then shows the current CPU load. + */ + port = psionw_readb(PDDR); + psionw_writeb(port & ~PDDR_SLED, PDDR); + break; + + case led_idle_end: + /* Turn on red front led when not idle*/ + port = psionw_readb(PDDR); + psionw_writeb(port | PDDR_SLED, PDDR); + break; + + case led_timer: + /* FIXME5MX Blink the green top led, does not work */ + port = psionw_readb(PCDR); + //psionw_writeb(port ^ PCDR_PLED, PCDR); + break; + + default: + break; + } + + local_irq_restore(flags); +} + +static int __init leds_init(void) +{ + leds_event = psionw_leds_event; + return 0; +} + +__initcall(leds_init); diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-power.c linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-power.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-power.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-power.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,249 @@ +/* + * arch/arm/mach-psionw/psionw-power.c - Psion power managemenent + * + * Copyright (C) 2002 Tony Lindgren + * + * Contrast restore after sleep fix (C) 2002 by Simon Howard + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +extern void disable_irq(unsigned int irq); +extern void enable_irq(unsigned int irq); +extern void psionw_lcd_powerdown(int lock); +extern void psionw_lcd_powerup(int lock); +extern void etna_powerdown(int lock); +extern void etna_powerup(int lock); +extern void ssi5mx_powerdown(int lock); +extern void ssi5mx_powerup(int lock); + +static int psion_rtc_off; + +/* + * Stops the DC to DC converter + */ +void stop_pump(int lock) +{ + long flags = 0; + + if (lock) + save_flags_cli(flags); + + psionw_writel(PUMP_STOP_VAL,PUMPCON); + psionw_writeb(psionw_readb(PDDR) & ~PDDR_PUMP_PWR1, PDDR); + + if (lock) + restore_flags(flags); +} + +void stop_timer(int lock) +{ + unsigned int cfg; + unsigned long goto_sleep; + long flags = 0; + + if (lock) + save_flags_cli(flags); + + psion_rtc_off = xtime.tv_sec - RTCTIME; + + goto_sleep = jiffies; + do { + disable_irq(IRQ_TC2OI); + } while (time_after(jiffies, goto_sleep + HZ/50)); + cfg = psionw_readl(TC2CTRL); + cfg &= ~TC_ENABLE; + psionw_writel(cfg, TC2CTRL); + + if (lock) + restore_flags(flags); +} + +void start_timer(int lock) +{ + unsigned int cfg; + long flags = 0; + + if (lock) + save_flags_cli(flags); + + cfg = psionw_readl(TC2CTRL); + + /* These bits need to initialized to 0 */ + cfg &= ~TC_BIT2; + cfg &= ~TC_BIT4; + cfg &= ~TC_BIT5; + cfg |= TC_CLKSEL; // 512kHz mode + cfg |= TC_MODE; + cfg |= TC_ENABLE; + + psionw_writel(cfg, TC2CTRL); + psionw_writel(5119, TC2LOAD); /* 512kHz / 100Hz - 1 */ + + psionw_writel(1, TC2EOI); + enable_irq(IRQ_TC2OI); + + if (lock) + restore_flags(flags); + + /* Set the correct time from RTC */ + xtime.tv_sec = RTCTIME; + xtime.tv_sec += psion_rtc_off; +} + +/* + * Puts the Psion into sleep mode until a keyboard, serial, + * touch panel, or RTC interrupt is received. + */ +void psion_off(void) +{ + int adc_clock = 0, rfdiv = 0, rtcdiv1 = 0, rtcdiv2 = 0; + int uart1 = 0, uart2 = 0; + long flags; + + if (psionw_readl(PDDR) & PDDR_PUMP_PWR1) { + + save_flags_cli(flags); + if (psionw_readb(PCDR) & PCDR_UART1) { + uart1 = 1; + //printk("Looks like UART1 is on\n"); + psionw_writeb(psionw_readb(PCDR) & ~PCDR_UART1, PCDR); + } + + if (psionw_readb(PCDR) & PCDR_UART2) { + uart2 = 1; + //printk("Looks like UART2 is on\n"); + psionw_writeb(psionw_readb(PCDR) & ~PCDR_UART2, PCDR); + } + restore_flags(flags); + + /* First we must stop the timer */ + stop_timer(1); + + /* + * We establish a long lock for the whole sleep-wake procedure + */ + save_flags_cli(flags); + + psionw_writeb(psionw_readb(PDDR) & ~PDDR_SLED, PDDR); + psionw_writel(0, KSCAN); + ssi5mx_powerdown(0); /* SSI, saves only about 0.1mA */ + +#ifdef CONFIG_PCMCIA_ETNA + etna_powerdown(0); +#endif + + psionw_lcd_powerdown(0); + stop_pump(0); /* DC to DC, saves about 0.5mA */ + + /* Lower the DRAM refresh to 1 KHz, no real savings */ + rfdiv = psionw_readl(DRAM_CFG) & 0x7f; + psionw_writel(psionw_readl(DRAM_CFG) | 0x7f, DRAM_CFG); + + /* Disable the ADC clock, no real savings */ + adc_clock = (psionw_readl(PWRCNT) >> 8) & 0xff; + psionw_writel(psionw_readl(PWRCNT) | (0xff << 8), PWRCNT); + + cpu_cache_clean_invalidate_all(); + + rtcdiv1 = psionw_readb(PWRSR) & 0x3f; + while(rtcdiv1 == rtcdiv2) { + rtcdiv2 = psionw_readb(PWRSR) & 0x3f; + } + while(rtcdiv2 == rtcdiv1) { + rtcdiv1 = psionw_readb(PWRSR) & 0x3f; + } + + /* Now go to sleep */ + psionw_writel(1, STBY); + __asm__ __volatile__(" + mov r0, r0 + mov r0, r0 + mov r0, r0 + "); + + /* We're back from sleep */ + + /* Restore the ADC clock */ + psionw_writel(psionw_readl(PWRCNT) & ~(0xff << 8), PWRCNT); + psionw_writel(psionw_readl(PWRCNT) | (adc_clock << 8), PWRCNT); + + /* Restore DRAM refresh rate */ + psionw_writel(psionw_readl(DRAM_CFG) & ~0x7f, DRAM_CFG); + psionw_writel(psionw_readl(DRAM_CFG) | rfdiv, DRAM_CFG); + + start_pump(0); + psionw_lcd_powerup(0); + + /* Restore contrast */ + psion_set_contrast(psion_get_contrast(), 1); + +#ifdef CONFIG_PCMCIA_ETNA + etna_powerup(0); +#endif + + ssi5mx_powerup(0); + + /* + * And finally we release the long lock + */ + restore_flags(flags); + start_timer(1); + + save_flags_cli(flags); + if (uart1) + psionw_writeb(psionw_readb(PCDR) | PCDR_UART1, PCDR); + + if (uart2) + psionw_writeb(psionw_readb(PCDR) | PCDR_UART2, PCDR); + restore_flags(flags); + + } else { + /* Just in case the LCD is off */ + psionw_lcd_powerup(1); + } +} + +/* + * Returns the CPU speed + */ +unsigned int psionw_get_cpu_speed(int cpu) +{ + int speed; + speed = (psionw_readl(PWRCNT) & 0x7) >> 2; + if (speed) { + return 36864000; + } else { + return 11432000; + } +} + +/* + * Changes the CPU speed + */ +void psionw_set_cpu_speed(int speed) +{ + int pwrcnt; + long flags = 0; + + save_flags_cli(flags); + cpu_cache_clean_invalidate_all(); + pwrcnt = psionw_readl(PWRCNT); + if (speed) { + pwrcnt |= (1 << 2); + printk("Setting the CPU speed to 36Mhz\n"); + psionw_writel(pwrcnt, PWRCNT); + } else { + pwrcnt &= ~(1 << 2); + printk("Setting the CPU speed to 18Mhz\n"); + psionw_writel(pwrcnt, PWRCNT); + } + restore_flags(flags); +} diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-time.c linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-time.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/psionw-time.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/psionw-time.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,171 @@ +/* + * linux/arch/arm/mach-psionw/time.c + * + * RTC handler for Psion 5mx. + * + * Copyright (C) 2001 Yuji Shinokawa + * + * 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 + +#undef DEBUG_RTC + +/* + * Offset to compatible with EPOC time handling. + * In EPOC, it seems a time for rtc = 0 is "00:00:00 1 Jan 2000 UTC" + * and rtc has signed value. + * + * RTC Time & date + * 0x00000000 = 00:00:00 1 Jan 2000 (London Inner, United Kingdom) + * + * You can get this offset by following perl script; + * #!/usr/bin/perl + * require 'timelocal.pl'; + * $time = timegm (0, 0, 0, 1, 0, 2000); + * print "$time\n"; + */ +#define EPOC_RTC_OFFSET 946684800 + +extern int (*set_rtc) (void); +extern unsigned long (*gettimeoffset) (void); + +unsigned int psionw_read_rtc(void) +{ + int try_count, rtc1, rtc2; + u_int xrtc; + + try_count = 3; + do { + rtc1 = + (psionw_readl(RTCDRU) << 16) | (psionw_readl(RTCDRL) & + 0xffff); + rtc2 = + (psionw_readl(RTCDRU) << 16) | (psionw_readl(RTCDRL) & + 0xffff); + } while (rtc1 != rtc2 && --try_count); + +#if DEBUG_RTC + printk("DEBUG: (psionw_get_rtc) read rtc = %08x\n", rtc1); +#endif + + xrtc = rtc1 + EPOC_RTC_OFFSET; + + return xrtc; +} + +void psionw_write_rtc(u_int xrtc) +{ + int rtc; + + rtc = xrtc - EPOC_RTC_OFFSET; + +#if DEBUG_RTC + printk("DEBUG: (psionw_set_rtc) write rtc = %08x\n", rtc); +#endif + + /* Writing order is important. */ + psionw_writel((rtc >> 16), RTCDRU); + psionw_writel((rtc & 0xffff), RTCDRL); +} + +unsigned int psionw_read_rtc_alarm(void) +{ + int try_count, rtc1, rtc2; + u_int xrtc; + + try_count = 3; + do { + rtc1 = + (psionw_readl(RTCMRU) << 16) | (psionw_readl(RTCMRL) & + 0xffff); + rtc2 = + (psionw_readl(RTCMRU) << 16) | (psionw_readl(RTCMRL) & + 0xffff); + } while (rtc1 != rtc2 && --try_count); + +#if DEBUG_RTC + printk("DEBUG: (psionw_get_rtc_alarm) read rtc alarm = %08x\n", rtc1); +#endif + + xrtc = rtc1 + EPOC_RTC_OFFSET; + + return xrtc; +} + +void psionw_write_rtc_alarm(u_int xrtc) +{ + int rtc; + + rtc = xrtc - EPOC_RTC_OFFSET; + +#if DEBUG_RTC + printk("DEBUG: (psionw_set_rtc_alarm) write rtc alarm = %08x\n", rtc); +#endif + + /* Writing order is important. */ + psionw_writel((rtc >> 16), RTCMRU); + psionw_writel((rtc & 0xffff), RTCMRL); +} + +EXPORT_SYMBOL(psionw_read_rtc); +EXPORT_SYMBOL(psionw_write_rtc); +EXPORT_SYMBOL(psionw_read_rtc_alarm); +EXPORT_SYMBOL(psionw_write_rtc_alarm); + +static int +psionw_set_rtc(void) +{ + u_int xrtc, rtc; + + xrtc = (u_int) xtime.tv_sec; + + psionw_write_rtc(xrtc); + + rtc = psionw_read_rtc(); + if (xrtc > rtc || rtc - xrtc > 1) + return 1; /* Write failed. */ + + return 0; +} + +static unsigned long +psionw_gettimeoffset(void) +{ + return 0; +} + +static int +psionw_rtc_init(void) +{ + /* Set the initial RTC value. */ + xtime.tv_sec = (time_t) psionw_read_rtc(); + + /* Setup hook. */ + set_rtc = psionw_set_rtc; + gettimeoffset = psionw_gettimeoffset; + + return 0; +} + +__initcall(psionw_rtc_init); diff -Nur linux-2.6.4-rc2.org/arch/arm/mach-psionw/serial-debug.c linux-2.6.4-rc2/arch/arm/mach-psionw/serial-debug.c --- linux-2.6.4-rc2.org/arch/arm/mach-psionw/serial-debug.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mach-psionw/serial-debug.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,34 @@ +#include +#include + +#define DEBUG 1 + +/* + * Allows printing debug information over the serial + * line even before the console is initialized. Uses + * the low level debug functions. + * To use in the code, just add: + * + * extern void serial_printk(char *fmt, ...); + * + * For debugging only, do not leave serial_printk + * statements in the code. + * + * Copied from the drivers/video/cyber2000fb.h + */ +#if defined(DEBUG) && defined(CONFIG_DEBUG_LL) +void serial_printk(char *fmt, ...) +{ + extern void printascii(const char *); + char buffer[128]; + va_list ap; + + va_start(ap, fmt); + vsprintf(buffer, fmt, ap); + va_end(ap); + + printascii(buffer); +} +#else +inline void serial_printk(char *fmt, ...) {} +#endif diff -Nur linux-2.6.4-rc2.org/arch/arm/mm/Kconfig linux-2.6.4-rc2/arch/arm/mm/Kconfig --- linux-2.6.4-rc2.org/arch/arm/mm/Kconfig 2004-03-09 13:22:59.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mm/Kconfig 2004-03-09 13:25:56.000000000 +0000 @@ -43,7 +43,7 @@ # ARM720T config CPU_ARM720T bool "Support ARM720T processor" if !ARCH_CLPS711X && !ARCH_L7200 && !ARCH_CDB89712 && ARCH_INTEGRATOR - default y if ARCH_CLPS711X || ARCH_L7200 || ARCH_CDB89712 + default y if ARCH_CLPS711X || ARCH_L7200 || ARCH_CDB89712 || ARCH_PSIONW select CPU_32v4 select CPU_ABRT_LV4T select CPU_CACHE_V4 diff -Nur linux-2.6.4-rc2.org/arch/arm/mm/proc-arm720.S linux-2.6.4-rc2/arch/arm/mm/proc-arm720.S --- linux-2.6.4-rc2.org/arch/arm/mm/proc-arm720.S 2004-03-04 06:16:50.000000000 +0000 +++ linux-2.6.4-rc2/arch/arm/mm/proc-arm720.S 2004-03-09 13:25:56.000000000 +0000 @@ -141,6 +141,21 @@ mov pc, lr @ __ret (head-armv.S) .size __arm710_setup, . - __arm710_setup + .type __arm710_setup, #function +__arm710_setup: mov r0, #0 + mcr p15, 0, r0, c7, c7, 0 @ invalidate caches + mcr p15, 0, r0, c8, c7, 0 @ flush TLB (v4) + mcr p15, 0, r4, c2, c0 @ load page table pointer + mov r0, #0x1f @ Domains 0, 1 = client + mcr p15, 0, r0, c3, c0 @ load domain access register + + mrc p15, 0, r0, c1, c0 @ get control register + bic r0, r0, #0x0e00 @ ..V. ..RS BLDP WCAM + orr r0, r0, #0x0100 @ .... .... .111 .... (old) + orr r0, r0, #0x003d @ .... ..01 ..11 1101 (new) + mov pc, lr @ __ret (head-armv.S) + .size __arm710_setup, . - __arm710_setup + .type __arm720_setup, #function __arm720_setup: mov r0, #0 mcr p15, 0, r0, c7, c7, 0 @ invalidate caches @@ -189,6 +204,11 @@ .asciz "ARM710T" .size cpu_arm710_name, . - cpu_arm710_name + .type cpu_arm710_name, #object +cpu_arm710_name: + .asciz "ARM710T" + .size cpu_arm710_name, . - cpu_arm710_name + .type cpu_arm720_name, #object cpu_arm720_name: .asciz "ARM720T" @@ -218,6 +238,22 @@ .long v4_cache_fns .size __arm710_proc_info, . - __arm710_proc_info + .type __arm710_proc_info, #object +__arm710_proc_info: + .long 0x41807100 @ cpu_val + .long 0xffffff00 @ cpu_mask + .long 0x00000c1e @ section_mmu_flags + b __arm710_setup @ cpu_flush + .long cpu_arch_name @ arch_name + .long cpu_elf_name @ elf_name + .long HWCAP_SWP | HWCAP_HALF | HWCAP_THUMB @ elf_hwcap + .long cpu_arm710_name @ name + .long arm720_processor_functions + .long v4_tlb_fns + .long v4wt_user_fns + .long v4_cache_fns + .size __arm710_proc_info, . - __arm710_proc_info + .type __arm720_proc_info, #object __arm720_proc_info: .long 0x41807200 @ cpu_val diff -Nur linux-2.6.4-rc2.org/drivers/serial/Kconfig linux-2.6.4-rc2/drivers/serial/Kconfig --- linux-2.6.4-rc2.org/drivers/serial/Kconfig 2004-03-09 13:23:00.000000000 +0000 +++ linux-2.6.4-rc2/drivers/serial/Kconfig 2004-03-09 13:25:56.000000000 +0000 @@ -226,6 +226,33 @@ your boot loader (lilo or loadlin) about how to pass options to the kernel at boot time.) +config SERIAL_PSIONW + tristate "Psion Windermere serial port support" + depends on ARCH_PSIONW + select SERIAL_CORE + help + This selects the Psion Windermere serial port. If you have a + Psion 5MX or Revo type palmtop, say Y or M here. If you have + Psion 5 palmtop, say N here. + + If unsure, say N. + +config SERIAL_PSIONW_CONSOLE + bool "Support for console on Psion Windermere serial port" + depends on SERIAL_PSIONW + select SERIAL_CORE_CONSOLE + ---help--- + Say Y here if you wish to use the Psion Windermere UART as the system + console (the system console is the device which receives all kernel + messages and warnings and which allows logins in single user mode). + + Even if you say Y here, the currently visible framebuffer console + (/dev/tty0) will still be used as the system console by default, but + you can alter that using a kernel command line option such as + "console=ttyAM0". (Try "man bootparam" or see the documentation of + your boot loader (lilo or loadlin) about how to pass options to the + kernel at boot time.) + config SERIAL_INTEGRATOR bool depends on SERIAL_AMBA && ARCH_INTEGRATOR diff -Nur linux-2.6.4-rc2.org/drivers/serial/Makefile linux-2.6.4-rc2/drivers/serial/Makefile --- linux-2.6.4-rc2.org/drivers/serial/Makefile 2004-03-04 06:16:46.000000000 +0000 +++ linux-2.6.4-rc2/drivers/serial/Makefile 2004-03-09 13:29:22.000000000 +0000 @@ -19,6 +19,7 @@ obj-$(CONFIG_SERIAL_ANAKIN) += anakin.o obj-$(CONFIG_SERIAL_AMBA) += amba.o obj-$(CONFIG_SERIAL_CLPS711X) += clps711x.o +obj-$(CONFIG_SERIAL_PSIONW) += psionw.o obj-$(CONFIG_SERIAL_PXA) += pxa.o obj-$(CONFIG_SERIAL_SA1100) += sa1100.o obj-$(CONFIG_SERIAL_UART00) += uart00.o diff -Nur linux-2.6.4-rc2.org/drivers/serial/psionw.c linux-2.6.4-rc2/drivers/serial/psionw.c --- linux-2.6.4-rc2.org/drivers/serial/psionw.c 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/drivers/serial/psionw.c 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,765 @@ +/* + * linux/drivers/serial/psionw.c + * + * Copyright (C) 2001 Yuji Shinokawa + * + * Written by Yuji Shinokawa, Irda port support and generic + * updates by Tony Lindgren + * + * Based on the amba.c code, some portions of the code + * Copyright (C) 2000 Deep Blue Solutions Ltd. + * + * 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 + +#if defined(CONFIG_SERIAL_PSIONW_CONSOLE) && defined(CONFIG_MAGIC_SYSRQ) +#define SUPPORT_SYSRQ +#endif + +#include + +#include "psionw.h" + +#define UART_NR 2 + +/* Make the Psion serial port appear as standard serial port */ +#define SERIAL_PSIONW_MAJOR 4 +#define SERIAL_PSIONW_MINOR 64 +#define SERIAL_PSIONW_NAME "ttyS" +#define SERIAL_PSIONW_NR UART_NR +#define SERIAL_PSIONW_VERSION "040102" + +/* + * We wrap our port structure around the generic uart_port. + */ +struct uart_psionw_port { + struct uart_port port; + unsigned int old_status; +}; + +static void psionwuart_stop_tx(struct uart_port *port, unsigned int from_tty) +{ + unsigned int uartintm; + + uartintm = UART_GET_INT_MASK(port); + uartintm &= ~PSIONW_UART_TXINT; + UART_PUT_INT_MASK(port, uartintm); +} + +static void psionwuart_start_tx(struct uart_port *port, unsigned int tty_start) +{ + unsigned int uartintm; + + uartintm = UART_GET_INT_MASK(port); + uartintm |= PSIONW_UART_TXINT; + UART_PUT_INT_MASK(port, uartintm); +} + +static void psionwuart_stop_rx(struct uart_port *port) +{ + unsigned int uartintm; + + uartintm = UART_GET_INT_MASK(port); + uartintm &= ~PSIONW_UART_RXINT; + UART_PUT_INT_MASK(port, uartintm); +} + +static void psionwuart_enable_ms(struct uart_port *port) +{ + unsigned int uartintm; + + uartintm = UART_GET_INT_MASK(port); + uartintm |= PSIONW_UART_MSINT; + UART_PUT_INT_MASK(port, uartintm); +} + +static void +#ifdef SUPPORT_SYSRQ +psionwuart_rx_chars(struct uart_port *port, struct pt_regs *regs) +#else +psionwuart_rx_chars(struct uart_port *port) +#endif +{ + struct tty_struct *tty = port->info->tty; + unsigned int status, ch, rsr, max_count = 256; + + status = UART_GET_FR(port); + while (UART_RX_DATA(status) && max_count--) { + if (tty->flip.count >= TTY_FLIPBUF_SIZE) { + tty->flip.work.func((void *) tty); + if (tty->flip.count >= TTY_FLIPBUF_SIZE) { + printk(KERN_WARNING "TTY_DONT_FLIP set\n"); + return; + } + } + + /* Get the data plus 3 error bits */ + rsr = UART_GET_CHAR(port); + ch = (rsr & 0xff); + + *tty->flip.char_buf_ptr = ch; + *tty->flip.flag_buf_ptr = TTY_NORMAL; + port->icount.rx++; + + /* + * Note that the error handling code is + * out of the main execution path. + * Note also that psionw has the error bits + * in the data register. + */ + //rsr = UART_GET_RSR(port) | UART_DUMMY_RSR_RX; + //rsr |= UART_DUMMY_RSR_RX; + if (rsr & PSIONW_UARTRSR_ANY) { + if (rsr & PSIONW_UARTRSR_PE) { + port->icount.parity++; + } else if (rsr & PSIONW_UARTRSR_FE) { + port->icount.frame++; + } + if (rsr & PSIONW_UARTRSR_OE) { + port->icount.overrun++; + } + rsr &= port->read_status_mask; + if (rsr & PSIONW_UARTRSR_PE) + *tty->flip.flag_buf_ptr = TTY_PARITY; + else if (rsr & PSIONW_UARTRSR_FE) + *tty->flip.flag_buf_ptr = TTY_FRAME; + } + + if (uart_handle_sysrq_char(port, ch, regs)) + goto ignore_char; + + if ((rsr & port->ignore_status_mask) == 0) { + tty->flip.flag_buf_ptr++; + tty->flip.char_buf_ptr++; + tty->flip.count++; + } + if ((rsr & PSIONW_UARTRSR_OE) && + tty->flip.count < TTY_FLIPBUF_SIZE) { + /* + * Overrun is special, since it's reported + * immediately, and doesn't affect the current + * character + */ + *tty->flip.char_buf_ptr++ = 0; + *tty->flip.flag_buf_ptr++ = TTY_OVERRUN; + tty->flip.count++; + } + ignore_char: + status = UART_GET_FR(port); + } + tty_flip_buffer_push(tty); + return; +} + +static void psionwuart_tx_chars(struct uart_port *port) +{ + struct circ_buf *xmit = &port->info->xmit; + int count; + + if (port->x_char) { + UART_PUT_CHAR(port, port->x_char); + port->icount.tx++; + port->x_char = 0; + return; + } + if (uart_circ_empty(xmit) || uart_tx_stopped(port)) { + psionwuart_stop_tx(port, 0); + return; + } + + count = port->fifosize >> 1; + do { + UART_PUT_CHAR(port, xmit->buf[xmit->tail]); + xmit->tail = (xmit->tail + 1) & (UART_XMIT_SIZE - 1); + port->icount.tx++; + if (uart_circ_empty(xmit)) + break; + } while (--count > 0); + + if (uart_circ_chars_pending(xmit) < WAKEUP_CHARS) + uart_write_wakeup(port); + + if (uart_circ_empty(xmit)) + psionwuart_stop_tx(port, 0); +} + +/* + * Only used for the UART1, the Irda port does not support this. + */ +static void psionwuart_modem_status(struct uart_port *port) +{ + struct uart_psionw_port *pp = (struct uart_psionw_port *)port; + unsigned int status, delta; + + status = UART_GET_FR(&pp->port) & PSIONW_UARTFR_MODEM_ANY; + psionw_writel(0, UMSEOI); + + delta = status ^ pp->old_status; + pp->old_status = status; + + if (!delta) + return; + + if (delta & AMBA_UARTFR_DCD) + uart_handle_dcd_change(&pp->port, status & AMBA_UARTFR_DCD); + + if (delta & AMBA_UARTFR_DSR) + pp->port.icount.dsr++; + + if (delta & AMBA_UARTFR_CTS) + uart_handle_cts_change(&pp->port, status & AMBA_UARTFR_CTS); + + wake_up_interruptible(&pp->port.info->delta_msr_wait); +} + +/* + * Serial interrupts + */ +static irqreturn_t psionwuart_int(int irq, void *dev_id, struct pt_regs *regs) +{ + struct uart_port *port = dev_id; + unsigned int status, pass_counter = AMBA_ISR_PASS_LIMIT; + unsigned int psionwuart_int_mask = + (PSIONW_UART_RXINT | PSIONW_UART_TXINT | PSIONW_UART_MSINT); + + /* Irda port does not support modem status */ + if (port->mapbase == PSIONW_UART0_V_BASE) + psionwuart_int_mask = (PSIONW_UART_RXINT | PSIONW_UART_TXINT); + + status = UART_GET_INT_STATUS(port); + do { + if (status & PSIONW_UART_RXINT) { +#ifdef SUPPORT_SYSRQ + psionwuart_rx_chars(port, regs); +#else + psionwuart_rx_chars(port); +#endif + } + if (status & PSIONW_UART_TXINT) { + psionwuart_tx_chars(port); + } + if ((status & PSIONW_UART_MSINT) + && (port->mapbase == PSIONW_UART1_V_BASE)) { + + /* Clear modem status interrupt */ + UART_CLEAR_INT(port, 1); + + psionwuart_modem_status(port); + } + if (pass_counter-- == 0) { + break; + } + status = UART_GET_INT_STATUS(port); + } while (status & psionwuart_int_mask); + + return IRQ_HANDLED; +} + + +static unsigned int psionwuart_tx_empty(struct uart_port *port) +{ + return UART_GET_FR(port) & AMBA_UARTFR_BUSY ? 0 : TIOCSER_TEMT; +} + +static unsigned int psionwuart_get_mctrl(struct uart_port *port) +{ + unsigned int result = 0; + unsigned int status; + + status = UART_GET_FR(port); + if (status & AMBA_UARTFR_DCD) + result |= TIOCM_CAR; + if (status & AMBA_UARTFR_DSR) + result |= TIOCM_DSR; + if (status & AMBA_UARTFR_CTS) + result |= TIOCM_CTS; + + return result; +} + +static void psionwuart_set_mctrl(struct uart_port *port, unsigned int mctrl) +{ + unsigned int pcdr = 0; + + /* NOTE: printk's here will corrupt the terminal */ + if (mctrl & TIOCM_RTS) { + pcdr = psionw_readl(PCDR); + if (port->mapbase == PSIONW_UART0_V_BASE) { + pcdr |= PCDR_UART1; + } else if (port->mapbase == PSIONW_UART1_V_BASE) { + pcdr |= PCDR_UART2; + } + psionw_writel(pcdr, PCDR); + } +} + +static void psionwuart_break_ctl(struct uart_port *port, int break_state) +{ + unsigned long flags; + unsigned int ubrfcr; + + spin_lock_irqsave(&port->lock, flags); + ubrfcr = UART_GET_FCR(port); + if (break_state == -1) + ubrfcr |= PSIONW_UARTFCR_BREAK; + else + ubrfcr &= ~PSIONW_UARTFCR_BREAK; + UART_PUT_FCR(port, ubrfcr); + spin_unlock_irqrestore(&port->lock, flags); +} + +static int psionwuart_startup(struct uart_port *port) +{ + struct uart_psionw_port *pp = (struct uart_psionw_port *)port; + unsigned int cfg; + int retval; + unsigned int uartintm; + + /* + * Allocate the IRQs + */ + retval = request_irq(port->irq, psionwuart_int, 0, "psionwuart", port); + if (retval) + return retval; + + /* + * initialise the old status of the modem signals + */ + pp->old_status = UART_GET_FR(port) & PSIONW_UARTFR_MODEM_ANY; + + /* + * enable the port + */ + UART_PUT_CR(port, PSIONW_UARTCR_UARTEN); + + uartintm = UART_GET_INT_MASK(port); + uartintm |= PSIONW_UART_TXINT | PSIONW_UART_RXINT | PSIONW_UART_MSINT; + UART_PUT_INT_MASK(port, uartintm); + + // Enable the irda for uart0 + if (port->mapbase == PSIONW_UART0_V_BASE) { + cfg = UART_GET_CR(port); + cfg &= ~PSIONW_UARTCR_SIREN; + cfg |= PSIONW_UARTCR_IRTXM; // power friendly tx encoding + UART_PUT_CR(port, cfg); + +#if 0 + /* + * Unblock irda rx while tx (full duplex) + * Won't work with IrTTY because of + * duplicate packets + */ + cfg = readl(port->membase + PSIONW_UARTTR3); + cfg |= PSIONW_UARTTR3_IRUBLOCK; + writel(cfg, port->membase + PSIONW_UARTTR3); +#endif + + } + + return 0; +} + +static void psionwuart_shutdown(struct uart_port *port) +{ + unsigned int pcdr; + unsigned int uartintm; + + /* + * Free the interrupt + */ + free_irq(port->irq, port); /* UART interrupt */ + uartintm = UART_GET_INT_MASK(port); + uartintm &= ~(PSIONW_UART_TXINT | PSIONW_UART_RXINT | PSIONW_UART_MSINT); + UART_PUT_INT_MASK(port, uartintm); + + /* + * disable the port + */ + UART_PUT_CR(port, 0); + + /* + * disable break condition and fifos + */ + UART_PUT_FCR(port, UART_GET_FCR(port) & + ~(PSIONW_UARTFCR_UFIFOEN | PSIONW_UARTFCR_BREAK)); + + /* + * Don't forget to disable port in PCDR + */ + pcdr = psionw_readl(PCDR); + if (port->mapbase == PSIONW_UART0_V_BASE) { + pcdr &= ~PCDR_UART1; + } else if (port->mapbase == PSIONW_UART1_V_BASE) { + pcdr &= ~PCDR_UART2; + } + psionw_writel(pcdr, PCDR); + +} + +static void psionwuart_set_termios(struct uart_port *port, struct termios *termios, + struct termios *old) +{ + unsigned int fcr; + unsigned long flags; + unsigned int baud, quot; + + /* + * Ask the core to calculate the divisor for us. + */ + baud = uart_get_baud_rate(port, termios, old, 0, port->uartclk/16); + quot = uart_get_divisor(port, baud); + + /* byte size and parity */ + switch (termios->c_cflag & CSIZE) { + case CS5: + fcr = PSIONW_UARTFCR_WLEN_5; + break; + case CS6: + fcr = PSIONW_UARTFCR_WLEN_6; + break; + case CS7: + fcr = PSIONW_UARTFCR_WLEN_7; + break; + default: + fcr = PSIONW_UARTFCR_WLEN_8; + break; // CS8 + } + if (termios->c_cflag & CSTOPB) + fcr |= PSIONW_UARTFCR_XSTOP; + if (termios->c_cflag & PARENB) { + fcr |= PSIONW_UARTFCR_PRTEN; + if (!(termios->c_cflag & PARODD)) + fcr |= PSIONW_UARTFCR_EVENPRT; + } + if (port->fifosize > 1) + fcr |= PSIONW_UARTFCR_UFIFOEN; + + spin_lock_irqsave(&port->lock, flags); + + /* + * Update the per-port timeout. + */ + uart_update_timeout(port, termios->c_cflag, baud); + + port->read_status_mask = PSIONW_UARTRSR_OE; + if (termios->c_iflag & INPCK) + port->read_status_mask |= PSIONW_UARTRSR_FE | PSIONW_UARTRSR_PE; + + /* + * Characters to ignore + */ + port->ignore_status_mask = 0; + if (termios->c_iflag & IGNPAR) + port->ignore_status_mask |= + PSIONW_UARTRSR_FE | PSIONW_UARTRSR_PE; + if (termios->c_iflag & IGNBRK) { + /* + * If we're ignoring parity and break indicators, + * ignore overruns too (for real raw support). + */ + if (termios->c_iflag & IGNPAR) + port->ignore_status_mask |= PSIONW_UARTRSR_OE; + } + + /* + * Ignore all characters if CREAD is not set. + */ +// if ((cflag & CREAD) == 0) +// port->ignore_status_mask |= UART_DUMMY_RSR_RX; + + /* first, disable everything */ + /* REVISIT: Do we need to something here? */ + + /* Set baud rate */ + quot -= 1; + UART_PUT_LCR(port, quot); + + /* Set the frame control */ + UART_PUT_FCR(port, fcr); + + spin_unlock_irqrestore(&port->lock, flags); +} + +static const char *psionwuart_type(struct uart_port *port) +{ + return port->type == PORT_PSIONW ? "PSIONW" : NULL; +} + +/* + * Release the memory region(s) being used by 'port' + */ +static void psionwuart_release_port(struct uart_port *port) +{ + release_mem_region(port->mapbase, UART_PORT_SIZE); +} + +/* + * Request the memory region(s) being used by 'port' + */ +static int psionwuart_request_port(struct uart_port *port) +{ + return request_region(port->mapbase, UART_PORT_SIZE, "serial_psionw") + != NULL ? 0 : -EBUSY; +} + +/* + * Configure/autoconfigure the port. + */ +static void psionwuart_config_port(struct uart_port *port, int flags) +{ + if (flags & UART_CONFIG_TYPE) { + port->type = PORT_PSIONW; + psionwuart_request_port(port); + } +} + +/* + * verify the new serial_struct (for TIOCSSERIAL). + */ +static int psionwuart_verify_port(struct uart_port *port, struct serial_struct *ser) +{ + int ret = 0; + if (ser->type != PORT_UNKNOWN && ser->type != PORT_PSIONW) + ret = -EINVAL; + if (ser->irq < 0 || ser->irq >= NR_IRQS) + ret = -EINVAL; + if (ser->baud_base < 9600) + ret = -EINVAL; + return ret; +} + +static struct uart_ops psionw_pops = { + .tx_empty = psionwuart_tx_empty, + .set_mctrl = psionwuart_set_mctrl, + .get_mctrl = psionwuart_get_mctrl, + .stop_tx = psionwuart_stop_tx, + .start_tx = psionwuart_start_tx, + .stop_rx = psionwuart_stop_rx, + .enable_ms = psionwuart_enable_ms, + .break_ctl = psionwuart_break_ctl, + .startup = psionwuart_startup, + .shutdown = psionwuart_shutdown, + .set_termios = psionwuart_set_termios, + .type = psionwuart_type, + .release_port = psionwuart_release_port, + .request_port = psionwuart_request_port, + .config_port = psionwuart_config_port, + .verify_port = psionwuart_verify_port, +}; + +/* + * NOTE: Ports are swapped to have the serial port at ttyS0 and + * the IrDA port at ttyS1 + */ +static struct uart_psionw_port psionw_ports[UART_NR] = { + { + .port = { + .membase = (void *)PSIONW_UART1_V_BASE, + .mapbase = PSIONW_UART1_V_BASE, + .iotype = SERIAL_IO_MEM, + .irq = IRQ_UART2, + .uartclk = 7372800, + .fifosize = 16, + .ops = &psionw_pops, + .flags = ASYNC_BOOT_AUTOCONF, + .line = 0, + }, + }, + { + .port = { + .membase = (void *)PSIONW_UART0_V_BASE, + .mapbase = PSIONW_UART0_V_BASE, + .iotype = SERIAL_IO_MEM, + .irq = IRQ_UART1, + .uartclk = 7372800, + .fifosize = 16, + .ops = &psionw_pops, + .flags = ASYNC_BOOT_AUTOCONF, + .line = 0, + }, + } +}; + +#ifdef CONFIG_SERIAL_PSIONW_CONSOLE + +static void +psionwuart_console_write(struct console *co, const char *s, unsigned int count) +{ + struct uart_port *port = &psionw_ports[co->index].port; + unsigned int status, old_cr; + int i; + + /* + * Ensure that the port is enabled. + */ + old_cr = UART_GET_CR(port); + UART_PUT_CR(port, PSIONW_UARTCR_UARTEN); + + /* + * Now, do each character + */ + for (i = 0; i < count; i++) { + do { + status = UART_GET_FR(port); + } while (status & AMBA_UARTFR_TXFF); + UART_PUT_CHAR(port, s[i]); + if (s[i] == '\n') { + do { + status = UART_GET_FR(port); + } while (status & AMBA_UARTFR_TXFF); + UART_PUT_CHAR(port, '\r'); + } + } + + /* + * Finally, wait for transmitter to become empty + * and restore the uart state. + */ + do { + status = UART_GET_FR(port); + } while (status & AMBA_UARTFR_BUSY); + + UART_PUT_CR(port, old_cr); +} + +static void __init +psionwuart_console_get_options(struct uart_port *port, int *baud, int *parity, + int *bits) +{ + if (UART_GET_CR(port) & PSIONW_UARTCR_UARTEN) { + unsigned int ubrfcr, quot; + + ubrfcr = UART_GET_FCR(port); + + *parity = 'n'; + if (ubrfcr & PSIONW_UARTFCR_PRTEN) { + if (ubrfcr & PSIONW_UARTFCR_EVENPRT) + *parity = 'e'; + else + *parity = 'o'; + } + + if ((ubrfcr & PSIONW_UARTFCR_WRDLEN_MASK) == PSIONW_UARTFCR_WLEN_7) + *bits = 7; + else + *bits = 8; + quot = UART_GET_LCR(port) & PSIONW_UART_BAUD_MASK; + + *baud = port->uartclk / (16 * (quot + 1)); + } +} + +static int __init psionwuart_console_setup(struct console *co, char *options) +{ + struct uart_port *port; + int baud = 115200; + int bits = 8; + int parity = 'n'; + int flow = 'n'; + + /* + * Check whether an invalid uart number has been specified, and + * if so, search for the first available port that does have + * console support. + */ + if (co->index >= UART_NR) + co->index = 0; + port = &psionw_ports[co->index].port; + + if (options) + uart_parse_options(options, &baud, &parity, &bits, &flow); + else + psionwuart_console_get_options(port, &baud, &parity, &bits); + + return uart_set_options(port, co, baud, parity, bits, flow); +} + +extern struct uart_driver psionw_reg; +static struct console psionw_console = { + .name = SERIAL_PSIONW_NAME, + .write = psionwuart_console_write, + .device = uart_console_device, + .setup = psionwuart_console_setup, + .flags = CON_PRINTBUFFER, + .index = -1, + .data = &psionw_reg, +}; + +static int __init psionwuart_console_init(void) +{ + register_console(&psionw_console); + return 0; +} +console_initcall(psionwuart_console_init); + +#define PSIONW_CONSOLE &psionw_console +#else +#define PSIONW_CONSOLE NULL +#endif + +static struct uart_driver psionw_reg = { + .owner = THIS_MODULE, + .driver_name = SERIAL_PSIONW_NAME, + .dev_name = SERIAL_PSIONW_NAME, + .major = SERIAL_PSIONW_MAJOR, + .minor = SERIAL_PSIONW_MINOR, + .nr = UART_NR, + .cons = PSIONW_CONSOLE, +}; + +static int __init psionwuart_init(void) +{ + int ret; + + printk(KERN_INFO "Serial: Psion Windermere driver version: %s\n", + SERIAL_PSIONW_VERSION); + + ret = uart_register_driver(&psionw_reg); + if (ret == 0) { + int i; + + for (i = 0; i < UART_NR; i++) + uart_add_one_port(&psionw_reg, &psionw_ports[i].port); + } + return ret; +} + +static void __exit psionwuart_exit(void) +{ + int i; + + for (i = 0; i < UART_NR; i++) + uart_remove_one_port(&psionw_reg, &psionw_ports[i].port); + + uart_unregister_driver(&psionw_reg); +} + +module_init(psionwuart_init); +module_exit(psionwuart_exit); + +MODULE_AUTHOR("Yuji Shinokawa & Tony Lindgren"); +MODULE_DESCRIPTION("Psion Windermere serial driver"); +MODULE_LICENSE("GPL"); diff -Nur linux-2.6.4-rc2.org/drivers/serial/psionw.h linux-2.6.4-rc2/drivers/serial/psionw.h --- linux-2.6.4-rc2.org/drivers/serial/psionw.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/drivers/serial/psionw.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,93 @@ +/* + * linux/drivers/char/serial_psionw.h + */ + +/* Common with AMBA */ +#define AMBA_ISR_PASS_LIMIT 256 +#define AMBA_UARTIIR 0x1C /* Same as Psion UARTINTR (Read only) */ +#define AMBA_UARTDR 0x00 /* Data read or written from the interface. */ +#define AMBA_UARTRSR 0x04 /* Receive status register (Read only). */ +#define AMBA_UARTFR_TXFF 0x20 /* Same as Psion UTXFF */ +#define AMBA_UARTFR_RXFE 0x10 /* Same as Psion URXFE */ +#define AMBA_UARTFR_BUSY 0x08 /* Same as Psion UBUSY */ +#define AMBA_UARTFR_DCD 0x04 /* Same as Psion DCD */ +#define AMBA_UARTFR_DSR 0x02 /* Same as Psion DSR */ +#define AMBA_UARTFR_CTS 0x01 /* Same as Psion CTS */ +#define AMBA_UARTFR_TMSK (AMBA_UARTFR_TXFF + AMBA_UARTFR_BUSY) + +/* Psion specific port base addresses */ +#define PSIONW_UART0_BASE (0x0600) +#define PSIONW_UART1_BASE (0x0700) +#define PSIONW_UART0_V_BASE (PSIONW_BASE + PSIONW_UART0_BASE) +#define PSIONW_UART1_V_BASE (PSIONW_BASE + PSIONW_UART1_BASE) + +/* Offsets from the base address for each port */ +#define PSIONW_UARTDR (0x00) /* Data register */ +#define PSIONW_UARTFCR (0x04) /* Frame control register */ +#define PSIONW_UARTLCR (0x08) /* Line control register, UBRCR */ +#define PSIONW_UARTCON (0x0c) /* Port control register */ +#define PSIONW_UARTFR (0x10) /* Flag register (Read only) UARTFLG */ +#define PSIONW_UARTINT (0x14) /* Second level interrupt register */ +#define PSIONW_UARTINTM (0x18) /* Interrupt mask register */ +#define PSIONW_UARTINTR (0x1c) /* Interrupt raw status register (Read only) */ +#define PSIONW_UARTTR1 (0x20) /* Test register */ +#define PSIONW_UARTTR2 (0x24) /* Test register */ +#define PSIONW_UARTTR3 (0x28) /* Test register */ + +#define PSIONW_UART_RXINT (1 << 0) /* Rx interrupt */ +#define PSIONW_UART_TXINT (1 << 1) /* Tx interrupt */ +#define PSIONW_UART_MSINT (1 << 2) /* Modem status interrupt */ + +#define PSIONW_UART_BAUD_MASK ((1 << 16) - 1) +#define PSIONW_UARTTR3_IRUBLOCK (1 << 1) /* Unblock irda rx */ + +#define PSIONW_UARTCR_UARTEN (1 << 0) /* Uart enable */ +#define PSIONW_UARTCR_SIREN (1 << 1) /* SiR disable, clear to enable IrDA */ +#define PSIONW_UARTCR_IRTXM (1 << 2) /* IrDA Tx mode bit, set for power savings */ + +#define PSIONW_UARTRSR_FE (1 << 8) /* Frame error */ +#define PSIONW_UARTRSR_PE (1 << 9) /* Parity error */ +#define PSIONW_UARTRSR_OE (1 << 10) /* Overrun error */ + +#define PSIONW_UARTFCR_BREAK (1 << 0) +#define PSIONW_UARTFCR_PRTEN (1 << 1) +#define PSIONW_UARTFCR_EVENPRT (1 << 2) +#define PSIONW_UARTFCR_XSTOP (1 << 3) +#define PSIONW_UARTFCR_UFIFOEN (1 << 4) +#define PSIONW_UARTFCR_WLEN_5 (0 << 5) +#define PSIONW_UARTFCR_WLEN_6 (1 << 5) +#define PSIONW_UARTFCR_WLEN_7 (2 << 5) +#define PSIONW_UARTFCR_WLEN_8 (3 << 5) +#define PSIONW_UARTFCR_WRDLEN_MASK (3 << 5) + +#define UART_PORT_SIZE 64 + +#define PSIONW_UARTFR_MODEM_ANY (AMBA_UARTFR_DCD|AMBA_UARTFR_DSR|AMBA_UARTFR_CTS) + +/* No modem break in Psion */ +#define PSIONW_UARTRSR_ANY (PSIONW_UARTRSR_OE|PSIONW_UARTRSR_PE|PSIONW_UARTRSR_FE) + +#define UART_GET_INT_MASK(p) readb((p)->membase + PSIONW_UARTINTM) +#define UART_PUT_INT_MASK(p,c) writeb((c), (p)->membase + PSIONW_UARTINTM) +#define UART_CLEAR_INT(p,c) writeb((c), (p)->membase + PSIONW_UARTINT) +#define UART_GET_INT_STATUS(p) readb((p)->membase + PSIONW_UARTINTR) + +#define UART_GET_FR(p) readb((p)->membase + PSIONW_UARTFR) + +#define UART_GET_CR(p) readb((p)->membase + PSIONW_UARTCON) +#define UART_PUT_CR(p,c) writeb((c), (p)->membase + PSIONW_UARTCON) + +#define UART_PUT_CHAR(p, c) writeb((c), (p)->membase + AMBA_UARTDR) + +/* Must be readl for error bits */ +#define UART_GET_CHAR(p) readl((p)->membase + AMBA_UARTDR) +#define UART_RX_DATA(s) (((s) & AMBA_UARTFR_RXFE) == 0) +#define UART_TX_READY(s) (((s) & AMBA_UARTFR_TXFF) == 0) +#define UART_TX_EMPTY(p) ((UART_GET_FR(p) & AMBA_UARTFR_TMSK) == 0) +#define UART_GET_RSR(p) readb((p)->membase + AMBA_UARTRSR) + +#define UART_GET_FCR(p) readb((p)->membase + PSIONW_UARTFCR) +#define UART_PUT_FCR(p,c) writeb((c), (p)->membase + PSIONW_UARTFCR) + +#define UART_GET_LCR(p) readl((p)->membase + PSIONW_UARTLCR) +#define UART_PUT_LCR(p,c) writel((c), (p)->membase + PSIONW_UARTLCR) diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/dma.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/dma.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/dma.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/dma.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,28 @@ +/* + * linux/include/asm-arm/arch-psionw/dma.h + * + * Copyright (C) 1997,1998 Russell King + * + * 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 + */ + +#ifndef __ASM_ARCH_DMA_H +#define __ASM_ARCH_DMA_H + +#define MAX_DMA_ADDRESS 0xffffffff + +#define MAX_DMA_CHANNELS 0 + +#endif /* _ASM_ARCH_DMA_H */ diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/hardware.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/hardware.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/hardware.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/hardware.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,39 @@ +/* + * linux/include/asm-arm/arch-psionw/hardware.h + * + * Copyright (C) 2000 Deep Blue Solutions Ltd. + * + * 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 + */ + +#ifndef __ASM_ARCH_HARDWARE_H +#define __ASM_ARCH_HARDWARE_H + +#include + +#define PSIONW_VIRT_BASE 0xdf000000 +#define PSIONW_BASE PSIONW_VIRT_BASE + +#define IO_BASE PSIONW_VIRT_BASE +#define PCIO_BASE IO_BASE + +#ifndef __ASSEMBLY__ +extern unsigned int psionw_read_rtc(void); +extern void psionw_write_rtc(unsigned int xrtc); +extern unsigned int psionw_read_rtc_alarm(void); +extern void psionw_write_rtc_alarm(unsigned int xrtc); +#endif + +#endif diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/ide.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/ide.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/ide.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/ide.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,77 @@ +/* + * linux/include/asm-arm/arch-psionw/ide.h + * + * Copyright (C) 2001 Tony Lindgren + * + * Contains code from the Psion 5 ETNA driver for linux, + * Copyright (C) 1999 Werner Almesberger. + * + * Some code based on the code from sa1100 ide.h + * Copyright (c) 1998 Hugo Fiennes & Nicolas Pitre + * + */ + +#include +#include +#include +#include +#include + +#include <../drivers/pcmcia/psion_etna.h> + +#if !defined(CONFIG_PSIONW_REVO) && !defined(CONFIG_PSIONW_REVOPLUS) + +//#define DISK_RECOVERY_TIME 500 +#define WAIT_DRQ (50*HZ/100) /* 50msec - spec allows up to 20ms */ +#define WAIT_READY (5*HZ) /* 5sec - some laptops are very slow */ +#define WAIT_CMD (10*HZ) /* 10sec - maximum wait for an IRQ to happen */ +//#define CONFIG_BLK_DEV_IDEDMA 1 + +/* + * We need to override the default insw and outsw, as the ETNA + * chip does automatic word to half-word translation. For some + * weird reason the translation only seems to happen for IDE cards. + * See also etna_insw_direct() and etna_outsw_direct(). + */ +#define insw(p,d,l) etna_insw_ide(p,d,l) +#define outsw(p,d,l) etna_outsw_ide(p,d,l) + +static __inline__ void +ide_init_hwif_ports(hw_regs_t * hw, int data_port, int ctrl_port, int *irq) +{ + ide_ioreg_t reg; + int i; + int regincr = 1; + + /* + * The CF card is not powered up on 5mx Pro when + * booting without Epoc. Optionally this is not + * needed for 5mx, as ETNA is already powered. + * Also the cold init resets the Epoc CF config. + */ + etna_cold_init(); + + memset(hw, 0, sizeof (*hw)); + + reg = (ide_ioreg_t) data_port; + + for (i = IDE_DATA_OFFSET; i <= IDE_STATUS_OFFSET; i++) { + hw->io_ports[i] = reg; + reg += regincr; + } + + hw->io_ports[IDE_CONTROL_OFFSET] = (ide_ioreg_t) ctrl_port; +} + +static __inline__ void +ide_init_default_hwifs(void) +{ + hw_regs_t hw; + + /* init the interface */ + ide_init_hwif_ports(&hw, 0x1f0, 0x3f6, NULL); + hw.irq = IRQ_EINT1; + ide_register_hw(&hw, NULL); +} + +#endif /* End ifndef CONFIG_PSIONW_REVO */ diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/io.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/io.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/io.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/io.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,280 @@ +/* + * linux/include/asm-arm/arch-psionw/io.h + * + * Copyright (C) 1999 ARM Limited + * + * 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 + +#ifndef __ASM_ARM_ARCH_IO_H +#define __ASM_ARM_ARCH_IO_H + +#define IO_SPACE_LIMIT 0xffffffff + +#ifdef __io +#undef __io +#endif + +#define __io(a) ((a)) +#define __mem_pci(a) ((unsigned long)(a)) +#define __mem_isa(a) ((unsigned long)(a)) + +#define etna_readb(p) (*(volatile u8 *)(ETNA_V_BASE + (p))) +#define etna_writeb(v,p) (*(volatile u8 *)(ETNA_V_BASE + (p)) = (v)) + +#define etna_readl(p) (*(volatile unsigned int *)(ETNA_V_BASE + (p))) + +/* + * Epoc boot EEPROM reading. Writing would be dangerous, as there is + * no known alternate boot method. + */ +#define psion_br_read(p) (*(volatile u8 *)(PSION_V_BR + (p))) + +/* + * Epoc boot flash reading. Writing would be dangerous, as there is + * no known alternate boot method. + */ +#define psion_bf_read(p) (*(volatile u8 *)(PSION_V_BF + (p))) + +#define DEBUG_MEM_BASE() ({ printk(" 0x%02x-0x%02x", \ + (*(volatile u8 *)(CF1_V_BASE + CF_MEM_BASE + 0x2)), \ + (*(volatile u8 *)(CF1_V_BASE + CF_MEM_BASE + 0x7))); }) + +#define ETNA_GET_MEMBASE(p) (*(volatile u8 *)(CF1_V_BASE + CF_MEM_BASE + (p))) + +/* + * Reads the CompactFlash ready status. Defined at least for SanDisk cards. + * 0x1f7 clears the pending interrupt, while 0x3f6 does not. + */ +#define CF_GET_STAT() (*(volatile u8 *)(CF1_V_BASE + CF_IO8_BASE + 0x1f7)) +#define CF_GET_ALTSTAT() (*(volatile u8 *)(CF1_V_BASE + CF_IO8_BASE + 0x3f6)) +#define CF_CARD_BUSY_BIT (1 << 7) + +#define etna_mem_inb(p) ({ unsigned int __v =__raw_readb(CF1_V_BASE + CF_MEM_BASE + (p)); __v; }) + +#define etna_mem_outb(v,p) __raw_writeb(v, CF1_V_BASE + CF_MEM_BASE + (p)) + +/* + * Most CF cards need an extra delay before a 16-bit write. + * Otherwise we may get tons of ide status=0x58 errors and a + * corrupted disk. The delay time needed depends on the card + * and needs to be somewhere between 300 and 1500. + * + * The problem happens in the following way: + * + * 1. Ide driver issues a write command to the 8-bit command bus + * 2. CompactFlash card sets DRQ etc + * 3. Ide driver waits for not busy and checks for DRQ etc + * 4. Ide driver starts to write the data to the 16-bit bus + * 5. Ide driver checks for a successful write + * 6. CompactFlash card still expects more data, and gives status 0x58 + * 7. Ide driver produces an error, as it expects 0x50 but gets 0x58 + * + * So it looks like the Psion 32-bit to 16-bit translation bus is not + * ready to accept data, and the beginning of the write never makese it + * to the CompactFlash. + */ +static __inline__ void +etna_status_check(void) +{ + +#if 0 + psionw_writeb(psionw_readb(PBDDR) | 0x3, PBDDR); + psionw_writeb(psionw_readb(PBDR) & ~0x3, PBDR); + + psionw_writeb(psionw_readb(PBDDR) & ~0x3, PBDDR); + while ((psionw_readb(PBDR) & 0x3) != 0x3) { + printk("."); + udelay(1); + } + printk("o"); +#endif + udelay(1500); +} + + +/* Boundary alignment for ETNA CF access, not currently used */ +#define PCMCIA_IO16(a) (CF1_V_BASE + 0x0c000000 + ((a) & ~3) + (((a) & 2) << 24) ) + +#ifdef DEBUG_INSW +#define INSW_DEBUG(x...) printk(x) +#else +#define INSW_DEBUG(x...) do { ; } while(0) +#endif + +/* + * Translate a series of N x 16-bit reads into N x 32-bit reads + * + * Used for ide flash cards only. The automatic translation does not work for + * network cards, for example. See also etna_insw_direct. + */ +static __inline__ void +etna_insw_ide(unsigned int port, void *to, int len) +{ + int i; + + for (i = 0; i < len; i++) { + ((unsigned short *) to)[i] = (unsigned short) __raw_readl(CF1_V_BASE + CF_IO16_BASE + port); + //((unsigned short *) to)[i] = (unsigned short) (__raw_readl(PCMCIA_IO16(port)) & 0xffff); + } +} + +/* + * Translate a series of N x 16-bit reads into N/2 x 32-bit reads for ETNA. + * + * Used for non-ide cards. + */ +static __inline__ void +etna_insw_direct(unsigned int port, void *to, int len) +{ + int i, val = 0; + + INSW_DEBUG("\nI <--- Reading %d half words from port 0x%04x\n", len, port); + for (i = 0; i < len; i++) { + if (i & 0x1) { + val = __raw_readl(CF1_V_BASE + CF_IO16_BASE + port); + INSW_DEBUG(" +<-- 0x%08x\n", val); + ((unsigned short *) to)[i - 1] = (unsigned short) (val & 0xffff); + ((unsigned short *) to)[i] = (unsigned short) (val >> 16); + INSW_DEBUG(" +<-- flush to[%d] = 0x%04x to[%d] = 0x%04x\n", i - 1, + ((unsigned short *) to)[i - 1], i, + ((unsigned short *) to)[i]); + } + } + + if (len & 0x1) { + val = __raw_readl(CF1_V_BASE + CF_IO16_BASE + port); + ((unsigned short *) to)[len - 1] = (unsigned short) (val & 0xffff); + INSW_DEBUG(" +<-- flush to[%d] = 0x%04x\n", len - 1, + ((unsigned short *) to)[i - 1]); + } +} + + +#ifdef DEBUG_OUTSW +#define OUTSW_DEBUG(x...) printk(x) +#else +#define OUTSW_DEBUG(x...) do { ; } while(0) +#endif + +/* + * Capures selected IO port values for debugging + */ +static __inline__ void +psion_debug_regb(char *res, char* desc, unsigned int port, int range) +{ + int len, i; + + if (res == NULL) + return; + + len = strlen(res); + + if (len > 0) + res += len; + + sprintf(res, "%s 0x%08x: ", desc, port); + res += strlen(desc) + 13; + + for (i = 0; i < range; i++) { + sprintf(res, "0x%02x ", __raw_readb(port + i)); + res += 5; + } + //sprintf(res, "\n"); + *res = '\n'; + res++; + //sprintf(res, "\0"); + *res = '\0'; + res++; +} + + +/* + * Translate a series of N x 16-bit writes into N x 32-bit writes + * + * Used for ide flash cards only. The automatic translation does not work for + * network cards, for example. See also etna_outsw_direct. + */ +static __inline__ void +etna_outsw_ide(unsigned int port, const void *from, int len) +{ + int i; + + etna_status_check(); + + for (i = 0; i < len; i++) { + __raw_writel(((unsigned short *) from)[i], CF1_V_BASE + CF_IO16_BASE + port); + //__raw_writel(((unsigned short *) from)[i], PCMCIA_IO16(port)); + } +} + +/* + * Translate a series of N x 16-bit writes into N/2 x 32-bit writes for ETNA. + * + * Used for non-ide cards. + */ +static __inline__ void +etna_outsw_direct(unsigned int port, const void *from, int len) +{ + int i, val, prev = 0; + + OUTSW_DEBUG("\nO ---> Writing %d half words to port 0x%04x\n", len, port); + + for (i = 0; i < len; i++) { + val = (unsigned int) ( ((unsigned short *) from)[i] ); + + OUTSW_DEBUG(" +--> 0x%04x\n", val); + + if (i & 0x1) { + __raw_writel( ((val<<16) | prev), CF1_V_BASE+CF_IO16_BASE+port); + OUTSW_DEBUG(" +--> flush 0x%08x\n", ((val<<16) | prev)); + } + prev = val; + } + if (len & 0x1) { + __raw_writel( (val), CF1_V_BASE+CF_IO16_BASE+port); + OUTSW_DEBUG(" +--> flush 0x%08x\n", (val)); + } +} + +#if 0 +#define outb(v,p) __raw_writeb(v, CF1_V_BASE + CF_IO8_BASE + (p)) +#define outw(v,p) __raw_writel(v, CF1_V_BASE + CF_IO16_BASE + (p)) +#define outl(v,p) printk("Error: Unsupported outl called 0x%x\n", (p)) + +#define inb(p) ({ unsigned int __v =__raw_readb(CF1_V_BASE + CF_IO8_BASE + (p)); __v; }) +#define inw(p) ({ unsigned int __v =__raw_readl(CF1_V_BASE + CF_IO16_BASE + (p)) & 0xffff; __v; }) +#define inl(p) printk("Error: Unsupported inl called 0x%x\n", (p)) + +#define outsb(p,d,l) __raw_writesb(CF1_V_BASE + CF_IO8_BASE + p,d,l) +#define outsw(p,d,l) etna_outsw_direct(p,d,l) +#define outsl(p,d,l) printk("Error: Unsupported outsl called 0x%x\n", (p)) + +#define insb(p,d,l) __raw_readsb(CF1_V_BASE + CF_IO8_BASE + p,d,l) +#define insw(p,d,l) etna_insw_direct(p,d,l) +#define insl(p,d,l) printk("Error: Unsupported insl called 0x%x\n", (p)) +#endif + +/* + * ioremap support - validate a PCI memory address, and convert it + * to a physical address for the page tables. + */ +#define iomem_valid_addr(iomem,size) (1) +#define iomem_to_phys(iomem) (iomem) + +#endif diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/irqs.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/irqs.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/irqs.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/irqs.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,56 @@ +/* + * linux/include/asm-arm/arch-psionw/irqs.h + * + * Copyright (C) 2001 Tony Lindgren + * Copyright (C) 2001 Yuji Shinokawa + * + * 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 + */ + +/* + * Interrupts from INTSR1 + */ +#define IRQ_EXTFIQ 0 /* External fiq (Nextfiq pin) */ +#define IRQ_BLINT 1 /* Battery low */ +#define IRQ_WEINT 2 /* Watch dog expired */ +#define IRQ_MCINT 3 /* Media changed */ +#define IRQ_CSINT 4 /* Sound codec */ +#define IRQ_EINT1 5 /* CF card, external 1 (Neint1 pin) */ +#define IRQ_EINT2 6 /* External 2 (Neint2 pin) */ +#define IRQ_EINT3 7 /* Touch panel, external 3 (Neint3 pin) */ +#define IRQ_TC1OI 8 /* TC1 under flow */ +#define IRQ_TC2OI 9 /* TC2 under flow */ +#define IRQ_RTCMI 10 /* RTC compare match */ +#define IRQ_TINT 11 /* 64Hz tick */ +#define IRQ_UART1 12 /* Uart1 */ +#define IRQ_UART2 13 /* Uart2 */ +#define IRQ_LCDINT 14 /* LCD */ +#define IRQ_SSEOTI 15 /* SSI */ + +/* + * Define the irqs in use, and the irqs that need custom handling with + * mask_ack_irq_int1 + */ +#define INT1_IRQS (0x0000ffff) +#define INT1_ACK_IRQS (0x00000f50) + +#define NR_IRQS 16 + +/* First four interrupts are FIQs */ +#define FIQ_START 0 + +/* This is needed by rtc.c */ +#undef RTC_IRQ +#define RTC_IRQ IRQ_RTCMI diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/keyboard.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/keyboard.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/keyboard.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/keyboard.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,43 @@ +/* + * linux/include/asm-arm/arch-psionw/keyboard.h + * + * Copyright (C) 1998 Russell King + * Copyright (C) 2001 Tony Lindgren + * + * 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 + */ + +#define NR_KEYCODES 64 +#if NR_KEYCODES>0x80 +#error Out of bits for scancode +#endif + +#define SYSRQ_KEY 0x100 /* dummy */ + +extern int kbdpsion_translate(unsigned char scancode, unsigned char *keycode_p); +extern void kbdpsion_hw_init(void); +extern unsigned char kbdpsion_sysrq_xlate[NR_KEYCODES]; +extern void psion_arch_handler(unsigned char value, char up_flag); + +#define kbd_setkeycode(x...) (-EINVAL) +#define kbd_getkeycode(x...) (-EINVAL) +#define kbd_translate(sc,kc,rm) kbdpsion_translate(sc,kc) +#define kbd_unexpected_up(kc) (0x80) +#define kbd_enable_irq(x...) do { } while (0) +#define kbd_disable_irq(x...) do { } while (0) +#define kbd_leds(x...) do { } while (0) +#define kbd_init_hw() kbdpsion_hw_init() +#define kbd_sysrq_xlate ((sysrq_pressed = 0), kbdpsion_sysrq_xlate) +#define kbd_arch_handler psion_arch_handler diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/memory.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/memory.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/memory.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/memory.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,113 @@ +/* + * linux/include/asm-arm/arch-psionw/memory.h + * + * Copyright (C) 2001 Tony Lindgren + * + * Based on the sa1100 code, some portions of the code + * Copyright (c) 1999 Nicolas Pitre + * + * 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 + */ + +#ifndef __ASM_ARCH_MMU_H +#define __ASM_ARCH_MMU_H + +/* + * Task size: 3GB + */ +#define TASK_SIZE (0xc0000000UL) +#define TASK_SIZE_26 (0x04000000UL) + +/* + * This decides where the kernel will search for a free chunk of vm + * space during mmap's. + */ +#define TASK_UNMAPPED_BASE (TASK_SIZE / 3) + +/* + * Page offset: 3GB + */ +#define PAGE_OFFSET (0xc0000000UL) +#define PHYS_OFFSET (0xc0000000UL) + +/* + * We take advantage of the fact that physical and virtual address can be the + * same. The NUMA code is handling the large holes that might exist between + * all memory banks. + */ +#define __virt_to_phys__is_a_macro +#define __phys_to_virt__is_a_macro +#define __virt_to_phys(x) (x) +#define __phys_to_virt(x) (x) + +/* + * Virtual view <-> DMA view memory address translations + * virt_to_bus: Used to translate the virtual address to an + * address suitable to be passed to set_dma_addr + * bus_to_virt: Used to convert an address for DMA operations + * to an address that the kernel can use. + * + * On the PSIONW, bus addresses are equivalent to physical addresses. + * FIXME5MX: This may not be needed + */ +#define __virt_to_bus__is_a_macro +#define __bus_to_virt__is_a_macro +#define __virt_to_bus(x) __virt_to_phys(x) +#define __bus_to_virt(x) __phys_to_virt(x) + +#ifdef CONFIG_DISCONTIGMEM + +#define NR_NODES 4 +/* + * Currently defined in arch/arm/mm/mm-sa1100.c + */ + +#define NODE_MAX_MEM_SHIFT 27 +#define NODE_MAX_MEM_SIZE (1<> NODE_MAX_MEM_SHIFT) + +/* + * Given a page frame number, convert it to a node id. + */ +#define PFN_TO_NID(pfn) \ + (((pfn) - PHYS_PFN_OFFSET) >> (NODE_MAX_MEM_SHIFT - PAGE_SHIFT)) + +/* + * Given a kaddr, ADDR_TO_MAPBASE finds the owning node of the memory + * and returns the mem_map of that node. + */ +#define ADDR_TO_MAPBASE(kaddr) \ + NODE_MEM_MAP(KVADDR_TO_NID((unsigned long)(kaddr))) + +#define PFN_TO_MAPBASE(pfn) NODE_MEM_MAP(PFN_TO_NID(pfn)) + +/* + * Given a kaddr, LOCAL_MAR_NR finds the owning node of the memory + * and returns the index corresponding to the appropriate page in the + * node's mem_map. + */ +#define LOCAL_MAP_NR(addr) \ + (((unsigned long)(addr) & (NODE_MAX_MEM_SIZE - 1)) >> PAGE_SHIFT) + +#else +#error "CONFIG_DISCONTIGMEM is needed for Psion" +#endif /* CONFIG_DISCONTIGMEM */ + +#endif diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/param.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/param.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/param.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/param.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,19 @@ +/* + * linux/include/asm-arm/arch-psionw/param.h + * + * Copyright (C) 2000 Deep Blue Solutions Ltd. + * + * 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 + */ diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/psionw-power.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/psionw-power.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/psionw-power.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/psionw-power.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,24 @@ +/* + * linux/include/asm-arm/arch-psionw/psionw-power.h + */ +#include +#include +#include + +/* + * Starts the DC to DC converter + */ +static __inline__ +void start_pump(int lock) +{ + if (psionw_readl(PUMPCON) == PUMP_STOP_VAL) { + psionw_writel(PUMP_RUN_VAL, PUMPCON); + } + + if (!(psionw_readb(PDDR) & PDDR_PUMP_PWR1) || + !(psionw_readb(PDDR) & PDDR_PUMP_PWR2)) { + psionw_writeb(psionw_readb(PDDR) | PDDR_PUMP_PWR1, PDDR); + mdelay(30); + psionw_writeb(psionw_readb(PDDR) | PDDR_PUMP_PWR2, PDDR); + } +} diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/serial.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/serial.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/serial.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/serial.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,39 @@ +/* + * include/asm-arm/arch-sa1100/serial.h + * (C) 1999 Nicolas Pitre + * + * All this is intended to be used with a 16550-like UART on the SA1100's + * PCMCIA bus. It has nothing to do with the SA1100's internal serial ports. + * This is included by serial.c -- serial_sa1100.c makes no use of it. + */ + + +/* + * This assumes you have a 1.8432 MHz clock for your UART. + * + * It'd be nice if someone built a serial card with a 24.576 MHz + * clock, since the 16550A is capable of handling a top speed of 1.5 + * megabits/second; but this requires the faster clock. + */ +#define BASE_BAUD ( 1843200 / 16 ) + +/* Standard COM flags */ +#define STD_COM_FLAGS (ASYNC_BOOT_AUTOCONF | ASYNC_SKIP_TEST) + +#define RS_TABLE_SIZE 4 + + +/* + * Rather empty table... + * Hardwired serial ports should be defined here. + * PCMCIA will fill it dynamically. + */ +#define STD_SERIAL_PORT_DEFNS \ + /* UART CLK PORT IRQ FLAGS */ \ + { 0, BASE_BAUD, 0, 0, STD_COM_FLAGS }, \ + { 0, BASE_BAUD, 0, 0, STD_COM_FLAGS }, \ + { 0, BASE_BAUD, 0, 0, STD_COM_FLAGS }, \ + { 0, BASE_BAUD, 0, 0, STD_COM_FLAGS } + +#define EXTRA_SERIAL_PORT_DEFNS + diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/system.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/system.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/system.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/system.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,43 @@ +/* + * linux/include/asm-arm/arch-psionw/system.h + * + * Copyright (C) 2000 Deep Blue Solutions Ltd + * + * 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 + */ + +#ifndef __ASM_ARCH_SYSTEM_H +#define __ASM_ARCH_SYSTEM_H + +#include +#include +#include + +static void +arch_idle(void) +{ + psionw_writel(1, HALT); + __asm__ __volatile__( + "mov r0, r0\n\ + mov r0, r0 \n\ + mov r0, r0"); +} + +static inline void arch_reset(char mode) +{ + cpu_reset(0); +} + +#endif diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/time.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/time.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/time.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/time.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,78 @@ +/* + * linux/include/asm-arm/arch-psionw/time.h + * + * Copyright (C) 2001 Tony Lindgren + * Copyright (C) 2001 Yuji Shinokawa + * + * Based on the clps711x code, some portions of the code + * Copyright (C) 2000 Deep Blue Solutions Ltd. + * + * 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 + * + * 2001/02/22 Modified for Psion 5MX by Tony Lindgren + * + * 15 Mar 2001 Yuji Shinokawa + * Added to call do_set_rtc() in psionw_timer_interrupt() to adjust RTC. + * Adjust xtime.tv_sec for CONFIG_ARCH_PSIONW. + */ + +#include +#include +#include + +#define RTC_PORT(x) (PSIONW_BASE + x) + +/* + * IRQ handler for the timer + */ +static irqreturn_t +psionw_timer_interrupt(int irq, void *dev_id, struct pt_regs *regs) +{ + do_leds(); + do_timer(regs); + do_set_rtc(); + do_profile(regs); + + return IRQ_HANDLED; +} + +/* + * Set up timer interrupt, and return the current time in seconds. + */ +extern __inline__ void +psionw_setup_timer(void) +{ + unsigned int timer = 0; + timer = psionw_readl(TC2CTRL); + timer |= TC_CLKSEL; /* 512kHz mode */ + timer |= TC_MODE; /* Periodic mode */ + timer |= TC_ENABLE; + psionw_writel(timer, TC2CTRL); + psionw_writel(5119, TC2LOAD); /* 512kHz / 100Hz - 1 */ + timer_irq.handler = psionw_timer_interrupt; +} + +/* + * Set up timer interrupt, and return the current time in seconds. + */ +void __init time_init(void) +{ + psionw_setup_timer(); + timer_irq.handler = psionw_timer_interrupt; + setup_irq(IRQ_TC2OI, &timer_irq); + + xtime.tv_sec = (psionw_readl(RTCDRU) << 16); + xtime.tv_sec |= (psionw_readl(RTCDRL) & 0xffff); +} diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/timex.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/timex.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/timex.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/timex.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,22 @@ +/* + * linux/include/asm-arm/arch-psionw/timex.h + * + * Prospector 720T architecture timex specifications + * + * Copyright (C) 2000 Deep Blue Solutions Ltd. + * + * 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 + */ +#define CLOCK_TICK_RATE 512000 diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/uncompress.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/uncompress.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/uncompress.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/uncompress.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,52 @@ +/* + * linux/include/asm-arm/arch-psionw/uncompress.h + * + * Copyright (C) 2000 Deep Blue Solutions Ltd + * + * 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 + +#undef PSIONW_BASE +#define PSIONW_BASE PSIONW_PHYS_BASE + +#define __raw_readl(p) (*(unsigned long *)(p)) +#define __raw_writel(v,p) (*(unsigned long *)(p) = (v)) + +/* + * This does not append a newline + */ +static void +puts(const char *s) +{ + char c; + + while ((c = *s++) != '\0') { + serial_printf(c); + if (c == '\n') { + serial_printf('\r'); + } + } +} + +/* + * nothing to do + */ +#define arch_decomp_setup() + +#define arch_decomp_wdog() diff -Nur linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/vmalloc.h linux-2.6.4-rc2/include/asm-arm/arch-psionw/vmalloc.h --- linux-2.6.4-rc2.org/include/asm-arm/arch-psionw/vmalloc.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/arch-psionw/vmalloc.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,36 @@ +/* + * linux/include/asm-arm/arch-psionw/vmalloc.h + * + * Copyright (C) 2000 Deep Blue Solutions Ltd. + * + * 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 + */ + +/* + * Just any arbitrary offset to the start of the vmalloc VM area: the + * current 8MB value just means that there will be a 8MB "hole" after the + * physical memory until the kernel virtual memory starts. That means that + * any out-of-bounds memory accesses will hopefully be caught. + * The vmalloc() routines leaves a hole of 4kB between each vmalloced + * area for the same reason. ;) + */ +#define VMALLOC_OFFSET (8*1024*1024) +#define VMALLOC_START (((unsigned long)high_memory + VMALLOC_OFFSET) & \ + ~(VMALLOC_OFFSET-1)) +#define VMALLOC_VMADDR(x) ((unsigned long)(x)) +#define VMALLOC_END (PAGE_OFFSET + 0x1c000000) + +#define MODULE_START (PAGE_OFFSET - 16*1048576) +#define MODULE_END (PAGE_OFFSET) diff -Nur linux-2.6.4-rc2.org/include/asm-arm/hardware/psionw.h linux-2.6.4-rc2/include/asm-arm/hardware/psionw.h --- linux-2.6.4-rc2.org/include/asm-arm/hardware/psionw.h 1970-01-01 00:00:00.000000000 +0000 +++ linux-2.6.4-rc2/include/asm-arm/hardware/psionw.h 2004-03-09 13:25:56.000000000 +0000 @@ -0,0 +1,402 @@ +/* + * linux/include/asm-arm/hardware/psionw.h + * + * This file contains the hardware definitions of the PSIONW internal + * registers. + * + * Copyright (C) 2001 Tony Lindgren + * Copyright (C) 2001 Yuji Shinokawa + * + * 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 + * + * ************************ NOTE FOR DEVELOPERS *************************** + * + * Please see also the "Windermere Software Interface Specification" + * PDF file. (Series_5mx_specs.pdf) + * + * This file is not publicly available, but is available for Linux + * developers without a NDA. Thank you Psion! + * + * Please contact the PsiLinux mailing list at: + * + * linux-7110-psion@lists.sourceforge.net + * + * to get a copy of this file. + * + * ************************************************************************ + */ + +#ifndef __ASM_HARDWARE_PSIONW_H +#define __ASM_HARDWARE_PSIONW_H + +#define PSIONW_PHYS_BASE (0x80000000) + +#ifndef __ASSEMBLY__ +#define psionw_readb(off) __raw_readb(PSIONW_BASE + (off)) +#define psionw_readl(off) __raw_readl(PSIONW_BASE + (off)) +#define psionw_writeb(val,off) __raw_writeb(val, PSIONW_BASE + (off)) +#define psionw_writel(val,off) __raw_writel(val, PSIONW_BASE + (off)) +#endif + +/* + * LCD Controller + */ + +#define PSION_HSW (0x02 << 10) /* Horiz sync pulse width */ +#define PSION_HFP (0x01 << 16) /* Horiz front porch */ +#define PSION_HBP (0x01 << 24) /* Horiz back porch */ + +#define PSION_VSW (0x02 << 10) /* Vert sync pulse width */ +#define PSION_VFP (0x01 << 16) /* Vert front porch */ +#define PSION_VBP (0x01 << 24) /* Vert back porch */ + +#if defined(CONFIG_PSIONW_REVO) || defined(CONFIG_PSIONW_REVOPLUS) +#define PSION_LCD_W 480 /* LCD width */ +#define PSION_LCD_H 160 /* LCD heigth */ +#define PSION_ACB (0xc << 8) /* AC-bias frequency */ +#else +#define PSION_LCD_W 640 /* LCD width */ +#define PSION_LCD_H 240 /* LCD height */ +#define PSION_ACB (0xb << 8) /* AC-bias frequency */ +#endif + +#define PSION_LCD_OFF 0xd000 /* LCD memory start offset */ +#define LCD_PAL_SIZE (0x20) /* LCD palette size */ +#define LCD_BUF_SIZE (PSION_LCD_W*PSION_LCD_H*4/8) /* LCD buffer size */ +#define LCD_MEM_SIZE (LCD_PAL_SIZE + LCD_BUF_SIZE) /* LCD memory size */ +#define LCD_MEM_START PAGE_OFFSET + PSION_LCD_OFF /* LCD memory start offset */ +#define LCD_PAL_START LCD_MEM_START /* LCD palette start offset */ +#define LCD_BUF_START LCD_PAL_START + LCD_PAL_SIZE /* LCD buffer start offset */ + +#define LCDCTL (0x0200) +#define LCDCTL_EN (1 << 0) +#define LCDCTL_BW (1 << 1) +#define LCDCTL_DP (1 << 2) +#define LCDCTL_DONE (1 << 3) +#define LCDCTL_NEXT (1 << 4) +#define LCDCTL_ERR (1 << 5) +#define LCDCTL_TFT (1 << 7) +#define LCDCTL_M8B (1 << 8) + +#define LCDST (0x0204) +#define LCDST_NEXT (1 << 1) +#define LCDST_BER (1 << 2) +#define LCDST_ABC (1 << 3) +#define LCDST_FUF (1 << 5) + +#define LCD_DBAR1 (0x0210) + +#define LCDT0 (0x0220) +#define LCDT1 (0x0224) +#define LCDT2 (0x0228) +#define LCDT2_IVS (1 << 20) +#define LCDT2_IHS (1 << 21) +#define LCDT2_IPC (1 << 22) +#define LCDT2_IEO (1 << 23) + +#define LCD_DEF_CMASK (0x10) /* Default value for the LCD contrast */ + +/* + * ETNA PCMCIA Controller + */ +#if defined(CONFIG_PSIONW_5MXPRO24MB) || defined(CONFIG_PSIONW_5MXPRO32MB) +#define ETNA_P_BASE 0x50000000 /* ETNA controller physical base */ +#else +#define ETNA_P_BASE 0x20000000 /* ETNA controller physical base */ +#endif + +#define ETNA_V_BASE 0xde000000 /* ETNA controller virtual base */ +#define ETNA_SIZE 0x00100000 /* ETNA controller size */ + +#define ETNA_UNKNOWN_0 0x0 /* Seems to be always 0x0f */ +#define ETNA_UNKNONW_1 0x1 /* Seems to be always 0x00 */ +#define ETNA_UNKNOWN_2 0x2 /* Seems to be always 0x02 */ +#define ETNA_UNKNOWN_3 0x3 /* Seems to be always 0x00 */ +#define ETNA_UNKNOWN_4 0x4 /* Seems to be always 0x00 */ +#define ETNA_UNKNOWN_5 0x5 /* Seems to be always 0x00 */ +#define ETNA_INT_STATUS 0x6 /* ETNA interrupt Status */ +#define ETNA_INT_MASK 0x7 /* ETNA interrupt Mask */ +#define ETNA_INT_CLEAR 0x8 /* ETNA interrupt Clear */ +#define ETNA_SKT_STATUS 0x9 /* Socket status ??? */ +#define ETNA_SKT_CFG 0xa /* Socket config ??? */ +#define ETNA_SKT_CTRL 0xb /* Enable socket ??? */ +#define ETNA_WAKE_1 0xc /* Socket wake up; Usually 0x88, goes to 0x00 after STBY */ +#define ETNA_SKT_ACTIVE 0xd /* Socket active ??? */ +#define ETNA_UNKNOWN_E 0xe /* Seems to be always 0x00 */ +#define ETNA_WAKE_2 0xf /* Socket wake up; Usually 0x10, goes to 0x00 after STBY */ + +#define SKT_BUSY (1 << 0) /* ETNA socket busy */ +#define SKT_NOT_READY (1 << 1) /* ETNA socket not ready */ +#define SKT_CARD_OUT (1 << 2) /* ETNA card out */ + +#define ETNA_CARD_INT (1 << 0) /* ETNA card interrupt */ +#define ETNA_BUSY_INT (1 << 2) /* ETNA socket interrupt */ +#define ETNA_SOCK_INT1 (1 << 4) +#define ETNA_SOCK_INT2 (1 << 5) + +#define CARD_INT_MASK 0x05 /* Normal card interrupt = ETNA_CARD_INT | ETNA_BUSY_INT */ +#define ETNA_CLEAR_MASK 0xff /* Clear ETNA interrupt */ +#define ETNA_CF_IRQ 0x01 /* Enable ETNA Interrupt */ + +#if defined(CONFIG_PSIONW_5MXPRO24MB) || defined(CONFIG_PSIONW_5MXPRO32MB) +#define CF1_P_BASE 0x30000000 /* PCMCIA physical base */ +#else +#define CF1_P_BASE 0x40000000 /* PCMCIA physical base */ +#endif + +#define CF1_V_BASE 0xe0000000 /* PCMCIA virtual base */ +#define CF_SIZE 0x10000000 /* 4 areas of 64MB each */ +#define CF_ATTR_BASE 0x00000000 /* This is needed, or it won't work!!! */ +#define CF_MEM_BASE 0x04000000 /* Address bit 26 set */ +#define CF_IO8_BASE 0x08000000 /* Address bit 27 set */ +#define CF_IO16_BASE 0x0c000000 /* Address bits 26 & 27 set */ + +#define CF_CFG_REG 0x003c +#define CF_CFG_VAL 0x00730069 /* Epoc value from e 0x5801603c in ArLo */ +#define CF_CUR_CFG 0x200 + +/* + * Boot EEPROM used by Epoc (Verified on 5mx Pro 32MB only) + */ +#define PSION_P_BR 0x00000000 +#define PSION_V_BR 0xde200000 +#define PSION_BR_SIZE (1024*128) + +/* + * Boot Flash used by Epoc, not used in 5mx Pro (Not verified on 5mx) + */ +#define PSION_P_BF 0x10000000 +#define PSION_V_BF 0xde300000 +#define PSION_BF_SIZE (1024*1024*2) + +/* + * GPIO/KBD Registers + */ +#define PADR (0x0e00) +#define PBDR (0x0e04) +#define PCDR (0x0e08) +#define PDDR (0x0e0c) +#define PADDR (0x0e10) +#define PBDDR (0x0e14) +#define PCDDR (0x0e18) +#define PDDDR (0x0e1c) +#define PEDR (0x0e20) +#define PEDDR (0x0e24) +#define KSCAN (0x0e28) +#define LCDMUX (0x0e2c) + +/* + * Port A, Keyboard + */ +#define PADR_0 (1 << 0) +#define PADR_1 (1 << 1) +#define PADR_2 (1 << 2) +#define PADR_3 (1 << 3) +#define PADR_4 (1 << 4) +#define PADR_5 (1 << 5) +#define PADR_6 (1 << 6) +#define PADR_7 (1 << 7) + +/* + * Port B, Data copied from Psion 5 code + * + * +--7--+--6--+--5--+--4--+--3--+--2--+--1--+--0--+ + * |VPCEN|OPEN |VLDD3|VLDD2|VLDD1|VLDD0|EECLK|EECS | + * | out |in/ou|in/ou|in/ou|in/ou|in/ou| out | out | + * +-----+-----+-----+-----+-----+-----+-----+-----+ + */ +#define PBDR_EECS (1 << 0) /* Ext clock?, NOT TESTED */ +#define PBDR_EECLK (1 << 1) /* Ext clock?, NOT TESTED */ +#define PBDR_VLDD0 (1 << 2) /* LCD contrast reg0 */ +#define PBDR_VLDD1 (1 << 3) /* LCD contrast reg1 */ +#define PBDR_VLDD2 (1 << 4) /* LCD contrast reg2 */ +#define PBDR_VLDD3 (1 << 5) /* LCD contrast reg3 */ +#define PBDR_OPEN (1 << 6) /* Case open/closed */ +#define PBDR_VPCEN (1 << 7) /* ETNA CF power disabled */ + +#define PBDR_VLD_MASK 0x3c /* LCD contrast mask */ +#define PBDR_VLD_SHIFT 2 /* LCD contrast shift */ + + +/* + * Port C, Data copied from Psion 5 code + * + * +--7--+--6--+--5--+--4--+--3--+--2--+--1--+--0--+ + * |ADICT|BBLD |UART1|LIGHT|UART2|PLED | DTR | RTS | + * | out | out | out | out | out | out | out | out | + * +-----+-----+-----+-----+-----+-----+-----+-----+ + */ +#define PCDR_RTS (1 << 0) /* RS-232 RTS, NOT TESTED */ +#define PCDR_DTR (1 << 1) /* RS-232 DTR toggle, NOT TESTED */ +#define PCDR_PLED (1 << 2) /* Disable power LED, NOT TESTED */ +#define PCDR_UART2 (1 << 3) /* Enable UART1 */ +#define PCDR_LIGHT (1 << 4) /* LCD backlight */ +#define PCDR_UART1 (1 << 5) /* Enable UART0 */ +#define PCDR_ADICT (1 << 6) /* Set audio to dictaphone */ + +/* + * Port D, Data copied from Psion 5 code + * + * +--7--+--6--+--5--+--4--+--3--+--2--+--1--+--0--+ + * | X2 |LCDLR|TRIX2|SLED |DORSW| LCD |AMPEN|CDEN | + * |in/ou| out | n/a | out | out | out | out | out | + * +-----+-----+-----+-----+-----+-----+-----+-----+ + */ +#define PDDR_CDE (1 << 0) /* Codec enable, NOT TESTED */ +#define PDDR_AMPEN (1 << 1) /* Audio amp enable, NOT TESTED */ +#define PDDR_LCD_PWR (1 << 2) /* LCD power */ +#define PDDR_ETNA_DOOR (1 << 3) /* ETNA door switch power, NOT TESTED */ +#define PDDR_SLED (1 << 4) /* Front status LED on */ +#define PDDR_PUMP_PWR2 (1 << 5) /* ETNA and LCD need this */ +#define PDDR_PUMP_PWR1 (1 << 6) /* DC to DC converter power */ +#define PDDR_ETNA_ERR (1 << 7) /* ETNA access error */ + +/* + * Port E, Data copied from Psion 5 code + * + * +--3--+--2--+--1--+--0--+ + * |Y1EN |X1EN |Y2EN |X2EN | + * | out | out | out | out | + * +-----+-----+-----+-----+ + */ +#define PEDR_X2EN (1 << 0) /* Digitiser X2 drive, NOT TESTED */ +#define PEDR_Y2EN (1 << 1) /* Digitiser Y2 drive, NOT TESTED */ +#define PEDR_X1EN (1 << 2) /* Digitiser X1 drive, NOT TESTED */ +#define PEDR_Y1EN (1 << 3) /* Digitiser Y1 drive, NOT TESTED */ + +#define MEMCFG1 (0x0000) /* Memory configuration */ +#define MEMCFG2 (0x0004) /* Memory configuration */ +#define DRAM_CFG (0x0100) /* DRAM control register */ + +/* + * State and Power Controller + */ +#define PWRSR (0x0400) /* Power control state */ +#define PWRCNT (0x0404) /* Clock/debug control status */ +#define HALT (0x0408) /* Enter idle mode */ +#define STBY (0x040c) /* Enter standby mode */ + +#define BLEOI (0x0410) /* Clear battery low interrupt, write only */ +#define MCEOI (0x0414) /* Clear media changed interrupt, write only */ +#define TEOI (0x0418) /* Clear tick interrupt, write only */ +#define STFCLR (0x041c) /* Clear NBFLG, RSTFLG, PFFLG, CLDFLG, write only */ +#define E2EOI (0x0420) /* Clear NEINT2, write only */ + +#define TC1EOI (0x0c0c) /* Clear timer 1 interrupt, write only */ +#define TC2EOI (0x0c2c) /* Clear timer 2 interrupt, write only */ +#define RTCEOI (0x0d10) /* Clear RTC interrupt, write only */ +#define UMSEOI (0x0714) /* Clear UART 2 modem status interrupt, write only */ + +/* + * PWRSR Flags + */ +#define RTCDIV (1 << 0) /* 6 bits, 64Hz ticks since the increment of RTC, 32 counts ahead of RTC */ +#define MCDR (1 << 6) /* Media changed direct read */ +#define DCDET (1 << 7) /* Power from the mains adapter */ +#define WUDR (1 << 8) /* Wake up direct read */ +#define WUON (1 << 9) /* Wake up out of stanby, clear at HALT STDBY or STFCLR */ +#define NBFLG (1 << 10) /* New battery flag, clear at STFCLR */ +#define RSTFLG (1 << 11) /* Reset flag, clear at STFCLR */ +#define PFFLG (1 << 12) /* Power fail flag, clear at STFCLR */ +#define CLDFLG (1 << 13) /* Cold start flag, clear at STFCLR */ +#define VERID (1 << 14) /* Windermere version id, two bits, 0 for first version */ + +/* + * PWRCNT Flags + */ +#define EXCKEN (1 << 0) /* External expansion clock enable, 1=on, 0=on only for bit 7 memcfg */ +#define WAKEDIR (1 << 1) /* Disable waking up from STANDBY mode via the wakeup input */ +#define CLKFLG (1 << 2) /* Clock speed, 1=36MHz, 0=18MHz */ +#define ADCCLK (1 << 3) /* 8 bit to set the clock divider for ADCCLK output clock */ + +/* + * Interrupts + */ +#define INTSR (0x0500) /* Interrupt status after masking, read-only */ +#define INTRSR (0x0504) /* Interrupt status before masking, read-only */ +#define INTENS (0x0508) /* Interrupt enable, read-write */ +#define INTENC (0x050c) /* Interrupt disable, write-only */ +#define INTTEST1 (0x0514) /* Interrupt test register */ +#define INTTEST2 (0x0518) /* Interrupt test register */ + +#define INT_EXTFIQ (1 << 0) +#define INT_BLINT (1 << 1) +#define INT_WEINT (1 << 2) +#define INT_MCINT (1 << 3) +#define INT_CSINT (1 << 4) +#define INT_EINT1 (1 << 5) /* PCMCIA/external interrupt 1 */ +#define INT_EINT2 (1 << 6) +#define INT_EINT3 (1 << 7) +#define INT_TC1OI (1 << 8) +#define INT_TC2OI (1 << 9) +#define INT_RTCMI (1 << 10) +#define INT_TINT (1 << 11) +#define INT_UART1 (1 << 12) +#define INT_UART2 (1 << 13) +#define INT_LCDINT (1 << 14) +#define INT_SSEOTI (1 << 15) + +/* + * Clock + */ +#define RTCTIME ((psionw_readl(RTCDRU) << 16) | (psionw_readl(RTCDRL) & 0xffff)) + +#define TC1LOAD (0x0c00) +#define TC1VAL (0x0c04) +#define TC1CTRL (0x0c08) + +#define TC2LOAD (0x0c20) +#define TC2VAL (0x0c24) +#define TC2CTRL (0x0c28) +#define TC_BIT2 (1 << 2) +#define TC_CLKSEL (1 << 3) +#define TC_BIT4 (1 << 4) +#define TC_BIT5 (1 << 5) +#define TC_MODE (1 << 6) +#define TC_ENABLE (1 << 7) +#define BZCONT (0x0c40) +#define BZ_BZTOG (1 << 0) +#define BZ_BZMOD (1 << 1) + +#define RTCDRL (0x0d00) /* RTC data register low */ +#define RTCDRU (0x0d04) /* RTC data register high */ +#define RTCMRL (0x0d08) /* RTC match register low */ +#define RTCMRU (0x0d0c) /* RTC match register high */ + +/* + * SSI - Synchronous Serial Interface + */ +#define SSCR0 (0x0b00) /* Serial control register 0 */ +#define SSCR1 (0x0b04) /* Serial control register 1 */ +#define SSDR (0x0b0c) /* Data register */ +#define SSSR (0x0b14) /* Status register */ + +/* + * DC to DC Converter + */ +#define PUMPCON (0x0900) +#define PUMP_RUN_VAL (0xbbb) +#define PUMP_STOP_VAL (0x0) + +/* + * Codec + */ +#define CODR (0x0a00) /* Codec data register */ +#define CONFG (0x0a04) /* Codec config register */ +#define COLFG (0x0a08) /* Codec flag register */ +#define COEOI (0x0a0c) /* Codec end of interrupt, write only */ +#define COTEST (0x0a10) /* Codec test register */ + +#endif /* __ASM_HARDWARE_PSIONW_H */ diff -Nur linux-2.6.4-rc2.org/include/linux/serial_core.h linux-2.6.4-rc2/include/linux/serial_core.h --- linux-2.6.4-rc2.org/include/linux/serial_core.h 2004-03-09 13:23:01.000000000 +0000 +++ linux-2.6.4-rc2/include/linux/serial_core.h 2004-03-09 13:25:56.000000000 +0000 @@ -52,6 +52,7 @@ #define PORT_SA1100 34 #define PORT_UART00 35 #define PORT_21285 37 +#define PORT_PSIONW 38 /* Sparc type numbers. */ #define PORT_SUNZILOG 38