]> nv-tegra.nvidia Code Review - linux-2.6.git/commitdiff
Merge git://git.kernel.org/pub/scm/linux/kernel/git/paulus/powerpc
authorLinus Torvalds <torvalds@g5.osdl.org>
Thu, 29 Jun 2006 18:32:34 +0000 (11:32 -0700)
committerLinus Torvalds <torvalds@g5.osdl.org>
Thu, 29 Jun 2006 18:32:34 +0000 (11:32 -0700)
* git://git.kernel.org/pub/scm/linux/kernel/git/paulus/powerpc: (43 commits)
  [POWERPC] Use little-endian bit from firmware ibm,pa-features property
  [POWERPC] Make sure smp_processor_id works very early in boot
  [POWERPC] U4 DART improvements
  [POWERPC] todc: add support for Time-Of-Day-Clock
  [POWERPC] Make lparcfg.c work when both iseries and pseries are selected
  [POWERPC] Fix idr locking in init_new_context
  [POWERPC] mpc7448hpc2 (taiga) board config file
  [POWERPC] Add tsi108 pci and platform device data register function
  [POWERPC] Add general support for mpc7448hpc2 (Taiga) platform
  [POWERPC] Correct the MAX_CONTEXT definition
  powerpc: minor cleanups for mpc86xx
  [POWERPC] Make sure we select CONFIG_NEW_LEDS if ADB_PMU_LED is set
  [POWERPC] Simplify the code defining the 64-bit CPU features
  [POWERPC] powerpc: kconfig warning fix
  [POWERPC] Consolidate some of kernel/misc*.S
  [POWERPC] Remove unused function call_with_mmu_off
  [POWERPC] update asm-powerpc/time.h
  [POWERPC] Clean up it_lp_queue.h
  [POWERPC] Skip the "copy down" of the kernel if it is already at zero.
  [POWERPC] Add the use of the firmware soft-reset-nmi to kdump.
  ...

77 files changed:
arch/powerpc/Kconfig
arch/powerpc/Kconfig.debug
arch/powerpc/configs/cell_defconfig
arch/powerpc/configs/mpc7448_hpc2_defconfig [new file with mode: 0644]
arch/powerpc/kernel/Makefile
arch/powerpc/kernel/cpu_setup_power4.S
arch/powerpc/kernel/cputable.c
arch/powerpc/kernel/crash.c
arch/powerpc/kernel/head_64.S
arch/powerpc/kernel/iommu.c
arch/powerpc/kernel/legacy_serial.c
arch/powerpc/kernel/lparcfg.c
arch/powerpc/kernel/machine_kexec_64.c
arch/powerpc/kernel/misc.S [new file with mode: 0644]
arch/powerpc/kernel/misc_32.S
arch/powerpc/kernel/misc_64.S
arch/powerpc/kernel/paca.c
arch/powerpc/kernel/prom.c
arch/powerpc/kernel/rtas.c
arch/powerpc/kernel/setup_64.c
arch/powerpc/kernel/traps.c
arch/powerpc/kernel/udbg.c
arch/powerpc/mm/hash_native_64.c
arch/powerpc/mm/hash_utils_64.c
arch/powerpc/mm/mmu_context_64.c
arch/powerpc/platforms/86xx/Kconfig
arch/powerpc/platforms/86xx/Makefile
arch/powerpc/platforms/86xx/mpc8641_hpcn.h
arch/powerpc/platforms/86xx/mpc86xx.h
arch/powerpc/platforms/86xx/mpc86xx_hpcn.c
arch/powerpc/platforms/86xx/mpc86xx_smp.c
arch/powerpc/platforms/86xx/pci.c
arch/powerpc/platforms/Makefile
arch/powerpc/platforms/cell/Kconfig
arch/powerpc/platforms/cell/setup.c
arch/powerpc/platforms/cell/spu_base.c
arch/powerpc/platforms/cell/spufs/file.c
arch/powerpc/platforms/cell/spufs/switch.c
arch/powerpc/platforms/embedded6xx/Kconfig
arch/powerpc/platforms/embedded6xx/Makefile [new file with mode: 0644]
arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.c [new file with mode: 0644]
arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.h [new file with mode: 0644]
arch/powerpc/platforms/iseries/dt.c
arch/powerpc/platforms/iseries/htab.c
arch/powerpc/platforms/iseries/lpevents.c
arch/powerpc/platforms/iseries/proc.c
arch/powerpc/platforms/iseries/setup.c
arch/powerpc/platforms/maple/setup.c
arch/powerpc/platforms/powermac/setup.c
arch/powerpc/platforms/pseries/iommu.c
arch/powerpc/platforms/pseries/lpar.c
arch/powerpc/platforms/pseries/setup.c
arch/powerpc/sysdev/Makefile
arch/powerpc/sysdev/dart.h
arch/powerpc/sysdev/dart_iommu.c
arch/powerpc/sysdev/todc.c [new file with mode: 0644]
arch/powerpc/sysdev/tsi108_dev.c [new file with mode: 0644]
arch/powerpc/sysdev/tsi108_pci.c [new file with mode: 0644]
drivers/ide/Kconfig
drivers/ide/ppc/pmac.c
drivers/macintosh/Kconfig
drivers/macintosh/Makefile
drivers/macintosh/via-pmu-led.c [new file with mode: 0644]
include/asm-powerpc/cputable.h
include/asm-powerpc/iseries/it_lp_queue.h
include/asm-powerpc/kdump.h
include/asm-powerpc/kexec.h
include/asm-powerpc/machdep.h
include/asm-powerpc/mmu.h
include/asm-powerpc/mmu_context.h
include/asm-powerpc/mpc86xx.h
include/asm-powerpc/rtas.h
include/asm-powerpc/time.h
include/asm-powerpc/todc.h [new file with mode: 0644]
include/asm-powerpc/tsi108.h [new file with mode: 0644]
include/asm-powerpc/udbg.h
kernel/kexec.c

index d43e4521abf2c962378fe14395e546d5298090d9..b9a40a35a9ed22d98cdccaf519d14eb08dc1b040 100644 (file)
@@ -340,7 +340,7 @@ config PPC_ISERIES
 
 config EMBEDDED6xx
        bool "Embedded 6xx/7xx/7xxx-based board"
-       depends on PPC32 && BROKEN
+       depends on PPC32 && (BROKEN||BROKEN_ON_SMP)
 
 config APUS
        bool "Amiga-APUS"
@@ -417,12 +417,17 @@ config PPC_CELL_NATIVE
        default n
 
 config PPC_IBM_CELL_BLADE
-       bool "  IBM Cell Blade"
+       bool "IBM Cell Blade"
        depends on PPC_MULTIPLATFORM && PPC64
        select PPC_CELL_NATIVE
        select PPC_RTAS
        select MMIO_NVRAM
        select PPC_UDBG_16550
+       select UDBG_RTAS_CONSOLE
+
+config UDBG_RTAS_CONSOLE
+       bool
+       default n
 
 config XICS
        depends on PPC_PSERIES
@@ -435,7 +440,8 @@ config U3_DART
        default n
 
 config MPIC
-       depends on PPC_PSERIES || PPC_PMAC || PPC_MAPLE || PPC_CHRP
+       depends on PPC_PSERIES || PPC_PMAC || PPC_MAPLE || PPC_CHRP \
+                              || MPC7448HPC2
        bool
        default y
 
@@ -561,6 +567,13 @@ config TAU_AVERAGE
          /proc/cpuinfo.
 
          If in doubt, say N here.
+
+config PPC_TODC
+       depends on EMBEDDED6xx
+       bool "Generic Time-of-day Clock (TODC) support"
+       ---help---
+         This adds support for many TODC/RTC chips.
+
 endmenu
 
 source arch/powerpc/platforms/embedded6xx/Kconfig
@@ -801,7 +814,6 @@ config GENERIC_ISA_DMA
 
 config PPC_I8259
        bool
-       default y if MPC8641_HPCN
        default n
 
 config PPC_INDIRECT_PCI
@@ -824,7 +836,8 @@ config MCA
        bool
 
 config PCI
-       bool "PCI support" if 40x || CPM2 || PPC_83xx || PPC_85xx || PPC_86xx || PPC_MPC52xx || (EMBEDDED && PPC_ISERIES)
+       bool "PCI support" if 40x || CPM2 || PPC_83xx || PPC_85xx || PPC_MPC52xx || (EMBEDDED && PPC_ISERIES) \
+                                 || MPC7448HPC2
        default y if !40x && !CPM2 && !8xx && !APUS && !PPC_83xx && !PPC_85xx && !PPC_86xx
        default PCI_PERMEDIA if !4xx && !CPM2 && !8xx && APUS
        default PCI_QSPAN if !4xx && !CPM2 && 8xx
index c69006ae8246abc6bbc756752779473bf5c4467c..e29ef77d3b0016ef7d164ce28b5176194e6efeb7 100644 (file)
@@ -134,12 +134,19 @@ config PPC_EARLY_DEBUG_G5
        help
          Select this to enable early debugging for Apple G5 machines.
 
-config PPC_EARLY_DEBUG_RTAS
+config PPC_EARLY_DEBUG_RTAS_PANEL
        bool "RTAS Panel"
        depends on PPC_RTAS
        help
          Select this to enable early debugging via the RTAS panel.
 
+config PPC_EARLY_DEBUG_RTAS_CONSOLE
+       bool "RTAS Console"
+       depends on PPC_RTAS
+       select UDBG_RTAS_CONSOLE
+       help
+         Select this to enable early debugging via the RTAS console.
+
 config PPC_EARLY_DEBUG_MAPLE
        bool "Maple real mode"
        depends on PPC_MAPLE
index b8b8d4675dc04f201a674c4a72f6e07607d8efee..e028a2ecb8a356694218bdfc97005277d1da2630 100644 (file)
@@ -1,7 +1,7 @@
 #
 # Automatically generated make config: don't edit
-# Linux kernel version: 2.6.17
-# Mon Jun 19 17:23:03 2006
+# Linux kernel version: 2.6.17-rc6
+# Thu Jun 22 15:28:36 2006
 #
 CONFIG_PPC64=y
 CONFIG_64BIT=y
@@ -1063,7 +1063,8 @@ CONFIG_DEBUG_FS=y
 # CONFIG_DEBUG_STACKOVERFLOW is not set
 # CONFIG_DEBUG_STACK_USAGE is not set
 CONFIG_DEBUGGER=y
-# CONFIG_XMON is not set
+CONFIG_XMON=y
+CONFIG_XMON_DEFAULT=y
 CONFIG_IRQSTACKS=y
 # CONFIG_BOOTX_TEXT is not set
 # CONFIG_PPC_EARLY_DEBUG is not set
diff --git a/arch/powerpc/configs/mpc7448_hpc2_defconfig b/arch/powerpc/configs/mpc7448_hpc2_defconfig
new file mode 100644 (file)
index 0000000..15a50f4
--- /dev/null
@@ -0,0 +1,923 @@
+#
+# Automatically generated make config: don't edit
+# Linux kernel version: 2.6.17-rc4
+# Sat May 27 18:45:55 2006
+#
+# CONFIG_PPC64 is not set
+CONFIG_PPC32=y
+CONFIG_PPC_MERGE=y
+CONFIG_MMU=y
+CONFIG_GENERIC_HARDIRQS=y
+CONFIG_RWSEM_XCHGADD_ALGORITHM=y
+CONFIG_GENERIC_HWEIGHT=y
+CONFIG_GENERIC_CALIBRATE_DELAY=y
+CONFIG_PPC=y
+CONFIG_EARLY_PRINTK=y
+CONFIG_GENERIC_NVRAM=y
+CONFIG_SCHED_NO_NO_OMIT_FRAME_POINTER=y
+CONFIG_ARCH_MAY_HAVE_PC_FDC=y
+CONFIG_PPC_OF=y
+CONFIG_PPC_UDBG_16550=y
+# CONFIG_GENERIC_TBSYNC is not set
+CONFIG_DEFAULT_UIMAGE=y
+
+#
+# Processor support
+#
+CONFIG_CLASSIC32=y
+# CONFIG_PPC_52xx is not set
+# CONFIG_PPC_82xx is not set
+# CONFIG_PPC_83xx is not set
+# CONFIG_PPC_85xx is not set
+# CONFIG_40x is not set
+# CONFIG_44x is not set
+# CONFIG_8xx is not set
+# CONFIG_E200 is not set
+CONFIG_6xx=y
+CONFIG_PPC_FPU=y
+# CONFIG_ALTIVEC is not set
+CONFIG_PPC_STD_MMU=y
+CONFIG_PPC_STD_MMU_32=y
+# CONFIG_SMP is not set
+
+#
+# Code maturity level options
+#
+CONFIG_EXPERIMENTAL=y
+CONFIG_BROKEN_ON_SMP=y
+CONFIG_INIT_ENV_ARG_LIMIT=32
+
+#
+# General setup
+#
+CONFIG_LOCALVERSION=""
+CONFIG_LOCALVERSION_AUTO=y
+CONFIG_SWAP=y
+CONFIG_SYSVIPC=y
+# CONFIG_POSIX_MQUEUE is not set
+# CONFIG_BSD_PROCESS_ACCT is not set
+CONFIG_SYSCTL=y
+# CONFIG_AUDIT is not set
+# CONFIG_IKCONFIG is not set
+# CONFIG_RELAY is not set
+CONFIG_INITRAMFS_SOURCE=""
+# CONFIG_CC_OPTIMIZE_FOR_SIZE is not set
+CONFIG_EMBEDDED=y
+CONFIG_KALLSYMS=y
+# CONFIG_KALLSYMS_EXTRA_PASS is not set
+CONFIG_HOTPLUG=y
+CONFIG_PRINTK=y
+CONFIG_BUG=y
+CONFIG_ELF_CORE=y
+CONFIG_BASE_FULL=y
+CONFIG_FUTEX=y
+CONFIG_EPOLL=y
+CONFIG_SHMEM=y
+CONFIG_SLAB=y
+# CONFIG_TINY_SHMEM is not set
+CONFIG_BASE_SMALL=0
+# CONFIG_SLOB is not set
+
+#
+# Loadable module support
+#
+# CONFIG_MODULES is not set
+
+#
+# Block layer
+#
+CONFIG_LBD=y
+# CONFIG_BLK_DEV_IO_TRACE is not set
+# CONFIG_LSF is not set
+
+#
+# IO Schedulers
+#
+CONFIG_IOSCHED_NOOP=y
+CONFIG_IOSCHED_AS=y
+CONFIG_IOSCHED_DEADLINE=y
+CONFIG_IOSCHED_CFQ=y
+CONFIG_DEFAULT_AS=y
+# CONFIG_DEFAULT_DEADLINE is not set
+# CONFIG_DEFAULT_CFQ is not set
+# CONFIG_DEFAULT_NOOP is not set
+CONFIG_DEFAULT_IOSCHED="anticipatory"
+
+#
+# Platform support
+#
+# CONFIG_PPC_MULTIPLATFORM is not set
+# CONFIG_PPC_ISERIES is not set
+CONFIG_EMBEDDED6xx=y
+# CONFIG_APUS is not set
+CONFIG_MPIC=y
+# CONFIG_PPC_RTAS is not set
+# CONFIG_MMIO_NVRAM is not set
+# CONFIG_PPC_MPC106 is not set
+# CONFIG_PPC_970_NAP is not set
+# CONFIG_CPU_FREQ is not set
+# CONFIG_TAU is not set
+# CONFIG_KATANA is not set
+# CONFIG_WILLOW is not set
+# CONFIG_CPCI690 is not set
+# CONFIG_POWERPMC250 is not set
+# CONFIG_CHESTNUT is not set
+# CONFIG_SPRUCE is not set
+# CONFIG_HDPU is not set
+# CONFIG_EV64260 is not set
+# CONFIG_LOPEC is not set
+# CONFIG_MVME5100 is not set
+# CONFIG_PPLUS is not set
+# CONFIG_PRPMC750 is not set
+# CONFIG_PRPMC800 is not set
+# CONFIG_SANDPOINT is not set
+CONFIG_MPC7448HPC2=y
+# CONFIG_RADSTONE_PPC7D is not set
+# CONFIG_PAL4 is not set
+# CONFIG_GEMINI is not set
+# CONFIG_EST8260 is not set
+# CONFIG_SBC82xx is not set
+# CONFIG_SBS8260 is not set
+# CONFIG_RPX8260 is not set
+# CONFIG_TQM8260 is not set
+# CONFIG_ADS8272 is not set
+# CONFIG_PQ2FADS is not set
+# CONFIG_LITE5200 is not set
+# CONFIG_EV64360 is not set
+CONFIG_TSI108_BRIDGE=y
+# CONFIG_WANT_EARLY_SERIAL is not set
+
+#
+# Kernel options
+#
+# CONFIG_HIGHMEM is not set
+# CONFIG_HZ_100 is not set
+CONFIG_HZ_250=y
+# CONFIG_HZ_1000 is not set
+CONFIG_HZ=250
+CONFIG_PREEMPT_NONE=y
+# CONFIG_PREEMPT_VOLUNTARY is not set
+# CONFIG_PREEMPT is not set
+CONFIG_BINFMT_ELF=y
+CONFIG_BINFMT_MISC=y
+CONFIG_ARCH_FLATMEM_ENABLE=y
+CONFIG_SELECT_MEMORY_MODEL=y
+CONFIG_FLATMEM_MANUAL=y
+# CONFIG_DISCONTIGMEM_MANUAL is not set
+# CONFIG_SPARSEMEM_MANUAL is not set
+CONFIG_FLATMEM=y
+CONFIG_FLAT_NODE_MEM_MAP=y
+# CONFIG_SPARSEMEM_STATIC is not set
+CONFIG_SPLIT_PTLOCK_CPUS=4
+CONFIG_PROC_DEVICETREE=y
+# CONFIG_CMDLINE_BOOL is not set
+# CONFIG_PM is not set
+# CONFIG_SOFTWARE_SUSPEND is not set
+# CONFIG_SECCOMP is not set
+CONFIG_ISA_DMA_API=y
+
+#
+# Bus options
+#
+CONFIG_GENERIC_ISA_DMA=y
+# CONFIG_PPC_I8259 is not set
+# CONFIG_PPC_INDIRECT_PCI is not set
+CONFIG_PCI=y
+CONFIG_PCI_DOMAINS=y
+
+#
+# PCCARD (PCMCIA/CardBus) support
+#
+# CONFIG_PCCARD is not set
+
+#
+# PCI Hotplug Support
+#
+# CONFIG_HOTPLUG_PCI is not set
+
+#
+# Advanced setup
+#
+# CONFIG_ADVANCED_OPTIONS is not set
+
+#
+# Default settings for advanced configuration options are used
+#
+CONFIG_HIGHMEM_START=0xfe000000
+CONFIG_LOWMEM_SIZE=0x30000000
+CONFIG_KERNEL_START=0xc0000000
+CONFIG_TASK_SIZE=0x80000000
+CONFIG_BOOT_LOAD=0x00800000
+
+#
+# Networking
+#
+CONFIG_NET=y
+
+#
+# Networking options
+#
+# CONFIG_NETDEBUG is not set
+CONFIG_PACKET=y
+# CONFIG_PACKET_MMAP is not set
+CONFIG_UNIX=y
+# CONFIG_NET_KEY is not set
+CONFIG_INET=y
+CONFIG_IP_MULTICAST=y
+# CONFIG_IP_ADVANCED_ROUTER is not set
+CONFIG_IP_FIB_HASH=y
+CONFIG_IP_PNP=y
+CONFIG_IP_PNP_DHCP=y
+CONFIG_IP_PNP_BOOTP=y
+# CONFIG_IP_PNP_RARP is not set
+# CONFIG_NET_IPIP is not set
+# CONFIG_NET_IPGRE is not set
+# CONFIG_IP_MROUTE is not set
+# CONFIG_ARPD is not set
+CONFIG_SYN_COOKIES=y
+# CONFIG_INET_AH is not set
+# CONFIG_INET_ESP is not set
+# CONFIG_INET_IPCOMP is not set
+# CONFIG_INET_XFRM_TUNNEL is not set
+# CONFIG_INET_TUNNEL is not set
+CONFIG_INET_DIAG=y
+CONFIG_INET_TCP_DIAG=y
+# CONFIG_TCP_CONG_ADVANCED is not set
+CONFIG_TCP_CONG_BIC=y
+# CONFIG_IPV6 is not set
+# CONFIG_INET6_XFRM_TUNNEL is not set
+# CONFIG_INET6_TUNNEL is not set
+# CONFIG_NETFILTER is not set
+
+#
+# DCCP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_DCCP is not set
+
+#
+# SCTP Configuration (EXPERIMENTAL)
+#
+# CONFIG_IP_SCTP is not set
+
+#
+# TIPC Configuration (EXPERIMENTAL)
+#
+# CONFIG_TIPC is not set
+# CONFIG_ATM is not set
+# CONFIG_BRIDGE is not set
+# CONFIG_VLAN_8021Q is not set
+# CONFIG_DECNET is not set
+# CONFIG_LLC2 is not set
+# CONFIG_IPX is not set
+# CONFIG_ATALK is not set
+# CONFIG_X25 is not set
+# CONFIG_LAPB is not set
+# CONFIG_NET_DIVERT is not set
+# CONFIG_ECONET is not set
+# CONFIG_WAN_ROUTER is not set
+
+#
+# QoS and/or fair queueing
+#
+# CONFIG_NET_SCHED is not set
+
+#
+# Network testing
+#
+# CONFIG_NET_PKTGEN is not set
+# CONFIG_HAMRADIO is not set
+# CONFIG_IRDA is not set
+# CONFIG_BT is not set
+# CONFIG_IEEE80211 is not set
+
+#
+# Device Drivers
+#
+
+#
+# Generic Driver Options
+#
+CONFIG_STANDALONE=y
+CONFIG_PREVENT_FIRMWARE_BUILD=y
+# CONFIG_FW_LOADER is not set
+
+#
+# Connector - unified userspace <-> kernelspace linker
+#
+# CONFIG_CONNECTOR is not set
+
+#
+# Memory Technology Devices (MTD)
+#
+# CONFIG_MTD is not set
+
+#
+# Parallel port support
+#
+# CONFIG_PARPORT is not set
+
+#
+# Plug and Play support
+#
+
+#
+# Block devices
+#
+# CONFIG_BLK_DEV_FD is not set
+# CONFIG_BLK_CPQ_DA is not set
+# CONFIG_BLK_CPQ_CISS_DA is not set
+# CONFIG_BLK_DEV_DAC960 is not set
+# CONFIG_BLK_DEV_UMEM is not set
+# CONFIG_BLK_DEV_COW_COMMON is not set
+CONFIG_BLK_DEV_LOOP=y
+# CONFIG_BLK_DEV_CRYPTOLOOP is not set
+# CONFIG_BLK_DEV_NBD is not set
+# CONFIG_BLK_DEV_SX8 is not set
+CONFIG_BLK_DEV_RAM=y
+CONFIG_BLK_DEV_RAM_COUNT=16
+CONFIG_BLK_DEV_RAM_SIZE=131072
+CONFIG_BLK_DEV_INITRD=y
+# CONFIG_CDROM_PKTCDVD is not set
+# CONFIG_ATA_OVER_ETH is not set
+
+#
+# ATA/ATAPI/MFM/RLL support
+#
+# CONFIG_IDE is not set
+
+#
+# SCSI device support
+#
+# CONFIG_RAID_ATTRS is not set
+CONFIG_SCSI=y
+CONFIG_SCSI_PROC_FS=y
+
+#
+# SCSI support type (disk, tape, CD-ROM)
+#
+CONFIG_BLK_DEV_SD=y
+# CONFIG_CHR_DEV_ST is not set
+# CONFIG_CHR_DEV_OSST is not set
+# CONFIG_BLK_DEV_SR is not set
+# CONFIG_CHR_DEV_SG is not set
+# CONFIG_CHR_DEV_SCH is not set
+
+#
+# Some SCSI devices (e.g. CD jukebox) support multiple LUNs
+#
+# CONFIG_SCSI_MULTI_LUN is not set
+# CONFIG_SCSI_CONSTANTS is not set
+# CONFIG_SCSI_LOGGING is not set
+
+#
+# SCSI Transport Attributes
+#
+# CONFIG_SCSI_SPI_ATTRS is not set
+# CONFIG_SCSI_FC_ATTRS is not set
+# CONFIG_SCSI_ISCSI_ATTRS is not set
+# CONFIG_SCSI_SAS_ATTRS is not set
+
+#
+# SCSI low-level drivers
+#
+# CONFIG_ISCSI_TCP is not set
+# CONFIG_BLK_DEV_3W_XXXX_RAID is not set
+# CONFIG_SCSI_3W_9XXX is not set
+# CONFIG_SCSI_ACARD is not set
+# CONFIG_SCSI_AACRAID is not set
+# CONFIG_SCSI_AIC7XXX is not set
+# CONFIG_SCSI_AIC7XXX_OLD is not set
+# CONFIG_SCSI_AIC79XX is not set
+# CONFIG_SCSI_DPT_I2O is not set
+# CONFIG_MEGARAID_NEWGEN is not set
+# CONFIG_MEGARAID_LEGACY is not set
+# CONFIG_MEGARAID_SAS is not set
+CONFIG_SCSI_SATA=y
+# CONFIG_SCSI_SATA_AHCI is not set
+# CONFIG_SCSI_SATA_SVW is not set
+# CONFIG_SCSI_ATA_PIIX is not set
+CONFIG_SCSI_SATA_MV=y
+# CONFIG_SCSI_SATA_NV is not set
+# CONFIG_SCSI_PDC_ADMA is not set
+# CONFIG_SCSI_SATA_QSTOR is not set
+# CONFIG_SCSI_SATA_PROMISE is not set
+# CONFIG_SCSI_SATA_SX4 is not set
+# CONFIG_SCSI_SATA_SIL is not set
+# CONFIG_SCSI_SATA_SIL24 is not set
+# CONFIG_SCSI_SATA_SIS is not set
+# CONFIG_SCSI_SATA_ULI is not set
+# CONFIG_SCSI_SATA_VIA is not set
+# CONFIG_SCSI_SATA_VITESSE is not set
+# CONFIG_SCSI_BUSLOGIC is not set
+# CONFIG_SCSI_DMX3191D is not set
+# CONFIG_SCSI_EATA is not set
+# CONFIG_SCSI_FUTURE_DOMAIN is not set
+# CONFIG_SCSI_GDTH is not set
+# CONFIG_SCSI_IPS is not set
+# CONFIG_SCSI_INITIO is not set
+# CONFIG_SCSI_INIA100 is not set
+# CONFIG_SCSI_SYM53C8XX_2 is not set
+# CONFIG_SCSI_IPR is not set
+# CONFIG_SCSI_QLOGIC_1280 is not set
+# CONFIG_SCSI_QLA_FC is not set
+# CONFIG_SCSI_LPFC is not set
+# CONFIG_SCSI_DC395x is not set
+# CONFIG_SCSI_DC390T is not set
+# CONFIG_SCSI_NSP32 is not set
+# CONFIG_SCSI_DEBUG is not set
+
+#
+# Multi-device support (RAID and LVM)
+#
+# CONFIG_MD is not set
+
+#
+# Fusion MPT device support
+#
+# CONFIG_FUSION is not set
+# CONFIG_FUSION_SPI is not set
+# CONFIG_FUSION_FC is not set
+# CONFIG_FUSION_SAS is not set
+
+#
+# IEEE 1394 (FireWire) support
+#
+# CONFIG_IEEE1394 is not set
+
+#
+# I2O device support
+#
+# CONFIG_I2O is not set
+
+#
+# Macintosh device drivers
+#
+# CONFIG_WINDFARM is not set
+
+#
+# Network device support
+#
+CONFIG_NETDEVICES=y
+# CONFIG_DUMMY is not set
+# CONFIG_BONDING is not set
+# CONFIG_EQUALIZER is not set
+# CONFIG_TUN is not set
+
+#
+# ARCnet devices
+#
+# CONFIG_ARCNET is not set
+
+#
+# PHY device support
+#
+CONFIG_PHYLIB=y
+
+#
+# MII PHY device drivers
+#
+# CONFIG_MARVELL_PHY is not set
+# CONFIG_DAVICOM_PHY is not set
+# CONFIG_QSEMI_PHY is not set
+# CONFIG_LXT_PHY is not set
+# CONFIG_CICADA_PHY is not set
+
+#
+# Ethernet (10 or 100Mbit)
+#
+CONFIG_NET_ETHERNET=y
+CONFIG_MII=y
+# CONFIG_HAPPYMEAL is not set
+# CONFIG_SUNGEM is not set
+# CONFIG_CASSINI is not set
+# CONFIG_NET_VENDOR_3COM is not set
+
+#
+# Tulip family network device support
+#
+# CONFIG_NET_TULIP is not set
+# CONFIG_HP100 is not set
+CONFIG_NET_PCI=y
+# CONFIG_PCNET32 is not set
+# CONFIG_AMD8111_ETH is not set
+# CONFIG_ADAPTEC_STARFIRE is not set
+# CONFIG_B44 is not set
+# CONFIG_FORCEDETH is not set
+# CONFIG_DGRS is not set
+# CONFIG_EEPRO100 is not set
+CONFIG_E100=y
+# CONFIG_FEALNX is not set
+# CONFIG_NATSEMI is not set
+# CONFIG_NE2K_PCI is not set
+# CONFIG_8139CP is not set
+CONFIG_8139TOO=y
+# CONFIG_8139TOO_PIO is not set
+# CONFIG_8139TOO_TUNE_TWISTER is not set
+# CONFIG_8139TOO_8129 is not set
+# CONFIG_8139_OLD_RX_RESET is not set
+# CONFIG_SIS900 is not set
+# CONFIG_EPIC100 is not set
+# CONFIG_SUNDANCE is not set
+# CONFIG_TLAN is not set
+# CONFIG_VIA_RHINE is not set
+
+#
+# Ethernet (1000 Mbit)
+#
+# CONFIG_ACENIC is not set
+# CONFIG_DL2K is not set
+# CONFIG_E1000 is not set
+# CONFIG_NS83820 is not set
+# CONFIG_HAMACHI is not set
+# CONFIG_YELLOWFIN is not set
+# CONFIG_R8169 is not set
+# CONFIG_SIS190 is not set
+# CONFIG_SKGE is not set
+# CONFIG_SKY2 is not set
+# CONFIG_SK98LIN is not set
+# CONFIG_VIA_VELOCITY is not set
+# CONFIG_TIGON3 is not set
+# CONFIG_BNX2 is not set
+CONFIG_TSI108_ETH=y
+
+#
+# Ethernet (10000 Mbit)
+#
+# CONFIG_CHELSIO_T1 is not set
+# CONFIG_IXGB is not set
+# CONFIG_S2IO is not set
+
+#
+# Token Ring devices
+#
+# CONFIG_TR is not set
+
+#
+# Wireless LAN (non-hamradio)
+#
+# CONFIG_NET_RADIO is not set
+
+#
+# Wan interfaces
+#
+# CONFIG_WAN is not set
+# CONFIG_FDDI is not set
+# CONFIG_HIPPI is not set
+# CONFIG_PPP is not set
+# CONFIG_SLIP is not set
+# CONFIG_NET_FC is not set
+# CONFIG_SHAPER is not set
+# CONFIG_NETCONSOLE is not set
+# CONFIG_NETPOLL is not set
+# CONFIG_NET_POLL_CONTROLLER is not set
+
+#
+# ISDN subsystem
+#
+# CONFIG_ISDN is not set
+
+#
+# Telephony Support
+#
+# CONFIG_PHONE is not set
+
+#
+# Input device support
+#
+CONFIG_INPUT=y
+
+#
+# Userland interfaces
+#
+# CONFIG_INPUT_MOUSEDEV is not set
+# CONFIG_INPUT_JOYDEV is not set
+# CONFIG_INPUT_TSDEV is not set
+# CONFIG_INPUT_EVDEV is not set
+# CONFIG_INPUT_EVBUG is not set
+
+#
+# Input Device Drivers
+#
+# CONFIG_INPUT_KEYBOARD is not set
+# CONFIG_INPUT_MOUSE is not set
+# CONFIG_INPUT_JOYSTICK is not set
+# CONFIG_INPUT_TOUCHSCREEN is not set
+# CONFIG_INPUT_MISC is not set
+
+#
+# Hardware I/O ports
+#
+# CONFIG_SERIO is not set
+# CONFIG_GAMEPORT is not set
+
+#
+# Character devices
+#
+# CONFIG_VT is not set
+# CONFIG_SERIAL_NONSTANDARD is not set
+
+#
+# Serial drivers
+#
+CONFIG_SERIAL_8250=y
+CONFIG_SERIAL_8250_CONSOLE=y
+CONFIG_SERIAL_8250_PCI=y
+CONFIG_SERIAL_8250_NR_UARTS=4
+CONFIG_SERIAL_8250_RUNTIME_UARTS=4
+# CONFIG_SERIAL_8250_EXTENDED is not set
+
+#
+# Non-8250 serial port support
+#
+CONFIG_SERIAL_CORE=y
+CONFIG_SERIAL_CORE_CONSOLE=y
+# CONFIG_SERIAL_JSM is not set
+CONFIG_UNIX98_PTYS=y
+CONFIG_LEGACY_PTYS=y
+CONFIG_LEGACY_PTY_COUNT=256
+
+#
+# IPMI
+#
+# CONFIG_IPMI_HANDLER is not set
+
+#
+# Watchdog Cards
+#
+# CONFIG_WATCHDOG is not set
+# CONFIG_NVRAM is not set
+CONFIG_GEN_RTC=y
+# CONFIG_GEN_RTC_X 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_AGP is not set
+# CONFIG_DRM is not set
+# CONFIG_RAW_DRIVER is not set
+
+#
+# TPM devices
+#
+# CONFIG_TCG_TPM is not set
+# CONFIG_TELCLOCK is not set
+
+#
+# I2C support
+#
+# CONFIG_I2C is not set
+
+#
+# SPI support
+#
+# CONFIG_SPI is not set
+# CONFIG_SPI_MASTER is not set
+
+#
+# Dallas's 1-wire bus
+#
+# CONFIG_W1 is not set
+
+#
+# Hardware Monitoring support
+#
+CONFIG_HWMON=y
+# CONFIG_HWMON_VID is not set
+# CONFIG_SENSORS_F71805F is not set
+# CONFIG_HWMON_DEBUG_CHIP is not set
+
+#
+# Misc devices
+#
+
+#
+# Multimedia devices
+#
+# CONFIG_VIDEO_DEV is not set
+
+#
+# Digital Video Broadcasting Devices
+#
+# CONFIG_DVB is not set
+
+#
+# Graphics support
+#
+# CONFIG_FB is not set
+
+#
+# Sound
+#
+# CONFIG_SOUND is not set
+
+#
+# USB support
+#
+CONFIG_USB_ARCH_HAS_HCD=y
+CONFIG_USB_ARCH_HAS_OHCI=y
+CONFIG_USB_ARCH_HAS_EHCI=y
+# CONFIG_USB is not set
+
+#
+# NOTE: USB_STORAGE enables SCSI, and 'SCSI disk support'
+#
+
+#
+# USB Gadget Support
+#
+# CONFIG_USB_GADGET is not set
+
+#
+# MMC/SD Card support
+#
+# CONFIG_MMC is not set
+
+#
+# LED devices
+#
+# CONFIG_NEW_LEDS is not set
+
+#
+# LED drivers
+#
+
+#
+# LED Triggers
+#
+
+#
+# InfiniBand support
+#
+# CONFIG_INFINIBAND is not set
+
+#
+# EDAC - error detection and reporting (RAS) (EXPERIMENTAL)
+#
+
+#
+# Real Time Clock
+#
+# CONFIG_RTC_CLASS is not set
+
+#
+# File systems
+#
+CONFIG_EXT2_FS=y
+# CONFIG_EXT2_FS_XATTR is not set
+# CONFIG_EXT2_FS_XIP is not set
+CONFIG_EXT3_FS=y
+CONFIG_EXT3_FS_XATTR=y
+# CONFIG_EXT3_FS_POSIX_ACL is not set
+# CONFIG_EXT3_FS_SECURITY is not set
+CONFIG_JBD=y
+# CONFIG_JBD_DEBUG is not set
+CONFIG_FS_MBCACHE=y
+# CONFIG_REISERFS_FS is not set
+# CONFIG_JFS_FS is not set
+# CONFIG_FS_POSIX_ACL is not set
+# CONFIG_XFS_FS is not set
+# CONFIG_OCFS2_FS is not set
+# CONFIG_MINIX_FS is not set
+# CONFIG_ROMFS_FS is not set
+CONFIG_INOTIFY=y
+# CONFIG_QUOTA is not set
+CONFIG_DNOTIFY=y
+# CONFIG_AUTOFS_FS is not set
+# CONFIG_AUTOFS4_FS is not set
+# CONFIG_FUSE_FS is not set
+
+#
+# CD-ROM/DVD Filesystems
+#
+# CONFIG_ISO9660_FS is not set
+# CONFIG_UDF_FS is not set
+
+#
+# DOS/FAT/NT Filesystems
+#
+# CONFIG_MSDOS_FS is not set
+# CONFIG_VFAT_FS is not set
+# CONFIG_NTFS_FS is not set
+
+#
+# Pseudo filesystems
+#
+CONFIG_PROC_FS=y
+CONFIG_PROC_KCORE=y
+CONFIG_SYSFS=y
+CONFIG_TMPFS=y
+# CONFIG_HUGETLB_PAGE is not set
+CONFIG_RAMFS=y
+# CONFIG_CONFIGFS_FS is not set
+
+#
+# Miscellaneous filesystems
+#
+# CONFIG_ADFS_FS is not set
+# CONFIG_AFFS_FS is not set
+# CONFIG_HFS_FS is not set
+# CONFIG_HFSPLUS_FS is not set
+# CONFIG_BEFS_FS is not set
+# CONFIG_BFS_FS is not set
+# CONFIG_EFS_FS is not set
+# CONFIG_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
+
+#
+# Network File Systems
+#
+CONFIG_NFS_FS=y
+# CONFIG_NFS_V3 is not set
+# CONFIG_NFS_V4 is not set
+# CONFIG_NFS_DIRECTIO is not set
+# CONFIG_NFSD is not set
+CONFIG_ROOT_NFS=y
+CONFIG_LOCKD=y
+CONFIG_NFS_COMMON=y
+CONFIG_SUNRPC=y
+# CONFIG_RPCSEC_GSS_KRB5 is not set
+# CONFIG_RPCSEC_GSS_SPKM3 is not set
+# CONFIG_SMB_FS is not set
+# CONFIG_CIFS is not set
+# CONFIG_NCP_FS is not set
+# CONFIG_CODA_FS is not set
+# CONFIG_AFS_FS is not set
+# CONFIG_9P_FS is not set
+
+#
+# Partition Types
+#
+CONFIG_PARTITION_ADVANCED=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_SGI_PARTITION is not set
+# CONFIG_ULTRIX_PARTITION is not set
+# CONFIG_SUN_PARTITION is not set
+# CONFIG_KARMA_PARTITION is not set
+# CONFIG_EFI_PARTITION is not set
+
+#
+# Native Language Support
+#
+# CONFIG_NLS is not set
+
+#
+# Library routines
+#
+# CONFIG_CRC_CCITT is not set
+# CONFIG_CRC16 is not set
+CONFIG_CRC32=y
+# CONFIG_LIBCRC32C is not set
+
+#
+# Instrumentation Support
+#
+# CONFIG_PROFILING is not set
+
+#
+# Kernel hacking
+#
+# CONFIG_PRINTK_TIME is not set
+# CONFIG_MAGIC_SYSRQ is not set
+# CONFIG_DEBUG_KERNEL is not set
+CONFIG_LOG_BUF_SHIFT=14
+# CONFIG_DEBUG_FS is not set
+# CONFIG_UNWIND_INFO is not set
+# CONFIG_BOOTX_TEXT is not set
+# CONFIG_SERIAL_TEXT_DEBUG is not set
+# CONFIG_PPC_EARLY_DEBUG_LPAR is not set
+# CONFIG_PPC_EARLY_DEBUG_G5 is not set
+# CONFIG_PPC_EARLY_DEBUG_RTAS is not set
+# CONFIG_PPC_EARLY_DEBUG_MAPLE is not set
+# CONFIG_PPC_EARLY_DEBUG_ISERIES is not set
+
+#
+# Security options
+#
+# CONFIG_KEYS is not set
+# CONFIG_SECURITY is not set
+
+#
+# Cryptographic options
+#
+# CONFIG_CRYPTO is not set
+
+#
+# Hardware crypto devices
+#
index 803858e8616031054c62fbb04021e0d6a3f13052..814f242aeb8cc06348603c2df8478b0dd0d4e274 100644 (file)
@@ -50,7 +50,8 @@ extra-$(CONFIG_FSL_BOOKE)     := head_fsl_booke.o
 extra-$(CONFIG_8xx)            := head_8xx.o
 extra-y                                += vmlinux.lds
 
-obj-y                          += time.o prom.o traps.o setup-common.o udbg.o
+obj-y                          += time.o prom.o traps.o setup-common.o \
+                                  udbg.o misc.o
 obj-$(CONFIG_PPC32)            += entry_32.o setup_32.o misc_32.o
 obj-$(CONFIG_PPC64)            += misc_64.o dma_64.o iommu.o
 obj-$(CONFIG_PPC_MULTIPLATFORM)        += prom_init.o
index 271418308d536de53601ae69a0c070ac24a11490..1fc8632610030c7da76bd33933ecfda1b5373c35 100644 (file)
@@ -125,7 +125,12 @@ _GLOBAL(__save_cpu_setup)
        cmpwi   r0,0x44
        bne     2f
 
-1:     /* Save HID0,1,4 and 5 */
+1:     /* skip if not running in HV mode */
+       mfmsr   r0
+       rldicl. r0,r0,4,63
+       beq     2f
+
+       /* Save HID0,1,4 and 5 */
        mfspr   r3,SPRN_HID0
        std     r3,CS_HID0(r5)
        mfspr   r3,SPRN_HID1
@@ -159,7 +164,12 @@ _GLOBAL(__restore_cpu_setup)
        cmpwi   r0,0x44
        bnelr
 
-1:     /* Before accessing memory, we make sure rm_ci is clear */
+1:     /* skip if not running in HV mode */
+       mfmsr   r0
+       rldicl. r0,r0,4,63
+       beqlr
+
+       /* Before accessing memory, we make sure rm_ci is clear */
        li      r0,0
        mfspr   r3,SPRN_HID4
        rldimi  r3,r0,40,23     /* clear bit 23 (rm_ci) */
index 1c114880dc0504fe7d8e5c64b851ad23fdc69cab..abf7d42a8b07f6bee788f8ced65656188ef59aae 100644 (file)
@@ -722,18 +722,6 @@ struct cpu_spec    cpu_specs[] = {
                .oprofile_type          = PPC_OPROFILE_G4,
                .platform               = "ppc7450",
        },
-        {       /* 8641 */
-               .pvr_mask               = 0xffffffff,
-               .pvr_value              = 0x80040010,
-               .cpu_name               = "8641",
-               .cpu_features           = CPU_FTRS_7447A,
-               .cpu_user_features      = COMMON_USER | PPC_FEATURE_HAS_ALTIVEC_COMP,
-               .icache_bsize           = 32,
-               .dcache_bsize           = 32,
-               .num_pmcs               = 6,
-               .cpu_setup              = __setup_cpu_745x
-        },
-
        {       /* 82xx (8240, 8245, 8260 are all 603e cores) */
                .pvr_mask               = 0x7fff0000,
                .pvr_value              = 0x00810000,
index 22ceba844bf4ae729c4f898347a5715ab807b316..358cecdc6aef2e1ab8e91778897db3accce3fd11 100644 (file)
 #include <linux/init.h>
 #include <linux/irq.h>
 #include <linux/types.h>
+#include <linux/irq.h>
 
 #include <asm/processor.h>
 #include <asm/machdep.h>
+#include <asm/kexec.h>
 #include <asm/kdump.h>
 #include <asm/lmb.h>
 #include <asm/firmware.h>
@@ -41,6 +43,7 @@
 
 /* This keeps a track of which one is crashing cpu. */
 int crashing_cpu = -1;
+static cpumask_t cpus_in_crash = CPU_MASK_NONE;
 
 static u32 *append_elf_note(u32 *buf, char *name, unsigned type, void *data,
                                                               size_t data_len)
@@ -98,34 +101,66 @@ static void crash_save_this_cpu(struct pt_regs *regs, int cpu)
 }
 
 #ifdef CONFIG_SMP
-static atomic_t waiting_for_crash_ipi;
+static atomic_t enter_on_soft_reset = ATOMIC_INIT(0);
 
 void crash_ipi_callback(struct pt_regs *regs)
 {
        int cpu = smp_processor_id();
 
-       if (cpu == crashing_cpu)
-               return;
-
        if (!cpu_online(cpu))
                return;
 
-       if (ppc_md.kexec_cpu_down)
-               ppc_md.kexec_cpu_down(1, 1);
-
        local_irq_disable();
+       if (!cpu_isset(cpu, cpus_in_crash))
+               crash_save_this_cpu(regs, cpu);
+       cpu_set(cpu, cpus_in_crash);
 
-       crash_save_this_cpu(regs, cpu);
-       atomic_dec(&waiting_for_crash_ipi);
+       /*
+        * Entered via soft-reset - could be the kdump
+        * process is invoked using soft-reset or user activated
+        * it if some CPU did not respond to an IPI.
+        * For soft-reset, the secondary CPU can enter this func
+        * twice. 1 - using IPI, and 2. soft-reset.
+        * Tell the kexec CPU that entered via soft-reset and ready
+        * to go down.
+        */
+       if (cpu_isset(cpu, cpus_in_sr)) {
+               cpu_clear(cpu, cpus_in_sr);
+               atomic_inc(&enter_on_soft_reset);
+       }
+
+       /*
+        * Starting the kdump boot.
+        * This barrier is needed to make sure that all CPUs are stopped.
+        * If not, soft-reset will be invoked to bring other CPUs.
+        */
+       while (!cpu_isset(crashing_cpu, cpus_in_crash))
+               cpu_relax();
+
+       if (ppc_md.kexec_cpu_down)
+               ppc_md.kexec_cpu_down(1, 1);
        kexec_smp_wait();
        /* NOTREACHED */
 }
 
-static void crash_kexec_prepare_cpus(void)
+/*
+ * Wait until all CPUs are entered via soft-reset.
+ */
+static void crash_soft_reset_check(int cpu)
+{
+       unsigned int ncpus = num_online_cpus() - 1;/* Excluding the panic cpu */
+
+       cpu_clear(cpu, cpus_in_sr);
+       while (atomic_read(&enter_on_soft_reset) != ncpus)
+               cpu_relax();
+}
+
+
+static void crash_kexec_prepare_cpus(int cpu)
 {
        unsigned int msecs;
 
-       atomic_set(&waiting_for_crash_ipi, num_online_cpus() - 1);
+       unsigned int ncpus = num_online_cpus() - 1;/* Excluding the panic cpu */
 
        crash_send_ipi(crash_ipi_callback);
        smp_wmb();
@@ -133,14 +168,13 @@ static void crash_kexec_prepare_cpus(void)
        /*
         * FIXME: Until we will have the way to stop other CPUSs reliabally,
         * the crash CPU will send an IPI and wait for other CPUs to
-        * respond. If not, proceed the kexec boot even though we failed to
-        * capture other CPU states.
+        * respond.
         * Delay of at least 10 seconds.
         */
-       printk(KERN_ALERT "Sending IPI to other cpus...\n");
+       printk(KERN_EMERG "Sending IPI to other cpus...\n");
        msecs = 10000;
-       while ((atomic_read(&waiting_for_crash_ipi) > 0) && (--msecs > 0)) {
-               barrier();
+       while ((cpus_weight(cpus_in_crash) < ncpus) && (--msecs > 0)) {
+               cpu_relax();
                mdelay(1);
        }
 
@@ -149,18 +183,71 @@ static void crash_kexec_prepare_cpus(void)
        /*
         * FIXME: In case if we do not get all CPUs, one possibility: ask the
         * user to do soft reset such that we get all.
-        * IPI handler is already set by the panic cpu initially. Therefore,
-        * all cpus could invoke this handler from die() and the panic CPU
-        * will call machine_kexec() directly from this handler to do
-        * kexec boot.
+        * Soft-reset will be used until better mechanism is implemented.
+        */
+       if (cpus_weight(cpus_in_crash) < ncpus) {
+               printk(KERN_EMERG "done waiting: %d cpu(s) not responding\n",
+                       ncpus - cpus_weight(cpus_in_crash));
+               printk(KERN_EMERG "Activate soft-reset to stop other cpu(s)\n");
+               cpus_in_sr = CPU_MASK_NONE;
+               atomic_set(&enter_on_soft_reset, 0);
+               while (cpus_weight(cpus_in_crash) < ncpus)
+                       cpu_relax();
+       }
+       /*
+        * Make sure all CPUs are entered via soft-reset if the kdump is
+        * invoked using soft-reset.
         */
-       if (atomic_read(&waiting_for_crash_ipi))
-               printk(KERN_ALERT "done waiting: %d cpus not responding\n",
-                       atomic_read(&waiting_for_crash_ipi));
+       if (cpu_isset(cpu, cpus_in_sr))
+               crash_soft_reset_check(cpu);
        /* Leave the IPI callback set */
 }
+
+/*
+ * This function will be called by secondary cpus or by kexec cpu
+ * if soft-reset is activated to stop some CPUs.
+ */
+void crash_kexec_secondary(struct pt_regs *regs)
+{
+       int cpu = smp_processor_id();
+       unsigned long flags;
+       int msecs = 5;
+
+       local_irq_save(flags);
+       /* Wait 5ms if the kexec CPU is not entered yet. */
+       while (crashing_cpu < 0) {
+               if (--msecs < 0) {
+                       /*
+                        * Either kdump image is not loaded or
+                        * kdump process is not started - Probably xmon
+                        * exited using 'x'(exit and recover) or
+                        * kexec_should_crash() failed for all running tasks.
+                        */
+                       cpu_clear(cpu, cpus_in_sr);
+                       local_irq_restore(flags);
+                       return;
+               }
+               mdelay(1);
+               cpu_relax();
+       }
+       if (cpu == crashing_cpu) {
+               /*
+                * Panic CPU will enter this func only via soft-reset.
+                * Wait until all secondary CPUs entered and
+                * then start kexec boot.
+                */
+               crash_soft_reset_check(cpu);
+               cpu_set(crashing_cpu, cpus_in_crash);
+               if (ppc_md.kexec_cpu_down)
+                       ppc_md.kexec_cpu_down(1, 0);
+               machine_kexec(kexec_crash_image);
+               /* NOTREACHED */
+       }
+       crash_ipi_callback(regs);
+}
+
 #else
-static void crash_kexec_prepare_cpus(void)
+static void crash_kexec_prepare_cpus(int cpu)
 {
        /*
         * move the secondarys to us so that we can copy
@@ -171,6 +258,10 @@ static void crash_kexec_prepare_cpus(void)
        smp_release_cpus();
 }
 
+void crash_kexec_secondary(struct pt_regs *regs)
+{
+       cpus_in_sr = CPU_MASK_NONE;
+}
 #endif
 
 void default_machine_crash_shutdown(struct pt_regs *regs)
@@ -199,14 +290,14 @@ void default_machine_crash_shutdown(struct pt_regs *regs)
                        desc->chip->disable(irq);
        }
 
-       if (ppc_md.kexec_cpu_down)
-               ppc_md.kexec_cpu_down(1, 0);
-
        /*
         * Make a note of crashing cpu. Will be used in machine_kexec
         * such that another IPI will not be sent.
         */
        crashing_cpu = smp_processor_id();
-       crash_kexec_prepare_cpus();
        crash_save_this_cpu(regs, crashing_cpu);
+       crash_kexec_prepare_cpus(crashing_cpu);
+       cpu_set(crashing_cpu, cpus_in_crash);
+       if (ppc_md.kexec_cpu_down)
+               ppc_md.kexec_cpu_down(1, 0);
 }
index 831acbdf2592508734c45b3ab35b2a61482b5172..8cfd040d1f50c07211eca77ce4694d1cabf0f12e 100644 (file)
@@ -85,34 +85,6 @@ END_FTR_SECTION(0, 1)
        /* Catch branch to 0 in real mode */
        trap
 
-#ifdef CONFIG_PPC_ISERIES
-       /*
-        * At offset 0x20, there is a pointer to iSeries LPAR data.
-        * This is required by the hypervisor
-        */
-       . = 0x20
-       .llong hvReleaseData-KERNELBASE
-
-       /*
-        * At offset 0x28 and 0x30 are offsets to the mschunks_map
-        * array (used by the iSeries LPAR debugger to do translation
-        * between physical addresses and absolute addresses) and
-        * to the pidhash table (also used by the debugger)
-        */
-       .llong mschunks_map-KERNELBASE
-       .llong 0        /* pidhash-KERNELBASE SFRXXX */
-
-       /* Offset 0x38 - Pointer to start of embedded System.map */
-       .globl  embedded_sysmap_start
-embedded_sysmap_start:
-       .llong  0
-       /* Offset 0x40 - Pointer to end of embedded System.map */
-       .globl  embedded_sysmap_end
-embedded_sysmap_end:
-       .llong  0
-
-#endif /* CONFIG_PPC_ISERIES */
-
        /* Secondary processors spin on this value until it goes to 1. */
        .globl  __secondary_hold_spinloop
 __secondary_hold_spinloop:
@@ -124,6 +96,15 @@ __secondary_hold_spinloop:
 __secondary_hold_acknowledge:
        .llong  0x0
 
+#ifdef CONFIG_PPC_ISERIES
+       /*
+        * At offset 0x20, there is a pointer to iSeries LPAR data.
+        * This is required by the hypervisor
+        */
+       . = 0x20
+       .llong hvReleaseData-KERNELBASE
+#endif /* CONFIG_PPC_ISERIES */
+
        . = 0x60
 /*
  * The following code is used on pSeries to hold secondary processors
@@ -1602,9 +1583,6 @@ _GLOBAL(__start_initialization_multiplatform)
        /* Setup some critical 970 SPRs before switching MMU off */
        bl      .__970_cpu_preinit
 
-       /* cpu # */
-       li      r24,0
-
        /* Switch off MMU if not already */
        LOAD_REG_IMMEDIATE(r4, .__after_prom_start - KERNELBASE)
        add     r4,r4,r30
@@ -1683,6 +1661,9 @@ _STATIC(__after_prom_start)
                                        /*   i.e. where we are running   */
                                        /*      the source addr          */
 
+       cmpdi   r4,0                    /* In some cases the loader may  */
+       beq     .start_here_multiplatform /* have already put us at zero */
+                                       /* so we can skip the copy.      */
        LOAD_REG_IMMEDIATE(r5,copy_to_here) /* # bytes of memory to copy */
        sub     r5,r5,r27
 
@@ -1962,14 +1943,6 @@ _STATIC(start_here_common)
        li      r3,0
        bl      .do_cpu_ftr_fixups
 
-       LOAD_REG_IMMEDIATE(r26, boot_cpuid)
-       lwz     r26,0(r26)
-
-       LOAD_REG_IMMEDIATE(r24, paca)   /* Get base vaddr of paca array  */
-       mulli   r13,r26,PACA_SIZE       /* Calculate vaddr of right paca */
-       add     r13,r13,r24             /* for this processor.           */
-       mtspr   SPRN_SPRG3,r13
-
        /* ptr to current */
        LOAD_REG_IMMEDIATE(r4, init_task)
        std     r4,PACACURRENT(r13)
@@ -1995,17 +1968,6 @@ _STATIC(start_here_common)
        /* Not reached */
        BUG_OPCODE
 
-/* Put the paca pointer into r13 and SPRG3 */
-_GLOBAL(setup_boot_paca)
-       LOAD_REG_IMMEDIATE(r3, boot_cpuid)
-       lwz     r3,0(r3)
-       LOAD_REG_IMMEDIATE(r4, paca)    /* Get base vaddr of paca array  */
-       mulli   r3,r3,PACA_SIZE         /* Calculate vaddr of right paca */
-       add     r13,r3,r4               /* for this processor.           */
-       mtspr   SPRN_SPRG3,r13
-
-       blr
-
 /*
  * We put a few things here that have to be page-aligned.
  * This stuff goes at the beginning of the bss, which is page-aligned.
index 7cb77c20fc5d0a5c979eade8dbe1ea86ecfa4bad..3d677ac996592d1cb4c15462499c41b6e0e1ecf0 100644 (file)
@@ -38,6 +38,7 @@
 #include <asm/iommu.h>
 #include <asm/pci-bridge.h>
 #include <asm/machdep.h>
+#include <asm/kdump.h>
 
 #define DBG(...)
 
@@ -440,8 +441,37 @@ struct iommu_table *iommu_init_table(struct iommu_table *tbl, int nid)
        tbl->it_largehint = tbl->it_halfpoint;
        spin_lock_init(&tbl->it_lock);
 
+#ifdef CONFIG_CRASH_DUMP
+       if (ppc_md.tce_get) {
+               unsigned long index, tceval;
+               unsigned long tcecount = 0;
+
+               /*
+                * Reserve the existing mappings left by the first kernel.
+                */
+               for (index = 0; index < tbl->it_size; index++) {
+                       tceval = ppc_md.tce_get(tbl, index + tbl->it_offset);
+                       /*
+                        * Freed TCE entry contains 0x7fffffffffffffff on JS20
+                        */
+                       if (tceval && (tceval != 0x7fffffffffffffffUL)) {
+                               __set_bit(index, tbl->it_map);
+                               tcecount++;
+                       }
+               }
+               if ((tbl->it_size - tcecount) < KDUMP_MIN_TCE_ENTRIES) {
+                       printk(KERN_WARNING "TCE table is full; ");
+                       printk(KERN_WARNING "freeing %d entries for the kdump boot\n",
+                               KDUMP_MIN_TCE_ENTRIES);
+                       for (index = tbl->it_size - KDUMP_MIN_TCE_ENTRIES;
+                               index < tbl->it_size; index++)
+                               __clear_bit(index, tbl->it_map);
+               }
+       }
+#else
        /* Clear the hardware table in case firmware left allocations in it */
        ppc_md.tce_free(tbl, tbl->it_offset, tbl->it_size);
+#endif
 
        if (!welcomed) {
                printk(KERN_INFO "IOMMU table initialized, virtual merging %s\n",
index 6e67b5b49ba1aedaa44a818835e396a0701a1185..3a9b78d0354205d27a92bc1fab94235ea12f46ee 100644 (file)
@@ -302,6 +302,17 @@ void __init find_legacy_serial_ports(void)
                of_node_put(isa);
        }
 
+       /* First fill our array with tsi-bridge ports */
+       for (np = NULL; (np = of_find_compatible_node(np, "serial", "ns16550")) != NULL;) {
+               struct device_node *tsi = of_get_parent(np);
+               if (tsi && !strcmp(tsi->type, "tsi-bridge")) {
+                       index = add_legacy_soc_port(np, np);
+                       if (index >= 0 && np == stdout)
+                               legacy_serial_console = index;
+               }
+               of_node_put(tsi);
+       }
+
 #ifdef CONFIG_PCI
        /* Next, try to locate PCI ports */
        for (np = NULL; (np = of_find_all_nodes(np));) {
index c02deaab26c78d241f15b6c805a38309fdfe52b7..73edc3c16137f532a84754536da5509575d3b927 100644 (file)
 static struct proc_dir_entry *proc_ppc64_lparcfg;
 #define LPARCFG_BUFF_SIZE 4096
 
-#ifdef CONFIG_PPC_ISERIES
-
 /*
- * For iSeries legacy systems, the PPA purr function is available from the
- * emulated_time_base field in the paca.
+ * Track sum of all purrs across all processors. This is used to further
+ * calculate usage values by different applications
  */
 static unsigned long get_purr(void)
 {
@@ -57,48 +55,31 @@ static unsigned long get_purr(void)
        int cpu;
 
        for_each_possible_cpu(cpu) {
-               sum_purr += lppaca[cpu].emulated_time_base;
+               if (firmware_has_feature(FW_FEATURE_ISERIES))
+                       sum_purr += lppaca[cpu].emulated_time_base;
+               else {
+                       struct cpu_usage *cu;
 
-#ifdef PURR_DEBUG
-               printk(KERN_INFO "get_purr for cpu (%d) has value (%ld) \n",
-                       cpu, lppaca[cpu].emulated_time_base);
-#endif
+                       cu = &per_cpu(cpu_usage_array, cpu);
+                       sum_purr += cu->current_tb;
+               }
        }
        return sum_purr;
 }
 
-#define lparcfg_write NULL
+#ifdef CONFIG_PPC_ISERIES
 
 /*
  * Methods used to fetch LPAR data when running on an iSeries platform.
  */
-static int lparcfg_data(struct seq_file *m, void *v)
+static int iseries_lparcfg_data(struct seq_file *m, void *v)
 {
-       unsigned long pool_id, lp_index;
+       unsigned long pool_id;
        int shared, entitled_capacity, max_entitled_capacity;
        int processors, max_processors;
        unsigned long purr = get_purr();
 
-       seq_printf(m, "%s %s \n", MODULE_NAME, MODULE_VERS);
-
        shared = (int)(get_lppaca()->shared_proc);
-       seq_printf(m, "serial_number=%c%c%c%c%c%c%c\n",
-                  e2a(xItExtVpdPanel.mfgID[2]),
-                  e2a(xItExtVpdPanel.mfgID[3]),
-                  e2a(xItExtVpdPanel.systemSerial[1]),
-                  e2a(xItExtVpdPanel.systemSerial[2]),
-                  e2a(xItExtVpdPanel.systemSerial[3]),
-                  e2a(xItExtVpdPanel.systemSerial[4]),
-                  e2a(xItExtVpdPanel.systemSerial[5]));
-
-       seq_printf(m, "system_type=%c%c%c%c\n",
-                  e2a(xItExtVpdPanel.machineType[0]),
-                  e2a(xItExtVpdPanel.machineType[1]),
-                  e2a(xItExtVpdPanel.machineType[2]),
-                  e2a(xItExtVpdPanel.machineType[3]));
-
-       lp_index = HvLpConfig_getLpIndex();
-       seq_printf(m, "partition_id=%d\n", (int)lp_index);
 
        seq_printf(m, "system_active_processors=%d\n",
                   (int)HvLpConfig_getSystemPhysicalProcessors());
@@ -137,6 +118,14 @@ static int lparcfg_data(struct seq_file *m, void *v)
 
        return 0;
 }
+
+#else                          /* CONFIG_PPC_ISERIES */
+
+static int iseries_lparcfg_data(struct seq_file *m, void *v)
+{
+       return 0;
+}
+
 #endif                         /* CONFIG_PPC_ISERIES */
 
 #ifdef CONFIG_PPC_PSERIES
@@ -213,22 +202,6 @@ static void h_pic(unsigned long *pool_idle_time, unsigned long *num_procs)
                log_plpar_hcall_return(rc, "H_PIC");
 }
 
-/* Track sum of all purrs across all processors. This is used to further */
-/* calculate usage values by different applications                       */
-
-static unsigned long get_purr(void)
-{
-       unsigned long sum_purr = 0;
-       int cpu;
-       struct cpu_usage *cu;
-
-       for_each_possible_cpu(cpu) {
-               cu = &per_cpu(cpu_usage_array, cpu);
-               sum_purr += cu->current_tb;
-       }
-       return sum_purr;
-}
-
 #define SPLPAR_CHARACTERISTICS_TOKEN 20
 #define SPLPAR_MAXLENGTH 1026*(sizeof(char))
 
@@ -333,35 +306,13 @@ static int lparcfg_count_active_processors(void)
        return count;
 }
 
-static int lparcfg_data(struct seq_file *m, void *v)
+static int pseries_lparcfg_data(struct seq_file *m, void *v)
 {
        int partition_potential_processors;
        int partition_active_processors;
-       struct device_node *rootdn;
-       const char *model = "";
-       const char *system_id = "";
-       unsigned int *lp_index_ptr, lp_index = 0;
        struct device_node *rtas_node;
        int *lrdrp = NULL;
 
-       rootdn = find_path_device("/");
-       if (rootdn) {
-               model = get_property(rootdn, "model", NULL);
-               system_id = get_property(rootdn, "system-id", NULL);
-               lp_index_ptr = (unsigned int *)
-                   get_property(rootdn, "ibm,partition-no", NULL);
-               if (lp_index_ptr)
-                       lp_index = *lp_index_ptr;
-       }
-
-       seq_printf(m, "%s %s \n", MODULE_NAME, MODULE_VERS);
-
-       seq_printf(m, "serial_number=%s\n", system_id);
-
-       seq_printf(m, "system_type=%s\n", model);
-
-       seq_printf(m, "partition_id=%d\n", (int)lp_index);
-
        rtas_node = find_path_device("/rtas");
        if (rtas_node)
                lrdrp = (int *)get_property(rtas_node, "ibm,lrdr-capacity",
@@ -549,8 +500,61 @@ out:
        return retval;
 }
 
+#else                          /* CONFIG_PPC_PSERIES */
+
+static int pseries_lparcfg_data(struct seq_file *m, void *v)
+{
+       return 0;
+}
+
+static ssize_t lparcfg_write(struct file *file, const char __user * buf,
+                            size_t count, loff_t * off)
+{
+       return count;
+}
+
 #endif                         /* CONFIG_PPC_PSERIES */
 
+static int lparcfg_data(struct seq_file *m, void *v)
+{
+       struct device_node *rootdn;
+       const char *model = "";
+       const char *system_id = "";
+       const char *tmp;
+       unsigned int *lp_index_ptr, lp_index = 0;
+
+       seq_printf(m, "%s %s \n", MODULE_NAME, MODULE_VERS);
+
+       rootdn = find_path_device("/");
+       if (rootdn) {
+               tmp = get_property(rootdn, "model", NULL);
+               if (tmp) {
+                       model = tmp;
+                       /* Skip "IBM," - see platforms/iseries/dt.c */
+                       if (firmware_has_feature(FW_FEATURE_ISERIES))
+                               model += 4;
+               }
+               tmp = get_property(rootdn, "system-id", NULL);
+               if (tmp) {
+                       system_id = tmp;
+                       /* Skip "IBM," - see platforms/iseries/dt.c */
+                       if (firmware_has_feature(FW_FEATURE_ISERIES))
+                               system_id += 4;
+               }
+               lp_index_ptr = (unsigned int *)
+                       get_property(rootdn, "ibm,partition-no", NULL);
+               if (lp_index_ptr)
+                       lp_index = *lp_index_ptr;
+       }
+       seq_printf(m, "serial_number=%s\n", system_id);
+       seq_printf(m, "system_type=%s\n", model);
+       seq_printf(m, "partition_id=%d\n", (int)lp_index);
+
+       if (firmware_has_feature(FW_FEATURE_ISERIES))
+               return iseries_lparcfg_data(m, v);
+       return pseries_lparcfg_data(m, v);
+}
+
 static int lparcfg_open(struct inode *inode, struct file *file)
 {
        return single_open(file, lparcfg_data, NULL);
@@ -569,7 +573,8 @@ int __init lparcfg_init(void)
        mode_t mode = S_IRUSR | S_IRGRP | S_IROTH;
 
        /* Allow writing if we have FW_FEATURE_SPLPAR */
-       if (firmware_has_feature(FW_FEATURE_SPLPAR)) {
+       if (firmware_has_feature(FW_FEATURE_SPLPAR) &&
+                       !firmware_has_feature(FW_FEATURE_ISERIES)) {
                lparcfg_fops.write = lparcfg_write;
                mode |= S_IWUSR;
        }
index a8fa04ef27cd79597a65842f8e9b380d8eb3d828..b438d45a068c6b0dd621b0f51520f9478b729539 100644 (file)
@@ -378,11 +378,13 @@ static void __init export_crashk_values(void)
        of_node_put(node);
 }
 
-void __init kexec_setup(void)
+static int __init kexec_setup(void)
 {
        export_htab_values();
        export_crashk_values();
+       return 0;
 }
+__initcall(kexec_setup);
 
 static int __init early_parse_crashk(char *p)
 {
diff --git a/arch/powerpc/kernel/misc.S b/arch/powerpc/kernel/misc.S
new file mode 100644 (file)
index 0000000..fc23040
--- /dev/null
@@ -0,0 +1,203 @@
+/*
+ * This file contains miscellaneous low-level functions.
+ *    Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org)
+ *
+ * Largely rewritten by Cort Dougan (cort@cs.nmt.edu)
+ * and Paul Mackerras.
+ *
+ * Adapted for iSeries by Mike Corrigan (mikejc@us.ibm.com)
+ * PPC64 updates by Dave Engebretsen (engebret@us.ibm.com)
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License
+ * as published by the Free Software Foundation; either version
+ * 2 of the License, or (at your option) any later version.
+ */
+#include <asm/ppc_asm.h>
+
+       .text
+
+#ifdef CONFIG_PPC64
+#define IN_SYNC                twi     0,r5,0; isync
+#define EIEIO_32
+#define SYNC_64                sync
+#else /* CONFIG_PPC32 */
+#define IN_SYNC
+#define EIEIO_32       eieio
+#define SYNC_64
+#endif
+/*
+ * Returns (address we are running at) - (address we were linked at)
+ * for use before the text and data are mapped to KERNELBASE.
+ */
+
+_GLOBAL(reloc_offset)
+       mflr    r0
+       bl      1f
+1:     mflr    r3
+       LOAD_REG_IMMEDIATE(r4,1b)
+       subf    r3,r4,r3
+       mtlr    r0
+       blr
+
+/*
+ * add_reloc_offset(x) returns x + reloc_offset().
+ */
+_GLOBAL(add_reloc_offset)
+       mflr    r0
+       bl      1f
+1:     mflr    r5
+       LOAD_REG_IMMEDIATE(r4,1b)
+       subf    r5,r4,r5
+       add     r3,r3,r5
+       mtlr    r0
+       blr
+
+/*
+ * I/O string operations
+ *
+ * insb(port, buf, len)
+ * outsb(port, buf, len)
+ * insw(port, buf, len)
+ * outsw(port, buf, len)
+ * insl(port, buf, len)
+ * outsl(port, buf, len)
+ * insw_ns(port, buf, len)
+ * outsw_ns(port, buf, len)
+ * insl_ns(port, buf, len)
+ * outsl_ns(port, buf, len)
+ *
+ * The *_ns versions don't do byte-swapping.
+ */
+_GLOBAL(_insb)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,1
+       blelr-
+00:    lbz     r5,0(r3)
+       eieio
+       stbu    r5,1(r4)
+       bdnz    00b
+       IN_SYNC
+       blr
+
+_GLOBAL(_outsb)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,1
+       blelr-
+00:    lbzu    r5,1(r4)
+       stb     r5,0(r3)
+       EIEIO_32
+       bdnz    00b
+       SYNC_64
+       blr
+
+_GLOBAL(_insw)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,2
+       blelr-
+00:    lhbrx   r5,0,r3
+       eieio
+       sthu    r5,2(r4)
+       bdnz    00b
+       IN_SYNC
+       blr
+
+_GLOBAL(_outsw)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,2
+       blelr-
+00:    lhzu    r5,2(r4)
+       EIEIO_32
+       sthbrx  r5,0,r3
+       bdnz    00b
+       SYNC_64
+       blr
+
+_GLOBAL(_insl)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,4
+       blelr-
+00:    lwbrx   r5,0,r3
+       eieio
+       stwu    r5,4(r4)
+       bdnz    00b
+       IN_SYNC
+       blr
+
+_GLOBAL(_outsl)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,4
+       blelr-
+00:    lwzu    r5,4(r4)
+       stwbrx  r5,0,r3
+       EIEIO_32
+       bdnz    00b
+       SYNC_64
+       blr
+
+#ifdef CONFIG_PPC32
+_GLOBAL(__ide_mm_insw)
+#endif
+_GLOBAL(_insw_ns)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,2
+       blelr-
+00:    lhz     r5,0(r3)
+       eieio
+       sthu    r5,2(r4)
+       bdnz    00b
+       IN_SYNC
+       blr
+
+#ifdef CONFIG_PPC32
+_GLOBAL(__ide_mm_outsw)
+#endif
+_GLOBAL(_outsw_ns)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,2
+       blelr-
+00:    lhzu    r5,2(r4)
+       sth     r5,0(r3)
+       EIEIO_32
+       bdnz    00b
+       SYNC_64
+       blr
+
+#ifdef CONFIG_PPC32
+_GLOBAL(__ide_mm_insl)
+#endif
+_GLOBAL(_insl_ns)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,4
+       blelr-
+00:    lwz     r5,0(r3)
+       eieio
+       stwu    r5,4(r4)
+       bdnz    00b
+       IN_SYNC
+       blr
+
+#ifdef CONFIG_PPC32
+_GLOBAL(__ide_mm_outsl)
+#endif
+_GLOBAL(_outsl_ns)
+       cmpwi   0,r5,0
+       mtctr   r5
+       subi    r4,r4,4
+       blelr-
+00:    lwzu    r5,4(r4)
+       stw     r5,0(r3)
+       EIEIO_32
+       bdnz    00b
+       SYNC_64
+       blr
+
index 01d3916c4cb13f6dc01b431328f3f2a1a49e4007..c74774e2175d9075a8a60a9b0636f18bf5fddc66 100644 (file)
@@ -60,32 +60,6 @@ _GLOBAL(mulhdu)
        addze   r3,r3
        blr
 
-/*
- * Returns (address we're running at) - (address we were linked at)
- * for use before the text and data are mapped to KERNELBASE.
- */
-_GLOBAL(reloc_offset)
-       mflr    r0
-       bl      1f
-1:     mflr    r3
-       LOAD_REG_IMMEDIATE(r4,1b)
-       subf    r3,r4,r3
-       mtlr    r0
-       blr
-
-/*
- * add_reloc_offset(x) returns x + reloc_offset().
- */
-_GLOBAL(add_reloc_offset)
-       mflr    r0
-       bl      1f
-1:     mflr    r5
-       LOAD_REG_IMMEDIATE(r4,1b)
-       subf    r5,r4,r5
-       add     r3,r3,r5
-       mtlr    r0
-       blr
-
 /*
  * sub_reloc_offset(x) returns x - reloc_offset().
  */
@@ -780,136 +754,6 @@ _GLOBAL(atomic_set_mask)
        bne-    10b
        blr
 
-/*
- * I/O string operations
- *
- * insb(port, buf, len)
- * outsb(port, buf, len)
- * insw(port, buf, len)
- * outsw(port, buf, len)
- * insl(port, buf, len)
- * outsl(port, buf, len)
- * insw_ns(port, buf, len)
- * outsw_ns(port, buf, len)
- * insl_ns(port, buf, len)
- * outsl_ns(port, buf, len)
- *
- * The *_ns versions don't do byte-swapping.
- */
-_GLOBAL(_insb)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,1
-       blelr-
-00:    lbz     r5,0(r3)
-       eieio
-       stbu    r5,1(r4)
-       bdnz    00b
-       blr
-
-_GLOBAL(_outsb)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,1
-       blelr-
-00:    lbzu    r5,1(r4)
-       stb     r5,0(r3)
-       eieio
-       bdnz    00b
-       blr
-
-_GLOBAL(_insw)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhbrx   r5,0,r3
-       eieio
-       sthu    r5,2(r4)
-       bdnz    00b
-       blr
-
-_GLOBAL(_outsw)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhzu    r5,2(r4)
-       eieio
-       sthbrx  r5,0,r3
-       bdnz    00b
-       blr
-
-_GLOBAL(_insl)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwbrx   r5,0,r3
-       eieio
-       stwu    r5,4(r4)
-       bdnz    00b
-       blr
-
-_GLOBAL(_outsl)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwzu    r5,4(r4)
-       stwbrx  r5,0,r3
-       eieio
-       bdnz    00b
-       blr
-
-_GLOBAL(__ide_mm_insw)
-_GLOBAL(_insw_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhz     r5,0(r3)
-       eieio
-       sthu    r5,2(r4)
-       bdnz    00b
-       blr
-
-_GLOBAL(__ide_mm_outsw)
-_GLOBAL(_outsw_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhzu    r5,2(r4)
-       sth     r5,0(r3)
-       eieio
-       bdnz    00b
-       blr
-
-_GLOBAL(__ide_mm_insl)
-_GLOBAL(_insl_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwz     r5,0(r3)
-       eieio
-       stwu    r5,4(r4)
-       bdnz    00b
-       blr
-
-_GLOBAL(__ide_mm_outsl)
-_GLOBAL(_outsl_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwzu    r5,4(r4)
-       stw     r5,0(r3)
-       eieio
-       bdnz    00b
-       blr
-
 /*
  * Extended precision shifts.
  *
index e8883d42c43c16c2d237d9cf81ea3a34a8105bd8..580891cb8ccb68766e4f5a28534eb29d81edea36 100644 (file)
@@ -1,14 +1,12 @@
 /*
- *  arch/powerpc/kernel/misc64.S
- *
  * This file contains miscellaneous low-level functions.
  *    Copyright (C) 1995-1996 Gary Thomas (gdt@linuxppc.org)
  *
  * Largely rewritten by Cort Dougan (cort@cs.nmt.edu)
  * and Paul Mackerras.
  * Adapted for iSeries by Mike Corrigan (mikejc@us.ibm.com)
- * PPC64 updates by Dave Engebretsen (engebret@us.ibm.com) 
- * 
+ * PPC64 updates by Dave Engebretsen (engebret@us.ibm.com)
+ *
  * 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
 
        .text
 
-/*
- * Returns (address we are running at) - (address we were linked at)
- * for use before the text and data are mapped to KERNELBASE.
- */
-
-_GLOBAL(reloc_offset)
-       mflr    r0
-       bl      1f
-1:     mflr    r3
-       LOAD_REG_IMMEDIATE(r4,1b)
-       subf    r3,r4,r3
-       mtlr    r0
-       blr
-
-/*
- * add_reloc_offset(x) returns x + reloc_offset().
- */
-_GLOBAL(add_reloc_offset)
-       mflr    r0
-       bl      1f
-1:     mflr    r5
-       LOAD_REG_IMMEDIATE(r4,1b)
-       subf    r5,r4,r5
-       add     r3,r3,r5
-       mtlr    r0
-       blr
-
 _GLOBAL(get_msr)
        mfmsr   r3
        blr
 
-_GLOBAL(get_dar)
-       mfdar   r3
-       blr
-
 _GLOBAL(get_srr0)
        mfsrr0  r3
        blr
@@ -72,10 +39,6 @@ _GLOBAL(get_srr0)
 _GLOBAL(get_srr1)
        mfsrr1  r3
        blr
-       
-_GLOBAL(get_sp)
-       mr      r3,r1
-       blr
 
 #ifdef CONFIG_IRQSTACKS
 _GLOBAL(call_do_softirq)
@@ -101,48 +64,6 @@ _GLOBAL(call___do_IRQ)
        blr
 #endif /* CONFIG_IRQSTACKS */
 
-       /*
- * To be called by C code which needs to do some operations with MMU
- * disabled. Note that interrupts have to be disabled by the caller
- * prior to calling us. The code called _MUST_ be in the RMO of course
- * and part of the linear mapping as we don't attempt to translate the
- * stack pointer at all. The function is called with the stack switched
- * to this CPU emergency stack
- *
- * prototype is void *call_with_mmu_off(void *func, void *data);
- *
- * the called function is expected to be of the form
- *
- * void *called(void *data); 
- */
-_GLOBAL(call_with_mmu_off)
-       mflr    r0                      /* get link, save it on stackframe */
-       std     r0,16(r1)
-       mr      r1,r5                   /* save old stack ptr */
-       ld      r1,PACAEMERGSP(r13)     /* get emerg. stack */
-       subi    r1,r1,STACK_FRAME_OVERHEAD
-       std     r0,16(r1)               /* save link on emerg. stack */
-       std     r5,0(r1)                /* save old stack ptr in backchain */
-       ld      r3,0(r3)                /* get to real function ptr (assume same TOC) */
-       bl      2f                      /* we need LR to return, continue at label 2 */
-
-       ld      r0,16(r1)               /* we return here from the call, get LR and */
-       ld      r1,0(r1)                /* .. old stack ptr */
-       mtspr   SPRN_SRR0,r0            /* and get back to virtual mode with these */
-       mfmsr   r4
-       ori     r4,r4,MSR_IR|MSR_DR
-       mtspr   SPRN_SRR1,r4
-       rfid
-
-2:     mtspr   SPRN_SRR0,r3            /* coming from above, enter real mode */
-       mr      r3,r4                   /* get parameter */
-       mfmsr   r0
-       ori     r0,r0,MSR_IR|MSR_DR
-       xori    r0,r0,MSR_IR|MSR_DR
-       mtspr   SPRN_SRR1,r0
-       rfid
-
-
        .section        ".toc","aw"
 PPC64_CACHES:
        .tc             ppc64_caches[TC],ppc64_caches
@@ -323,144 +244,6 @@ _GLOBAL(__flush_dcache_icache)
        bdnz    1b
        isync
        blr
-       
-/*
- * I/O string operations
- *
- * insb(port, buf, len)
- * outsb(port, buf, len)
- * insw(port, buf, len)
- * outsw(port, buf, len)
- * insl(port, buf, len)
- * outsl(port, buf, len)
- * insw_ns(port, buf, len)
- * outsw_ns(port, buf, len)
- * insl_ns(port, buf, len)
- * outsl_ns(port, buf, len)
- *
- * The *_ns versions don't do byte-swapping.
- */
-_GLOBAL(_insb)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,1
-       blelr-
-00:    lbz     r5,0(r3)
-       eieio
-       stbu    r5,1(r4)
-       bdnz    00b
-       twi     0,r5,0
-       isync
-       blr
-
-_GLOBAL(_outsb)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,1
-       blelr-
-00:    lbzu    r5,1(r4)
-       stb     r5,0(r3)
-       bdnz    00b
-       sync
-       blr     
-
-_GLOBAL(_insw)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhbrx   r5,0,r3
-       eieio
-       sthu    r5,2(r4)
-       bdnz    00b
-       twi     0,r5,0
-       isync
-       blr
-
-_GLOBAL(_outsw)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhzu    r5,2(r4)
-       sthbrx  r5,0,r3 
-       bdnz    00b
-       sync
-       blr     
-
-_GLOBAL(_insl)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwbrx   r5,0,r3
-       eieio
-       stwu    r5,4(r4)
-       bdnz    00b
-       twi     0,r5,0
-       isync
-       blr
-
-_GLOBAL(_outsl)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwzu    r5,4(r4)
-       stwbrx  r5,0,r3
-       bdnz    00b
-       sync
-       blr     
-
-/* _GLOBAL(ide_insw) now in drivers/ide/ide-iops.c */
-_GLOBAL(_insw_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhz     r5,0(r3)
-       eieio
-       sthu    r5,2(r4)
-       bdnz    00b
-       twi     0,r5,0
-       isync
-       blr
-
-/* _GLOBAL(ide_outsw) now in drivers/ide/ide-iops.c */
-_GLOBAL(_outsw_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,2
-       blelr-
-00:    lhzu    r5,2(r4)
-       sth     r5,0(r3)
-       bdnz    00b
-       sync
-       blr     
-
-_GLOBAL(_insl_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwz     r5,0(r3)
-       eieio
-       stwu    r5,4(r4)
-       bdnz    00b
-       twi     0,r5,0
-       isync
-       blr
-
-_GLOBAL(_outsl_ns)
-       cmpwi   0,r5,0
-       mtctr   r5
-       subi    r4,r4,4
-       blelr-
-00:    lwzu    r5,4(r4)
-       stw     r5,0(r3)
-       bdnz    00b
-       sync
-       blr     
 
 /*
  * identify_cpu and calls setup_cpu
@@ -605,6 +388,7 @@ _GLOBAL(real_writeb)
        blr
 #endif /* defined(CONFIG_PPC_PMAC) || defined(CONFIG_PPC_MAPLE) */
 
+#ifdef CONFIG_CPU_FREQ_PMAC64
 /*
  * SCOM access functions for 970 (FX only for now)
  *
@@ -673,6 +457,7 @@ _GLOBAL(scom970_write)
        /* restore interrupts */
        mtmsrd  r5,1
        blr
+#endif /* CONFIG_CPU_FREQ_PMAC64 */
 
 
 /*
index f505a8827e3ea67c81b0329b2af390b5ddf4e657..a0bb354c1c08154e070ea032b290b0e5a07d35d8 100644 (file)
@@ -16,7 +16,6 @@
 #include <asm/ptrace.h>
 #include <asm/page.h>
 #include <asm/lppaca.h>
-#include <asm/iseries/it_lp_queue.h>
 #include <asm/iseries/it_lp_reg_save.h>
 #include <asm/paca.h>
 
index 483455c5bb02e5ab00ae04ce6a138168e7f8075b..320c913435cd149a40cd2f8e4f16385184d7bde0 100644 (file)
@@ -30,6 +30,7 @@
 #include <linux/bitops.h>
 #include <linux/module.h>
 #include <linux/kexec.h>
+#include <linux/debugfs.h>
 
 #include <asm/prom.h>
 #include <asm/rtas.h>
@@ -952,6 +953,7 @@ static struct ibm_pa_feature {
        /* put this back once we know how to test if firmware does 64k IO */
        {CPU_FTR_CI_LARGE_PAGE, 0,      1, 2, 0},
 #endif
+       {CPU_FTR_REAL_LE, PPC_FEATURE_TRUE_LE, 5, 0, 0},
 };
 
 static void __init check_cpu_pa_features(unsigned long node)
@@ -1124,24 +1126,6 @@ static int __init early_init_dt_scan_chosen(unsigned long node,
                tce_alloc_end = *lprop;
 #endif
 
-#ifdef CONFIG_PPC_RTAS
-       /* To help early debugging via the front panel, we retrieve a minimal
-        * set of RTAS infos now if available
-        */
-       {
-               u64 *basep, *entryp, *sizep;
-
-               basep = of_get_flat_dt_prop(node, "linux,rtas-base", NULL);
-               entryp = of_get_flat_dt_prop(node, "linux,rtas-entry", NULL);
-               sizep = of_get_flat_dt_prop(node, "linux,rtas-size", NULL);
-               if (basep && entryp && sizep) {
-                       rtas.base = *basep;
-                       rtas.entry = *entryp;
-                       rtas.size = *sizep;
-               }
-       }
-#endif /* CONFIG_PPC_RTAS */
-
 #ifdef CONFIG_KEXEC
        lprop = (u64*)of_get_flat_dt_prop(node, "linux,crashkernel-base", NULL);
        if (lprop)
@@ -1326,6 +1310,11 @@ void __init early_init_devtree(void *params)
        /* Setup flat device-tree pointer */
        initial_boot_params = params;
 
+#ifdef CONFIG_PPC_RTAS
+       /* Some machines might need RTAS info for debugging, grab it now. */
+       of_scan_flat_dt(early_init_dt_scan_rtas, NULL);
+#endif
+
        /* Retrieve various informations from the /chosen node of the
         * device-tree, including the platform type, initrd location and
         * size, TCE reserve, and more ...
@@ -2148,3 +2137,27 @@ struct device_node *of_get_cpu_node(int cpu, unsigned int *thread)
        }
        return NULL;
 }
+
+#ifdef DEBUG
+static struct debugfs_blob_wrapper flat_dt_blob;
+
+static int __init export_flat_device_tree(void)
+{
+       struct dentry *d;
+
+       d = debugfs_create_dir("powerpc", NULL);
+       if (!d)
+               return 1;
+
+       flat_dt_blob.data = initial_boot_params;
+       flat_dt_blob.size = initial_boot_params->totalsize;
+
+       d = debugfs_create_blob("flat-device-tree", S_IFREG | S_IRUSR,
+                               d, &flat_dt_blob);
+       if (!d)
+               return 1;
+
+       return 0;
+}
+__initcall(export_flat_device_tree);
+#endif
index 17dc79198515d8f61f0879b10e9535dbbe5be9ab..4a4cb5598402731afaa5717b25607a5272bab6ec 100644 (file)
 struct rtas_t rtas = {
        .lock = SPIN_LOCK_UNLOCKED
 };
+EXPORT_SYMBOL(rtas);
 
 struct rtas_suspend_me_data {
        long waiting;
        struct rtas_args *args;
 };
 
-EXPORT_SYMBOL(rtas);
-
 DEFINE_SPINLOCK(rtas_data_buf_lock);
+EXPORT_SYMBOL(rtas_data_buf_lock);
+
 char rtas_data_buf[RTAS_DATA_BUF_SIZE] __cacheline_aligned;
+EXPORT_SYMBOL(rtas_data_buf);
+
 unsigned long rtas_rmo_buf;
 
 /*
@@ -106,11 +109,71 @@ static void call_rtas_display_status_delay(char c)
        }
 }
 
-void __init udbg_init_rtas(void)
+void __init udbg_init_rtas_panel(void)
 {
        udbg_putc = call_rtas_display_status_delay;
 }
 
+#ifdef CONFIG_UDBG_RTAS_CONSOLE
+
+/* If you think you're dying before early_init_dt_scan_rtas() does its
+ * work, you can hard code the token values for your firmware here and
+ * hardcode rtas.base/entry etc.
+ */
+static unsigned int rtas_putchar_token = RTAS_UNKNOWN_SERVICE;
+static unsigned int rtas_getchar_token = RTAS_UNKNOWN_SERVICE;
+
+static void udbg_rtascon_putc(char c)
+{
+       int tries;
+
+       if (!rtas.base)
+               return;
+
+       /* Add CRs before LFs */
+       if (c == '\n')
+               udbg_rtascon_putc('\r');
+
+       /* if there is more than one character to be displayed, wait a bit */
+       for (tries = 0; tries < 16; tries++) {
+               if (rtas_call(rtas_putchar_token, 1, 1, NULL, c) == 0)
+                       break;
+               udelay(1000);
+       }
+}
+
+static int udbg_rtascon_getc_poll(void)
+{
+       int c;
+
+       if (!rtas.base)
+               return -1;
+
+       if (rtas_call(rtas_getchar_token, 0, 2, &c))
+               return -1;
+
+       return c;
+}
+
+static int udbg_rtascon_getc(void)
+{
+       int c;
+
+       while ((c = udbg_rtascon_getc_poll()) == -1)
+               ;
+
+       return c;
+}
+
+
+void __init udbg_init_rtas_console(void)
+{
+       udbg_putc = udbg_rtascon_putc;
+       udbg_getc = udbg_rtascon_getc;
+       udbg_getc_poll = udbg_rtascon_getc_poll;
+}
+#endif /* CONFIG_UDBG_RTAS_CONSOLE */
+
 void rtas_progress(char *s, unsigned short hex)
 {
        struct device_node *root;
@@ -236,6 +299,7 @@ int rtas_token(const char *service)
        tokp = (int *) get_property(rtas.dev, service, NULL);
        return tokp ? *tokp : RTAS_UNKNOWN_SERVICE;
 }
+EXPORT_SYMBOL(rtas_token);
 
 #ifdef CONFIG_RTAS_ERROR_LOGGING
 /*
@@ -328,7 +392,7 @@ int rtas_call(int token, int nargs, int nret, int *outputs, ...)
        char *buff_copy = NULL;
        int ret;
 
-       if (token == RTAS_UNKNOWN_SERVICE)
+       if (!rtas.entry || token == RTAS_UNKNOWN_SERVICE)
                return -1;
 
        /* Gotta do something different here, use global lock for now... */
@@ -369,6 +433,7 @@ int rtas_call(int token, int nargs, int nret, int *outputs, ...)
        }
        return ret;
 }
+EXPORT_SYMBOL(rtas_call);
 
 /* For RTAS_BUSY (-2), delay for 1 millisecond.  For an extended busy status
  * code of 990n, perform the hinted delay of 10^n (last digit) milliseconds.
@@ -388,6 +453,7 @@ unsigned int rtas_busy_delay_time(int status)
 
        return ms;
 }
+EXPORT_SYMBOL(rtas_busy_delay_time);
 
 /* For an RTAS busy status code, perform the hinted delay. */
 unsigned int rtas_busy_delay(int status)
@@ -401,6 +467,7 @@ unsigned int rtas_busy_delay(int status)
 
        return ms;
 }
+EXPORT_SYMBOL(rtas_busy_delay);
 
 int rtas_error_rc(int rtas_rc)
 {
@@ -446,6 +513,7 @@ int rtas_get_power_level(int powerdomain, int *level)
                return rtas_error_rc(rc);
        return rc;
 }
+EXPORT_SYMBOL(rtas_get_power_level);
 
 int rtas_set_power_level(int powerdomain, int level, int *setlevel)
 {
@@ -463,6 +531,7 @@ int rtas_set_power_level(int powerdomain, int level, int *setlevel)
                return rtas_error_rc(rc);
        return rc;
 }
+EXPORT_SYMBOL(rtas_set_power_level);
 
 int rtas_get_sensor(int sensor, int index, int *state)
 {
@@ -480,6 +549,7 @@ int rtas_get_sensor(int sensor, int index, int *state)
                return rtas_error_rc(rc);
        return rc;
 }
+EXPORT_SYMBOL(rtas_get_sensor);
 
 int rtas_set_indicator(int indicator, int index, int new_value)
 {
@@ -497,6 +567,7 @@ int rtas_set_indicator(int indicator, int index, int new_value)
                return rtas_error_rc(rc);
        return rc;
 }
+EXPORT_SYMBOL(rtas_set_indicator);
 
 void rtas_restart(char *cmd)
 {
@@ -791,14 +862,34 @@ void __init rtas_initialize(void)
 #endif
 }
 
+int __init early_init_dt_scan_rtas(unsigned long node,
+               const char *uname, int depth, void *data)
+{
+       u32 *basep, *entryp, *sizep;
 
-EXPORT_SYMBOL(rtas_token);
-EXPORT_SYMBOL(rtas_call);
-EXPORT_SYMBOL(rtas_data_buf);
-EXPORT_SYMBOL(rtas_data_buf_lock);
-EXPORT_SYMBOL(rtas_busy_delay_time);
-EXPORT_SYMBOL(rtas_busy_delay);
-EXPORT_SYMBOL(rtas_get_sensor);
-EXPORT_SYMBOL(rtas_get_power_level);
-EXPORT_SYMBOL(rtas_set_power_level);
-EXPORT_SYMBOL(rtas_set_indicator);
+       if (depth != 1 || strcmp(uname, "rtas") != 0)
+               return 0;
+
+       basep  = of_get_flat_dt_prop(node, "linux,rtas-base", NULL);
+       entryp = of_get_flat_dt_prop(node, "linux,rtas-entry", NULL);
+       sizep  = of_get_flat_dt_prop(node, "rtas-size", NULL);
+
+       if (basep && entryp && sizep) {
+               rtas.base = *basep;
+               rtas.entry = *entryp;
+               rtas.size = *sizep;
+       }
+
+#ifdef CONFIG_UDBG_RTAS_CONSOLE
+       basep = of_get_flat_dt_prop(node, "put-term-char", NULL);
+       if (basep)
+               rtas_putchar_token = *basep;
+
+       basep = of_get_flat_dt_prop(node, "get-term-char", NULL);
+       if (basep)
+               rtas_getchar_token = *basep;
+#endif
+
+       /* break now */
+       return 1;
+}
index 78f3a5fd43f635b37a1186d056d11c78fb0897c2..175539c9afa066c9b3d2b3596423b0cda5e63a0c 100644 (file)
@@ -149,6 +149,13 @@ early_param("smt-enabled", early_smt_enabled);
 #define check_smt_enabled()
 #endif /* CONFIG_SMP */
 
+/* Put the paca pointer into r13 and SPRG3 */
+void __init setup_paca(int cpu)
+{
+       local_paca = &paca[cpu];
+       mtspr(SPRN_SPRG3, local_paca);
+}
+
 /*
  * Early initialization entry point. This is called by head.S
  * with MMU translation disabled. We rely on the "feature" of
@@ -170,6 +177,9 @@ early_param("smt-enabled", early_smt_enabled);
 
 void __init early_setup(unsigned long dt_ptr)
 {
+       /* Assume we're on cpu 0 for now. Don't write to the paca yet! */
+       setup_paca(0);
+
        /* Enable early debugging if any specified (see udbg.h) */
        udbg_early_init();
 
@@ -183,7 +193,7 @@ void __init early_setup(unsigned long dt_ptr)
        early_init_devtree(__va(dt_ptr));
 
        /* Now we know the logical id of our boot cpu, setup the paca. */
-       setup_boot_paca();
+       setup_paca(boot_cpuid);
 
        /* Fix up paca fields required for the boot cpu */
        get_paca()->cpu_start = 1;
@@ -350,19 +360,11 @@ void __init setup_system(void)
         */
        unflatten_device_tree();
 
-#ifdef CONFIG_KEXEC
-       kexec_setup();  /* requires unflattened device tree. */
-#endif
-
        /*
         * Fill the ppc64_caches & systemcfg structures with informations
         * retrieved from the device-tree. Need to be called before
         * finish_device_tree() since the later requires some of the
-        * informations filled up here to properly parse the interrupt
-        * tree.
-        * It also sets up the cache line sizes which allows to call
-        * routines like flush_icache_range (used by the hash init
-        * later on).
+        * informations filled up here to properly parse the interrupt tree.
         */
        initialize_cache_info();
 
index 52f5659534f48042da4f68ddaad02806f70a3a0c..fa6bd97b6b9d59c30fd4897dd241c53064d28339 100644 (file)
 #include <asm/firmware.h>
 #include <asm/processor.h>
 #endif
+#include <asm/kexec.h>
 
 #ifdef CONFIG_PPC64    /* XXX */
 #define _IO_BASE       pci_io_base
+#ifdef CONFIG_KEXEC
+cpumask_t cpus_in_sr = CPU_MASK_NONE;
+#endif
 #endif
 
 #ifdef CONFIG_DEBUGGER
@@ -97,7 +101,7 @@ static DEFINE_SPINLOCK(die_lock);
 
 int die(const char *str, struct pt_regs *regs, long err)
 {
-       static int die_counter, crash_dump_start = 0;
+       static int die_counter;
 
        if (debugger(regs))
                return 1;
@@ -137,21 +141,12 @@ int die(const char *str, struct pt_regs *regs, long err)
        print_modules();
        show_regs(regs);
        bust_spinlocks(0);
+       spin_unlock_irq(&die_lock);
 
-       if (!crash_dump_start && kexec_should_crash(current)) {
-               crash_dump_start = 1;
-               spin_unlock_irq(&die_lock);
+       if (kexec_should_crash(current) ||
+               kexec_sr_activated(smp_processor_id()))
                crash_kexec(regs);
-               /* NOTREACHED */
-       }
-       spin_unlock_irq(&die_lock);
-       if (crash_dump_start)
-               /*
-                * Only for soft-reset: Other CPUs will be responded to an IPI
-                * sent by first kexec CPU.
-                */
-               for(;;)
-                       ;
+       crash_kexec_secondary(regs);
 
        if (in_interrupt())
                panic("Fatal exception in interrupt");
@@ -215,6 +210,10 @@ void system_reset_exception(struct pt_regs *regs)
                        return;
        }
 
+#ifdef CONFIG_KEXEC
+       cpu_set(smp_processor_id(), cpus_in_sr);
+#endif
+
        die("System Reset", regs, SIGABRT);
 
        /* Must die if the interrupt is not recoverable */
index 67d9fd9ae2b53092cc2bf7727f29060f4331f921..759afd5e0d8a3c8a567c7609facb75264930a4aa 100644 (file)
@@ -34,9 +34,12 @@ void __init udbg_early_init(void)
 #elif defined(CONFIG_PPC_EARLY_DEBUG_G5)
        /* For use on Apple G5 machines */
        udbg_init_pmac_realmode();
-#elif defined(CONFIG_PPC_EARLY_DEBUG_RTAS)
+#elif defined(CONFIG_PPC_EARLY_DEBUG_RTAS_PANEL)
        /* RTAS panel debug */
-       udbg_init_rtas();
+       udbg_init_rtas_panel();
+#elif defined(CONFIG_PPC_EARLY_DEBUG_RTAS_CONSOLE)
+       /* RTAS console debug */
+       udbg_init_rtas_console();
 #elif defined(CONFIG_PPC_EARLY_DEBUG_MAPLE)
        /* Maple real mode debug */
        udbg_init_maple_realmode();
index a0f3cbd00d397a3356cf2162340580dcdfe6d78d..c90f124f3c71caed159f9eb04b6ab5b85d6194ed 100644 (file)
@@ -520,7 +520,7 @@ static inline int tlb_batching_enabled(void)
 }
 #endif
 
-void hpte_init_native(void)
+void __init hpte_init_native(void)
 {
        ppc_md.hpte_invalidate  = native_hpte_invalidate;
        ppc_md.hpte_updatepp    = native_hpte_updatepp;
@@ -530,5 +530,4 @@ void hpte_init_native(void)
        ppc_md.hpte_clear_all   = native_hpte_clear;
        if (tlb_batching_enabled())
                ppc_md.flush_hash_range = native_flush_hash_range;
-       htab_finish_init();
 }
index d03fd2b4445e1f43e5cde417b760e71f227d9f84..3cc6d68f71171f3d8953d753a7bd671c3b8fb474 100644 (file)
@@ -167,34 +167,12 @@ int htab_bolt_mapping(unsigned long vstart, unsigned long vend,
                hash = hpt_hash(va, shift);
                hpteg = ((hash & htab_hash_mask) * HPTES_PER_GROUP);
 
-               /* The crap below can be cleaned once ppd_md.probe() can
-                * set up the hash callbacks, thus we can just used the
-                * normal insert callback here.
-                */
-#ifdef CONFIG_PPC_ISERIES
-               if (machine_is(iseries))
-                       ret = iSeries_hpte_insert(hpteg, va,
-                                                 paddr,
-                                                 tmp_mode,
-                                                 HPTE_V_BOLTED,
-                                                 psize);
-               else
-#endif
-#ifdef CONFIG_PPC_PSERIES
-               if (machine_is(pseries) && firmware_has_feature(FW_FEATURE_LPAR))
-                       ret = pSeries_lpar_hpte_insert(hpteg, va,
-                                                      paddr,
-                                                      tmp_mode,
-                                                      HPTE_V_BOLTED,
-                                                      psize);
-               else
-#endif
-#ifdef CONFIG_PPC_MULTIPLATFORM
-                       ret = native_hpte_insert(hpteg, va,
-                                                paddr,
-                                                tmp_mode, HPTE_V_BOLTED,
-                                                psize);
-#endif
+               DBG("htab_bolt_mapping: calling %p\n", ppc_md.hpte_insert);
+
+               BUG_ON(!ppc_md.hpte_insert);
+               ret = ppc_md.hpte_insert(hpteg, va, paddr,
+                               tmp_mode, HPTE_V_BOLTED, psize);
+
                if (ret < 0)
                        break;
        }
@@ -413,6 +391,41 @@ void create_section_mapping(unsigned long start, unsigned long end)
 }
 #endif /* CONFIG_MEMORY_HOTPLUG */
 
+static inline void make_bl(unsigned int *insn_addr, void *func)
+{
+       unsigned long funcp = *((unsigned long *)func);
+       int offset = funcp - (unsigned long)insn_addr;
+
+       *insn_addr = (unsigned int)(0x48000001 | (offset & 0x03fffffc));
+       flush_icache_range((unsigned long)insn_addr, 4+
+                          (unsigned long)insn_addr);
+}
+
+static void __init htab_finish_init(void)
+{
+       extern unsigned int *htab_call_hpte_insert1;
+       extern unsigned int *htab_call_hpte_insert2;
+       extern unsigned int *htab_call_hpte_remove;
+       extern unsigned int *htab_call_hpte_updatepp;
+
+#ifdef CONFIG_PPC_64K_PAGES
+       extern unsigned int *ht64_call_hpte_insert1;
+       extern unsigned int *ht64_call_hpte_insert2;
+       extern unsigned int *ht64_call_hpte_remove;
+       extern unsigned int *ht64_call_hpte_updatepp;
+
+       make_bl(ht64_call_hpte_insert1, ppc_md.hpte_insert);
+       make_bl(ht64_call_hpte_insert2, ppc_md.hpte_insert);
+       make_bl(ht64_call_hpte_remove, ppc_md.hpte_remove);
+       make_bl(ht64_call_hpte_updatepp, ppc_md.hpte_updatepp);
+#endif /* CONFIG_PPC_64K_PAGES */
+
+       make_bl(htab_call_hpte_insert1, ppc_md.hpte_insert);
+       make_bl(htab_call_hpte_insert2, ppc_md.hpte_insert);
+       make_bl(htab_call_hpte_remove, ppc_md.hpte_remove);
+       make_bl(htab_call_hpte_updatepp, ppc_md.hpte_updatepp);
+}
+
 void __init htab_initialize(void)
 {
        unsigned long table;
@@ -525,6 +538,8 @@ void __init htab_initialize(void)
                                         mmu_linear_psize));
        }
 
+       htab_finish_init();
+
        DBG(" <- htab_initialize()\n");
 }
 #undef KB
@@ -787,16 +802,6 @@ void flush_hash_range(unsigned long number, int local)
        }
 }
 
-static inline void make_bl(unsigned int *insn_addr, void *func)
-{
-       unsigned long funcp = *((unsigned long *)func);
-       int offset = funcp - (unsigned long)insn_addr;
-
-       *insn_addr = (unsigned int)(0x48000001 | (offset & 0x03fffffc));
-       flush_icache_range((unsigned long)insn_addr, 4+
-                          (unsigned long)insn_addr);
-}
-
 /*
  * low_hash_fault is called when we the low level hash code failed
  * to instert a PTE due to an hypervisor error
@@ -815,28 +820,3 @@ void low_hash_fault(struct pt_regs *regs, unsigned long address)
        }
        bad_page_fault(regs, address, SIGBUS);
 }
-
-void __init htab_finish_init(void)
-{
-       extern unsigned int *htab_call_hpte_insert1;
-       extern unsigned int *htab_call_hpte_insert2;
-       extern unsigned int *htab_call_hpte_remove;
-       extern unsigned int *htab_call_hpte_updatepp;
-
-#ifdef CONFIG_PPC_64K_PAGES
-       extern unsigned int *ht64_call_hpte_insert1;
-       extern unsigned int *ht64_call_hpte_insert2;
-       extern unsigned int *ht64_call_hpte_remove;
-       extern unsigned int *ht64_call_hpte_updatepp;
-
-       make_bl(ht64_call_hpte_insert1, ppc_md.hpte_insert);
-       make_bl(ht64_call_hpte_insert2, ppc_md.hpte_insert);
-       make_bl(ht64_call_hpte_remove, ppc_md.hpte_remove);
-       make_bl(ht64_call_hpte_updatepp, ppc_md.hpte_updatepp);
-#endif /* CONFIG_PPC_64K_PAGES */
-
-       make_bl(htab_call_hpte_insert1, ppc_md.hpte_insert);
-       make_bl(htab_call_hpte_insert2, ppc_md.hpte_insert);
-       make_bl(htab_call_hpte_remove, ppc_md.hpte_remove);
-       make_bl(htab_call_hpte_updatepp, ppc_md.hpte_updatepp);
-}
index 65d18dca266ff0e3b26ed1212ca3da5990ee150c..e2051efa09c58d413d95814615c94f2d683b8b22 100644 (file)
@@ -44,7 +44,9 @@ again:
                return err;
 
        if (index > MAX_CONTEXT) {
+               spin_lock(&mmu_context_lock);
                idr_remove(&mmu_context_idr, index);
+               spin_unlock(&mmu_context_lock);
                return -ENOMEM;
        }
 
index 3a87863d287611d94984dc06c35a2ade3d6c5449..d1ecc0f9ab586164277dd12c27021af74d00a836 100644 (file)
@@ -7,6 +7,7 @@ choice
 
 config MPC8641_HPCN
        bool "Freescale MPC8641 HPCN"
+       select PPC_I8259
        help
          This option enables support for the MPC8641 HPCN board.
 
@@ -28,9 +29,4 @@ config PPC_INDIRECT_PCI_BE
        depends on PPC_86xx
        default y
 
-config PPC_STD_MMU
-       bool
-       depends on PPC_86xx
-       default y
-
 endmenu
index 7be796c5d5c942c7a0d1dff0c3c9666ccc0a1211..476a6eeee710d314eb2ad4eba2a2987b71d5d9aa 100644 (file)
@@ -2,9 +2,6 @@
 # Makefile for the PowerPC 86xx linux kernel.
 #
 
-
-ifeq ($(CONFIG_PPC_86xx),y)
 obj-$(CONFIG_SMP)              += mpc86xx_smp.o
-endif
 obj-$(CONFIG_MPC8641_HPCN)     += mpc86xx_hpcn.o
 obj-$(CONFIG_PCI)              += pci.o mpc86xx_pcie.o
index 5042253758b7b30a295cfcef994c1d206f3eccd2..5d2bcf78cef70e2ac323877e7af79c76d0ed9496 100644 (file)
@@ -14,7 +14,6 @@
 #ifndef __MPC8641_HPCN_H__
 #define __MPC8641_HPCN_H__
 
-#include <linux/config.h>
 #include <linux/init.h>
 
 /* PCI interrupt controller */
index e3c9e4f417d39f95505e118c7a7b5dfedef743a6..2834462590b809ae80de941d77a46aa925bc24e1 100644 (file)
  * mpc86xx_* files. Mostly for use by mpc86xx_setup().
  */
 
-extern int __init add_bridge(struct device_node *dev);
+extern int add_bridge(struct device_node *dev);
 
-extern void __init setup_indirect_pcie(struct pci_controller *hose,
+extern int mpc86xx_exclude_device(u_char bus, u_char devfn);
+
+extern void setup_indirect_pcie(struct pci_controller *hose,
                                       u32 cfg_addr, u32 cfg_data);
-extern void __init setup_indirect_pcie_nomap(struct pci_controller *hose,
+extern void setup_indirect_pcie_nomap(struct pci_controller *hose,
                                             void __iomem *cfg_addr,
                                             void __iomem *cfg_data);
 
index 483c21df181ec1e9938de9295fa3a199a4a6eb34..ebae73eb00630f460a926e9b56dfbf004cd1756d 100644 (file)
@@ -12,7 +12,6 @@
  * option) any later version.
  */
 
-#include <linux/config.h>
 #include <linux/stddef.h>
 #include <linux/kernel.h>
 #include <linux/pci.h>
@@ -36,6 +35,7 @@
 #include <sysdev/fsl_soc.h>
 
 #include "mpc86xx.h"
+#include "mpc8641_hpcn.h"
 
 #ifndef CONFIG_PCI
 unsigned long isa_io_base = 0;
@@ -186,17 +186,130 @@ mpc86xx_map_irq(struct pci_dev *dev, unsigned char idsel, unsigned char pin)
        return PCI_IRQ_TABLE_LOOKUP + I8259_OFFSET;
 }
 
+static void __devinit quirk_ali1575(struct pci_dev *dev)
+{
+       unsigned short temp;
+
+       /*
+        * ALI1575 interrupts route table setup:
+        *
+        * IRQ pin   IRQ#
+        * PIRQA ---- 3
+        * PIRQB ---- 4
+        * PIRQC ---- 5
+        * PIRQD ---- 6
+        * PIRQE ---- 9
+        * PIRQF ---- 10
+        * PIRQG ---- 11
+        * PIRQH ---- 12
+        *
+        * interrupts for PCI slot0 -- PIRQA / PIRQB / PIRQC / PIRQD
+        *                PCI slot1 -- PIRQB / PIRQC / PIRQD / PIRQA
+        */
+       pci_write_config_dword(dev, 0x48, 0xb9317542);
+
+       /* USB 1.1 OHCI controller 1, interrupt: PIRQE */
+       pci_write_config_byte(dev, 0x86, 0x0c);
+
+       /* USB 1.1 OHCI controller 2, interrupt: PIRQF */
+       pci_write_config_byte(dev, 0x87, 0x0d);
+
+       /* USB 1.1 OHCI controller 3, interrupt: PIRQH */
+       pci_write_config_byte(dev, 0x88, 0x0f);
+
+       /* USB 2.0 controller, interrupt: PIRQ7 */
+       pci_write_config_byte(dev, 0x74, 0x06);
+
+       /* Audio controller, interrupt: PIRQE */
+       pci_write_config_byte(dev, 0x8a, 0x0c);
+
+       /* Modem controller, interrupt: PIRQF */
+       pci_write_config_byte(dev, 0x8b, 0x0d);
+
+       /* HD audio controller, interrupt: PIRQG */
+       pci_write_config_byte(dev, 0x8c, 0x0e);
+
+       /* Serial ATA interrupt: PIRQD */
+       pci_write_config_byte(dev, 0x8d, 0x0b);
+
+       /* SMB interrupt: PIRQH */
+       pci_write_config_byte(dev, 0x8e, 0x0f);
+
+       /* PMU ACPI SCI interrupt: PIRQH */
+       pci_write_config_byte(dev, 0x8f, 0x0f);
+
+       /* Primary PATA IDE IRQ: 14
+        * Secondary PATA IDE IRQ: 15
+        */
+       pci_write_config_byte(dev, 0x44, 0x3d);
+       pci_write_config_byte(dev, 0x75, 0x0f);
+
+       /* Set IRQ14 and IRQ15 to legacy IRQs */
+       pci_read_config_word(dev, 0x46, &temp);
+       temp |= 0xc000;
+       pci_write_config_word(dev, 0x46, temp);
+
+       /* Set i8259 interrupt trigger
+        * IRQ 3:  Level
+        * IRQ 4:  Level
+        * IRQ 5:  Level
+        * IRQ 6:  Level
+        * IRQ 7:  Level
+        * IRQ 9:  Level
+        * IRQ 10: Level
+        * IRQ 11: Level
+        * IRQ 12: Level
+        * IRQ 14: Edge
+        * IRQ 15: Edge
+        */
+       outb(0xfa, 0x4d0);
+       outb(0x1e, 0x4d1);
+}
 
-int
-mpc86xx_exclude_device(u_char bus, u_char devfn)
+static void __devinit quirk_uli5288(struct pci_dev *dev)
 {
-#if !defined(CONFIG_PCI)
-       if (bus == 0 && PCI_SLOT(devfn) == 0)
-               return PCIBIOS_DEVICE_NOT_FOUND;
-#endif
+       unsigned char c;
+
+       pci_read_config_byte(dev,0x83,&c);
+       c |= 0x80;
+       pci_write_config_byte(dev, 0x83, c);
+
+       pci_write_config_byte(dev, 0x09, 0x01);
+       pci_write_config_byte(dev, 0x0a, 0x06);
+
+       pci_read_config_byte(dev,0x83,&c);
+       c &= 0x7f;
+       pci_write_config_byte(dev, 0x83, c);
 
-       return PCIBIOS_SUCCESSFUL;
+       pci_read_config_byte(dev,0x84,&c);
+       c |= 0x01;
+       pci_write_config_byte(dev, 0x84, c);
 }
+
+static void __devinit quirk_uli5229(struct pci_dev *dev)
+{
+       unsigned short temp;
+       pci_write_config_word(dev, 0x04, 0x0405);
+       pci_read_config_word(dev, 0x4a, &temp);
+       temp |= 0x1000;
+       pci_write_config_word(dev, 0x4a, temp);
+}
+
+static void __devinit early_uli5249(struct pci_dev *dev)
+{
+       unsigned char temp;
+       pci_write_config_word(dev, 0x04, 0x0007);
+       pci_read_config_byte(dev, 0x7c, &temp);
+       pci_write_config_byte(dev, 0x7c, 0x80);
+       pci_write_config_byte(dev, 0x09, 0x01);
+       pci_write_config_byte(dev, 0x7c, temp);
+       dev->class |= 0x1;
+}
+
+DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x1575, quirk_ali1575);
+DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5288, quirk_uli5288);
+DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5229, quirk_uli5229);
+DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_AL, 0x5249, early_uli5249);
 #endif /* CONFIG_PCI */
 
 
index 944ec4b714160c5b9498a4a641e7be20c9ec2950..bb7fb41933ad8abe557ae857ceaaf5b8d3f22d53 100644 (file)
@@ -10,7 +10,6 @@
  * option) any later version.
  */
 
-#include <linux/config.h>
 #include <linux/stddef.h>
 #include <linux/kernel.h>
 #include <linux/init.h>
@@ -34,8 +33,8 @@ extern unsigned long __secondary_hold_acknowledge;
 static void __init
 smp_86xx_release_core(int nr)
 {
-       void *mcm_vaddr;
-       unsigned long vaddr, pcr;
+       __be32 __iomem *mcm_vaddr;
+       unsigned long pcr;
 
        if (nr < 0 || nr >= NR_CPUS)
                return;
@@ -45,10 +44,9 @@ smp_86xx_release_core(int nr)
         */
        mcm_vaddr = ioremap(get_immrbase() + MPC86xx_MCM_OFFSET,
                            MPC86xx_MCM_SIZE);
-       vaddr = (unsigned long)mcm_vaddr +  MCM_PORT_CONFIG_OFFSET;
-       pcr = in_be32((volatile unsigned *)vaddr);
+       pcr = in_be32(mcm_vaddr + (MCM_PORT_CONFIG_OFFSET >> 2));
        pcr |= 1 << (nr + 24);
-       out_be32((volatile unsigned *)vaddr, pcr);
+       out_be32(mcm_vaddr + (MCM_PORT_CONFIG_OFFSET >> 2), pcr);
 }
 
 
index 5180df7c75bc34b566a6e66f72edb59e477bd711..bc5139043112e934f340b2691dabddadad355abc 100644 (file)
@@ -12,7 +12,6 @@
  * option) any later version.
  */
 
-#include <linux/config.h>
 #include <linux/types.h>
 #include <linux/module.h>
 #include <linux/init.h>
@@ -122,15 +121,12 @@ static void __init setup_pcie_atmu(struct pci_controller *hose, struct resource
 static void __init
 mpc86xx_setup_pcie(struct pci_controller *hose, u32 pcie_offset, u32 pcie_size)
 {
-       volatile struct ccsr_pex *pcie;
        u16 cmd;
        unsigned int temps;
 
        DBG("PCIE host controller register offset 0x%08x, size 0x%08x.\n",
                        pcie_offset, pcie_size);
 
-       pcie = ioremap(pcie_offset, pcie_size);
-
        early_read_config_word(hose, 0, 0, PCI_COMMAND, &cmd);
        cmd |= PCI_COMMAND_SERR | PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY
            | PCI_COMMAND_IO;
@@ -144,6 +140,14 @@ mpc86xx_setup_pcie(struct pci_controller *hose, u32 pcie_offset, u32 pcie_size)
        early_write_config_dword(hose, 0, 0, PCI_PRIMARY_BUS, temps);
 }
 
+int mpc86xx_exclude_device(u_char bus, u_char devfn)
+{
+       if (bus == 0 && PCI_SLOT(devfn) == 0)
+               return PCIBIOS_DEVICE_NOT_FOUND;
+
+       return PCIBIOS_SUCCESSFUL;
+}
+
 int __init add_bridge(struct device_node *dev)
 {
        int len;
@@ -198,128 +202,3 @@ int __init add_bridge(struct device_node *dev)
 
        return 0;
 }
-
-static void __devinit quirk_ali1575(struct pci_dev *dev)
-{
-       unsigned short temp;
-
-       /*
-        * ALI1575 interrupts route table setup:
-        *
-        * IRQ pin   IRQ#
-        * PIRQA ---- 3
-        * PIRQB ---- 4
-        * PIRQC ---- 5
-        * PIRQD ---- 6
-        * PIRQE ---- 9
-        * PIRQF ---- 10
-        * PIRQG ---- 11
-        * PIRQH ---- 12
-        *
-        * interrupts for PCI slot0 -- PIRQA / PIRQB / PIRQC / PIRQD
-        *                PCI slot1 -- PIRQB / PIRQC / PIRQD / PIRQA
-        */
-       pci_write_config_dword(dev, 0x48, 0xb9317542);
-
-       /* USB 1.1 OHCI controller 1, interrupt: PIRQE */
-       pci_write_config_byte(dev, 0x86, 0x0c);
-
-       /* USB 1.1 OHCI controller 2, interrupt: PIRQF */
-       pci_write_config_byte(dev, 0x87, 0x0d);
-
-       /* USB 1.1 OHCI controller 3, interrupt: PIRQH */
-       pci_write_config_byte(dev, 0x88, 0x0f);
-
-       /* USB 2.0 controller, interrupt: PIRQ7 */
-       pci_write_config_byte(dev, 0x74, 0x06);
-
-       /* Audio controller, interrupt: PIRQE */
-       pci_write_config_byte(dev, 0x8a, 0x0c);
-
-       /* Modem controller, interrupt: PIRQF */
-       pci_write_config_byte(dev, 0x8b, 0x0d);
-
-       /* HD audio controller, interrupt: PIRQG */
-       pci_write_config_byte(dev, 0x8c, 0x0e);
-
-       /* Serial ATA interrupt: PIRQD */
-       pci_write_config_byte(dev, 0x8d, 0x0b);
-
-       /* SMB interrupt: PIRQH */
-       pci_write_config_byte(dev, 0x8e, 0x0f);
-
-       /* PMU ACPI SCI interrupt: PIRQH */
-       pci_write_config_byte(dev, 0x8f, 0x0f);
-
-       /* Primary PATA IDE IRQ: 14
-        * Secondary PATA IDE IRQ: 15
-        */
-       pci_write_config_byte(dev, 0x44, 0x3d);
-       pci_write_config_byte(dev, 0x75, 0x0f);
-
-       /* Set IRQ14 and IRQ15 to legacy IRQs */
-       pci_read_config_word(dev, 0x46, &temp);
-       temp |= 0xc000;
-       pci_write_config_word(dev, 0x46, temp);
-
-       /* Set i8259 interrupt trigger
-        * IRQ 3:  Level
-        * IRQ 4:  Level
-        * IRQ 5:  Level
-        * IRQ 6:  Level
-        * IRQ 7:  Level
-        * IRQ 9:  Level
-        * IRQ 10: Level
-        * IRQ 11: Level
-        * IRQ 12: Level
-        * IRQ 14: Edge
-        * IRQ 15: Edge
-        */
-       outb(0xfa, 0x4d0);
-       outb(0x1e, 0x4d1);
-}
-
-static void __devinit quirk_uli5288(struct pci_dev *dev)
-{
-       unsigned char c;
-
-       pci_read_config_byte(dev,0x83,&c);
-       c |= 0x80;
-       pci_write_config_byte(dev, 0x83, c);
-
-       pci_write_config_byte(dev, 0x09, 0x01);
-       pci_write_config_byte(dev, 0x0a, 0x06);
-
-       pci_read_config_byte(dev,0x83,&c);
-       c &= 0x7f;
-       pci_write_config_byte(dev, 0x83, c);
-
-       pci_read_config_byte(dev,0x84,&c);
-       c |= 0x01;
-       pci_write_config_byte(dev, 0x84, c);
-}
-
-static void __devinit quirk_uli5229(struct pci_dev *dev)
-{
-       unsigned short temp;
-       pci_write_config_word(dev, 0x04, 0x0405);
-       pci_read_config_word(dev, 0x4a, &temp);
-       temp |= 0x1000;
-       pci_write_config_word(dev, 0x4a, temp);
-}
-
-static void __devinit early_uli5249(struct pci_dev *dev)
-{
-       unsigned char temp;
-       pci_write_config_word(dev, 0x04, 0x0007);
-       pci_read_config_byte(dev, 0x7c, &temp);
-       pci_write_config_byte(dev, 0x7c, 0x80);
-       pci_write_config_byte(dev, 0x09, 0x01);
-       pci_write_config_byte(dev, 0x7c, temp);
-       dev->class |= 0x1;
-}
-
-DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x1575, quirk_ali1575);
-DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5288, quirk_uli5288);
-DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_AL, 0x5229, quirk_uli5229);
-DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_AL, 0x5249, early_uli5249);
index 292863694562b713b1ae194ba85b102ebf994942..5cf46dc57895671e5c17f1170f879f4a2d0f0730 100644 (file)
@@ -14,3 +14,4 @@ obj-$(CONFIG_PPC_PSERIES)     += pseries/
 obj-$(CONFIG_PPC_ISERIES)      += iseries/
 obj-$(CONFIG_PPC_MAPLE)                += maple/
 obj-$(CONFIG_PPC_CELL)         += cell/
+obj-$(CONFIG_EMBEDDED6xx)      += embedded6xx/
index 352bbbacde9ad478fe8a8f02603cd3ed5be26e22..0c8c7b6ab897657866c37212195f87acba59a860 100644 (file)
@@ -6,6 +6,7 @@ config SPU_FS
        default m
        depends on PPC_CELL
        select SPU_BASE
+       select MEMORY_HOTPLUG
        help
          The SPU file system is used to access Synergistic Processing
          Units on machines implementing the Broadband Processor
@@ -18,7 +19,6 @@ config SPU_BASE
 config SPUFS_MMAP
        bool
        depends on SPU_FS && SPARSEMEM
-       select MEMORY_HOTPLUG
        default y
 
 config CBE_RAS
index 3d1831d331e5de73c8f17ae3b789610d438ed04b..00d112f92272fcda65c20adece8499b68e6bb318 100644 (file)
@@ -125,8 +125,6 @@ static void __init cell_init_early(void)
 {
        DBG(" -> cell_init_early()\n");
 
-       hpte_init_native();
-
        cell_init_iommu();
 
        ppc64_interrupt_controller = IC_CELL_PIC;
@@ -139,11 +137,17 @@ static int __init cell_probe(void)
 {
        unsigned long root = of_get_flat_dt_root();
 
-       if (of_flat_dt_is_compatible(root, "IBM,CBEA") ||
-           of_flat_dt_is_compatible(root, "IBM,CPBW-1.0"))
-               return 1;
+       if (!of_flat_dt_is_compatible(root, "IBM,CBEA") &&
+           !of_flat_dt_is_compatible(root, "IBM,CPBW-1.0"))
+               return 0;
+
+#ifdef CONFIG_UDBG_RTAS_CONSOLE
+       udbg_init_rtas_console();
+#endif
+
+       hpte_init_native();
 
-       return 0;
+       return 1;
 }
 
 /*
index db82f503ba2cc53ad11cfca0ac2193a9ff8d2a99..b306723abb87ba2f07f3169cfed713e54dc9e152 100644 (file)
@@ -168,12 +168,12 @@ spu_irq_class_0_bottom(struct spu *spu)
 
        stat &= mask;
 
-       if (stat & 1) /* invalid MFC DMA */
-               __spu_trap_invalid_dma(spu);
-
-       if (stat & 2) /* invalid DMA alignment */
+       if (stat & 1) /* invalid DMA alignment */
                __spu_trap_dma_align(spu);
 
+       if (stat & 2) /* invalid MFC DMA */
+               __spu_trap_invalid_dma(spu);
+
        if (stat & 4) /* error on SPU */
                __spu_trap_error(spu);
 
index 7854a380dce257c13732f7a067fa8f58941e6bae..58e794f9da1b6a5b920f95ba6fe57f0f054d1cb7 100644 (file)
@@ -204,7 +204,7 @@ static int spufs_cntl_mmap(struct file *file, struct vm_area_struct *vma)
 
        vma->vm_flags |= VM_RESERVED;
        vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot)
-                                    | _PAGE_NO_CACHE);
+                                    | _PAGE_NO_CACHE | _PAGE_GUARDED);
 
        vma->vm_ops = &spufs_cntl_mmap_vmops;
        return 0;
@@ -675,7 +675,7 @@ static int spufs_signal1_mmap(struct file *file, struct vm_area_struct *vma)
 
        vma->vm_flags |= VM_RESERVED;
        vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot)
-                                    | _PAGE_NO_CACHE);
+                                    | _PAGE_NO_CACHE | _PAGE_GUARDED);
 
        vma->vm_ops = &spufs_signal1_mmap_vmops;
        return 0;
@@ -762,7 +762,7 @@ static int spufs_signal2_mmap(struct file *file, struct vm_area_struct *vma)
        /* FIXME: */
        vma->vm_flags |= VM_RESERVED;
        vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot)
-                                    | _PAGE_NO_CACHE);
+                                    | _PAGE_NO_CACHE | _PAGE_GUARDED);
 
        vma->vm_ops = &spufs_signal2_mmap_vmops;
        return 0;
@@ -850,7 +850,7 @@ static int spufs_mss_mmap(struct file *file, struct vm_area_struct *vma)
 
        vma->vm_flags |= VM_RESERVED;
        vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot)
-                                    | _PAGE_NO_CACHE);
+                                    | _PAGE_NO_CACHE | _PAGE_GUARDED);
 
        vma->vm_ops = &spufs_mss_mmap_vmops;
        return 0;
@@ -899,7 +899,7 @@ static int spufs_mfc_mmap(struct file *file, struct vm_area_struct *vma)
 
        vma->vm_flags |= VM_RESERVED;
        vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot)
-                                    | _PAGE_NO_CACHE);
+                                    | _PAGE_NO_CACHE | _PAGE_GUARDED);
 
        vma->vm_ops = &spufs_mfc_mmap_vmops;
        return 0;
index a656d810a44aa6b6f34690deefd4dc8c65c617ab..c7fea2cca5346fbbd675233bc2506fd1adc9576b 100644 (file)
@@ -464,7 +464,8 @@ static inline void wait_purge_complete(struct spu_state *csa, struct spu *spu)
         *     Poll MFC_CNTL[Ps] until value '11' is read
         *     (purge complete).
         */
-       POLL_WHILE_FALSE(in_be64(&priv2->mfc_control_RW) &
+       POLL_WHILE_FALSE((in_be64(&priv2->mfc_control_RW) &
+                        MFC_CNTL_PURGE_DMA_STATUS_MASK) ==
                         MFC_CNTL_PURGE_DMA_COMPLETE);
 }
 
@@ -1028,7 +1029,8 @@ static inline void wait_suspend_mfc_complete(struct spu_state *csa,
         * Restore, Step 47.
         *     Poll MFC_CNTL[Ss] until 11 is returned.
         */
-       POLL_WHILE_FALSE(in_be64(&priv2->mfc_control_RW) &
+       POLL_WHILE_FALSE((in_be64(&priv2->mfc_control_RW) &
+                        MFC_CNTL_SUSPEND_DMA_STATUS_MASK) ==
                         MFC_CNTL_SUSPEND_COMPLETE);
 }
 
index 4fdbc9ae876b495d05edcc906276eaa4a7625d86..ba07a9a7c0398718f91e61d3e4c037dd9ae83503 100644 (file)
@@ -74,6 +74,16 @@ config SANDPOINT
          Select SANDPOINT if configuring for a Motorola Sandpoint X3
          (any flavor).
 
+config MPC7448HPC2
+       bool "Freescale MPC7448HPC2(Taiga)"
+       select TSI108_BRIDGE
+       select DEFAULT_UIMAGE
+       select PPC_UDBG_16550
+       select MPIC
+       help
+         Select MPC7448HPC2 if configuring for Freescale MPC7448HPC2 (Taiga)
+         platform
+
 config RADSTONE_PPC7D
        bool "Radstone Technology PPC7D board"
        select PPC_I8259
@@ -221,6 +231,11 @@ config MV64X60
        select PPC_INDIRECT_PCI
        default y
 
+config TSI108_BRIDGE
+       bool
+       depends on MPC7448HPC2
+       default y
+
 menu "Set bridge options"
        depends on MV64X60
 
diff --git a/arch/powerpc/platforms/embedded6xx/Makefile b/arch/powerpc/platforms/embedded6xx/Makefile
new file mode 100644 (file)
index 0000000..fa499fe
--- /dev/null
@@ -0,0 +1,4 @@
+#
+# Makefile for the 6xx/7xx/7xxxx linux kernel.
+#
+obj-$(CONFIG_MPC7448HPC2)      += mpc7448_hpc2.o
diff --git a/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.c b/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.c
new file mode 100644 (file)
index 0000000..d7a4fc7
--- /dev/null
@@ -0,0 +1,335 @@
+/*
+ * mpc7448_hpc2.c
+ *
+ * Board setup routines for the Freescale Taiga platform
+ *
+ * Author: Jacob Pan
+ *      jacob.pan@freescale.com
+ * Author: Xianghua Xiao
+ *       x.xiao@freescale.com
+ * Maintainer: Roy Zang <tie-fei.zang@freescale.com>
+ *     Add Flat Device Tree support fot mpc7448hpc2 board
+ *
+ * Copyright 2004-2006 Freescale Semiconductor, Inc.
+ *
+ * This file is licensed under
+ * the terms of the GNU General Public License version 2.  This program
+ * is licensed "as is" without any warranty of any kind, whether express
+ * or implied.
+ */
+
+#include <linux/config.h>
+#include <linux/stddef.h>
+#include <linux/kernel.h>
+#include <linux/pci.h>
+#include <linux/kdev_t.h>
+#include <linux/console.h>
+#include <linux/delay.h>
+#include <linux/irq.h>
+#include <linux/ide.h>
+#include <linux/seq_file.h>
+#include <linux/root_dev.h>
+#include <linux/serial.h>
+#include <linux/tty.h>
+#include <linux/serial_core.h>
+
+#include <asm/system.h>
+#include <asm/time.h>
+#include <asm/machdep.h>
+#include <asm/prom.h>
+#include <asm/udbg.h>
+#include <asm/tsi108.h>
+#include <asm/pci-bridge.h>
+#include <asm/reg.h>
+#include <mm/mmu_decl.h>
+#include "mpc7448_hpc2.h"
+#include <asm/tsi108_irq.h>
+#include <asm/mpic.h>
+
+#undef DEBUG
+#ifdef DEBUG
+#define DBG(fmt...) do { printk(fmt); } while(0)
+#else
+#define DBG(fmt...) do { } while(0)
+#endif
+
+#ifndef CONFIG_PCI
+isa_io_base = MPC7448_HPC2_ISA_IO_BASE;
+isa_mem_base = MPC7448_HPC2_ISA_MEM_BASE;
+pci_dram_offset = MPC7448_HPC2_PCI_MEM_OFFSET;
+#endif
+
+extern int tsi108_setup_pci(struct device_node *dev);
+extern void _nmask_and_or_msr(unsigned long nmask, unsigned long or_val);
+extern void tsi108_pci_int_init(void);
+extern int tsi108_irq_cascade(struct pt_regs *regs, void *unused);
+
+/*
+ * Define all of the IRQ senses and polarities.  Taken from the
+ * mpc7448hpc  manual.
+ * Note:  Likely, this table and the following function should be
+ *        obtained and derived from the OF Device Tree.
+ */
+
+static u_char mpc7448_hpc2_pic_initsenses[] __initdata = {
+       /* External on-board sources */
+       (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),      /* INT[0] XINT0 from FPGA */
+       (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),      /* INT[1] XINT1 from FPGA */
+       (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),      /* INT[2] PHY_INT from both GIGE */
+       (IRQ_SENSE_LEVEL | IRQ_POLARITY_NEGATIVE),      /* INT[3] RESERVED */
+       /* Internal Tsi108/109 interrupt sources */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* Reserved IRQ */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* Reserved IRQ */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* Reserved IRQ */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* Reserved IRQ */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* DMA0 */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* DMA1 */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* DMA2 */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* DMA3 */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* UART0 */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* UART1 */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* I2C */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* GPIO */
+       (IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),      /* GIGE0 */
+       (IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),      /* GIGE1 */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* Reserved IRQ */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* HLP */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* SDC */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* Processor IF */
+       (IRQ_SENSE_EDGE  | IRQ_POLARITY_POSITIVE),      /* Reserved IRQ */
+       (IRQ_SENSE_LEVEL | IRQ_POLARITY_POSITIVE),      /* PCI/X block */
+};
+
+int mpc7448_hpc2_exclude_device(u_char bus, u_char devfn)
+{
+       if (bus == 0 && PCI_SLOT(devfn) == 0)
+               return PCIBIOS_DEVICE_NOT_FOUND;
+       else
+               return PCIBIOS_SUCCESSFUL;
+}
+
+/*
+ * find pci slot by devfn in interrupt map of OF tree
+ */
+u8 find_slot_by_devfn(unsigned int *interrupt_map, unsigned int devfn)
+{
+       int i;
+       unsigned int tmp;
+       for (i = 0; i < 4; i++){
+               tmp = interrupt_map[i*4*7];
+               if ((tmp >> 11) == (devfn >> 3))
+                       return i;
+       }
+       return i;
+}
+
+/*
+ * Scans the interrupt map for pci device
+ */
+void mpc7448_hpc2_fixup_irq(struct pci_dev *dev)
+{
+       struct pci_controller *hose;
+       struct device_node *node;
+       unsigned int *interrupt;
+       int busnr;
+       int len;
+       u8 slot;
+       u8 pin;
+
+       /* Lookup the hose */
+       busnr = dev->bus->number;
+       hose = pci_bus_to_hose(busnr);
+       if (!hose)
+               printk(KERN_ERR "No pci hose found\n");
+
+       /* Check it has an OF node associated */
+       node = (struct device_node *) hose->arch_data;
+       if (!node)
+               printk(KERN_ERR "No pci node found\n");
+
+       interrupt = (unsigned int *) get_property(node, "interrupt-map", &len);
+       slot = find_slot_by_devfn(interrupt, dev->devfn);
+       pci_read_config_byte(dev, PCI_INTERRUPT_PIN, &pin);
+       if (pin == 0 || pin > 4)
+               pin = 1;
+       pin--;
+       dev->irq  = interrupt[slot*4*7 + pin*7 + 5];
+       DBG("TSI_PCI: dev->irq = 0x%x\n", dev->irq);
+}
+/* temporary pci irq map fixup*/
+
+void __init mpc7448_hpc2_pcibios_fixup(void)
+{
+       struct pci_dev *dev = NULL;
+       for_each_pci_dev(dev) {
+               mpc7448_hpc2_fixup_irq(dev);
+               pci_write_config_byte(dev, PCI_INTERRUPT_LINE, dev->irq);
+       }
+}
+
+static void __init mpc7448_hpc2_setup_arch(void)
+{
+       struct device_node *cpu;
+       struct device_node *np;
+       if (ppc_md.progress)
+               ppc_md.progress("mpc7448_hpc2_setup_arch():set_bridge", 0);
+
+       cpu = of_find_node_by_type(NULL, "cpu");
+       if (cpu != 0) {
+               unsigned int *fp;
+
+               fp = (int *)get_property(cpu, "clock-frequency", NULL);
+               if (fp != 0)
+                       loops_per_jiffy = *fp / HZ;
+               else
+                       loops_per_jiffy = 50000000 / HZ;
+               of_node_put(cpu);
+       }
+       tsi108_csr_vir_base = get_vir_csrbase();
+
+#ifdef CONFIG_ROOT_NFS
+       ROOT_DEV = Root_NFS;
+#else
+       ROOT_DEV = Root_HDA1;
+#endif
+
+#ifdef CONFIG_BLK_DEV_INITRD
+       ROOT_DEV = Root_RAM0;
+#endif
+
+       /* setup PCI host bridge */
+#ifdef CONFIG_PCI
+       for (np = NULL; (np = of_find_node_by_type(np, "pci")) != NULL;)
+               tsi108_setup_pci(np);
+
+       ppc_md.pci_exclude_device = mpc7448_hpc2_exclude_device;
+       if (ppc_md.progress)
+               ppc_md.progress("tsi108: resources set", 0x100);
+#endif
+
+       printk(KERN_INFO "MPC7448HPC2 (TAIGA) Platform\n");
+       printk(KERN_INFO
+              "Jointly ported by Freescale and Tundra Semiconductor\n");
+       printk(KERN_INFO
+              "Enabling L2 cache then enabling the HID0 prefetch engine.\n");
+}
+
+/*
+ * Interrupt setup and service.  Interrrupts on the mpc7448_hpc2 come
+ * from the four external INT pins, PCI interrupts are routed via
+ * PCI interrupt control registers, it generates internal IRQ23
+ *
+ * Interrupt routing on the Taiga Board:
+ * TSI108:PB_INT[0] -> CPU0:INT#
+ * TSI108:PB_INT[1] -> CPU0:MCP#
+ * TSI108:PB_INT[2] -> N/C
+ * TSI108:PB_INT[3] -> N/C
+ */
+static void __init mpc7448_hpc2_init_IRQ(void)
+{
+       struct mpic *mpic;
+       phys_addr_t mpic_paddr = 0;
+       struct device_node *tsi_pic;
+
+       tsi_pic = of_find_node_by_type(NULL, "open-pic");
+       if (tsi_pic) {
+               unsigned int size;
+               void *prop = get_property(tsi_pic, "reg", &size);
+               mpic_paddr = of_translate_address(tsi_pic, prop);
+       }
+
+       if (mpic_paddr == 0) {
+               printk("%s: No tsi108 PIC found !\n", __FUNCTION__);
+               return;
+       }
+
+       DBG("%s: tsi108pic phys_addr = 0x%x\n", __FUNCTION__,
+           (u32) mpic_paddr);
+
+       mpic = mpic_alloc(mpic_paddr,
+                       MPIC_PRIMARY | MPIC_BIG_ENDIAN | MPIC_WANTS_RESET |
+                       MPIC_SPV_EOI | MPIC_MOD_ID(MPIC_ID_TSI108),
+                       0, /* num_sources used */
+                       TSI108_IRQ_BASE,
+                       0, /* num_sources used */
+                       NR_IRQS - 4 /* XXXX */,
+                       mpc7448_hpc2_pic_initsenses,
+                       sizeof(mpc7448_hpc2_pic_initsenses), "Tsi108_PIC");
+
+       BUG_ON(mpic == NULL); /* XXXX */
+
+       mpic_init(mpic);
+       mpic_setup_cascade(IRQ_TSI108_PCI, tsi108_irq_cascade, mpic);
+       tsi108_pci_int_init();
+
+       /* Configure MPIC outputs to CPU0 */
+       tsi108_write_reg(TSI108_MPIC_OFFSET + 0x30c, 0);
+}
+
+void mpc7448_hpc2_show_cpuinfo(struct seq_file *m)
+{
+       seq_printf(m, "vendor\t\t: Freescale Semiconductor\n");
+       seq_printf(m, "machine\t\t: MPC7448hpc2\n");
+}
+
+void mpc7448_hpc2_restart(char *cmd)
+{
+       local_irq_disable();
+
+       /* Set exception prefix high - to the firmware */
+       _nmask_and_or_msr(0, MSR_IP);
+
+       for (;;) ;              /* Spin until reset happens */
+}
+
+void mpc7448_hpc2_power_off(void)
+{
+       local_irq_disable();
+       for (;;) ;              /* No way to shut power off with software */
+}
+
+void mpc7448_hpc2_halt(void)
+{
+       mpc7448_hpc2_power_off();
+}
+
+/*
+ * Called very early, device-tree isn't unflattened
+ */
+static int __init mpc7448_hpc2_probe(void)
+{
+       unsigned long root = of_get_flat_dt_root();
+
+       if (!of_flat_dt_is_compatible(root, "mpc74xx"))
+               return 0;
+       return 1;
+}
+
+static int mpc7448_machine_check_exception(struct pt_regs *regs)
+{
+       extern void tsi108_clear_pci_cfg_error(void);
+       const struct exception_table_entry *entry;
+
+       /* Are we prepared to handle this fault */
+       if ((entry = search_exception_tables(regs->nip)) != NULL) {
+               tsi108_clear_pci_cfg_error();
+               regs->msr |= MSR_RI;
+               regs->nip = entry->fixup;
+               return 1;
+       }
+       return 0;
+
+}
+define_machine(mpc7448_hpc2){
+       .name                   = "MPC7448 HPC2",
+       .probe                  = mpc7448_hpc2_probe,
+       .setup_arch             = mpc7448_hpc2_setup_arch,
+       .init_IRQ               = mpc7448_hpc2_init_IRQ,
+       .show_cpuinfo           = mpc7448_hpc2_show_cpuinfo,
+       .get_irq                = mpic_get_irq,
+       .pcibios_fixup          = mpc7448_hpc2_pcibios_fixup,
+       .restart                = mpc7448_hpc2_restart,
+       .calibrate_decr         = generic_calibrate_decr,
+       .machine_check_exception= mpc7448_machine_check_exception,
+       .progress               = udbg_progress,
+};
diff --git a/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.h b/arch/powerpc/platforms/embedded6xx/mpc7448_hpc2.h
new file mode 100644 (file)
index 0000000..a543a52
--- /dev/null
@@ -0,0 +1,26 @@
+/*
+ * mpc7448_hpc2.h
+ *
+ * Definitions for Freescale MPC7448_HPC2 platform
+ *
+ * Author: Jacob Pan
+ *         jacob.pan@freescale.com
+ * Maintainer: Roy Zang <roy.zang@freescale.com>
+ *
+ * 2006 (c) Freescale Semiconductor, Inc.  This file is licensed under
+ * the terms of the GNU General Public License version 2.  This program
+ * is licensed "as is" without any warranty of any kind, whether express
+ * or implied.
+ */
+
+#ifndef __PPC_PLATFORMS_MPC7448_HPC2_H
+#define __PPC_PLATFORMS_MPC7448_HPC2_H
+
+#include <asm/ppcboot.h>
+
+/* Base Addresses for the PCI bus
+ */
+#define MPC7448_HPC2_PCI_MEM_OFFSET    (0x00000000)
+#define MPC7448_HPC2_ISA_IO_BASE       (0x00000000)
+#define MPC7448_HPC2_ISA_MEM_BASE      (0x00000000)
+#endif                         /* __PPC_PLATFORMS_MPC7448_HPC2_H */
index d3444aabe76e46bdda0cd6832cb56a480fe6095f..d194140c1ebf083cba4dc24e133f46b09c672143 100644 (file)
@@ -252,6 +252,7 @@ static void __init dt_model(struct iseries_flat_dt *dt)
 {
        char buf[16] = "IBM,";
 
+       /* N.B. lparcfg.c knows about the "IBM," prefixes ... */
        /* "IBM," + mfgId[2:3] + systemSerial[1:5] */
        strne2a(buf + 4, xItExtVpdPanel.mfgID + 2, 2);
        strne2a(buf + 6, xItExtVpdPanel.systemSerial + 1, 5);
@@ -264,6 +265,7 @@ static void __init dt_model(struct iseries_flat_dt *dt)
        dt_prop_str(dt, "model", buf);
 
        dt_prop_str(dt, "compatible", "IBM,iSeries");
+       dt_prop_u32(dt, "ibm,partition-no", HvLpConfig_getLpIndex());
 }
 
 static void __init dt_do_vdevice(struct iseries_flat_dt *dt,
index 30bdcf3925d9b1727cc37a82c48582c06eff6f30..ed44dfceaa45069f016ba6a809d0c3c2cf3cf4d9 100644 (file)
@@ -242,13 +242,11 @@ static void iSeries_hpte_invalidate(unsigned long slot, unsigned long va,
        local_irq_restore(flags);
 }
 
-void hpte_init_iSeries(void)
+void __init hpte_init_iSeries(void)
 {
        ppc_md.hpte_invalidate  = iSeries_hpte_invalidate;
        ppc_md.hpte_updatepp    = iSeries_hpte_updatepp;
        ppc_md.hpte_updateboltedpp = iSeries_hpte_updateboltedpp;
        ppc_md.hpte_insert      = iSeries_hpte_insert;
        ppc_md.hpte_remove      = iSeries_hpte_remove;
-
-       htab_finish_init();
 }
index 8ca7b939635574c5079513060ce4d6657cf985f8..2a9f81ea27d6b0ab2bb8933ff7f20ada4c82d35b 100644 (file)
@@ -51,20 +51,21 @@ static unsigned lpEventHandlerPaths[HvLpEvent_Type_NumTypes];
 static struct HvLpEvent * get_next_hvlpevent(void)
 {
        struct HvLpEvent * event;
-       event = (struct HvLpEvent *)hvlpevent_queue.xSlicCurEventPtr;
+       event = (struct HvLpEvent *)hvlpevent_queue.hq_current_event;
 
        if (hvlpevent_is_valid(event)) {
                /* rmb() needed only for weakly consistent machines (regatta) */
                rmb();
                /* Set pointer to next potential event */
-               hvlpevent_queue.xSlicCurEventPtr += ((event->xSizeMinus1 +
-                               LpEventAlign) / LpEventAlign) * LpEventAlign;
+               hvlpevent_queue.hq_current_event += ((event->xSizeMinus1 +
+                               IT_LP_EVENT_ALIGN) / IT_LP_EVENT_ALIGN) *
+                                       IT_LP_EVENT_ALIGN;
 
                /* Wrap to beginning if no room at end */
-               if (hvlpevent_queue.xSlicCurEventPtr >
-                               hvlpevent_queue.xSlicLastValidEventPtr) {
-                       hvlpevent_queue.xSlicCurEventPtr =
-                               hvlpevent_queue.xSlicEventStackPtr;
+               if (hvlpevent_queue.hq_current_event >
+                               hvlpevent_queue.hq_last_event) {
+                       hvlpevent_queue.hq_current_event =
+                               hvlpevent_queue.hq_event_stack;
                }
        } else {
                event = NULL;
@@ -82,10 +83,10 @@ int hvlpevent_is_pending(void)
        if (smp_processor_id() >= spread_lpevents)
                return 0;
 
-       next_event = (struct HvLpEvent *)hvlpevent_queue.xSlicCurEventPtr;
+       next_event = (struct HvLpEvent *)hvlpevent_queue.hq_current_event;
 
        return hvlpevent_is_valid(next_event) ||
-               hvlpevent_queue.xPlicOverflowIntPending;
+               hvlpevent_queue.hq_overflow_pending;
 }
 
 static void hvlpevent_clear_valid(struct HvLpEvent * event)
@@ -95,18 +96,18 @@ static void hvlpevent_clear_valid(struct HvLpEvent * event)
         * ie. on 64-byte boundaries.
         */
        struct HvLpEvent *tmp;
-       unsigned extra = ((event->xSizeMinus1 + LpEventAlign) /
-                                                LpEventAlign) - 1;
+       unsigned extra = ((event->xSizeMinus1 + IT_LP_EVENT_ALIGN) /
+                               IT_LP_EVENT_ALIGN) - 1;
 
        switch (extra) {
        case 3:
-               tmp = (struct HvLpEvent*)((char*)event + 3 * LpEventAlign);
+               tmp = (struct HvLpEvent*)((char*)event + 3 * IT_LP_EVENT_ALIGN);
                hvlpevent_invalidate(tmp);
        case 2:
-               tmp = (struct HvLpEvent*)((char*)event + 2 * LpEventAlign);
+               tmp = (struct HvLpEvent*)((char*)event + 2 * IT_LP_EVENT_ALIGN);
                hvlpevent_invalidate(tmp);
        case 1:
-               tmp = (struct HvLpEvent*)((char*)event + 1 * LpEventAlign);
+               tmp = (struct HvLpEvent*)((char*)event + 1 * IT_LP_EVENT_ALIGN);
                hvlpevent_invalidate(tmp);
        }
 
@@ -120,7 +121,7 @@ void process_hvlpevents(struct pt_regs *regs)
        struct HvLpEvent * event;
 
        /* If we have recursed, just return */
-       if (!spin_trylock(&hvlpevent_queue.lock))
+       if (!spin_trylock(&hvlpevent_queue.hq_lock))
                return;
 
        for (;;) {
@@ -148,17 +149,17 @@ void process_hvlpevents(struct pt_regs *regs)
                                printk(KERN_INFO "Unexpected Lp Event type=%d\n", event->xType );
 
                        hvlpevent_clear_valid(event);
-               } else if (hvlpevent_queue.xPlicOverflowIntPending)
+               } else if (hvlpevent_queue.hq_overflow_pending)
                        /*
                         * No more valid events. If overflow events are
                         * pending process them
                         */
-                       HvCallEvent_getOverflowLpEvents(hvlpevent_queue.xIndex);
+                       HvCallEvent_getOverflowLpEvents(hvlpevent_queue.hq_index);
                else
                        break;
        }
 
-       spin_unlock(&hvlpevent_queue.lock);
+       spin_unlock(&hvlpevent_queue.hq_lock);
 }
 
 static int set_spread_lpevents(char *str)
@@ -184,20 +185,20 @@ void setup_hvlpevent_queue(void)
 {
        void *eventStack;
 
-       spin_lock_init(&hvlpevent_queue.lock);
+       spin_lock_init(&hvlpevent_queue.hq_lock);
 
        /* Allocate a page for the Event Stack. */
-       eventStack = alloc_bootmem_pages(LpEventStackSize);
-       memset(eventStack, 0, LpEventStackSize);
+       eventStack = alloc_bootmem_pages(IT_LP_EVENT_STACK_SIZE);
+       memset(eventStack, 0, IT_LP_EVENT_STACK_SIZE);
 
        /* Invoke the hypervisor to initialize the event stack */
-       HvCallEvent_setLpEventStack(0, eventStack, LpEventStackSize);
+       HvCallEvent_setLpEventStack(0, eventStack, IT_LP_EVENT_STACK_SIZE);
 
-       hvlpevent_queue.xSlicEventStackPtr = (char *)eventStack;
-       hvlpevent_queue.xSlicCurEventPtr = (char *)eventStack;
-       hvlpevent_queue.xSlicLastValidEventPtr = (char *)eventStack +
-                                       (LpEventStackSize - LpEventMaxSize);
-       hvlpevent_queue.xIndex = 0;
+       hvlpevent_queue.hq_event_stack = eventStack;
+       hvlpevent_queue.hq_current_event = eventStack;
+       hvlpevent_queue.hq_last_event = (char *)eventStack +
+               (IT_LP_EVENT_STACK_SIZE - IT_LP_EVENT_MAX_SIZE);
+       hvlpevent_queue.hq_index = 0;
 }
 
 /* Register a handler for an LpEvent type */
index e68b6b5fa89f0b0e20446af206779af6e8d632f4..c241413629ac155266cb7fcddb8fa68da759a3c6 100644 (file)
@@ -24,7 +24,6 @@
 #include <asm/processor.h>
 #include <asm/time.h>
 #include <asm/lppaca.h>
-#include <asm/iseries/it_lp_queue.h>
 #include <asm/iseries/hv_call_xm.h>
 
 #include "processor_vpd.h"
index 617c724c4590841df47f43e1512743db0d155f62..66c77e4f8ec2441c932d30f26db8a5d1e3e209ce 100644 (file)
@@ -81,8 +81,6 @@ static void iSeries_pci_final_fixup(void) { }
 #endif
 
 extern int rd_size;            /* Defined in drivers/block/rd.c */
-extern unsigned long embedded_sysmap_start;
-extern unsigned long embedded_sysmap_end;
 
 extern unsigned long iSeries_recal_tb;
 extern unsigned long iSeries_recal_titan;
@@ -320,11 +318,6 @@ static void __init iSeries_init_early(void)
        iSeries_recal_tb = get_tb();
        iSeries_recal_titan = HvCallXm_loadTod();
 
-       /*
-        * Initialize the hash table management pointers
-        */
-       hpte_init_iSeries();
-
        /*
         * Initialize the DMA/TCE management
         */
@@ -563,16 +556,6 @@ static void __init iSeries_fixup_klimit(void)
        if (naca.xRamDisk)
                klimit = KERNELBASE + (u64)naca.xRamDisk +
                        (naca.xRamDiskSize * HW_PAGE_SIZE);
-       else {
-               /*
-                * No ram disk was included - check and see if there
-                * was an embedded system map.  Change klimit to take
-                * into account any embedded system map
-                */
-               if (embedded_sysmap_end)
-                       klimit = KERNELBASE + ((embedded_sysmap_end + 4095) &
-                                       0xfffffffffffff000);
-       }
 }
 
 static int __init iSeries_src_init(void)
@@ -683,6 +666,8 @@ static int __init iseries_probe(void)
         */
        virt_irq_max = 255;
 
+       hpte_init_iSeries();
+
        return 1;
 }
 
index a0505ea48a86ca75343206829d06fb0e361920c6..4e32a5417fd14897e17cf1bf69ae3fa6b5c43ed0 100644 (file)
@@ -199,11 +199,6 @@ static void __init maple_init_early(void)
 {
        DBG(" -> maple_init_early\n");
 
-       /* Initialize hash table, from now on, we can take hash faults
-        * and call ioremap
-        */
-       hpte_init_native();
-
        /* Setup interrupt mapping options */
        ppc64_interrupt_controller = IC_OPEN_PIC;
 
@@ -272,6 +267,8 @@ static int __init maple_probe(void)
         */
        alloc_dart_table();
 
+       hpte_init_native();
+
        return 1;
 }
 
index 9cc7db7a8bdc443a1da0af1cb4adf34ad7b462af..89c5775f83beffb4947fb5c466bb6478096e84e4 100644 (file)
@@ -600,13 +600,6 @@ pmac_halt(void)
  */
 static void __init pmac_init_early(void)
 {
-#ifdef CONFIG_PPC64
-       /* Initialize hash table, from now on, we can take hash faults
-        * and call ioremap
-        */
-       hpte_init_native();
-#endif
-
        /* Enable early btext debug if requested */
        if (strstr(cmd_line, "btextdbg")) {
                udbg_adb_init_early();
@@ -683,6 +676,8 @@ static int __init pmac_probe(void)
         * part of the cacheable linar mapping
         */
        alloc_dart_table();
+
+       hpte_init_native();
 #endif
 
 #ifdef CONFIG_PPC32
index d03a8b078f9db09ffa72cffbd01cba8aa4cc8413..8cfb5706790ecd395bd7039463a435a6a0574405 100644 (file)
@@ -92,6 +92,15 @@ static void tce_free_pSeries(struct iommu_table *tbl, long index, long npages)
                *(tcep++) = 0;
 }
 
+static unsigned long tce_get_pseries(struct iommu_table *tbl, long index)
+{
+       u64 *tcep;
+
+       index <<= TCE_PAGE_FACTOR;
+       tcep = ((u64 *)tbl->it_base) + index;
+
+       return *tcep;
+}
 
 static void tce_build_pSeriesLP(struct iommu_table *tbl, long tcenum,
                                long npages, unsigned long uaddr,
@@ -235,6 +244,25 @@ static void tce_freemulti_pSeriesLP(struct iommu_table *tbl, long tcenum, long n
        }
 }
 
+static unsigned long tce_get_pSeriesLP(struct iommu_table *tbl, long tcenum)
+{
+       u64 rc;
+       unsigned long tce_ret;
+
+       tcenum <<= TCE_PAGE_FACTOR;
+       rc = plpar_tce_get((u64)tbl->it_index, (u64)tcenum << 12, &tce_ret);
+
+       if (rc && printk_ratelimit()) {
+               printk("tce_get_pSeriesLP: plpar_tce_get failed. rc=%ld\n",
+                       rc);
+               printk("\tindex   = 0x%lx\n", (u64)tbl->it_index);
+               printk("\ttcenum  = 0x%lx\n", (u64)tcenum);
+               show_stack(current, (unsigned long *)__get_SP());
+       }
+
+       return tce_ret;
+}
+
 static void iommu_table_setparms(struct pci_controller *phb,
                                 struct device_node *dn,
                                 struct iommu_table *tbl)
@@ -254,7 +282,10 @@ static void iommu_table_setparms(struct pci_controller *phb,
        }
 
        tbl->it_base = (unsigned long)__va(*basep);
+
+#ifndef CONFIG_CRASH_DUMP
        memset((void *)tbl->it_base, 0, *sizep);
+#endif
 
        tbl->it_busno = phb->bus->number;
 
@@ -560,11 +591,13 @@ void iommu_init_early_pSeries(void)
                        ppc_md.tce_build = tce_build_pSeriesLP;
                        ppc_md.tce_free  = tce_free_pSeriesLP;
                }
+               ppc_md.tce_get   = tce_get_pSeriesLP;
                ppc_md.iommu_bus_setup = iommu_bus_setup_pSeriesLP;
                ppc_md.iommu_dev_setup = iommu_dev_setup_pSeriesLP;
        } else {
                ppc_md.tce_build = tce_build_pSeries;
                ppc_md.tce_free  = tce_free_pSeries;
+               ppc_md.tce_get   = tce_get_pseries;
                ppc_md.iommu_bus_setup = iommu_bus_setup_pSeries;
                ppc_md.iommu_dev_setup = iommu_dev_setup_pSeries;
        }
index 634b7d06d3cc2a7df78645104294fae0e491647a..27480705996f988ae6335925930bb08911afa173 100644 (file)
@@ -513,7 +513,7 @@ void pSeries_lpar_flush_hash_range(unsigned long number, int local)
                spin_unlock_irqrestore(&pSeries_lpar_tlbie_lock, flags);
 }
 
-void hpte_init_lpar(void)
+void __init hpte_init_lpar(void)
 {
        ppc_md.hpte_invalidate  = pSeries_lpar_hpte_invalidate;
        ppc_md.hpte_updatepp    = pSeries_lpar_hpte_updatepp;
@@ -522,6 +522,4 @@ void hpte_init_lpar(void)
        ppc_md.hpte_remove      = pSeries_lpar_hpte_remove;
        ppc_md.flush_hash_range = pSeries_lpar_flush_hash_range;
        ppc_md.hpte_clear_all   = pSeries_lpar_hptab_clear;
-
-       htab_finish_init();
 }
index 1e28518c6121f7431526b75501ff15aa3d9e0ef4..b3197ff156c6ab277b46abe710eb8fbc0a6c18e4 100644 (file)
@@ -322,11 +322,6 @@ static void __init pSeries_init_early(void)
        DBG(" -> pSeries_init_early()\n");
 
        fw_feature_init();
-       
-       if (firmware_has_feature(FW_FEATURE_LPAR))
-               hpte_init_lpar();
-       else
-               hpte_init_native();
 
        if (firmware_has_feature(FW_FEATURE_LPAR))
                find_udbg_vterm();
@@ -384,6 +379,11 @@ static int __init pSeries_probe_hypertas(unsigned long node,
        if (of_get_flat_dt_prop(node, "ibm,hypertas-functions", NULL) != NULL)
                powerpc_firmware_features |= FW_FEATURE_LPAR;
 
+       if (firmware_has_feature(FW_FEATURE_LPAR))
+               hpte_init_lpar();
+       else
+               hpte_init_native();
+
        return 1;
 }
 
index cef95b023730aefa9aa865a10c4f783bd1c67ce6..054bd8b41ef51d5851c37c47ae0bb6a5513bf056 100644 (file)
@@ -12,3 +12,5 @@ obj-$(CONFIG_U3_DART)         += dart_iommu.o
 obj-$(CONFIG_MMIO_NVRAM)       += mmio_nvram.o
 obj-$(CONFIG_PPC_83xx)         += ipic.o
 obj-$(CONFIG_FSL_SOC)          += fsl_soc.o
+obj-$(CONFIG_PPC_TODC)         += todc.o
+obj-$(CONFIG_TSI108_BRIDGE)    += tsi108_pci.o tsi108_dev.o
index c2d05763ccbe679b09a24fe57563b4fc1287b956..1c8817c4835ee780dcf5f0e0cc285cd4f790d86f 100644 (file)
 /* U4 registers */
 #define DART_BASE_U4_BASE_MASK 0xffffff
 #define DART_BASE_U4_BASE_SHIFT        0
-#define DART_CNTL_U4_FLUSHTLB  0x20000000
 #define DART_CNTL_U4_ENABLE    0x80000000
+#define DART_CNTL_U4_IONE      0x40000000
+#define DART_CNTL_U4_FLUSHTLB  0x20000000
+#define DART_CNTL_U4_IDLE      0x10000000
+#define DART_CNTL_U4_PAR_EN    0x08000000
+#define DART_CNTL_U4_IONE_MASK 0x07ffffff
 #define DART_SIZE_U4_SIZE_MASK 0x1fff
 #define DART_SIZE_U4_SIZE_SHIFT        0
 
index 6232091cc72bcd87b8e6f69c9242257b770926e1..7c7f34ce4986621808f0d5d731f55f9fe19e6711 100644 (file)
@@ -101,8 +101,8 @@ retry:
        if (l == (1L << limit)) {
                if (limit < 4) {
                        limit++;
-                       reg = DART_IN(DART_CNTL);
-                       reg &= ~inv_bit;
+                       reg = DART_IN(DART_CNTL);
+                       reg &= ~inv_bit;
                        DART_OUT(DART_CNTL, reg);
                        goto retry;
                } else
@@ -111,11 +111,39 @@ retry:
        }
 }
 
+static inline void dart_tlb_invalidate_one(unsigned long bus_rpn)
+{
+       unsigned int reg;
+       unsigned int l, limit;
+
+       reg = DART_CNTL_U4_ENABLE | DART_CNTL_U4_IONE |
+               (bus_rpn & DART_CNTL_U4_IONE_MASK);
+       DART_OUT(DART_CNTL, reg);
+
+       limit = 0;
+wait_more:
+       l = 0;
+       while ((DART_IN(DART_CNTL) & DART_CNTL_U4_IONE) && l < (1L << limit)) {
+               rmb();
+               l++;
+       }
+
+       if (l == (1L << limit)) {
+               if (limit < 4) {
+                       limit++;
+                       goto wait_more;
+               } else
+                       panic("DART: TLB did not flush after waiting a long "
+                             "time. Buggy U4 ?");
+       }
+}
+
 static void dart_flush(struct iommu_table *tbl)
 {
-       if (dart_dirty)
+       if (dart_dirty) {
                dart_tlb_invalidate_all();
-       dart_dirty = 0;
+               dart_dirty = 0;
+       }
 }
 
 static void dart_build(struct iommu_table *tbl, long index,
@@ -124,6 +152,7 @@ static void dart_build(struct iommu_table *tbl, long index,
 {
        unsigned int *dp;
        unsigned int rpn;
+       long l;
 
        DBG("dart: build at: %lx, %lx, addr: %x\n", index, npages, uaddr);
 
@@ -135,7 +164,8 @@ static void dart_build(struct iommu_table *tbl, long index,
        /* On U3, all memory is contigous, so we can move this
         * out of the loop.
         */
-       while (npages--) {
+       l = npages;
+       while (l--) {
                rpn = virt_to_abs(uaddr) >> DART_PAGE_SHIFT;
 
                *(dp++) = DARTMAP_VALID | (rpn & DARTMAP_RPNMASK);
@@ -143,7 +173,14 @@ static void dart_build(struct iommu_table *tbl, long index,
                uaddr += DART_PAGE_SIZE;
        }
 
-       dart_dirty = 1;
+       if (dart_is_u4) {
+               rpn = index;
+               mb(); /* make sure all updates have reached memory */
+               while (npages--)
+                       dart_tlb_invalidate_one(rpn++);
+       } else {
+               dart_dirty = 1;
+       }
 }
 
 
diff --git a/arch/powerpc/sysdev/todc.c b/arch/powerpc/sysdev/todc.c
new file mode 100644 (file)
index 0000000..0a65980
--- /dev/null
@@ -0,0 +1,392 @@
+/*
+ * Time of Day Clock support for the M48T35, M48T37, M48T59, and MC146818
+ * Real Time Clocks/Timekeepers.
+ *
+ * Author: Mark A. Greer <mgreer@mvista.com>
+ *
+ * 2001-2004 (c) MontaVista, Software, Inc.  This file is licensed under
+ * the terms of the GNU General Public License version 2.  This program
+ * is licensed "as is" without any warranty of any kind, whether express
+ * or implied.
+ */
+#include <linux/errno.h>
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/time.h>
+#include <linux/timex.h>
+#include <linux/bcd.h>
+#include <linux/mc146818rtc.h>
+
+#include <asm/machdep.h>
+#include <asm/io.h>
+#include <asm/time.h>
+#include <asm/todc.h>
+
+/*
+ * Depending on the hardware on your board and your board design, the
+ * RTC/NVRAM may be accessed either directly (like normal memory) or via
+ * address/data registers.  If your board uses the direct method, set
+ * 'nvram_data' to the base address of your nvram and leave 'nvram_as0' and
+ * 'nvram_as1' NULL.  If your board uses address/data regs to access nvram,
+ * set 'nvram_as0' to the address of the lower byte, set 'nvram_as1' to the
+ * address of the upper byte (leave NULL if using mc146818), and set
+ * 'nvram_data' to the address of the 8-bit data register.
+ *
+ * Note: Even though the documentation for the various RTC chips say that it
+ *      take up to a second before it starts updating once the 'R' bit is
+ *      cleared, they always seem to update even though we bang on it many
+ *      times a second.  This is true, except for the Dallas Semi 1746/1747
+ *      (possibly others).  Those chips seem to have a real problem whenever
+ *      we set the 'R' bit before reading them, they basically stop counting.
+ *                                             --MAG
+ */
+
+/*
+ * 'todc_info' should be initialized in your *_setup.c file to
+ * point to a fully initialized 'todc_info_t' structure.
+ * This structure holds all the register offsets for your particular
+ * TODC/RTC chip.
+ * TODC_ALLOC()/TODC_INIT() will allocate and initialize this table for you.
+ */
+
+#ifdef RTC_FREQ_SELECT
+#undef RTC_FREQ_SELECT
+#define        RTC_FREQ_SELECT         control_b       /* Register A */
+#endif
+
+#ifdef RTC_CONTROL
+#undef RTC_CONTROL
+#define        RTC_CONTROL             control_a       /* Register B */
+#endif
+
+#ifdef RTC_INTR_FLAGS
+#undef RTC_INTR_FLAGS
+#define        RTC_INTR_FLAGS          watchdog        /* Register C */
+#endif
+
+#ifdef RTC_VALID
+#undef RTC_VALID
+#define        RTC_VALID               interrupts      /* Register D */
+#endif
+
+/* Access routines when RTC accessed directly (like normal memory) */
+u_char
+todc_direct_read_val(int addr)
+{
+       return readb((void __iomem *)(todc_info->nvram_data + addr));
+}
+
+void
+todc_direct_write_val(int addr, unsigned char val)
+{
+       writeb(val, (void __iomem *)(todc_info->nvram_data + addr));
+       return;
+}
+
+/* Access routines for accessing m48txx type chips via addr/data regs */
+u_char
+todc_m48txx_read_val(int addr)
+{
+       outb(addr, todc_info->nvram_as0);
+       outb(addr>>todc_info->as0_bits, todc_info->nvram_as1);
+       return inb(todc_info->nvram_data);
+}
+
+void
+todc_m48txx_write_val(int addr, unsigned char val)
+{
+       outb(addr, todc_info->nvram_as0);
+       outb(addr>>todc_info->as0_bits, todc_info->nvram_as1);
+       outb(val, todc_info->nvram_data);
+       return;
+}
+
+/* Access routines for accessing mc146818 type chips via addr/data regs */
+u_char
+todc_mc146818_read_val(int addr)
+{
+       outb_p(addr, todc_info->nvram_as0);
+       return inb_p(todc_info->nvram_data);
+}
+
+void
+todc_mc146818_write_val(int addr, unsigned char val)
+{
+       outb_p(addr, todc_info->nvram_as0);
+       outb_p(val, todc_info->nvram_data);
+}
+
+
+/*
+ * Routines to make RTC chips with NVRAM buried behind an addr/data pair
+ * have the NVRAM and clock regs appear at the same level.
+ * The NVRAM will appear to start at addr 0 and the clock regs will appear
+ * to start immediately after the NVRAM (actually, start at offset
+ * todc_info->nvram_size).
+ */
+static inline u_char
+todc_read_val(int addr)
+{
+       u_char  val;
+
+       if (todc_info->sw_flags & TODC_FLAG_2_LEVEL_NVRAM) {
+               if (addr < todc_info->nvram_size) { /* NVRAM */
+                       ppc_md.rtc_write_val(todc_info->nvram_addr_reg, addr);
+                       val = ppc_md.rtc_read_val(todc_info->nvram_data_reg);
+               } else { /* Clock Reg */
+                       addr -= todc_info->nvram_size;
+                       val = ppc_md.rtc_read_val(addr);
+               }
+       } else
+               val = ppc_md.rtc_read_val(addr);
+
+       return val;
+}
+
+static inline void
+todc_write_val(int addr, u_char val)
+{
+       if (todc_info->sw_flags & TODC_FLAG_2_LEVEL_NVRAM) {
+               if (addr < todc_info->nvram_size) { /* NVRAM */
+                       ppc_md.rtc_write_val(todc_info->nvram_addr_reg, addr);
+                       ppc_md.rtc_write_val(todc_info->nvram_data_reg, val);
+               } else { /* Clock Reg */
+                       addr -= todc_info->nvram_size;
+                       ppc_md.rtc_write_val(addr, val);
+               }
+       } else
+               ppc_md.rtc_write_val(addr, val);
+}
+
+/*
+ * TODC routines
+ *
+ * There is some ugly stuff in that there are assumptions for the mc146818.
+ *
+ * Assumptions:
+ *     - todc_info->control_a has the offset as mc146818 Register B reg
+ *     - todc_info->control_b has the offset as mc146818 Register A reg
+ *     - m48txx control reg's write enable or 'W' bit is same as
+ *       mc146818 Register B 'SET' bit (i.e., 0x80)
+ *
+ * These assumptions were made to make the code simpler.
+ */
+long __init
+todc_time_init(void)
+{
+       u_char  cntl_b;
+
+       if (!ppc_md.rtc_read_val)
+               ppc_md.rtc_read_val = ppc_md.nvram_read_val;
+       if (!ppc_md.rtc_write_val)
+               ppc_md.rtc_write_val = ppc_md.nvram_write_val;
+
+       cntl_b = todc_read_val(todc_info->control_b);
+
+       if (todc_info->rtc_type == TODC_TYPE_MC146818) {
+               if ((cntl_b & 0x70) != 0x20) {
+                       printk(KERN_INFO "TODC real-time-clock was stopped."
+                               "  Now starting...");
+                       cntl_b &= ~0x70;
+                       cntl_b |= 0x20;
+               }
+
+               todc_write_val(todc_info->control_b, cntl_b);
+       } else if (todc_info->rtc_type == TODC_TYPE_DS17285) {
+               u_char mode;
+
+               mode = todc_read_val(TODC_TYPE_DS17285_CNTL_A);
+               /* Make sure countdown clear is not set */
+               mode &= ~0x40;
+               /* Enable oscillator, extended register set */
+               mode |= 0x30;
+               todc_write_val(TODC_TYPE_DS17285_CNTL_A, mode);
+
+       } else if (todc_info->rtc_type == TODC_TYPE_DS1501) {
+               u_char  month;
+
+               todc_info->enable_read = TODC_DS1501_CNTL_B_TE;
+               todc_info->enable_write = TODC_DS1501_CNTL_B_TE;
+
+               month = todc_read_val(todc_info->month);
+
+               if ((month & 0x80) == 0x80) {
+                       printk(KERN_INFO "TODC %s %s\n",
+                               "real-time-clock was stopped.",
+                               "Now starting...");
+                       month &= ~0x80;
+                       todc_write_val(todc_info->month, month);
+               }
+
+               cntl_b &= ~TODC_DS1501_CNTL_B_TE;
+               todc_write_val(todc_info->control_b, cntl_b);
+       } else { /* must be a m48txx type */
+               u_char  cntl_a;
+
+               todc_info->enable_read = TODC_MK48TXX_CNTL_A_R;
+               todc_info->enable_write = TODC_MK48TXX_CNTL_A_W;
+
+               cntl_a = todc_read_val(todc_info->control_a);
+
+               /* Check & clear STOP bit in control B register */
+               if (cntl_b & TODC_MK48TXX_DAY_CB) {
+                       printk(KERN_INFO "TODC %s %s\n",
+                               "real-time-clock was stopped.",
+                               "Now starting...");
+
+                       cntl_a |= todc_info->enable_write;
+                       cntl_b &= ~TODC_MK48TXX_DAY_CB;/* Start Oscil */
+
+                       todc_write_val(todc_info->control_a, cntl_a);
+                       todc_write_val(todc_info->control_b, cntl_b);
+               }
+
+               /* Make sure READ & WRITE bits are cleared. */
+               cntl_a &= ~(todc_info->enable_write | todc_info->enable_read);
+               todc_write_val(todc_info->control_a, cntl_a);
+       }
+
+       return 0;
+}
+
+/*
+ * There is some ugly stuff in that there are assumptions that for a mc146818,
+ * the todc_info->control_a has the offset of the mc146818 Register B reg and
+ * that the register'ss 'SET' bit is the same as the m48txx's write enable
+ * bit in the control register of the m48txx (i.e., 0x80).
+ *
+ * It was done to make the code look simpler.
+ */
+void
+todc_get_rtc_time(struct rtc_time *tm)
+{
+       uint    year = 0, mon = 0, mday = 0, hour = 0, min = 0, sec = 0;
+       uint    limit, i;
+       u_char  save_control, uip = 0;
+       extern void GregorianDay(struct rtc_time *);
+
+       spin_lock(&rtc_lock);
+       save_control = todc_read_val(todc_info->control_a);
+
+       if (todc_info->rtc_type != TODC_TYPE_MC146818) {
+               limit = 1;
+
+               switch (todc_info->rtc_type) {
+               case TODC_TYPE_DS1553:
+               case TODC_TYPE_DS1557:
+               case TODC_TYPE_DS1743:
+               case TODC_TYPE_DS1746:  /* XXXX BAD HACK -> FIX */
+               case TODC_TYPE_DS1747:
+               case TODC_TYPE_DS17285:
+                       break;
+               default:
+                       todc_write_val(todc_info->control_a,
+                               (save_control | todc_info->enable_read));
+               }
+       } else
+               limit = 100000000;
+
+       for (i=0; i<limit; i++) {
+               if (todc_info->rtc_type == TODC_TYPE_MC146818)
+                       uip = todc_read_val(todc_info->RTC_FREQ_SELECT);
+
+               sec = todc_read_val(todc_info->seconds) & 0x7f;
+               min = todc_read_val(todc_info->minutes) & 0x7f;
+               hour = todc_read_val(todc_info->hours) & 0x3f;
+               mday = todc_read_val(todc_info->day_of_month) & 0x3f;
+               mon = todc_read_val(todc_info->month) & 0x1f;
+               year = todc_read_val(todc_info->year) & 0xff;
+
+               if (todc_info->rtc_type == TODC_TYPE_MC146818) {
+                       uip |= todc_read_val(todc_info->RTC_FREQ_SELECT);
+                       if ((uip & RTC_UIP) == 0)
+                               break;
+               }
+       }
+
+       if (todc_info->rtc_type != TODC_TYPE_MC146818) {
+               switch (todc_info->rtc_type) {
+               case TODC_TYPE_DS1553:
+               case TODC_TYPE_DS1557:
+               case TODC_TYPE_DS1743:
+               case TODC_TYPE_DS1746:  /* XXXX BAD HACK -> FIX */
+               case TODC_TYPE_DS1747:
+               case TODC_TYPE_DS17285:
+                       break;
+               default:
+                       save_control &= ~(todc_info->enable_read);
+                       todc_write_val(todc_info->control_a, save_control);
+               }
+       }
+       spin_unlock(&rtc_lock);
+
+       if ((todc_info->rtc_type != TODC_TYPE_MC146818)
+                       || ((save_control & RTC_DM_BINARY) == 0)
+                       || RTC_ALWAYS_BCD) {
+               BCD_TO_BIN(sec);
+               BCD_TO_BIN(min);
+               BCD_TO_BIN(hour);
+               BCD_TO_BIN(mday);
+               BCD_TO_BIN(mon);
+               BCD_TO_BIN(year);
+       }
+
+       if ((year + 1900) < 1970) {
+               year += 100;
+       }
+
+       tm->tm_sec = sec;
+       tm->tm_min = min;
+       tm->tm_hour = hour;
+       tm->tm_mday = mday;
+       tm->tm_mon = mon;
+       tm->tm_year = year;
+
+       GregorianDay(tm);
+}
+
+int
+todc_set_rtc_time(struct rtc_time *tm)
+{
+       u_char save_control, save_freq_select = 0;
+
+       spin_lock(&rtc_lock);
+       save_control = todc_read_val(todc_info->control_a);
+
+       /* Assuming MK48T59_RTC_CA_WRITE & RTC_SET are equal */
+       todc_write_val(todc_info->control_a,
+               (save_control | todc_info->enable_write));
+       save_control &= ~(todc_info->enable_write); /* in case it was set */
+
+       if (todc_info->rtc_type == TODC_TYPE_MC146818) {
+               save_freq_select = todc_read_val(todc_info->RTC_FREQ_SELECT);
+               todc_write_val(todc_info->RTC_FREQ_SELECT,
+                       save_freq_select | RTC_DIV_RESET2);
+       }
+
+       if ((todc_info->rtc_type != TODC_TYPE_MC146818)
+                       || ((save_control & RTC_DM_BINARY) == 0)
+                       || RTC_ALWAYS_BCD) {
+               BIN_TO_BCD(tm->tm_sec);
+               BIN_TO_BCD(tm->tm_min);
+               BIN_TO_BCD(tm->tm_hour);
+               BIN_TO_BCD(tm->tm_mon);
+               BIN_TO_BCD(tm->tm_mday);
+               BIN_TO_BCD(tm->tm_year);
+       }
+
+       todc_write_val(todc_info->seconds, tm->tm_sec);
+       todc_write_val(todc_info->minutes, tm->tm_min);
+       todc_write_val(todc_info->hours, tm->tm_hour);
+       todc_write_val(todc_info->month, tm->tm_mon);
+       todc_write_val(todc_info->day_of_month, tm->tm_mday);
+       todc_write_val(todc_info->year, tm->tm_year);
+
+       todc_write_val(todc_info->control_a, save_control);
+
+       if (todc_info->rtc_type == TODC_TYPE_MC146818)
+               todc_write_val(todc_info->RTC_FREQ_SELECT, save_freq_select);
+
+       spin_unlock(&rtc_lock);
+       return 0;
+}
diff --git a/arch/powerpc/sysdev/tsi108_dev.c b/arch/powerpc/sysdev/tsi108_dev.c
new file mode 100644 (file)
index 0000000..26a0cc8
--- /dev/null
@@ -0,0 +1,145 @@
+/*
+ * tsi108/109 device setup code
+ *
+ * Maintained by Roy Zang < tie-fei.zang@freescale.com >
+ *
+ * This program is free software; you can redistribute  it and/or modify it
+ * under  the terms of  the GNU General  Public License as published by the
+ * Free Software Foundation;  either version 2 of the  License, or (at your
+ * option) any later version.
+ */
+
+#include <linux/config.h>
+#include <linux/stddef.h>
+#include <linux/kernel.h>
+#include <linux/init.h>
+#include <linux/errno.h>
+#include <linux/major.h>
+#include <linux/delay.h>
+#include <linux/irq.h>
+#include <linux/module.h>
+#include <linux/device.h>
+#include <linux/platform_device.h>
+#include <asm/tsi108.h>
+
+#include <asm/system.h>
+#include <asm/atomic.h>
+#include <asm/io.h>
+#include <asm/irq.h>
+#include <asm/prom.h>
+#include <mm/mmu_decl.h>
+
+#undef DEBUG
+
+#ifdef DEBUG
+#define DBG(fmt...) do { printk(fmt); } while(0)
+#else
+#define DBG(fmt...) do { } while(0)
+#endif
+
+static phys_addr_t tsi108_csr_base = -1;
+
+phys_addr_t get_csrbase(void)
+{
+       struct device_node *tsi;
+
+       if (tsi108_csr_base != -1)
+               return tsi108_csr_base;
+
+       tsi = of_find_node_by_type(NULL, "tsi-bridge");
+       if (tsi) {
+               unsigned int size;
+               void *prop = get_property(tsi, "reg", &size);
+               tsi108_csr_base = of_translate_address(tsi, prop);
+               of_node_put(tsi);
+       };
+       return tsi108_csr_base;
+}
+
+u32 get_vir_csrbase(void)
+{
+       return (u32) (ioremap(get_csrbase(), 0x10000));
+}
+
+EXPORT_SYMBOL(get_csrbase);
+EXPORT_SYMBOL(get_vir_csrbase);
+
+static int __init tsi108_eth_of_init(void)
+{
+       struct device_node *np;
+       unsigned int i;
+       struct platform_device *tsi_eth_dev;
+       struct resource res;
+       int ret;
+
+       for (np = NULL, i = 0;
+            (np = of_find_compatible_node(np, "network", "tsi-ethernet")) != NULL;
+            i++) {
+               struct resource r[2];
+               struct device_node *phy;
+               hw_info tsi_eth_data;
+               unsigned int *id;
+               unsigned int *phy_id;
+               void *mac_addr;
+               phandle *ph;
+
+               memset(r, 0, sizeof(r));
+               memset(&tsi_eth_data, 0, sizeof(tsi_eth_data));
+
+               ret = of_address_to_resource(np, 0, &r[0]);
+               DBG("%s: name:start->end = %s:0x%lx-> 0x%lx\n",
+                       __FUNCTION__,r[0].name, r[0].start, r[0].end);
+               if (ret)
+                       goto err;
+
+               r[1].name = "tx";
+               r[1].start = np->intrs[0].line;
+               r[1].end = np->intrs[0].line;
+               r[1].flags = IORESOURCE_IRQ;
+
+               tsi_eth_dev =
+                   platform_device_register_simple("tsi-ethernet", i, &r[0],
+                                                   np->n_intrs + 1);
+
+               if (IS_ERR(tsi_eth_dev)) {
+                       ret = PTR_ERR(tsi_eth_dev);
+                       goto err;
+               }
+
+               mac_addr = get_property(np, "address", NULL);
+               memcpy(tsi_eth_data.mac_addr, mac_addr, 6);
+
+               ph = (phandle *) get_property(np, "phy-handle", NULL);
+               phy = of_find_node_by_phandle(*ph);
+
+               if (phy == NULL) {
+                       ret = -ENODEV;
+                       goto unreg;
+               }
+
+               id = (u32 *) get_property(phy, "reg", NULL);
+               phy_id = (u32 *) get_property(phy, "phy-id", NULL);
+               ret = of_address_to_resource(phy, 0, &res);
+               if (ret) {
+                       of_node_put(phy);
+                       goto unreg;
+               }
+               tsi_eth_data.regs = r[0].start;
+               tsi_eth_data.phyregs = res.start;
+               tsi_eth_data.phy = *phy_id;
+               tsi_eth_data.irq_num = np->intrs[0].line;
+               of_node_put(phy);
+               ret =
+                   platform_device_add_data(tsi_eth_dev, &tsi_eth_data,
+                                            sizeof(hw_info));
+               if (ret)
+                       goto unreg;
+       }
+       return 0;
+unreg:
+       platform_device_unregister(tsi_eth_dev);
+err:
+       return ret;
+}
+
+arch_initcall(tsi108_eth_of_init);
diff --git a/arch/powerpc/sysdev/tsi108_pci.c b/arch/powerpc/sysdev/tsi108_pci.c
new file mode 100644 (file)
index 0000000..3265d54
--- /dev/null
@@ -0,0 +1,412 @@
+/*
+ * Common routines for Tundra Semiconductor TSI108 host bridge.
+ *
+ * 2004-2005 (c) Tundra Semiconductor Corp.
+ * Author: Alex Bounine (alexandreb@tundra.com)
+ *
+ * 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 <linux/kernel.h>
+#include <linux/init.h>
+#include <linux/pci.h>
+#include <linux/slab.h>
+#include <linux/irq.h>
+#include <linux/interrupt.h>
+
+
+#include <asm/byteorder.h>
+#include <asm/io.h>
+#include <asm/irq.h>
+#include <asm/uaccess.h>
+#include <asm/machdep.h>
+#include <asm/pci-bridge.h>
+#include <asm/tsi108.h>
+#include <asm/tsi108_irq.h>
+#include <asm/prom.h>
+
+#undef DEBUG
+#ifdef DEBUG
+#define DBG(x...) printk(x)
+#else
+#define DBG(x...)
+#endif
+
+#define tsi_mk_config_addr(bus, devfunc, offset) \
+       ((((bus)<<16) | ((devfunc)<<8) | (offset & 0xfc)) + tsi108_pci_cfg_base)
+
+u32 tsi108_pci_cfg_base;
+u32 tsi108_csr_vir_base;
+
+extern u32 get_vir_csrbase(void);
+extern u32 tsi108_read_reg(u32 reg_offset);
+extern void tsi108_write_reg(u32 reg_offset, u32 val);
+
+int
+tsi108_direct_write_config(struct pci_bus *bus, unsigned int devfunc,
+                          int offset, int len, u32 val)
+{
+       volatile unsigned char *cfg_addr;
+
+       if (ppc_md.pci_exclude_device)
+               if (ppc_md.pci_exclude_device(bus->number, devfunc))
+                       return PCIBIOS_DEVICE_NOT_FOUND;
+
+       cfg_addr = (unsigned char *)(tsi_mk_config_addr(bus->number,
+                                                       devfunc, offset) |
+                                                       (offset & 0x03));
+
+#ifdef DEBUG
+       printk("PCI CFG write : ");
+       printk("%d:0x%x:0x%x ", bus->number, devfunc, offset);
+       printk("%d ADDR=0x%08x ", len, (uint) cfg_addr);
+       printk("data = 0x%08x\n", val);
+#endif
+
+       switch (len) {
+       case 1:
+               out_8((u8 *) cfg_addr, val);
+               break;
+       case 2:
+               out_le16((u16 *) cfg_addr, val);
+               break;
+       default:
+               out_le32((u32 *) cfg_addr, val);
+               break;
+       }
+
+       return PCIBIOS_SUCCESSFUL;
+}
+
+void tsi108_clear_pci_error(u32 pci_cfg_base)
+{
+       u32 err_stat, err_addr, pci_stat;
+
+       /*
+        * Quietly clear PB and PCI error flags set as result
+        * of PCI/X configuration read requests.
+        */
+
+       /* Read PB Error Log Registers */
+
+       err_stat = tsi108_read_reg(TSI108_PB_OFFSET + TSI108_PB_ERRCS);
+       err_addr = tsi108_read_reg(TSI108_PB_OFFSET + TSI108_PB_AERR);
+
+       if (err_stat & TSI108_PB_ERRCS_ES) {
+               /* Clear error flag */
+               tsi108_write_reg(TSI108_PB_OFFSET + TSI108_PB_ERRCS,
+                                TSI108_PB_ERRCS_ES);
+
+               /* Clear read error reported in PB_ISR */
+               tsi108_write_reg(TSI108_PB_OFFSET + TSI108_PB_ISR,
+                                TSI108_PB_ISR_PBS_RD_ERR);
+
+               /* Clear PCI/X bus cfg errors if applicable */
+               if ((err_addr & 0xFF000000) == pci_cfg_base) {
+                       pci_stat =
+                           tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_CSR);
+                       tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_CSR,
+                                        pci_stat);
+               }
+       }
+
+       return;
+}
+
+#define __tsi108_read_pci_config(x, addr, op)          \
+       __asm__ __volatile__(                           \
+               "       "op" %0,0,%1\n"         \
+               "1:     eieio\n"                        \
+               "2:\n"                                  \
+               ".section .fixup,\"ax\"\n"              \
+               "3:     li %0,-1\n"                     \
+               "       b 2b\n"                         \
+               ".section __ex_table,\"a\"\n"           \
+               "       .align 2\n"                     \
+               "       .long 1b,3b\n"                  \
+               ".text"                                 \
+               : "=r"(x) : "r"(addr))
+
+int
+tsi108_direct_read_config(struct pci_bus *bus, unsigned int devfn, int offset,
+                         int len, u32 * val)
+{
+       volatile unsigned char *cfg_addr;
+       u32 temp;
+
+       if (ppc_md.pci_exclude_device)
+               if (ppc_md.pci_exclude_device(bus->number, devfn))
+                       return PCIBIOS_DEVICE_NOT_FOUND;
+
+       cfg_addr = (unsigned char *)(tsi_mk_config_addr(bus->number,
+                                                       devfn,
+                                                       offset) | (offset &
+                                                                  0x03));
+
+       switch (len) {
+       case 1:
+               __tsi108_read_pci_config(temp, cfg_addr, "lbzx");
+               break;
+       case 2:
+               __tsi108_read_pci_config(temp, cfg_addr, "lhbrx");
+               break;
+       default:
+               __tsi108_read_pci_config(temp, cfg_addr, "lwbrx");
+               break;
+       }
+
+       *val = temp;
+
+#ifdef DEBUG
+       if ((0xFFFFFFFF != temp) && (0xFFFF != temp) && (0xFF != temp)) {
+               printk("PCI CFG read : ");
+               printk("%d:0x%x:0x%x ", bus->number, devfn, offset);
+               printk("%d ADDR=0x%08x ", len, (uint) cfg_addr);
+               printk("data = 0x%x\n", *val);
+       }
+#endif
+       return PCIBIOS_SUCCESSFUL;
+}
+
+void tsi108_clear_pci_cfg_error(void)
+{
+       tsi108_clear_pci_error(TSI108_PCI_CFG_BASE_PHYS);
+}
+
+static struct pci_ops tsi108_direct_pci_ops = {
+       tsi108_direct_read_config,
+       tsi108_direct_write_config
+};
+
+int __init tsi108_setup_pci(struct device_node *dev)
+{
+       int len;
+       struct pci_controller *hose;
+       struct resource rsrc;
+       int *bus_range;
+       int primary = 0, has_address = 0;
+
+       /* PCI Config mapping */
+       tsi108_pci_cfg_base = (u32)ioremap(TSI108_PCI_CFG_BASE_PHYS,
+                       TSI108_PCI_CFG_SIZE);
+       DBG("TSI_PCI: %s tsi108_pci_cfg_base=0x%x\n", __FUNCTION__,
+           tsi108_pci_cfg_base);
+
+       /* Fetch host bridge registers address */
+       has_address = (of_address_to_resource(dev, 0, &rsrc) == 0);
+
+       /* Get bus range if any */
+       bus_range = (int *)get_property(dev, "bus-range", &len);
+       if (bus_range == NULL || len < 2 * sizeof(int)) {
+               printk(KERN_WARNING "Can't get bus-range for %s, assume"
+                      " bus 0\n", dev->full_name);
+       }
+
+       hose = pcibios_alloc_controller();
+
+       if (!hose) {
+               printk("PCI Host bridge init failed\n");
+               return -ENOMEM;
+       }
+       hose->arch_data = dev;
+       hose->set_cfg_type = 1;
+
+       hose->first_busno = bus_range ? bus_range[0] : 0;
+       hose->last_busno = bus_range ? bus_range[1] : 0xff;
+
+       (hose)->ops = &tsi108_direct_pci_ops;
+
+       printk(KERN_INFO "Found tsi108 PCI host bridge at 0x%08lx. "
+              "Firmware bus number: %d->%d\n",
+              rsrc.start, hose->first_busno, hose->last_busno);
+
+       /* Interpret the "ranges" property */
+       /* This also maps the I/O region and sets isa_io/mem_base */
+       pci_process_bridge_OF_ranges(hose, dev, primary);
+       return 0;
+}
+
+/*
+ * Low level utility functions
+ */
+
+static void tsi108_pci_int_mask(u_int irq)
+{
+       u_int irp_cfg;
+       int int_line = (irq - IRQ_PCI_INTAD_BASE);
+
+       irp_cfg = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL);
+       mb();
+       irp_cfg |= (1 << int_line);     /* INTx_DIR = output */
+       irp_cfg &= ~(3 << (8 + (int_line * 2)));        /* INTx_TYPE = unused */
+       tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL, irp_cfg);
+       mb();
+       irp_cfg = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL);
+}
+
+static void tsi108_pci_int_unmask(u_int irq)
+{
+       u_int irp_cfg;
+       int int_line = (irq - IRQ_PCI_INTAD_BASE);
+
+       irp_cfg = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL);
+       mb();
+       irp_cfg &= ~(1 << int_line);
+       irp_cfg |= (3 << (8 + (int_line * 2)));
+       tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL, irp_cfg);
+       mb();
+}
+
+static void init_pci_source(void)
+{
+       tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL,
+                       0x0000ff00);
+       tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE,
+                       TSI108_PCI_IRP_ENABLE_P_INT);
+       mb();
+}
+
+static inline int get_pci_source(void)
+{
+       u_int temp = 0;
+       int irq = -1;
+       int i;
+       u_int pci_irp_stat;
+       static int mask = 0;
+
+       /* Read PCI/X block interrupt status register */
+       pci_irp_stat = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_STAT);
+       mb();
+
+       if (pci_irp_stat & TSI108_PCI_IRP_STAT_P_INT) {
+               /* Process Interrupt from PCI bus INTA# - INTD# lines */
+               temp =
+                   tsi108_read_reg(TSI108_PCI_OFFSET +
+                                   TSI108_PCI_IRP_INTAD) & 0xf;
+               mb();
+               for (i = 0; i < 4; i++, mask++) {
+                       if (temp & (1 << mask % 4)) {
+                               irq = IRQ_PCI_INTA + mask % 4;
+                               mask++;
+                               break;
+                       }
+               }
+
+               /* Disable interrupts from PCI block */
+               temp = tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE);
+               tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE,
+                               temp & ~TSI108_PCI_IRP_ENABLE_P_INT);
+               mb();
+               (void)tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE);
+               mb();
+       }
+#ifdef DEBUG
+       else {
+               printk("TSI108_PIC: error in TSI108_PCI_IRP_STAT\n");
+               pci_irp_stat =
+                   tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_STAT);
+               temp =
+                   tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_INTAD);
+               mb();
+               printk(">> stat=0x%08x intad=0x%08x ", pci_irp_stat, temp);
+               temp =
+                   tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_CFG_CTL);
+               mb();
+               printk("cfg_ctl=0x%08x ", temp);
+               temp =
+                   tsi108_read_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE);
+               mb();
+               printk("irp_enable=0x%08x\n", temp);
+       }
+#endif /* end of DEBUG */
+
+       return irq;
+}
+
+
+/*
+ * Linux descriptor level callbacks
+ */
+
+static void tsi108_pci_irq_enable(u_int irq)
+{
+       tsi108_pci_int_unmask(irq);
+}
+
+static void tsi108_pci_irq_disable(u_int irq)
+{
+       tsi108_pci_int_mask(irq);
+}
+
+static void tsi108_pci_irq_ack(u_int irq)
+{
+       tsi108_pci_int_mask(irq);
+}
+
+static void tsi108_pci_irq_end(u_int irq)
+{
+       tsi108_pci_int_unmask(irq);
+
+       /* Enable interrupts from PCI block */
+       tsi108_write_reg(TSI108_PCI_OFFSET + TSI108_PCI_IRP_ENABLE,
+                        tsi108_read_reg(TSI108_PCI_OFFSET +
+                                        TSI108_PCI_IRP_ENABLE) |
+                        TSI108_PCI_IRP_ENABLE_P_INT);
+       mb();
+}
+
+/*
+ * Interrupt controller descriptor for cascaded PCI interrupt controller.
+ */
+
+struct hw_interrupt_type tsi108_pci_irq = {
+       .typename = "tsi108_PCI_int",
+       .enable = tsi108_pci_irq_enable,
+       .disable = tsi108_pci_irq_disable,
+       .ack = tsi108_pci_irq_ack,
+       .end = tsi108_pci_irq_end,
+};
+
+/*
+ * Exported functions
+ */
+
+/*
+ * The Tsi108 PCI interrupts initialization routine.
+ *
+ * The INTA# - INTD# interrupts on the PCI bus are reported by the PCI block
+ * to the MPIC using single interrupt source (IRQ_TSI108_PCI). Therefore the
+ * PCI block has to be treated as a cascaded interrupt controller connected
+ * to the MPIC.
+ */
+
+void __init tsi108_pci_int_init(void)
+{
+       u_int i;
+
+       DBG("Tsi108_pci_int_init: initializing PCI interrupts\n");
+
+       for (i = 0; i < NUM_PCI_IRQS; i++) {
+               irq_desc[i + IRQ_PCI_INTAD_BASE].handler = &tsi108_pci_irq;
+               irq_desc[i + IRQ_PCI_INTAD_BASE].status |= IRQ_LEVEL;
+       }
+
+       init_pci_source();
+}
+
+int tsi108_irq_cascade(struct pt_regs *regs, void *unused)
+{
+       return get_pci_source();
+}
index d633081fa4c58123bc8769e7439af651039cb415..d1266fe2d1abc9b53277c9719019cd97f632cfd2 100644 (file)
@@ -774,11 +774,18 @@ config BLK_DEV_IDEDMA_PMAC
          performance.
 
 config BLK_DEV_IDE_PMAC_BLINK
-       bool "Blink laptop LED on drive activity"
+       bool "Blink laptop LED on drive activity (DEPRECATED)"
        depends on BLK_DEV_IDE_PMAC && ADB_PMU
+       select ADB_PMU_LED
+       select LEDS_TRIGGERS
+       select LEDS_TRIGGER_IDE_DISK
        help
          This option enables the use of the sleep LED as a hard drive
          activity LED.
+         This option is deprecated, it only selects ADB_PMU_LED and
+         LEDS_TRIGGER_IDE_DISK and changes the code in the new led class
+         device to default to the ide-disk trigger (which should be set
+         from userspace via sysfs).
 
 config BLK_DEV_IDE_SWARM
        tristate "IDE for Sibyte evaluation boards"
index ffca8b63ee79af28a1363df86c359fbcde1e12ef..e8ef3455ec356e4c9bf835f42532cb62cf57bea9 100644 (file)
@@ -420,107 +420,6 @@ static void pmac_ide_kauai_selectproc(ide_drive_t *drive);
 
 #endif /* CONFIG_BLK_DEV_IDEDMA_PMAC */
 
-/*
- * Below is the code for blinking the laptop LED along with hard
- * disk activity.
- */
-
-#ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK
-
-/* Set to 50ms minimum led-on time (also used to limit frequency
- * of requests sent to the PMU
- */
-#define PMU_HD_BLINK_TIME      (HZ/50)
-
-static struct adb_request pmu_blink_on, pmu_blink_off;
-static spinlock_t pmu_blink_lock;
-static unsigned long pmu_blink_stoptime;
-static int pmu_blink_ledstate;
-static struct timer_list pmu_blink_timer;
-static int pmu_ide_blink_enabled;
-
-
-static void
-pmu_hd_blink_timeout(unsigned long data)
-{
-       unsigned long flags;
-       
-       spin_lock_irqsave(&pmu_blink_lock, flags);
-
-       /* We may have been triggered again in a racy way, check
-        * that we really want to switch it off
-        */
-       if (time_after(pmu_blink_stoptime, jiffies))
-               goto done;
-
-       /* Previous req. not complete, try 100ms more */
-       if (pmu_blink_off.complete == 0)
-               mod_timer(&pmu_blink_timer, jiffies + PMU_HD_BLINK_TIME);
-       else if (pmu_blink_ledstate) {
-               pmu_request(&pmu_blink_off, NULL, 4, 0xee, 4, 0, 0);
-               pmu_blink_ledstate = 0;
-       }
-done:
-       spin_unlock_irqrestore(&pmu_blink_lock, flags);
-}
-
-static void
-pmu_hd_kick_blink(void *data, int rw)
-{
-       unsigned long flags;
-       
-       pmu_blink_stoptime = jiffies + PMU_HD_BLINK_TIME;
-       wmb();
-       mod_timer(&pmu_blink_timer, pmu_blink_stoptime);
-       /* Fast path when LED is already ON */
-       if (pmu_blink_ledstate == 1)
-               return;
-       spin_lock_irqsave(&pmu_blink_lock, flags);
-       if (pmu_blink_on.complete && !pmu_blink_ledstate) {
-               pmu_request(&pmu_blink_on, NULL, 4, 0xee, 4, 0, 1);
-               pmu_blink_ledstate = 1;
-       }
-       spin_unlock_irqrestore(&pmu_blink_lock, flags);
-}
-
-static int
-pmu_hd_blink_init(void)
-{
-       struct device_node *dt;
-       const char *model;
-
-       /* Currently, I only enable this feature on KeyLargo based laptops,
-        * older laptops may support it (at least heathrow/paddington) but
-        * I don't feel like loading those venerable old machines with so
-        * much additional interrupt & PMU activity...
-        */
-       if (pmu_get_model() != PMU_KEYLARGO_BASED)
-               return 0;
-       
-       dt = of_find_node_by_path("/");
-       if (dt == NULL)
-               return 0;
-       model = (const char *)get_property(dt, "model", NULL);
-       if (model == NULL)
-               return 0;
-       if (strncmp(model, "PowerBook", strlen("PowerBook")) != 0 &&
-           strncmp(model, "iBook", strlen("iBook")) != 0) {
-               of_node_put(dt);
-               return 0;
-       }
-       of_node_put(dt);
-
-       pmu_blink_on.complete = 1;
-       pmu_blink_off.complete = 1;
-       spin_lock_init(&pmu_blink_lock);
-       init_timer(&pmu_blink_timer);
-       pmu_blink_timer.function = pmu_hd_blink_timeout;
-
-       return 1;
-}
-
-#endif /* CONFIG_BLK_DEV_IDE_PMAC_BLINK */
-
 /*
  * N.B. this can't be an initfunc, because the media-bay task can
  * call ide_[un]register at any time.
@@ -1192,23 +1091,6 @@ pmac_ide_do_suspend(ide_hwif_t *hwif)
        pmif->timings[0] = 0;
        pmif->timings[1] = 0;
        
-#ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK
-       /* Note: This code will be called for every hwif, thus we'll
-        * try several time to stop the LED blinker timer,  but that
-        * should be harmless
-        */
-       if (pmu_ide_blink_enabled) {
-               unsigned long flags;
-
-               /* Make sure we don't hit the PMU blink */
-               spin_lock_irqsave(&pmu_blink_lock, flags);
-               if (pmu_blink_ledstate)
-                       del_timer(&pmu_blink_timer);
-               pmu_blink_ledstate = 0;
-               spin_unlock_irqrestore(&pmu_blink_lock, flags);
-       }
-#endif /* CONFIG_BLK_DEV_IDE_PMAC_BLINK */
-
        disable_irq(pmif->irq);
 
        /* The media bay will handle itself just fine */
@@ -1376,13 +1258,6 @@ pmac_ide_setup_device(pmac_ide_hwif_t *pmif, ide_hwif_t *hwif)
                hwif->selectproc = pmac_ide_selectproc;
        hwif->speedproc = pmac_ide_tune_chipset;
 
-#ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK
-       pmu_ide_blink_enabled = pmu_hd_blink_init();
-
-       if (pmu_ide_blink_enabled)
-               hwif->led_act = pmu_hd_kick_blink;
-#endif
-
        printk(KERN_INFO "ide%d: Found Apple %s controller, bus ID %d%s, irq %d\n",
               hwif->index, model_name[pmif->kind], pmif->aapl_bus_id,
               pmif->mediabay ? " (mediabay)" : "", hwif->irq);
index 37cd6ee4586b35b6110a5d948a5dd01d1bbd6031..54f3f6b94efc1e4ac9a2a3bfdff4a70dbf6b2863 100644 (file)
@@ -78,6 +78,18 @@ config ADB_PMU
          this device; you should do so if your machine is one of those
          mentioned above.
 
+config ADB_PMU_LED
+       bool "Support for the Power/iBook front LED"
+       depends on ADB_PMU
+       select NEW_LEDS
+       select LEDS_CLASS
+       help
+         Support the front LED on Power/iBooks as a generic LED that can
+         be triggered by any of the supported triggers. To get the
+         behaviour of the old CONFIG_BLK_DEV_IDE_PMAC_BLINK, select this
+         and the ide-disk LED trigger and configure appropriately through
+         sysfs.
+
 config PMAC_SMU
        bool "Support for SMU  based PowerMacs"
        depends on PPC_PMAC64
index 45a268f8047ed83fd39503cc116e0e6ea9b8675b..b53d45f87b0bee7a74834cab9b2897f7d8eaa0f9 100644 (file)
@@ -12,6 +12,7 @@ obj-$(CONFIG_INPUT_ADBHID)    += adbhid.o
 obj-$(CONFIG_ANSLCD)           += ans-lcd.o
 
 obj-$(CONFIG_ADB_PMU)          += via-pmu.o via-pmu-event.o
+obj-$(CONFIG_ADB_PMU_LED)      += via-pmu-led.o
 obj-$(CONFIG_PMAC_BACKLIGHT)   += via-pmu-backlight.o
 obj-$(CONFIG_ADB_CUDA)         += via-cuda.o
 obj-$(CONFIG_PMAC_APM_EMU)     += apm_emu.o
diff --git a/drivers/macintosh/via-pmu-led.c b/drivers/macintosh/via-pmu-led.c
new file mode 100644 (file)
index 0000000..af8375e
--- /dev/null
@@ -0,0 +1,144 @@
+/*
+ * via-pmu LED class device
+ *
+ * Copyright 2006 Johannes Berg <johannes@sipsolutions.net>
+ *
+ * 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, GOOD TITLE or
+ * NON INFRINGEMENT.  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., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301 USA
+ *
+ */
+#include <linux/types.h>
+#include <linux/kernel.h>
+#include <linux/device.h>
+#include <linux/leds.h>
+#include <linux/adb.h>
+#include <linux/pmu.h>
+#include <asm/prom.h>
+
+static spinlock_t pmu_blink_lock;
+static struct adb_request pmu_blink_req;
+/* -1: no change, 0: request off, 1: request on */
+static int requested_change;
+static int sleeping;
+
+static void pmu_req_done(struct adb_request * req)
+{
+       unsigned long flags;
+
+       spin_lock_irqsave(&pmu_blink_lock, flags);
+       /* if someone requested a change in the meantime
+        * (we only see the last one which is fine)
+        * then apply it now */
+       if (requested_change != -1 && !sleeping)
+               pmu_request(&pmu_blink_req, NULL, 4, 0xee, 4, 0, requested_change);
+       /* reset requested change */
+       requested_change = -1;
+       spin_unlock_irqrestore(&pmu_blink_lock, flags);
+}
+
+static void pmu_led_set(struct led_classdev *led_cdev,
+                       enum led_brightness brightness)
+{
+       unsigned long flags;
+
+       spin_lock_irqsave(&pmu_blink_lock, flags);
+       switch (brightness) {
+       case LED_OFF:
+               requested_change = 0;
+               break;
+       case LED_FULL:
+               requested_change = 1;
+               break;
+       default:
+               goto out;
+               break;
+       }
+       /* if request isn't done, then don't do anything */
+       if (pmu_blink_req.complete && !sleeping)
+               pmu_request(&pmu_blink_req, NULL, 4, 0xee, 4, 0, requested_change);
+ out:
+       spin_unlock_irqrestore(&pmu_blink_lock, flags);
+}
+
+static struct led_classdev pmu_led = {
+       .name = "pmu-front-led",
+#ifdef CONFIG_BLK_DEV_IDE_PMAC_BLINK
+       .default_trigger = "ide-disk",
+#endif
+       .brightness_set = pmu_led_set,
+};
+
+#ifdef CONFIG_PM
+static int pmu_led_sleep_call(struct pmu_sleep_notifier *self, int when)
+{
+       unsigned long flags;
+
+       spin_lock_irqsave(&pmu_blink_lock, flags);
+
+       switch (when) {
+       case PBOOK_SLEEP_REQUEST:
+               sleeping = 1;
+               break;
+       case PBOOK_WAKE:
+               sleeping = 0;
+               break;
+       default:
+               /* do nothing */
+               break;
+       }
+       spin_unlock_irqrestore(&pmu_blink_lock, flags);
+
+       return PBOOK_SLEEP_OK;
+}
+
+static struct pmu_sleep_notifier via_pmu_led_sleep_notif = {
+       .notifier_call = pmu_led_sleep_call,
+};
+#endif
+
+static int __init via_pmu_led_init(void)
+{
+       struct device_node *dt;
+       const char *model;
+
+       /* only do this on keylargo based models */
+       if (pmu_get_model() != PMU_KEYLARGO_BASED)
+               return -ENODEV;
+
+       dt = of_find_node_by_path("/");
+       if (dt == NULL)
+               return -ENODEV;
+       model = (const char *)get_property(dt, "model", NULL);
+       if (model == NULL)
+               return -ENODEV;
+       if (strncmp(model, "PowerBook", strlen("PowerBook")) != 0 &&
+           strncmp(model, "iBook", strlen("iBook")) != 0) {
+               of_node_put(dt);
+               /* ignore */
+               return -ENODEV;
+       }
+       of_node_put(dt);
+
+       spin_lock_init(&pmu_blink_lock);
+       /* no outstanding req */
+       pmu_blink_req.complete = 1;
+       pmu_blink_req.done = pmu_req_done;
+#ifdef CONFIG_PM
+       pmu_register_sleep_notifier(&via_pmu_led_sleep_notif);
+#endif
+       return led_classdev_register(NULL, &pmu_led);
+}
+
+late_initcall(via_pmu_led_init);
index fab41c280aa1993697eff52dfebf3b5de2129a6e..1ba3c9983614dc9232f4dd921b32abc7e20f4a92 100644 (file)
@@ -117,38 +117,30 @@ extern void do_cpu_ftr_fixups(unsigned long offset);
 #define CPU_FTR_PPC_LE                 ASM_CONST(0x0000000000200000)
 #define CPU_FTR_REAL_LE                        ASM_CONST(0x0000000000400000)
 
+/*
+ * Add the 64-bit processor unique features in the top half of the word;
+ * on 32-bit, make the names available but defined to be 0.
+ */
 #ifdef __powerpc64__
-/* Add the 64b processor unique features in the top half of the word */
-#define CPU_FTR_SLB                    ASM_CONST(0x0000000100000000)
-#define CPU_FTR_16M_PAGE               ASM_CONST(0x0000000200000000)
-#define CPU_FTR_TLBIEL                 ASM_CONST(0x0000000400000000)
-#define CPU_FTR_NOEXECUTE              ASM_CONST(0x0000000800000000)
-#define CPU_FTR_IABR                   ASM_CONST(0x0000002000000000)
-#define CPU_FTR_MMCRA                  ASM_CONST(0x0000004000000000)
-#define CPU_FTR_CTRL                   ASM_CONST(0x0000008000000000)
-#define CPU_FTR_SMT                    ASM_CONST(0x0000010000000000)
-#define CPU_FTR_COHERENT_ICACHE                ASM_CONST(0x0000020000000000)
-#define CPU_FTR_LOCKLESS_TLBIE         ASM_CONST(0x0000040000000000)
-#define CPU_FTR_CI_LARGE_PAGE          ASM_CONST(0x0000100000000000)
-#define CPU_FTR_PAUSE_ZERO             ASM_CONST(0x0000200000000000)
-#define CPU_FTR_PURR                   ASM_CONST(0x0000400000000000)
+#define LONG_ASM_CONST(x)              ASM_CONST(x)
 #else
-/* ensure on 32b processors the flags are available for compiling but
- * don't do anything */
-#define CPU_FTR_SLB                    ASM_CONST(0x0)
-#define CPU_FTR_16M_PAGE               ASM_CONST(0x0)
-#define CPU_FTR_TLBIEL                 ASM_CONST(0x0)
-#define CPU_FTR_NOEXECUTE              ASM_CONST(0x0)
-#define CPU_FTR_IABR                   ASM_CONST(0x0)
-#define CPU_FTR_MMCRA                  ASM_CONST(0x0)
-#define CPU_FTR_CTRL                   ASM_CONST(0x0)
-#define CPU_FTR_SMT                    ASM_CONST(0x0)
-#define CPU_FTR_COHERENT_ICACHE                ASM_CONST(0x0)
-#define CPU_FTR_LOCKLESS_TLBIE         ASM_CONST(0x0)
-#define CPU_FTR_CI_LARGE_PAGE          ASM_CONST(0x0)
-#define CPU_FTR_PURR                   ASM_CONST(0x0)
+#define LONG_ASM_CONST(x)              0
 #endif
 
+#define CPU_FTR_SLB                    LONG_ASM_CONST(0x0000000100000000)
+#define CPU_FTR_16M_PAGE               LONG_ASM_CONST(0x0000000200000000)
+#define CPU_FTR_TLBIEL                 LONG_ASM_CONST(0x0000000400000000)
+#define CPU_FTR_NOEXECUTE              LONG_ASM_CONST(0x0000000800000000)
+#define CPU_FTR_IABR                   LONG_ASM_CONST(0x0000002000000000)
+#define CPU_FTR_MMCRA                  LONG_ASM_CONST(0x0000004000000000)
+#define CPU_FTR_CTRL                   LONG_ASM_CONST(0x0000008000000000)
+#define CPU_FTR_SMT                    LONG_ASM_CONST(0x0000010000000000)
+#define CPU_FTR_COHERENT_ICACHE                LONG_ASM_CONST(0x0000020000000000)
+#define CPU_FTR_LOCKLESS_TLBIE         LONG_ASM_CONST(0x0000040000000000)
+#define CPU_FTR_CI_LARGE_PAGE          LONG_ASM_CONST(0x0000100000000000)
+#define CPU_FTR_PAUSE_ZERO             LONG_ASM_CONST(0x0000200000000000)
+#define CPU_FTR_PURR                   LONG_ASM_CONST(0x0000400000000000)
+
 #ifndef __ASSEMBLY__
 
 #define CPU_FTR_PPCAS_ARCH_V2_BASE (CPU_FTR_SLB | \
index b7c6fc12cce22e0cb90da14178f9071693a82bc6..284c5a7db3ac43bb5790ed4ea7687ede2aad98b3 100644 (file)
 
 struct HvLpEvent;
 
-#define ITMaxLpQueues  8
+#define IT_LP_MAX_QUEUES       8
 
-#define NotUsed                0       // Queue will not be used by PLIC
-#define DedicatedIo    1       // Queue dedicated to IO processor specified
-#define DedicatedLp    2       // Queue dedicated to LP specified
-#define Shared         3       // Queue shared for both IO and LP
+#define IT_LP_NOT_USED         0       /* Queue will not be used by PLIC */
+#define IT_LP_DEDICATED_IO     1       /* Queue dedicated to IO processor specified */
+#define IT_LP_DEDICATED_LP     2       /* Queue dedicated to LP specified */
+#define IT_LP_SHARED           3       /* Queue shared for both IO and LP */
 
-#define LpEventStackSize       4096
-#define LpEventMaxSize         256
-#define LpEventAlign           64
+#define IT_LP_EVENT_STACK_SIZE 4096
+#define IT_LP_EVENT_MAX_SIZE   256
+#define IT_LP_EVENT_ALIGN      64
 
 struct hvlpevent_queue {
 /*
- * The xSlicCurEventPtr is the pointer to the next event stack entry
+ * The hq_current_event is the pointer to the next event stack entry
  * that will become valid.  The OS must peek at this entry to determine
  * if it is valid.  PLIC will set the valid indicator as the very last
  * store into that entry.
@@ -52,23 +52,23 @@ struct hvlpevent_queue {
  * location again.
  *
  * If the event stack fills and there are overflow events, then PLIC
- * will set the xPlicOverflowIntPending flag in which case the OS will
+ * will set the hq_overflow_pending flag in which case the OS will
  * have to fetch the additional LP events once they have drained the
  * event stack.
  *
  * The first 16-bytes are known by both the OS and PLIC.  The remainder
  * of the cache line is for use by the OS.
  */
-       u8      xPlicOverflowIntPending;// 0x00 Overflow events are pending
-       u8      xPlicStatus;            // 0x01 DedicatedIo or DedicatedLp or NotUsed
-       u16     xSlicLogicalProcIndex;  // 0x02 Logical Proc Index for correlation
-       u8      xPlicRsvd[12];          // 0x04
-       char    *xSlicCurEventPtr;      // 0x10
-       char    *xSlicLastValidEventPtr; // 0x18
-       char    *xSlicEventStackPtr;    // 0x20
-       u8      xIndex;                 // 0x28 unique sequential index.
-       u8      xSlicRsvd[3];           // 0x29-2b
-       spinlock_t      lock;
+       u8              hq_overflow_pending;    /* 0x00 Overflow events are pending */
+       u8              hq_status;              /* 0x01 DedicatedIo or DedicatedLp or NotUsed */
+       u16             hq_proc_index;          /* 0x02 Logical Proc Index for correlation */
+       u8              hq_reserved1[12];       /* 0x04 */
+       char            *hq_current_event;      /* 0x10 */
+       char            *hq_last_event;         /* 0x18 */
+       char            *hq_event_stack;        /* 0x20 */
+       u8              hq_index;               /* 0x28 unique sequential index. */
+       u8              hq_reserved2[3];        /* 0x29-2b */
+       spinlock_t      hq_lock;
 };
 
 extern struct hvlpevent_queue hvlpevent_queue;
index 5a5c3b5ab1e0236686975c0abb9d94bb9a0ef9fd..dc1574c945f8fb8a605413aa8b5b384ef2bba19a 100644 (file)
@@ -15,6 +15,8 @@
 #define KDUMP_TRAMPOLINE_START 0x0100
 #define KDUMP_TRAMPOLINE_END   0x3000
 
+#define KDUMP_MIN_TCE_ENTRIES  2048
+
 #else /* !CONFIG_CRASH_DUMP */
 
 #define PHYSICAL_START 0x0
index efe8872ec58382f78ba3807944d601e7409c80b4..8f7fd5cfec34f4c9fa0a39843ae443825f277fda 100644 (file)
@@ -112,9 +112,13 @@ static inline void crash_setup_regs(struct pt_regs *newregs,
 #ifdef __powerpc64__
 extern void kexec_smp_wait(void);      /* get and clear naca physid, wait for
                                          master to copy new code to 0 */
-extern void __init kexec_setup(void);
 extern int crashing_cpu;
 extern void crash_send_ipi(void (*crash_ipi_callback)(struct pt_regs *));
+extern cpumask_t cpus_in_sr;
+static inline int kexec_sr_activated(int cpu)
+{
+       return cpu_isset(cpu,cpus_in_sr);
+}
 #endif /* __powerpc64 __ */
 
 struct kimage;
@@ -124,10 +128,13 @@ extern int default_machine_kexec_prepare(struct kimage *image);
 extern void default_machine_crash_shutdown(struct pt_regs *regs);
 
 extern void machine_kexec_simple(struct kimage *image);
+extern void crash_kexec_secondary(struct pt_regs *regs);
 extern int overlaps_crashkernel(unsigned long start, unsigned long size);
 extern void reserve_crashkernel(void);
 
 #else /* !CONFIG_KEXEC */
+static inline int kexec_sr_activated(int cpu) { return 0; }
+static inline void crash_kexec_secondary(struct pt_regs *regs) { }
 
 static inline int overlaps_crashkernel(unsigned long start, unsigned long size)
 {
index 73db1f71329db02702e323408338b272a3cd6cc5..eba133d149a793d3e7c2b05b25bb4036920a6a5b 100644 (file)
@@ -81,6 +81,8 @@ struct machdep_calls {
        void            (*tce_free)(struct iommu_table *tbl,
                                    long index,
                                    long npages);
+       unsigned long   (*tce_get)(struct iommu_table *tbl,
+                                   long index);
        void            (*tce_flush)(struct iommu_table *tbl);
        void            (*iommu_dev_setup)(struct pci_dev *dev);
        void            (*iommu_bus_setup)(struct pci_bus *bus);
index 3a5ebe229af56763ec8956573d579161aad4e4cb..c3fc7a28e3cd0cb73dd245c727cf0b3d979ee082 100644 (file)
@@ -238,7 +238,6 @@ extern int hash_huge_page(struct mm_struct *mm, unsigned long access,
                          unsigned long ea, unsigned long vsid, int local,
                          unsigned long trap);
 
-extern void htab_finish_init(void);
 extern int htab_bolt_mapping(unsigned long vstart, unsigned long vend,
                             unsigned long pstart, unsigned long mode,
                             int psize);
index 8c6b1a6d944f57e8ead421ea1e42a0db0fcbecc5..083ac917bd293b4be1640d50efdad07272260117 100644 (file)
@@ -25,8 +25,13 @@ static inline void enter_lazy_tlb(struct mm_struct *mm,
 {
 }
 
+/*
+ * The proto-VSID space has 2^35 - 1 segments available for user mappings.
+ * Each segment contains 2^28 bytes.  Each context maps 2^44 bytes,
+ * so we can support 2^19-1 contexts (19 == 35 + 28 - 44).
+ */
 #define NO_CONTEXT     0
-#define MAX_CONTEXT    (0x100000-1)
+#define MAX_CONTEXT    ((1UL << 19) - 1)
 
 extern int init_new_context(struct task_struct *tsk, struct mm_struct *mm);
 extern void destroy_context(struct mm_struct *mm);
index d0a6718d188bfb4dc3f85145758c06c6d1fac671..f260382739faa81018e2f63c066432da9ece11a7 100644 (file)
 #ifndef __ASM_POWERPC_MPC86xx_H__
 #define __ASM_POWERPC_MPC86xx_H__
 
-#include <linux/config.h>
 #include <asm/mmu.h>
 
 #ifdef CONFIG_PPC_86xx
 
-#ifdef CONFIG_MPC8641_HPCN
-#include <platforms/86xx/mpc8641_hpcn.h>
-#endif
-
 #define _IO_BASE        isa_io_base
 #define _ISA_MEM_BASE   isa_mem_base
 #ifdef CONFIG_PCI
index 02e213e3d69f0cc8151b96c8b0f9a4e526a187ee..a33c6acffa61f5c8bad8fbb007b1fc0dd0590563 100644 (file)
@@ -181,6 +181,9 @@ extern int rtas_set_rtc_time(struct rtc_time *rtc_time);
 extern unsigned int rtas_busy_delay_time(int status);
 extern unsigned int rtas_busy_delay(int status);
 
+extern int early_init_dt_scan_rtas(unsigned long node,
+               const char *uname, int depth, void *data);
+
 extern void pSeries_log_error(char *buf, unsigned int err_type, int fatal);
 
 /* Error types logged.  */
index 4463148c659f9672b4b4cadf48d79a037a462dcc..dcde4410348d2da87c890c6cb9fe8a2f30dcb69f 100644 (file)
@@ -18,8 +18,9 @@
 #include <linux/percpu.h>
 
 #include <asm/processor.h>
-#ifdef CONFIG_PPC64
+#ifdef CONFIG_PPC_ISERIES
 #include <asm/paca.h>
+#include <asm/firmware.h>
 #include <asm/iseries/hv_call.h>
 #endif
 
@@ -177,7 +178,8 @@ static inline void set_dec(int val)
 #ifdef CONFIG_PPC_ISERIES
        int cur_dec;
 
-       if (get_lppaca()->shared_proc) {
+       if (firmware_has_feature(FW_FEATURE_ISERIES) &&
+                       get_lppaca()->shared_proc) {
                get_lppaca()->virtual_decr = val;
                cur_dec = get_dec();
                if (cur_dec > val)
diff --git a/include/asm-powerpc/todc.h b/include/asm-powerpc/todc.h
new file mode 100644 (file)
index 0000000..60a8c39
--- /dev/null
@@ -0,0 +1,487 @@
+/*
+ * Definitions for the M48Txx and mc146818 series of Time of day/Real Time
+ * Clock chips.
+ *
+ * Author: Mark A. Greer <mgreer@mvista.com>
+ *
+ * 2001 (c) MontaVista, Software, Inc.  This file is licensed under
+ * the terms of the GNU General Public License version 2.  This program
+ * is licensed "as is" without any warranty of any kind, whether express
+ * or implied.
+ */
+
+/*
+ * Support for the M48T37/M48T59/.../mc146818 Real Time Clock chips.
+ * Purpose is to make one generic file that handles all of these chips instead
+ * of every platform implementing the same code over & over again.
+ */
+
+#ifndef __PPC_KERNEL_TODC_H
+#define __PPC_KERNEL_TODC_H
+
+typedef struct {
+       uint rtc_type;          /* your particular chip */
+
+       /*
+        * Following are the addresses of the AS0, AS1, and DATA registers
+        * of these chips.  Note that these are board-specific.
+        */
+       unsigned int nvram_as0;
+       unsigned int nvram_as1;
+       unsigned int nvram_data;
+
+       /*
+        * Define bits to stop external set of regs from changing so
+        * the chip can be read/written reliably.
+        */
+       unsigned char enable_read;
+       unsigned char enable_write;
+
+       /*
+        * Following is the number of AS0 address bits.  This is normally
+        * 8 but some bad hardware routes address lines incorrectly.
+        */
+       int as0_bits;
+
+       int nvram_size; /* Size of NVRAM on chip */
+       int sw_flags;   /* Software control flags */
+
+       /* Following are the register offsets for the particular chip */
+       int year;
+       int month;
+       int day_of_month;
+       int day_of_week;
+       int hours;
+       int minutes;
+       int seconds;
+       int control_b;
+       int control_a;
+       int watchdog;
+       int interrupts;
+       int alarm_date;
+       int alarm_hour;
+       int alarm_minutes;
+       int alarm_seconds;
+       int century;
+       int flags;
+
+       /*
+        * Some RTC chips have their NVRAM buried behind a addr/data pair of
+        * regs on the first level/clock registers.  The following fields
+        * are the addresses for those addr/data regs.
+        */
+       int nvram_addr_reg;
+       int nvram_data_reg;
+} todc_info_t;
+
+/*
+ * Define the types of TODC/RTC variants that are supported in
+ * arch/ppc/kernel/todc_time.c
+ * Make a new one of these for any chip somehow differs from what's already
+ * defined.  That way, if you ever need to put in code to touch those
+ * bits/registers in todc_time.c, you can put it inside an
+ * 'if (todc_info->rtc_type == TODC_TYPE_XXX)' so you won't break
+ * anyone else.
+ */
+#define TODC_TYPE_MK48T35              1
+#define TODC_TYPE_MK48T37              2
+#define TODC_TYPE_MK48T59              3
+#define TODC_TYPE_DS1693               4       /* Dallas DS1693 RTC */
+#define TODC_TYPE_DS1743               5       /* Dallas DS1743 RTC */
+#define TODC_TYPE_DS1746               6       /* Dallas DS1746 RTC */
+#define TODC_TYPE_DS1747               7       /* Dallas DS1747 RTC */
+#define TODC_TYPE_DS1501               8       /* Dallas DS1501 RTC */
+#define TODC_TYPE_DS1643               9       /* Dallas DS1643 RTC */
+#define TODC_TYPE_PC97307              10      /* PC97307 internal RTC */
+#define TODC_TYPE_DS1557               11      /* Dallas DS1557 RTC */
+#define TODC_TYPE_DS17285              12      /* Dallas DS17285 RTC */
+#define TODC_TYPE_DS1553               13      /* Dallas DS1553 RTC */
+#define TODC_TYPE_MC146818             100     /* Leave room for m48txx's */
+
+/*
+ * Bit to clear/set to enable reads/writes to the chip
+ */
+#define TODC_MK48TXX_CNTL_A_R          0x40
+#define TODC_MK48TXX_CNTL_A_W          0x80
+#define TODC_MK48TXX_DAY_CB            0x80
+
+#define TODC_DS1501_CNTL_B_TE          0x80
+
+/*
+ * Define flag bits used by todc routines.
+ */
+#define TODC_FLAG_2_LEVEL_NVRAM                0x00000001
+
+/*
+ * Define the values for the various RTC's that should to into the todc_info
+ * table.
+ * Note: The XXX_NVRAM_SIZE, XXX_NVRAM_ADDR_REG, and XXX_NVRAM_DATA_REG only
+ * matter if XXX_SW_FLAGS has TODC_FLAG_2_LEVEL_NVRAM set.
+ */
+#define TODC_TYPE_MK48T35_NVRAM_SIZE           0x7ff8
+#define TODC_TYPE_MK48T35_SW_FLAGS             0
+#define TODC_TYPE_MK48T35_YEAR                 0x7fff
+#define TODC_TYPE_MK48T35_MONTH                        0x7ffe
+#define TODC_TYPE_MK48T35_DOM                  0x7ffd  /* Day of Month */
+#define TODC_TYPE_MK48T35_DOW                  0x7ffc  /* Day of Week */
+#define TODC_TYPE_MK48T35_HOURS                        0x7ffb
+#define TODC_TYPE_MK48T35_MINUTES              0x7ffa
+#define TODC_TYPE_MK48T35_SECONDS              0x7ff9
+#define TODC_TYPE_MK48T35_CNTL_B               0x7ff9
+#define TODC_TYPE_MK48T35_CNTL_A               0x7ff8
+#define TODC_TYPE_MK48T35_WATCHDOG             0x0000
+#define TODC_TYPE_MK48T35_INTERRUPTS           0x0000
+#define TODC_TYPE_MK48T35_ALARM_DATE           0x0000
+#define TODC_TYPE_MK48T35_ALARM_HOUR           0x0000
+#define TODC_TYPE_MK48T35_ALARM_MINUTES                0x0000
+#define TODC_TYPE_MK48T35_ALARM_SECONDS                0x0000
+#define TODC_TYPE_MK48T35_CENTURY              0x0000
+#define TODC_TYPE_MK48T35_FLAGS                        0x0000
+#define TODC_TYPE_MK48T35_NVRAM_ADDR_REG       0
+#define TODC_TYPE_MK48T35_NVRAM_DATA_REG       0
+
+#define TODC_TYPE_MK48T37_NVRAM_SIZE           0x7ff0
+#define TODC_TYPE_MK48T37_SW_FLAGS             0
+#define TODC_TYPE_MK48T37_YEAR                 0x7fff
+#define TODC_TYPE_MK48T37_MONTH                        0x7ffe
+#define TODC_TYPE_MK48T37_DOM                  0x7ffd  /* Day of Month */
+#define TODC_TYPE_MK48T37_DOW                  0x7ffc  /* Day of Week */
+#define TODC_TYPE_MK48T37_HOURS                        0x7ffb
+#define TODC_TYPE_MK48T37_MINUTES              0x7ffa
+#define TODC_TYPE_MK48T37_SECONDS              0x7ff9
+#define TODC_TYPE_MK48T37_CNTL_B               0x7ff9
+#define TODC_TYPE_MK48T37_CNTL_A               0x7ff8
+#define TODC_TYPE_MK48T37_WATCHDOG             0x7ff7
+#define TODC_TYPE_MK48T37_INTERRUPTS           0x7ff6
+#define TODC_TYPE_MK48T37_ALARM_DATE           0x7ff5
+#define TODC_TYPE_MK48T37_ALARM_HOUR           0x7ff4
+#define TODC_TYPE_MK48T37_ALARM_MINUTES                0x7ff3
+#define TODC_TYPE_MK48T37_ALARM_SECONDS                0x7ff2
+#define TODC_TYPE_MK48T37_CENTURY              0x7ff1
+#define TODC_TYPE_MK48T37_FLAGS                        0x7ff0
+#define TODC_TYPE_MK48T37_NVRAM_ADDR_REG       0
+#define TODC_TYPE_MK48T37_NVRAM_DATA_REG       0
+
+#define TODC_TYPE_MK48T59_NVRAM_SIZE           0x1ff0
+#define TODC_TYPE_MK48T59_SW_FLAGS             0
+#define TODC_TYPE_MK48T59_YEAR                 0x1fff
+#define TODC_TYPE_MK48T59_MONTH                        0x1ffe
+#define TODC_TYPE_MK48T59_DOM                  0x1ffd  /* Day of Month */
+#define TODC_TYPE_MK48T59_DOW                  0x1ffc  /* Day of Week */
+#define TODC_TYPE_MK48T59_HOURS                        0x1ffb
+#define TODC_TYPE_MK48T59_MINUTES              0x1ffa
+#define TODC_TYPE_MK48T59_SECONDS              0x1ff9
+#define TODC_TYPE_MK48T59_CNTL_B               0x1ff9
+#define TODC_TYPE_MK48T59_CNTL_A               0x1ff8
+#define TODC_TYPE_MK48T59_WATCHDOG             0x1fff
+#define TODC_TYPE_MK48T59_INTERRUPTS           0x1fff
+#define TODC_TYPE_MK48T59_ALARM_DATE           0x1fff
+#define TODC_TYPE_MK48T59_ALARM_HOUR           0x1fff
+#define TODC_TYPE_MK48T59_ALARM_MINUTES                0x1fff
+#define TODC_TYPE_MK48T59_ALARM_SECONDS                0x1fff
+#define TODC_TYPE_MK48T59_CENTURY              0x1fff
+#define TODC_TYPE_MK48T59_FLAGS                        0x1fff
+#define TODC_TYPE_MK48T59_NVRAM_ADDR_REG       0
+#define TODC_TYPE_MK48T59_NVRAM_DATA_REG       0
+
+#define TODC_TYPE_DS1501_NVRAM_SIZE    0x100
+#define TODC_TYPE_DS1501_SW_FLAGS      TODC_FLAG_2_LEVEL_NVRAM
+#define TODC_TYPE_DS1501_YEAR          (TODC_TYPE_DS1501_NVRAM_SIZE + 0x06)
+#define TODC_TYPE_DS1501_MONTH         (TODC_TYPE_DS1501_NVRAM_SIZE + 0x05)
+#define TODC_TYPE_DS1501_DOM           (TODC_TYPE_DS1501_NVRAM_SIZE + 0x04)
+#define TODC_TYPE_DS1501_DOW           (TODC_TYPE_DS1501_NVRAM_SIZE + 0x03)
+#define TODC_TYPE_DS1501_HOURS         (TODC_TYPE_DS1501_NVRAM_SIZE + 0x02)
+#define TODC_TYPE_DS1501_MINUTES       (TODC_TYPE_DS1501_NVRAM_SIZE + 0x01)
+#define TODC_TYPE_DS1501_SECONDS       (TODC_TYPE_DS1501_NVRAM_SIZE + 0x00)
+#define TODC_TYPE_DS1501_CNTL_B                (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0f)
+#define TODC_TYPE_DS1501_CNTL_A                (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0f)
+#define TODC_TYPE_DS1501_WATCHDOG      (TODC_TYPE_DS1501_NVRAM_SIZE + 0xff)
+#define TODC_TYPE_DS1501_INTERRUPTS    (TODC_TYPE_DS1501_NVRAM_SIZE + 0xff)
+#define TODC_TYPE_DS1501_ALARM_DATE    (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0b)
+#define TODC_TYPE_DS1501_ALARM_HOUR    (TODC_TYPE_DS1501_NVRAM_SIZE + 0x0a)
+#define TODC_TYPE_DS1501_ALARM_MINUTES (TODC_TYPE_DS1501_NVRAM_SIZE + 0x09)
+#define TODC_TYPE_DS1501_ALARM_SECONDS (TODC_TYPE_DS1501_NVRAM_SIZE + 0x08)
+#define TODC_TYPE_DS1501_CENTURY       (TODC_TYPE_DS1501_NVRAM_SIZE + 0x07)
+#define TODC_TYPE_DS1501_FLAGS         (TODC_TYPE_DS1501_NVRAM_SIZE + 0xff)
+#define TODC_TYPE_DS1501_NVRAM_ADDR_REG        0x10
+#define TODC_TYPE_DS1501_NVRAM_DATA_REG        0x13
+
+#define TODC_TYPE_DS1553_NVRAM_SIZE            0x1ff0
+#define TODC_TYPE_DS1553_SW_FLAGS              0
+#define TODC_TYPE_DS1553_YEAR                  0x1fff
+#define TODC_TYPE_DS1553_MONTH                 0x1ffe
+#define TODC_TYPE_DS1553_DOM                   0x1ffd  /* Day of Month */
+#define TODC_TYPE_DS1553_DOW                   0x1ffc  /* Day of Week */
+#define TODC_TYPE_DS1553_HOURS                 0x1ffb
+#define TODC_TYPE_DS1553_MINUTES               0x1ffa
+#define TODC_TYPE_DS1553_SECONDS               0x1ff9
+#define TODC_TYPE_DS1553_CNTL_B                        0x1ff9
+#define TODC_TYPE_DS1553_CNTL_A                        0x1ff8  /* control_a R/W regs */
+#define TODC_TYPE_DS1553_WATCHDOG              0x1ff7
+#define TODC_TYPE_DS1553_INTERRUPTS            0x1ff6
+#define TODC_TYPE_DS1553_ALARM_DATE            0x1ff5
+#define TODC_TYPE_DS1553_ALARM_HOUR            0x1ff4
+#define TODC_TYPE_DS1553_ALARM_MINUTES         0x1ff3
+#define TODC_TYPE_DS1553_ALARM_SECONDS         0x1ff2
+#define TODC_TYPE_DS1553_CENTURY               0x1ff8
+#define TODC_TYPE_DS1553_FLAGS                 0x1ff0
+#define TODC_TYPE_DS1553_NVRAM_ADDR_REG                0
+#define TODC_TYPE_DS1553_NVRAM_DATA_REG                0
+
+#define TODC_TYPE_DS1557_NVRAM_SIZE            0x7fff0
+#define TODC_TYPE_DS1557_SW_FLAGS              0
+#define TODC_TYPE_DS1557_YEAR                  0x7ffff
+#define TODC_TYPE_DS1557_MONTH                 0x7fffe
+#define TODC_TYPE_DS1557_DOM                   0x7fffd /* Day of Month */
+#define TODC_TYPE_DS1557_DOW                   0x7fffc /* Day of Week */
+#define TODC_TYPE_DS1557_HOURS                 0x7fffb
+#define TODC_TYPE_DS1557_MINUTES               0x7fffa
+#define TODC_TYPE_DS1557_SECONDS               0x7fff9
+#define TODC_TYPE_DS1557_CNTL_B                        0x7fff9
+#define TODC_TYPE_DS1557_CNTL_A                        0x7fff8 /* control_a R/W regs */
+#define TODC_TYPE_DS1557_WATCHDOG              0x7fff7
+#define TODC_TYPE_DS1557_INTERRUPTS            0x7fff6
+#define TODC_TYPE_DS1557_ALARM_DATE            0x7fff5
+#define TODC_TYPE_DS1557_ALARM_HOUR            0x7fff4
+#define TODC_TYPE_DS1557_ALARM_MINUTES         0x7fff3
+#define TODC_TYPE_DS1557_ALARM_SECONDS         0x7fff2
+#define TODC_TYPE_DS1557_CENTURY               0x7fff8
+#define TODC_TYPE_DS1557_FLAGS                 0x7fff0
+#define TODC_TYPE_DS1557_NVRAM_ADDR_REG                0
+#define TODC_TYPE_DS1557_NVRAM_DATA_REG                0
+
+#define TODC_TYPE_DS1643_NVRAM_SIZE            0x1ff8
+#define TODC_TYPE_DS1643_SW_FLAGS              0
+#define TODC_TYPE_DS1643_YEAR                  0x1fff
+#define TODC_TYPE_DS1643_MONTH                 0x1ffe
+#define TODC_TYPE_DS1643_DOM                   0x1ffd  /* Day of Month */
+#define TODC_TYPE_DS1643_DOW                   0x1ffc  /* Day of Week */
+#define TODC_TYPE_DS1643_HOURS                 0x1ffb
+#define TODC_TYPE_DS1643_MINUTES               0x1ffa
+#define TODC_TYPE_DS1643_SECONDS               0x1ff9
+#define TODC_TYPE_DS1643_CNTL_B                        0x1ff9
+#define TODC_TYPE_DS1643_CNTL_A                        0x1ff8  /* control_a R/W regs */
+#define TODC_TYPE_DS1643_WATCHDOG              0x1fff
+#define TODC_TYPE_DS1643_INTERRUPTS            0x1fff
+#define TODC_TYPE_DS1643_ALARM_DATE            0x1fff
+#define TODC_TYPE_DS1643_ALARM_HOUR            0x1fff
+#define TODC_TYPE_DS1643_ALARM_MINUTES         0x1fff
+#define TODC_TYPE_DS1643_ALARM_SECONDS         0x1fff
+#define TODC_TYPE_DS1643_CENTURY               0x1ff8
+#define TODC_TYPE_DS1643_FLAGS                 0x1fff
+#define TODC_TYPE_DS1643_NVRAM_ADDR_REG                0
+#define TODC_TYPE_DS1643_NVRAM_DATA_REG                0
+
+#define TODC_TYPE_DS1693_NVRAM_SIZE            0 /* Not handled yet */
+#define TODC_TYPE_DS1693_SW_FLAGS              0
+#define TODC_TYPE_DS1693_YEAR                  0x09
+#define TODC_TYPE_DS1693_MONTH                 0x08
+#define TODC_TYPE_DS1693_DOM                   0x07    /* Day of Month */
+#define TODC_TYPE_DS1693_DOW                   0x06    /* Day of Week */
+#define TODC_TYPE_DS1693_HOURS                 0x04
+#define TODC_TYPE_DS1693_MINUTES               0x02
+#define TODC_TYPE_DS1693_SECONDS               0x00
+#define TODC_TYPE_DS1693_CNTL_B                        0x0b
+#define TODC_TYPE_DS1693_CNTL_A                        0x0a
+#define TODC_TYPE_DS1693_WATCHDOG              0xff
+#define TODC_TYPE_DS1693_INTERRUPTS            0xff
+#define TODC_TYPE_DS1693_ALARM_DATE            0x49
+#define TODC_TYPE_DS1693_ALARM_HOUR            0x05
+#define TODC_TYPE_DS1693_ALARM_MINUTES         0x03
+#define TODC_TYPE_DS1693_ALARM_SECONDS         0x01
+#define TODC_TYPE_DS1693_CENTURY               0x48
+#define TODC_TYPE_DS1693_FLAGS                 0xff
+#define TODC_TYPE_DS1693_NVRAM_ADDR_REG                0
+#define TODC_TYPE_DS1693_NVRAM_DATA_REG                0
+
+#define TODC_TYPE_DS1743_NVRAM_SIZE            0x1ff8
+#define TODC_TYPE_DS1743_SW_FLAGS              0
+#define TODC_TYPE_DS1743_YEAR                  0x1fff
+#define TODC_TYPE_DS1743_MONTH                 0x1ffe
+#define TODC_TYPE_DS1743_DOM                   0x1ffd  /* Day of Month */
+#define TODC_TYPE_DS1743_DOW                   0x1ffc  /* Day of Week */
+#define TODC_TYPE_DS1743_HOURS                 0x1ffb
+#define TODC_TYPE_DS1743_MINUTES               0x1ffa
+#define TODC_TYPE_DS1743_SECONDS               0x1ff9
+#define TODC_TYPE_DS1743_CNTL_B                        0x1ff9
+#define TODC_TYPE_DS1743_CNTL_A                        0x1ff8  /* control_a R/W regs */
+#define TODC_TYPE_DS1743_WATCHDOG              0x1fff
+#define TODC_TYPE_DS1743_INTERRUPTS            0x1fff
+#define TODC_TYPE_DS1743_ALARM_DATE            0x1fff
+#define TODC_TYPE_DS1743_ALARM_HOUR            0x1fff
+#define TODC_TYPE_DS1743_ALARM_MINUTES         0x1fff
+#define TODC_TYPE_DS1743_ALARM_SECONDS         0x1fff
+#define TODC_TYPE_DS1743_CENTURY               0x1ff8
+#define TODC_TYPE_DS1743_FLAGS                 0x1fff
+#define TODC_TYPE_DS1743_NVRAM_ADDR_REG                0
+#define TODC_TYPE_DS1743_NVRAM_DATA_REG                0
+
+#define TODC_TYPE_DS1746_NVRAM_SIZE            0x1fff8
+#define TODC_TYPE_DS1746_SW_FLAGS              0
+#define TODC_TYPE_DS1746_YEAR                  0x1ffff
+#define TODC_TYPE_DS1746_MONTH                 0x1fffe
+#define TODC_TYPE_DS1746_DOM                   0x1fffd /* Day of Month */
+#define TODC_TYPE_DS1746_DOW                   0x1fffc /* Day of Week */
+#define TODC_TYPE_DS1746_HOURS                 0x1fffb
+#define TODC_TYPE_DS1746_MINUTES               0x1fffa
+#define TODC_TYPE_DS1746_SECONDS               0x1fff9
+#define TODC_TYPE_DS1746_CNTL_B                        0x1fff9
+#define TODC_TYPE_DS1746_CNTL_A                        0x1fff8 /* control_a R/W regs */
+#define TODC_TYPE_DS1746_WATCHDOG              0x00000
+#define TODC_TYPE_DS1746_INTERRUPTS            0x00000
+#define TODC_TYPE_DS1746_ALARM_DATE            0x00000
+#define TODC_TYPE_DS1746_ALARM_HOUR            0x00000
+#define TODC_TYPE_DS1746_ALARM_MINUTES         0x00000
+#define TODC_TYPE_DS1746_ALARM_SECONDS         0x00000
+#define TODC_TYPE_DS1746_CENTURY               0x00000
+#define TODC_TYPE_DS1746_FLAGS                 0x00000
+#define TODC_TYPE_DS1746_NVRAM_ADDR_REG                0
+#define TODC_TYPE_DS1746_NVRAM_DATA_REG                0
+
+#define TODC_TYPE_DS1747_NVRAM_SIZE            0x7fff8
+#define TODC_TYPE_DS1747_SW_FLAGS              0
+#define TODC_TYPE_DS1747_YEAR                  0x7ffff
+#define TODC_TYPE_DS1747_MONTH                 0x7fffe
+#define TODC_TYPE_DS1747_DOM                   0x7fffd /* Day of Month */
+#define TODC_TYPE_DS1747_DOW                   0x7fffc /* Day of Week */
+#define TODC_TYPE_DS1747_HOURS                 0x7fffb
+#define TODC_TYPE_DS1747_MINUTES               0x7fffa
+#define TODC_TYPE_DS1747_SECONDS               0x7fff9
+#define TODC_TYPE_DS1747_CNTL_B                        0x7fff9
+#define TODC_TYPE_DS1747_CNTL_A                        0x7fff8 /* control_a R/W regs */
+#define TODC_TYPE_DS1747_WATCHDOG              0x00000
+#define TODC_TYPE_DS1747_INTERRUPTS            0x00000
+#define TODC_TYPE_DS1747_ALARM_DATE            0x00000
+#define TODC_TYPE_DS1747_ALARM_HOUR            0x00000
+#define TODC_TYPE_DS1747_ALARM_MINUTES         0x00000
+#define TODC_TYPE_DS1747_ALARM_SECONDS         0x00000
+#define TODC_TYPE_DS1747_CENTURY               0x00000
+#define TODC_TYPE_DS1747_FLAGS                 0x00000
+#define TODC_TYPE_DS1747_NVRAM_ADDR_REG                0
+#define TODC_TYPE_DS1747_NVRAM_DATA_REG                0
+
+#define TODC_TYPE_DS17285_NVRAM_SIZE           (0x1000-0x80) /* 4Kx8 NVRAM (minus RTC regs) */
+#define TODC_TYPE_DS17285_SW_FLAGS             TODC_FLAG_2_LEVEL_NVRAM
+#define TODC_TYPE_DS17285_SECONDS              (TODC_TYPE_DS17285_NVRAM_SIZE + 0x00)
+#define TODC_TYPE_DS17285_ALARM_SECONDS                (TODC_TYPE_DS17285_NVRAM_SIZE + 0x01)
+#define TODC_TYPE_DS17285_MINUTES              (TODC_TYPE_DS17285_NVRAM_SIZE + 0x02)
+#define TODC_TYPE_DS17285_ALARM_MINUTES                (TODC_TYPE_DS17285_NVRAM_SIZE + 0x03)
+#define TODC_TYPE_DS17285_HOURS                        (TODC_TYPE_DS17285_NVRAM_SIZE + 0x04)
+#define TODC_TYPE_DS17285_ALARM_HOUR           (TODC_TYPE_DS17285_NVRAM_SIZE + 0x05)
+#define TODC_TYPE_DS17285_DOW                  (TODC_TYPE_DS17285_NVRAM_SIZE + 0x06)
+#define TODC_TYPE_DS17285_DOM                  (TODC_TYPE_DS17285_NVRAM_SIZE + 0x07)
+#define TODC_TYPE_DS17285_MONTH                        (TODC_TYPE_DS17285_NVRAM_SIZE + 0x08)
+#define TODC_TYPE_DS17285_YEAR                 (TODC_TYPE_DS17285_NVRAM_SIZE + 0x09)
+#define TODC_TYPE_DS17285_CNTL_A               (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0A)
+#define TODC_TYPE_DS17285_CNTL_B               (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0B)
+#define TODC_TYPE_DS17285_CNTL_C               (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0C)
+#define TODC_TYPE_DS17285_CNTL_D               (TODC_TYPE_DS17285_NVRAM_SIZE + 0x0D)
+#define TODC_TYPE_DS17285_WATCHDOG             0
+#define TODC_TYPE_DS17285_INTERRUPTS           0
+#define TODC_TYPE_DS17285_ALARM_DATE           0
+#define TODC_TYPE_DS17285_CENTURY              0
+#define TODC_TYPE_DS17285_FLAGS                        0
+#define TODC_TYPE_DS17285_NVRAM_ADDR_REG       0x50
+#define TODC_TYPE_DS17285_NVRAM_DATA_REG       0x53
+
+#define TODC_TYPE_MC146818_NVRAM_SIZE          0       /* XXXX */
+#define TODC_TYPE_MC146818_SW_FLAGS            0
+#define TODC_TYPE_MC146818_YEAR                        0x09
+#define TODC_TYPE_MC146818_MONTH               0x08
+#define TODC_TYPE_MC146818_DOM                 0x07    /* Day of Month */
+#define TODC_TYPE_MC146818_DOW                 0x06    /* Day of Week */
+#define TODC_TYPE_MC146818_HOURS               0x04
+#define TODC_TYPE_MC146818_MINUTES             0x02
+#define TODC_TYPE_MC146818_SECONDS             0x00
+#define TODC_TYPE_MC146818_CNTL_B              0x0a
+#define TODC_TYPE_MC146818_CNTL_A              0x0b    /* control_a R/W regs */
+#define TODC_TYPE_MC146818_WATCHDOG            0
+#define TODC_TYPE_MC146818_INTERRUPTS          0x0c
+#define TODC_TYPE_MC146818_ALARM_DATE          0xff
+#define TODC_TYPE_MC146818_ALARM_HOUR          0x05
+#define TODC_TYPE_MC146818_ALARM_MINUTES       0x03
+#define TODC_TYPE_MC146818_ALARM_SECONDS       0x01
+#define TODC_TYPE_MC146818_CENTURY             0xff
+#define TODC_TYPE_MC146818_FLAGS               0xff
+#define TODC_TYPE_MC146818_NVRAM_ADDR_REG      0
+#define TODC_TYPE_MC146818_NVRAM_DATA_REG      0
+
+#define TODC_TYPE_PC97307_NVRAM_SIZE           0       /* No NVRAM? */
+#define TODC_TYPE_PC97307_SW_FLAGS             0
+#define TODC_TYPE_PC97307_YEAR                 0x09
+#define TODC_TYPE_PC97307_MONTH                        0x08
+#define TODC_TYPE_PC97307_DOM                  0x07    /* Day of Month */
+#define TODC_TYPE_PC97307_DOW                  0x06    /* Day of Week */
+#define TODC_TYPE_PC97307_HOURS                        0x04
+#define TODC_TYPE_PC97307_MINUTES              0x02
+#define TODC_TYPE_PC97307_SECONDS              0x00
+#define TODC_TYPE_PC97307_CNTL_B               0x0a
+#define TODC_TYPE_PC97307_CNTL_A               0x0b    /* control_a R/W regs */
+#define TODC_TYPE_PC97307_WATCHDOG             0x0c
+#define TODC_TYPE_PC97307_INTERRUPTS           0x0d
+#define TODC_TYPE_PC97307_ALARM_DATE           0xff
+#define TODC_TYPE_PC97307_ALARM_HOUR           0x05
+#define TODC_TYPE_PC97307_ALARM_MINUTES                0x03
+#define TODC_TYPE_PC97307_ALARM_SECONDS                0x01
+#define TODC_TYPE_PC97307_CENTURY              0xff
+#define TODC_TYPE_PC97307_FLAGS                        0xff
+#define TODC_TYPE_PC97307_NVRAM_ADDR_REG       0
+#define TODC_TYPE_PC97307_NVRAM_DATA_REG       0
+
+/*
+ * Define macros to allocate and init the todc_info_t table that will
+ * be used by the todc_time.c routines.
+ */
+#define TODC_ALLOC()                                                   \
+       static todc_info_t todc_info_alloc;                             \
+       todc_info_t *todc_info = &todc_info_alloc;
+
+#define TODC_INIT(clock_type, as0, as1, data, bits) {                  \
+       todc_info->rtc_type = clock_type;                               \
+                                                                       \
+       todc_info->nvram_as0 = (unsigned int)(as0);                     \
+       todc_info->nvram_as1 = (unsigned int)(as1);                     \
+       todc_info->nvram_data = (unsigned int)(data);                   \
+                                                                       \
+       todc_info->as0_bits = (bits);                                   \
+                                                                       \
+       todc_info->nvram_size = clock_type ##_NVRAM_SIZE;               \
+       todc_info->sw_flags = clock_type ##_SW_FLAGS;                   \
+                                                                       \
+       todc_info->year = clock_type ##_YEAR;                           \
+       todc_info->month = clock_type ##_MONTH;                         \
+       todc_info->day_of_month = clock_type ##_DOM;                    \
+       todc_info->day_of_week = clock_type ##_DOW;                     \
+       todc_info->hours = clock_type ##_HOURS;                         \
+       todc_info->minutes = clock_type ##_MINUTES;                     \
+       todc_info->seconds = clock_type ##_SECONDS;                     \
+       todc_info->control_b = clock_type ##_CNTL_B;                    \
+       todc_info->control_a = clock_type ##_CNTL_A;                    \
+       todc_info->watchdog = clock_type ##_WATCHDOG;                   \
+       todc_info->interrupts = clock_type ##_INTERRUPTS;               \
+       todc_info->alarm_date = clock_type ##_ALARM_DATE;               \
+       todc_info->alarm_hour = clock_type ##_ALARM_HOUR;               \
+       todc_info->alarm_minutes = clock_type ##_ALARM_MINUTES;         \
+       todc_info->alarm_seconds = clock_type ##_ALARM_SECONDS;         \
+       todc_info->century = clock_type ##_CENTURY;                     \
+       todc_info->flags = clock_type ##_FLAGS;                         \
+                                                                       \
+       todc_info->nvram_addr_reg = clock_type ##_NVRAM_ADDR_REG;       \
+       todc_info->nvram_data_reg = clock_type ##_NVRAM_DATA_REG;       \
+}
+
+extern todc_info_t *todc_info;
+
+unsigned char todc_direct_read_val(int addr);
+void todc_direct_write_val(int addr, unsigned char val);
+unsigned char todc_m48txx_read_val(int addr);
+void todc_m48txx_write_val(int addr, unsigned char val);
+unsigned char todc_mc146818_read_val(int addr);
+void todc_mc146818_write_val(int addr, unsigned char val);
+
+long todc_time_init(void);
+void todc_get_rtc_time(struct rtc_time *);
+int todc_set_rtc_time(struct rtc_time *);
+void todc_calibrate_decr(void);
+
+#endif                         /* __PPC_KERNEL_TODC_H */
diff --git a/include/asm-powerpc/tsi108.h b/include/asm-powerpc/tsi108.h
new file mode 100644 (file)
index 0000000..c4c278d
--- /dev/null
@@ -0,0 +1,109 @@
+/*
+ * include/asm-ppc/tsi108.h
+ *
+ * common routine and memory layout for Tundra TSI108(Grendel) host bridge
+ * memory controller.
+ *
+ * Author: Jacob Pan (jacob.pan@freescale.com)
+ *        Alex Bounine (alexandreb@tundra.com)
+ * 2004 (c) Freescale Semiconductor Inc.  This file is licensed under
+ * the terms of the GNU General Public License version 2.  This program
+ * is licensed "as is" without any warranty of any kind, whether express
+ * or implied.
+ */
+#ifndef __PPC_KERNEL_TSI108_H
+#define __PPC_KERNEL_TSI108_H
+
+#include <asm/pci-bridge.h>
+
+/* Size of entire register space */
+#define TSI108_REG_SIZE                (0x10000)
+
+/* Sizes of register spaces for individual blocks */
+#define TSI108_HLP_SIZE                0x1000
+#define TSI108_PCI_SIZE                0x1000
+#define TSI108_CLK_SIZE                0x1000
+#define TSI108_PB_SIZE         0x1000
+#define TSI108_SD_SIZE         0x1000
+#define TSI108_DMA_SIZE                0x1000
+#define TSI108_ETH_SIZE                0x1000
+#define TSI108_I2C_SIZE                0x400
+#define TSI108_MPIC_SIZE       0x400
+#define TSI108_UART0_SIZE      0x200
+#define TSI108_GPIO_SIZE       0x200
+#define TSI108_UART1_SIZE      0x200
+
+/* Offsets within Tsi108(A) CSR space for individual blocks */
+#define TSI108_HLP_OFFSET      0x0000
+#define TSI108_PCI_OFFSET      0x1000
+#define TSI108_CLK_OFFSET      0x2000
+#define TSI108_PB_OFFSET       0x3000
+#define TSI108_SD_OFFSET       0x4000
+#define TSI108_DMA_OFFSET      0x5000
+#define TSI108_ETH_OFFSET      0x6000
+#define TSI108_I2C_OFFSET      0x7000
+#define TSI108_MPIC_OFFSET     0x7400
+#define TSI108_UART0_OFFSET    0x7800
+#define TSI108_GPIO_OFFSET     0x7A00
+#define TSI108_UART1_OFFSET    0x7C00
+
+/* Tsi108 registers used by common code components */
+#define TSI108_PCI_CSR         (0x004)
+#define TSI108_PCI_IRP_CFG_CTL (0x180)
+#define TSI108_PCI_IRP_STAT    (0x184)
+#define TSI108_PCI_IRP_ENABLE  (0x188)
+#define TSI108_PCI_IRP_INTAD   (0x18C)
+
+#define TSI108_PCI_IRP_STAT_P_INT      (0x00400000)
+#define TSI108_PCI_IRP_ENABLE_P_INT    (0x00400000)
+
+#define TSI108_CG_PWRUP_STATUS (0x234)
+
+#define TSI108_PB_ISR          (0x00C)
+#define TSI108_PB_ERRCS                (0x404)
+#define TSI108_PB_AERR         (0x408)
+
+#define TSI108_PB_ERRCS_ES             (1 << 1)
+#define TSI108_PB_ISR_PBS_RD_ERR       (1 << 8)
+
+#define TSI108_PCI_CFG_BASE_PHYS       (0xfb000000)
+#define TSI108_PCI_CFG_SIZE            (0x01000000)
+/* Global variables */
+
+extern u32 tsi108_pci_cfg_base;
+/* Exported functions */
+
+extern int tsi108_bridge_init(struct pci_controller *hose, uint phys_csr_base);
+extern unsigned long tsi108_get_mem_size(void);
+extern unsigned long tsi108_get_cpu_clk(void);
+extern unsigned long tsi108_get_sdc_clk(void);
+extern int tsi108_direct_write_config(struct pci_bus *bus, unsigned int devfn,
+                                     int offset, int len, u32 val);
+extern int tsi108_direct_read_config(struct pci_bus *bus, unsigned int devfn,
+                                    int offset, int len, u32 * val);
+extern void tsi108_clear_pci_error(u32 pci_cfg_base);
+
+extern phys_addr_t get_csrbase(void);
+
+typedef struct {
+       u32 regs;               /* hw registers base address */
+       u32 phyregs;            /* phy registers base address */
+       u16 phy;                /* phy address */
+       u16 irq_num;            /* irq number */
+       u8 mac_addr[6];         /* phy mac address */
+} hw_info;
+
+extern u32 get_vir_csrbase(void);
+extern u32 tsi108_csr_vir_base;
+
+extern inline u32 tsi108_read_reg(u32 reg_offset)
+{
+       return in_be32((volatile u32 *)(tsi108_csr_vir_base + reg_offset));
+}
+
+extern inline void tsi108_write_reg(u32 reg_offset, u32 val)
+{
+       out_be32((volatile u32 *)(tsi108_csr_vir_base + reg_offset), val);
+}
+
+#endif                         /* __PPC_KERNEL_TSI108_H */
index 19a1517ac43b7266f1fad7034863dd0fb8594bf9..55e57844fa789422f88858505f669a549809987f 100644 (file)
@@ -42,7 +42,8 @@ extern void __init udbg_init_debug_lpar(void);
 extern void __init udbg_init_pmac_realmode(void);
 extern void __init udbg_init_maple_realmode(void);
 extern void __init udbg_init_iseries(void);
-extern void __init udbg_init_rtas(void);
+extern void __init udbg_init_rtas_panel(void);
+extern void __init udbg_init_rtas_console(void);
 
 #endif /* __KERNEL__ */
 #endif /* _ASM_POWERPC_UDBG_H */
index 58f0f382597cf4416e475c63c2fa3736462de7f2..50087ecf337ea17e5429188688187b6623a57f20 100644 (file)
@@ -1042,7 +1042,6 @@ asmlinkage long compat_sys_kexec_load(unsigned long entry,
 
 void crash_kexec(struct pt_regs *regs)
 {
-       struct kimage *image;
        int locked;
 
 
@@ -1056,12 +1055,11 @@ void crash_kexec(struct pt_regs *regs)
         */
        locked = xchg(&kexec_lock, 1);
        if (!locked) {
-               image = xchg(&kexec_crash_image, NULL);
-               if (image) {
+               if (kexec_crash_image) {
                        struct pt_regs fixed_regs;
                        crash_setup_regs(&fixed_regs, regs);
                        machine_crash_shutdown(&fixed_regs);
-                       machine_kexec(image);
+                       machine_kexec(kexec_crash_image);
                }
                xchg(&kexec_lock, 0);
        }