Merge tag 'watchdog-for-linus-v4.11-2' of git://git.kernel.org/pub/scm/linux/kernel...
authorLinus Torvalds <torvalds@linux-foundation.org>
Thu, 2 Mar 2017 20:45:46 +0000 (12:45 -0800)
committerLinus Torvalds <torvalds@linux-foundation.org>
Thu, 2 Mar 2017 20:45:46 +0000 (12:45 -0800)
Pull more watchdog updates from Guenter Roeck:

 - fix fallout from enabling COMPILE_TEST

 - fix gcc-4.3 build of kempld watchdog driver

 - use hrtimer in softdog

* tag 'watchdog-for-linus-v4.11-2' of git://git.kernel.org/pub/scm/linux/kernel/git/groeck/linux-staging:
  watchdog: retu: restore MFD dependency
  watchdog: db8500: add back prmcu dependency
  watchdog: kempld: fix gcc-4.3 build
  watchdog: softdog: fire watchdog even if softirqs do not get to run
  watchdog: kempld: revert to full dependency
  watchdog: bcm2835: add CONFIG_OF dependency
  watchdog: sp805: add back AMBA dependency
  watchdog: menf21bmc: add I2C dependency
  watchdog: geode: restore hard CS5535_MFGPT dependency
  watchdog: wm831x watchdog really needs mfd

197 files changed:
Documentation/devicetree/bindings/pwm/imx-pwm.txt
Documentation/devicetree/bindings/thermal/qoriq-thermal.txt
Documentation/devicetree/bindings/thermal/rcar-gen3-thermal.txt [new file with mode: 0644]
Documentation/devicetree/bindings/thermal/zx2967-thermal.txt [new file with mode: 0644]
Documentation/filesystems/f2fs.txt
MAINTAINERS
arch/arm64/include/asm/cpufeature.h
arch/arm64/mm/mmu.c
arch/arm64/mm/proc.S
arch/powerpc/Kconfig
arch/powerpc/boot/dts/fsl/kmcent2.dts [new file with mode: 0644]
arch/powerpc/boot/dts/fsl/kmcoge4.dts
arch/powerpc/boot/dts/fsl/t1023si-post.dtsi
arch/powerpc/boot/dts/fsl/t1040si-post.dtsi
arch/powerpc/configs/85xx/kmp204x_defconfig [deleted file]
arch/powerpc/configs/pseries_defconfig
arch/powerpc/include/asm/bitops.h
arch/powerpc/include/asm/pnv-pci.h
arch/powerpc/include/asm/ppc_asm.h
arch/powerpc/include/asm/processor.h
arch/powerpc/include/asm/prom.h
arch/powerpc/include/asm/reg.h
arch/powerpc/include/asm/reg_8xx.h
arch/powerpc/include/asm/rtas.h
arch/powerpc/kernel/asm-offsets.c
arch/powerpc/kernel/cpu_setup_power.S
arch/powerpc/kernel/cputable.c
arch/powerpc/kernel/entry_32.S
arch/powerpc/kernel/head_32.S
arch/powerpc/kernel/head_8xx.S
arch/powerpc/kernel/hw_breakpoint.c
arch/powerpc/kernel/optprobes_head.S
arch/powerpc/kernel/pci-common.c
arch/powerpc/kernel/process.c
arch/powerpc/kernel/prom_init.c
arch/powerpc/kernel/setup_64.c
arch/powerpc/kernel/time.c
arch/powerpc/mm/pgtable.c
arch/powerpc/mm/slb_low.S
arch/powerpc/perf/8xx-pmu.c [new file with mode: 0644]
arch/powerpc/perf/Makefile
arch/powerpc/perf/core-book3s.c
arch/powerpc/perf/isa207-common.c
arch/powerpc/perf/isa207-common.h
arch/powerpc/perf/power8-pmu.c
arch/powerpc/perf/power9-events-list.h
arch/powerpc/perf/power9-pmu.c
arch/powerpc/platforms/85xx/Makefile
arch/powerpc/platforms/85xx/corenet_generic.c
arch/powerpc/platforms/85xx/t1042rdb_diu.c [new file with mode: 0644]
arch/powerpc/platforms/Kconfig.cputype
arch/powerpc/platforms/cell/spufs/file.c
arch/powerpc/platforms/cell/spufs/spufs.h
arch/powerpc/platforms/powernv/Kconfig
arch/powerpc/platforms/powernv/pci-ioda.c
arch/powerpc/platforms/pseries/dlpar.c
arch/powerpc/platforms/pseries/hotplug-memory.c
arch/powerpc/xmon/ppc-dis.c
arch/powerpc/xmon/ppc-opc.c
arch/powerpc/xmon/ppc.h
arch/powerpc/xmon/xmon.c
arch/x86/kernel/vmlinux.lds.S
drivers/acpi/acpi_lpss.c
drivers/dma-buf/dma-buf.c
drivers/gpu/drm/ast/ast_dram_tables.h
drivers/gpu/drm/ast/ast_drv.h
drivers/gpu/drm/ast/ast_main.c
drivers/gpu/drm/ast/ast_mode.c
drivers/gpu/drm/ast/ast_post.c
drivers/gpu/drm/ast/ast_tables.h
drivers/gpu/drm/rockchip/Kconfig
drivers/gpu/drm/rockchip/cdn-dp-core.c
drivers/gpu/drm/vmwgfx/vmwgfx_drv.c
drivers/gpu/drm/vmwgfx/vmwgfx_drv.h
drivers/gpu/drm/zte/zx_plane.c
drivers/input/rmi4/rmi_f30.c
drivers/leds/leds-pwm.c
drivers/misc/cxl/cxl.h
drivers/misc/cxl/main.c
drivers/misc/cxl/pci.c
drivers/misc/cxl/vphb.c
drivers/pci/hotplug/pnv_php.c
drivers/pwm/Kconfig
drivers/pwm/core.c
drivers/pwm/pwm-atmel-hlcdc.c
drivers/pwm/pwm-atmel.c
drivers/pwm/pwm-bcm-kona.c
drivers/pwm/pwm-berlin.c
drivers/pwm/pwm-bfin.c
drivers/pwm/pwm-brcmstb.c
drivers/pwm/pwm-fsl-ftm.c
drivers/pwm/pwm-imx.c
drivers/pwm/pwm-lp3943.c
drivers/pwm/pwm-lpss-pci.c
drivers/pwm/pwm-lpss-platform.c
drivers/pwm/pwm-lpss.c
drivers/pwm/pwm-lpss.h
drivers/pwm/pwm-mxs.c
drivers/pwm/pwm-pca9685.c
drivers/pwm/pwm-pxa.c
drivers/pwm/pwm-sti.c
drivers/pwm/pwm-sun4i.c
drivers/pwm/pwm-twl-led.c
drivers/pwm/pwm-twl.c
drivers/pwm/pwm-vt8500.c
drivers/staging/greybus/pwm.c
drivers/thermal/Kconfig
drivers/thermal/Makefile
drivers/thermal/clock_cooling.c
drivers/thermal/cpu_cooling.c
drivers/thermal/devfreq_cooling.c
drivers/thermal/imx_thermal.c
drivers/thermal/intel_powerclamp.c
drivers/thermal/mtk_thermal.c
drivers/thermal/rcar_gen3_thermal.c [new file with mode: 0644]
drivers/thermal/samsung/exynos_tmu.c
drivers/thermal/samsung/exynos_tmu.h
drivers/thermal/thermal_core.c
drivers/thermal/ti-soc-thermal/Kconfig
drivers/thermal/ti-soc-thermal/dra752-bandgap.h
drivers/thermal/ti-soc-thermal/dra752-thermal-data.c
drivers/thermal/zx2967_thermal.c [new file with mode: 0644]
fs/f2fs/checkpoint.c
fs/f2fs/data.c
fs/f2fs/debug.c
fs/f2fs/dir.c
fs/f2fs/extent_cache.c
fs/f2fs/f2fs.h
fs/f2fs/file.c
fs/f2fs/gc.c
fs/f2fs/inode.c
fs/f2fs/namei.c
fs/f2fs/node.c
fs/f2fs/node.h
fs/f2fs/recovery.c
fs/f2fs/segment.c
fs/f2fs/segment.h
fs/f2fs/super.c
fs/f2fs/xattr.c
fs/f2fs/xattr.h
fs/nfs/cache_lib.c
fs/nfs/callback_xdr.c
fs/nfs/dir.c
fs/nfs/filelayout/filelayout.c
fs/nfs/flexfilelayout/flexfilelayout.c
fs/nfs/nfs42proc.c
fs/nfs/nfs4_fs.h
fs/nfs/nfs4proc.c
fs/nfs/nfs4renewd.c
fs/nfs/nfs4session.h
fs/nfs/nfs4state.c
fs/nfs/nfs4trace.h
fs/nfs/nfs4xdr.c
fs/nfs/super.c
fs/nfs/write.c
include/linux/compiler-gcc.h
include/linux/f2fs_fs.h
include/linux/frame.h
include/linux/lockd/lockd.h
include/linux/log2.h
include/linux/pwm.h
include/linux/sunrpc/auth.h
include/linux/sunrpc/cache.h
include/linux/sunrpc/clnt.h
include/linux/sunrpc/debug.h
include/linux/sunrpc/xdr.h
include/linux/sunrpc/xprt.h
include/linux/sunrpc/xprtsock.h
include/linux/thermal.h
include/trace/events/f2fs.h
net/sunrpc/auth.c
net/sunrpc/auth_null.c
net/sunrpc/auth_unix.c
net/sunrpc/cache.c
net/sunrpc/clnt.c
net/sunrpc/debugfs.c
net/sunrpc/svcauth_unix.c
net/sunrpc/xdr.c
net/sunrpc/xprt.c
net/sunrpc/xprtrdma/fmr_ops.c
net/sunrpc/xprtrdma/frwr_ops.c
net/sunrpc/xprtrdma/rpc_rdma.c
net/sunrpc/xprtrdma/transport.c
net/sunrpc/xprtrdma/verbs.c
net/sunrpc/xprtrdma/xprt_rdma.h
net/sunrpc/xprtsock.c
scripts/mod/modpost.c
scripts/module-common.lds
sound/core/seq/seq_fifo.c
sound/core/timer.c
sound/pci/ctxfi/cthw20k1.c
sound/pci/ctxfi/cthw20k2.c
sound/pci/hda/hda_intel.c
sound/pci/hda/patch_hdmi.c
sound/pci/hda/patch_realtek.c
tools/include/linux/log2.h
tools/objtool/builtin-check.c

index e00c2e9f484dceea28c71df05461f0e61336f6ec..c61bdf8cd41bc775f0923a104cdeafe3562f5f0c 100644 (file)
@@ -6,8 +6,8 @@ Required properties:
   - "fsl,imx1-pwm" for PWM compatible with the one integrated on i.MX1
   - "fsl,imx27-pwm" for PWM compatible with the one integrated on i.MX27
 - reg: physical base address and length of the controller's registers
-- #pwm-cells: should be 2. See pwm.txt in this directory for a description of
-  the cells format.
+- #pwm-cells: 2 for i.MX1 and 3 for i.MX27 and newer SoCs. See pwm.txt
+  in this directory for a description of the cells format.
 - clocks : Clock specifiers for both ipg and per clocks.
 - clock-names : Clock names should include both "ipg" and "per"
 See the clock consumer binding,
@@ -17,7 +17,7 @@ See the clock consumer binding,
 Example:
 
 pwm1: pwm@53fb4000 {
-       #pwm-cells = <2>;
+       #pwm-cells = <3>;
        compatible = "fsl,imx53-pwm", "fsl,imx27-pwm";
        reg = <0x53fb4000 0x4000>;
        clocks = <&clks IMX5_CLK_PWM1_IPG_GATE>,
index 66223d561972c47a30c469230177ea8ea5bb59e9..20ca4ef9d77609a0bc0432256c70694e0ac1cbac 100644 (file)
@@ -17,6 +17,12 @@ Required properties:
        calibration data, as specified by the SoC reference manual.
        The first cell of each pair is the value to be written to TTCFGR,
        and the second is the value to be written to TSCFGR.
+- #thermal-sensor-cells : Must be 1. The sensor specifier is the monitoring
+       site ID, and represents the "n" in TRITSRn and TRATSRn.
+
+Optional property:
+- little-endian : If present, the TMU registers are little endian. If absent,
+       the default is big endian.
 
 Example:
 
@@ -60,4 +66,5 @@ tmu@f0000 {
 
                               0x00030000 0x00000012
                               0x00030001 0x0000001d>;
+       #thermal-sensor-cells = <1>;
 };
diff --git a/Documentation/devicetree/bindings/thermal/rcar-gen3-thermal.txt b/Documentation/devicetree/bindings/thermal/rcar-gen3-thermal.txt
new file mode 100644 (file)
index 0000000..07a9713
--- /dev/null
@@ -0,0 +1,56 @@
+* DT bindings for Renesas R-Car Gen3 Thermal Sensor driver
+
+On R-Car Gen3 SoCs, the thermal sensor controllers (TSC) control the thermal
+sensors (THS) which are the analog circuits for measuring temperature (Tj)
+inside the LSI.
+
+Required properties:
+- compatible           : "renesas,<soctype>-thermal",
+                         Examples with soctypes are:
+                           - "renesas,r8a7795-thermal" (R-Car H3)
+                           - "renesas,r8a7796-thermal" (R-Car M3-W)
+- reg                  : Address ranges of the thermal registers. Each sensor
+                         needs one address range. Sorting must be done in
+                         increasing order according to datasheet, i.e.
+                         TSC1, TSC2, ...
+- clocks               : Must contain a reference to the functional clock.
+- #thermal-sensor-cells : must be <1>.
+
+Optional properties:
+
+- interrupts           : interrupts routed to the TSC (3 for H3 and M3-W)
+- power-domain         : Must contain a reference to the power domain. This
+                         property is mandatory if the thermal sensor instance
+                         is part of a controllable power domain.
+
+Example:
+
+       tsc: thermal@e6198000 {
+               compatible = "renesas,r8a7795-thermal";
+               reg = <0 0xe6198000 0 0x68>,
+                     <0 0xe61a0000 0 0x5c>,
+                     <0 0xe61a8000 0 0x5c>;
+               interrupts = <GIC_SPI 67 IRQ_TYPE_LEVEL_HIGH>,
+                            <GIC_SPI 68 IRQ_TYPE_LEVEL_HIGH>,
+                            <GIC_SPI 69 IRQ_TYPE_LEVEL_HIGH>;
+               clocks = <&cpg CPG_MOD 522>;
+               power-domains = <&sysc R8A7795_PD_ALWAYS_ON>;
+               #thermal-sensor-cells = <1>;
+               status = "okay";
+       };
+
+       thermal-zones {
+               sensor_thermal1: sensor-thermal1 {
+                       polling-delay-passive = <250>;
+                       polling-delay = <1000>;
+                       thermal-sensors = <&tsc 0>;
+
+                       trips {
+                               sensor1_crit: sensor1-crit {
+                                       temperature = <90000>;
+                                       hysteresis = <2000>;
+                                       type = "critical";
+                               };
+                       };
+               };
+       };
diff --git a/Documentation/devicetree/bindings/thermal/zx2967-thermal.txt b/Documentation/devicetree/bindings/thermal/zx2967-thermal.txt
new file mode 100644 (file)
index 0000000..3dc1c6b
--- /dev/null
@@ -0,0 +1,116 @@
+* ZTE zx2967 family Thermal
+
+Required Properties:
+- compatible: should be one of the following.
+    * zte,zx296718-thermal
+- reg: physical base address of the controller and length of memory mapped
+    region.
+- clocks : Pairs of phandle and specifier referencing the controller's clocks.
+- clock-names: "topcrm" for the topcrm clock.
+              "apb" for the apb clock.
+- #thermal-sensor-cells: must be 0.
+
+Please note: slope coefficient defined in thermal-zones section need to be
+multiplied by 1000.
+
+Example for tempsensor:
+
+       tempsensor: tempsensor@148a000 {
+               compatible = "zte,zx296718-thermal";
+               reg = <0x0148a000 0x20>;
+               clocks = <&topcrm TEMPSENSOR_GATE>, <&audiocrm AUDIO_TS_PCLK>;
+               clock-names = "topcrm", "apb";
+               #thermal-sensor-cells = <0>;
+       };
+
+Example for cooling device:
+
+       cooling_dev: cooling_dev {
+               cluster0_cooling_dev: cluster0-cooling-dev {
+                       #cooling-cells = <2>;
+                       cpumask = <0xf>;
+                       capacitance = <1500>;
+               };
+
+       cluster1_cooling_dev: cluster1-cooling-dev {
+                       #cooling-cells = <2>;
+                       cpumask = <0x30>;
+                       capacitance = <2000>;
+               };
+       };
+
+Example for thermal zones:
+
+       thermal-zones {
+               zx296718_thermal: zx296718_thermal {
+                       polling-delay-passive = <500>;
+                       polling-delay = <1000>;
+                       sustainable-power = <6500>;
+
+                       thermal-sensors = <&tempsensor 0>;
+                       /*
+                        * slope need to be multiplied by 1000.
+                        */
+                       coefficients = <1951 (-922)>;
+
+                       trips {
+                               trip0: switch_on_temperature {
+                                       temperature = <90000>;
+                                       hysteresis = <2000>;
+                                       type = "passive";
+                               };
+
+                               trip1: desired_temperature {
+                                       temperature = <100000>;
+                                       hysteresis = <2000>;
+                                       type = "passive";
+                               };
+
+                               crit: critical_temperature {
+                                       temperature = <110000>;
+                                       hysteresis = <2000>;
+                                       type = "critical";
+                               };
+                       };
+
+                       cooling-maps {
+                               map0 {
+                                       trip = <&trip0>;
+                                       cooling-device = <&gpu 2 5>;
+                               };
+
+                               map1 {
+                                       trip = <&trip0>;
+                                       cooling-device = <&cluster0_cooling_dev 1 2>;
+                               };
+
+                               map2 {
+                                       trip = <&trip1>;
+                                       cooling-device = <&cluster0_cooling_dev 1 2>;
+                               };
+
+                               map3 {
+                                       trip = <&crit>;
+                                       cooling-device = <&cluster0_cooling_dev 1 2>;
+                               };
+
+                               map4 {
+                                       trip = <&trip0>;
+                                       cooling-device = <&cluster1_cooling_dev 1 2>;
+                                       contribution = <9000>;
+                               };
+
+                               map5 {
+                                       trip = <&trip1>;
+                                       cooling-device = <&cluster1_cooling_dev 1 2>;
+                                       contribution = <4096>;
+                               };
+
+                               map6 {
+                                       trip = <&crit>;
+                                       cooling-device = <&cluster1_cooling_dev 1 2>;
+                                       contribution = <4096>;
+                               };
+                       };
+               };
+       };
index 753dd4f96afe402e324ac437127a079726fae105..4f6531a4701bef5529a5ca05c29a3556d4c696e9 100644 (file)
@@ -125,13 +125,14 @@ active_logs=%u         Support configuring the number of active logs. In the
 disable_ext_identify   Disable the extension list configured by mkfs, so f2fs
                        does not aware of cold files such as media files.
 inline_xattr           Enable the inline xattrs feature.
+noinline_xattr         Disable the inline xattrs feature.
 inline_data            Enable the inline data feature: New created small(<~3.4k)
                        files can be written into inode block.
 inline_dentry          Enable the inline dir feature: data in new created
                        directory entries can be written into inode block. The
                        space of inode block which is used to store inline
                        dentries is limited to ~3.4k.
-noinline_dentry        Diable the inline dentry feature.
+noinline_dentry        Disable the inline dentry feature.
 flush_merge           Merge concurrent cache_flush commands as much as possible
                        to eliminate redundant command issues. If the underlying
                       device handles the cache_flush command relatively slowly,
@@ -157,6 +158,8 @@ data_flush             Enable data flushing before checkpoint in order to
 mode=%s                Control block allocation mode which supports "adaptive"
                        and "lfs". In "lfs" mode, there should be no random
                        writes towards main area.
+io_bits=%u             Set the bit size of write IO requests. It should be set
+                       with "mode=lfs".
 
 ================================================================================
 DEBUGFS ENTRIES
@@ -174,7 +177,7 @@ f2fs. Each file shows the whole f2fs information.
 SYSFS ENTRIES
 ================================================================================
 
-Information about mounted f2f2 file systems can be found in
+Information about mounted f2fs file systems can be found in
 /sys/fs/f2fs.  Each mounted filesystem will have a directory in
 /sys/fs/f2fs based on its device name (i.e., /sys/fs/f2fs/sda).
 The files in each per-device directory are shown in table below.
index 846f97aa3508554d70be28d319b55708ba6bae14..00018356f4a5200bdaf22230708dccef9497fb7d 100644 (file)
@@ -7483,18 +7483,24 @@ L:      linuxppc-dev@lists.ozlabs.org
 Q:     http://patchwork.ozlabs.org/project/linuxppc-dev/list/
 T:     git git://git.kernel.org/pub/scm/linux/kernel/git/powerpc/linux.git
 S:     Supported
+F:     Documentation/ABI/stable/sysfs-firmware-opal-*
+F:     Documentation/devicetree/bindings/powerpc/opal/
+F:     Documentation/devicetree/bindings/rtc/rtc-opal.txt
+F:     Documentation/devicetree/bindings/i2c/i2c-opal.txt
 F:     Documentation/powerpc/
 F:     arch/powerpc/
 F:     drivers/char/tpm/tpm_ibmvtpm*
 F:     drivers/crypto/nx/
 F:     drivers/crypto/vmx/
+F:     drivers/i2c/busses/i2c-opal.c
 F:     drivers/net/ethernet/ibm/ibmveth.*
 F:     drivers/net/ethernet/ibm/ibmvnic.*
 F:     drivers/pci/hotplug/pnv_php.c
 F:     drivers/pci/hotplug/rpa*
+F:     drivers/rtc/rtc-opal.c
 F:     drivers/scsi/ibmvscsi/
+F:     drivers/tty/hvc/hvc_opal.c
 F:     tools/testing/selftests/powerpc
-N:     opal
 N:     /pmac
 N:     powermac
 N:     powernv
index 4ce82ed3e7c346d507a5844973c0a4f166284481..05310ad8c5abec54a445cb2dfcd3df5fefcefe3a 100644 (file)
@@ -184,16 +184,22 @@ static inline u64 arm64_ftr_reg_user_value(const struct arm64_ftr_reg *reg)
 }
 
 static inline int __attribute_const__
-cpuid_feature_extract_field(u64 features, int field, bool sign)
+cpuid_feature_extract_field_width(u64 features, int field, int width, bool sign)
 {
        return (sign) ?
-               cpuid_feature_extract_signed_field(features, field) :
-               cpuid_feature_extract_unsigned_field(features, field);
+               cpuid_feature_extract_signed_field_width(features, field, width) :
+               cpuid_feature_extract_unsigned_field_width(features, field, width);
+}
+
+static inline int __attribute_const__
+cpuid_feature_extract_field(u64 features, int field, bool sign)
+{
+       return cpuid_feature_extract_field_width(features, field, 4, sign);
 }
 
 static inline s64 arm64_ftr_value(const struct arm64_ftr_bits *ftrp, u64 val)
 {
-       return (s64)cpuid_feature_extract_field(val, ftrp->shift, ftrp->sign);
+       return (s64)cpuid_feature_extract_field_width(val, ftrp->shift, ftrp->width, ftrp->sign);
 }
 
 static inline bool id_aa64mmfr0_mixed_endian_el0(u64 mmfr0)
index b805c017f7899ea9012046e024ac8c9951d2dd8c..d28dbcf596b6477b1357026e78af3770a2850fe8 100644 (file)
@@ -109,10 +109,8 @@ static bool pgattr_change_is_safe(u64 old, u64 new)
 static void alloc_init_pte(pmd_t *pmd, unsigned long addr,
                                  unsigned long end, unsigned long pfn,
                                  pgprot_t prot,
-                                 phys_addr_t (*pgtable_alloc)(void),
-                                 bool page_mappings_only)
+                                 phys_addr_t (*pgtable_alloc)(void))
 {
-       pgprot_t __prot = prot;
        pte_t *pte;
 
        BUG_ON(pmd_sect(*pmd));
@@ -130,18 +128,7 @@ static void alloc_init_pte(pmd_t *pmd, unsigned long addr,
        do {
                pte_t old_pte = *pte;
 
-               /*
-                * Set the contiguous bit for the subsequent group of PTEs if
-                * its size and alignment are appropriate.
-                */
-               if (((addr | PFN_PHYS(pfn)) & ~CONT_PTE_MASK) == 0) {
-                       if (end - addr >= CONT_PTE_SIZE && !page_mappings_only)
-                               __prot = __pgprot(pgprot_val(prot) | PTE_CONT);
-                       else
-                               __prot = prot;
-               }
-
-               set_pte(pte, pfn_pte(pfn, __prot));
+               set_pte(pte, pfn_pte(pfn, prot));
                pfn++;
 
                /*
@@ -160,7 +147,6 @@ static void alloc_init_pmd(pud_t *pud, unsigned long addr, unsigned long end,
                                  phys_addr_t (*pgtable_alloc)(void),
                                  bool page_mappings_only)
 {
-       pgprot_t __prot = prot;
        pmd_t *pmd;
        unsigned long next;
 
@@ -187,18 +173,7 @@ static void alloc_init_pmd(pud_t *pud, unsigned long addr, unsigned long end,
                /* try section mapping first */
                if (((addr | next | phys) & ~SECTION_MASK) == 0 &&
                      !page_mappings_only) {
-                       /*
-                        * Set the contiguous bit for the subsequent group of
-                        * PMDs if its size and alignment are appropriate.
-                        */
-                       if (((addr | phys) & ~CONT_PMD_MASK) == 0) {
-                               if (end - addr >= CONT_PMD_SIZE)
-                                       __prot = __pgprot(pgprot_val(prot) |
-                                                         PTE_CONT);
-                               else
-                                       __prot = prot;
-                       }
-                       pmd_set_huge(pmd, phys, __prot);
+                       pmd_set_huge(pmd, phys, prot);
 
                        /*
                         * After the PMD entry has been populated once, we
@@ -208,8 +183,7 @@ static void alloc_init_pmd(pud_t *pud, unsigned long addr, unsigned long end,
                                                      pmd_val(*pmd)));
                } else {
                        alloc_init_pte(pmd, addr, next, __phys_to_pfn(phys),
-                                      prot, pgtable_alloc,
-                                      page_mappings_only);
+                                      prot, pgtable_alloc);
 
                        BUG_ON(pmd_val(old_pmd) != 0 &&
                               pmd_val(old_pmd) != pmd_val(*pmd));
index cd4d53d7e4582909f02a8aafb23ea6a5cd4a5576..877d42fb0df655c77a8fe3f0f7f517d9aa7c9247 100644 (file)
@@ -138,7 +138,7 @@ ENDPROC(cpu_do_resume)
  *     - pgd_phys - physical address of new TTB
  */
 ENTRY(cpu_do_switch_mm)
-       pre_ttbr0_update_workaround x0, x1, x2
+       pre_ttbr0_update_workaround x0, x2, x3
        mmid    x1, x1                          // get mm->context.id
        bfi     x0, x1, #48, #16                // set the ASID
        msr     ttbr0_el1, x0                   // set TTBR0
index 8582121d7a455f6181c374fbf4cba97c3dfbdb8c..494091762bd7f3a43afe15945943343c4cb23fe0 100644 (file)
@@ -115,7 +115,7 @@ config PPC
        select HAVE_PERF_REGS
        select HAVE_PERF_USER_STACK_DUMP
        select HAVE_REGS_AND_STACK_ACCESS_API
-       select HAVE_HW_BREAKPOINT if PERF_EVENTS && PPC_BOOK3S_64
+       select HAVE_HW_BREAKPOINT if PERF_EVENTS && (PPC_BOOK3S || PPC_8xx)
        select ARCH_WANT_IPC_PARSE_VERSION
        select SPARSE_IRQ
        select IRQ_DOMAIN
diff --git a/arch/powerpc/boot/dts/fsl/kmcent2.dts b/arch/powerpc/boot/dts/fsl/kmcent2.dts
new file mode 100644 (file)
index 0000000..47afa43
--- /dev/null
@@ -0,0 +1,303 @@
+/*
+ * Keymile kmcent2 Device Tree Source, based on T1040RDB DTS
+ *
+ * (C) Copyright 2016
+ * Valentin Longchamp, Keymile AG, valentin.longchamp@keymile.com
+ *
+ * Copyright 2014 - 2015 Freescale Semiconductor Inc.
+ *
+ * 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/ "t104xsi-pre.dtsi"
+
+/ {
+       model = "keymile,kmcent2";
+       compatible = "keymile,kmcent2";
+
+       aliases {
+               front_phy = &front_phy;
+       };
+
+       reserved-memory {
+               #address-cells = <2>;
+               #size-cells = <2>;
+               ranges;
+
+               bman_fbpr: bman-fbpr {
+                       size = <0 0x1000000>;
+                       alignment = <0 0x1000000>;
+               };
+               qman_fqd: qman-fqd {
+                       size = <0 0x400000>;
+                       alignment = <0 0x400000>;
+               };
+               qman_pfdr: qman-pfdr {
+                       size = <0 0x2000000>;
+                       alignment = <0 0x2000000>;
+               };
+       };
+
+       ifc: localbus@ffe124000 {
+               reg = <0xf 0xfe124000 0 0x2000>;
+               ranges = <0 0 0xf 0xe8000000 0x04000000
+                         1 0 0xf 0xfa000000 0x00010000
+                         2 0 0xf 0xfb000000 0x00010000
+                         4 0 0xf 0xc0000000 0x08000000
+                         6 0 0xf 0xd0000000 0x08000000
+                         7 0 0xf 0xd8000000 0x08000000>;
+
+               nor@0,0 {
+                       #address-cells = <1>;
+                       #size-cells = <1>;
+                       compatible = "cfi-flash";
+                       reg = <0x0 0x0 0x04000000>;
+                       bank-width = <2>;
+                       device-width = <2>;
+               };
+
+               nand@1,0 {
+                       #address-cells = <1>;
+                       #size-cells = <1>;
+                       compatible = "fsl,ifc-nand";
+                       reg = <0x1 0x0 0x10000>;
+               };
+
+               board-control@2,0 {
+                       compatible = "keymile,qriox";
+                       reg = <0x2 0x0 0x80>;
+               };
+
+               chassis-mgmt@6,0 {
+                       compatible = "keymile,bfticu";
+                       reg = <6 0 0x100>;
+                       interrupt-controller;
+                       interrupt-parent = <&mpic>;
+                       interrupts = <11 1 0 0>;
+                       #interrupt-cells = <1>;
+               };
+
+       };
+
+       memory {
+               device_type = "memory";
+       };
+
+       dcsr: dcsr@f00000000 {
+               ranges = <0x00000000 0xf 0x00000000 0x01072000>;
+       };
+
+       bportals: bman-portals@ff4000000 {
+               ranges = <0x0 0xf 0xf4000000 0x2000000>;
+       };
+
+       qportals: qman-portals@ff6000000 {
+               ranges = <0x0 0xf 0xf6000000 0x2000000>;
+       };
+
+       soc: soc@ffe000000 {
+               ranges = <0x00000000 0xf 0xfe000000 0x1000000>;
+               reg = <0xf 0xfe000000 0 0x00001000>;
+
+               spi@110000 {
+                       network-clock@1 {
+                               compatible = "zarlink,zl30364";
+                               reg = <1>;
+                               spi-max-frequency = <1000000>;
+                       };
+               };
+
+               sdhc@114000 {
+                       status = "disabled";
+               };
+
+               i2c@118000 {
+                       clock-frequency = <100000>;
+
+                       mux@70 {
+                               compatible = "nxp,pca9547";
+                               reg = <0x70>;
+                               #address-cells = <1>;
+                               #size-cells = <0>;
+                               i2c-mux-idle-disconnect;
+
+                               i2c@0 {
+                                       reg = <0>;
+                                       #address-cells = <1>;
+                                       #size-cells = <0>;
+
+                                       eeprom@54 {
+                                               compatible = "24c02";
+                                               reg = <0x54>;
+                                               pagesize = <2>;
+                                               read-only;
+                                               label = "ddr3-spd";
+                                       };
+                               };
+
+                               i2c@7 {
+                                       reg = <7>;
+                                       #address-cells = <1>;
+                                       #size-cells = <0>;
+
+                                       temp-sensor@48 {
+                                               compatible = "national,lm75";
+                                               reg = <0x48>;
+                                               label = "SENSOR_0";
+                                       };
+                                       temp-sensor@4a {
+                                               compatible = "national,lm75";
+                                               reg = <0x4a>;
+                                               label = "SENSOR_2";
+                                       };
+                                       temp-sensor@4b {
+                                               compatible = "national,lm75";
+                                               reg = <0x4b>;
+                                               label = "SENSOR_3";
+                                       };
+                               };
+                       };
+               };
+
+               i2c@118100 {
+                       clock-frequency = <100000>;
+
+                       eeprom@50 {
+                               compatible = "atmel,24c08";
+                               reg = <0x50>;
+                               pagesize = <16>;
+                       };
+
+                       eeprom@54 {
+                               compatible = "atmel,24c08";
+                               reg = <0x54>;
+                               pagesize = <16>;
+                       };
+               };
+
+               i2c@119000 {
+                       status = "disabled";
+               };
+
+               i2c@119100 {
+                       status = "disabled";
+               };
+
+               serial2: serial@11d500 {
+                       status = "disabled";
+               };
+
+               serial3: serial@11d600 {
+                       status = "disabled";
+               };
+
+               usb0: usb@210000 {
+                       status = "disabled";
+               };
+               usb1: usb@211000 {
+                       status = "disabled";
+               };
+
+               display@180000 {
+                       status = "disabled";
+               };
+
+               sata@220000 {
+                       status = "disabled";
+               };
+               sata@221000 {
+                       status = "disabled";
+               };
+
+               fman@400000 {
+                       ethernet@e0000 {
+                               fixed-link = <0 1 1000 0 0>;
+                               phy-connection-type = "sgmii";
+                       };
+
+                       ethernet@e2000 {
+                               fixed-link = <1 1 1000 0 0>;
+                               phy-connection-type = "sgmii";
+                       };
+
+                       ethernet@e4000 {
+                               status = "disabled";
+                       };
+
+                       ethernet@e6000 {
+                               status = "disabled";
+                       };
+
+                       ethernet@e8000 {
+                               phy-handle = <&front_phy>;
+                               phy-connection-type = "rgmii";
+                       };
+
+                       mdio0: mdio@fc000 {
+                               front_phy: ethernet-phy@11 {
+                                       reg = <0x11>;
+                               };
+                       };
+               };
+       };
+
+
+       pci0: pcie@ffe240000 {
+               reg = <0xf 0xfe240000 0 0x10000>;
+               ranges = <0x02000000 0 0xe0000000 0xc 0x00000000 0x0 0x20000000
+                         0x01000000 0 0x00000000 0xf 0xf8000000 0x0 0x00010000>;
+               pcie@0 {
+                       ranges = <0x02000000 0 0xe0000000
+                                 0x02000000 0 0xe0000000
+                                 0 0x20000000
+
+                                 0x01000000 0 0x00000000
+                                 0x01000000 0 0x00000000
+                                 0 0x00010000>;
+               };
+       };
+
+       pci1: pcie@ffe250000 {
+               status = "disabled";
+       };
+
+       pci2: pcie@ffe260000 {
+               status = "disabled";
+       };
+
+       pci3: pcie@ffe270000 {
+               status = "disabled";
+       };
+
+       qe: qe@ffe140000 {
+               ranges = <0x0 0xf 0xfe140000 0x40000>;
+               reg = <0xf 0xfe140000 0 0x480>;
+               brg-frequency = <0>;
+               bus-frequency = <0>;
+
+               si1: si@700 {
+                       compatible = "fsl,t1040-qe-si";
+                       reg = <0x700 0x80>;
+               };
+
+               siram1: siram@1000 {
+                       compatible = "fsl,t1040-qe-siram";
+                       reg = <0x1000 0x800>;
+               };
+
+               ucc_hdlc: ucc@2000 {
+                       device_type = "hdlc";
+                       compatible = "fsl,ucc-hdlc";
+                       rx-clock-name = "clk9";
+                       tx-clock-name = "clk9";
+                       fsl,tx-timeslot-mask = <0xfffffffe>;
+                       fsl,rx-timeslot-mask = <0xfffffffe>;
+                       fsl,siram-entry-id = <0>;
+               };
+       };
+};
+
+#include "t1040si-post.dtsi"
index ae70a24094b02bf3cf46e2edaba45d81e8ab132c..e103c0f3f650cb868a69b0f75696a7a2e344eefb 100644 (file)
                        };
                };
 
+               sdhc@114000 {
+                       status = "disabled";
+               };
+
                i2c@119000 {
                        status = "disabled";
                };
index da2894c594790e347b4126cd8fc6d95842cd9a70..4908af5010983c2af7df21020d18a9e9c2e2ffb7 100644 (file)
                                       0x00030001 0x0000000d
                                       0x00030002 0x00000019
                                       0x00030003 0x00000024>;
-               #thermal-sensor-cells = <0>;
+               #thermal-sensor-cells = <1>;
        };
 
        thermal-zones {
                        polling-delay-passive = <1000>;
                        polling-delay = <5000>;
 
-                       thermal-sensors = <&tmu>;
+                       thermal-sensors = <&tmu 0>;
 
                        trips {
                                cpu_alert: cpu-alert {
index 44e399b17f6fc99fd489920e097217a32082f501..145c7f43b5b6011874092180d300767bdfc2b82c 100644 (file)
 
                                       0x00030000 0x00000012
                                       0x00030001 0x0000001d>;
-               #thermal-sensor-cells = <0>;
+               #thermal-sensor-cells = <1>;
        };
 
        thermal-zones {
                        polling-delay-passive = <1000>;
                        polling-delay = <5000>;
 
-                       thermal-sensors = <&tmu>;
+                       thermal-sensors = <&tmu 2>;
 
                        trips {
                                cpu_alert: cpu-alert {
diff --git a/arch/powerpc/configs/85xx/kmp204x_defconfig b/arch/powerpc/configs/85xx/kmp204x_defconfig
deleted file mode 100644 (file)
index aaaaa60..0000000
+++ /dev/null
@@ -1,220 +0,0 @@
-CONFIG_PPC_85xx=y
-CONFIG_SMP=y
-CONFIG_NR_CPUS=8
-CONFIG_SYSVIPC=y
-CONFIG_POSIX_MQUEUE=y
-CONFIG_AUDIT=y
-CONFIG_NO_HZ=y
-CONFIG_HIGH_RES_TIMERS=y
-CONFIG_BSD_PROCESS_ACCT=y
-CONFIG_IKCONFIG=y
-CONFIG_IKCONFIG_PROC=y
-CONFIG_LOG_BUF_SHIFT=14
-CONFIG_CGROUPS=y
-CONFIG_CGROUP_SCHED=y
-CONFIG_RELAY=y
-CONFIG_BLK_DEV_INITRD=y
-CONFIG_KALLSYMS_ALL=y
-CONFIG_EMBEDDED=y
-CONFIG_PERF_EVENTS=y
-CONFIG_SLAB=y
-CONFIG_MODULES=y
-CONFIG_MODULE_UNLOAD=y
-CONFIG_MODULE_FORCE_UNLOAD=y
-CONFIG_MODVERSIONS=y
-# CONFIG_BLK_DEV_BSG is not set
-CONFIG_PARTITION_ADVANCED=y
-CONFIG_MAC_PARTITION=y
-CONFIG_CORENET_GENERIC=y
-CONFIG_MPIC_MSGR=y
-CONFIG_HIGHMEM=y
-# CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS is not set
-CONFIG_BINFMT_MISC=m
-CONFIG_KEXEC=y
-CONFIG_FORCE_MAX_ZONEORDER=13
-CONFIG_PCI=y
-CONFIG_PCIEPORTBUS=y
-# CONFIG_PCIEASPM is not set
-CONFIG_PCI_MSI=y
-CONFIG_ADVANCED_OPTIONS=y
-CONFIG_LOWMEM_SIZE_BOOL=y
-CONFIG_LOWMEM_SIZE=0x20000000
-CONFIG_NET=y
-CONFIG_PACKET=y
-CONFIG_UNIX=y
-CONFIG_XFRM_USER=y
-CONFIG_XFRM_SUB_POLICY=y
-CONFIG_XFRM_STATISTICS=y
-CONFIG_NET_KEY=y
-CONFIG_NET_KEY_MIGRATE=y
-CONFIG_INET=y
-CONFIG_IP_MULTICAST=y
-CONFIG_IP_ADVANCED_ROUTER=y
-CONFIG_IP_MULTIPLE_TABLES=y
-CONFIG_IP_ROUTE_MULTIPATH=y
-CONFIG_IP_ROUTE_VERBOSE=y
-CONFIG_IP_PNP=y
-CONFIG_IP_PNP_DHCP=y
-CONFIG_IP_PNP_BOOTP=y
-CONFIG_IP_PNP_RARP=y
-CONFIG_NET_IPIP=y
-CONFIG_IP_MROUTE=y
-CONFIG_IP_PIMSM_V1=y
-CONFIG_IP_PIMSM_V2=y
-CONFIG_INET_AH=y
-CONFIG_INET_ESP=y
-CONFIG_INET_IPCOMP=y
-CONFIG_IPV6=y
-CONFIG_IP_SCTP=m
-CONFIG_TIPC=y
-CONFIG_NET_SCHED=y
-CONFIG_NET_SCH_CBQ=y
-CONFIG_NET_SCH_HTB=y
-CONFIG_NET_SCH_HFSC=y
-CONFIG_NET_SCH_PRIO=y
-CONFIG_NET_SCH_MULTIQ=y
-CONFIG_NET_SCH_RED=y
-CONFIG_NET_SCH_SFQ=y
-CONFIG_NET_SCH_TEQL=y
-CONFIG_NET_SCH_TBF=y
-CONFIG_NET_SCH_GRED=y
-CONFIG_NET_CLS_BASIC=y
-CONFIG_NET_CLS_TCINDEX=y
-CONFIG_NET_CLS_U32=y
-CONFIG_CLS_U32_PERF=y
-CONFIG_CLS_U32_MARK=y
-CONFIG_NET_CLS_FLOW=y
-CONFIG_NET_CLS_CGROUP=y
-CONFIG_UEVENT_HELPER_PATH="/sbin/mdev"
-CONFIG_DEVTMPFS=y
-CONFIG_MTD=y
-CONFIG_MTD_CMDLINE_PARTS=y
-CONFIG_MTD_BLOCK=y
-CONFIG_MTD_CFI=y
-CONFIG_MTD_CFI_AMDSTD=y
-CONFIG_MTD_PHYSMAP_OF=y
-CONFIG_MTD_PHRAM=y
-CONFIG_MTD_NAND=y
-CONFIG_MTD_NAND_ECC_BCH=y
-CONFIG_MTD_NAND_FSL_ELBC=y
-CONFIG_MTD_UBI=y
-CONFIG_MTD_UBI_GLUEBI=y
-CONFIG_BLK_DEV_LOOP=y
-CONFIG_BLK_DEV_RAM=y
-CONFIG_BLK_DEV_RAM_COUNT=2
-CONFIG_BLK_DEV_RAM_SIZE=2048
-CONFIG_EEPROM_AT24=y
-CONFIG_SCSI=y
-CONFIG_BLK_DEV_SD=y
-CONFIG_CHR_DEV_ST=y
-CONFIG_BLK_DEV_SR=y
-CONFIG_CHR_DEV_SG=y
-CONFIG_SCSI_LOGGING=y
-CONFIG_SCSI_SYM53C8XX_2=y
-CONFIG_NETDEVICES=y
-# CONFIG_NET_VENDOR_3COM is not set
-# CONFIG_NET_VENDOR_ADAPTEC is not set
-# CONFIG_NET_VENDOR_ALTEON is not set
-# CONFIG_NET_VENDOR_AMD is not set
-# CONFIG_NET_VENDOR_ATHEROS is not set
-# CONFIG_NET_VENDOR_BROADCOM is not set
-# CONFIG_NET_VENDOR_BROCADE is not set
-# CONFIG_NET_VENDOR_CHELSIO is not set
-# CONFIG_NET_VENDOR_CISCO is not set
-# CONFIG_NET_VENDOR_DEC is not set
-# CONFIG_NET_VENDOR_DLINK is not set
-# CONFIG_NET_VENDOR_EMULEX is not set
-# CONFIG_NET_VENDOR_EXAR is not set
-CONFIG_FSL_PQ_MDIO=y
-CONFIG_FSL_XGMAC_MDIO=y
-# CONFIG_NET_VENDOR_HP is not set
-# CONFIG_NET_VENDOR_INTEL is not set
-# CONFIG_NET_VENDOR_MARVELL is not set
-# CONFIG_NET_VENDOR_MELLANOX is not set
-# CONFIG_NET_VENDOR_MICREL is not set
-# CONFIG_NET_VENDOR_MICROCHIP is not set
-# CONFIG_NET_VENDOR_MYRI is not set
-# CONFIG_NET_VENDOR_NATSEMI is not set
-# CONFIG_NET_VENDOR_NVIDIA is not set
-# CONFIG_NET_VENDOR_OKI is not set
-# CONFIG_NET_PACKET_ENGINE is not set
-# CONFIG_NET_VENDOR_QLOGIC is not set
-# CONFIG_NET_VENDOR_REALTEK is not set
-# CONFIG_NET_VENDOR_RDC is not set
-# CONFIG_NET_VENDOR_SEEQ is not set
-# CONFIG_NET_VENDOR_SILAN is not set
-# CONFIG_NET_VENDOR_SIS is not set
-# CONFIG_NET_VENDOR_SMSC is not set
-# CONFIG_NET_VENDOR_STMICRO is not set
-# CONFIG_NET_VENDOR_SUN is not set
-# CONFIG_NET_VENDOR_TEHUTI is not set
-# CONFIG_NET_VENDOR_TI is not set
-# CONFIG_NET_VENDOR_VIA is not set
-# CONFIG_NET_VENDOR_WIZNET is not set
-# CONFIG_NET_VENDOR_XILINX is not set
-CONFIG_MARVELL_PHY=y
-CONFIG_VITESSE_PHY=y
-CONFIG_FIXED_PHY=y
-# CONFIG_WLAN is not set
-# CONFIG_INPUT_MOUSEDEV is not set
-# CONFIG_INPUT_KEYBOARD is not set
-# CONFIG_INPUT_MOUSE is not set
-CONFIG_SERIO_LIBPS2=y
-# CONFIG_LEGACY_PTYS is not set
-CONFIG_PPC_EPAPR_HV_BYTECHAN=y
-CONFIG_SERIAL_8250=y
-CONFIG_SERIAL_8250_CONSOLE=y
-CONFIG_SERIAL_8250_MANY_PORTS=y
-CONFIG_SERIAL_8250_DETECT_IRQ=y
-CONFIG_SERIAL_8250_RSA=y
-CONFIG_NVRAM=y
-CONFIG_I2C=y
-CONFIG_I2C_CHARDEV=y
-CONFIG_I2C_MUX=y
-CONFIG_I2C_MUX_PCA954x=y
-CONFIG_I2C_MPC=y
-CONFIG_SPI=y
-CONFIG_SPI_FSL_SPI=y
-CONFIG_SPI_FSL_ESPI=y
-CONFIG_SPI_SPIDEV=m
-CONFIG_PTP_1588_CLOCK=y
-# CONFIG_HWMON is not set
-# CONFIG_USB_SUPPORT is not set
-CONFIG_EDAC=y
-CONFIG_EDAC_MM_EDAC=y
-CONFIG_EDAC_MPC85XX=y
-CONFIG_RTC_CLASS=y
-CONFIG_RTC_DRV_DS3232=y
-CONFIG_RTC_DRV_CMOS=y
-CONFIG_UIO=y
-CONFIG_STAGING=y
-CONFIG_CLK_QORIQ=y
-CONFIG_EXT2_FS=y
-CONFIG_NTFS_FS=y
-CONFIG_PROC_KCORE=y
-CONFIG_TMPFS=y
-CONFIG_JFFS2_FS=y
-CONFIG_UBIFS_FS=y
-CONFIG_CRAMFS=y
-CONFIG_SQUASHFS=y
-CONFIG_SQUASHFS_XZ=y
-CONFIG_NFS_FS=y
-CONFIG_NFS_V4=y
-CONFIG_ROOT_NFS=y
-CONFIG_NLS_ISO8859_1=y
-CONFIG_NLS_UTF8=m
-CONFIG_CRC_ITU_T=m
-CONFIG_DEBUG_INFO=y
-CONFIG_MAGIC_SYSRQ=y
-CONFIG_DEBUG_SHIRQ=y
-CONFIG_DETECT_HUNG_TASK=y
-CONFIG_SCHEDSTATS=y
-CONFIG_RCU_TRACE=y
-CONFIG_UPROBE_EVENT=y
-CONFIG_CRYPTO_NULL=y
-CONFIG_CRYPTO_PCBC=m
-CONFIG_CRYPTO_MD4=y
-CONFIG_CRYPTO_SHA256=y
-CONFIG_CRYPTO_SHA512=y
-# CONFIG_CRYPTO_ANSI_CPRNG is not set
-CONFIG_CRYPTO_DEV_FSL_CAAM=y
index 6d0eb02fefa471a436a15d2baae1465a4f417615..4ff68b752618e31405093c95dba253d8cab02684 100644 (file)
@@ -58,7 +58,6 @@ CONFIG_KEXEC_FILE=y
 CONFIG_IRQ_ALL_CPUS=y
 CONFIG_MEMORY_HOTPLUG=y
 CONFIG_MEMORY_HOTREMOVE=y
-CONFIG_MEMORY_HOTPLUG_DEFAULT_ONLINE=y
 CONFIG_KSM=y
 CONFIG_TRANSPARENT_HUGEPAGE=y
 CONFIG_PPC_64K_PAGES=y
index 59abc620f8e8a10de4e7329993092af678f8778e..73eb794d6163811c45729984f0d9fb06bbde31a9 100644 (file)
@@ -154,6 +154,34 @@ static __inline__ int test_and_change_bit(unsigned long nr,
        return test_and_change_bits(BIT_MASK(nr), addr + BIT_WORD(nr)) != 0;
 }
 
+#ifdef CONFIG_PPC64
+static __inline__ unsigned long clear_bit_unlock_return_word(int nr,
+                                               volatile unsigned long *addr)
+{
+       unsigned long old, t;
+       unsigned long *p = (unsigned long *)addr + BIT_WORD(nr);
+       unsigned long mask = BIT_MASK(nr);
+
+       __asm__ __volatile__ (
+       PPC_RELEASE_BARRIER
+"1:"   PPC_LLARX(%0,0,%3,0) "\n"
+       "andc %1,%0,%2\n"
+       PPC405_ERR77(0,%3)
+       PPC_STLCX "%1,0,%3\n"
+       "bne- 1b\n"
+       : "=&r" (old), "=&r" (t)
+       : "r" (mask), "r" (p)
+       : "cc", "memory");
+
+       return old;
+}
+
+/* This is a special function for mm/filemap.c */
+#define clear_bit_unlock_is_negative_byte(nr, addr)                    \
+       (clear_bit_unlock_return_word(nr, addr) & BIT_MASK(PG_waiters))
+
+#endif /* CONFIG_PPC64 */
+
 #include <asm-generic/bitops/non-atomic.h>
 
 static __inline__ void __clear_bit_unlock(int nr, volatile unsigned long *addr)
index 696438f09aeab1399683cd8e504ddb317b092caf..de9681034353c661d3e0a6299c3c6b7c3573b832 100644 (file)
@@ -57,6 +57,8 @@ struct pnv_php_slot {
        uint64_t                        id;
        char                            *name;
        int                             slot_no;
+       unsigned int                    flags;
+#define PNV_PHP_FLAG_BROKEN_PDC                0x1
        struct kref                     kref;
 #define PNV_PHP_STATE_INITIALIZED      0
 #define PNV_PHP_STATE_REGISTERED       1
index 025833b8df9fb1a841888f418dd00ad70e146baf..359c443417616c0137b08e7361bb6ea151263b30 100644 (file)
@@ -505,7 +505,6 @@ END_FTR_SECTION_IFCLR(CPU_FTR_601)
 #define MTMSRD(r)      mtmsrd  r
 #define MTMSR_EERI(reg)        mtmsrd  reg,1
 #else
-#define FIX_SRR1(ra, rb)
 #ifndef CONFIG_40x
 #define        RFI             rfi
 #else
index 21e0b52685b5afdc65c3220ba97d13f82d8ad240..e0fecbcea2a2c0752d6fde459f56803029d258fe 100644 (file)
@@ -225,6 +225,7 @@ struct thread_struct {
 #ifdef CONFIG_PPC64
        unsigned long   start_tb;       /* Start purr when proc switched in */
        unsigned long   accum_tb;       /* Total accumulated purr for process */
+#endif
 #ifdef CONFIG_HAVE_HW_BREAKPOINT
        struct perf_event *ptrace_bps[HBP_NUM];
        /*
@@ -233,7 +234,6 @@ struct thread_struct {
         */
        struct perf_event *last_hit_ubp;
 #endif /* CONFIG_HAVE_HW_BREAKPOINT */
-#endif
        struct arch_hw_breakpoint hw_brk; /* info on the hardware breakpoint */
        unsigned long   trap_nr;        /* last trap # on this thread */
        u8 load_fp;
index 2c8001cc93b649e789b6415fb06c44ad9cea97db..4a90634e83223c25bdf839f54ca9b3f91cb76330 100644 (file)
@@ -153,6 +153,7 @@ struct of_drconf_cell {
 #define OV5_XCMO               0x0440  /* Page Coalescing */
 #define OV5_TYPE1_AFFINITY     0x0580  /* Type 1 NUMA affinity */
 #define OV5_PRRN               0x0540  /* Platform Resource Reassignment */
+#define OV5_HP_EVT             0x0604  /* Hot Plug Event support */
 #define OV5_RESIZE_HPT         0x0601  /* Hash Page Table resizing */
 #define OV5_PFO_HW_RNG         0x1180  /* PFO Random Number Generator */
 #define OV5_PFO_HW_842         0x1140  /* PFO Compression Accelerator */
index cb02d32db14789acbb682ef7045678f4313a1918..fc879fd6bdaed2456c0d80f2061ad7286d0db111 100644 (file)
 #define SPRN_IBAT7U    0x236           /* Instruction BAT 7 Upper Register */
 #define SPRN_ICMP      0x3D5           /* Instruction TLB Compare Register */
 #define SPRN_ICTC      0x3FB   /* Instruction Cache Throttling Control Reg */
+#ifndef SPRN_ICTRL
 #define SPRN_ICTRL     0x3F3   /* 1011 7450 icache and interrupt ctrl */
+#endif
 #define ICTRL_EICE     0x08000000      /* enable icache parity errs */
 #define ICTRL_EDC      0x04000000      /* enable dcache parity errs */
 #define ICTRL_EICP     0x00000100      /* enable icache par. check */
index 1f1636124a04c80c6b85945d66539a135f0dc0fb..ae16fef7a4d63ad65a3a8b259b1340f1d45fc559 100644 (file)
 /* Special MSR manipulation registers */
 #define SPRN_EIE       80      /* External interrupt enable (EE=1, RI=1) */
 #define SPRN_EID       81      /* External interrupt disable (EE=0, RI=1) */
+#define SPRN_NRI       82      /* Non recoverable interrupt (EE=0, RI=0) */
+
+/* Debug registers */
+#define SPRN_CMPA      144
+#define SPRN_COUNTA    150
+#define SPRN_CMPE      152
+#define SPRN_CMPF      153
+#define SPRN_LCTRL1    156
+#define SPRN_LCTRL2    157
+#define SPRN_ICTRL     158
+#define SPRN_BAR       159
 
 /* Commands.  Only the first few are available to the instruction cache.
 */
index 076b89247ab58f2f10a534773c560c086b0bd1a0..ec9dd79398ee975a4d343bca6ad91debdefda857 100644 (file)
@@ -307,6 +307,7 @@ struct pseries_hp_errorlog {
        union {
                __be32  drc_index;
                __be32  drc_count;
+               struct { __be32 count, index; } ic;
                char    drc_name[1];
        } _drc_u;
 };
@@ -323,6 +324,7 @@ struct pseries_hp_errorlog {
 #define PSERIES_HP_ELOG_ID_DRC_NAME    1
 #define PSERIES_HP_ELOG_ID_DRC_INDEX   2
 #define PSERIES_HP_ELOG_ID_DRC_COUNT   3
+#define PSERIES_HP_ELOG_ID_DRC_IC      4
 
 struct pseries_errorlog *get_pseries_errorlog(struct rtas_error_log *log,
                                              uint16_t section_id);
index f25239b3a06f4934a6d2e0e448680a3dfe329e87..4367e7df51a18567af06a86aab714ed0dda79211 100644 (file)
 #include <asm/fixmap.h>
 #endif
 
+#define STACK_PT_REGS_OFFSET(sym, val) \
+       DEFINE(sym, STACK_FRAME_OVERHEAD + offsetof(struct pt_regs, val))
+
 int main(void)
 {
-       DEFINE(THREAD, offsetof(struct task_struct, thread));
-       DEFINE(MM, offsetof(struct task_struct, mm));
-       DEFINE(MMCONTEXTID, offsetof(struct mm_struct, context.id));
+       OFFSET(THREAD, task_struct, thread);
+       OFFSET(MM, task_struct, mm);
+       OFFSET(MMCONTEXTID, mm_struct, context.id);
 #ifdef CONFIG_PPC64
        DEFINE(SIGSEGV, SIGSEGV);
        DEFINE(NMI_MASK, NMI_MASK);
-       DEFINE(TASKTHREADPPR, offsetof(struct task_struct, thread.ppr));
+       OFFSET(TASKTHREADPPR, task_struct, thread.ppr);
 #else
-       DEFINE(THREAD_INFO, offsetof(struct task_struct, stack));
+       OFFSET(THREAD_INFO, task_struct, stack);
        DEFINE(THREAD_INFO_GAP, _ALIGN_UP(sizeof(struct thread_info), 16));
-       DEFINE(KSP_LIMIT, offsetof(struct thread_struct, ksp_limit));
+       OFFSET(KSP_LIMIT, thread_struct, ksp_limit);
 #endif /* CONFIG_PPC64 */
 
 #ifdef CONFIG_LIVEPATCH
-       DEFINE(TI_livepatch_sp, offsetof(struct thread_info, livepatch_sp));
+       OFFSET(TI_livepatch_sp, thread_info, livepatch_sp);
 #endif
 
-       DEFINE(KSP, offsetof(struct thread_struct, ksp));
-       DEFINE(PT_REGS, offsetof(struct thread_struct, regs));
+       OFFSET(KSP, thread_struct, ksp);
+       OFFSET(PT_REGS, thread_struct, regs);
 #ifdef CONFIG_BOOKE
-       DEFINE(THREAD_NORMSAVES, offsetof(struct thread_struct, normsave[0]));
+       OFFSET(THREAD_NORMSAVES, thread_struct, normsave[0]);
 #endif
-       DEFINE(THREAD_FPEXC_MODE, offsetof(struct thread_struct, fpexc_mode));
-       DEFINE(THREAD_FPSTATE, offsetof(struct thread_struct, fp_state));
-       DEFINE(THREAD_FPSAVEAREA, offsetof(struct thread_struct, fp_save_area));
-       DEFINE(FPSTATE_FPSCR, offsetof(struct thread_fp_state, fpscr));
-       DEFINE(THREAD_LOAD_FP, offsetof(struct thread_struct, load_fp));
+       OFFSET(THREAD_FPEXC_MODE, thread_struct, fpexc_mode);
+       OFFSET(THREAD_FPSTATE, thread_struct, fp_state);
+       OFFSET(THREAD_FPSAVEAREA, thread_struct, fp_save_area);
+       OFFSET(FPSTATE_FPSCR, thread_fp_state, fpscr);
+       OFFSET(THREAD_LOAD_FP, thread_struct, load_fp);
 #ifdef CONFIG_ALTIVEC
-       DEFINE(THREAD_VRSTATE, offsetof(struct thread_struct, vr_state));
-       DEFINE(THREAD_VRSAVEAREA, offsetof(struct thread_struct, vr_save_area));
-       DEFINE(THREAD_VRSAVE, offsetof(struct thread_struct, vrsave));
-       DEFINE(THREAD_USED_VR, offsetof(struct thread_struct, used_vr));
-       DEFINE(VRSTATE_VSCR, offsetof(struct thread_vr_state, vscr));
-       DEFINE(THREAD_LOAD_VEC, offsetof(struct thread_struct, load_vec));
+       OFFSET(THREAD_VRSTATE, thread_struct, vr_state);
+       OFFSET(THREAD_VRSAVEAREA, thread_struct, vr_save_area);
+       OFFSET(THREAD_VRSAVE, thread_struct, vrsave);
+       OFFSET(THREAD_USED_VR, thread_struct, used_vr);
+       OFFSET(VRSTATE_VSCR, thread_vr_state, vscr);
+       OFFSET(THREAD_LOAD_VEC, thread_struct, load_vec);
 #endif /* CONFIG_ALTIVEC */
 #ifdef CONFIG_VSX
-       DEFINE(THREAD_USED_VSR, offsetof(struct thread_struct, used_vsr));
+       OFFSET(THREAD_USED_VSR, thread_struct, used_vsr);
 #endif /* CONFIG_VSX */
 #ifdef CONFIG_PPC64
-       DEFINE(KSP_VSID, offsetof(struct thread_struct, ksp_vsid));
+       OFFSET(KSP_VSID, thread_struct, ksp_vsid);
 #else /* CONFIG_PPC64 */
-       DEFINE(PGDIR, offsetof(struct thread_struct, pgdir));
+       OFFSET(PGDIR, thread_struct, pgdir);
 #ifdef CONFIG_SPE
-       DEFINE(THREAD_EVR0, offsetof(struct thread_struct, evr[0]));
-       DEFINE(THREAD_ACC, offsetof(struct thread_struct, acc));
-       DEFINE(THREAD_SPEFSCR, offsetof(struct thread_struct, spefscr));
-       DEFINE(THREAD_USED_SPE, offsetof(struct thread_struct, used_spe));
+       OFFSET(THREAD_EVR0, thread_struct, evr[0]);
+       OFFSET(THREAD_ACC, thread_struct, acc);
+       OFFSET(THREAD_SPEFSCR, thread_struct, spefscr);
+       OFFSET(THREAD_USED_SPE, thread_struct, used_spe);
 #endif /* CONFIG_SPE */
 #endif /* CONFIG_PPC64 */
 #if defined(CONFIG_4xx) || defined(CONFIG_BOOKE)
-       DEFINE(THREAD_DBCR0, offsetof(struct thread_struct, debug.dbcr0));
+       OFFSET(THREAD_DBCR0, thread_struct, debug.dbcr0);
 #endif
 #ifdef CONFIG_KVM_BOOK3S_32_HANDLER
-       DEFINE(THREAD_KVM_SVCPU, offsetof(struct thread_struct, kvm_shadow_vcpu));
+       OFFSET(THREAD_KVM_SVCPU, thread_struct, kvm_shadow_vcpu);
 #endif
 #if defined(CONFIG_KVM) && defined(CONFIG_BOOKE)
-       DEFINE(THREAD_KVM_VCPU, offsetof(struct thread_struct, kvm_vcpu));
+       OFFSET(THREAD_KVM_VCPU, thread_struct, kvm_vcpu);
 #endif
 
 #ifdef CONFIG_PPC_TRANSACTIONAL_MEM
-       DEFINE(PACATMSCRATCH, offsetof(struct paca_struct, tm_scratch));
-       DEFINE(THREAD_TM_TFHAR, offsetof(struct thread_struct, tm_tfhar));
-       DEFINE(THREAD_TM_TEXASR, offsetof(struct thread_struct, tm_texasr));
-       DEFINE(THREAD_TM_TFIAR, offsetof(struct thread_struct, tm_tfiar));
-       DEFINE(THREAD_TM_TAR, offsetof(struct thread_struct, tm_tar));
-       DEFINE(THREAD_TM_PPR, offsetof(struct thread_struct, tm_ppr));
-       DEFINE(THREAD_TM_DSCR, offsetof(struct thread_struct, tm_dscr));
-       DEFINE(PT_CKPT_REGS, offsetof(struct thread_struct, ckpt_regs));
-       DEFINE(THREAD_CKVRSTATE, offsetof(struct thread_struct,
-                                                ckvr_state));
-       DEFINE(THREAD_CKVRSAVE, offsetof(struct thread_struct,
-                                           ckvrsave));
-       DEFINE(THREAD_CKFPSTATE, offsetof(struct thread_struct,
-                                                ckfp_state));
+       OFFSET(PACATMSCRATCH, paca_struct, tm_scratch);
+       OFFSET(THREAD_TM_TFHAR, thread_struct, tm_tfhar);
+       OFFSET(THREAD_TM_TEXASR, thread_struct, tm_texasr);
+       OFFSET(THREAD_TM_TFIAR, thread_struct, tm_tfiar);
+       OFFSET(THREAD_TM_TAR, thread_struct, tm_tar);
+       OFFSET(THREAD_TM_PPR, thread_struct, tm_ppr);
+       OFFSET(THREAD_TM_DSCR, thread_struct, tm_dscr);
+       OFFSET(PT_CKPT_REGS, thread_struct, ckpt_regs);
+       OFFSET(THREAD_CKVRSTATE, thread_struct, ckvr_state);
+       OFFSET(THREAD_CKVRSAVE, thread_struct, ckvrsave);
+       OFFSET(THREAD_CKFPSTATE, thread_struct, ckfp_state);
        /* Local pt_regs on stack for Transactional Memory funcs. */
        DEFINE(TM_FRAME_SIZE, STACK_FRAME_OVERHEAD +
               sizeof(struct pt_regs) + 16);
 #endif /* CONFIG_PPC_TRANSACTIONAL_MEM */
 
-       DEFINE(TI_FLAGS, offsetof(struct thread_info, flags));
-       DEFINE(TI_LOCAL_FLAGS, offsetof(struct thread_info, local_flags));
-       DEFINE(TI_PREEMPT, offsetof(struct thread_info, preempt_count));
-       DEFINE(TI_TASK, offsetof(struct thread_info, task));
-       DEFINE(TI_CPU, offsetof(struct thread_info, cpu));
+       OFFSET(TI_FLAGS, thread_info, flags);
+       OFFSET(TI_LOCAL_FLAGS, thread_info, local_flags);
+       OFFSET(TI_PREEMPT, thread_info, preempt_count);
+       OFFSET(TI_TASK, thread_info, task);
+       OFFSET(TI_CPU, thread_info, cpu);
 
 #ifdef CONFIG_PPC64
-       DEFINE(DCACHEL1BLOCKSIZE, offsetof(struct ppc64_caches, l1d.block_size));
-       DEFINE(DCACHEL1LOGBLOCKSIZE, offsetof(struct ppc64_caches, l1d.log_block_size));
-       DEFINE(DCACHEL1BLOCKSPERPAGE, offsetof(struct ppc64_caches, l1d.blocks_per_page));
-       DEFINE(ICACHEL1BLOCKSIZE, offsetof(struct ppc64_caches, l1i.block_size));
-       DEFINE(ICACHEL1LOGBLOCKSIZE, offsetof(struct ppc64_caches, l1i.log_block_size));
-       DEFINE(ICACHEL1BLOCKSPERPAGE, offsetof(struct ppc64_caches, l1i.blocks_per_page));
+       OFFSET(DCACHEL1BLOCKSIZE, ppc64_caches, l1d.block_size);
+       OFFSET(DCACHEL1LOGBLOCKSIZE, ppc64_caches, l1d.log_block_size);
+       OFFSET(DCACHEL1BLOCKSPERPAGE, ppc64_caches, l1d.blocks_per_page);
+       OFFSET(ICACHEL1BLOCKSIZE, ppc64_caches, l1i.block_size);
+       OFFSET(ICACHEL1LOGBLOCKSIZE, ppc64_caches, l1i.log_block_size);
+       OFFSET(ICACHEL1BLOCKSPERPAGE, ppc64_caches, l1i.blocks_per_page);
        /* paca */
        DEFINE(PACA_SIZE, sizeof(struct paca_struct));
-       DEFINE(PACAPACAINDEX, offsetof(struct paca_struct, paca_index));
-       DEFINE(PACAPROCSTART, offsetof(struct paca_struct, cpu_start));
-       DEFINE(PACAKSAVE, offsetof(struct paca_struct, kstack));
-       DEFINE(PACACURRENT, offsetof(struct paca_struct, __current));
-       DEFINE(PACASAVEDMSR, offsetof(struct paca_struct, saved_msr));
-       DEFINE(PACASTABRR, offsetof(struct paca_struct, stab_rr));
-       DEFINE(PACAR1, offsetof(struct paca_struct, saved_r1));
-       DEFINE(PACATOC, offsetof(struct paca_struct, kernel_toc));
-       DEFINE(PACAKBASE, offsetof(struct paca_struct, kernelbase));
-       DEFINE(PACAKMSR, offsetof(struct paca_struct, kernel_msr));
-       DEFINE(PACASOFTIRQEN, offsetof(struct paca_struct, soft_enabled));
-       DEFINE(PACAIRQHAPPENED, offsetof(struct paca_struct, irq_happened));
+       OFFSET(PACAPACAINDEX, paca_struct, paca_index);
+       OFFSET(PACAPROCSTART, paca_struct, cpu_start);
+       OFFSET(PACAKSAVE, paca_struct, kstack);
+       OFFSET(PACACURRENT, paca_struct, __current);
+       OFFSET(PACASAVEDMSR, paca_struct, saved_msr);
+       OFFSET(PACASTABRR, paca_struct, stab_rr);
+       OFFSET(PACAR1, paca_struct, saved_r1);
+       OFFSET(PACATOC, paca_struct, kernel_toc);
+       OFFSET(PACAKBASE, paca_struct, kernelbase);
+       OFFSET(PACAKMSR, paca_struct, kernel_msr);
+       OFFSET(PACASOFTIRQEN, paca_struct, soft_enabled);
+       OFFSET(PACAIRQHAPPENED, paca_struct, irq_happened);
 #ifdef CONFIG_PPC_BOOK3S
-       DEFINE(PACACONTEXTID, offsetof(struct paca_struct, mm_ctx_id));
+       OFFSET(PACACONTEXTID, paca_struct, mm_ctx_id);
 #ifdef CONFIG_PPC_MM_SLICES
-       DEFINE(PACALOWSLICESPSIZE, offsetof(struct paca_struct,
-                                           mm_ctx_low_slices_psize));
-       DEFINE(PACAHIGHSLICEPSIZE, offsetof(struct paca_struct,
-                                           mm_ctx_high_slices_psize));
+       OFFSET(PACALOWSLICESPSIZE, paca_struct, mm_ctx_low_slices_psize);
+       OFFSET(PACAHIGHSLICEPSIZE, paca_struct, mm_ctx_high_slices_psize);
        DEFINE(MMUPSIZEDEFSIZE, sizeof(struct mmu_psize_def));
 #endif /* CONFIG_PPC_MM_SLICES */
 #endif
 
 #ifdef CONFIG_PPC_BOOK3E
-       DEFINE(PACAPGD, offsetof(struct paca_struct, pgd));
-       DEFINE(PACA_KERNELPGD, offsetof(struct paca_struct, kernel_pgd));
-       DEFINE(PACA_EXGEN, offsetof(struct paca_struct, exgen));
-       DEFINE(PACA_EXTLB, offsetof(struct paca_struct, extlb));
-       DEFINE(PACA_EXMC, offsetof(struct paca_struct, exmc));
-       DEFINE(PACA_EXCRIT, offsetof(struct paca_struct, excrit));
-       DEFINE(PACA_EXDBG, offsetof(struct paca_struct, exdbg));
-       DEFINE(PACA_MC_STACK, offsetof(struct paca_struct, mc_kstack));
-       DEFINE(PACA_CRIT_STACK, offsetof(struct paca_struct, crit_kstack));
-       DEFINE(PACA_DBG_STACK, offsetof(struct paca_struct, dbg_kstack));
-       DEFINE(PACA_TCD_PTR, offsetof(struct paca_struct, tcd_ptr));
-
-       DEFINE(TCD_ESEL_NEXT,
-               offsetof(struct tlb_core_data, esel_next));
-       DEFINE(TCD_ESEL_MAX,
-               offsetof(struct tlb_core_data, esel_max));
-       DEFINE(TCD_ESEL_FIRST,
-               offsetof(struct tlb_core_data, esel_first));
+       OFFSET(PACAPGD, paca_struct, pgd);
+       OFFSET(PACA_KERNELPGD, paca_struct, kernel_pgd);
+       OFFSET(PACA_EXGEN, paca_struct, exgen);
+       OFFSET(PACA_EXTLB, paca_struct, extlb);
+       OFFSET(PACA_EXMC, paca_struct, exmc);
+       OFFSET(PACA_EXCRIT, paca_struct, excrit);
+       OFFSET(PACA_EXDBG, paca_struct, exdbg);
+       OFFSET(PACA_MC_STACK, paca_struct, mc_kstack);
+       OFFSET(PACA_CRIT_STACK, paca_struct, crit_kstack);
+       OFFSET(PACA_DBG_STACK, paca_struct, dbg_kstack);
+       OFFSET(PACA_TCD_PTR, paca_struct, tcd_ptr);
+
+       OFFSET(TCD_ESEL_NEXT, tlb_core_data, esel_next);
+       OFFSET(TCD_ESEL_MAX, tlb_core_data, esel_max);
+       OFFSET(TCD_ESEL_FIRST, tlb_core_data, esel_first);
 #endif /* CONFIG_PPC_BOOK3E */
 
 #ifdef CONFIG_PPC_STD_MMU_64
-       DEFINE(PACASLBCACHE, offsetof(struct paca_struct, slb_cache));
-       DEFINE(PACASLBCACHEPTR, offsetof(struct paca_struct, slb_cache_ptr));
-       DEFINE(PACAVMALLOCSLLP, offsetof(struct paca_struct, vmalloc_sllp));
+       OFFSET(PACASLBCACHE, paca_struct, slb_cache);
+       OFFSET(PACASLBCACHEPTR, paca_struct, slb_cache_ptr);
+       OFFSET(PACAVMALLOCSLLP, paca_struct, vmalloc_sllp);
 #ifdef CONFIG_PPC_MM_SLICES
-       DEFINE(MMUPSIZESLLP, offsetof(struct mmu_psize_def, sllp));
+       OFFSET(MMUPSIZESLLP, mmu_psize_def, sllp);
 #else
-       DEFINE(PACACONTEXTSLLP, offsetof(struct paca_struct, mm_ctx_sllp));
+       OFFSET(PACACONTEXTSLLP, paca_struct, mm_ctx_sllp);
 #endif /* CONFIG_PPC_MM_SLICES */
-       DEFINE(PACA_EXGEN, offsetof(struct paca_struct, exgen));
-       DEFINE(PACA_EXMC, offsetof(struct paca_struct, exmc));
-       DEFINE(PACA_EXSLB, offsetof(struct paca_struct, exslb));
-       DEFINE(PACALPPACAPTR, offsetof(struct paca_struct, lppaca_ptr));
-       DEFINE(PACA_SLBSHADOWPTR, offsetof(struct paca_struct, slb_shadow_ptr));
-       DEFINE(SLBSHADOW_STACKVSID,
-              offsetof(struct slb_shadow, save_area[SLB_NUM_BOLTED - 1].vsid));
-       DEFINE(SLBSHADOW_STACKESID,
-              offsetof(struct slb_shadow, save_area[SLB_NUM_BOLTED - 1].esid));
-       DEFINE(SLBSHADOW_SAVEAREA, offsetof(struct slb_shadow, save_area));
-       DEFINE(LPPACA_PMCINUSE, offsetof(struct lppaca, pmcregs_in_use));
-       DEFINE(LPPACA_DTLIDX, offsetof(struct lppaca, dtl_idx));
-       DEFINE(LPPACA_YIELDCOUNT, offsetof(struct lppaca, yield_count));
-       DEFINE(PACA_DTL_RIDX, offsetof(struct paca_struct, dtl_ridx));
+       OFFSET(PACA_EXGEN, paca_struct, exgen);
+       OFFSET(PACA_EXMC, paca_struct, exmc);
+       OFFSET(PACA_EXSLB, paca_struct, exslb);
+       OFFSET(PACALPPACAPTR, paca_struct, lppaca_ptr);
+       OFFSET(PACA_SLBSHADOWPTR, paca_struct, slb_shadow_ptr);
+       OFFSET(SLBSHADOW_STACKVSID, slb_shadow, save_area[SLB_NUM_BOLTED - 1].vsid);
+       OFFSET(SLBSHADOW_STACKESID, slb_shadow, save_area[SLB_NUM_BOLTED - 1].esid);
+       OFFSET(SLBSHADOW_SAVEAREA, slb_shadow, save_area);
+       OFFSET(LPPACA_PMCINUSE, lppaca, pmcregs_in_use);
+       OFFSET(LPPACA_DTLIDX, lppaca, dtl_idx);
+       OFFSET(LPPACA_YIELDCOUNT, lppaca, yield_count);
+       OFFSET(PACA_DTL_RIDX, paca_struct, dtl_ridx);
 #endif /* CONFIG_PPC_STD_MMU_64 */
-       DEFINE(PACAEMERGSP, offsetof(struct paca_struct, emergency_sp));
+       OFFSET(PACAEMERGSP, paca_struct, emergency_sp);
 #ifdef CONFIG_PPC_BOOK3S_64
-       DEFINE(PACAMCEMERGSP, offsetof(struct paca_struct, mc_emergency_sp));
-       DEFINE(PACA_IN_MCE, offsetof(struct paca_struct, in_mce));
-#endif
-       DEFINE(PACAHWCPUID, offsetof(struct paca_struct, hw_cpu_id));
-       DEFINE(PACAKEXECSTATE, offsetof(struct paca_struct, kexec_state));
-       DEFINE(PACA_DSCR_DEFAULT, offsetof(struct paca_struct, dscr_default));
-       DEFINE(ACCOUNT_STARTTIME,
-              offsetof(struct paca_struct, accounting.starttime));
-       DEFINE(ACCOUNT_STARTTIME_USER,
-              offsetof(struct paca_struct, accounting.starttime_user));
-       DEFINE(ACCOUNT_USER_TIME,
-              offsetof(struct paca_struct, accounting.utime));
-       DEFINE(ACCOUNT_SYSTEM_TIME,
-              offsetof(struct paca_struct, accounting.stime));
-       DEFINE(PACA_TRAP_SAVE, offsetof(struct paca_struct, trap_save));
-       DEFINE(PACA_NAPSTATELOST, offsetof(struct paca_struct, nap_state_lost));
-       DEFINE(PACA_SPRG_VDSO, offsetof(struct paca_struct, sprg_vdso));
+       OFFSET(PACAMCEMERGSP, paca_struct, mc_emergency_sp);
+       OFFSET(PACA_IN_MCE, paca_struct, in_mce);
+#endif
+       OFFSET(PACAHWCPUID, paca_struct, hw_cpu_id);
+       OFFSET(PACAKEXECSTATE, paca_struct, kexec_state);
+       OFFSET(PACA_DSCR_DEFAULT, paca_struct, dscr_default);
+       OFFSET(ACCOUNT_STARTTIME, paca_struct, accounting.starttime);
+       OFFSET(ACCOUNT_STARTTIME_USER, paca_struct, accounting.starttime_user);
+       OFFSET(ACCOUNT_USER_TIME, paca_struct, accounting.utime);
+       OFFSET(ACCOUNT_SYSTEM_TIME, paca_struct, accounting.stime);
+       OFFSET(PACA_TRAP_SAVE, paca_struct, trap_save);
+       OFFSET(PACA_NAPSTATELOST, paca_struct, nap_state_lost);
+       OFFSET(PACA_SPRG_VDSO, paca_struct, sprg_vdso);
 #else /* CONFIG_PPC64 */
 #ifdef CONFIG_VIRT_CPU_ACCOUNTING_NATIVE
-       DEFINE(ACCOUNT_STARTTIME,
-              offsetof(struct thread_info, accounting.starttime));
-       DEFINE(ACCOUNT_STARTTIME_USER,
-              offsetof(struct thread_info, accounting.starttime_user));
-       DEFINE(ACCOUNT_USER_TIME,
-              offsetof(struct thread_info, accounting.utime));
-       DEFINE(ACCOUNT_SYSTEM_TIME,
-              offsetof(struct thread_info, accounting.stime));
+       OFFSET(ACCOUNT_STARTTIME, thread_info, accounting.starttime);
+       OFFSET(ACCOUNT_STARTTIME_USER, thread_info, accounting.starttime_user);
+       OFFSET(ACCOUNT_USER_TIME, thread_info, accounting.utime);
+       OFFSET(ACCOUNT_SYSTEM_TIME, thread_info, accounting.stime);
 #endif
 #endif /* CONFIG_PPC64 */
 
        /* RTAS */
-       DEFINE(RTASBASE, offsetof(struct rtas_t, base));
-       DEFINE(RTASENTRY, offsetof(struct rtas_t, entry));
+       OFFSET(RTASBASE, rtas_t, base);
+       OFFSET(RTASENTRY, rtas_t, entry);
 
        /* Interrupt register frame */
        DEFINE(INT_FRAME_SIZE, STACK_INT_FRAME_SIZE);
@@ -280,38 +265,38 @@ int main(void)
        DEFINE(PROM_FRAME_SIZE, STACK_FRAME_OVERHEAD + sizeof(struct pt_regs) + 16);
        DEFINE(RTAS_FRAME_SIZE, STACK_FRAME_OVERHEAD + sizeof(struct pt_regs) + 16);
 #endif /* CONFIG_PPC64 */
-       DEFINE(GPR0, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[0]));
-       DEFINE(GPR1, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[1]));
-       DEFINE(GPR2, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[2]));
-       DEFINE(GPR3, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[3]));
-       DEFINE(GPR4, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[4]));
-       DEFINE(GPR5, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[5]));
-       DEFINE(GPR6, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[6]));
-       DEFINE(GPR7, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[7]));
-       DEFINE(GPR8, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[8]));
-       DEFINE(GPR9, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[9]));
-       DEFINE(GPR10, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[10]));
-       DEFINE(GPR11, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[11]));
-       DEFINE(GPR12, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[12]));
-       DEFINE(GPR13, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[13]));
+       STACK_PT_REGS_OFFSET(GPR0, gpr[0]);
+       STACK_PT_REGS_OFFSET(GPR1, gpr[1]);
+       STACK_PT_REGS_OFFSET(GPR2, gpr[2]);
+       STACK_PT_REGS_OFFSET(GPR3, gpr[3]);
+       STACK_PT_REGS_OFFSET(GPR4, gpr[4]);
+       STACK_PT_REGS_OFFSET(GPR5, gpr[5]);
+       STACK_PT_REGS_OFFSET(GPR6, gpr[6]);
+       STACK_PT_REGS_OFFSET(GPR7, gpr[7]);
+       STACK_PT_REGS_OFFSET(GPR8, gpr[8]);
+       STACK_PT_REGS_OFFSET(GPR9, gpr[9]);
+       STACK_PT_REGS_OFFSET(GPR10, gpr[10]);
+       STACK_PT_REGS_OFFSET(GPR11, gpr[11]);
+       STACK_PT_REGS_OFFSET(GPR12, gpr[12]);
+       STACK_PT_REGS_OFFSET(GPR13, gpr[13]);
 #ifndef CONFIG_PPC64
-       DEFINE(GPR14, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, gpr[14]));
+       STACK_PT_REGS_OFFSET(GPR14, gpr[14]);
 #endif /* CONFIG_PPC64 */
        /*
         * Note: these symbols include _ because they overlap with special
         * register names
         */
-       DEFINE(_NIP, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, nip));
-       DEFINE(_MSR, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, msr));
-       DEFINE(_CTR, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, ctr));
-       DEFINE(_LINK, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, link));
-       DEFINE(_CCR, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, ccr));
-       DEFINE(_XER, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, xer));
-       DEFINE(_DAR, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, dar));
-       DEFINE(_DSISR, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, dsisr));
-       DEFINE(ORIG_GPR3, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, orig_gpr3));
-       DEFINE(RESULT, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, result));
-       DEFINE(_TRAP, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, trap));
+       STACK_PT_REGS_OFFSET(_NIP, nip);
+       STACK_PT_REGS_OFFSET(_MSR, msr);
+       STACK_PT_REGS_OFFSET(_CTR, ctr);
+       STACK_PT_REGS_OFFSET(_LINK, link);
+       STACK_PT_REGS_OFFSET(_CCR, ccr);
+       STACK_PT_REGS_OFFSET(_XER, xer);
+       STACK_PT_REGS_OFFSET(_DAR, dar);
+       STACK_PT_REGS_OFFSET(_DSISR, dsisr);
+       STACK_PT_REGS_OFFSET(ORIG_GPR3, orig_gpr3);
+       STACK_PT_REGS_OFFSET(RESULT, result);
+       STACK_PT_REGS_OFFSET(_TRAP, trap);
 #ifndef CONFIG_PPC64
        /*
         * The PowerPC 400-class & Book-E processors have neither the DAR
@@ -319,10 +304,10 @@ int main(void)
         * DEAR and ESR SPRs for such processors.  For critical interrupts
         * we use them to hold SRR0 and SRR1.
         */
-       DEFINE(_DEAR, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, dar));
-       DEFINE(_ESR, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, dsisr));
+       STACK_PT_REGS_OFFSET(_DEAR, dar);
+       STACK_PT_REGS_OFFSET(_ESR, dsisr);
 #else /* CONFIG_PPC64 */
-       DEFINE(SOFTE, STACK_FRAME_OVERHEAD+offsetof(struct pt_regs, softe));
+       STACK_PT_REGS_OFFSET(SOFTE, softe);
 
        /* These _only_ to be used with {PROM,RTAS}_FRAME_SIZE!!! */
        DEFINE(_SRR0, STACK_FRAME_OVERHEAD+sizeof(struct pt_regs));
@@ -351,17 +336,17 @@ int main(void)
 #endif
 
 #ifndef CONFIG_PPC64
-       DEFINE(MM_PGD, offsetof(struct mm_struct, pgd));
+       OFFSET(MM_PGD, mm_struct, pgd);
 #endif /* ! CONFIG_PPC64 */
 
        /* About the CPU features table */
-       DEFINE(CPU_SPEC_FEATURES, offsetof(struct cpu_spec, cpu_features));
-       DEFINE(CPU_SPEC_SETUP, offsetof(struct cpu_spec, cpu_setup));
-       DEFINE(CPU_SPEC_RESTORE, offsetof(struct cpu_spec, cpu_restore));
+       OFFSET(CPU_SPEC_FEATURES, cpu_spec, cpu_features);
+       OFFSET(CPU_SPEC_SETUP, cpu_spec, cpu_setup);
+       OFFSET(CPU_SPEC_RESTORE, cpu_spec, cpu_restore);
 
-       DEFINE(pbe_address, offsetof(struct pbe, address));
-       DEFINE(pbe_orig_address, offsetof(struct pbe, orig_address));
-       DEFINE(pbe_next, offsetof(struct pbe, next));
+       OFFSET(pbe_address, pbe, address);
+       OFFSET(pbe_orig_address, pbe, orig_address);
+       OFFSET(pbe_next, pbe, next);
 
 #ifndef CONFIG_PPC64
        DEFINE(TASK_SIZE, TASK_SIZE);
@@ -369,40 +354,40 @@ int main(void)
 #endif /* ! CONFIG_PPC64 */
 
        /* datapage offsets for use by vdso */
-       DEFINE(CFG_TB_ORIG_STAMP, offsetof(struct vdso_data, tb_orig_stamp));
-       DEFINE(CFG_TB_TICKS_PER_SEC, offsetof(struct vdso_data, tb_ticks_per_sec));
-       DEFINE(CFG_TB_TO_XS, offsetof(struct vdso_data, tb_to_xs));
-       DEFINE(CFG_TB_UPDATE_COUNT, offsetof(struct vdso_data, tb_update_count));
-       DEFINE(CFG_TZ_MINUTEWEST, offsetof(struct vdso_data, tz_minuteswest));
-       DEFINE(CFG_TZ_DSTTIME, offsetof(struct vdso_data, tz_dsttime));
-       DEFINE(CFG_SYSCALL_MAP32, offsetof(struct vdso_data, syscall_map_32));
-       DEFINE(WTOM_CLOCK_SEC, offsetof(struct vdso_data, wtom_clock_sec));
-       DEFINE(WTOM_CLOCK_NSEC, offsetof(struct vdso_data, wtom_clock_nsec));
-       DEFINE(STAMP_XTIME, offsetof(struct vdso_data, stamp_xtime));
-       DEFINE(STAMP_SEC_FRAC, offsetof(struct vdso_data, stamp_sec_fraction));
-       DEFINE(CFG_ICACHE_BLOCKSZ, offsetof(struct vdso_data, icache_block_size));
-       DEFINE(CFG_DCACHE_BLOCKSZ, offsetof(struct vdso_data, dcache_block_size));
-       DEFINE(CFG_ICACHE_LOGBLOCKSZ, offsetof(struct vdso_data, icache_log_block_size));
-       DEFINE(CFG_DCACHE_LOGBLOCKSZ, offsetof(struct vdso_data, dcache_log_block_size));
+       OFFSET(CFG_TB_ORIG_STAMP, vdso_data, tb_orig_stamp);
+       OFFSET(CFG_TB_TICKS_PER_SEC, vdso_data, tb_ticks_per_sec);
+       OFFSET(CFG_TB_TO_XS, vdso_data, tb_to_xs);
+       OFFSET(CFG_TB_UPDATE_COUNT, vdso_data, tb_update_count);
+       OFFSET(CFG_TZ_MINUTEWEST, vdso_data, tz_minuteswest);
+       OFFSET(CFG_TZ_DSTTIME, vdso_data, tz_dsttime);
+       OFFSET(CFG_SYSCALL_MAP32, vdso_data, syscall_map_32);
+       OFFSET(WTOM_CLOCK_SEC, vdso_data, wtom_clock_sec);
+       OFFSET(WTOM_CLOCK_NSEC, vdso_data, wtom_clock_nsec);
+       OFFSET(STAMP_XTIME, vdso_data, stamp_xtime);
+       OFFSET(STAMP_SEC_FRAC, vdso_data, stamp_sec_fraction);
+       OFFSET(CFG_ICACHE_BLOCKSZ, vdso_data, icache_block_size);
+       OFFSET(CFG_DCACHE_BLOCKSZ, vdso_data, dcache_block_size);
+       OFFSET(CFG_ICACHE_LOGBLOCKSZ, vdso_data, icache_log_block_size);
+       OFFSET(CFG_DCACHE_LOGBLOCKSZ, vdso_data, dcache_log_block_size);
 #ifdef CONFIG_PPC64
-       DEFINE(CFG_SYSCALL_MAP64, offsetof(struct vdso_data, syscall_map_64));
-       DEFINE(TVAL64_TV_SEC, offsetof(struct timeval, tv_sec));
-       DEFINE(TVAL64_TV_USEC, offsetof(struct timeval, tv_usec));
-       DEFINE(TVAL32_TV_SEC, offsetof(struct compat_timeval, tv_sec));
-       DEFINE(TVAL32_TV_USEC, offsetof(struct compat_timeval, tv_usec));
-       DEFINE(TSPC64_TV_SEC, offsetof(struct timespec, tv_sec));
-       DEFINE(TSPC64_TV_NSEC, offsetof(struct timespec, tv_nsec));
-       DEFINE(TSPC32_TV_SEC, offsetof(struct compat_timespec, tv_sec));
-       DEFINE(TSPC32_TV_NSEC, offsetof(struct compat_timespec, tv_nsec));
+       OFFSET(CFG_SYSCALL_MAP64, vdso_data, syscall_map_64);
+       OFFSET(TVAL64_TV_SEC, timeval, tv_sec);
+       OFFSET(TVAL64_TV_USEC, timeval, tv_usec);
+       OFFSET(TVAL32_TV_SEC, compat_timeval, tv_sec);
+       OFFSET(TVAL32_TV_USEC, compat_timeval, tv_usec);
+       OFFSET(TSPC64_TV_SEC, timespec, tv_sec);
+       OFFSET(TSPC64_TV_NSEC, timespec, tv_nsec);
+       OFFSET(TSPC32_TV_SEC, compat_timespec, tv_sec);
+       OFFSET(TSPC32_TV_NSEC, compat_timespec, tv_nsec);
 #else
-       DEFINE(TVAL32_TV_SEC, offsetof(struct timeval, tv_sec));
-       DEFINE(TVAL32_TV_USEC, offsetof(struct timeval, tv_usec));
-       DEFINE(TSPC32_TV_SEC, offsetof(struct timespec, tv_sec));
-       DEFINE(TSPC32_TV_NSEC, offsetof(struct timespec, tv_nsec));
+       OFFSET(TVAL32_TV_SEC, timeval, tv_sec);
+       OFFSET(TVAL32_TV_USEC, timeval, tv_usec);
+       OFFSET(TSPC32_TV_SEC, timespec, tv_sec);
+       OFFSET(TSPC32_TV_NSEC, timespec, tv_nsec);
 #endif
        /* timeval/timezone offsets for use by vdso */
-       DEFINE(TZONE_TZ_MINWEST, offsetof(struct timezone, tz_minuteswest));
-       DEFINE(TZONE_TZ_DSTTIME, offsetof(struct timezone, tz_dsttime));
+       OFFSET(TZONE_TZ_MINWEST, timezone, tz_minuteswest);
+       OFFSET(TZONE_TZ_DSTTIME, timezone, tz_dsttime);
 
        /* Other bits used by the vdso */
        DEFINE(CLOCK_REALTIME, CLOCK_REALTIME);
@@ -422,170 +407,170 @@ int main(void)
        DEFINE(PTE_SIZE, sizeof(pte_t));
 
 #ifdef CONFIG_KVM
-       DEFINE(VCPU_HOST_STACK, offsetof(struct kvm_vcpu, arch.host_stack));
-       DEFINE(VCPU_HOST_PID, offsetof(struct kvm_vcpu, arch.host_pid));
-       DEFINE(VCPU_GUEST_PID, offsetof(struct kvm_vcpu, arch.pid));
-       DEFINE(VCPU_GPRS, offsetof(struct kvm_vcpu, arch.gpr));
-       DEFINE(VCPU_VRSAVE, offsetof(struct kvm_vcpu, arch.vrsave));
-       DEFINE(VCPU_FPRS, offsetof(struct kvm_vcpu, arch.fp.fpr));
+       OFFSET(VCPU_HOST_STACK, kvm_vcpu, arch.host_stack);
+       OFFSET(VCPU_HOST_PID, kvm_vcpu, arch.host_pid);
+       OFFSET(VCPU_GUEST_PID, kvm_vcpu, arch.pid);
+       OFFSET(VCPU_GPRS, kvm_vcpu, arch.gpr);
+       OFFSET(VCPU_VRSAVE, kvm_vcpu, arch.vrsave);
+       OFFSET(VCPU_FPRS, kvm_vcpu, arch.fp.fpr);
 #ifdef CONFIG_ALTIVEC
-       DEFINE(VCPU_VRS, offsetof(struct kvm_vcpu, arch.vr.vr));
+       OFFSET(VCPU_VRS, kvm_vcpu, arch.vr.vr);
 #endif
-       DEFINE(VCPU_XER, offsetof(struct kvm_vcpu, arch.xer));
-       DEFINE(VCPU_CTR, offsetof(struct kvm_vcpu, arch.ctr));
-       DEFINE(VCPU_LR, offsetof(struct kvm_vcpu, arch.lr));
+       OFFSET(VCPU_XER, kvm_vcpu, arch.xer);
+       OFFSET(VCPU_CTR, kvm_vcpu, arch.ctr);
+       OFFSET(VCPU_LR, kvm_vcpu, arch.lr);
 #ifdef CONFIG_PPC_BOOK3S
-       DEFINE(VCPU_TAR, offsetof(struct kvm_vcpu, arch.tar));
+       OFFSET(VCPU_TAR, kvm_vcpu, arch.tar);
 #endif
-       DEFINE(VCPU_CR, offsetof(struct kvm_vcpu, arch.cr));
-       DEFINE(VCPU_PC, offsetof(struct kvm_vcpu, arch.pc));
+       OFFSET(VCPU_CR, kvm_vcpu, arch.cr);
+       OFFSET(VCPU_PC, kvm_vcpu, arch.pc);
 #ifdef CONFIG_KVM_BOOK3S_HV_POSSIBLE
-       DEFINE(VCPU_MSR, offsetof(struct kvm_vcpu, arch.shregs.msr));
-       DEFINE(VCPU_SRR0, offsetof(struct kvm_vcpu, arch.shregs.srr0));
-       DEFINE(VCPU_SRR1, offsetof(struct kvm_vcpu, arch.shregs.srr1));
-       DEFINE(VCPU_SPRG0, offsetof(struct kvm_vcpu, arch.shregs.sprg0));
-       DEFINE(VCPU_SPRG1, offsetof(struct kvm_vcpu, arch.shregs.sprg1));
-       DEFINE(VCPU_SPRG2, offsetof(struct kvm_vcpu, arch.shregs.sprg2));
-       DEFINE(VCPU_SPRG3, offsetof(struct kvm_vcpu, arch.shregs.sprg3));
+       OFFSET(VCPU_MSR, kvm_vcpu, arch.shregs.msr);
+       OFFSET(VCPU_SRR0, kvm_vcpu, arch.shregs.srr0);
+       OFFSET(VCPU_SRR1, kvm_vcpu, arch.shregs.srr1);
+       OFFSET(VCPU_SPRG0, kvm_vcpu, arch.shregs.sprg0);
+       OFFSET(VCPU_SPRG1, kvm_vcpu, arch.shregs.sprg1);
+       OFFSET(VCPU_SPRG2, kvm_vcpu, arch.shregs.sprg2);
+       OFFSET(VCPU_SPRG3, kvm_vcpu, arch.shregs.sprg3);
 #endif
 #ifdef CONFIG_KVM_BOOK3S_HV_EXIT_TIMING
-       DEFINE(VCPU_TB_RMENTRY, offsetof(struct kvm_vcpu, arch.rm_entry));
-       DEFINE(VCPU_TB_RMINTR, offsetof(struct kvm_vcpu, arch.rm_intr));
-       DEFINE(VCPU_TB_RMEXIT, offsetof(struct kvm_vcpu, arch.rm_exit));
-       DEFINE(VCPU_TB_GUEST, offsetof(struct kvm_vcpu, arch.guest_time));
-       DEFINE(VCPU_TB_CEDE, offsetof(struct kvm_vcpu, arch.cede_time));
-       DEFINE(VCPU_CUR_ACTIVITY, offsetof(struct kvm_vcpu, arch.cur_activity));
-       DEFINE(VCPU_ACTIVITY_START, offsetof(struct kvm_vcpu, arch.cur_tb_start));
-       DEFINE(TAS_SEQCOUNT, offsetof(struct kvmhv_tb_accumulator, seqcount));
-       DEFINE(TAS_TOTAL, offsetof(struct kvmhv_tb_accumulator, tb_total));
-       DEFINE(TAS_MIN, offsetof(struct kvmhv_tb_accumulator, tb_min));
-       DEFINE(TAS_MAX, offsetof(struct kvmhv_tb_accumulator, tb_max));
-#endif
-       DEFINE(VCPU_SHARED_SPRG3, offsetof(struct kvm_vcpu_arch_shared, sprg3));
-       DEFINE(VCPU_SHARED_SPRG4, offsetof(struct kvm_vcpu_arch_shared, sprg4));
-       DEFINE(VCPU_SHARED_SPRG5, offsetof(struct kvm_vcpu_arch_shared, sprg5));
-       DEFINE(VCPU_SHARED_SPRG6, offsetof(struct kvm_vcpu_arch_shared, sprg6));
-       DEFINE(VCPU_SHARED_SPRG7, offsetof(struct kvm_vcpu_arch_shared, sprg7));
-       DEFINE(VCPU_SHADOW_PID, offsetof(struct kvm_vcpu, arch.shadow_pid));
-       DEFINE(VCPU_SHADOW_PID1, offsetof(struct kvm_vcpu, arch.shadow_pid1));
-       DEFINE(VCPU_SHARED, offsetof(struct kvm_vcpu, arch.shared));
-       DEFINE(VCPU_SHARED_MSR, offsetof(struct kvm_vcpu_arch_shared, msr));
-       DEFINE(VCPU_SHADOW_MSR, offsetof(struct kvm_vcpu, arch.shadow_msr));
+       OFFSET(VCPU_TB_RMENTRY, kvm_vcpu, arch.rm_entry);
+       OFFSET(VCPU_TB_RMINTR, kvm_vcpu, arch.rm_intr);
+       OFFSET(VCPU_TB_RMEXIT, kvm_vcpu, arch.rm_exit);
+       OFFSET(VCPU_TB_GUEST, kvm_vcpu, arch.guest_time);
+       OFFSET(VCPU_TB_CEDE, kvm_vcpu, arch.cede_time);
+       OFFSET(VCPU_CUR_ACTIVITY, kvm_vcpu, arch.cur_activity);
+       OFFSET(VCPU_ACTIVITY_START, kvm_vcpu, arch.cur_tb_start);
+       OFFSET(TAS_SEQCOUNT, kvmhv_tb_accumulator, seqcount);
+       OFFSET(TAS_TOTAL, kvmhv_tb_accumulator, tb_total);
+       OFFSET(TAS_MIN, kvmhv_tb_accumulator, tb_min);
+       OFFSET(TAS_MAX, kvmhv_tb_accumulator, tb_max);
+#endif
+       OFFSET(VCPU_SHARED_SPRG3, kvm_vcpu_arch_shared, sprg3);
+       OFFSET(VCPU_SHARED_SPRG4, kvm_vcpu_arch_shared, sprg4);
+       OFFSET(VCPU_SHARED_SPRG5, kvm_vcpu_arch_shared, sprg5);
+       OFFSET(VCPU_SHARED_SPRG6, kvm_vcpu_arch_shared, sprg6);
+       OFFSET(VCPU_SHARED_SPRG7, kvm_vcpu_arch_shared, sprg7);
+       OFFSET(VCPU_SHADOW_PID, kvm_vcpu, arch.shadow_pid);
+       OFFSET(VCPU_SHADOW_PID1, kvm_vcpu, arch.shadow_pid1);
+       OFFSET(VCPU_SHARED, kvm_vcpu, arch.shared);
+       OFFSET(VCPU_SHARED_MSR, kvm_vcpu_arch_shared, msr);
+       OFFSET(VCPU_SHADOW_MSR, kvm_vcpu, arch.shadow_msr);
 #if defined(CONFIG_PPC_BOOK3S_64) && defined(CONFIG_KVM_BOOK3S_PR_POSSIBLE)
-       DEFINE(VCPU_SHAREDBE, offsetof(struct kvm_vcpu, arch.shared_big_endian));
+       OFFSET(VCPU_SHAREDBE, kvm_vcpu, arch.shared_big_endian);
 #endif
 
-       DEFINE(VCPU_SHARED_MAS0, offsetof(struct kvm_vcpu_arch_shared, mas0));
-       DEFINE(VCPU_SHARED_MAS1, offsetof(struct kvm_vcpu_arch_shared, mas1));
-       DEFINE(VCPU_SHARED_MAS2, offsetof(struct kvm_vcpu_arch_shared, mas2));
-       DEFINE(VCPU_SHARED_MAS7_3, offsetof(struct kvm_vcpu_arch_shared, mas7_3));
-       DEFINE(VCPU_SHARED_MAS4, offsetof(struct kvm_vcpu_arch_shared, mas4));
-       DEFINE(VCPU_SHARED_MAS6, offsetof(struct kvm_vcpu_arch_shared, mas6));
+       OFFSET(VCPU_SHARED_MAS0, kvm_vcpu_arch_shared, mas0);
+       OFFSET(VCPU_SHARED_MAS1, kvm_vcpu_arch_shared, mas1);
+       OFFSET(VCPU_SHARED_MAS2, kvm_vcpu_arch_shared, mas2);
+       OFFSET(VCPU_SHARED_MAS7_3, kvm_vcpu_arch_shared, mas7_3);
+       OFFSET(VCPU_SHARED_MAS4, kvm_vcpu_arch_shared, mas4);
+       OFFSET(VCPU_SHARED_MAS6, kvm_vcpu_arch_shared, mas6);
 
-       DEFINE(VCPU_KVM, offsetof(struct kvm_vcpu, kvm));
-       DEFINE(KVM_LPID, offsetof(struct kvm, arch.lpid));
+       OFFSET(VCPU_KVM, kvm_vcpu, kvm);
+       OFFSET(KVM_LPID, kvm, arch.lpid);
 
        /* book3s */
 #ifdef CONFIG_KVM_BOOK3S_HV_POSSIBLE
-       DEFINE(KVM_TLB_SETS, offsetof(struct kvm, arch.tlb_sets));
-       DEFINE(KVM_SDR1, offsetof(struct kvm, arch.sdr1));
-       DEFINE(KVM_HOST_LPID, offsetof(struct kvm, arch.host_lpid));
-       DEFINE(KVM_HOST_LPCR, offsetof(struct kvm, arch.host_lpcr));
-       DEFINE(KVM_HOST_SDR1, offsetof(struct kvm, arch.host_sdr1));
-       DEFINE(KVM_NEED_FLUSH, offsetof(struct kvm, arch.need_tlb_flush.bits));
-       DEFINE(KVM_ENABLED_HCALLS, offsetof(struct kvm, arch.enabled_hcalls));
-       DEFINE(KVM_VRMA_SLB_V, offsetof(struct kvm, arch.vrma_slb_v));
-       DEFINE(KVM_RADIX, offsetof(struct kvm, arch.radix));
-       DEFINE(VCPU_DSISR, offsetof(struct kvm_vcpu, arch.shregs.dsisr));
-       DEFINE(VCPU_DAR, offsetof(struct kvm_vcpu, arch.shregs.dar));
-       DEFINE(VCPU_VPA, offsetof(struct kvm_vcpu, arch.vpa.pinned_addr));
-       DEFINE(VCPU_VPA_DIRTY, offsetof(struct kvm_vcpu, arch.vpa.dirty));
-       DEFINE(VCPU_HEIR, offsetof(struct kvm_vcpu, arch.emul_inst));
-       DEFINE(VCPU_CPU, offsetof(struct kvm_vcpu, cpu));
-       DEFINE(VCPU_THREAD_CPU, offsetof(struct kvm_vcpu, arch.thread_cpu));
+       OFFSET(KVM_TLB_SETS, kvm, arch.tlb_sets);
+       OFFSET(KVM_SDR1, kvm, arch.sdr1);
+       OFFSET(KVM_HOST_LPID, kvm, arch.host_lpid);
+       OFFSET(KVM_HOST_LPCR, kvm, arch.host_lpcr);
+       OFFSET(KVM_HOST_SDR1, kvm, arch.host_sdr1);
+       OFFSET(KVM_NEED_FLUSH, kvm, arch.need_tlb_flush.bits);
+       OFFSET(KVM_ENABLED_HCALLS, kvm, arch.enabled_hcalls);
+       OFFSET(KVM_VRMA_SLB_V, kvm, arch.vrma_slb_v);
+       OFFSET(KVM_RADIX, kvm, arch.radix);
+       OFFSET(VCPU_DSISR, kvm_vcpu, arch.shregs.dsisr);
+       OFFSET(VCPU_DAR, kvm_vcpu, arch.shregs.dar);
+       OFFSET(VCPU_VPA, kvm_vcpu, arch.vpa.pinned_addr);
+       OFFSET(VCPU_VPA_DIRTY, kvm_vcpu, arch.vpa.dirty);
+       OFFSET(VCPU_HEIR, kvm_vcpu, arch.emul_inst);
+       OFFSET(VCPU_CPU, kvm_vcpu, cpu);
+       OFFSET(VCPU_THREAD_CPU, kvm_vcpu, arch.thread_cpu);
 #endif
 #ifdef CONFIG_PPC_BOOK3S
-       DEFINE(VCPU_PURR, offsetof(struct kvm_vcpu, arch.purr));
-       DEFINE(VCPU_SPURR, offsetof(struct kvm_vcpu, arch.spurr));
-       DEFINE(VCPU_IC, offsetof(struct kvm_vcpu, arch.ic));
-       DEFINE(VCPU_DSCR, offsetof(struct kvm_vcpu, arch.dscr));
-       DEFINE(VCPU_AMR, offsetof(struct kvm_vcpu, arch.amr));
-       DEFINE(VCPU_UAMOR, offsetof(struct kvm_vcpu, arch.uamor));
-       DEFINE(VCPU_IAMR, offsetof(struct kvm_vcpu, arch.iamr));
-       DEFINE(VCPU_CTRL, offsetof(struct kvm_vcpu, arch.ctrl));
-       DEFINE(VCPU_DABR, offsetof(struct kvm_vcpu, arch.dabr));
-       DEFINE(VCPU_DABRX, offsetof(struct kvm_vcpu, arch.dabrx));
-       DEFINE(VCPU_DAWR, offsetof(struct kvm_vcpu, arch.dawr));
-       DEFINE(VCPU_DAWRX, offsetof(struct kvm_vcpu, arch.dawrx));
-       DEFINE(VCPU_CIABR, offsetof(struct kvm_vcpu, arch.ciabr));
-       DEFINE(VCPU_HFLAGS, offsetof(struct kvm_vcpu, arch.hflags));
-       DEFINE(VCPU_DEC, offsetof(struct kvm_vcpu, arch.dec));
-       DEFINE(VCPU_DEC_EXPIRES, offsetof(struct kvm_vcpu, arch.dec_expires));
-       DEFINE(VCPU_PENDING_EXC, offsetof(struct kvm_vcpu, arch.pending_exceptions));
-       DEFINE(VCPU_CEDED, offsetof(struct kvm_vcpu, arch.ceded));
-       DEFINE(VCPU_PRODDED, offsetof(struct kvm_vcpu, arch.prodded));
-       DEFINE(VCPU_MMCR, offsetof(struct kvm_vcpu, arch.mmcr));
-       DEFINE(VCPU_PMC, offsetof(struct kvm_vcpu, arch.pmc));
-       DEFINE(VCPU_SPMC, offsetof(struct kvm_vcpu, arch.spmc));
-       DEFINE(VCPU_SIAR, offsetof(struct kvm_vcpu, arch.siar));
-       DEFINE(VCPU_SDAR, offsetof(struct kvm_vcpu, arch.sdar));
-       DEFINE(VCPU_SIER, offsetof(struct kvm_vcpu, arch.sier));
-       DEFINE(VCPU_SLB, offsetof(struct kvm_vcpu, arch.slb));
-       DEFINE(VCPU_SLB_MAX, offsetof(struct kvm_vcpu, arch.slb_max));
-       DEFINE(VCPU_SLB_NR, offsetof(struct kvm_vcpu, arch.slb_nr));
-       DEFINE(VCPU_FAULT_DSISR, offsetof(struct kvm_vcpu, arch.fault_dsisr));
-       DEFINE(VCPU_FAULT_DAR, offsetof(struct kvm_vcpu, arch.fault_dar));
-       DEFINE(VCPU_FAULT_GPA, offsetof(struct kvm_vcpu, arch.fault_gpa));
-       DEFINE(VCPU_INTR_MSR, offsetof(struct kvm_vcpu, arch.intr_msr));
-       DEFINE(VCPU_LAST_INST, offsetof(struct kvm_vcpu, arch.last_inst));
-       DEFINE(VCPU_TRAP, offsetof(struct kvm_vcpu, arch.trap));
-       DEFINE(VCPU_CFAR, offsetof(struct kvm_vcpu, arch.cfar));
-       DEFINE(VCPU_PPR, offsetof(struct kvm_vcpu, arch.ppr));
-       DEFINE(VCPU_FSCR, offsetof(struct kvm_vcpu, arch.fscr));
-       DEFINE(VCPU_PSPB, offsetof(struct kvm_vcpu, arch.pspb));
-       DEFINE(VCPU_EBBHR, offsetof(struct kvm_vcpu, arch.ebbhr));
-       DEFINE(VCPU_EBBRR, offsetof(struct kvm_vcpu, arch.ebbrr));
-       DEFINE(VCPU_BESCR, offsetof(struct kvm_vcpu, arch.bescr));
-       DEFINE(VCPU_CSIGR, offsetof(struct kvm_vcpu, arch.csigr));
-       DEFINE(VCPU_TACR, offsetof(struct kvm_vcpu, arch.tacr));
-       DEFINE(VCPU_TCSCR, offsetof(struct kvm_vcpu, arch.tcscr));
-       DEFINE(VCPU_ACOP, offsetof(struct kvm_vcpu, arch.acop));
-       DEFINE(VCPU_WORT, offsetof(struct kvm_vcpu, arch.wort));
-       DEFINE(VCPU_TID, offsetof(struct kvm_vcpu, arch.tid));
-       DEFINE(VCPU_PSSCR, offsetof(struct kvm_vcpu, arch.psscr));
-       DEFINE(VCORE_ENTRY_EXIT, offsetof(struct kvmppc_vcore, entry_exit_map));
-       DEFINE(VCORE_IN_GUEST, offsetof(struct kvmppc_vcore, in_guest));
-       DEFINE(VCORE_NAPPING_THREADS, offsetof(struct kvmppc_vcore, napping_threads));
-       DEFINE(VCORE_KVM, offsetof(struct kvmppc_vcore, kvm));
-       DEFINE(VCORE_TB_OFFSET, offsetof(struct kvmppc_vcore, tb_offset));
-       DEFINE(VCORE_LPCR, offsetof(struct kvmppc_vcore, lpcr));
-       DEFINE(VCORE_PCR, offsetof(struct kvmppc_vcore, pcr));
-       DEFINE(VCORE_DPDES, offsetof(struct kvmppc_vcore, dpdes));
-       DEFINE(VCORE_VTB, offsetof(struct kvmppc_vcore, vtb));
-       DEFINE(VCPU_SLB_E, offsetof(struct kvmppc_slb, orige));
-       DEFINE(VCPU_SLB_V, offsetof(struct kvmppc_slb, origv));
+       OFFSET(VCPU_PURR, kvm_vcpu, arch.purr);
+       OFFSET(VCPU_SPURR, kvm_vcpu, arch.spurr);
+       OFFSET(VCPU_IC, kvm_vcpu, arch.ic);
+       OFFSET(VCPU_DSCR, kvm_vcpu, arch.dscr);
+       OFFSET(VCPU_AMR, kvm_vcpu, arch.amr);
+       OFFSET(VCPU_UAMOR, kvm_vcpu, arch.uamor);
+       OFFSET(VCPU_IAMR, kvm_vcpu, arch.iamr);
+       OFFSET(VCPU_CTRL, kvm_vcpu, arch.ctrl);
+       OFFSET(VCPU_DABR, kvm_vcpu, arch.dabr);
+       OFFSET(VCPU_DABRX, kvm_vcpu, arch.dabrx);
+       OFFSET(VCPU_DAWR, kvm_vcpu, arch.dawr);
+       OFFSET(VCPU_DAWRX, kvm_vcpu, arch.dawrx);
+       OFFSET(VCPU_CIABR, kvm_vcpu, arch.ciabr);
+       OFFSET(VCPU_HFLAGS, kvm_vcpu, arch.hflags);
+       OFFSET(VCPU_DEC, kvm_vcpu, arch.dec);
+       OFFSET(VCPU_DEC_EXPIRES, kvm_vcpu, arch.dec_expires);
+       OFFSET(VCPU_PENDING_EXC, kvm_vcpu, arch.pending_exceptions);
+       OFFSET(VCPU_CEDED, kvm_vcpu, arch.ceded);
+       OFFSET(VCPU_PRODDED, kvm_vcpu, arch.prodded);
+       OFFSET(VCPU_MMCR, kvm_vcpu, arch.mmcr);
+       OFFSET(VCPU_PMC, kvm_vcpu, arch.pmc);
+       OFFSET(VCPU_SPMC, kvm_vcpu, arch.spmc);
+       OFFSET(VCPU_SIAR, kvm_vcpu, arch.siar);
+       OFFSET(VCPU_SDAR, kvm_vcpu, arch.sdar);
+       OFFSET(VCPU_SIER, kvm_vcpu, arch.sier);
+       OFFSET(VCPU_SLB, kvm_vcpu, arch.slb);
+       OFFSET(VCPU_SLB_MAX, kvm_vcpu, arch.slb_max);
+       OFFSET(VCPU_SLB_NR, kvm_vcpu, arch.slb_nr);
+       OFFSET(VCPU_FAULT_DSISR, kvm_vcpu, arch.fault_dsisr);
+       OFFSET(VCPU_FAULT_DAR, kvm_vcpu, arch.fault_dar);
+       OFFSET(VCPU_FAULT_GPA, kvm_vcpu, arch.fault_gpa);
+       OFFSET(VCPU_INTR_MSR, kvm_vcpu, arch.intr_msr);
+       OFFSET(VCPU_LAST_INST, kvm_vcpu, arch.last_inst);
+       OFFSET(VCPU_TRAP, kvm_vcpu, arch.trap);
+       OFFSET(VCPU_CFAR, kvm_vcpu, arch.cfar);
+       OFFSET(VCPU_PPR, kvm_vcpu, arch.ppr);
+       OFFSET(VCPU_FSCR, kvm_vcpu, arch.fscr);
+       OFFSET(VCPU_PSPB, kvm_vcpu, arch.pspb);
+       OFFSET(VCPU_EBBHR, kvm_vcpu, arch.ebbhr);
+       OFFSET(VCPU_EBBRR, kvm_vcpu, arch.ebbrr);
+       OFFSET(VCPU_BESCR, kvm_vcpu, arch.bescr);
+       OFFSET(VCPU_CSIGR, kvm_vcpu, arch.csigr);
+       OFFSET(VCPU_TACR, kvm_vcpu, arch.tacr);
+       OFFSET(VCPU_TCSCR, kvm_vcpu, arch.tcscr);
+       OFFSET(VCPU_ACOP, kvm_vcpu, arch.acop);
+       OFFSET(VCPU_WORT, kvm_vcpu, arch.wort);
+       OFFSET(VCPU_TID, kvm_vcpu, arch.tid);
+       OFFSET(VCPU_PSSCR, kvm_vcpu, arch.psscr);
+       OFFSET(VCORE_ENTRY_EXIT, kvmppc_vcore, entry_exit_map);
+       OFFSET(VCORE_IN_GUEST, kvmppc_vcore, in_guest);
+       OFFSET(VCORE_NAPPING_THREADS, kvmppc_vcore, napping_threads);
+       OFFSET(VCORE_KVM, kvmppc_vcore, kvm);
+       OFFSET(VCORE_TB_OFFSET, kvmppc_vcore, tb_offset);
+       OFFSET(VCORE_LPCR, kvmppc_vcore, lpcr);
+       OFFSET(VCORE_PCR, kvmppc_vcore, pcr);
+       OFFSET(VCORE_DPDES, kvmppc_vcore, dpdes);
+       OFFSET(VCORE_VTB, kvmppc_vcore, vtb);
+       OFFSET(VCPU_SLB_E, kvmppc_slb, orige);
+       OFFSET(VCPU_SLB_V, kvmppc_slb, origv);
        DEFINE(VCPU_SLB_SIZE, sizeof(struct kvmppc_slb));
 #ifdef CONFIG_PPC_TRANSACTIONAL_MEM
-       DEFINE(VCPU_TFHAR, offsetof(struct kvm_vcpu, arch.tfhar));
-       DEFINE(VCPU_TFIAR, offsetof(struct kvm_vcpu, arch.tfiar));
-       DEFINE(VCPU_TEXASR, offsetof(struct kvm_vcpu, arch.texasr));
-       DEFINE(VCPU_GPR_TM, offsetof(struct kvm_vcpu, arch.gpr_tm));
-       DEFINE(VCPU_FPRS_TM, offsetof(struct kvm_vcpu, arch.fp_tm.fpr));
-       DEFINE(VCPU_VRS_TM, offsetof(struct kvm_vcpu, arch.vr_tm.vr));
-       DEFINE(VCPU_VRSAVE_TM, offsetof(struct kvm_vcpu, arch.vrsave_tm));
-       DEFINE(VCPU_CR_TM, offsetof(struct kvm_vcpu, arch.cr_tm));
-       DEFINE(VCPU_XER_TM, offsetof(struct kvm_vcpu, arch.xer_tm));
-       DEFINE(VCPU_LR_TM, offsetof(struct kvm_vcpu, arch.lr_tm));
-       DEFINE(VCPU_CTR_TM, offsetof(struct kvm_vcpu, arch.ctr_tm));
-       DEFINE(VCPU_AMR_TM, offsetof(struct kvm_vcpu, arch.amr_tm));
-       DEFINE(VCPU_PPR_TM, offsetof(struct kvm_vcpu, arch.ppr_tm));
-       DEFINE(VCPU_DSCR_TM, offsetof(struct kvm_vcpu, arch.dscr_tm));
-       DEFINE(VCPU_TAR_TM, offsetof(struct kvm_vcpu, arch.tar_tm));
+       OFFSET(VCPU_TFHAR, kvm_vcpu, arch.tfhar);
+       OFFSET(VCPU_TFIAR, kvm_vcpu, arch.tfiar);
+       OFFSET(VCPU_TEXASR, kvm_vcpu, arch.texasr);
+       OFFSET(VCPU_GPR_TM, kvm_vcpu, arch.gpr_tm);
+       OFFSET(VCPU_FPRS_TM, kvm_vcpu, arch.fp_tm.fpr);
+       OFFSET(VCPU_VRS_TM, kvm_vcpu, arch.vr_tm.vr);
+       OFFSET(VCPU_VRSAVE_TM, kvm_vcpu, arch.vrsave_tm);
+       OFFSET(VCPU_CR_TM, kvm_vcpu, arch.cr_tm);
+       OFFSET(VCPU_XER_TM, kvm_vcpu, arch.xer_tm);
+       OFFSET(VCPU_LR_TM, kvm_vcpu, arch.lr_tm);
+       OFFSET(VCPU_CTR_TM, kvm_vcpu, arch.ctr_tm);
+       OFFSET(VCPU_AMR_TM, kvm_vcpu, arch.amr_tm);
+       OFFSET(VCPU_PPR_TM, kvm_vcpu, arch.ppr_tm);
+       OFFSET(VCPU_DSCR_TM, kvm_vcpu, arch.dscr_tm);
+       OFFSET(VCPU_TAR_TM, kvm_vcpu, arch.tar_tm);
 #endif
 
 #ifdef CONFIG_PPC_BOOK3S_64
 #ifdef CONFIG_KVM_BOOK3S_PR_POSSIBLE
-       DEFINE(PACA_SVCPU, offsetof(struct paca_struct, shadow_vcpu));
+       OFFSET(PACA_SVCPU, paca_struct, shadow_vcpu);
 # define SVCPU_FIELD(x, f)     DEFINE(x, offsetof(struct paca_struct, shadow_vcpu.f))
 #else
 # define SVCPU_FIELD(x, f)
@@ -668,11 +653,11 @@ int main(void)
        HSTATE_FIELD(HSTATE_DECEXP, dec_expires);
        HSTATE_FIELD(HSTATE_SPLIT_MODE, kvm_split_mode);
        DEFINE(IPI_PRIORITY, IPI_PRIORITY);
-       DEFINE(KVM_SPLIT_RPR, offsetof(struct kvm_split_mode, rpr));
-       DEFINE(KVM_SPLIT_PMMAR, offsetof(struct kvm_split_mode, pmmar));
-       DEFINE(KVM_SPLIT_LDBAR, offsetof(struct kvm_split_mode, ldbar));
-       DEFINE(KVM_SPLIT_DO_NAP, offsetof(struct kvm_split_mode, do_nap));
-       DEFINE(KVM_SPLIT_NAPPED, offsetof(struct kvm_split_mode, napped));
+       OFFSET(KVM_SPLIT_RPR, kvm_split_mode, rpr);
+       OFFSET(KVM_SPLIT_PMMAR, kvm_split_mode, pmmar);
+       OFFSET(KVM_SPLIT_LDBAR, kvm_split_mode, ldbar);
+       OFFSET(KVM_SPLIT_DO_NAP, kvm_split_mode, do_nap);
+       OFFSET(KVM_SPLIT_NAPPED, kvm_split_mode, napped);
 #endif /* CONFIG_KVM_BOOK3S_HV_POSSIBLE */
 
 #ifdef CONFIG_PPC_BOOK3S_64
@@ -682,32 +667,27 @@ int main(void)
 #endif /* CONFIG_PPC_BOOK3S_64 */
 
 #else /* CONFIG_PPC_BOOK3S */
-       DEFINE(VCPU_CR, offsetof(struct kvm_vcpu, arch.cr));
-       DEFINE(VCPU_XER, offsetof(struct kvm_vcpu, arch.xer));
-       DEFINE(VCPU_LR, offsetof(struct kvm_vcpu, arch.lr));
-       DEFINE(VCPU_CTR, offsetof(struct kvm_vcpu, arch.ctr));
-       DEFINE(VCPU_PC, offsetof(struct kvm_vcpu, arch.pc));
-       DEFINE(VCPU_SPRG9, offsetof(struct kvm_vcpu, arch.sprg9));
-       DEFINE(VCPU_LAST_INST, offsetof(struct kvm_vcpu, arch.last_inst));
-       DEFINE(VCPU_FAULT_DEAR, offsetof(struct kvm_vcpu, arch.fault_dear));
-       DEFINE(VCPU_FAULT_ESR, offsetof(struct kvm_vcpu, arch.fault_esr));
-       DEFINE(VCPU_CRIT_SAVE, offsetof(struct kvm_vcpu, arch.crit_save));
+       OFFSET(VCPU_CR, kvm_vcpu, arch.cr);
+       OFFSET(VCPU_XER, kvm_vcpu, arch.xer);
+       OFFSET(VCPU_LR, kvm_vcpu, arch.lr);
+       OFFSET(VCPU_CTR, kvm_vcpu, arch.ctr);
+       OFFSET(VCPU_PC, kvm_vcpu, arch.pc);
+       OFFSET(VCPU_SPRG9, kvm_vcpu, arch.sprg9);
+       OFFSET(VCPU_LAST_INST, kvm_vcpu, arch.last_inst);
+       OFFSET(VCPU_FAULT_DEAR, kvm_vcpu, arch.fault_dear);
+       OFFSET(VCPU_FAULT_ESR, kvm_vcpu, arch.fault_esr);
+       OFFSET(VCPU_CRIT_SAVE, kvm_vcpu, arch.crit_save);
 #endif /* CONFIG_PPC_BOOK3S */
 #endif /* CONFIG_KVM */
 
 #ifdef CONFIG_KVM_GUEST
-       DEFINE(KVM_MAGIC_SCRATCH1, offsetof(struct kvm_vcpu_arch_shared,
-                                           scratch1));
-       DEFINE(KVM_MAGIC_SCRATCH2, offsetof(struct kvm_vcpu_arch_shared,
-                                           scratch2));
-       DEFINE(KVM_MAGIC_SCRATCH3, offsetof(struct kvm_vcpu_arch_shared,
-                                           scratch3));
-       DEFINE(KVM_MAGIC_INT, offsetof(struct kvm_vcpu_arch_shared,
-                                      int_pending));
-       DEFINE(KVM_MAGIC_MSR, offsetof(struct kvm_vcpu_arch_shared, msr));
-       DEFINE(KVM_MAGIC_CRITICAL, offsetof(struct kvm_vcpu_arch_shared,
-                                           critical));
-       DEFINE(KVM_MAGIC_SR, offsetof(struct kvm_vcpu_arch_shared, sr));
+       OFFSET(KVM_MAGIC_SCRATCH1, kvm_vcpu_arch_shared, scratch1);
+       OFFSET(KVM_MAGIC_SCRATCH2, kvm_vcpu_arch_shared, scratch2);
+       OFFSET(KVM_MAGIC_SCRATCH3, kvm_vcpu_arch_shared, scratch3);
+       OFFSET(KVM_MAGIC_INT, kvm_vcpu_arch_shared, int_pending);
+       OFFSET(KVM_MAGIC_MSR, kvm_vcpu_arch_shared, msr);
+       OFFSET(KVM_MAGIC_CRITICAL, kvm_vcpu_arch_shared, critical);
+       OFFSET(KVM_MAGIC_SR, kvm_vcpu_arch_shared, sr);
 #endif
 
 #ifdef CONFIG_44x
@@ -716,45 +696,37 @@ int main(void)
 #endif
 #ifdef CONFIG_PPC_FSL_BOOK3E
        DEFINE(TLBCAM_SIZE, sizeof(struct tlbcam));
-       DEFINE(TLBCAM_MAS0, offsetof(struct tlbcam, MAS0));
-       DEFINE(TLBCAM_MAS1, offsetof(struct tlbcam, MAS1));
-       DEFINE(TLBCAM_MAS2, offsetof(struct tlbcam, MAS2));
-       DEFINE(TLBCAM_MAS3, offsetof(struct tlbcam, MAS3));
-       DEFINE(TLBCAM_MAS7, offsetof(struct tlbcam, MAS7));
+       OFFSET(TLBCAM_MAS0, tlbcam, MAS0);
+       OFFSET(TLBCAM_MAS1, tlbcam, MAS1);
+       OFFSET(TLBCAM_MAS2, tlbcam, MAS2);
+       OFFSET(TLBCAM_MAS3, tlbcam, MAS3);
+       OFFSET(TLBCAM_MAS7, tlbcam, MAS7);
 #endif
 
 #if defined(CONFIG_KVM) && defined(CONFIG_SPE)
-       DEFINE(VCPU_EVR, offsetof(struct kvm_vcpu, arch.evr[0]));
-       DEFINE(VCPU_ACC, offsetof(struct kvm_vcpu, arch.acc));
-       DEFINE(VCPU_SPEFSCR, offsetof(struct kvm_vcpu, arch.spefscr));
-       DEFINE(VCPU_HOST_SPEFSCR, offsetof(struct kvm_vcpu, arch.host_spefscr));
+       OFFSET(VCPU_EVR, kvm_vcpu, arch.evr[0]);
+       OFFSET(VCPU_ACC, kvm_vcpu, arch.acc);
+       OFFSET(VCPU_SPEFSCR, kvm_vcpu, arch.spefscr);
+       OFFSET(VCPU_HOST_SPEFSCR, kvm_vcpu, arch.host_spefscr);
 #endif
 
 #ifdef CONFIG_KVM_BOOKE_HV
-       DEFINE(VCPU_HOST_MAS4, offsetof(struct kvm_vcpu, arch.host_mas4));
-       DEFINE(VCPU_HOST_MAS6, offsetof(struct kvm_vcpu, arch.host_mas6));
+       OFFSET(VCPU_HOST_MAS4, kvm_vcpu, arch.host_mas4);
+       OFFSET(VCPU_HOST_MAS6, kvm_vcpu, arch.host_mas6);
 #endif
 
 #ifdef CONFIG_KVM_EXIT_TIMING
-       DEFINE(VCPU_TIMING_EXIT_TBU, offsetof(struct kvm_vcpu,
-                                               arch.timing_exit.tv32.tbu));
-       DEFINE(VCPU_TIMING_EXIT_TBL, offsetof(struct kvm_vcpu,
-                                               arch.timing_exit.tv32.tbl));
-       DEFINE(VCPU_TIMING_LAST_ENTER_TBU, offsetof(struct kvm_vcpu,
-                                       arch.timing_last_enter.tv32.tbu));
-       DEFINE(VCPU_TIMING_LAST_ENTER_TBL, offsetof(struct kvm_vcpu,
-                                       arch.timing_last_enter.tv32.tbl));
+       OFFSET(VCPU_TIMING_EXIT_TBU, kvm_vcpu, arch.timing_exit.tv32.tbu);
+       OFFSET(VCPU_TIMING_EXIT_TBL, kvm_vcpu, arch.timing_exit.tv32.tbl);
+       OFFSET(VCPU_TIMING_LAST_ENTER_TBU, kvm_vcpu, arch.timing_last_enter.tv32.tbu);
+       OFFSET(VCPU_TIMING_LAST_ENTER_TBL, kvm_vcpu, arch.timing_last_enter.tv32.tbl);
 #endif
 
 #ifdef CONFIG_PPC_POWERNV
-       DEFINE(PACA_CORE_IDLE_STATE_PTR,
-                       offsetof(struct paca_struct, core_idle_state_ptr));
-       DEFINE(PACA_THREAD_IDLE_STATE,
-                       offsetof(struct paca_struct, thread_idle_state));
-       DEFINE(PACA_THREAD_MASK,
-                       offsetof(struct paca_struct, thread_mask));
-       DEFINE(PACA_SUBCORE_SIBLING_MASK,
-                       offsetof(struct paca_struct, subcore_sibling_mask));
+       OFFSET(PACA_CORE_IDLE_STATE_PTR, paca_struct, core_idle_state_ptr);
+       OFFSET(PACA_THREAD_IDLE_STATE, paca_struct, thread_idle_state);
+       OFFSET(PACA_THREAD_MASK, paca_struct, thread_mask);
+       OFFSET(PACA_SUBCORE_SIBLING_MASK, paca_struct, subcore_sibling_mask);
 #endif
 
        DEFINE(PPC_DBELL_SERVER, PPC_DBELL_SERVER);
index 917188615bf52c3d4bbfa944d8f36fff8260afa3..7fe8c79e693791898abbfef5a796c08490d6eb6a 100644 (file)
@@ -101,6 +101,8 @@ _GLOBAL(__setup_cpu_power9)
        mfspr   r3,SPRN_LPCR
        LOAD_REG_IMMEDIATE(r4, LPCR_PECEDH | LPCR_PECE_HVEE | LPCR_HVICE)
        or      r3, r3, r4
+       LOAD_REG_IMMEDIATE(r4, LPCR_UPRT | LPCR_HR)
+       andc    r3, r3, r4
        bl      __init_LPCR
        bl      __init_HFSCR
        bl      __init_tlb_power9
@@ -122,6 +124,8 @@ _GLOBAL(__restore_cpu_power9)
        mfspr   r3,SPRN_LPCR
        LOAD_REG_IMMEDIATE(r4, LPCR_PECEDH | LPCR_PECE_HVEE | LPCR_HVICE)
        or      r3, r3, r4
+       LOAD_REG_IMMEDIATE(r4, LPCR_UPRT | LPCR_HR)
+       andc    r3, r3, r4
        bl      __init_LPCR
        bl      __init_HFSCR
        bl      __init_tlb_power9
index 6a82ef039c509746f5afa66ebc286fa5da429ed3..bb7a1890aeb7fb8e95cf8ca0c7aa53765e12eb45 100644 (file)
@@ -386,6 +386,23 @@ static struct cpu_spec __initdata cpu_specs[] = {
                .machine_check_early    = __machine_check_early_realmode_p8,
                .platform               = "power8",
        },
+       {       /* 3.00-compliant processor, i.e. Power9 "architected" mode */
+               .pvr_mask               = 0xffffffff,
+               .pvr_value              = 0x0f000005,
+               .cpu_name               = "POWER9 (architected)",
+               .cpu_features           = CPU_FTRS_POWER9,
+               .cpu_user_features      = COMMON_USER_POWER9,
+               .cpu_user_features2     = COMMON_USER2_POWER9,
+               .mmu_features           = MMU_FTRS_POWER9,
+               .icache_bsize           = 128,
+               .dcache_bsize           = 128,
+               .oprofile_type          = PPC_OPROFILE_INVALID,
+               .oprofile_cpu_type      = "ppc64/ibm-compat-v1",
+               .cpu_setup              = __setup_cpu_power9,
+               .cpu_restore            = __restore_cpu_power9,
+               .flush_tlb              = __flush_tlb_power9,
+               .platform               = "power9",
+       },
        {       /* Power7 */
                .pvr_mask               = 0xffff0000,
                .pvr_value              = 0x003f0000,
index 3841d749a430069f4d4f2705c4199c08609b3757..a38600949f3ab2cd9e39b201348405a4b00e737a 100644 (file)
@@ -205,6 +205,9 @@ transfer_to_handler_cont:
        mflr    r9
        lwz     r11,0(r9)               /* virtual address of handler */
        lwz     r9,4(r9)                /* where to go when done */
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       mtspr   SPRN_NRI, r0
+#endif
 #ifdef CONFIG_TRACE_IRQFLAGS
        lis     r12,reenable_mmu@h
        ori     r12,r12,reenable_mmu@l
@@ -292,7 +295,9 @@ stack_ovf:
        lis     r9,StackOverflow@ha
        addi    r9,r9,StackOverflow@l
        LOAD_MSR_KERNEL(r10,MSR_KERNEL)
-       FIX_SRR1(r10,r12)
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       mtspr   SPRN_NRI, r0
+#endif
        mtspr   SPRN_SRR0,r9
        mtspr   SPRN_SRR1,r10
        SYNC
@@ -417,9 +422,11 @@ END_FTR_SECTION_IFSET(CPU_FTR_NEED_PAIRED_STWCX)
        mtlr    r4
        mtcr    r5
        lwz     r7,_NIP(r1)
-       FIX_SRR1(r8, r0)
        lwz     r2,GPR2(r1)
        lwz     r1,GPR1(r1)
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       mtspr   SPRN_NRI, r0
+#endif
        mtspr   SPRN_SRR0,r7
        mtspr   SPRN_SRR1,r8
        SYNC
@@ -699,6 +706,9 @@ fast_exception_return:
        lwz     r10,_LINK(r11)
        mtlr    r10
        REST_GPR(10, r11)
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       mtspr   SPRN_NRI, r0
+#endif
        mtspr   SPRN_SRR1,r9
        mtspr   SPRN_SRR0,r12
        REST_GPR(9, r11)
@@ -947,7 +957,9 @@ END_FTR_SECTION_IFSET(CPU_FTR_NEED_PAIRED_STWCX)
        .globl exc_exit_restart
 exc_exit_restart:
        lwz     r12,_NIP(r1)
-       FIX_SRR1(r9,r10)
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       mtspr   SPRN_NRI, r0
+#endif
        mtspr   SPRN_SRR0,r12
        mtspr   SPRN_SRR1,r9
        REST_4GPRS(9, r1)
@@ -1290,7 +1302,6 @@ _GLOBAL(enter_rtas)
 1:     tophys(r9,r1)
        lwz     r8,INT_FRAME_SIZE+4(r9) /* get return address */
        lwz     r9,8(r9)        /* original msr value */
-       FIX_SRR1(r9,r0)
        addi    r1,r1,INT_FRAME_SIZE
        li      r0,0
        mtspr   SPRN_SPRG_RTAS,r0
index 9d963547d2438864d36662271912c4a2c28f21ef..1607be7c0ef2dddc88f27daf19eefc6fc116b291 100644 (file)
@@ -869,7 +869,6 @@ __secondary_start:
 
        /* enable MMU and jump to start_secondary */
        li      r4,MSR_KERNEL
-       FIX_SRR1(r4,r5)
        lis     r3,start_secondary@h
        ori     r3,r3,start_secondary@l
        mtspr   SPRN_SRR0,r3
@@ -977,7 +976,6 @@ start_here:
        ori     r4,r4,2f@l
        tophys(r4,r4)
        li      r3,MSR_KERNEL & ~(MSR_IR|MSR_DR)
-       FIX_SRR1(r3,r5)
        mtspr   SPRN_SRR0,r4
        mtspr   SPRN_SRR1,r3
        SYNC
@@ -1001,7 +999,6 @@ start_here:
 
 /* Now turn on the MMU for real! */
        li      r4,MSR_KERNEL
-       FIX_SRR1(r4,r5)
        lis     r3,start_kernel@h
        ori     r3,r3,start_kernel@l
        mtspr   SPRN_SRR0,r3
index 1a9c99d3e5d80e758a7c77fa36a5d5b87dcdc986..c032fe8c2d26e49f5be446060556229542992ca2 100644 (file)
@@ -329,6 +329,12 @@ InstructionTLBMiss:
        mtspr   SPRN_SPRG_SCRATCH2, r3
 #endif
        EXCEPTION_PROLOG_0
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       lis     r10, (itlb_miss_counter - PAGE_OFFSET)@ha
+       lwz     r11, (itlb_miss_counter - PAGE_OFFSET)@l(r10)
+       addi    r11, r11, 1
+       stw     r11, (itlb_miss_counter - PAGE_OFFSET)@l(r10)
+#endif
 
        /* If we are faulting a kernel address, we have to use the
         * kernel page tables.
@@ -429,6 +435,12 @@ InstructionTLBMiss:
 DataStoreTLBMiss:
        mtspr   SPRN_SPRG_SCRATCH2, r3
        EXCEPTION_PROLOG_0
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       lis     r10, (dtlb_miss_counter - PAGE_OFFSET)@ha
+       lwz     r11, (dtlb_miss_counter - PAGE_OFFSET)@l(r10)
+       addi    r11, r11, 1
+       stw     r11, (dtlb_miss_counter - PAGE_OFFSET)@l(r10)
+#endif
        mfcr    r3
 
        /* If we are faulting a kernel address, we have to use the
@@ -561,6 +573,7 @@ InstructionTLBError:
        andis.  r10,r5,0x4000
        beq+    1f
        tlbie   r4
+itlbie:
        /* 0x400 is InstructionAccess exception, needed by bad_page_fault() */
 1:     EXC_XFER_LITE(0x400, handle_page_fault)
 
@@ -585,6 +598,7 @@ DARFixed:/* Return from dcbx instruction bug workaround */
        andis.  r10,r5,0x4000
        beq+    1f
        tlbie   r4
+dtlbie:
 1:     li      r10,RPN_PATTERN
        mtspr   SPRN_DAR,r10    /* Tag DAR, to be used in DTLB Error */
        /* 0x300 is DataAccess exception, needed by bad_page_fault() */
@@ -602,8 +616,43 @@ DARFixed:/* Return from dcbx instruction bug workaround */
  * support of breakpoints and such.  Someday I will get around to
  * using them.
  */
-       EXCEPTION(0x1c00, Trap_1c, unknown_exception, EXC_XFER_EE)
+       . = 0x1c00
+DataBreakpoint:
+       EXCEPTION_PROLOG_0
+       mfcr    r10
+       mfspr   r11, SPRN_SRR0
+       cmplwi  cr0, r11, (dtlbie - PAGE_OFFSET)@l
+       cmplwi  cr7, r11, (itlbie - PAGE_OFFSET)@l
+       beq-    cr0, 11f
+       beq-    cr7, 11f
+       EXCEPTION_PROLOG_1
+       EXCEPTION_PROLOG_2
+       addi    r3,r1,STACK_FRAME_OVERHEAD
+       mfspr   r4,SPRN_BAR
+       stw     r4,_DAR(r11)
+       mfspr   r5,SPRN_DSISR
+       EXC_XFER_EE(0x1c00, do_break)
+11:
+       mtcr    r10
+       EXCEPTION_EPILOG_0
+       rfi
+
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       . = 0x1d00
+InstructionBreakpoint:
+       EXCEPTION_PROLOG_0
+       lis     r10, (instruction_counter - PAGE_OFFSET)@ha
+       lwz     r11, (instruction_counter - PAGE_OFFSET)@l(r10)
+       addi    r11, r11, -1
+       stw     r11, (instruction_counter - PAGE_OFFSET)@l(r10)
+       lis     r10, 0xffff
+       ori     r10, r10, 0x01
+       mtspr   SPRN_COUNTA, r10
+       EXCEPTION_EPILOG_0
+       rfi
+#else
        EXCEPTION(0x1d00, Trap_1d, unknown_exception, EXC_XFER_EE)
+#endif
        EXCEPTION(0x1e00, Trap_1e, unknown_exception, EXC_XFER_EE)
        EXCEPTION(0x1f00, Trap_1f, unknown_exception, EXC_XFER_EE)
 
@@ -977,6 +1026,14 @@ initial_mmu:
        lis     r8, IDC_ENABLE@h
        mtspr   SPRN_DC_CST, r8
 #endif
+       /* Disable debug mode entry on breakpoints */
+       mfspr   r8, SPRN_DER
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       rlwinm  r8, r8, 0, ~0xc
+#else
+       rlwinm  r8, r8, 0, ~0x8
+#endif
+       mtspr   SPRN_DER, r8
        blr
 
 
@@ -1010,3 +1067,16 @@ cpu6_errata_word:
        .space  16
 #endif
 
+#ifdef CONFIG_PPC_8xx_PERF_EVENT
+       .globl  itlb_miss_counter
+itlb_miss_counter:
+       .space  4
+
+       .globl  dtlb_miss_counter
+dtlb_miss_counter:
+       .space  4
+
+       .globl  instruction_counter
+instruction_counter:
+       .space  4
+#endif
index 53cc9270aac8bb9f4226d7cde41f8b76e161d13f..53b9c1dfd7d978dddf909d3699e06713d83c025a 100644 (file)
@@ -211,9 +211,11 @@ int hw_breakpoint_handler(struct die_args *args)
        int rc = NOTIFY_STOP;
        struct perf_event *bp;
        struct pt_regs *regs = args->regs;
+#ifndef CONFIG_PPC_8xx
        int stepped = 1;
-       struct arch_hw_breakpoint *info;
        unsigned int instr;
+#endif
+       struct arch_hw_breakpoint *info;
        unsigned long dar = regs->dar;
 
        /* Disable breakpoints during exception handling */
@@ -257,6 +259,7 @@ int hw_breakpoint_handler(struct die_args *args)
              (dar - bp->attr.bp_addr < bp->attr.bp_len)))
                info->type |= HW_BRK_TYPE_EXTRANEOUS_IRQ;
 
+#ifndef CONFIG_PPC_8xx
        /* Do not emulate user-space instructions, instead single-step them */
        if (user_mode(regs)) {
                current->thread.last_hit_ubp = bp;
@@ -280,6 +283,7 @@ int hw_breakpoint_handler(struct die_args *args)
                perf_event_disable_inatomic(bp);
                goto out;
        }
+#endif
        /*
         * As a policy, the callback is invoked in a 'trigger-after-execute'
         * fashion
index 53e429b5a29d58f7290d306fc8b2638602b870c7..4937bef7652f4bc3dd1837be993d5d117917664c 100644 (file)
@@ -65,6 +65,13 @@ optprobe_template_entry:
        mfdsisr r5
        std     r5,_DSISR(r1)
 
+       /*
+        * We may get here from a module, so load the kernel TOC in r2.
+        * The original TOC gets restored when pt_regs is restored
+        * further below.
+        */
+       ld      r2,PACATOC(r13)
+
        .global optprobe_template_op_address
 optprobe_template_op_address:
        /*
index 8e6fde8d28f362649f61b859bcf99d20ec06a916..ffda24a38dda278d2ffabf387cd0b1b6256cc652 100644 (file)
@@ -1560,16 +1560,10 @@ static void pcibios_setup_phb_resources(struct pci_controller *hose,
        /* Hookup PHB Memory resources */
        for (i = 0; i < 3; ++i) {
                res = &hose->mem_resources[i];
-               if (!res->flags) {
-                       if (i == 0)
-                               printk(KERN_ERR "PCI: Memory resource 0 not set for "
-                                      "host bridge %s (domain %d)\n",
-                                      hose->dn->full_name, hose->global_number);
+               if (!res->flags)
                        continue;
-               }
-               offset = hose->mem_offset[i];
-
 
+               offset = hose->mem_offset[i];
                pr_debug("PCI: PHB MEM resource %d = %pR off 0x%08llx\n", i,
                         res, (unsigned long long)offset);
 
index 5dd056df0baaec576431adb4cbe8ab370d8f44c1..4379a079b3c25fa0831e9f339f9193365913f1cc 100644 (file)
@@ -730,6 +730,28 @@ static inline int __set_dabr(unsigned long dabr, unsigned long dabrx)
                mtspr(SPRN_DABRX, dabrx);
        return 0;
 }
+#elif defined(CONFIG_PPC_8xx)
+static inline int __set_dabr(unsigned long dabr, unsigned long dabrx)
+{
+       unsigned long addr = dabr & ~HW_BRK_TYPE_DABR;
+       unsigned long lctrl1 = 0x90000000; /* compare type: equal on E & F */
+       unsigned long lctrl2 = 0x8e000002; /* watchpoint 1 on cmp E | F */
+
+       if ((dabr & HW_BRK_TYPE_RDWR) == HW_BRK_TYPE_READ)
+               lctrl1 |= 0xa0000;
+       else if ((dabr & HW_BRK_TYPE_RDWR) == HW_BRK_TYPE_WRITE)
+               lctrl1 |= 0xf0000;
+       else if ((dabr & HW_BRK_TYPE_RDWR) == 0)
+               lctrl2 = 0;
+
+       mtspr(SPRN_LCTRL2, 0);
+       mtspr(SPRN_CMPE, addr);
+       mtspr(SPRN_CMPF, addr + 4);
+       mtspr(SPRN_LCTRL1, lctrl1);
+       mtspr(SPRN_LCTRL2, lctrl2);
+
+       return 0;
+}
 #else
 static inline int __set_dabr(unsigned long dabr, unsigned long dabrx)
 {
index 616de028f7f8872a738790d99bab451ca8a39021..a3944540fe0d56b0245f65ffcc0c0719f3c57a54 100644 (file)
@@ -839,7 +839,7 @@ struct ibm_arch_vec __cacheline_aligned ibm_architecture_vec = {
                0,
 #endif
                .associativity = OV5_FEAT(OV5_TYPE1_AFFINITY) | OV5_FEAT(OV5_PRRN),
-               .bin_opts = OV5_FEAT(OV5_RESIZE_HPT),
+               .bin_opts = OV5_FEAT(OV5_RESIZE_HPT) | OV5_FEAT(OV5_HP_EVT),
                .micro_checkpoint = 0,
                .reserved0 = 0,
                .max_cpus = cpu_to_be32(NR_CPUS),       /* number of cores supported */
index b9855f1b290af32b4392cf8ad35e0c13d8e1db54..adf2084f214b2bd01d5aa3ef2a613e66b7b66a05 100644 (file)
@@ -113,14 +113,12 @@ void __init setup_tlb_core_data(void)
                 * If we have threads, we need either tlbsrx.
                 * or e6500 tablewalk mode, or else TLB handlers
                 * will be racy and could produce duplicate entries.
+                * Should we panic instead?
                 */
-               if (smt_enabled_at_boot >= 2 &&
-                   !mmu_has_feature(MMU_FTR_USE_TLBRSRV) &&
-                   book3e_htw_mode != PPC_HTW_E6500) {
-                       /* Should we panic instead? */
-                       WARN_ONCE("%s: unsupported MMU configuration -- expect problems\n",
-                                 __func__);
-               }
+               WARN_ONCE(smt_enabled_at_boot >= 2 &&
+                         !mmu_has_feature(MMU_FTR_USE_TLBRSRV) &&
+                         book3e_htw_mode != PPC_HTW_E6500,
+                         "%s: unsupported MMU configuration\n", __func__);
        }
 }
 #endif
index 14e485525e317907c52d0183c88d8887cc77ff97..bc84a8d47b9e88ce823fb026186d02167b5f6f53 100644 (file)
@@ -709,7 +709,7 @@ unsigned long long running_clock(void)
         * time and on a host which doesn't do any virtualisation TB *should* equal
         * VTB so it makes no difference anyway.
         */
-       return local_clock() - cputime_to_nsecs(kcpustat_this_cpu->cpustat[CPUTIME_STEAL]);
+       return local_clock() - kcpustat_this_cpu->cpustat[CPUTIME_STEAL];
 }
 #endif
 
index cb39c8bd243656727f60b8975c9344766d8d79a9..a03ff3d99e0c420e87cf0f81cb64f43ba78f1998 100644 (file)
@@ -193,9 +193,7 @@ void set_pte_at(struct mm_struct *mm, unsigned long addr, pte_t *ptep,
         */
        VM_WARN_ON(pte_present(*ptep) && !pte_protnone(*ptep));
 
-       /*
-        * Add the pte bit when tryint set a pte
-        */
+       /* Add the pte bit when trying to set a pte */
        pte = __pte(pte_val(pte) | _PAGE_PTE);
 
        /* Note: mm->context.id might not yet have been assigned as
index e2974fcd20f17ba4811232a4cb77a69f2a9dbde8..a85e06ea6c2040a84f702b3c41b761808377552e 100644 (file)
@@ -71,9 +71,9 @@ slb_miss_kernel_load_linear:
 
 
 BEGIN_FTR_SECTION
-       b       slb_finish_load
+       b       .Lslb_finish_load
 END_MMU_FTR_SECTION_IFCLR(MMU_FTR_1T_SEGMENT)
-       b       slb_finish_load_1T
+       b       .Lslb_finish_load_1T
 
 1:
 #ifdef CONFIG_SPARSEMEM_VMEMMAP
@@ -109,9 +109,9 @@ slb_miss_kernel_load_io:
        addi    r9,r9,(MAX_USER_CONTEXT - 0xc + 1)@l
 
 BEGIN_FTR_SECTION
-       b       slb_finish_load
+       b       .Lslb_finish_load
 END_MMU_FTR_SECTION_IFCLR(MMU_FTR_1T_SEGMENT)
-       b       slb_finish_load_1T
+       b       .Lslb_finish_load_1T
 
 0:     /*
         * For userspace addresses, make sure this is region 0.
@@ -174,9 +174,9 @@ END_MMU_FTR_SECTION_IFCLR(MMU_FTR_1T_SEGMENT)
        ld      r9,PACACONTEXTID(r13)
 BEGIN_FTR_SECTION
        cmpldi  r10,0x1000
-       bge     slb_finish_load_1T
+       bge     .Lslb_finish_load_1T
 END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
-       b       slb_finish_load
+       b       .Lslb_finish_load
 
 8:     /* invalid EA - return an error indication */
        crset   4*cr0+eq                /* indicate failure */
@@ -187,7 +187,7 @@ END_MMU_FTR_SECTION_IFSET(MMU_FTR_1T_SEGMENT)
  *
  * r3 = EA, r9 = context, r10 = ESID, r11 = flags, clobbers r9, cr7 = <> PAGE_OFFSET
  */
-slb_finish_load:
+.Lslb_finish_load:
        rldimi  r10,r9,ESID_BITS,0
        ASM_VSID_SCRAMBLE(r10,r9,256M)
        /*
@@ -256,7 +256,7 @@ slb_compare_rr_to_size:
  *
  * r3 = EA, r9 = context, r10 = ESID(256MB), r11 = flags, clobbers r9
  */
-slb_finish_load_1T:
+.Lslb_finish_load_1T:
        srdi    r10,r10,(SID_SHIFT_1T - SID_SHIFT)      /* get 1T ESID */
        rldimi  r10,r9,ESID_BITS_1T,0
        ASM_VSID_SCRAMBLE(r10,r9,1T)
@@ -272,3 +272,11 @@ slb_finish_load_1T:
        clrrdi  r3,r3,SID_SHIFT_1T      /* clear out non-ESID bits */
        b       7b
 
+
+_ASM_NOKPROBE_SYMBOL(slb_allocate_realmode)
+_ASM_NOKPROBE_SYMBOL(slb_miss_kernel_load_linear)
+_ASM_NOKPROBE_SYMBOL(slb_miss_kernel_load_io)
+_ASM_NOKPROBE_SYMBOL(slb_compare_rr_to_size)
+#ifdef CONFIG_SPARSEMEM_VMEMMAP
+_ASM_NOKPROBE_SYMBOL(slb_miss_kernel_load_vmemmap)
+#endif
diff --git a/arch/powerpc/perf/8xx-pmu.c b/arch/powerpc/perf/8xx-pmu.c
new file mode 100644 (file)
index 0000000..3c39f05
--- /dev/null
@@ -0,0 +1,173 @@
+/*
+ * Performance event support - PPC 8xx
+ *
+ * Copyright 2016 Christophe Leroy, CS Systemes d'Information
+ *
+ * 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/kernel.h>
+#include <linux/sched.h>
+#include <linux/perf_event.h>
+#include <linux/percpu.h>
+#include <linux/hardirq.h>
+#include <asm/pmc.h>
+#include <asm/machdep.h>
+#include <asm/firmware.h>
+#include <asm/ptrace.h>
+
+#define PERF_8xx_ID_CPU_CYCLES         1
+#define PERF_8xx_ID_HW_INSTRUCTIONS    2
+#define PERF_8xx_ID_ITLB_LOAD_MISS     3
+#define PERF_8xx_ID_DTLB_LOAD_MISS     4
+
+#define C(x)   PERF_COUNT_HW_CACHE_##x
+#define DTLB_LOAD_MISS (C(DTLB) | (C(OP_READ) << 8) | (C(RESULT_MISS) << 16))
+#define ITLB_LOAD_MISS (C(ITLB) | (C(OP_READ) << 8) | (C(RESULT_MISS) << 16))
+
+extern unsigned long itlb_miss_counter, dtlb_miss_counter;
+extern atomic_t instruction_counter;
+
+static atomic_t insn_ctr_ref;
+
+static s64 get_insn_ctr(void)
+{
+       int ctr;
+       unsigned long counta;
+
+       do {
+               ctr = atomic_read(&instruction_counter);
+               counta = mfspr(SPRN_COUNTA);
+       } while (ctr != atomic_read(&instruction_counter));
+
+       return ((s64)ctr << 16) | (counta >> 16);
+}
+
+static int event_type(struct perf_event *event)
+{
+       switch (event->attr.type) {
+       case PERF_TYPE_HARDWARE:
+               if (event->attr.config == PERF_COUNT_HW_CPU_CYCLES)
+                       return PERF_8xx_ID_CPU_CYCLES;
+               if (event->attr.config == PERF_COUNT_HW_INSTRUCTIONS)
+                       return PERF_8xx_ID_HW_INSTRUCTIONS;
+               break;
+       case PERF_TYPE_HW_CACHE:
+               if (event->attr.config == ITLB_LOAD_MISS)
+                       return PERF_8xx_ID_ITLB_LOAD_MISS;
+               if (event->attr.config == DTLB_LOAD_MISS)
+                       return PERF_8xx_ID_DTLB_LOAD_MISS;
+               break;
+       case PERF_TYPE_RAW:
+               break;
+       default:
+               return -ENOENT;
+       }
+       return -EOPNOTSUPP;
+}
+
+static int mpc8xx_pmu_event_init(struct perf_event *event)
+{
+       int type = event_type(event);
+
+       if (type < 0)
+               return type;
+       return 0;
+}
+
+static int mpc8xx_pmu_add(struct perf_event *event, int flags)
+{
+       int type = event_type(event);
+       s64 val = 0;
+
+       if (type < 0)
+               return type;
+
+       switch (type) {
+       case PERF_8xx_ID_CPU_CYCLES:
+               val = get_tb();
+               break;
+       case PERF_8xx_ID_HW_INSTRUCTIONS:
+               if (atomic_inc_return(&insn_ctr_ref) == 1)
+                       mtspr(SPRN_ICTRL, 0xc0080007);
+               val = get_insn_ctr();
+               break;
+       case PERF_8xx_ID_ITLB_LOAD_MISS:
+               val = itlb_miss_counter;
+               break;
+       case PERF_8xx_ID_DTLB_LOAD_MISS:
+               val = dtlb_miss_counter;
+               break;
+       }
+       local64_set(&event->hw.prev_count, val);
+       return 0;
+}
+
+static void mpc8xx_pmu_read(struct perf_event *event)
+{
+       int type = event_type(event);
+       s64 prev, val = 0, delta = 0;
+
+       if (type < 0)
+               return;
+
+       do {
+               prev = local64_read(&event->hw.prev_count);
+               switch (type) {
+               case PERF_8xx_ID_CPU_CYCLES:
+                       val = get_tb();
+                       delta = 16 * (val - prev);
+                       break;
+               case PERF_8xx_ID_HW_INSTRUCTIONS:
+                       val = get_insn_ctr();
+                       delta = prev - val;
+                       if (delta < 0)
+                               delta += 0x1000000000000LL;
+                       break;
+               case PERF_8xx_ID_ITLB_LOAD_MISS:
+                       val = itlb_miss_counter;
+                       delta = (s64)((s32)val - (s32)prev);
+                       break;
+               case PERF_8xx_ID_DTLB_LOAD_MISS:
+                       val = dtlb_miss_counter;
+                       delta = (s64)((s32)val - (s32)prev);
+                       break;
+               }
+       } while (local64_cmpxchg(&event->hw.prev_count, prev, val) != prev);
+
+       local64_add(delta, &event->count);
+}
+
+static void mpc8xx_pmu_del(struct perf_event *event, int flags)
+{
+       mpc8xx_pmu_read(event);
+       if (event_type(event) != PERF_8xx_ID_HW_INSTRUCTIONS)
+               return;
+
+       /* If it was the last user, stop counting to avoid useles overhead */
+       if (atomic_dec_return(&insn_ctr_ref) == 0)
+               mtspr(SPRN_ICTRL, 7);
+}
+
+static struct pmu mpc8xx_pmu = {
+       .event_init     = mpc8xx_pmu_event_init,
+       .add            = mpc8xx_pmu_add,
+       .del            = mpc8xx_pmu_del,
+       .read           = mpc8xx_pmu_read,
+       .capabilities   = PERF_PMU_CAP_NO_INTERRUPT |
+                         PERF_PMU_CAP_NO_NMI,
+};
+
+static int init_mpc8xx_pmu(void)
+{
+       mtspr(SPRN_ICTRL, 7);
+       mtspr(SPRN_CMPA, 0);
+       mtspr(SPRN_COUNTA, 0xffff);
+
+       return perf_pmu_register(&mpc8xx_pmu, "cpu", PERF_TYPE_RAW);
+}
+
+early_initcall(init_mpc8xx_pmu);
index f102d53701016fbf74246f291934e424020af65c..4d606b99a5cb94302a0a40d5ee2bb84d3319c6ba 100644 (file)
@@ -13,5 +13,7 @@ obj-$(CONFIG_FSL_EMB_PERF_EVENT_E500) += e500-pmu.o e6500-pmu.o
 
 obj-$(CONFIG_HV_PERF_CTRS) += hv-24x7.o hv-gpci.o hv-common.o
 
+obj-$(CONFIG_PPC_8xx_PERF_EVENT) += 8xx-pmu.o
+
 obj-$(CONFIG_PPC64)            += $(obj64-y)
 obj-$(CONFIG_PPC32)            += $(obj32-y)
index 270eb9b74e2e13eff5f37b441f76a37a019ff73e..595dd718ea8718b010fed1ca5c08f5f121f674c0 100644 (file)
@@ -57,6 +57,7 @@ struct cpu_hw_events {
        void                            *bhrb_context;
        struct  perf_branch_stack       bhrb_stack;
        struct  perf_branch_entry       bhrb_entries[BHRB_MAX_ENTRIES];
+       u64                             ic_init;
 };
 
 static DEFINE_PER_CPU(struct cpu_hw_events, cpu_hw_events);
@@ -127,6 +128,10 @@ static inline void power_pmu_bhrb_disable(struct perf_event *event) {}
 static void power_pmu_sched_task(struct perf_event_context *ctx, bool sched_in) {}
 static inline void power_pmu_bhrb_read(struct cpu_hw_events *cpuhw) {}
 static void pmao_restore_workaround(bool ebb) { }
+static bool use_ic(u64 event)
+{
+       return false;
+}
 #endif /* CONFIG_PPC32 */
 
 static bool regs_use_siar(struct pt_regs *regs)
@@ -243,7 +248,7 @@ static inline u32 perf_get_misc_flags(struct pt_regs *regs)
         */
        if (ppmu->flags & PPMU_NO_SIPR) {
                unsigned long siar = mfspr(SPRN_SIAR);
-               if (siar >= PAGE_OFFSET)
+               if (is_kernel_addr(siar))
                        return PERF_RECORD_MISC_KERNEL;
                return PERF_RECORD_MISC_USER;
        }
@@ -688,6 +693,15 @@ static void pmao_restore_workaround(bool ebb)
        mtspr(SPRN_PMC5, pmcs[4]);
        mtspr(SPRN_PMC6, pmcs[5]);
 }
+
+static bool use_ic(u64 event)
+{
+       if (cpu_has_feature(CPU_FTR_POWER9_DD1) &&
+                       (event == 0x200f2 || event == 0x300f2))
+               return true;
+
+       return false;
+}
 #endif /* CONFIG_PPC64 */
 
 static void perf_event_interrupt(struct pt_regs *regs);
@@ -1007,6 +1021,7 @@ static u64 check_and_compute_delta(u64 prev, u64 val)
 static void power_pmu_read(struct perf_event *event)
 {
        s64 val, delta, prev;
+       struct cpu_hw_events *cpuhw = this_cpu_ptr(&cpu_hw_events);
 
        if (event->hw.state & PERF_HES_STOPPED)
                return;
@@ -1016,6 +1031,13 @@ static void power_pmu_read(struct perf_event *event)
 
        if (is_ebb_event(event)) {
                val = read_pmc(event->hw.idx);
+               if (use_ic(event->attr.config)) {
+                       val = mfspr(SPRN_IC);
+                       if (val > cpuhw->ic_init)
+                               val = val - cpuhw->ic_init;
+                       else
+                               val = val + (0 - cpuhw->ic_init);
+               }
                local64_set(&event->hw.prev_count, val);
                return;
        }
@@ -1029,6 +1051,13 @@ static void power_pmu_read(struct perf_event *event)
                prev = local64_read(&event->hw.prev_count);
                barrier();
                val = read_pmc(event->hw.idx);
+               if (use_ic(event->attr.config)) {
+                       val = mfspr(SPRN_IC);
+                       if (val > cpuhw->ic_init)
+                               val = val - cpuhw->ic_init;
+                       else
+                               val = val + (0 - cpuhw->ic_init);
+               }
                delta = check_and_compute_delta(prev, val);
                if (!delta)
                        return;
@@ -1466,6 +1495,13 @@ nocheck:
                                        event->attr.branch_sample_type);
        }
 
+       /*
+        * Workaround for POWER9 DD1 to use the Instruction Counter
+        * register value for instruction counting
+        */
+       if (use_ic(event->attr.config))
+               cpuhw->ic_init = mfspr(SPRN_IC);
+
        perf_pmu_enable(event->pmu);
        local_irq_restore(flags);
        return ret;
index 50e598cf644b5968312c465407c68a52a3524400..e79fb5fb817dbe21cd19f633d89ca3bbbf51ad0c 100644 (file)
@@ -97,6 +97,28 @@ static unsigned long combine_shift(unsigned long pmc)
        return MMCR1_COMBINE_SHIFT(pmc);
 }
 
+static inline bool event_is_threshold(u64 event)
+{
+       return (event >> EVENT_THR_SEL_SHIFT) & EVENT_THR_SEL_MASK;
+}
+
+static bool is_thresh_cmp_valid(u64 event)
+{
+       unsigned int cmp, exp;
+
+       /*
+        * Check the mantissa upper two bits are not zero, unless the
+        * exponent is also zero. See the THRESH_CMP_MANTISSA doc.
+        */
+       cmp = (event >> EVENT_THR_CMP_SHIFT) & EVENT_THR_CMP_MASK;
+       exp = cmp >> 7;
+
+       if (exp && (cmp & 0x60) == 0)
+               return false;
+
+       return true;
+}
+
 int isa207_get_constraint(u64 event, unsigned long *maskp, unsigned long *valp)
 {
        unsigned int unit, pmc, cache, ebb;
@@ -163,28 +185,26 @@ int isa207_get_constraint(u64 event, unsigned long *maskp, unsigned long *valp)
                value |= CNST_SAMPLE_VAL(event >> EVENT_SAMPLE_SHIFT);
        }
 
-       /*
-        * Special case for PM_MRK_FAB_RSP_MATCH and PM_MRK_FAB_RSP_MATCH_CYC,
-        * the threshold control bits are used for the match value.
-        */
-       if (event_is_fab_match(event)) {
-               mask  |= CNST_FAB_MATCH_MASK;
-               value |= CNST_FAB_MATCH_VAL(event >> EVENT_THR_CTL_SHIFT);
+       if (cpu_has_feature(CPU_FTR_ARCH_300))  {
+               if (event_is_threshold(event) && is_thresh_cmp_valid(event)) {
+                       mask  |= CNST_THRESH_MASK;
+                       value |= CNST_THRESH_VAL(event >> EVENT_THRESH_SHIFT);
+               }
        } else {
                /*
-                * Check the mantissa upper two bits are not zero, unless the
-                * exponent is also zero. See the THRESH_CMP_MANTISSA doc.
+                * Special case for PM_MRK_FAB_RSP_MATCH and PM_MRK_FAB_RSP_MATCH_CYC,
+                * the threshold control bits are used for the match value.
                 */
-               unsigned int cmp, exp;
-
-               cmp = (event >> EVENT_THR_CMP_SHIFT) & EVENT_THR_CMP_MASK;
-               exp = cmp >> 7;
-
-               if (exp && (cmp & 0x60) == 0)
-                       return -1;
+               if (event_is_fab_match(event)) {
+                       mask  |= CNST_FAB_MATCH_MASK;
+                       value |= CNST_FAB_MATCH_VAL(event >> EVENT_THR_CTL_SHIFT);
+               } else {
+                       if (!is_thresh_cmp_valid(event))
+                               return -1;
 
-               mask  |= CNST_THRESH_MASK;
-               value |= CNST_THRESH_VAL(event >> EVENT_THRESH_SHIFT);
+                       mask  |= CNST_THRESH_MASK;
+                       value |= CNST_THRESH_VAL(event >> EVENT_THRESH_SHIFT);
+               }
        }
 
        if (!pmc && ebb)
@@ -279,7 +299,7 @@ int isa207_compute_mmcr(u64 event[], int n_ev,
                 * PM_MRK_FAB_RSP_MATCH and PM_MRK_FAB_RSP_MATCH_CYC,
                 * the threshold bits are used for the match value.
                 */
-               if (event_is_fab_match(event[i])) {
+               if (!cpu_has_feature(CPU_FTR_ARCH_300) && event_is_fab_match(event[i])) {
                        mmcr1 |= ((event[i] >> EVENT_THR_CTL_SHIFT) &
                                  EVENT_THR_CTL_MASK) << MMCR1_FAB_SHIFT;
                } else {
@@ -338,3 +358,39 @@ void isa207_disable_pmc(unsigned int pmc, unsigned long mmcr[])
        if (pmc <= 3)
                mmcr[1] &= ~(0xffUL << MMCR1_PMCSEL_SHIFT(pmc + 1));
 }
+
+static int find_alternative(u64 event, const unsigned int ev_alt[][MAX_ALT], int size)
+{
+       int i, j;
+
+       for (i = 0; i < size; ++i) {
+               if (event < ev_alt[i][0])
+                       break;
+
+               for (j = 0; j < MAX_ALT && ev_alt[i][j]; ++j)
+                       if (event == ev_alt[i][j])
+                               return i;
+       }
+
+       return -1;
+}
+
+int isa207_get_alternatives(u64 event, u64 alt[],
+                               const unsigned int ev_alt[][MAX_ALT], int size)
+{
+       int i, j, num_alt = 0;
+       u64 alt_event;
+
+       alt[num_alt++] = event;
+       i = find_alternative(event, ev_alt, size);
+       if (i >= 0) {
+               /* Filter out the original event, it's already in alt[0] */
+               for (j = 0; j < MAX_ALT; ++j) {
+                       alt_event = ev_alt[i][j];
+                       if (alt_event && alt_event != event)
+                               alt[num_alt++] = alt_event;
+               }
+       }
+
+       return num_alt;
+}
index 90495f1580c7d9f2001a0e9532a723fbea6b938c..cf9bd89901595cc38b793bc916a2096d873054eb 100644 (file)
        CNST_PMC_VAL(1) | CNST_PMC_VAL(2) | CNST_PMC_VAL(3) | \
        CNST_PMC_VAL(4) | CNST_PMC_VAL(5) | CNST_PMC_VAL(6) | CNST_NC_VAL
 
+/*
+ * Lets restrict use of PMC5 for instruction counting.
+ */
+#define P9_DD1_TEST_ADDER      (ISA207_TEST_ADDER | CNST_PMC_VAL(5))
 
 /* Bits in MMCR1 for PowerISA v2.07 */
 #define MMCR1_UNIT_SHIFT(pmc)          (60 - (4 * ((pmc) - 1)))
@@ -260,5 +264,8 @@ int isa207_compute_mmcr(u64 event[], int n_ev,
                                unsigned int hwc[], unsigned long mmcr[],
                                struct perf_event *pevents[]);
 void isa207_disable_pmc(unsigned int pmc, unsigned long mmcr[]);
+int isa207_get_alternatives(u64 event, u64 alt[],
+                               const unsigned int ev_alt[][MAX_ALT], int size);
+
 
 #endif
index d07186382f3a75b147bfe582563f98341f50ea7e..ce15b19a7962c1de92f2d32f1ef4626c90a804be 100644 (file)
@@ -48,43 +48,12 @@ static const unsigned int event_alternatives[][MAX_ALT] = {
        { PM_RUN_INST_CMPL_ALT,         PM_RUN_INST_CMPL },
 };
 
-/*
- * Scan the alternatives table for a match and return the
- * index into the alternatives table if found, else -1.
- */
-static int find_alternative(u64 event)
-{
-       int i, j;
-
-       for (i = 0; i < ARRAY_SIZE(event_alternatives); ++i) {
-               if (event < event_alternatives[i][0])
-                       break;
-
-               for (j = 0; j < MAX_ALT && event_alternatives[i][j]; ++j)
-                       if (event == event_alternatives[i][j])
-                               return i;
-       }
-
-       return -1;
-}
-
 static int power8_get_alternatives(u64 event, unsigned int flags, u64 alt[])
 {
        int i, j, num_alt = 0;
-       u64 alt_event;
-
-       alt[num_alt++] = event;
-
-       i = find_alternative(event);
-       if (i >= 0) {
-               /* Filter out the original event, it's already in alt[0] */
-               for (j = 0; j < MAX_ALT; ++j) {
-                       alt_event = event_alternatives[i][j];
-                       if (alt_event && alt_event != event)
-                               alt[num_alt++] = alt_event;
-               }
-       }
 
+       num_alt = isa207_get_alternatives(event, alt, event_alternatives,
+                                       (int)ARRAY_SIZE(event_alternatives));
        if (flags & PPMU_ONLY_COUNT_RUN) {
                /*
                 * We're only counting in RUN state, so PM_CYC is equivalent to
index 929b56d47ad9bf6bc79f7ae9dd0ab27b2142427d..71a6bfee5c027149b6dd1549abc795598fdbc685 100644 (file)
@@ -53,3 +53,6 @@ EVENT(PM_ITLB_MISS,                           0x400fc)
 EVENT(PM_RUN_INST_CMPL,                                0x500fa)
 /* Run_cycles */
 EVENT(PM_RUN_CYC,                              0x600f4)
+/* Instruction Dispatched */
+EVENT(PM_INST_DISP,                            0x200f2)
+EVENT(PM_INST_DISP_ALT,                                0x300f2)
index 7332634e18c95212f1448c578f2726b8ebf3aee0..7f6582708e0641121f5654cbb71bb6a75877b256 100644 (file)
@@ -22,7 +22,7 @@
  * | - - - - | - - - - | - - - - | - - - - | - - - - | - - - - | - - - - | - - - - |
  *   | | [ ]                       [ ] [      thresh_cmp     ]   [  thresh_ctl   ]
  *   | |  |                         |                                     |
- *   | |  *- IFM (Linux)            |    thresh start/stop OR FAB match -*
+ *   | |  *- IFM (Linux)            |                 thresh start/stop -*
  *   | *- BHRB (Linux)              *sm
  *   *- EBB (Linux)
  *
  * MMCR1[31]   = pmc4combine[1]
  *
  * if pmc == 3 and unit == 0 and pmcxsel[0:6] == 0b0101011
- *     # PM_MRK_FAB_RSP_MATCH
- *     MMCR1[20:27] = thresh_ctl   (FAB_CRESP_MATCH / FAB_TYPE_MATCH)
+ *     MMCR1[20:27] = thresh_ctl
  * else if pmc == 4 and unit == 0xf and pmcxsel[0:6] == 0b0101001
- *     # PM_MRK_FAB_RSP_MATCH_CYC
- *     MMCR1[20:27] = thresh_ctl   (FAB_CRESP_MATCH / FAB_TYPE_MATCH)
+ *     MMCR1[20:27] = thresh_ctl
  * else
  *     MMCRA[48:55] = thresh_ctl   (THRESH START/END)
  *
@@ -106,6 +104,21 @@ enum {
 /* PowerISA v2.07 format attribute structure*/
 extern struct attribute_group isa207_pmu_format_group;
 
+/* Table of alternatives, sorted by column 0 */
+static const unsigned int power9_event_alternatives[][MAX_ALT] = {
+       { PM_INST_DISP,                 PM_INST_DISP_ALT },
+};
+
+static int power9_get_alternatives(u64 event, unsigned int flags, u64 alt[])
+{
+       int num_alt = 0;
+
+       num_alt = isa207_get_alternatives(event, alt, power9_event_alternatives,
+                               (int)ARRAY_SIZE(power9_event_alternatives));
+
+       return num_alt;
+}
+
 GENERIC_EVENT_ATTR(cpu-cycles,                 PM_CYC);
 GENERIC_EVENT_ATTR(stalled-cycles-frontend,    PM_ICT_NOSLOT_CYC);
 GENERIC_EVENT_ATTR(stalled-cycles-backend,     PM_CMPLU_STALL);
@@ -213,6 +226,17 @@ static const struct attribute_group *power9_pmu_attr_groups[] = {
        NULL,
 };
 
+static int power9_generic_events_dd1[] = {
+       [PERF_COUNT_HW_CPU_CYCLES] =                    PM_CYC,
+       [PERF_COUNT_HW_STALLED_CYCLES_FRONTEND] =       PM_ICT_NOSLOT_CYC,
+       [PERF_COUNT_HW_STALLED_CYCLES_BACKEND] =        PM_CMPLU_STALL,
+       [PERF_COUNT_HW_INSTRUCTIONS] =                  PM_INST_DISP,
+       [PERF_COUNT_HW_BRANCH_INSTRUCTIONS] =           PM_BRU_CMPL,
+       [PERF_COUNT_HW_BRANCH_MISSES] =                 PM_BR_MPRED_CMPL,
+       [PERF_COUNT_HW_CACHE_REFERENCES] =              PM_LD_REF_L1,
+       [PERF_COUNT_HW_CACHE_MISSES] =                  PM_LD_MISS_L1_FIN,
+};
+
 static int power9_generic_events[] = {
        [PERF_COUNT_HW_CPU_CYCLES] =                    PM_CYC,
        [PERF_COUNT_HW_STALLED_CYCLES_FRONTEND] =       PM_ICT_NOSLOT_CYC,
@@ -383,10 +407,11 @@ static struct power_pmu power9_isa207_pmu = {
        .config_bhrb            = power9_config_bhrb,
        .bhrb_filter_map        = power9_bhrb_filter_map,
        .get_constraint         = isa207_get_constraint,
+       .get_alternatives       = power9_get_alternatives,
        .disable_pmc            = isa207_disable_pmc,
        .flags                  = PPMU_NO_SIAR | PPMU_ARCH_207S,
-       .n_generic              = ARRAY_SIZE(power9_generic_events),
-       .generic_events         = power9_generic_events,
+       .n_generic              = ARRAY_SIZE(power9_generic_events_dd1),
+       .generic_events         = power9_generic_events_dd1,
        .cache_events           = &power9_cache_events,
        .attr_groups            = power9_isa207_pmu_attr_groups,
        .bhrb_nr                = 32,
@@ -396,11 +421,12 @@ static struct power_pmu power9_pmu = {
        .name                   = "POWER9",
        .n_counter              = MAX_PMU_COUNTERS,
        .add_fields             = ISA207_ADD_FIELDS,
-       .test_adder             = ISA207_TEST_ADDER,
+       .test_adder             = P9_DD1_TEST_ADDER,
        .compute_mmcr           = isa207_compute_mmcr,
        .config_bhrb            = power9_config_bhrb,
        .bhrb_filter_map        = power9_bhrb_filter_map,
        .get_constraint         = isa207_get_constraint,
+       .get_alternatives       = power9_get_alternatives,
        .disable_pmc            = isa207_disable_pmc,
        .flags                  = PPMU_HAS_SIER | PPMU_ARCH_207S,
        .n_generic              = ARRAY_SIZE(power9_generic_events),
@@ -420,6 +446,11 @@ static int __init init_power9_pmu(void)
                return -ENODEV;
 
        if (cpu_has_feature(CPU_FTR_POWER9_DD1)) {
+               /*
+                * Since PM_INST_CMPL may not provide right counts in all
+                * sampling scenarios in power9 DD1, instead use PM_INST_DISP.
+                */
+               EVENT_VAR(PM_INST_CMPL, _g).id = PM_INST_DISP;
                rc = register_power_pmu(&power9_isa207_pmu);
        } else {
                rc = register_power_pmu(&power9_pmu);
index 7bc86dae9517654cc14a379c6022f56b05f00f9f..fe19dad568e2d2c4e01a798326db6169838ec200 100644 (file)
@@ -22,6 +22,7 @@ obj-$(CONFIG_P1022_RDK)   += p1022_rdk.o
 obj-$(CONFIG_P1023_RDB)   += p1023_rdb.o
 obj-$(CONFIG_TWR_P102x)   += twr_p102x.o
 obj-$(CONFIG_CORENET_GENERIC)   += corenet_generic.o
+obj-$(CONFIG_FB_FSL_DIU)       += t1042rdb_diu.o
 obj-$(CONFIG_STX_GP3)    += stx_gp3.o
 obj-$(CONFIG_TQM85xx)    += tqm85xx.o
 obj-$(CONFIG_SBC8548)     += sbc8548.o
index 6c0ba75fb2561f730908050c18afc35ebd45eb5f..ac191a7a133701cc2faf289edd59402c5cc8700b 100644 (file)
@@ -157,6 +157,7 @@ static const char * const boards[] __initconst = {
        "fsl,T1040RDB",
        "fsl,T1042RDB",
        "fsl,T1042RDB_PI",
+       "keymile,kmcent2",
        "keymile,kmcoge4",
        "varisys,CYRUS",
        NULL
diff --git a/arch/powerpc/platforms/85xx/t1042rdb_diu.c b/arch/powerpc/platforms/85xx/t1042rdb_diu.c
new file mode 100644 (file)
index 0000000..58fa3d3
--- /dev/null
@@ -0,0 +1,152 @@
+/*
+ * T1042 platform DIU operation
+ *
+ * Copyright 2014 Freescale Semiconductor Inc.
+ *
+ * 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/io.h>
+#include <linux/kernel.h>
+#include <linux/of.h>
+#include <linux/of_address.h>
+
+#include <sysdev/fsl_soc.h>
+
+/*DIU Pixel ClockCR offset in scfg*/
+#define CCSR_SCFG_PIXCLKCR      0x28
+
+/* DIU Pixel Clock bits of the PIXCLKCR */
+#define PIXCLKCR_PXCKEN                0x80000000
+#define PIXCLKCR_PXCKINV       0x40000000
+#define PIXCLKCR_PXCKDLY       0x0000FF00
+#define PIXCLKCR_PXCLK_MASK    0x00FF0000
+
+/* Some CPLD register definitions */
+#define CPLD_DIUCSR            0x16
+#define CPLD_DIUCSR_DVIEN      0x80
+#define CPLD_DIUCSR_BACKLIGHT  0x0f
+
+struct device_node *cpld_node;
+
+/**
+ * t1042rdb_set_monitor_port: switch the output to a different monitor port
+ */
+static void t1042rdb_set_monitor_port(enum fsl_diu_monitor_port port)
+{
+       static void __iomem *cpld_base;
+
+       cpld_base = of_iomap(cpld_node, 0);
+       if (!cpld_base) {
+               pr_err("%s: Could not map cpld registers\n", __func__);
+               goto exit;
+       }
+
+       switch (port) {
+       case FSL_DIU_PORT_DVI:
+               /* Enable the DVI(HDMI) port, disable the DFP and
+                * the backlight
+                */
+               clrbits8(cpld_base + CPLD_DIUCSR, CPLD_DIUCSR_DVIEN);
+               break;
+       case FSL_DIU_PORT_LVDS:
+               /*
+                * LVDS also needs backlight enabled, otherwise the display
+                * will be blank.
+                */
+               /* Enable the DFP port, disable the DVI*/
+               setbits8(cpld_base + CPLD_DIUCSR, 0x01 << 8);
+               setbits8(cpld_base + CPLD_DIUCSR, 0x01 << 4);
+               setbits8(cpld_base + CPLD_DIUCSR, CPLD_DIUCSR_BACKLIGHT);
+               break;
+       default:
+               pr_err("%s: Unsupported monitor port %i\n", __func__, port);
+       }
+
+       iounmap(cpld_base);
+exit:
+       of_node_put(cpld_node);
+}
+
+/**
+ * t1042rdb_set_pixel_clock: program the DIU's clock
+ * @pixclock: pixel clock in ps (pico seconds)
+ */
+static void t1042rdb_set_pixel_clock(unsigned int pixclock)
+{
+       struct device_node *scfg_np;
+       void __iomem *scfg;
+       unsigned long freq;
+       u64 temp;
+       u32 pxclk;
+
+       scfg_np = of_find_compatible_node(NULL, NULL, "fsl,t1040-scfg");
+       if (!scfg_np) {
+               pr_err("%s: Missing scfg node. Can not display video.\n",
+                      __func__);
+               return;
+       }
+
+       scfg = of_iomap(scfg_np, 0);
+       of_node_put(scfg_np);
+       if (!scfg) {
+               pr_err("%s: Could not map device. Can not display video.\n",
+                      __func__);
+               return;
+       }
+
+       /* Convert pixclock into frequency */
+       temp = 1000000000000ULL;
+       do_div(temp, pixclock);
+       freq = temp;
+
+       /*
+        * 'pxclk' is the ratio of the platform clock to the pixel clock.
+        * This number is programmed into the PIXCLKCR register, and the valid
+        * range of values is 2-255.
+        */
+       pxclk = DIV_ROUND_CLOSEST(fsl_get_sys_freq(), freq);
+       pxclk = clamp_t(u32, pxclk, 2, 255);
+
+       /* Disable the pixel clock, and set it to non-inverted and no delay */
+       clrbits32(scfg + CCSR_SCFG_PIXCLKCR,
+                 PIXCLKCR_PXCKEN | PIXCLKCR_PXCKDLY | PIXCLKCR_PXCLK_MASK);
+
+       /* Enable the clock and set the pxclk */
+       setbits32(scfg + CCSR_SCFG_PIXCLKCR, PIXCLKCR_PXCKEN | (pxclk << 16));
+
+       iounmap(scfg);
+}
+
+/**
+ * t1042rdb_valid_monitor_port: set the monitor port for sysfs
+ */
+static enum fsl_diu_monitor_port
+t1042rdb_valid_monitor_port(enum fsl_diu_monitor_port port)
+{
+       switch (port) {
+       case FSL_DIU_PORT_DVI:
+       case FSL_DIU_PORT_LVDS:
+               return port;
+       default:
+               return FSL_DIU_PORT_DVI; /* Dual-link LVDS is not supported */
+       }
+}
+
+static int __init t1042rdb_diu_init(void)
+{
+       cpld_node = of_find_compatible_node(NULL, NULL, "fsl,t1042rdb-cpld");
+       if (!cpld_node)
+               return 0;
+
+       diu_ops.set_monitor_port        = t1042rdb_set_monitor_port;
+       diu_ops.set_pixel_clock         = t1042rdb_set_pixel_clock;
+       diu_ops.valid_monitor_port      = t1042rdb_valid_monitor_port;
+
+       return 0;
+}
+
+early_initcall(t1042rdb_diu_init);
index 6e89e5a8d4fbfad10b724b010e5d95c9742b03a7..99b0ae8acb783399b47bbfaf7af1567c5b63d084 100644 (file)
@@ -172,6 +172,13 @@ config PPC_FPU
        bool
        default y if PPC64
 
+config PPC_8xx_PERF_EVENT
+       bool "PPC 8xx perf events"
+       depends on PPC_8xx && PERF_EVENTS
+       help
+         This is Performance Events support for PPC 8xx. The 8xx doesn't
+         have a PMU but some events are emulated using 8xx features.
+
 config FSL_EMB_PERFMON
        bool "Freescale Embedded Perfmon"
        depends on E500 || PPC_83xx
index e5ec1368f0cd7723a6f80c86fd5eadd516f8f6c0..ae2f740a82f1493df8a2e8283271d6bb09ac8836 100644 (file)
@@ -683,23 +683,13 @@ size_t spu_ibox_read(struct spu_context *ctx, u32 *data)
        return ctx->ops->ibox_read(ctx, data);
 }
 
-static int spufs_ibox_fasync(int fd, struct file *file, int on)
-{
-       struct spu_context *ctx = file->private_data;
-
-       return fasync_helper(fd, file, on, &ctx->ibox_fasync);
-}
-
 /* interrupt-level ibox callback function. */
 void spufs_ibox_callback(struct spu *spu)
 {
        struct spu_context *ctx = spu->ctx;
 
-       if (!ctx)
-               return;
-
-       wake_up_all(&ctx->ibox_wq);
-       kill_fasync(&ctx->ibox_fasync, SIGIO, POLLIN);
+       if (ctx)
+               wake_up_all(&ctx->ibox_wq);
 }
 
 /*
@@ -794,7 +784,6 @@ static const struct file_operations spufs_ibox_fops = {
        .open   = spufs_pipe_open,
        .read   = spufs_ibox_read,
        .poll   = spufs_ibox_poll,
-       .fasync = spufs_ibox_fasync,
        .llseek = no_llseek,
 };
 
@@ -832,26 +821,13 @@ size_t spu_wbox_write(struct spu_context *ctx, u32 data)
        return ctx->ops->wbox_write(ctx, data);
 }
 
-static int spufs_wbox_fasync(int fd, struct file *file, int on)
-{
-       struct spu_context *ctx = file->private_data;
-       int ret;
-
-       ret = fasync_helper(fd, file, on, &ctx->wbox_fasync);
-
-       return ret;
-}
-
 /* interrupt-level wbox callback function. */
 void spufs_wbox_callback(struct spu *spu)
 {
        struct spu_context *ctx = spu->ctx;
 
-       if (!ctx)
-               return;
-
-       wake_up_all(&ctx->wbox_wq);
-       kill_fasync(&ctx->wbox_fasync, SIGIO, POLLOUT);
+       if (ctx)
+               wake_up_all(&ctx->wbox_wq);
 }
 
 /*
@@ -944,7 +920,6 @@ static const struct file_operations spufs_wbox_fops = {
        .open   = spufs_pipe_open,
        .write  = spufs_wbox_write,
        .poll   = spufs_wbox_poll,
-       .fasync = spufs_wbox_fasync,
        .llseek = no_llseek,
 };
 
@@ -1520,28 +1495,8 @@ void spufs_mfc_callback(struct spu *spu)
 {
        struct spu_context *ctx = spu->ctx;
 
-       if (!ctx)
-               return;
-
-       wake_up_all(&ctx->mfc_wq);
-
-       pr_debug("%s %s\n", __func__, spu->name);
-       if (ctx->mfc_fasync) {
-               u32 free_elements, tagstatus;
-               unsigned int mask;
-
-               /* no need for spu_acquire in interrupt context */
-               free_elements = ctx->ops->get_mfc_free_elements(ctx);
-               tagstatus = ctx->ops->read_mfc_tagstatus(ctx);
-
-               mask = 0;
-               if (free_elements & 0xffff)
-                       mask |= POLLOUT;
-               if (tagstatus & ctx->tagwait)
-                       mask |= POLLIN;
-
-               kill_fasync(&ctx->mfc_fasync, SIGIO, mask);
-       }
+       if (ctx)
+               wake_up_all(&ctx->mfc_wq);
 }
 
 static int spufs_read_mfc_tagstatus(struct spu_context *ctx, u32 *status)
@@ -1803,13 +1758,6 @@ static int spufs_mfc_fsync(struct file *file, loff_t start, loff_t end, int data
        return err;
 }
 
-static int spufs_mfc_fasync(int fd, struct file *file, int on)
-{
-       struct spu_context *ctx = file->private_data;
-
-       return fasync_helper(fd, file, on, &ctx->mfc_fasync);
-}
-
 static const struct file_operations spufs_mfc_fops = {
        .open    = spufs_mfc_open,
        .release = spufs_mfc_release,
@@ -1818,7 +1766,6 @@ static const struct file_operations spufs_mfc_fops = {
        .poll    = spufs_mfc_poll,
        .flush   = spufs_mfc_flush,
        .fsync   = spufs_mfc_fsync,
-       .fasync  = spufs_mfc_fasync,
        .mmap    = spufs_mfc_mmap,
        .llseek  = no_llseek,
 };
index bcfd6f063efa7e64d4e361af002f6e858ff10620..aac7339660923d1fa7dd1a4104a21ee3557ea90f 100644 (file)
@@ -102,9 +102,6 @@ struct spu_context {
        wait_queue_head_t stop_wq;
        wait_queue_head_t mfc_wq;
        wait_queue_head_t run_wq;
-       struct fasync_struct *ibox_fasync;
-       struct fasync_struct *wbox_fasync;
-       struct fasync_struct *mfc_fasync;
        u32 tagwait;
        struct spu_context_ops *ops;
        struct work_struct reap_work;
index 604190cab5227c6fd8957baa00aa3ae6ca87a790..3a07e4dcf97c43d7a1bf619294ea94f37ff032dc 100644 (file)
@@ -5,7 +5,8 @@ config PPC_POWERNV
        select PPC_XICS
        select PPC_ICP_NATIVE
        select PPC_P7_NAP
-       select PPC_PCI_CHOICE if EMBEDDED
+       select PCI
+       select PCI_MSI
        select EPAPR_BOOT
        select PPC_INDIRECT_PIO
        select PPC_UDBG_16550
index e0f83c204ccc79f22cc591c76d9b23387b3ef210..6901a06da2f90bddf70386667eaea5c4fe3505a7 100644 (file)
@@ -1468,14 +1468,12 @@ void pnv_pci_sriov_disable(struct pci_dev *pdev)
        struct pnv_phb        *phb;
        struct pnv_ioda_pe    *pe;
        struct pci_dn         *pdn;
-       struct pci_sriov      *iov;
        u16                    num_vfs, i;
 
        bus = pdev->bus;
        hose = pci_bus_to_host(bus);
        phb = hose->private_data;
        pdn = pci_get_pdn(pdev);
-       iov = pdev->sriov;
        num_vfs = pdn->num_vfs;
 
        /* Release VF PEs */
index d3a81e746fc48c3d06b30728cc2c4164487f1b85..193e052fa0dd888fe62b0fc85ac3cb4669b2c249 100644 (file)
@@ -354,11 +354,17 @@ static int handle_dlpar_errorlog(struct pseries_hp_errorlog *hp_elog)
        switch (hp_elog->id_type) {
        case PSERIES_HP_ELOG_ID_DRC_COUNT:
                hp_elog->_drc_u.drc_count =
-                                       be32_to_cpu(hp_elog->_drc_u.drc_count);
+                               be32_to_cpu(hp_elog->_drc_u.drc_count);
                break;
        case PSERIES_HP_ELOG_ID_DRC_INDEX:
                hp_elog->_drc_u.drc_index =
-                                       be32_to_cpu(hp_elog->_drc_u.drc_index);
+                               be32_to_cpu(hp_elog->_drc_u.drc_index);
+               break;
+       case PSERIES_HP_ELOG_ID_DRC_IC:
+               hp_elog->_drc_u.ic.count =
+                               be32_to_cpu(hp_elog->_drc_u.ic.count);
+               hp_elog->_drc_u.ic.index =
+                               be32_to_cpu(hp_elog->_drc_u.ic.index);
        }
 
        switch (hp_elog->resource) {
@@ -467,7 +473,33 @@ static int dlpar_parse_id_type(char **cmd, struct pseries_hp_errorlog *hp_elog)
        if (!arg)
                return -EINVAL;
 
-       if (sysfs_streq(arg, "index")) {
+       if (sysfs_streq(arg, "indexed-count")) {
+               hp_elog->id_type = PSERIES_HP_ELOG_ID_DRC_IC;
+               arg = strsep(cmd, " ");
+               if (!arg) {
+                       pr_err("No DRC count specified.\n");
+                       return -EINVAL;
+               }
+
+               if (kstrtou32(arg, 0, &count)) {
+                       pr_err("Invalid DRC count specified.\n");
+                       return -EINVAL;
+               }
+
+               arg = strsep(cmd, " ");
+               if (!arg) {
+                       pr_err("No DRC Index specified.\n");
+                       return -EINVAL;
+               }
+
+               if (kstrtou32(arg, 0, &index)) {
+                       pr_err("Invalid DRC Index specified.\n");
+                       return -EINVAL;
+               }
+
+               hp_elog->_drc_u.ic.count = cpu_to_be32(count);
+               hp_elog->_drc_u.ic.index = cpu_to_be32(index);
+       } else if (sysfs_streq(arg, "index")) {
                hp_elog->id_type = PSERIES_HP_ELOG_ID_DRC_INDEX;
                arg = strsep(cmd, " ");
                if (!arg) {
index 3381c20edbc0af692fefae655e1bc196b8e484b8..e104c71ea44ab5bf715fa5720c0a1ed47c6221c7 100644 (file)
@@ -320,6 +320,19 @@ static int dlpar_remove_device_tree_lmb(struct of_drconf_cell *lmb)
        return dlpar_update_device_tree_lmb(lmb);
 }
 
+static struct memory_block *lmb_to_memblock(struct of_drconf_cell *lmb)
+{
+       unsigned long section_nr;
+       struct mem_section *mem_sect;
+       struct memory_block *mem_block;
+
+       section_nr = pfn_to_section_nr(PFN_DOWN(lmb->base_addr));
+       mem_sect = __nr_to_section(section_nr);
+
+       mem_block = find_memory_block(mem_sect);
+       return mem_block;
+}
+
 #ifdef CONFIG_MEMORY_HOTREMOVE
 static int pseries_remove_memblock(unsigned long base, unsigned int memblock_size)
 {
@@ -407,19 +420,6 @@ static bool lmb_is_removable(struct of_drconf_cell *lmb)
 
 static int dlpar_add_lmb(struct of_drconf_cell *);
 
-static struct memory_block *lmb_to_memblock(struct of_drconf_cell *lmb)
-{
-       unsigned long section_nr;
-       struct mem_section *mem_sect;
-       struct memory_block *mem_block;
-
-       section_nr = pfn_to_section_nr(PFN_DOWN(lmb->base_addr));
-       mem_sect = __nr_to_section(section_nr);
-
-       mem_block = find_memory_block(mem_sect);
-       return mem_block;
-}
-
 static int dlpar_remove_lmb(struct of_drconf_cell *lmb)
 {
        struct memory_block *mem_block;
@@ -601,6 +601,94 @@ static int dlpar_memory_readd_by_index(u32 drc_index, struct property *prop)
 
        return rc;
 }
+
+static int dlpar_memory_remove_by_ic(u32 lmbs_to_remove, u32 drc_index,
+                                    struct property *prop)
+{
+       struct of_drconf_cell *lmbs;
+       u32 num_lmbs, *p;
+       int i, rc, start_lmb_found;
+       int lmbs_available = 0, start_index = 0, end_index;
+
+       pr_info("Attempting to hot-remove %u LMB(s) at %x\n",
+               lmbs_to_remove, drc_index);
+
+       if (lmbs_to_remove == 0)
+               return -EINVAL;
+
+       p = prop->value;
+       num_lmbs = *p++;
+       lmbs = (struct of_drconf_cell *)p;
+       start_lmb_found = 0;
+
+       /* Navigate to drc_index */
+       while (start_index < num_lmbs) {
+               if (lmbs[start_index].drc_index == drc_index) {
+                       start_lmb_found = 1;
+                       break;
+               }
+
+               start_index++;
+       }
+
+       if (!start_lmb_found)
+               return -EINVAL;
+
+       end_index = start_index + lmbs_to_remove;
+
+       /* Validate that there are enough LMBs to satisfy the request */
+       for (i = start_index; i < end_index; i++) {
+               if (lmbs[i].flags & DRCONF_MEM_RESERVED)
+                       break;
+
+               lmbs_available++;
+       }
+
+       if (lmbs_available < lmbs_to_remove)
+               return -EINVAL;
+
+       for (i = start_index; i < end_index; i++) {
+               if (!(lmbs[i].flags & DRCONF_MEM_ASSIGNED))
+                       continue;
+
+               rc = dlpar_remove_lmb(&lmbs[i]);
+               if (rc)
+                       break;
+
+               lmbs[i].reserved = 1;
+       }
+
+       if (rc) {
+               pr_err("Memory indexed-count-remove failed, adding any removed LMBs\n");
+
+               for (i = start_index; i < end_index; i++) {
+                       if (!lmbs[i].reserved)
+                               continue;
+
+                       rc = dlpar_add_lmb(&lmbs[i]);
+                       if (rc)
+                               pr_err("Failed to add LMB, drc index %x\n",
+                                      be32_to_cpu(lmbs[i].drc_index));
+
+                       lmbs[i].reserved = 0;
+               }
+               rc = -EINVAL;
+       } else {
+               for (i = start_index; i < end_index; i++) {
+                       if (!lmbs[i].reserved)
+                               continue;
+
+                       dlpar_release_drc(lmbs[i].drc_index);
+                       pr_info("Memory at %llx (drc index %x) was hot-removed\n",
+                               lmbs[i].base_addr, lmbs[i].drc_index);
+
+                       lmbs[i].reserved = 0;
+               }
+       }
+
+       return rc;
+}
+
 #else
 static inline int pseries_remove_memblock(unsigned long base,
                                          unsigned int memblock_size)
@@ -628,9 +716,32 @@ static int dlpar_memory_remove_by_index(u32 drc_index, struct property *prop)
 {
        return -EOPNOTSUPP;
 }
+static int dlpar_memory_readd_by_index(u32 drc_index, struct property *prop)
+{
+       return -EOPNOTSUPP;
+}
 
+static int dlpar_memory_remove_by_ic(u32 lmbs_to_remove, u32 drc_index,
+                                    struct property *prop)
+{
+       return -EOPNOTSUPP;
+}
 #endif /* CONFIG_MEMORY_HOTREMOVE */
 
+static int dlpar_online_lmb(struct of_drconf_cell *lmb)
+{
+       struct memory_block *mem_block;
+       int rc;
+
+       mem_block = lmb_to_memblock(lmb);
+       if (!mem_block)
+               return -EINVAL;
+
+       rc = device_online(&mem_block->dev);
+       put_device(&mem_block->dev);
+       return rc;
+}
+
 static int dlpar_add_lmb(struct of_drconf_cell *lmb)
 {
        unsigned long block_sz;
@@ -654,10 +765,18 @@ static int dlpar_add_lmb(struct of_drconf_cell *lmb)
 
        /* Add the memory */
        rc = add_memory(nid, lmb->base_addr, block_sz);
-       if (rc)
+       if (rc) {
                dlpar_remove_device_tree_lmb(lmb);
-       else
+               return rc;
+       }
+
+       rc = dlpar_online_lmb(lmb);
+       if (rc) {
+               remove_memory(nid, lmb->base_addr, block_sz);
+               dlpar_remove_device_tree_lmb(lmb);
+       } else {
                lmb->flags |= DRCONF_MEM_ASSIGNED;
+       }
 
        return rc;
 }
@@ -776,6 +895,97 @@ static int dlpar_memory_add_by_index(u32 drc_index, struct property *prop)
        return rc;
 }
 
+static int dlpar_memory_add_by_ic(u32 lmbs_to_add, u32 drc_index,
+                                 struct property *prop)
+{
+       struct of_drconf_cell *lmbs;
+       u32 num_lmbs, *p;
+       int i, rc, start_lmb_found;
+       int lmbs_available = 0, start_index = 0, end_index;
+
+       pr_info("Attempting to hot-add %u LMB(s) at index %x\n",
+               lmbs_to_add, drc_index);
+
+       if (lmbs_to_add == 0)
+               return -EINVAL;
+
+       p = prop->value;
+       num_lmbs = *p++;
+       lmbs = (struct of_drconf_cell *)p;
+       start_lmb_found = 0;
+
+       /* Navigate to drc_index */
+       while (start_index < num_lmbs) {
+               if (lmbs[start_index].drc_index == drc_index) {
+                       start_lmb_found = 1;
+                       break;
+               }
+
+               start_index++;
+       }
+
+       if (!start_lmb_found)
+               return -EINVAL;
+
+       end_index = start_index + lmbs_to_add;
+
+       /* Validate that the LMBs in this range are not reserved */
+       for (i = start_index; i < end_index; i++) {
+               if (lmbs[i].flags & DRCONF_MEM_RESERVED)
+                       break;
+
+               lmbs_available++;
+       }
+
+       if (lmbs_available < lmbs_to_add)
+               return -EINVAL;
+
+       for (i = start_index; i < end_index; i++) {
+               if (lmbs[i].flags & DRCONF_MEM_ASSIGNED)
+                       continue;
+
+               rc = dlpar_acquire_drc(lmbs[i].drc_index);
+               if (rc)
+                       break;
+
+               rc = dlpar_add_lmb(&lmbs[i]);
+               if (rc) {
+                       dlpar_release_drc(lmbs[i].drc_index);
+                       break;
+               }
+
+               lmbs[i].reserved = 1;
+       }
+
+       if (rc) {
+               pr_err("Memory indexed-count-add failed, removing any added LMBs\n");
+
+               for (i = start_index; i < end_index; i++) {
+                       if (!lmbs[i].reserved)
+                               continue;
+
+                       rc = dlpar_remove_lmb(&lmbs[i]);
+                       if (rc)
+                               pr_err("Failed to remove LMB, drc index %x\n",
+                                      be32_to_cpu(lmbs[i].drc_index));
+                       else
+                               dlpar_release_drc(lmbs[i].drc_index);
+               }
+               rc = -EINVAL;
+       } else {
+               for (i = start_index; i < end_index; i++) {
+                       if (!lmbs[i].reserved)
+                               continue;
+
+                       pr_info("Memory at %llx (drc index %x) was hot-added\n",
+                               lmbs[i].base_addr, lmbs[i].drc_index);
+                       lmbs[i].reserved = 0;
+               }
+       }
+
+       return rc;
+}
+
 int dlpar_memory(struct pseries_hp_errorlog *hp_elog)
 {
        struct device_node *dn;
@@ -783,9 +993,6 @@ int dlpar_memory(struct pseries_hp_errorlog *hp_elog)
        u32 count, drc_index;
        int rc;
 
-       count = hp_elog->_drc_u.drc_count;
-       drc_index = hp_elog->_drc_u.drc_index;
-
        lock_device_hotplug();
 
        dn = of_find_node_by_path("/ibm,dynamic-reconfiguration-memory");
@@ -802,22 +1009,39 @@ int dlpar_memory(struct pseries_hp_errorlog *hp_elog)
 
        switch (hp_elog->action) {
        case PSERIES_HP_ELOG_ACTION_ADD:
-               if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_COUNT)
+               if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_COUNT) {
+                       count = hp_elog->_drc_u.drc_count;
                        rc = dlpar_memory_add_by_count(count, prop);
-               else if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_INDEX)
+               } else if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_INDEX) {
+                       drc_index = hp_elog->_drc_u.drc_index;
                        rc = dlpar_memory_add_by_index(drc_index, prop);
-               else
+               } else if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_IC) {
+                       count = hp_elog->_drc_u.ic.count;
+                       drc_index = hp_elog->_drc_u.ic.index;
+                       rc = dlpar_memory_add_by_ic(count, drc_index, prop);
+               } else {
                        rc = -EINVAL;
+               }
+
                break;
        case PSERIES_HP_ELOG_ACTION_REMOVE:
-               if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_COUNT)
+               if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_COUNT) {
+                       count = hp_elog->_drc_u.drc_count;
                        rc = dlpar_memory_remove_by_count(count, prop);
-               else if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_INDEX)
+               } else if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_INDEX) {
+                       drc_index = hp_elog->_drc_u.drc_index;
                        rc = dlpar_memory_remove_by_index(drc_index, prop);
-               else
+               } else if (hp_elog->id_type == PSERIES_HP_ELOG_ID_DRC_IC) {
+                       count = hp_elog->_drc_u.ic.count;
+                       drc_index = hp_elog->_drc_u.ic.index;
+                       rc = dlpar_memory_remove_by_ic(count, drc_index, prop);
+               } else {
                        rc = -EINVAL;
+               }
+
                break;
        case PSERIES_HP_ELOG_ACTION_READD:
+               drc_index = hp_elog->_drc_u.drc_index;
                rc = dlpar_memory_readd_by_index(drc_index, prop);
                break;
        default:
index ee98917341496905876dadc6e51cdfd4b9ced815..31db8c072acd03b80dcf177c842273d508409d0a 100644 (file)
@@ -1,6 +1,5 @@
 /* ppc-dis.c -- Disassemble PowerPC instructions
-   Copyright 1994, 1995, 2000, 2001, 2002, 2003, 2004, 2005, 2006
-   Free Software Foundation, Inc.
+   Copyright (C) 1994-2016 Free Software Foundation, Inc.
    Written by Ian Lance Taylor, Cygnus Support
 
 This file is part of GDB, GAS, and the GNU binutils.
@@ -26,57 +25,94 @@ Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, US
 #include "ppc.h"
 #include "dis-asm.h"
 
-/* Print a PowerPC or POWER instruction.  */
+/* This file provides several disassembler functions, all of which use
+   the disassembler interface defined in dis-asm.h.  Several functions
+   are provided because this file handles disassembly for the PowerPC
+   in both big and little endian mode and also for the POWER (RS/6000)
+   chip.  */
+
+/* Extract the operand value from the PowerPC or POWER instruction.  */
 
-int
-print_insn_powerpc (unsigned long insn, unsigned long memaddr)
+static long
+operand_value_powerpc (const struct powerpc_operand *operand,
+                      unsigned long insn, ppc_cpu_t dialect)
 {
-  const struct powerpc_opcode *opcode;
-  const struct powerpc_opcode *opcode_end;
-  unsigned long op;
-  int dialect;
+  long value;
+  int invalid;
+  /* Extract the value from the instruction.  */
+  if (operand->extract)
+    value = (*operand->extract) (insn, dialect, &invalid);
+  else
+    {
+      if (operand->shift >= 0)
+       value = (insn >> operand->shift) & operand->bitm;
+      else
+       value = (insn << -operand->shift) & operand->bitm;
+      if ((operand->flags & PPC_OPERAND_SIGNED) != 0)
+       {
+         /* BITM is always some number of zeros followed by some
+            number of ones, followed by some number of zeros.  */
+         unsigned long top = operand->bitm;
+         /* top & -top gives the rightmost 1 bit, so this
+            fills in any trailing zeros.  */
+         top |= (top & -top) - 1;
+         top &= ~(top >> 1);
+         value = (value ^ top) - top;
+       }
+    }
 
-  dialect = PPC_OPCODE_PPC | PPC_OPCODE_CLASSIC | PPC_OPCODE_COMMON
-             | PPC_OPCODE_64 | PPC_OPCODE_POWER4 | PPC_OPCODE_ALTIVEC;
+  return value;
+}
 
-  if (cpu_has_feature(CPU_FTRS_POWER5))
-    dialect |= PPC_OPCODE_POWER5;
+/* Determine whether the optional operand(s) should be printed.  */
 
-  if (cpu_has_feature(CPU_FTRS_CELL))
-    dialect |= PPC_OPCODE_CELL | PPC_OPCODE_ALTIVEC;
+static int
+skip_optional_operands (const unsigned char *opindex,
+                       unsigned long insn, ppc_cpu_t dialect)
+{
+  const struct powerpc_operand *operand;
 
-  if (cpu_has_feature(CPU_FTRS_POWER6))
-    dialect |= PPC_OPCODE_POWER5 | PPC_OPCODE_POWER6 | PPC_OPCODE_ALTIVEC;
+  for (; *opindex != 0; opindex++)
+    {
+      operand = &powerpc_operands[*opindex];
+      if ((operand->flags & PPC_OPERAND_NEXT) != 0
+         || ((operand->flags & PPC_OPERAND_OPTIONAL) != 0
+             && operand_value_powerpc (operand, insn, dialect) !=
+                ppc_optional_operand_value (operand)))
+       return 0;
+    }
+
+  return 1;
+}
+
+/* Find a match for INSN in the opcode table, given machine DIALECT.
+   A DIALECT of -1 is special, matching all machine opcode variations.  */
+
+static const struct powerpc_opcode *
+lookup_powerpc (unsigned long insn, ppc_cpu_t dialect)
+{
+  const struct powerpc_opcode *opcode;
+  const struct powerpc_opcode *opcode_end;
+  unsigned long op;
 
   /* Get the major opcode of the instruction.  */
   op = PPC_OP (insn);
 
-  /* Find the first match in the opcode table.  We could speed this up
-     a bit by doing a binary search on the major opcode.  */
   opcode_end = powerpc_opcodes + powerpc_num_opcodes;
- again:
-  for (opcode = powerpc_opcodes; opcode < opcode_end; opcode++)
+  /* Find the first match in the opcode table for this major opcode.  */
+  for (opcode = powerpc_opcodes; opcode < opcode_end; ++opcode)
     {
-      unsigned long table_op;
       const unsigned char *opindex;
       const struct powerpc_operand *operand;
       int invalid;
-      int need_comma;
-      int need_paren;
-
-      table_op = PPC_OP (opcode->opcode);
-      if (op < table_op)
-       break;
-      if (op > table_op)
-       continue;
 
       if ((insn & opcode->mask) != opcode->opcode
-         || (opcode->flags & dialect) == 0)
+         || (dialect != (ppc_cpu_t) -1
+             && ((opcode->flags & dialect) == 0
+                 || (opcode->deprecated & dialect) != 0)))
        continue;
 
-      /* Make two passes over the operands.  First see if any of them
-        have extraction functions, and, if they do, make sure the
-        instruction is valid.  */
+      /* Check validity of operands.  */
       invalid = 0;
       for (opindex = opcode->operands; *opindex != 0; opindex++)
        {
@@ -87,14 +123,77 @@ print_insn_powerpc (unsigned long insn, unsigned long memaddr)
       if (invalid)
        continue;
 
-      /* The instruction is valid.  */
-      printf("%s", opcode->name);
+      return opcode;
+    }
+
+  return NULL;
+}
+
+/* Print a PowerPC or POWER instruction.  */
+
+int print_insn_powerpc (unsigned long insn, unsigned long memaddr)
+{
+  const struct powerpc_opcode *opcode;
+  bool insn_is_short;
+  ppc_cpu_t dialect;
+
+  dialect = PPC_OPCODE_PPC | PPC_OPCODE_COMMON
+            | PPC_OPCODE_64 | PPC_OPCODE_POWER4 | PPC_OPCODE_ALTIVEC;
+
+  if (cpu_has_feature(CPU_FTRS_POWER5))
+    dialect |= PPC_OPCODE_POWER5;
+
+  if (cpu_has_feature(CPU_FTRS_CELL))
+    dialect |= (PPC_OPCODE_CELL | PPC_OPCODE_ALTIVEC);
+
+  if (cpu_has_feature(CPU_FTRS_POWER6))
+    dialect |= (PPC_OPCODE_POWER5 | PPC_OPCODE_POWER6 | PPC_OPCODE_ALTIVEC);
+
+  if (cpu_has_feature(CPU_FTRS_POWER7))
+    dialect |= (PPC_OPCODE_POWER5 | PPC_OPCODE_POWER6 | PPC_OPCODE_POWER7
+                | PPC_OPCODE_ALTIVEC | PPC_OPCODE_VSX);
+
+  if (cpu_has_feature(CPU_FTRS_POWER8))
+    dialect |= (PPC_OPCODE_POWER5 | PPC_OPCODE_POWER6 | PPC_OPCODE_POWER7
+               | PPC_OPCODE_POWER8 | PPC_OPCODE_HTM
+               | PPC_OPCODE_ALTIVEC | PPC_OPCODE_ALTIVEC2 | PPC_OPCODE_VSX);
+
+  if (cpu_has_feature(CPU_FTRS_POWER9))
+    dialect |= (PPC_OPCODE_POWER5 | PPC_OPCODE_POWER6 | PPC_OPCODE_POWER7
+               | PPC_OPCODE_POWER8 | PPC_OPCODE_POWER9 | PPC_OPCODE_HTM
+               | PPC_OPCODE_ALTIVEC | PPC_OPCODE_ALTIVEC2
+               | PPC_OPCODE_VSX | PPC_OPCODE_VSX3),
+
+  /* Get the major opcode of the insn.  */
+  opcode = NULL;
+  insn_is_short = false;
+
+  if (opcode == NULL)
+    opcode = lookup_powerpc (insn, dialect);
+  if (opcode == NULL && (dialect & PPC_OPCODE_ANY) != 0)
+    opcode = lookup_powerpc (insn, (ppc_cpu_t) -1);
+
+  if (opcode != NULL)
+    {
+      const unsigned char *opindex;
+      const struct powerpc_operand *operand;
+      int need_comma;
+      int need_paren;
+      int skip_optional;
+
       if (opcode->operands[0] != 0)
-       printf("\t");
+       printf("%-7s ", opcode->name);
+      else
+       printf("%s", opcode->name);
+
+      if (insn_is_short)
+        /* The operands will be fetched out of the 16-bit instruction.  */
+        insn >>= 16;
 
       /* Now extract and print the operands.  */
       need_comma = 0;
       need_paren = 0;
+      skip_optional = -1;
       for (opindex = opcode->operands; *opindex != 0; opindex++)
        {
          long value;
@@ -107,23 +206,18 @@ print_insn_powerpc (unsigned long insn, unsigned long memaddr)
          if ((operand->flags & PPC_OPERAND_FAKE) != 0)
            continue;
 
-         /* Extract the value from the instruction.  */
-         if (operand->extract)
-           value = (*operand->extract) (insn, dialect, &invalid);
-         else
+         /* If all of the optional operands have the value zero,
+            then don't print any of them.  */
+         if ((operand->flags & PPC_OPERAND_OPTIONAL) != 0)
            {
-             value = (insn >> operand->shift) & ((1 << operand->bits) - 1);
-             if ((operand->flags & PPC_OPERAND_SIGNED) != 0
-                 && (value & (1 << (operand->bits - 1))) != 0)
-               value -= 1 << operand->bits;
+             if (skip_optional < 0)
+               skip_optional = skip_optional_operands (opindex, insn,
+                                                       dialect);
+             if (skip_optional)
+               continue;
            }
 
-         /* If the operand is optional, and the value is zero, don't
-            print anything.  */
-         if ((operand->flags & PPC_OPERAND_OPTIONAL) != 0
-             && (operand->flags & PPC_OPERAND_NEXT) == 0
-             && value == 0)
-           continue;
+         value = operand_value_powerpc (operand, insn, dialect);
 
          if (need_comma)
            {
@@ -139,30 +233,38 @@ print_insn_powerpc (unsigned long insn, unsigned long memaddr)
            printf("f%ld", value);
          else if ((operand->flags & PPC_OPERAND_VR) != 0)
            printf("v%ld", value);
+         else if ((operand->flags & PPC_OPERAND_VSR) != 0)
+           printf("vs%ld", value);
          else if ((operand->flags & PPC_OPERAND_RELATIVE) != 0)
-           print_address (memaddr + value);
+           print_address(memaddr + value);
          else if ((operand->flags & PPC_OPERAND_ABSOLUTE) != 0)
-           print_address (value & 0xffffffff);
-         else if ((operand->flags & PPC_OPERAND_CR) == 0
-                  || (dialect & PPC_OPCODE_PPC) == 0)
+           print_address(value & 0xffffffff);
+         else if ((operand->flags & PPC_OPERAND_FSL) != 0)
+           printf("fsl%ld", value);
+         else if ((operand->flags & PPC_OPERAND_FCR) != 0)
+           printf("fcr%ld", value);
+         else if ((operand->flags & PPC_OPERAND_UDI) != 0)
            printf("%ld", value);
-         else
+         else if ((operand->flags & PPC_OPERAND_CR_REG) != 0
+                  && (((dialect & PPC_OPCODE_PPC) != 0)
+                      || ((dialect & PPC_OPCODE_VLE) != 0)))
+           printf("cr%ld", value);
+         else if (((operand->flags & PPC_OPERAND_CR_BIT) != 0)
+                  && (((dialect & PPC_OPCODE_PPC) != 0)
+                      || ((dialect & PPC_OPCODE_VLE) != 0)))
            {
-             if (operand->bits == 3)
-               printf("cr%ld", value);
-             else
-               {
-                 static const char *cbnames[4] = { "lt", "gt", "eq", "so" };
-                 int cr;
-                 int cc;
-
-                 cr = value >> 2;
-                 if (cr != 0)
-                   printf("4*cr%d+", cr);
-                 cc = value & 3;
-                 printf("%s", cbnames[cc]);
-               }
+             static const char *cbnames[4] = { "lt", "gt", "eq", "so" };
+             int cr;
+             int cc;
+
+             cr = value >> 2;
+             if (cr != 0)
+               printf("4*cr%d+", cr);
+             cc = value & 3;
+             printf("%s", cbnames[cc]);
            }
+         else
+           printf("%d", (int) value);
 
          if (need_paren)
            {
@@ -179,14 +281,16 @@ print_insn_powerpc (unsigned long insn, unsigned long memaddr)
            }
        }
 
-      /* We have found and printed an instruction; return.  */
-      return 4;
-    }
-
-  if ((dialect & PPC_OPCODE_ANY) != 0)
-    {
-      dialect = ~PPC_OPCODE_ANY;
-      goto again;
+      /* We have found and printed an instruction.
+         If it was a short VLE instruction we have more to do.  */
+      if (insn_is_short)
+        {
+          memaddr += 2;
+          return 2;
+        }
+      else
+        /* Otherwise, return.  */
+        return 4;
     }
 
   /* We could not find a match.  */
index 954dbf8222d71098f95d21aa4ce98184199cef79..ac2b55b1332ed2fcc8573f44d268e3fad85ca84b 100644 (file)
@@ -1,6 +1,5 @@
 /* ppc-opc.c -- PowerPC opcode list
-   Copyright 1994, 1995, 1996, 1997, 1998, 2000, 2001, 2002, 2003, 2004,
-   2005 Free Software Foundation, Inc.
+   Copyright (C) 1994-2016 Free Software Foundation, Inc.
    Written by Ian Lance Taylor, Cygnus Support
 
    This file is part of GDB, GAS, and the GNU binutils.
 \f
 /* Local insertion and extraction functions.  */
 
-static unsigned long insert_bat (unsigned long, long, int, const char **);
-static long extract_bat (unsigned long, int, int *);
-static unsigned long insert_bba (unsigned long, long, int, const char **);
-static long extract_bba (unsigned long, int, int *);
-static unsigned long insert_bd (unsigned long, long, int, const char **);
-static long extract_bd (unsigned long, int, int *);
-static unsigned long insert_bdm (unsigned long, long, int, const char **);
-static long extract_bdm (unsigned long, int, int *);
-static unsigned long insert_bdp (unsigned long, long, int, const char **);
-static long extract_bdp (unsigned long, int, int *);
-static unsigned long insert_bo (unsigned long, long, int, const char **);
-static long extract_bo (unsigned long, int, int *);
-static unsigned long insert_boe (unsigned long, long, int, const char **);
-static long extract_boe (unsigned long, int, int *);
-static unsigned long insert_dq (unsigned long, long, int, const char **);
-static long extract_dq (unsigned long, int, int *);
-static unsigned long insert_ds (unsigned long, long, int, const char **);
-static long extract_ds (unsigned long, int, int *);
-static unsigned long insert_de (unsigned long, long, int, const char **);
-static long extract_de (unsigned long, int, int *);
-static unsigned long insert_des (unsigned long, long, int, const char **);
-static long extract_des (unsigned long, int, int *);
-static unsigned long insert_fxm (unsigned long, long, int, const char **);
-static long extract_fxm (unsigned long, int, int *);
-static unsigned long insert_li (unsigned long, long, int, const char **);
-static long extract_li (unsigned long, int, int *);
-static unsigned long insert_mbe (unsigned long, long, int, const char **);
-static long extract_mbe (unsigned long, int, int *);
-static unsigned long insert_mb6 (unsigned long, long, int, const char **);
-static long extract_mb6 (unsigned long, int, int *);
-static unsigned long insert_nb (unsigned long, long, int, const char **);
-static long extract_nb (unsigned long, int, int *);
-static unsigned long insert_nsi (unsigned long, long, int, const char **);
-static long extract_nsi (unsigned long, int, int *);
-static unsigned long insert_ral (unsigned long, long, int, const char **);
-static unsigned long insert_ram (unsigned long, long, int, const char **);
-static unsigned long insert_raq (unsigned long, long, int, const char **);
-static unsigned long insert_ras (unsigned long, long, int, const char **);
-static unsigned long insert_rbs (unsigned long, long, int, const char **);
-static long extract_rbs (unsigned long, int, int *);
-static unsigned long insert_rsq (unsigned long, long, int, const char **);
-static unsigned long insert_rtq (unsigned long, long, int, const char **);
-static unsigned long insert_sh6 (unsigned long, long, int, const char **);
-static long extract_sh6 (unsigned long, int, int *);
-static unsigned long insert_spr (unsigned long, long, int, const char **);
-static long extract_spr (unsigned long, int, int *);
-static unsigned long insert_sprg (unsigned long, long, int, const char **);
-static long extract_sprg (unsigned long, int, int *);
-static unsigned long insert_tbr (unsigned long, long, int, const char **);
-static long extract_tbr (unsigned long, int, int *);
-static unsigned long insert_ev2 (unsigned long, long, int, const char **);
-static long extract_ev2 (unsigned long, int, int *);
-static unsigned long insert_ev4 (unsigned long, long, int, const char **);
-static long extract_ev4 (unsigned long, int, int *);
-static unsigned long insert_ev8 (unsigned long, long, int, const char **);
-static long extract_ev8 (unsigned long, int, int *);
+static unsigned long insert_arx (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_arx (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_ary (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_ary (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_bat (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_bat (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_bba (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_bba (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_bdm (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_bdm (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_bdp (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_bdp (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_bo (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_bo (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_boe (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_boe (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_esync (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_dcmxs (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_dcmxs (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_dxd (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_dxd (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_dxdn (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_dxdn (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_fxm (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_fxm (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_li20 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_li20 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_ls (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_mbe (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_mbe (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_mb6 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_mb6 (unsigned long, ppc_cpu_t, int *);
+static long extract_nb (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_nbi (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_nsi (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_nsi (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_oimm (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_oimm (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_ral (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_ram (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_raq (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_ras (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_rbs (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_rbs (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_rbx (unsigned long, long, ppc_cpu_t, const char **);
+static unsigned long insert_rx (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_rx (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_ry (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_ry (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_sh6 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_sh6 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_sci8 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_sci8 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_sci8n (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_sci8n (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_sd4h (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_sd4h (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_sd4w (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_sd4w (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_spr (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_spr (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_sprg (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_sprg (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_tbr (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_tbr (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_xt6 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_xt6 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_xtq6 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_xtq6 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_xa6 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_xa6 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_xb6 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_xb6 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_xb6s (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_xb6s (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_xc6 (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_xc6 (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_dm (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_dm (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_vlesi (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_vlesi (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_vlensi (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_vlensi (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_vleui (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_vleui (unsigned long, ppc_cpu_t, int *);
+static unsigned long insert_vleil (unsigned long, long, ppc_cpu_t, const char **);
+static long extract_vleil (unsigned long, ppc_cpu_t, int *);
 \f
 /* The operands table.
 
-   The fields are bits, shift, insert, extract, flags.
+   The fields are bitm, shift, insert, extract, flags.
 
    We used to put parens around the various additions, like the one
    for BA just below.  However, that caused trouble with feeble
@@ -119,493 +149,934 @@ const struct powerpc_operand powerpc_operands[] =
 
   /* The BA field in an XL form instruction.  */
 #define BA UNUSED + 1
-#define BA_MASK (0x1f << 16)
-  { 5, 16, NULL, NULL, PPC_OPERAND_CR },
+  /* The BI field in a B form or XL form instruction.  */
+#define BI BA
+#define BI_MASK (0x1f << 16)
+  { 0x1f, 16, NULL, NULL, PPC_OPERAND_CR_BIT },
 
   /* The BA field in an XL form instruction when it must be the same
      as the BT field in the same instruction.  */
 #define BAT BA + 1
-  { 5, 16, insert_bat, extract_bat, PPC_OPERAND_FAKE },
+  { 0x1f, 16, insert_bat, extract_bat, PPC_OPERAND_FAKE },
 
   /* The BB field in an XL form instruction.  */
 #define BB BAT + 1
 #define BB_MASK (0x1f << 11)
-  { 5, 11, NULL, NULL, PPC_OPERAND_CR },
+  { 0x1f, 11, NULL, NULL, PPC_OPERAND_CR_BIT },
 
   /* The BB field in an XL form instruction when it must be the same
      as the BA field in the same instruction.  */
 #define BBA BB + 1
-  { 5, 11, insert_bba, extract_bba, PPC_OPERAND_FAKE },
+  /* The VB field in a VX form instruction when it must be the same
+     as the VA field in the same instruction.  */
+#define VBA BBA
+  { 0x1f, 11, insert_bba, extract_bba, PPC_OPERAND_FAKE },
 
   /* The BD field in a B form instruction.  The lower two bits are
      forced to zero.  */
 #define BD BBA + 1
-  { 16, 0, insert_bd, extract_bd, PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
+  { 0xfffc, 0, NULL, NULL, PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
 
   /* The BD field in a B form instruction when absolute addressing is
      used.  */
 #define BDA BD + 1
-  { 16, 0, insert_bd, extract_bd, PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
+  { 0xfffc, 0, NULL, NULL, PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
 
   /* The BD field in a B form instruction when the - modifier is used.
      This sets the y bit of the BO field appropriately.  */
 #define BDM BDA + 1
-  { 16, 0, insert_bdm, extract_bdm,
-      PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
+  { 0xfffc, 0, insert_bdm, extract_bdm,
+    PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
 
   /* The BD field in a B form instruction when the - modifier is used
      and absolute address is used.  */
 #define BDMA BDM + 1
-  { 16, 0, insert_bdm, extract_bdm,
-      PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
+  { 0xfffc, 0, insert_bdm, extract_bdm,
+    PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
 
   /* The BD field in a B form instruction when the + modifier is used.
      This sets the y bit of the BO field appropriately.  */
 #define BDP BDMA + 1
-  { 16, 0, insert_bdp, extract_bdp,
-      PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
+  { 0xfffc, 0, insert_bdp, extract_bdp,
+    PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
 
   /* The BD field in a B form instruction when the + modifier is used
      and absolute addressing is used.  */
 #define BDPA BDP + 1
-  { 16, 0, insert_bdp, extract_bdp,
-      PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
+  { 0xfffc, 0, insert_bdp, extract_bdp,
+    PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
 
   /* The BF field in an X or XL form instruction.  */
 #define BF BDPA + 1
-  { 3, 23, NULL, NULL, PPC_OPERAND_CR },
+  /* The CRFD field in an X form instruction.  */
+#define CRFD BF
+  /* The CRD field in an XL form instruction.  */
+#define CRD BF
+  { 0x7, 23, NULL, NULL, PPC_OPERAND_CR_REG },
+
+  /* The BF field in an X or XL form instruction.  */
+#define BFF BF + 1
+  { 0x7, 23, NULL, NULL, 0 },
 
   /* An optional BF field.  This is used for comparison instructions,
      in which an omitted BF field is taken as zero.  */
-#define OBF BF + 1
-  { 3, 23, NULL, NULL, PPC_OPERAND_CR | PPC_OPERAND_OPTIONAL },
+#define OBF BFF + 1
+  { 0x7, 23, NULL, NULL, PPC_OPERAND_CR_REG | PPC_OPERAND_OPTIONAL },
 
   /* The BFA field in an X or XL form instruction.  */
 #define BFA OBF + 1
-  { 3, 18, NULL, NULL, PPC_OPERAND_CR },
-
-  /* The BI field in a B form or XL form instruction.  */
-#define BI BFA + 1
-#define BI_MASK (0x1f << 16)
-  { 5, 16, NULL, NULL, PPC_OPERAND_CR },
+  { 0x7, 18, NULL, NULL, PPC_OPERAND_CR_REG },
 
   /* The BO field in a B form instruction.  Certain values are
      illegal.  */
-#define BO BI + 1
+#define BO BFA + 1
 #define BO_MASK (0x1f << 21)
-  { 5, 21, insert_bo, extract_bo, 0 },
+  { 0x1f, 21, insert_bo, extract_bo, 0 },
 
   /* The BO field in a B form instruction when the + or - modifier is
      used.  This is like the BO field, but it must be even.  */
 #define BOE BO + 1
-  { 5, 21, insert_boe, extract_boe, 0 },
+  { 0x1e, 21, insert_boe, extract_boe, 0 },
 
-#define BH BOE + 1
-  { 2, 11, NULL, NULL, PPC_OPERAND_OPTIONAL },
+  /* The RM field in an X form instruction.  */
+#define RM BOE + 1
+  { 0x3, 11, NULL, NULL, 0 },
+
+#define BH RM + 1
+  { 0x3, 11, NULL, NULL, PPC_OPERAND_OPTIONAL },
 
   /* The BT field in an X or XL form instruction.  */
 #define BT BH + 1
-  { 5, 21, NULL, NULL, PPC_OPERAND_CR },
+  { 0x1f, 21, NULL, NULL, PPC_OPERAND_CR_BIT },
+
+  /* The BI16 field in a BD8 form instruction.  */
+#define BI16 BT + 1
+  { 0x3, 8, NULL, NULL, PPC_OPERAND_CR_BIT },
+
+  /* The BI32 field in a BD15 form instruction.  */
+#define BI32 BI16 + 1
+  { 0xf, 16, NULL, NULL, PPC_OPERAND_CR_BIT },
+
+  /* The BO32 field in a BD15 form instruction.  */
+#define BO32 BI32 + 1
+  { 0x3, 20, NULL, NULL, 0 },
+
+  /* The B8 field in a BD8 form instruction.  */
+#define B8 BO32 + 1
+  { 0x1fe, -1, NULL, NULL, PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
+
+  /* The B15 field in a BD15 form instruction.  The lowest bit is
+     forced to zero.  */
+#define B15 B8 + 1
+  { 0xfffe, 0, NULL, NULL, PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
+
+  /* The B24 field in a BD24 form instruction.  The lowest bit is
+     forced to zero.  */
+#define B24 B15 + 1
+  { 0x1fffffe, 0, NULL, NULL, PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
 
   /* The condition register number portion of the BI field in a B form
      or XL form instruction.  This is used for the extended
      conditional branch mnemonics, which set the lower two bits of the
      BI field.  This field is optional.  */
-#define CR BT + 1
-  { 3, 18, NULL, NULL, PPC_OPERAND_CR | PPC_OPERAND_OPTIONAL },
+#define CR B24 + 1
+  { 0x7, 18, NULL, NULL, PPC_OPERAND_CR_REG | PPC_OPERAND_OPTIONAL },
 
   /* The CRB field in an X form instruction.  */
 #define CRB CR + 1
-  { 5, 6, NULL, NULL, 0 },
+  /* The MB field in an M form instruction.  */
+#define MB CRB
+#define MB_MASK (0x1f << 6)
+  { 0x1f, 6, NULL, NULL, 0 },
 
-  /* The CRFD field in an X form instruction.  */
-#define CRFD CRB + 1
-  { 3, 23, NULL, NULL, PPC_OPERAND_CR },
+  /* The CRD32 field in an XL form instruction.  */
+#define CRD32 CRB + 1
+  { 0x3, 21, NULL, NULL, PPC_OPERAND_CR_REG },
 
   /* The CRFS field in an X form instruction.  */
-#define CRFS CRFD + 1
-  { 3, 0, NULL, NULL, PPC_OPERAND_CR },
+#define CRFS CRD32 + 1
+  { 0x7, 0, NULL, NULL, PPC_OPERAND_CR_REG },
+
+#define CRS CRFS + 1
+  { 0x3, 18, NULL, NULL, PPC_OPERAND_CR_REG | PPC_OPERAND_OPTIONAL },
 
   /* The CT field in an X form instruction.  */
-#define CT CRFS + 1
-  { 5, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
+#define CT CRS + 1
+  /* The MO field in an mbar instruction.  */
+#define MO CT
+  { 0x1f, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
 
   /* The D field in a D form instruction.  This is a displacement off
      a register, and implies that the next operand is a register in
      parentheses.  */
 #define D CT + 1
-  { 16, 0, NULL, NULL, PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED },
+  { 0xffff, 0, NULL, NULL, PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED },
+
+  /* The D8 field in a D form instruction.  This is a displacement off
+     a register, and implies that the next operand is a register in
+     parentheses.  */
+#define D8 D + 1
+  { 0xff, 0, NULL, NULL, PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED },
 
-  /* The DE field in a DE form instruction.  This is like D, but is 12
-     bits only.  */
-#define DE D + 1
-  { 14, 0, insert_de, extract_de, PPC_OPERAND_PARENS },
+  /* The DCMX field in an X form instruction.  */
+#define DCMX D8 + 1
+  { 0x7f, 16, NULL, NULL, 0 },
 
-  /* The DES field in a DES form instruction.  This is like DS, but is 14
-     bits only (12 stored.)  */
-#define DES DE + 1
-  { 14, 0, insert_des, extract_des, PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED },
+  /* The split DCMX field in an X form instruction.  */
+#define DCMXS DCMX + 1
+  { 0x7f, PPC_OPSHIFT_INV, insert_dcmxs, extract_dcmxs, 0 },
 
   /* The DQ field in a DQ form instruction.  This is like D, but the
      lower four bits are forced to zero. */
-#define DQ DES + 1
-  { 16, 0, insert_dq, extract_dq,
-      PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED | PPC_OPERAND_DQ },
+#define DQ DCMXS + 1
+  { 0xfff0, 0, NULL, NULL,
+    PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED | PPC_OPERAND_DQ },
 
   /* The DS field in a DS form instruction.  This is like D, but the
      lower two bits are forced to zero.  */
 #define DS DQ + 1
-  { 16, 0, insert_ds, extract_ds,
-      PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED | PPC_OPERAND_DS },
+  { 0xfffc, 0, NULL, NULL,
+    PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED | PPC_OPERAND_DS },
+
+  /* The DUIS or BHRBE fields in a XFX form instruction, 10 bits
+     unsigned imediate */
+#define DUIS DS + 1
+#define BHRBE DUIS
+  { 0x3ff, 11, NULL, NULL, 0 },
+
+  /* The split D field in a DX form instruction.  */
+#define DXD DUIS + 1
+  { 0xffff, PPC_OPSHIFT_INV, insert_dxd, extract_dxd,
+    PPC_OPERAND_SIGNED | PPC_OPERAND_SIGNOPT},
+
+  /* The split ND field in a DX form instruction.
+     This is the same as the DX field, only negated.  */
+#define NDXD DXD + 1
+  { 0xffff, PPC_OPSHIFT_INV, insert_dxdn, extract_dxdn,
+    PPC_OPERAND_NEGATIVE | PPC_OPERAND_SIGNED | PPC_OPERAND_SIGNOPT},
 
   /* The E field in a wrteei instruction.  */
-#define E DS + 1
-  { 1, 15, NULL, NULL, 0 },
+  /* And the W bit in the pair singles instructions.  */
+  /* And the ST field in a VX form instruction.  */
+#define E NDXD + 1
+#define PSW E
+#define ST E
+  { 0x1, 15, NULL, NULL, 0 },
 
   /* The FL1 field in a POWER SC form instruction.  */
 #define FL1 E + 1
-  { 4, 12, NULL, NULL, 0 },
+  /* The U field in an X form instruction.  */
+#define U FL1
+  { 0xf, 12, NULL, NULL, 0 },
 
   /* The FL2 field in a POWER SC form instruction.  */
 #define FL2 FL1 + 1
-  { 3, 2, NULL, NULL, 0 },
+  { 0x7, 2, NULL, NULL, 0 },
 
   /* The FLM field in an XFL form instruction.  */
 #define FLM FL2 + 1
-  { 8, 17, NULL, NULL, 0 },
+  { 0xff, 17, NULL, NULL, 0 },
 
   /* The FRA field in an X or A form instruction.  */
 #define FRA FLM + 1
 #define FRA_MASK (0x1f << 16)
-  { 5, 16, NULL, NULL, PPC_OPERAND_FPR },
+  { 0x1f, 16, NULL, NULL, PPC_OPERAND_FPR },
+
+  /* The FRAp field of DFP instructions.  */
+#define FRAp FRA + 1
+  { 0x1e, 16, NULL, NULL, PPC_OPERAND_FPR },
 
   /* The FRB field in an X or A form instruction.  */
-#define FRB FRA + 1
+#define FRB FRAp + 1
 #define FRB_MASK (0x1f << 11)
-  { 5, 11, NULL, NULL, PPC_OPERAND_FPR },
+  { 0x1f, 11, NULL, NULL, PPC_OPERAND_FPR },
+
+  /* The FRBp field of DFP instructions.  */
+#define FRBp FRB + 1
+  { 0x1e, 11, NULL, NULL, PPC_OPERAND_FPR },
 
   /* The FRC field in an A form instruction.  */
-#define FRC FRB + 1
+#define FRC FRBp + 1
 #define FRC_MASK (0x1f << 6)
-  { 5, 6, NULL, NULL, PPC_OPERAND_FPR },
+  { 0x1f, 6, NULL, NULL, PPC_OPERAND_FPR },
 
   /* The FRS field in an X form instruction or the FRT field in a D, X
      or A form instruction.  */
 #define FRS FRC + 1
 #define FRT FRS
-  { 5, 21, NULL, NULL, PPC_OPERAND_FPR },
+  { 0x1f, 21, NULL, NULL, PPC_OPERAND_FPR },
+
+  /* The FRSp field of stfdp or the FRTp field of lfdp and DFP
+     instructions.  */
+#define FRSp FRS + 1
+#define FRTp FRSp
+  { 0x1e, 21, NULL, NULL, PPC_OPERAND_FPR },
 
   /* The FXM field in an XFX instruction.  */
-#define FXM FRS + 1
-#define FXM_MASK (0xff << 12)
-  { 8, 12, insert_fxm, extract_fxm, 0 },
+#define FXM FRSp + 1
+  { 0xff, 12, insert_fxm, extract_fxm, 0 },
 
   /* Power4 version for mfcr.  */
 #define FXM4 FXM + 1
-  { 8, 12, insert_fxm, extract_fxm, PPC_OPERAND_OPTIONAL },
+  { 0xff, 12, insert_fxm, extract_fxm,
+    PPC_OPERAND_OPTIONAL | PPC_OPERAND_OPTIONAL_VALUE},
+  /* If the FXM4 operand is ommitted, use the sentinel value -1.  */
+  { -1, -1, NULL, NULL, 0},
+
+  /* The IMM20 field in an LI instruction.  */
+#define IMM20 FXM4 + 2
+  { 0xfffff, PPC_OPSHIFT_INV, insert_li20, extract_li20, PPC_OPERAND_SIGNED},
 
   /* The L field in a D or X form instruction.  */
-#define L FXM4 + 1
-  { 1, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
+#define L IMM20 + 1
+  { 0x1, 21, NULL, NULL, 0 },
+
+  /* The optional L field in tlbie and tlbiel instructions.  */
+#define LOPT L + 1
+  /* The R field in a HTM X form instruction.  */
+#define HTM_R LOPT
+  { 0x1, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
+
+  /* The optional (for 32-bit) L field in cmp[l][i] instructions.  */
+#define L32OPT LOPT + 1
+  { 0x1, 21, NULL, NULL, PPC_OPERAND_OPTIONAL | PPC_OPERAND_OPTIONAL32 },
+
+  /* The L field in dcbf instruction.  */
+#define L2OPT L32OPT + 1
+  { 0x3, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
 
   /* The LEV field in a POWER SVC form instruction.  */
-#define SVC_LEV L + 1
-  { 7, 5, NULL, NULL, 0 },
+#define SVC_LEV L2OPT + 1
+  { 0x7f, 5, NULL, NULL, 0 },
 
   /* The LEV field in an SC form instruction.  */
 #define LEV SVC_LEV + 1
-  { 7, 5, NULL, NULL, PPC_OPERAND_OPTIONAL },
+  { 0x7f, 5, NULL, NULL, PPC_OPERAND_OPTIONAL },
 
   /* The LI field in an I form instruction.  The lower two bits are
      forced to zero.  */
 #define LI LEV + 1
-  { 26, 0, insert_li, extract_li, PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
+  { 0x3fffffc, 0, NULL, NULL, PPC_OPERAND_RELATIVE | PPC_OPERAND_SIGNED },
 
   /* The LI field in an I form instruction when used as an absolute
      address.  */
 #define LIA LI + 1
-  { 26, 0, insert_li, extract_li, PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
+  { 0x3fffffc, 0, NULL, NULL, PPC_OPERAND_ABSOLUTE | PPC_OPERAND_SIGNED },
 
-  /* The LS field in an X (sync) form instruction.  */
+  /* The LS or WC field in an X (sync or wait) form instruction.  */
 #define LS LIA + 1
-  { 2, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
-
-  /* The MB field in an M form instruction.  */
-#define MB LS + 1
-#define MB_MASK (0x1f << 6)
-  { 5, 6, NULL, NULL, 0 },
+#define WC LS
+  { 0x3, 21, insert_ls, NULL, PPC_OPERAND_OPTIONAL },
 
   /* The ME field in an M form instruction.  */
-#define ME MB + 1
+#define ME LS + 1
 #define ME_MASK (0x1f << 1)
-  { 5, 1, NULL, NULL, 0 },
+  { 0x1f, 1, NULL, NULL, 0 },
 
   /* The MB and ME fields in an M form instruction expressed a single
      operand which is a bitmask indicating which bits to select.  This
      is a two operand form using PPC_OPERAND_NEXT.  See the
      description in opcode/ppc.h for what this means.  */
 #define MBE ME + 1
-  { 5, 6, NULL, NULL, PPC_OPERAND_OPTIONAL | PPC_OPERAND_NEXT },
-  { 32, 0, insert_mbe, extract_mbe, 0 },
+  { 0x1f, 6, NULL, NULL, PPC_OPERAND_OPTIONAL | PPC_OPERAND_NEXT },
+  { -1, 0, insert_mbe, extract_mbe, 0 },
 
   /* The MB or ME field in an MD or MDS form instruction.  The high
      bit is wrapped to the low end.  */
 #define MB6 MBE + 2
 #define ME6 MB6
 #define MB6_MASK (0x3f << 5)
-  { 6, 5, insert_mb6, extract_mb6, 0 },
-
-  /* The MO field in an mbar instruction.  */
-#define MO MB6 + 1
-  { 5, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
+  { 0x3f, 5, insert_mb6, extract_mb6, 0 },
 
   /* The NB field in an X form instruction.  The value 32 is stored as
      0.  */
-#define NB MO + 1
-  { 6, 11, insert_nb, extract_nb, 0 },
+#define NB MB6 + 1
+  { 0x1f, 11, NULL, extract_nb, PPC_OPERAND_PLUS1 },
+
+  /* The NBI field in an lswi instruction, which has special value
+     restrictions.  The value 32 is stored as 0.  */
+#define NBI NB + 1
+  { 0x1f, 11, insert_nbi, extract_nb, PPC_OPERAND_PLUS1 },
 
   /* The NSI field in a D form instruction.  This is the same as the
      SI field, only negated.  */
-#define NSI NB + 1
-  { 16, 0, insert_nsi, extract_nsi,
-      PPC_OPERAND_NEGATIVE | PPC_OPERAND_SIGNED },
+#define NSI NBI + 1
+  { 0xffff, 0, insert_nsi, extract_nsi,
+    PPC_OPERAND_NEGATIVE | PPC_OPERAND_SIGNED },
+
+  /* The NSI field in a D form instruction when we accept a wide range
+     of positive values.  */
+#define NSISIGNOPT NSI + 1
+  { 0xffff, 0, insert_nsi, extract_nsi,
+    PPC_OPERAND_NEGATIVE | PPC_OPERAND_SIGNED | PPC_OPERAND_SIGNOPT },
 
   /* The RA field in an D, DS, DQ, X, XO, M, or MDS form instruction.  */
-#define RA NSI + 1
+#define RA NSISIGNOPT + 1
 #define RA_MASK (0x1f << 16)
-  { 5, 16, NULL, NULL, PPC_OPERAND_GPR },
+  { 0x1f, 16, NULL, NULL, PPC_OPERAND_GPR },
 
   /* As above, but 0 in the RA field means zero, not r0.  */
 #define RA0 RA + 1
-  { 5, 16, NULL, NULL, PPC_OPERAND_GPR_0 },
+  { 0x1f, 16, NULL, NULL, PPC_OPERAND_GPR_0 },
 
-  /* The RA field in the DQ form lq instruction, which has special
+  /* The RA field in the DQ form lq or an lswx instruction, which have special
      value restrictions.  */
 #define RAQ RA0 + 1
-  { 5, 16, insert_raq, NULL, PPC_OPERAND_GPR_0 },
+#define RAX RAQ
+  { 0x1f, 16, insert_raq, NULL, PPC_OPERAND_GPR_0 },
 
   /* The RA field in a D or X form instruction which is an updating
      load, which means that the RA field may not be zero and may not
      equal the RT field.  */
 #define RAL RAQ + 1
-  { 5, 16, insert_ral, NULL, PPC_OPERAND_GPR_0 },
+  { 0x1f, 16, insert_ral, NULL, PPC_OPERAND_GPR_0 },
 
   /* The RA field in an lmw instruction, which has special value
      restrictions.  */
 #define RAM RAL + 1
-  { 5, 16, insert_ram, NULL, PPC_OPERAND_GPR_0 },
+  { 0x1f, 16, insert_ram, NULL, PPC_OPERAND_GPR_0 },
 
   /* The RA field in a D or X form instruction which is an updating
      store or an updating floating point load, which means that the RA
      field may not be zero.  */
 #define RAS RAM + 1
-  { 5, 16, insert_ras, NULL, PPC_OPERAND_GPR_0 },
+  { 0x1f, 16, insert_ras, NULL, PPC_OPERAND_GPR_0 },
 
-  /* The RA field of the tlbwe instruction, which is optional.  */
+  /* The RA field of the tlbwe, dccci and iccci instructions,
+     which are optional.  */
 #define RAOPT RAS + 1
-  { 5, 16, NULL, NULL, PPC_OPERAND_GPR | PPC_OPERAND_OPTIONAL },
+  { 0x1f, 16, NULL, NULL, PPC_OPERAND_GPR | PPC_OPERAND_OPTIONAL },
 
   /* The RB field in an X, XO, M, or MDS form instruction.  */
 #define RB RAOPT + 1
 #define RB_MASK (0x1f << 11)
-  { 5, 11, NULL, NULL, PPC_OPERAND_GPR },
+  { 0x1f, 11, NULL, NULL, PPC_OPERAND_GPR },
 
   /* The RB field in an X form instruction when it must be the same as
      the RS field in the instruction.  This is used for extended
      mnemonics like mr.  */
 #define RBS RB + 1
-  { 5, 1, insert_rbs, extract_rbs, PPC_OPERAND_FAKE },
+  { 0x1f, 11, insert_rbs, extract_rbs, PPC_OPERAND_FAKE },
+
+  /* The RB field in an lswx instruction, which has special value
+     restrictions.  */
+#define RBX RBS + 1
+  { 0x1f, 11, insert_rbx, NULL, PPC_OPERAND_GPR },
+
+  /* The RB field of the dccci and iccci instructions, which are optional.  */
+#define RBOPT RBX + 1
+  { 0x1f, 11, NULL, NULL, PPC_OPERAND_GPR | PPC_OPERAND_OPTIONAL },
+
+  /* The RC register field in an maddld, maddhd or maddhdu instruction.  */
+#define RC RBOPT + 1
+  { 0x1f, 6, NULL, NULL, PPC_OPERAND_GPR },
 
   /* The RS field in a D, DS, X, XFX, XS, M, MD or MDS form
      instruction or the RT field in a D, DS, X, XFX or XO form
      instruction.  */
-#define RS RBS + 1
+#define RS RC + 1
 #define RT RS
 #define RT_MASK (0x1f << 21)
-  { 5, 21, NULL, NULL, PPC_OPERAND_GPR },
+#define RD RS
+  { 0x1f, 21, NULL, NULL, PPC_OPERAND_GPR },
 
-  /* The RS field of the DS form stq instruction, which has special
-     value restrictions.  */
+  /* The RS and RT fields of the DS form stq and DQ form lq instructions,
+     which have special value restrictions.  */
 #define RSQ RS + 1
-  { 5, 21, insert_rsq, NULL, PPC_OPERAND_GPR_0 },
-
-  /* The RT field of the DQ form lq instruction, which has special
-     value restrictions.  */
-#define RTQ RSQ + 1
-  { 5, 21, insert_rtq, NULL, PPC_OPERAND_GPR_0 },
+#define RTQ RSQ
+  { 0x1e, 21, NULL, NULL, PPC_OPERAND_GPR },
 
   /* The RS field of the tlbwe instruction, which is optional.  */
-#define RSO RTQ + 1
+#define RSO RSQ + 1
 #define RTO RSO
-  { 5, 21, NULL, NULL, PPC_OPERAND_GPR | PPC_OPERAND_OPTIONAL },
+  { 0x1f, 21, NULL, NULL, PPC_OPERAND_GPR | PPC_OPERAND_OPTIONAL },
+
+  /* The RX field of the SE_RR form instruction.  */
+#define RX RSO + 1
+  { 0x1f, PPC_OPSHIFT_INV, insert_rx, extract_rx, PPC_OPERAND_GPR },
+
+  /* The ARX field of the SE_RR form instruction.  */
+#define ARX RX + 1
+  { 0x1f, PPC_OPSHIFT_INV, insert_arx, extract_arx, PPC_OPERAND_GPR },
+
+  /* The RY field of the SE_RR form instruction.  */
+#define RY ARX + 1
+#define RZ RY
+  { 0x1f, PPC_OPSHIFT_INV, insert_ry, extract_ry, PPC_OPERAND_GPR },
+
+  /* The ARY field of the SE_RR form instruction.  */
+#define ARY RY + 1
+  { 0x1f, PPC_OPSHIFT_INV, insert_ary, extract_ary, PPC_OPERAND_GPR },
+
+  /* The SCLSCI8 field in a D form instruction.  */
+#define SCLSCI8 ARY + 1
+  { 0xffffffff, PPC_OPSHIFT_INV, insert_sci8, extract_sci8, 0 },
+
+  /* The SCLSCI8N field in a D form instruction.  This is the same as the
+     SCLSCI8 field, only negated.  */
+#define SCLSCI8N SCLSCI8 + 1
+  { 0xffffffff, PPC_OPSHIFT_INV, insert_sci8n, extract_sci8n,
+    PPC_OPERAND_NEGATIVE | PPC_OPERAND_SIGNED },
+
+  /* The SD field of the SD4 form instruction.  */
+#define SE_SD SCLSCI8N + 1
+  { 0xf, 8, NULL, NULL, PPC_OPERAND_PARENS },
+
+  /* The SD field of the SD4 form instruction, for halfword.  */
+#define SE_SDH SE_SD + 1
+  { 0x1e, PPC_OPSHIFT_INV, insert_sd4h, extract_sd4h, PPC_OPERAND_PARENS },
+
+  /* The SD field of the SD4 form instruction, for word.  */
+#define SE_SDW SE_SDH + 1
+  { 0x3c, PPC_OPSHIFT_INV, insert_sd4w, extract_sd4w, PPC_OPERAND_PARENS },
 
   /* The SH field in an X or M form instruction.  */
-#define SH RSO + 1
+#define SH SE_SDW + 1
 #define SH_MASK (0x1f << 11)
-  { 5, 11, NULL, NULL, 0 },
+  /* The other UIMM field in a EVX form instruction.  */
+#define EVUIMM SH
+  /* The FC field in an atomic X form instruction.  */
+#define FC SH
+  { 0x1f, 11, NULL, NULL, 0 },
+
+  /* The SI field in a HTM X form instruction.  */
+#define HTM_SI SH + 1
+  { 0x1f, 11, NULL, NULL, PPC_OPERAND_SIGNED },
 
   /* The SH field in an MD form instruction.  This is split.  */
-#define SH6 SH + 1
+#define SH6 HTM_SI + 1
 #define SH6_MASK ((0x1f << 11) | (1 << 1))
-  { 6, 1, insert_sh6, extract_sh6, 0 },
+  { 0x3f, PPC_OPSHIFT_INV, insert_sh6, extract_sh6, 0 },
 
   /* The SH field of the tlbwe instruction, which is optional.  */
 #define SHO SH6 + 1
-  { 5, 11,NULL, NULL, PPC_OPERAND_OPTIONAL },
+  { 0x1f, 11, NULL, NULL, PPC_OPERAND_OPTIONAL },
 
   /* The SI field in a D form instruction.  */
 #define SI SHO + 1
-  { 16, 0, NULL, NULL, PPC_OPERAND_SIGNED },
+  { 0xffff, 0, NULL, NULL, PPC_OPERAND_SIGNED },
 
   /* The SI field in a D form instruction when we accept a wide range
      of positive values.  */
 #define SISIGNOPT SI + 1
-  { 16, 0, NULL, NULL, PPC_OPERAND_SIGNED | PPC_OPERAND_SIGNOPT },
+  { 0xffff, 0, NULL, NULL, PPC_OPERAND_SIGNED | PPC_OPERAND_SIGNOPT },
+
+  /* The SI8 field in a D form instruction.  */
+#define SI8 SISIGNOPT + 1
+  { 0xff, 0, NULL, NULL, PPC_OPERAND_SIGNED },
 
   /* The SPR field in an XFX form instruction.  This is flipped--the
      lower 5 bits are stored in the upper 5 and vice- versa.  */
-#define SPR SISIGNOPT + 1
+#define SPR SI8 + 1
 #define PMR SPR
+#define TMR SPR
 #define SPR_MASK (0x3ff << 11)
-  { 10, 11, insert_spr, extract_spr, 0 },
+  { 0x3ff, 11, insert_spr, extract_spr, 0 },
 
   /* The BAT index number in an XFX form m[ft]ibat[lu] instruction.  */
 #define SPRBAT SPR + 1
 #define SPRBAT_MASK (0x3 << 17)
-  { 2, 17, NULL, NULL, 0 },
+  { 0x3, 17, NULL, NULL, 0 },
 
   /* The SPRG register number in an XFX form m[ft]sprg instruction.  */
 #define SPRG SPRBAT + 1
-  { 5, 16, insert_sprg, extract_sprg, 0 },
+  { 0x1f, 16, insert_sprg, extract_sprg, 0 },
 
   /* The SR field in an X form instruction.  */
 #define SR SPRG + 1
-  { 4, 16, NULL, NULL, 0 },
+  /* The 4-bit UIMM field in a VX form instruction.  */
+#define UIMM4 SR
+  { 0xf, 16, NULL, NULL, 0 },
 
   /* The STRM field in an X AltiVec form instruction.  */
 #define STRM SR + 1
-#define STRM_MASK (0x3 << 21)
-  { 2, 21, NULL, NULL, 0 },
+  /* The T field in a tlbilx form instruction.  */
+#define T STRM
+  /* The L field in wclr instructions.  */
+#define L2 STRM
+  { 0x3, 21, NULL, NULL, 0 },
+
+  /* The ESYNC field in an X (sync) form instruction.  */
+#define ESYNC STRM + 1
+  { 0xf, 16, insert_esync, NULL, PPC_OPERAND_OPTIONAL },
 
   /* The SV field in a POWER SC form instruction.  */
-#define SV STRM + 1
-  { 14, 2, NULL, NULL, 0 },
+#define SV ESYNC + 1
+  { 0x3fff, 2, NULL, NULL, 0 },
 
   /* The TBR field in an XFX form instruction.  This is like the SPR
      field, but it is optional.  */
 #define TBR SV + 1
-  { 10, 11, insert_tbr, extract_tbr, PPC_OPERAND_OPTIONAL },
+  { 0x3ff, 11, insert_tbr, extract_tbr,
+    PPC_OPERAND_OPTIONAL | PPC_OPERAND_OPTIONAL_VALUE},
+  /* If the TBR operand is ommitted, use the value 268.  */
+  { -1, 268, NULL, NULL, 0},
 
   /* The TO field in a D or X form instruction.  */
-#define TO TBR + 1
+#define TO TBR + 2
+#define DUI TO
 #define TO_MASK (0x1f << 21)
-  { 5, 21, NULL, NULL, 0 },
-
-  /* The U field in an X form instruction.  */
-#define U TO + 1
-  { 4, 12, NULL, NULL, 0 },
+  { 0x1f, 21, NULL, NULL, 0 },
 
   /* The UI field in a D form instruction.  */
-#define UI U + 1
-  { 16, 0, NULL, NULL, 0 },
+#define UI TO + 1
+  { 0xffff, 0, NULL, NULL, 0 },
+
+#define UISIGNOPT UI + 1
+  { 0xffff, 0, NULL, NULL, PPC_OPERAND_SIGNOPT },
+
+  /* The IMM field in an SE_IM5 instruction.  */
+#define UI5 UISIGNOPT + 1
+  { 0x1f, 4, NULL, NULL, 0 },
+
+  /* The OIMM field in an SE_OIM5 instruction.  */
+#define OIMM5 UI5 + 1
+  { 0x1f, PPC_OPSHIFT_INV, insert_oimm, extract_oimm, PPC_OPERAND_PLUS1 },
+
+  /* The UI7 field in an SE_LI instruction.  */
+#define UI7 OIMM5 + 1
+  { 0x7f, 4, NULL, NULL, 0 },
 
   /* The VA field in a VA, VX or VXR form instruction.  */
-#define VA UI + 1
-#define VA_MASK        (0x1f << 16)
-  { 5, 16, NULL, NULL, PPC_OPERAND_VR },
+#define VA UI7 + 1
+  { 0x1f, 16, NULL, NULL, PPC_OPERAND_VR },
 
   /* The VB field in a VA, VX or VXR form instruction.  */
 #define VB VA + 1
-#define VB_MASK (0x1f << 11)
-  { 5, 11, NULL, NULL, PPC_OPERAND_VR },
+  { 0x1f, 11, NULL, NULL, PPC_OPERAND_VR },
 
   /* The VC field in a VA form instruction.  */
 #define VC VB + 1
-#define VC_MASK (0x1f << 6)
-  { 5, 6, NULL, NULL, PPC_OPERAND_VR },
+  { 0x1f, 6, NULL, NULL, PPC_OPERAND_VR },
 
   /* The VD or VS field in a VA, VX, VXR or X form instruction.  */
 #define VD VC + 1
 #define VS VD
-#define VD_MASK (0x1f << 21)
-  { 5, 21, NULL, NULL, PPC_OPERAND_VR },
+  { 0x1f, 21, NULL, NULL, PPC_OPERAND_VR },
 
-  /* The SIMM field in a VX form instruction.  */
+  /* The SIMM field in a VX form instruction, and TE in Z form.  */
 #define SIMM VD + 1
-  { 5, 16, NULL, NULL, PPC_OPERAND_SIGNED},
+#define TE SIMM
+  { 0x1f, 16, NULL, NULL, PPC_OPERAND_SIGNED},
 
   /* The UIMM field in a VX form instruction.  */
 #define UIMM SIMM + 1
-  { 5, 16, NULL, NULL, 0 },
+#define DCTL UIMM
+  { 0x1f, 16, NULL, NULL, 0 },
 
-  /* The SHB field in a VA form instruction.  */
-#define SHB UIMM + 1
-  { 4, 6, NULL, NULL, 0 },
+  /* The 3-bit UIMM field in a VX form instruction.  */
+#define UIMM3 UIMM + 1
+  { 0x7, 16, NULL, NULL, 0 },
 
-  /* The other UIMM field in a EVX form instruction.  */
-#define EVUIMM SHB + 1
-  { 5, 11, NULL, NULL, 0 },
+  /* The 6-bit UIM field in a X form instruction.  */
+#define UIM6 UIMM3 + 1
+  { 0x3f, 16, NULL, NULL, 0 },
+
+  /* The SIX field in a VX form instruction.  */
+#define SIX UIM6 + 1
+  { 0xf, 11, NULL, NULL, 0 },
+
+  /* The PS field in a VX form instruction.  */
+#define PS SIX + 1
+  { 0x1, 9, NULL, NULL, 0 },
+
+  /* The SHB field in a VA form instruction.  */
+#define SHB PS + 1
+  { 0xf, 6, NULL, NULL, 0 },
 
   /* The other UIMM field in a half word EVX form instruction.  */
-#define EVUIMM_2 EVUIMM + 1
-  { 32, 11, insert_ev2, extract_ev2, PPC_OPERAND_PARENS },
+#define EVUIMM_2 SHB + 1
+  { 0x3e, 10, NULL, NULL, PPC_OPERAND_PARENS },
 
   /* The other UIMM field in a word EVX form instruction.  */
 #define EVUIMM_4 EVUIMM_2 + 1
-  { 32, 11, insert_ev4, extract_ev4, PPC_OPERAND_PARENS },
+  { 0x7c, 9, NULL, NULL, PPC_OPERAND_PARENS },
 
   /* The other UIMM field in a double EVX form instruction.  */
 #define EVUIMM_8 EVUIMM_4 + 1
-  { 32, 11, insert_ev8, extract_ev8, PPC_OPERAND_PARENS },
+  { 0xf8, 8, NULL, NULL, PPC_OPERAND_PARENS },
 
-  /* The WS field.  */
+  /* The WS or DRM field in an X form instruction.  */
 #define WS EVUIMM_8 + 1
-#define WS_MASK (0x7 << 11)
-  { 3, 11, NULL, NULL, 0 },
-
-  /* The L field in an mtmsrd or A form instruction.  */
-#define MTMSRD_L WS + 1
-#define A_L MTMSRD_L
-  { 1, 16, NULL, NULL, PPC_OPERAND_OPTIONAL },
-
-  /* The DCM field in a Z form instruction.  */
-#define DCM MTMSRD_L + 1
-  { 6, 16, NULL, NULL, 0 },
-
-  /* Likewise, the DGM field in a Z form instruction.  */
-#define DGM DCM + 1
-  { 6, 16, NULL, NULL, 0 },
+#define DRM WS
+  { 0x7, 11, NULL, NULL, 0 },
+
+  /* PowerPC paired singles extensions.  */
+  /* W bit in the pair singles instructions for x type instructions.  */
+#define PSWM WS + 1
+  /* The BO16 field in a BD8 form instruction.  */
+#define BO16 PSWM
+  {  0x1, 10, 0, 0, 0 },
+
+  /* IDX bits for quantization in the pair singles instructions.  */
+#define PSQ PSWM + 1
+  {  0x7, 12, 0, 0, 0 },
+
+  /* IDX bits for quantization in the pair singles x-type instructions.  */
+#define PSQM PSQ + 1
+  {  0x7, 7, 0, 0, 0 },
+
+  /* Smaller D field for quantization in the pair singles instructions.  */
+#define PSD PSQM + 1
+  {  0xfff, 0, 0, 0,  PPC_OPERAND_PARENS | PPC_OPERAND_SIGNED },
+
+  /* The L field in an mtmsrd or A form instruction or R or W in an X form.  */
+#define A_L PSD + 1
+#define W A_L
+#define X_R A_L
+  { 0x1, 16, NULL, NULL, PPC_OPERAND_OPTIONAL },
+
+  /* The RMC or CY field in a Z23 form instruction.  */
+#define RMC A_L + 1
+#define CY RMC
+  { 0x3, 9, NULL, NULL, 0 },
 
-#define TE DGM + 1
-  { 5, 11, NULL, NULL, 0 },
+#define R RMC + 1
+  { 0x1, 16, NULL, NULL, 0 },
 
-#define RMC TE + 1
-  { 2, 21, NULL, NULL, 0 },
+#define RIC R + 1
+  { 0x3, 18, NULL, NULL, PPC_OPERAND_OPTIONAL },
 
-#define R RMC + 1
-  { 1, 15, NULL, NULL, 0 },
+#define PRS RIC + 1
+  { 0x1, 17, NULL, NULL, PPC_OPERAND_OPTIONAL },
 
-#define SP R + 1
-  { 2, 11, NULL, NULL, 0 },
+#define SP PRS + 1
+  { 0x3, 19, NULL, NULL, 0 },
 
 #define S SP + 1
-  { 1, 11, NULL, NULL, 0 },
+  { 0x1, 20, NULL, NULL, 0 },
 
-  /* SH field starting at bit position 16.  */
-#define SH16 S + 1
-  { 6, 10, NULL, NULL, 0 },
+  /* The S field in a XL form instruction.  */
+#define SXL S + 1
+  { 0x1, 11, NULL, NULL, PPC_OPERAND_OPTIONAL | PPC_OPERAND_OPTIONAL_VALUE},
+  /* If the SXL operand is ommitted, use the value 1.  */
+  { -1, 1, NULL, NULL, 0},
 
-  /* The L field in an X form with the RT field fixed instruction.  */
-#define XRT_L SH16 + 1
-  { 2, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
+  /* SH field starting at bit position 16.  */
+#define SH16 SXL + 2
+  /* The DCM and DGM fields in a Z form instruction.  */
+#define DCM SH16
+#define DGM DCM
+  { 0x3f, 10, NULL, NULL, 0 },
 
   /* The EH field in larx instruction.  */
-#define EH XRT_L + 1
-  { 1, 0, NULL, NULL, PPC_OPERAND_OPTIONAL },
+#define EH SH16 + 1
+  { 0x1, 0, NULL, NULL, PPC_OPERAND_OPTIONAL },
+
+  /* The L field in an mtfsf or XFL form instruction.  */
+  /* The A field in a HTM X form instruction.  */
+#define XFL_L EH + 1
+#define HTM_A XFL_L
+  { 0x1, 25, NULL, NULL, PPC_OPERAND_OPTIONAL},
+
+  /* Xilinx APU related masks and macros */
+#define FCRT XFL_L + 1
+#define FCRT_MASK (0x1f << 21)
+  { 0x1f, 21, 0, 0, PPC_OPERAND_FCR },
+
+  /* Xilinx FSL related masks and macros */
+#define FSL FCRT + 1
+#define FSL_MASK (0x1f << 11)
+  { 0x1f, 11, 0, 0, PPC_OPERAND_FSL },
+
+  /* Xilinx UDI related masks and macros */
+#define URT FSL + 1
+  { 0x1f, 21, 0, 0, PPC_OPERAND_UDI },
+
+#define URA URT + 1
+  { 0x1f, 16, 0, 0, PPC_OPERAND_UDI },
+
+#define URB URA + 1
+  { 0x1f, 11, 0, 0, PPC_OPERAND_UDI },
+
+#define URC URB + 1
+  { 0x1f, 6, 0, 0, PPC_OPERAND_UDI },
+
+  /* The VLESIMM field in a D form instruction.  */
+#define VLESIMM URC + 1
+  { 0xffff, PPC_OPSHIFT_INV, insert_vlesi, extract_vlesi,
+    PPC_OPERAND_SIGNED | PPC_OPERAND_SIGNOPT },
+
+  /* The VLENSIMM field in a D form instruction.  */
+#define VLENSIMM VLESIMM + 1
+  { 0xffff, PPC_OPSHIFT_INV, insert_vlensi, extract_vlensi,
+    PPC_OPERAND_NEGATIVE | PPC_OPERAND_SIGNED | PPC_OPERAND_SIGNOPT },
+
+  /* The VLEUIMM field in a D form instruction.  */
+#define VLEUIMM VLENSIMM + 1
+  { 0xffff, PPC_OPSHIFT_INV, insert_vleui, extract_vleui, 0 },
+
+  /* The VLEUIMML field in a D form instruction.  */
+#define VLEUIMML VLEUIMM + 1
+  { 0xffff, PPC_OPSHIFT_INV, insert_vleil, extract_vleil, 0 },
+
+  /* The XT and XS fields in an XX1 or XX3 form instruction.  This is split.  */
+#define XS6 VLEUIMML + 1
+#define XT6 XS6
+  { 0x3f, PPC_OPSHIFT_INV, insert_xt6, extract_xt6, PPC_OPERAND_VSR },
+
+  /* The XT and XS fields in an DQ form VSX instruction.  This is split.  */
+#define XSQ6 XT6 + 1
+#define XTQ6 XSQ6
+  { 0x3f, PPC_OPSHIFT_INV, insert_xtq6, extract_xtq6, PPC_OPERAND_VSR },
+
+  /* The XA field in an XX3 form instruction.  This is split.  */
+#define XA6 XTQ6 + 1
+  { 0x3f, PPC_OPSHIFT_INV, insert_xa6, extract_xa6, PPC_OPERAND_VSR },
+
+  /* The XB field in an XX2 or XX3 form instruction.  This is split.  */
+#define XB6 XA6 + 1
+  { 0x3f, PPC_OPSHIFT_INV, insert_xb6, extract_xb6, PPC_OPERAND_VSR },
+
+  /* The XB field in an XX3 form instruction when it must be the same as
+     the XA field in the instruction.  This is used in extended mnemonics
+     like xvmovdp.  This is split.  */
+#define XB6S XB6 + 1
+  { 0x3f, PPC_OPSHIFT_INV, insert_xb6s, extract_xb6s, PPC_OPERAND_FAKE },
+
+  /* The XC field in an XX4 form instruction.  This is split.  */
+#define XC6 XB6S + 1
+  { 0x3f, PPC_OPSHIFT_INV, insert_xc6, extract_xc6, PPC_OPERAND_VSR },
+
+  /* The DM or SHW field in an XX3 form instruction.  */
+#define DM XC6 + 1
+#define SHW DM
+  { 0x3, 8, NULL, NULL, 0 },
+
+  /* The DM field in an extended mnemonic XX3 form instruction.  */
+#define DMEX DM + 1
+  { 0x3, 8, insert_dm, extract_dm, 0 },
+
+  /* The UIM field in an XX2 form instruction.  */
+#define UIM DMEX + 1
+  /* The 2-bit UIMM field in a VX form instruction.  */
+#define UIMM2 UIM
+  /* The 2-bit L field in a darn instruction.  */
+#define LRAND UIM
+  { 0x3, 16, NULL, NULL, 0 },
+
+#define ERAT_T UIM + 1
+  { 0x7, 21, NULL, NULL, 0 },
+
+#define IH ERAT_T + 1
+  { 0x7, 21, NULL, NULL, PPC_OPERAND_OPTIONAL },
+
+  /* The 8-bit IMM8 field in a XX1 form instruction.  */
+#define IMM8 IH + 1
+  { 0xff, 11, NULL, NULL, PPC_OPERAND_SIGNOPT },
 };
 
+const unsigned int num_powerpc_operands = (sizeof (powerpc_operands)
+                                          / sizeof (powerpc_operands[0]));
+
 /* The functions used to insert and extract complicated operands.  */
 
+/* The ARX, ARY, RX and RY operands are alternate encodings of GPRs.  */
+
+static unsigned long
+insert_arx (unsigned long insn,
+           long value,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           const char **errmsg ATTRIBUTE_UNUSED)
+{
+  if (value >= 8 && value < 24)
+    return insn | ((value - 8) & 0xf);
+  else
+    {
+      *errmsg = _("invalid register");
+      return 0;
+    }
+}
+
+static long
+extract_arx (unsigned long insn,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+            int *invalid ATTRIBUTE_UNUSED)
+{
+  return (insn & 0xf) + 8;
+}
+
+static unsigned long
+insert_ary (unsigned long insn,
+           long value,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           const char **errmsg ATTRIBUTE_UNUSED)
+{
+  if (value >= 8 && value < 24)
+    return insn | (((value - 8) & 0xf) << 4);
+  else
+    {
+      *errmsg = _("invalid register");
+      return 0;
+    }
+}
+
+static long
+extract_ary (unsigned long insn,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+            int *invalid ATTRIBUTE_UNUSED)
+{
+  return ((insn >> 4) & 0xf) + 8;
+}
+
+static unsigned long
+insert_rx (unsigned long insn,
+          long value,
+          ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+          const char **errmsg)
+{
+  if (value >= 0 && value < 8)
+    return insn | value;
+  else if (value >= 24 && value <= 31)
+    return insn | (value - 16);
+  else
+    {
+      *errmsg = _("invalid register");
+      return 0;
+    }
+}
+
+static long
+extract_rx (unsigned long insn,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           int *invalid ATTRIBUTE_UNUSED)
+{
+  int value = insn & 0xf;
+  if (value >= 0 && value < 8)
+    return value;
+  else
+    return value + 16;
+}
+
+static unsigned long
+insert_ry (unsigned long insn,
+          long value,
+          ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+          const char **errmsg)
+{
+  if (value >= 0 && value < 8)
+    return insn | (value << 4);
+  else if (value >= 24 && value <= 31)
+    return insn | ((value - 16) << 4);
+  else
+    {
+      *errmsg = _("invalid register");
+      return 0;
+    }
+}
+
+static long
+extract_ry (unsigned long insn,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           int *invalid ATTRIBUTE_UNUSED)
+{
+  int value = (insn >> 4) & 0xf;
+  if (value >= 0 && value < 8)
+    return value;
+  else
+    return value + 16;
+}
+
 /* The BA field in an XL form instruction when it must be the same as
    the BT field in the same instruction.  This operand is marked FAKE.
    The insertion function just copies the BT field into the BA field,
@@ -615,7 +1086,7 @@ const struct powerpc_operand powerpc_operands[] =
 static unsigned long
 insert_bat (unsigned long insn,
            long value ATTRIBUTE_UNUSED,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char **errmsg ATTRIBUTE_UNUSED)
 {
   return insn | (((insn >> 21) & 0x1f) << 16);
@@ -623,7 +1094,7 @@ insert_bat (unsigned long insn,
 
 static long
 extract_bat (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid)
 {
   if (((insn >> 21) & 0x1f) != ((insn >> 16) & 0x1f))
@@ -640,7 +1111,7 @@ extract_bat (unsigned long insn,
 static unsigned long
 insert_bba (unsigned long insn,
            long value ATTRIBUTE_UNUSED,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char **errmsg ATTRIBUTE_UNUSED)
 {
   return insn | (((insn >> 16) & 0x1f) << 11);
@@ -648,7 +1119,7 @@ insert_bba (unsigned long insn,
 
 static long
 extract_bba (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid)
 {
   if (((insn >> 16) & 0x1f) != ((insn >> 11) & 0x1f))
@@ -656,26 +1127,6 @@ extract_bba (unsigned long insn,
   return 0;
 }
 
-/* The BD field in a B form instruction.  The lower two bits are
-   forced to zero.  */
-
-static unsigned long
-insert_bd (unsigned long insn,
-          long value,
-          int dialect ATTRIBUTE_UNUSED,
-          const char **errmsg ATTRIBUTE_UNUSED)
-{
-  return insn | (value & 0xfffc);
-}
-
-static long
-extract_bd (unsigned long insn,
-           int dialect ATTRIBUTE_UNUSED,
-           int *invalid ATTRIBUTE_UNUSED)
-{
-  return ((insn & 0xfffc) ^ 0x8000) - 0x8000;
-}
-
 /* The BD field in a B form instruction when the - modifier is used.
    This modifier means that the branch is not expected to be taken.
    For chips built to versions of the architecture prior to version 2
@@ -687,15 +1138,21 @@ extract_bd (unsigned long insn,
    the "y" bit.  "at" == 00 => no hint, "at" == 01 => unpredictable,
    "at" == 10 => not taken, "at" == 11 => taken.  The "t" bit is 00001
    in BO field, the "a" bit is 00010 for branch on CR(BI) and 01000
-   for branch on CTR.  We only handle the taken/not-taken hint here.  */
+   for branch on CTR.  We only handle the taken/not-taken hint here.
+   Note that we don't relax the conditions tested here when
+   disassembling with -Many because insns using extract_bdm and
+   extract_bdp always occur in pairs.  One or the other will always
+   be valid.  */
+
+#define ISA_V2 (PPC_OPCODE_POWER4 | PPC_OPCODE_E500MC | PPC_OPCODE_TITAN)
 
 static unsigned long
 insert_bdm (unsigned long insn,
            long value,
-           int dialect,
+           ppc_cpu_t dialect,
            const char **errmsg ATTRIBUTE_UNUSED)
 {
-  if ((dialect & PPC_OPCODE_POWER4) == 0)
+  if ((dialect & ISA_V2) == 0)
     {
       if ((value & 0x8000) != 0)
        insn |= 1 << 21;
@@ -712,10 +1169,10 @@ insert_bdm (unsigned long insn,
 
 static long
 extract_bdm (unsigned long insn,
-            int dialect,
+            ppc_cpu_t dialect,
             int *invalid)
 {
-  if ((dialect & PPC_OPCODE_POWER4) == 0)
+  if ((dialect & ISA_V2) == 0)
     {
       if (((insn & (1 << 21)) == 0) != ((insn & (1 << 15)) == 0))
        *invalid = 1;
@@ -737,10 +1194,10 @@ extract_bdm (unsigned long insn,
 static unsigned long
 insert_bdp (unsigned long insn,
            long value,
-           int dialect,
+           ppc_cpu_t dialect,
            const char **errmsg ATTRIBUTE_UNUSED)
 {
-  if ((dialect & PPC_OPCODE_POWER4) == 0)
+  if ((dialect & ISA_V2) == 0)
     {
       if ((value & 0x8000) == 0)
        insn |= 1 << 21;
@@ -757,10 +1214,10 @@ insert_bdp (unsigned long insn,
 
 static long
 extract_bdp (unsigned long insn,
-            int dialect,
+            ppc_cpu_t dialect,
             int *invalid)
 {
-  if ((dialect & PPC_OPCODE_POWER4) == 0)
+  if ((dialect & ISA_V2) == 0)
     {
       if (((insn & (1 << 21)) == 0) == ((insn & (1 << 15)) == 0))
        *invalid = 1;
@@ -775,55 +1232,70 @@ extract_bdp (unsigned long insn,
   return ((insn & 0xfffc) ^ 0x8000) - 0x8000;
 }
 
+static inline int
+valid_bo_pre_v2 (long value)
+{
+  /* Certain encodings have bits that are required to be zero.
+     These are (z must be zero, y may be anything):
+        0000y
+        0001y
+        001zy
+        0100y
+        0101y
+        011zy
+        1z00y
+        1z01y
+        1z1zz
+  */
+  if ((value & 0x14) == 0)
+    return 1;
+  else if ((value & 0x14) == 0x4)
+    return (value & 0x2) == 0;
+  else if ((value & 0x14) == 0x10)
+    return (value & 0x8) == 0;
+  else
+    return value == 0x14;
+}
+
+static inline int
+valid_bo_post_v2 (long value)
+{
+  /* Certain encodings have bits that are required to be zero.
+     These are (z must be zero, a & t may be anything):
+        0000z
+        0001z
+        001at
+        0100z
+        0101z
+        011at
+        1a00t
+        1a01t
+        1z1zz
+  */
+  if ((value & 0x14) == 0)
+    return (value & 0x1) == 0;
+  else if ((value & 0x14) == 0x14)
+    return value == 0x14;
+  else
+    return 1;
+}
+
 /* Check for legal values of a BO field.  */
 
 static int
-valid_bo (long value, int dialect)
+valid_bo (long value, ppc_cpu_t dialect, int extract)
 {
-  if ((dialect & PPC_OPCODE_POWER4) == 0)
-    {
-      /* Certain encodings have bits that are required to be zero.
-        These are (z must be zero, y may be anything):
-            001zy
-            011zy
-            1z00y
-            1z01y
-            1z1zz
-      */
-      switch (value & 0x14)
-       {
-       default:
-       case 0:
-         return 1;
-       case 0x4:
-         return (value & 0x2) == 0;
-       case 0x10:
-         return (value & 0x8) == 0;
-       case 0x14:
-         return value == 0x14;
-       }
-    }
+  int valid_y = valid_bo_pre_v2 (value);
+  int valid_at = valid_bo_post_v2 (value);
+
+  /* When disassembling with -Many, accept either encoding on the
+     second pass through opcodes.  */
+  if (extract && dialect == ~(ppc_cpu_t) PPC_OPCODE_ANY)
+    return valid_y || valid_at;
+  if ((dialect & ISA_V2) == 0)
+    return valid_y;
   else
-    {
-      /* Certain encodings have bits that are required to be zero.
-        These are (z must be zero, a & t may be anything):
-            0000z
-            0001z
-            0100z
-            0101z
-            001at
-            011at
-            1a00t
-            1a01t
-            1z1zz
-      */
-      if ((value & 0x14) == 0)
-       return (value & 0x1) == 0;
-      else if ((value & 0x14) == 0x14)
-       return value == 0x14;
-      else
-       return 1;
-    }
+    return valid_at;
 }
 
 /* The BO field in a B form instruction.  Warn about attempts to set
@@ -832,23 +1304,25 @@ valid_bo (long value, int dialect)
 static unsigned long
 insert_bo (unsigned long insn,
           long value,
-          int dialect,
+          ppc_cpu_t dialect,
           const char **errmsg)
 {
-  if (!valid_bo (value, dialect))
+  if (!valid_bo (value, dialect, 0))
     *errmsg = _("invalid conditional option");
+  else if (PPC_OP (insn) == 19 && (insn & 0x400) && ! (value & 4))
+    *errmsg = _("invalid counter access");
   return insn | ((value & 0x1f) << 21);
 }
 
 static long
 extract_bo (unsigned long insn,
-           int dialect,
+           ppc_cpu_t dialect,
            int *invalid)
 {
   long value;
 
   value = (insn >> 21) & 0x1f;
-  if (!valid_bo (value, dialect))
+  if (!valid_bo (value, dialect, 1))
     *invalid = 1;
   return value;
 }
@@ -860,11 +1334,13 @@ extract_bo (unsigned long insn,
 static unsigned long
 insert_boe (unsigned long insn,
            long value,
-           int dialect,
+           ppc_cpu_t dialect,
            const char **errmsg)
 {
-  if (!valid_bo (value, dialect))
+  if (!valid_bo (value, dialect, 0))
     *errmsg = _("invalid conditional option");
+  else if (PPC_OP (insn) == 19 && (insn & 0x400) && ! (value & 4))
+    *errmsg = _("invalid counter access");
   else if ((value & 1) != 0)
     *errmsg = _("attempt to set y bit when using + or - modifier");
 
@@ -873,166 +1349,73 @@ insert_boe (unsigned long insn,
 
 static long
 extract_boe (unsigned long insn,
-            int dialect,
+            ppc_cpu_t dialect,
             int *invalid)
 {
   long value;
 
   value = (insn >> 21) & 0x1f;
-  if (!valid_bo (value, dialect))
+  if (!valid_bo (value, dialect, 1))
     *invalid = 1;
   return value & 0x1e;
 }
 
-/* The DQ field in a DQ form instruction.  This is like D, but the
-   lower four bits are forced to zero. */
-
-static unsigned long
-insert_dq (unsigned long insn,
-          long value,
-          int dialect ATTRIBUTE_UNUSED,
-          const char **errmsg)
-{
-  if ((value & 0xf) != 0)
-    *errmsg = _("offset not a multiple of 16");
-  return insn | (value & 0xfff0);
-}
-
-static long
-extract_dq (unsigned long insn,
-           int dialect ATTRIBUTE_UNUSED,
-           int *invalid ATTRIBUTE_UNUSED)
-{
-  return ((insn & 0xfff0) ^ 0x8000) - 0x8000;
-}
+/* The DCMX field in a X form instruction when the field is split
+   into separate DC, DM and DX fields.  */
 
 static unsigned long
-insert_ev2 (unsigned long insn,
+insert_dcmxs (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
-           const char **errmsg)
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           const char **errmsg ATTRIBUTE_UNUSED)
 {
-  if ((value & 1) != 0)
-    *errmsg = _("offset not a multiple of 2");
-  if ((value > 62) != 0)
-    *errmsg = _("offset greater than 62");
-  return insn | ((value & 0x3e) << 10);
+  return insn | ((value & 0x1f) << 16) | ((value & 0x20) >> 3) | (value & 0x40);
 }
 
 static long
-extract_ev2 (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+extract_dcmxs (unsigned long insn,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid ATTRIBUTE_UNUSED)
 {
-  return (insn >> 10) & 0x3e;
-}
-
-static unsigned long
-insert_ev4 (unsigned long insn,
-           long value,
-           int dialect ATTRIBUTE_UNUSED,
-           const char **errmsg)
-{
-  if ((value & 3) != 0)
-    *errmsg = _("offset not a multiple of 4");
-  if ((value > 124) != 0)
-    *errmsg = _("offset greater than 124");
-  return insn | ((value & 0x7c) << 9);
+  return (insn & 0x40) | ((insn << 3) & 0x20) | ((insn >> 16) & 0x1f);
 }
 
-static long
-extract_ev4 (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
-            int *invalid ATTRIBUTE_UNUSED)
-{
-  return (insn >> 9) & 0x7c;
-}
+/* The D field in a DX form instruction when the field is split
+   into separate D0, D1 and D2 fields.  */
 
 static unsigned long
-insert_ev8 (unsigned long insn,
+insert_dxd (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
-           const char **errmsg)
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           const char **errmsg ATTRIBUTE_UNUSED)
 {
-  if ((value & 7) != 0)
-    *errmsg = _("offset not a multiple of 8");
-  if ((value > 248) != 0)
-    *errmsg = _("offset greater than 248");
-  return insn | ((value & 0xf8) << 8);
+  return insn | (value & 0xffc1) | ((value & 0x3e) << 15);
 }
 
 static long
-extract_ev8 (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+extract_dxd (unsigned long insn,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid ATTRIBUTE_UNUSED)
 {
-  return (insn >> 8) & 0xf8;
-}
-
-/* The DS field in a DS form instruction.  This is like D, but the
-   lower two bits are forced to zero.  */
-
-static unsigned long
-insert_ds (unsigned long insn,
-          long value,
-          int dialect ATTRIBUTE_UNUSED,
-          const char **errmsg)
-{
-  if ((value & 3) != 0)
-    *errmsg = _("offset not a multiple of 4");
-  return insn | (value & 0xfffc);
-}
-
-static long
-extract_ds (unsigned long insn,
-           int dialect ATTRIBUTE_UNUSED,
-           int *invalid ATTRIBUTE_UNUSED)
-{
-  return ((insn & 0xfffc) ^ 0x8000) - 0x8000;
-}
-
-/* The DE field in a DE form instruction.  */
-
-static unsigned long
-insert_de (unsigned long insn,
-          long value,
-          int dialect ATTRIBUTE_UNUSED,
-          const char **errmsg)
-{
-  if (value > 2047 || value < -2048)
-    *errmsg = _("offset not between -2048 and 2047");
-  return insn | ((value << 4) & 0xfff0);
-}
-
-static long
-extract_de (unsigned long insn,
-           int dialect ATTRIBUTE_UNUSED,
-           int *invalid ATTRIBUTE_UNUSED)
-{
-  return (insn & 0xfff0) >> 4;
+  unsigned long dxd = (insn & 0xffc1) | ((insn >> 15) & 0x3e);
+  return (dxd ^ 0x8000) - 0x8000;
 }
 
-/* The DES field in a DES form instruction.  */
-
 static unsigned long
-insert_des (unsigned long insn,
+insert_dxdn (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
-           const char **errmsg)
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           const char **errmsg ATTRIBUTE_UNUSED)
 {
-  if (value > 8191 || value < -8192)
-    *errmsg = _("offset not between -8192 and 8191");
-  else if ((value & 3) != 0)
-    *errmsg = _("offset not a multiple of 4");
-  return insn | ((value << 2) & 0xfff0);
+  return insert_dxd (insn, -value, dialect, errmsg);
 }
 
 static long
-extract_des (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+extract_dxdn (unsigned long insn,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid ATTRIBUTE_UNUSED)
 {
-  return (((insn >> 2) & 0x3ffc) ^ 0x2000) - 0x2000;
+  return -extract_dxd (insn, dialect, invalid);
 }
 
 /* FXM mask in mfcr and mtcrf instructions.  */
@@ -1040,7 +1423,7 @@ extract_des (unsigned long insn,
 static unsigned long
 insert_fxm (unsigned long insn,
            long value,
-           int dialect,
+           ppc_cpu_t dialect,
            const char **errmsg)
 {
   /* If we're handling the mfocrf and mtocrf insns ensure that exactly
@@ -1054,19 +1437,13 @@ insert_fxm (unsigned long insn,
        }
     }
 
-  /* If the optional field on mfcr is missing that means we want to use
-     the old form of the instruction that moves the whole cr.  In that
-     case we'll have VALUE zero.  There doesn't seem to be a way to
-     distinguish this from the case where someone writes mfcr %r3,0.  */
-  else if (value == 0)
-    ;
-
   /* If only one bit of the FXM field is set, we can use the new form
      of the instruction, which is faster.  Unlike the Power4 branch hint
      encoding, this is not backward compatible.  Do not generate the
      new form unless -mpower4 has been given, or -many and the two
      operand form of mfcr was used.  */
-  else if ((value & -value) == value
+  else if (value > 0
+          && (value & -value) == value
           && ((dialect & PPC_OPCODE_POWER4) != 0
               || ((dialect & PPC_OPCODE_ANY) != 0
                   && (insn & (0x3ff << 1)) == 19 << 1)))
@@ -1075,7 +1452,10 @@ insert_fxm (unsigned long insn,
   /* Any other value on mfcr is an error.  */
   else if ((insn & (0x3ff << 1)) == 19 << 1)
     {
-      *errmsg = _("ignoring invalid mfcr mask");
+      /* A value of -1 means we used the one operand form of
+        mfcr which is valid.  */
+      if (value != -1)
+        *errmsg = _("invalid mfcr mask");
       value = 0;
     }
 
@@ -1084,7 +1464,7 @@ insert_fxm (unsigned long insn,
 
 static long
 extract_fxm (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid)
 {
   long mask = (insn >> 12) & 0xff;
@@ -1102,31 +1482,86 @@ extract_fxm (unsigned long insn,
     {
       if (mask != 0)
        *invalid = 1;
+      else
+       mask = -1;
     }
 
   return mask;
 }
 
-/* The LI field in an I form instruction.  The lower two bits are
-   forced to zero.  */
+static unsigned long
+insert_li20 (unsigned long insn,
+            long value,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+            const char **errmsg ATTRIBUTE_UNUSED)
+{
+  return insn | ((value & 0xf0000) >> 5) | ((value & 0x0f800) << 5) | (value & 0x7ff);
+}
+
+static long
+extract_li20 (unsigned long insn,
+             ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+             int *invalid ATTRIBUTE_UNUSED)
+{
+  long ext = ((insn & 0x4000) == 0x4000) ? 0xfff00000 : 0x00000000;
+
+  return ext
+         | (((insn >> 11) & 0xf) << 16)
+         | (((insn >> 17) & 0xf) << 12)
+         | (((insn >> 16) & 0x1) << 11)
+         | (insn & 0x7ff);
+}
+
+/* The 2-bit L field in a SYNC or WC field in a WAIT instruction.
+   For SYNC, some L values are reserved:
+     * Value 3 is reserved on newer server cpus.
+     * Values 2 and 3 are reserved on all other cpus.  */
 
 static unsigned long
-insert_li (unsigned long insn,
+insert_ls (unsigned long insn,
           long value,
-          int dialect ATTRIBUTE_UNUSED,
+          ppc_cpu_t dialect,
           const char **errmsg)
 {
-  if ((value & 3) != 0)
-    *errmsg = _("ignoring least significant bits in branch offset");
-  return insn | (value & 0x3fffffc);
+  /* For SYNC, some L values are illegal.  */
+  if (((insn >> 1) & 0x3ff) == 598)
+    {
+      long max_lvalue = (dialect & PPC_OPCODE_POWER4) ? 2 : 1;
+      if (value > max_lvalue)
+       {
+         *errmsg = _("illegal L operand value");
+         return insn;
+       }
+    }
+
+  return insn | ((value & 0x3) << 21);
 }
 
-static long
-extract_li (unsigned long insn,
-           int dialect ATTRIBUTE_UNUSED,
-           int *invalid ATTRIBUTE_UNUSED)
+/* The 4-bit E field in a sync instruction that accepts 2 operands.
+   If ESYNC is non-zero, then the L field must be either 0 or 1 and
+   the complement of ESYNC-bit2.  */
+
+static unsigned long
+insert_esync (unsigned long insn,
+             long value,
+             ppc_cpu_t dialect,
+             const char **errmsg)
 {
-  return ((insn & 0x3fffffc) ^ 0x2000000) - 0x2000000;
+  unsigned long ls = (insn >> 21) & 0x03;
+
+  if (value == 0)
+    {
+      if (((dialect & PPC_OPCODE_E6500) != 0 && ls > 1)
+         || ((dialect & PPC_OPCODE_POWER9) != 0 && ls > 2))
+        *errmsg = _("illegal L operand value");
+      return insn;
+    }
+
+  if ((ls & ~0x1)
+      || (((value >> 1) & 0x1) ^ ls) == 0)
+        *errmsg = _("incompatible L operand value");
+
+  return insn | ((value & 0xf) << 16);
 }
 
 /* The MB and ME fields in an M form instruction expressed as a single
@@ -1137,7 +1572,7 @@ extract_li (unsigned long insn,
 static unsigned long
 insert_mbe (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char **errmsg)
 {
   unsigned long uval, mask;
@@ -1189,7 +1624,7 @@ insert_mbe (unsigned long insn,
 
 static long
 extract_mbe (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid)
 {
   long ret;
@@ -1223,7 +1658,7 @@ extract_mbe (unsigned long insn,
 static unsigned long
 insert_mb6 (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char **errmsg ATTRIBUTE_UNUSED)
 {
   return insn | ((value & 0x1f) << 6) | (value & 0x20);
@@ -1231,7 +1666,7 @@ insert_mb6 (unsigned long insn,
 
 static long
 extract_mb6 (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid ATTRIBUTE_UNUSED)
 {
   return ((insn >> 6) & 0x1f) | (insn & 0x20);
@@ -1240,22 +1675,9 @@ extract_mb6 (unsigned long insn,
 /* The NB field in an X form instruction.  The value 32 is stored as
    0.  */
 
-static unsigned long
-insert_nb (unsigned long insn,
-          long value,
-          int dialect ATTRIBUTE_UNUSED,
-          const char **errmsg)
-{
-  if (value < 0 || value > 32)
-    *errmsg = _("value out of range");
-  if (value == 32)
-    value = 0;
-  return insn | ((value & 0x1f) << 11);
-}
-
 static long
 extract_nb (unsigned long insn,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            int *invalid ATTRIBUTE_UNUSED)
 {
   long ret;
@@ -1266,6 +1688,26 @@ extract_nb (unsigned long insn,
   return ret;
 }
 
+/* The NB field in an lswi instruction, which has special value
+   restrictions.  The value 32 is stored as 0.  */
+
+static unsigned long
+insert_nbi (unsigned long insn,
+           long value,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
+           const char **errmsg ATTRIBUTE_UNUSED)
+{
+  long rtvalue = (insn & RT_MASK) >> 21;
+  long ravalue = (insn & RA_MASK) >> 16;
+
+  if (value == 0)
+    value = 32;
+  if (rtvalue + (value + 3) / 4 > (rtvalue > ravalue ? ravalue + 32
+                                                    : ravalue))
+    *errmsg = _("address register in load range");
+  return insn | ((value & 0x1f) << 11);
+}
+
 /* The NSI field in a D form instruction.  This is the same as the SI
    field, only negated.  The extraction function always marks it as
    invalid, since we never want to recognize an instruction which uses
@@ -1274,7 +1716,7 @@ extract_nb (unsigned long insn,
 static unsigned long
 insert_nsi (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char **errmsg ATTRIBUTE_UNUSED)
 {
   return insn | (-value & 0xffff);
@@ -1282,7 +1724,7 @@ insert_nsi (unsigned long insn,
 
 static long
 extract_nsi (unsigned long insn,
-            int dialect ATTRIBUTE_UNUSED,
+            ppc_cpu_t dialect ATTRIBUTE_UNUSED,
             int *invalid)
 {
   *invalid = 1;
@@ -1296,7 +1738,7 @@ extract_nsi (unsigned long insn,
 static unsigned long
 insert_ral (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char **errmsg)
 {
   if (value == 0
@@ -1311,7 +1753,7 @@ insert_ral (unsigned long insn,
 static unsigned long
 insert_ram (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char **errmsg)
 {
   if ((unsigned long) value >= ((insn >> 21) & 0x1f))
@@ -1319,13 +1761,13 @@ insert_ram (unsigned long insn,
   return insn | ((value & 0x1f) << 16);
 }
 
-/* The RA field in the DQ form lq instruction, which has special
+/* The RA field in the DQ form lq or an lswx instruction, which have special
    value restrictions.  */
 
 static unsigned long
 insert_raq (unsigned long insn,
            long value,
-           int dialect ATTRIBUTE_UNUSED,
+           ppc_cpu_t dialect ATTRIBUTE_UNUSED,
            const char