LinuxPPC-Dev Archive on lore.kernel.org
 help / color / mirror / Atom feed
* Re: power management patch set for mpc85xx
From: Kumar Gala @ 2012-06-01 14:01 UTC (permalink / raw)
  To: Zhao Chenhui-B35336
  Cc: Scott Wood, Paul Mackerras, linuxppc-dev@lists.ozlabs.org list,
	Li Yang-R58472
In-Reply-To: <7AA2FF042C086D469F577FA6723434DA058123@039-SN1MPN1-002.039d.mgd.msft.net>


On Jun 1, 2012, at 5:29 AM, Zhao Chenhui-B35336 wrote:

> Hi Ben and Paul,
> 
> I am sorry to trouble you. It seems that Kumar is busy recently.
> 
> Could you have a review on the following patches? These patches
> implement the power management support on MPC85xx platform.
> 
> http://patchwork.ozlabs.org/patch/158484/
> http://patchwork.ozlabs.org/patch/158485/
> http://patchwork.ozlabs.org/patch/158487/
> http://patchwork.ozlabs.org/patch/158486/
> http://patchwork.ozlabs.org/patch/158488/

I have been, but was looking for Scott's Ack on these.

- k

^ permalink raw reply

* Re: [PATCH v5 1/5] powerpc/85xx: implement hardware timebase sync
From: Scott Wood @ 2012-06-01 15:40 UTC (permalink / raw)
  To: Zhao Chenhui; +Cc: linuxppc-dev, linux-kernel
In-Reply-To: <1336737235-15370-1-git-send-email-chenhui.zhao@freescale.com>

On 05/11/2012 06:53 AM, Zhao Chenhui wrote:
>  #ifdef CONFIG_KEXEC
> +static struct ccsr_guts __iomem *guts;
> +static u64 timebase;
> +static int tb_req;
> +static int tb_valid;
> +
> +static void mpc85xx_timebase_freeze(int freeze)

Why is this under CONFIG_KEXEC?  It'll also be needed for CPU hotplug.

> +{
> +	unsigned int mask;
> +
> +	if (!guts)
> +		return;
> +
> +	mask = CCSR_GUTS_DEVDISR_TB0 | CCSR_GUTS_DEVDISR_TB1;
> +	if (freeze)
> +		setbits32(&guts->devdisr, mask);
> +	else
> +		clrbits32(&guts->devdisr, mask);
> +
> +	in_be32(&guts->devdisr);
> +}
> +
> +static void mpc85xx_give_timebase(void)
> +{
> +	unsigned long flags;
> +
> +	local_irq_save(flags);
> +
> +	while (!tb_req)
> +		barrier();
> +	tb_req = 0;
> +
> +	mpc85xx_timebase_freeze(1);
> +	timebase = get_tb();
> +	mb();
> +	tb_valid = 1;
> +
> +	while (tb_valid)
> +		barrier();
> +
> +	mpc85xx_timebase_freeze(0);
> +
> +	local_irq_restore(flags);
> +}
> +
> +static void mpc85xx_take_timebase(void)
> +{
> +	unsigned long flags;
> +
> +	local_irq_save(flags);
> +
> +	tb_req = 1;
> +	while (!tb_valid)
> +		barrier();
> +
> +	set_tb(timebase >> 32, timebase & 0xffffffff);
> +	mb();
> +	tb_valid = 0;
> +
> +	local_irq_restore(flags);
> +}

I know you say this is for dual-core chips only, but it would be nice if
you'd write this in a way that doesn't assume that (even if the
corenet-specific timebase freezing comes later).

Do we need an isync after setting the timebase, to ensure it's happened
before we enable the timebase?  Likewise, do we need a readback after
disabling the timebase to ensure it's disabled before we read the
timebase in give_timebase?

>  atomic_t kexec_down_cpus = ATOMIC_INIT(0);
>  
>  void mpc85xx_smp_kexec_cpu_down(int crash_shutdown, int secondary)
> @@ -228,6 +286,20 @@ smp_85xx_setup_cpu(int cpu_nr)
>  		doorbell_setup_this_cpu();
>  }
>  
> +#ifdef CONFIG_KEXEC
> +static const struct of_device_id guts_ids[] = {
> +	{ .compatible = "fsl,mpc8572-guts", },
> +	{ .compatible = "fsl,mpc8560-guts", },
> +	{ .compatible = "fsl,mpc8536-guts", },
> +	{ .compatible = "fsl,p1020-guts", },
> +	{ .compatible = "fsl,p1021-guts", },
> +	{ .compatible = "fsl,p1022-guts", },
> +	{ .compatible = "fsl,p1023-guts", },
> +	{ .compatible = "fsl,p2020-guts", },
> +	{},
> +};
> +#endif

MPC8560 and MPC8536 are single-core...

Also please use a more specific name, such as e500v2_smp_guts_ids or
mpc85xx_smp_guts_ids -- when corenet support is added it will likely be
in the same file.

>  void __init mpc85xx_smp_init(void)
>  {
>  	struct device_node *np;
> @@ -249,6 +321,19 @@ void __init mpc85xx_smp_init(void)
>  		smp_85xx_ops.cause_ipi = doorbell_cause_ipi;
>  	}
>  
> +#ifdef CONFIG_KEXEC
> +	np = of_find_matching_node(NULL, guts_ids);
> +	if (np) {
> +		guts = of_iomap(np, 0);
> +		smp_85xx_ops.give_timebase = mpc85xx_give_timebase;
> +		smp_85xx_ops.take_timebase = mpc85xx_take_timebase;
> +		of_node_put(np);
> +	} else {
> +		smp_85xx_ops.give_timebase = smp_generic_give_timebase;
> +		smp_85xx_ops.take_timebase = smp_generic_take_timebase;
> +	}

Do not use smp_generic_give/take_timebase, ever.  If you don't have the
guts node, then just assume the timebase is already synced.

-Scott

^ permalink raw reply

* Re: [RFC] [PATCH] powerpc: Add MSR_DE to MSR_KERNEL
From: Scott Wood @ 2012-06-01 16:28 UTC (permalink / raw)
  To: Benjamin Herrenschmidt; +Cc: linuxppc-dev, Bob Cochran, support
In-Reply-To: <1338542089.16119.48.camel@pasglop>

On 06/01/2012 04:14 AM, Benjamin Herrenschmidt wrote:
> On Wed, 2012-05-30 at 09:26 -0400, Bob Cochran wrote:
>> I believe that additional patches are required for CodeWarrior to
>> work 
>> properly (e.g., assembly start up).  I think the patches should come 
>> from Freescale.  For whatever reason, they include them in their SDK, 
>> but haven't submitted them for inclusion in the mainline.
>>
>> As a developer on Freescale Power products, I would like to see 
>> Freescale offer up a CodeWarrior patch set, so I don't have to manage 
>> the patches myself when working outside the SDK (i.e., on a more
>> recent 
>> kernel).
> 
> Such patches would have a hard time getting upstream considering that
> codewarrior is a commercial product.

It's not really about CodeWarrior -- it's needed for any external debug
on these chips.

Those chips are commercial products too, BTW. :-)

-Scott

^ permalink raw reply

* Re: [PATCH 03/27] smpboot: Define and use cpu_state per-cpu variable in generic code
From: David Daney @ 2012-06-01 16:59 UTC (permalink / raw)
  To: Srivatsa S. Bhat
  Cc: Venkatesh Pallipadi, Jeremy Fitzhardinge, linux-ia64, linux-mips,
	peterz, linux-kernel, H. Peter Anvin, mingo, linux-arch,
	xen-devel, Suresh Siddha, linux-sh, x86, Ingo Molnar, paulmck,
	Fenghua Yu, Mike Frysinger, Peter Zijlstra, nikunj,
	Konrad Rzeszutek Wilk, rusty, Chris Metcalf, rjw, yong.zhang0,
	tglx, virtualization, Tony Luck, vatsa, Ralf Baechle, Paul Mundt,
	akpm, linuxppc-dev
In-Reply-To: <20120601091038.31979.67878.stgit@srivatsabhat.in.ibm.com>

On 06/01/2012 02:10 AM, Srivatsa S. Bhat wrote:
> The per-cpu variable cpu_state is used in x86 and also used in other
> architectures, to track the state of the cpu during bringup and hotplug.
> Pull it out into generic code.
>
> Cc: Tony Luck<tony.luck@intel.com>
> Cc: Fenghua Yu<fenghua.yu@intel.com>
> Cc: Ralf Baechle<ralf@linux-mips.org>
> Cc: Benjamin Herrenschmidt<benh@kernel.crashing.org>
> Cc: Paul Mundt<lethal@linux-sh.org>
> Cc: Chris Metcalf<cmetcalf@tilera.com>
> Cc: Thomas Gleixner<tglx@linutronix.de>
> Cc: Ingo Molnar<mingo@redhat.com>
> Cc: "H. Peter Anvin"<hpa@zytor.com>
> Cc: x86@kernel.org
> Cc: Konrad Rzeszutek Wilk<konrad.wilk@oracle.com>
> Cc: Jeremy Fitzhardinge<jeremy@goop.org>
> Cc: Peter Zijlstra<a.p.zijlstra@chello.nl>
> Cc: Andrew Morton<akpm@linux-foundation.org>
> Cc: Mike Frysinger<vapier@gentoo.org>
> Cc: Yong Zhang<yong.zhang0@gmail.com>
> Cc: Venkatesh Pallipadi<venki@google.com>
> Cc: Suresh Siddha<suresh.b.siddha@intel.com>
> Cc: linux-ia64@vger.kernel.org
> Cc: linux-mips@linux-mips.org
> Cc: linuxppc-dev@lists.ozlabs.org
> Cc: linux-sh@vger.kernel.org
> Cc: xen-devel@lists.xensource.com
> Cc: virtualization@lists.linux-foundation.org
> Signed-off-by: Srivatsa S. Bhat<srivatsa.bhat@linux.vnet.ibm.com>
> ---
>
>   arch/ia64/include/asm/cpu.h   |    2 --
>   arch/ia64/kernel/process.c    |    1 +
>   arch/ia64/kernel/smpboot.c    |    6 +-----
>   arch/mips/cavium-octeon/smp.c |    4 +---
>   arch/powerpc/kernel/smp.c     |    6 +-----
>   arch/sh/include/asm/smp.h     |    2 --
>   arch/sh/kernel/smp.c          |    4 +---
>   arch/tile/kernel/smpboot.c    |    4 +---
>   arch/x86/include/asm/cpu.h    |    2 --
>   arch/x86/kernel/smpboot.c     |    4 +---
>   arch/x86/xen/smp.c            |    1 +
>   include/linux/smpboot.h       |    1 +
>   kernel/smpboot.c              |    4 ++++
>   13 files changed, 13 insertions(+), 28 deletions(-)
>
[...]
> diff --git a/arch/mips/cavium-octeon/smp.c b/arch/mips/cavium-octeon/smp.c
> index 97e7ce9..93cd4b0 100644
> --- a/arch/mips/cavium-octeon/smp.c
> +++ b/arch/mips/cavium-octeon/smp.c
> @@ -13,6 +13,7 @@
>   #include<linux/kernel_stat.h>
>   #include<linux/sched.h>
>   #include<linux/module.h>
> +#include<linux/smpboot.h>
>
>   #include<asm/mmu_context.h>
>   #include<asm/time.h>
> @@ -252,9 +253,6 @@ static void octeon_cpus_done(void)
>
>   #ifdef CONFIG_HOTPLUG_CPU
>
> -/* State of each CPU. */
> -DEFINE_PER_CPU(int, cpu_state);
> -
>   extern void fixup_irqs(void);
>
>   static DEFINE_SPINLOCK(smp_reserve_lock);

The Octeon bit:

Acked-by: David Daney <david.daney@cavium.com>


FWIW, the rest looks good too.

^ permalink raw reply

* Serial RAPID IO kernel hang on maintenance read transaction
From: Proicou, Mike @ 2012-06-01 20:40 UTC (permalink / raw)
  To: linuxppc-dev@lists.ozlabs.org

[-- Attachment #1: Type: text/plain, Size: 9198 bytes --]


I've been struggling with a kernel hang during bootup + enumeration of a Rapid IO system.

My current system contains a N.A.T MCH (using the IDT/Tundra Tsi 578 switch) and a Vadatech AMC719 card using the Freescale P4080 processor.  There will be other cards added to the system, but I'm testing with just this for now.

I'm using a Linux kernel version 2.6.34.6.  I've set riohdid=0 on the kernel command line, and I'm expecting Linux to fully enumerate and configure the Rapid IO fabric. (This may be a bad assumption on my part.)

After lots of tracing, I've determined that the kernel is hanging on the first maintenance transaction to the switch.  The hang will often be followed by a "machine check in kernel mode" exception and panic.

 This is very similar to the behavior reported in this mailing list  thread from 2010: http://lists.ozlabs.org/pipermail/linuxppc-dev/2010-October/086235.html  I've read that thread several times and tries most of the suggestions, but they don't appear to apply in my hardware configuration.linu



Is it possible that something in the switch isn't completely initialized at the time that Linux tries to do the maintenance transaction?  If so, how do I find it?

Here's the console  log for a bootup using the supplied kernel:

Freescale XGMAC MDIO Bus: probed
Setting up RapidIO peer-to-peer network /rapidio@ffe0c0000
fsl-of-rio ffe0c0000.rapidio: Of-device full name /rapidio@ffe0c0000
fsl-of-rio ffe0c0000.rapidio: Regs: [mem 0xffe0c0000-0xffe0dffff]
fsl-of-rio ffe0c0000.rapidio: LAW start 0x0000000c20000000, size 0x0000000001000000.
fsl-of-rio ffe0c0000.rapidio: errirq: 16, bellirq: 57, txirq: 60, rxirq 61
fsl-of-rio ffe0c0000.rapidio: RapidIO PHY type: serial
SRIO Port 1 Status: Lane0Sync Lane1Sync Lane2Sync Lane3Sync Aligned
SRIO Port 2 Status: (Note: Freescale driver only supports Port 1)
fsl-of-rio ffe0c0000.rapidio: Hardware port width: 4
fsl-of-rio ffe0c0000.rapidio: Training connection status: Four-lane
fsl-of-rio ffe0c0000.rapidio: RapidIO Common Transport System size: 256
RIO: enumerate master port 0, RIO0 mport
Machine check in kernel mode.
RIO: port1 error
Caused by (from MCSR=a000): Load Error Report
Guarded Load Error Report
Oops: Machine check, sig: 7 [#1]
SMP NR_CPUS=8 amc718_based
last sysfs file:
Modules linked in:
NIP: c001a460 LR: c01ee41c CTR: c001a420
REGS: effc9f10 TRAP: 0204   Not tainted  (2.6.34.6-vt3-svn36835)
MSR: 00021002 <ME,CE>  CR: 24022024  XER: 00000000
TASK = ebc68000[1] 'swapper' THREAD: ebc62000 CPU: 6
GPR00: f1200000 ebc63d10 ebc68000 00000000 00000000 3fc00000 3fc00000 f1200068
GPR08: 00000004 ebc63d18 f1190c20 eb530000 24022022 d811c00a 00000000 00000000
GPR16: 00000000 7ffe2a00 00000000 00000000 7fff0df0 00000000 00000000 00000000
GPR24: 00000081 000000ff 00000000 ebd89400 00000068 00029002 c05e8914 ebc63d58
NIP [c001a460] fsl_rio_config_read+0x40/0x78
LR [c01ee41c] rio_mport_read_config_32+0x7c/0xac
Call Trace:
[ebc63d50] [c01eed64] rio_get_host_deviceid_lock+0x3c/0x50
[ebc63d70] [c045acd4] rio_enum_peer+0x28/0x3e4
[ebc63dd0] [c045b178] rio_enum_mport+0xe8/0x244
[ebc63e10] [c045a59c] rio_init_mports+0x90/0xe4
[ebc63e30] [c0457a5c] fsl_of_rio_rpn_probe+0x3c/0x50
[ebc63e40] [c034abe4] of_platform_device_probe+0x58/0x98
[ebc63e60] [c02274d8] driver_probe_device+0xa4/0x1b4
[ebc63e80] [c02260cc] bus_for_each_drv+0x6c/0xa8
[ebc63eb0] [c022735c] device_attach+0xa4/0xc8
[ebc63ed0] [c0226afc] bus_probe_device+0x2c/0x44
[ebc63ee0] [c02245f8] device_add+0x460/0x5a8
[ebc63f30] [c034a750] of_device_register+0x34/0x48
[ebc63f40] [c0008d64] of_platform_device_create+0x44/0x74
[ebc63f50] [c0008f90] of_platform_bus_probe+0x130/0x15c
[ebc63f70] [c0565480] declare_of_platform_devices+0x24/0x140
[ebc63f90] [c05651cc] __machine_initcall_amc718_based_declare_of_platform_devices+0x2c/0x3c
[ebc63fa0] [c0001cb8] do_one_initcall+0x3c/0x1d0
[ebc63fd0] [c055e9b0] kernel_init+0x190/0x230
[ebc63ff0] [c000f284] kernel_thread+0x4c/0x68
Instruction dump:
814b000c 54e0ba7e 7cc60378 7c0004ac 90ca0000 2f880001 800b0018 7ce03a14
419e0020 2f880002 419e002c 38600000 <80e70000> 7c2006ac 90e90000 4e800020
---[ end trace 561bb236c800851f ]---
Kernel panic - not syncing: Attempted to kill init!
Call Trace:
Rebooting in 180 seconds..

Here's a partial log with some additional output and a dump of the error registers at the time of failure:



fsl-elo-dma ffe101300.dma: request channel 0 IRQ
fsl-elo-dma ffe101300.dma: request channel 1 IRQ
fsl-elo-dma ffe101300.dma: request channel 2 IRQ
fsl-elo-dma ffe101300.dma: request channel 3 IRQ
Freescale PowerQUICC MII Bus: probed
Freescale XGMAC MDIO Bus: probed
fsl-of-rio ffe0c0000.rapidio: Setting up RapidIO peer-to-peer network /rapidio@ffe0c0000
fsl-of-rio ffe0c0000.rapidio: Of-device full name /rapidio@ffe0c0000
fsl-of-rio ffe0c0000.rapidio: Regs: [mem 0xffe0c0000-0xffe0dffff]
fsl-of-rio ffe0c0000.rapidio: LAW start 0x0000000c20000000, size 0x0000000001000000
fsl-of-rio ffe0c0000.rapidio: get_immrbase() ffe000000
fsl-of-rio ffe0c0000.rapidio: IO c20000000 c20ffffff
  alloc irq_desc for 57 on node 0
  alloc kstat_irqs on node 0
irq: irq 57 on host /soc@ffe000000/pic@40000 mapped to virtual irq 57
  alloc irq_desc for 60 on node 0
  alloc kstat_irqs on node 0
irq: irq 60 on host /soc@ffe000000/pic@40000 mapped to virtual irq 60
  alloc irq_desc for 61 on node 0
  alloc kstat_irqs on node 0
irq: irq 61 on host /soc@ffe000000/pic@40000 mapped to virtual irq 61
fsl-of-rio ffe0c0000.rapidio: errirq: 16, bellirq: 57, txirq: 60, rxirq 61
fsl-of-rio ffe0c0000.rapidio: Host deviceid 0
fsl-of-rio ffe0c0000.rapidio: RapidIO PHY type: serial
fsl-of-rio ffe0c0000.rapidio: SRIO Port 1 Status: Lane0Sync Lane1Sync Lane2Sync Lane3Sync Aligned
fsl-of-rio ffe0c0000.rapidio: SRIO Port 2 Status: (Note: Freescale driver only supports Port 1)
fsl-of-rio ffe0c0000.rapidio: Hardware port width: 4
fsl-of-rio ffe0c0000.rapidio: Training connection status: Four-lane
fsl-of-rio ffe0c0000.rapidio: RapidIO Common Transport System size: 256
RIO: enumerate master port 0, RIO0 mport
fsl_local_config_write: index 0 offset 00000068 data 00000000
fsl_local_config_read: index 0 offset 00000068 (ebc63da8) = 00000000
fsl_local_config_write: index 0 offset 00000060 data 00000000
fsl_local_config_read: index 0 offset 0000013c (ebc63da8) = e0000000
RIO0 mport PGCCSR e0000000
fsl_local_config_read: index 0 offset 0000000c (ebc63d58) = 00000100
fsl_local_config_read: index 0 offset 00000100 (ebc63d58) = 06000001
fsl_local_config_read: index 0 offset 00000158 (ebc63d88) = 00020302
fsl_local_config_read: index 0 offset 0000013c (ebc63da8) = e0000000
RIO0 mport is active PGCCSR e0000000
rio_enum_peer 1Machine check in kernel mode.
RIO: port1 error
 P1 error regs EDCSR 00000005 IECSR 00000000 ESCSR 00020302
   LTLEDCSR 00000000
Caused by (from MCSR=a000): Load Error Report
Guarded Load Error Report
Oops: Machine check, sig: 7 [#1]
SMP NR_CPUS=8 amc718_based
last sysfs file:
Modules linked in:
NIP: c001a838 LR: c01f201c CTR: c001a748
REGS: effc9f10 TRAP: 0204   Not tainted  (2.6.34.6-MCP-svn1717)
MSR: 00021002 <ME,CE>  CR: 24022022  XER: 00000000
TASK = ebc68000[1] 'swapper' THREAD: ebc62000 CPU: 6
GPR00: 00000068 ebc63cf0 ebc68000 ffffffea 00000000 000000ff 00000000 00000068
GPR08: 00000004 ebd80000 3fc00000 f1190c20 24022022 d814c00a 00000000 00000000
GPR16: 00000000 7ffe2a00 00000000 00000000 7fff0df0 00000000 00000000 00000000
GPR24: 00000081 000000ff f1200068 00000000 ebc63d18 00000000 000000ff 00000068
NIP [c001a838] fsl_rio_config_read+0xf0/0x11c
LR [c01f201c] rio_mport_read_config_32+0x7c/0xac
Call Trace:
[ebc63cf0] [7ffe2a00] 0x7ffe2a00 (unreliable)
[ebc63d10] [c01f201c] rio_mport_read_config_32+0x7c/0xac
[ebc63d50] [c01f28d0] rio_get_host_deviceid_lock+0x3c/0x60
[ebc63d70] [c045ec8c] rio_enum_peer+0x34/0x4c0
[ebc63dd0] [c045f228] rio_enum_mport+0x110/0x290
[ebc63e10] [c045e484] rio_init_mports+0x90/0xe4
[ebc63e30] [c045b944] fsl_of_rio_rpn_probe+0x4c/0x60
[ebc63e40] [c034ea48] of_platform_device_probe+0x58/0x98
[ebc63e60] [c022b334] driver_probe_device+0xa4/0x1b4
[ebc63e80] [c0229f28] bus_for_each_drv+0x6c/0xa8
[ebc63eb0] [c022b1b8] device_attach+0xa4/0xc8
[ebc63ed0] [c022a958] bus_probe_device+0x2c/0x44
[ebc63ee0] [c0228454] device_add+0x460/0x5a8
[ebc63f30] [c034e5b4] of_device_register+0x34/0x48
[ebc63f40] [c0008d64] of_platform_device_create+0x44/0x74
[ebc63f50] [c0008f90] of_platform_bus_probe+0x130/0x15c
[ebc63f70] [c056b534] declare_of_platform_devices+0x24/0x140
[ebc63f90] [c056b280] __machine_initcall_amc718_based_declare_of_platform_devices+0x2c/0x3c
[ebc63fa0] [c0001cb8] do_one_initcall+0x3c/0x1d0
[ebc63fd0] [c05649b0] kernel_init+0x190/0x230
[ebc63ff0] [c000f284] kernel_thread+0x4c/0x68
Instruction dump:
7fa6eb78 7fe7fb78 7f49d378 4843d975 2f9b0000 409e0028 935c0000 7f63db78
4bffff58 a35a0000 7c2006ac 4bffffc8 <835a0000> 7c2006ac 4bffffbc 3c60c04e
---[ end trace 561bb236c800851f ]---
Kernel panic - not syncing: Attempted to kill init!
Call Trace:
Rebooting in 180 seconds..

Thanks for any help ...

Mike Proicou


[-- Attachment #2: Type: text/html, Size: 10686 bytes --]

^ permalink raw reply

* Re: [PATCH v5 2/5] powerpc/85xx: add HOTPLUG_CPU support
From: Scott Wood @ 2012-06-01 21:27 UTC (permalink / raw)
  To: Zhao Chenhui; +Cc: linuxppc-dev, linux-kernel
In-Reply-To: <1336737235-15370-2-git-send-email-chenhui.zhao@freescale.com>

On 05/11/2012 06:53 AM, Zhao Chenhui wrote:
\> +#if defined(CONFIG_FSL_BOOKE) || defined(CONFIG_6xx)
> +extern void __flush_disable_L1(void);
> +#endif

Prototypes aren't normally guarded by ifdefs.

> +static void __cpuinit smp_85xx_mach_cpu_die(void)
> +{
> +	unsigned int cpu = smp_processor_id();
> +	u32 tmp;
> +
> +	local_irq_disable();
> +	idle_task_exit();
> +	generic_set_cpu_dead(cpu);
> +	mb();
> +
> +	mtspr(SPRN_TCR, 0);
> +
> +	__flush_disable_L1();
> +	tmp = (mfspr(SPRN_HID0) & ~(HID0_DOZE|HID0_SLEEP)) | HID0_NAP;
> +	mtspr(SPRN_HID0, tmp);
> +
> +	/* Enter NAP mode. */
> +	tmp = mfmsr();
> +	tmp |= MSR_WE;
> +	mb();
> +	mtmsr(tmp);
> +	isync();

Need isync after writing to HID0.

> +		/*
> +		 * We don't set the BPTR register here upon it points
> +		 * to the boot page properly.
> +		 */
> +		mpic_reset_core(hw_cpu);

That comment's wording is hard to follow -- maybe s/upon it points/since
it already points/

> +		/* wait until core is ready... */
> +		if (!spin_event_timeout(in_be32(&spin_table->addr_l) == 1,
> +						10000, 100)) {
> +			pr_err("%s: timeout waiting for core %d to reset\n",
> +							__func__, hw_cpu);
> +			ret = -ENOENT;
> +			goto out;
> +		}

We need to fix U-Boot to write addr_l last (with an msync beforehand).

> -#ifdef CONFIG_KEXEC
> +#if defined(CONFIG_KEXEC) || defined(CONFIG_HOTPLUG_CPU)

Let's not grow lists like this.  Is there any harm in building it
unconditionally?

-Scott

^ permalink raw reply

* Re: [PATCH v5 3/5] powerpc/85xx: add sleep and deep sleep support
From: Scott Wood @ 2012-06-01 21:54 UTC (permalink / raw)
  To: Zhao Chenhui; +Cc: linuxppc-dev, linux-kernel
In-Reply-To: <1336737235-15370-3-git-send-email-chenhui.zhao@freescale.com>

On 05/11/2012 06:53 AM, Zhao Chenhui wrote:
> From: Li Yang <leoli@freescale.com>
> 
> In sleep PM mode, the clocks of e500 core and unused IP blocks is
> turned off. IP blocks which are allowed to wake up the processor
> are still running.
> 
> Some Freescale chips like MPC8536 and P1022 has deep sleep PM mode
> in addtion to the sleep PM mode.
> 
> While in deep sleep PM mode, additionally, the power supply is
> removed from e500 core and most IP blocks. Only the blocks needed
> to wake up the chip out of deep sleep are ON.
> 
> This patch supports 32-bit and 36-bit address space.
> 
> The sleep mode is equal to the Standby state in Linux. The deep sleep
> mode is equal to the Suspend-to-RAM state of Linux Power Management.
> 
> Command to enter sleep mode.
>   echo standby > /sys/power/state
> Command to enter deep sleep mode.
>   echo mem > /sys/power/state
> 
> Signed-off-by: Dave Liu <daveliu@freescale.com>
> Signed-off-by: Li Yang <leoli@freescale.com>
> Signed-off-by: Jin Qing <b24347@freescale.com>
> Signed-off-by: Jerry Huang <Chang-Ming.Huang@freescale.com>
> Cc: Scott Wood <scottwood@freescale.com>
> Signed-off-by: Zhao Chenhui <chenhui.zhao@freescale.com>
> ---
> Changes for v5:
>  * Rename flush_disable_L1 to __flush_disable_L1.
> 
>  arch/powerpc/Kconfig                  |    2 +-
>  arch/powerpc/include/asm/cacheflush.h |    5 +
>  arch/powerpc/kernel/Makefile          |    3 +
>  arch/powerpc/kernel/l2cache_85xx.S    |   53 +++
>  arch/powerpc/platforms/85xx/Makefile  |    3 +
>  arch/powerpc/platforms/85xx/sleep.S   |  609 +++++++++++++++++++++++++++++++++
>  arch/powerpc/sysdev/fsl_pmc.c         |   91 ++++-
>  arch/powerpc/sysdev/fsl_soc.h         |    5 +
>  8 files changed, 752 insertions(+), 19 deletions(-)
>  create mode 100644 arch/powerpc/kernel/l2cache_85xx.S
>  create mode 100644 arch/powerpc/platforms/85xx/sleep.S
> 
> diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig
> index d65ae35..039f0a6 100644
> --- a/arch/powerpc/Kconfig
> +++ b/arch/powerpc/Kconfig
> @@ -673,7 +673,7 @@ config FSL_PCI
>  config FSL_PMC
>  	bool
>  	default y
> -	depends on SUSPEND && (PPC_85xx || PPC_86xx)
> +	depends on SUSPEND && (PPC_85xx || PPC_86xx) && !PPC_E500MC
>  	help
>  	  Freescale MPC85xx/MPC86xx power management controller support
>  	  (suspend/resume). For MPC83xx see platforms/83xx/suspend.c
> diff --git a/arch/powerpc/include/asm/cacheflush.h b/arch/powerpc/include/asm/cacheflush.h
> index 94ec20a..baa000c 100644
> --- a/arch/powerpc/include/asm/cacheflush.h
> +++ b/arch/powerpc/include/asm/cacheflush.h
> @@ -33,6 +33,11 @@ extern void flush_dcache_page(struct page *page);
>  #if defined(CONFIG_FSL_BOOKE) || defined(CONFIG_6xx)
>  extern void __flush_disable_L1(void);
>  #endif
> +#if defined(CONFIG_FSL_BOOKE)
> +extern void flush_dcache_L1(void);
> +#else
> +#define flush_dcache_L1()	do { } while (0)
> +#endif

It doesn't seem right to no-op this on other platforms.

>  extern void __flush_icache_range(unsigned long, unsigned long);
>  static inline void flush_icache_range(unsigned long start, unsigned long stop)
> diff --git a/arch/powerpc/kernel/Makefile b/arch/powerpc/kernel/Makefile
> index f5808a3..cb70dba 100644
> --- a/arch/powerpc/kernel/Makefile
> +++ b/arch/powerpc/kernel/Makefile
> @@ -64,6 +64,9 @@ obj-$(CONFIG_FA_DUMP)		+= fadump.o
>  ifeq ($(CONFIG_PPC32),y)
>  obj-$(CONFIG_E500)		+= idle_e500.o
>  endif
> +ifneq ($(CONFIG_PPC_E500MC),y)
> +obj-$(CONFIG_PPC_85xx)		+= l2cache_85xx.o
> +endif

Can we introduce a symbol that specifically means pre-e500mc e500,
rather than using negative logic?

I think something like CONFIG_PPC_E500_V1_V2 has been proposed before.

> -static int pmc_probe(struct platform_device *ofdev)
> +static int pmc_probe(struct platform_device *pdev)
>  {
> -	pmc_regs = of_iomap(ofdev->dev.of_node, 0);
> +	struct device_node *np = pdev->dev.of_node;
> +
> +	pmc_regs = of_iomap(np, 0);
>  	if (!pmc_regs)
>  		return -ENOMEM;
>  
> -	pmc_dev = &ofdev->dev;
> +	pmc_flag = PMC_SLEEP;
> +	if (of_device_is_compatible(np, "fsl,mpc8536-pmc"))
> +		pmc_flag |= PMC_DEEP_SLEEP;
> +
> +	if (of_device_is_compatible(np, "fsl,p1022-pmc"))
> +		pmc_flag |= PMC_DEEP_SLEEP;
> +
>  	suspend_set_ops(&pmc_suspend_ops);
> +
> +	pr_info("Freescale PMC driver\n");

If you're going to be noisy on probe, at least provide some useful info
like whether deep sleep or jog are supported.

>  	return 0;
>  }
>  
> diff --git a/arch/powerpc/sysdev/fsl_soc.h b/arch/powerpc/sysdev/fsl_soc.h
> index c6d0073..949377d 100644
> --- a/arch/powerpc/sysdev/fsl_soc.h
> +++ b/arch/powerpc/sysdev/fsl_soc.h
> @@ -48,5 +48,10 @@ extern struct platform_diu_data_ops diu_ops;
>  void fsl_hv_restart(char *cmd);
>  void fsl_hv_halt(void);
>  
> +/*
> + * Cast the ccsrbar to 64-bit parameter so that the assembly
> + * code can be compatible with both 32-bit & 36-bit.
> + */
> +extern void mpc85xx_enter_deep_sleep(u64 ccsrbar, u32 powmgtreq);

s/Cast the ccsrbar to 64-bit parameter/ccsrbar is u64 rather than
phys_addr_t/

-Scott

^ permalink raw reply

* Re: [PATCH v5 4/5] fsl_pmc: Add API to enable device as wakeup event source
From: Scott Wood @ 2012-06-01 22:08 UTC (permalink / raw)
  To: Zhao Chenhui; +Cc: linuxppc-dev, linux-kernel
In-Reply-To: <1336737235-15370-4-git-send-email-chenhui.zhao@freescale.com>

On 05/11/2012 06:53 AM, Zhao Chenhui wrote:
> Add APIs for setting wakeup source and lossless Ethernet in low power modes.
> These APIs can be used by wake-on-packet feature.
> 
> Signed-off-by: Dave Liu <daveliu@freescale.com>
> Signed-off-by: Li Yang <leoli@freescale.com>
> Signed-off-by: Jin Qing <b24347@freescale.com>
> Signed-off-by: Zhao Chenhui <chenhui.zhao@freescale.com>
> ---
>  arch/powerpc/sysdev/fsl_pmc.c |   71 ++++++++++++++++++++++++++++++++++++++++-
>  arch/powerpc/sysdev/fsl_soc.h |    9 +++++
>  2 files changed, 79 insertions(+), 1 deletions(-)
> 
> diff --git a/arch/powerpc/sysdev/fsl_pmc.c b/arch/powerpc/sysdev/fsl_pmc.c
> index 1dc6e9e..c1170f7 100644
> --- a/arch/powerpc/sysdev/fsl_pmc.c
> +++ b/arch/powerpc/sysdev/fsl_pmc.c
> @@ -34,6 +34,7 @@ struct pmc_regs {
>  	__be32 powmgtcsr;
>  #define POWMGTCSR_SLP		0x00020000
>  #define POWMGTCSR_DPSLP		0x00100000
> +#define POWMGTCSR_LOSSLESS	0x00400000
>  	__be32 res3[2];
>  	__be32 pmcdr;
>  };
> @@ -43,6 +44,74 @@ static unsigned int pmc_flag;
>  
>  #define PMC_SLEEP	0x1
>  #define PMC_DEEP_SLEEP	0x2
> +#define PMC_LOSSLESS	0x4
> +
> +/**
> + * mpc85xx_pmc_set_wake - enable devices as wakeup event source
> + * @pdev: platform device affected
> + * @enable: True to enable event generation; false to disable
> + *
> + * This enables the device as a wakeup event source, or disables it.
> + *
> + * RETURN VALUE:
> + * 0 is returned on success
> + * -EINVAL is returned if device is not supposed to wake up the system
> + * Error code depending on the platform is returned if both the platform and
> + * the native mechanism fail to enable the generation of wake-up events
> + */
> +int mpc85xx_pmc_set_wake(struct platform_device *pdev, bool enable)

Why does it have to be a platform_device?  Would a bare device_node work
here?  If it's for stuff like device_may_wakeup() that could be in a
platform_device wrapper function.

Where does this get called from?  I don't see an example user in this
patchset.

> +{
> +	int ret = 0;
> +	struct device_node *clk_np;
> +	u32 *prop;
> +	u32 pmcdr_mask;
> +
> +	if (!pmc_regs) {
> +		pr_err("%s: PMC is unavailable\n", __func__);
> +		return -ENODEV;
> +	}
> +
> +	if (enable && !device_may_wakeup(&pdev->dev))
> +		return -EINVAL;

Who is setting can_wakeup for these devices?

> +	clk_np = of_parse_phandle(pdev->dev.of_node, "fsl,pmc-handle", 0);
> +	if (!clk_np)
> +		return -EINVAL;
> +
> +	prop = (u32 *)of_get_property(clk_np, "fsl,pmcdr-mask", NULL);

Don't cast the const away.

> +	if (!prop) {
> +		ret = -EINVAL;
> +		goto out;
> +	}
> +	pmcdr_mask = be32_to_cpup(prop);
> +
> +	if (enable)
> +		/* clear to enable clock in low power mode */
> +		clrbits32(&pmc_regs->pmcdr, pmcdr_mask);
> +	else
> +		setbits32(&pmc_regs->pmcdr, pmcdr_mask);

What is the default PMCDR if this function is never called?  Should init
to all bits set on PM driver probe (or maybe limit it to defined bits
only, though that's a little harder to do generically).

-Scot

^ permalink raw reply

* Re: power management patch set for mpc85xx
From: Benjamin Herrenschmidt @ 2012-06-01 22:17 UTC (permalink / raw)
  To: Zhao Chenhui-B35336
  Cc: linuxppc-dev@lists.ozlabs.org, paulus@samba.org, Li Yang-R58472
In-Reply-To: <7AA2FF042C086D469F577FA6723434DA058123@039-SN1MPN1-002.039d.mgd.msft.net>

On Fri, 2012-06-01 at 10:29 +0000, Zhao Chenhui-B35336 wrote:
> Hi Ben and Paul,
> 
> I am sorry to trouble you. It seems that Kumar is busy recently.
> 
> Could you have a review on the following patches? These patches
> implement the power management support on MPC85xx platform.

At this point, I don't have the bandwidth for that and I suspect Paul
doesn't either.

If Kumar isn't able to maintain the FSL stuff anymore then somebody else
needs to step up, maybe Scott Wood ?

I haven't heard from Kumar in a while so I'm not sure what's up.

Cheers,
Ben.

^ permalink raw reply

* Re: power management patch set for mpc85xx
From: Benjamin Herrenschmidt @ 2012-06-01 22:24 UTC (permalink / raw)
  To: Zhao Chenhui-B35336
  Cc: linuxppc-dev@lists.ozlabs.org, paulus@samba.org, Li Yang-R58472
In-Reply-To: <1338589068.16119.54.camel@pasglop>

On Sat, 2012-06-02 at 08:17 +1000, Benjamin Herrenschmidt wrote:
> On Fri, 2012-06-01 at 10:29 +0000, Zhao Chenhui-B35336 wrote:
> > Hi Ben and Paul,
> > 
> > I am sorry to trouble you. It seems that Kumar is busy recently.
> > 
> > Could you have a review on the following patches? These patches
> > implement the power management support on MPC85xx platform.
> 
> At this point, I don't have the bandwidth for that and I suspect Paul
> doesn't either.
> 
> If Kumar isn't able to maintain the FSL stuff anymore then somebody else
> needs to step up, maybe Scott Wood ?
> 
> I haven't heard from Kumar in a while so I'm not sure what's up.

Ah, I finally did hear from Kumar. So things are still on track, it's
just a missing ack.

Cheers,
Ben.

^ permalink raw reply

* Re: [RFC] [PATCH] powerpc: Add MSR_DE to MSR_KERNEL
From: Benjamin Herrenschmidt @ 2012-06-01 22:30 UTC (permalink / raw)
  To: Scott Wood; +Cc: linuxppc-dev, Bob Cochran, support
In-Reply-To: <4FC8EDC4.2050704@freescale.com>

On Fri, 2012-06-01 at 11:28 -0500, Scott Wood wrote:
> 
> It's not really about CodeWarrior -- it's needed for any external
> debug
> on these chips.
> 
> Those chips are commercial products too, BTW. :-)

As long as it's not code to specifically interact with the CW software
it's ok.

I don't have a special axe to grind against CW (I use to love it under
ol' MacOS, though the new eclipse based one does seem to suck hard...
but then I never got a "licence" to use it past the demo anyway), it's
just that I don't want to start building SW interfaces to a foreign
tool.

BTW. My point of view is that this whole business about MSR:DE is a HW
design bug. There should be -no- (absolutely 0) interaction between the
SW state and the HW debugger for normal operations unless the user of
the debugger explicitly wants to change some state.

Cheers,
Ben.

^ permalink raw reply

* Re: [RFC] [PATCH] powerpc: Add MSR_DE to MSR_KERNEL
From: Scott Wood @ 2012-06-01 22:42 UTC (permalink / raw)
  To: Benjamin Herrenschmidt; +Cc: linuxppc-dev, Bob Cochran, support
In-Reply-To: <1338589800.16119.58.camel@pasglop>

On 06/01/2012 05:30 PM, Benjamin Herrenschmidt wrote:
> BTW. My point of view is that this whole business about MSR:DE is a HW
> design bug. There should be -no- (absolutely 0) interaction between the
> SW state and the HW debugger for normal operations unless the user of
> the debugger explicitly wants to change some state.

I agree entirely, and e500mc at least has less of this than e500v2 (not
sure if it still needs MSR[DE], but supposedly it doesn't have the
requirement for there to be a valid instruction at the debug vector,
which is lots of fun when booting).  But this isn't exactly something
Freescale is going to replace existing chips over.

Getting all the way to zero interaction would require a completely
separate debug facility so software can debug at the same time.  I'd be
all for that (and let's throw in a third, for the hypervisor), but I'm
not the one that needs to be convinced.

-Scott

^ permalink raw reply

* Re: [RFC] [PATCH] powerpc: Add MSR_DE to MSR_KERNEL
From: Benjamin Herrenschmidt @ 2012-06-01 23:24 UTC (permalink / raw)
  To: Scott Wood; +Cc: linuxppc-dev, Bob Cochran, support
In-Reply-To: <4FC9456B.8090400@freescale.com>

On Fri, 2012-06-01 at 17:42 -0500, Scott Wood wrote:
> On 06/01/2012 05:30 PM, Benjamin Herrenschmidt wrote:
> > BTW. My point of view is that this whole business about MSR:DE is a HW
> > design bug. There should be -no- (absolutely 0) interaction between the
> > SW state and the HW debugger for normal operations unless the user of
> > the debugger explicitly wants to change some state.
> 
> I agree entirely, and e500mc at least has less of this than e500v2 (not
> sure if it still needs MSR[DE], but supposedly it doesn't have the
> requirement for there to be a valid instruction at the debug vector,
> which is lots of fun when booting).  But this isn't exactly something
> Freescale is going to replace existing chips over.
> 
> Getting all the way to zero interaction would require a completely
> separate debug facility so software can debug at the same time.  I'd be
> all for that (and let's throw in a third, for the hypervisor), but I'm
> not the one that needs to be convinced.

You can find a good compromise. If you have some kind of SPR letting you
know now many DACs and IACs are available, you could essentially
"reserve" some for HW debug with the probe. Not as good as a fully
separate facility but still better than stepping on each other toes.

Things like DBCR should probably still be separated. There's no excuse
for the MSR:DE bullshit tho :-)

Cheers,
Ben.

^ permalink raw reply

* Re: [PATCH v5 5/5] powerpc/85xx: add support to JOG feature using cpufreq interface
From: Scott Wood @ 2012-06-01 23:30 UTC (permalink / raw)
  To: Zhao Chenhui; +Cc: linuxppc-dev, linux-kernel
In-Reply-To: <1336737235-15370-5-git-send-email-chenhui.zhao@freescale.com>

On 05/11/2012 06:53 AM, Zhao Chenhui wrote:
> Some 85xx silicons like MPC8536 and P1022 have a JOG feature, which provides
> a dynamic mechanism to lower or raise the CPU core clock at runtime.

Is there a reason P1023 isn't supported?

> This patch adds the support to change CPU frequency using the standard
> cpufreq interface. The ratio CORE to CCB can be 1:1(except MPC8536), 3:2,
> 2:1, 5:2, 3:1, 7:2 and 4:1.
> 
> Two CPU cores on P1022 must not in the low power state during the frequency
> transition. The driver uses a atomic counter to meet the requirement.
> 
> The jog mode frequency transition process on the MPC8536 is similar to
> the deep sleep process. The driver need save the CPU state and restore
> it after CPU warm reset.
> 
> Note:
>  * The I/O peripherals such as PCIe and eTSEC may lose packets during
>    the jog mode frequency transition.

That might be acceptable for eTSEC, but it is not acceptable to lose
anything on PCIe.  Especially not if you're going to make this "default y".


> +static int mpc85xx_job_probe(struct platform_device *ofdev)

Job?

> +{
> +	struct device_node *np = ofdev->dev.of_node;
> +	unsigned int svr;
> +
> +	if (of_device_is_compatible(np, "fsl,mpc8536-guts")) {
> +		svr = mfspr(SPRN_SVR);
> +		if ((svr & 0x7fff) == 0x10) {
> +			pr_err("MPC8536 Rev 1.0 do not support JOG.\n");
> +			return -ENODEV;
> +		}

s/do not support JOG/does not support cpufreq/

> +		mpc85xx_freqs = mpc8536_freqs_table;
> +		set_pll = mpc8536_set_pll;
> +	} else if (of_device_is_compatible(np, "fsl,p1022-guts")) {
> +		mpc85xx_freqs = p1022_freqs_table;
> +		set_pll = p1022_set_pll;
> +	} else {
> +		return -ENODEV;
> +	}
> +
> +	sysfreq = fsl_get_sys_freq();
> +
> +	guts = of_iomap(np, 0);
> +	if (!guts)
> +		return -ENODEV;
> +
> +	max_pll[0] = get_pll(0);
> +	if (mpc85xx_freqs == p1022_freqs_table)
> +		max_pll[1] = get_pll(1);
> +
> +	pr_info("Freescale MPC85xx CPU frequency switching(JOG) driver\n");
> +
> +	return cpufreq_register_driver(&mpc85xx_cpufreq_driver);
> +}
> +
> +static int mpc85xx_jog_remove(struct platform_device *ofdev)
> +{
> +	iounmap(guts);
> +	cpufreq_unregister_driver(&mpc85xx_cpufreq_driver);
> +
> +	return 0;
> +}
> +
> +static struct of_device_id mpc85xx_jog_ids[] = {
> +	{ .compatible = "fsl,mpc8536-guts", },
> +	{ .compatible = "fsl,p1022-guts", },
> +	{}
> +};
> +
> +static struct platform_driver mpc85xx_jog_driver = {
> +	.driver = {
> +		.name = "mpc85xx_cpufreq_jog",
> +		.owner = THIS_MODULE,
> +		.of_match_table = mpc85xx_jog_ids,
> +	},
> +	.probe = mpc85xx_job_probe,
> +	.remove = mpc85xx_jog_remove,
> +};

Why is this a separate driver from fsl_pmc.c?

Only one driver can bind to a node through normal mechanisms -- you
don't get to take the entire guts node for this.

> +static int __init mpc85xx_jog_init(void)
> +{
> +	return platform_driver_register(&mpc85xx_jog_driver);
> +}
> +
> +static void __exit mpc85xx_jog_exit(void)
> +{
> +	platform_driver_unregister(&mpc85xx_jog_driver);
> +}
> +
> +module_init(mpc85xx_jog_init);
> +module_exit(mpc85xx_jog_exit);
> +
> +MODULE_LICENSE("GPL");
> +MODULE_AUTHOR("Dave Liu <daveliu@freescale.com>");
> diff --git a/arch/powerpc/platforms/Kconfig b/arch/powerpc/platforms/Kconfig
> index a35ca44..445bedd 100644
> --- a/arch/powerpc/platforms/Kconfig
> +++ b/arch/powerpc/platforms/Kconfig
> @@ -204,6 +204,17 @@ config CPU_FREQ_PMAC64
>  	  This adds support for frequency switching on Apple iMac G5,
>  	  and some of the more recent desktop G5 machines as well.
>  
> +config MPC85xx_CPUFREQ
> +	bool "Support for Freescale MPC85xx CPU freq"
> +	depends on PPC_85xx && PPC32 && !PPC_E500MC

PPC32 is redundant given the !PPC_E500MC.

> index 8976534..401cac0 100644
> --- a/arch/powerpc/sysdev/fsl_soc.h
> +++ b/arch/powerpc/sysdev/fsl_soc.h
> @@ -62,5 +62,10 @@ void fsl_hv_halt(void);
>   * code can be compatible with both 32-bit & 36-bit.
>   */
>  extern void mpc85xx_enter_deep_sleep(u64 ccsrbar, u32 powmgtreq);
> +
> +static inline void mpc85xx_enter_jog(u64 ccsrbar, u32 powmgtreq)
> +{
> +	mpc85xx_enter_deep_sleep(ccsrbar, powmgtreq);
> +}

What value is this function adding over mpc85xx_enter_deep_sleep()?

> diff --git a/kernel/cpu.c b/kernel/cpu.c
> index 2060c6e..c4cd342 100644
> --- a/kernel/cpu.c
> +++ b/kernel/cpu.c
> @@ -381,6 +381,36 @@ out:
>  }
>  EXPORT_SYMBOL_GPL(cpu_up);
>  
> +/*
> + * Prevent regular CPU hotplug from racing with the freezer, by disabling CPU
> + * hotplug when tasks are about to be frozen. Also, don't allow the freezer
> + * to continue until any currently running CPU hotplug operation gets
> + * completed.
> + * To modify the 'cpu_hotplug_disabled' flag, we need to acquire the
> + * 'cpu_add_remove_lock'. And this same lock is also taken by the regular
> + * CPU hotplug path and released only after it is complete. Thus, we
> + * (and hence the freezer) will block here until any currently running CPU
> + * hotplug operation gets completed.
> + */
> +void cpu_hotplug_disable_before_freeze(void)
> +{
> +	cpu_maps_update_begin();
> +	cpu_hotplug_disabled = 1;
> +	cpu_maps_update_done();
> +}
> +
> +
> +/*
> + * When tasks have been thawed, re-enable regular CPU hotplug (which had been
> + * disabled while beginning to freeze tasks).
> + */
> +void cpu_hotplug_enable_after_thaw(void)
> +{
> +	cpu_maps_update_begin();
> +	cpu_hotplug_disabled = 0;
> +	cpu_maps_update_done();
> +}
> +
>  #ifdef CONFIG_PM_SLEEP_SMP
>  static cpumask_var_t frozen_cpus;
>  
> @@ -479,36 +509,6 @@ static int __init alloc_frozen_cpus(void)
>  core_initcall(alloc_frozen_cpus);
>  
>  /*
> - * Prevent regular CPU hotplug from racing with the freezer, by disabling CPU
> - * hotplug when tasks are about to be frozen. Also, don't allow the freezer
> - * to continue until any currently running CPU hotplug operation gets
> - * completed.
> - * To modify the 'cpu_hotplug_disabled' flag, we need to acquire the
> - * 'cpu_add_remove_lock'. And this same lock is also taken by the regular
> - * CPU hotplug path and released only after it is complete. Thus, we
> - * (and hence the freezer) will block here until any currently running CPU
> - * hotplug operation gets completed.
> - */
> -void cpu_hotplug_disable_before_freeze(void)
> -{
> -	cpu_maps_update_begin();
> -	cpu_hotplug_disabled = 1;
> -	cpu_maps_update_done();
> -}
> -
> -
> -/*
> - * When tasks have been thawed, re-enable regular CPU hotplug (which had been
> - * disabled while beginning to freeze tasks).
> - */
> -void cpu_hotplug_enable_after_thaw(void)
> -{
> -	cpu_maps_update_begin();
> -	cpu_hotplug_disabled = 0;
> -	cpu_maps_update_done();
> -}
> -
> -/*
>   * When callbacks for CPU hotplug notifications are being executed, we must
>   * ensure that the state of the system with respect to the tasks being frozen
>   * or not, as reported by the notification, remains unchanged *throughout the

Why did you need to move this?

-Scott

^ permalink raw reply

* Re: [PATCH 18/27] powerpc, smpboot: Use generic SMP booting infrastructure
From: Paul Mackerras @ 2012-06-02  6:14 UTC (permalink / raw)
  To: Srivatsa S. Bhat
  Cc: linux-arch, Nikunj A. Dadhania, Yong Zhang, peterz, rusty, vatsa,
	linux-kernel, rjw, Paul Gortmaker, mingo, tglx, paulmck,
	linuxppc-dev, akpm
In-Reply-To: <20120601091417.31979.6433.stgit@srivatsabhat.in.ibm.com>

On Fri, Jun 01, 2012 at 02:44:23PM +0530, Srivatsa S. Bhat wrote:
> From: Nikunj A. Dadhania <nikunj@linux.vnet.ibm.com>
> 
> Convert powerpc to use the generic framework to boot secondary CPUs.
> 
> Signed-off-by: Nikunj A. Dadhania <nikunj@linux.vnet.ibm.com>

Acked-by: Paul Mackerras <paulus@samba.org>

^ permalink raw reply

* [PATCH] powerpc: Fix size of st_nlink on 64bit
From: Anton Blanchard @ 2012-06-02 11:34 UTC (permalink / raw)
  To: benh, paulus, michael, viro; +Cc: linuxppc-dev


commit e57f93cc53b7 (powerpc: get rid of nlink_t uses, switch to
explicitly-sized type) changed the size of st_nlink on ppc64 from
a long to a short, resulting in boot failures.

Signed-off-by: Anton Blanchard <anton@samba.org>
---

Index: linux-build/arch/powerpc/include/asm/stat.h
===================================================================
--- linux-build.orig/arch/powerpc/include/asm/stat.h	2012-06-02 21:25:50.322275743 +1000
+++ linux-build/arch/powerpc/include/asm/stat.h	2012-06-02 21:26:35.183130538 +1000
@@ -30,7 +30,7 @@ struct stat {
 	unsigned long	st_dev;
 	ino_t		st_ino;
 #ifdef __powerpc64__
-	unsigned short	st_nlink;
+	unsigned long	st_nlink;
 	mode_t		st_mode;
 #else
 	mode_t		st_mode;

^ permalink raw reply

* Re: [RFC] [PATCH] powerpc: Add MSR_DE to MSR_KERNEL
From: Joakim Tjernlund @ 2012-06-02 18:29 UTC (permalink / raw)
  To: Benjamin Herrenschmidt; +Cc: Scott Wood, linuxppc-dev, Bob Cochran, support
In-Reply-To: <1338593099.16119.60.camel@pasglop>

>
> On Fri, 2012-06-01 at 17:42 -0500, Scott Wood wrote:
> > On 06/01/2012 05:30 PM, Benjamin Herrenschmidt wrote:
> > > BTW. My point of view is that this whole business about MSR:DE is a HW
> > > design bug. There should be -no- (absolutely 0) interaction between the
> > > SW state and the HW debugger for normal operations unless the user of
> > > the debugger explicitly wants to change some state.
> >
> > I agree entirely, and e500mc at least has less of this than e500v2 (not
> > sure if it still needs MSR[DE], but supposedly it doesn't have the
> > requirement for there to be a valid instruction at the debug vector,
> > which is lots of fun when booting).  But this isn't exactly something
> > Freescale is going to replace existing chips over.
> >
> > Getting all the way to zero interaction would require a completely
> > separate debug facility so software can debug at the same time.  I'd be
> > all for that (and let's throw in a third, for the hypervisor), but I'm
> > not the one that needs to be convinced.
>
> You can find a good compromise. If you have some kind of SPR letting you
> know now many DACs and IACs are available, you could essentially
> "reserve" some for HW debug with the probe. Not as good as a fully
> separate facility but still better than stepping on each other toes.
>
> Things like DBCR should probably still be separated. There's no excuse
> for the MSR:DE bullshit tho :-)

hmm, where does this go w.r.t the patch? Got the feeling that the
best thing is to just turn MSR:DE on and be done with it?

 Jocke

^ permalink raw reply

* Re: [PATCH] powerpc: Fix size of st_nlink on 64bit
From: Benjamin Herrenschmidt @ 2012-06-02 21:19 UTC (permalink / raw)
  To: Anton Blanchard; +Cc: michael, linuxppc-dev, paulus, viro
In-Reply-To: <20120602213452.66ba4cbb@kryten>

On Sat, 2012-06-02 at 21:34 +1000, Anton Blanchard wrote:
> commit e57f93cc53b7 (powerpc: get rid of nlink_t uses, switch to
> explicitly-sized type) changed the size of st_nlink on ppc64 from
> a long to a short, resulting in boot failures.
> 
> Signed-off-by: Anton Blanchard <anton@samba.org>

Acked-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>

Al, did you CC me on that ? I don't remember seeing it but it could be
my fault...

Cheers,
Ben.

> ---
> 
> Index: linux-build/arch/powerpc/include/asm/stat.h
> ===================================================================
> --- linux-build.orig/arch/powerpc/include/asm/stat.h	2012-06-02 21:25:50.322275743 +1000
> +++ linux-build/arch/powerpc/include/asm/stat.h	2012-06-02 21:26:35.183130538 +1000
> @@ -30,7 +30,7 @@ struct stat {
>  	unsigned long	st_dev;
>  	ino_t		st_ino;
>  #ifdef __powerpc64__
> -	unsigned short	st_nlink;
> +	unsigned long	st_nlink;
>  	mode_t		st_mode;
>  #else
>  	mode_t		st_mode;

^ permalink raw reply

* Re: [RFC] [PATCH] powerpc: Add MSR_DE to MSR_KERNEL
From: Benjamin Herrenschmidt @ 2012-06-02 21:21 UTC (permalink / raw)
  To: Joakim Tjernlund; +Cc: Scott Wood, linuxppc-dev, Bob Cochran, support
In-Reply-To: <OFF2E739FE.A96EBAF2-ONC1257A11.00655546-C1257A11.0065978F@transmode.se>

On Sat, 2012-06-02 at 20:29 +0200, Joakim Tjernlund wrote:
> 
> hmm, where does this go w.r.t the patch? Got the feeling that the
> best thing is to just turn MSR:DE on and be done with it? 

Not unconditionally, we need to have a close look, that might be ok
specifically for BookE 32-bit, it's certainly not ok for BookE 64-bit at
this point.

For now, I'm ok with a debug CONFIG_* option.

Also do we know if MSR:DE has any performance impact on any CPU ? I know
having DACs enabled has a major impact on some for example.

Ben.

^ permalink raw reply

* Re: [PATCH] powerpc: Fix size of st_nlink on 64bit
From: Stephen Rothwell @ 2012-06-03  2:28 UTC (permalink / raw)
  To: Anton Blanchard; +Cc: michael, linuxppc-dev, paulus, viro
In-Reply-To: <20120602213452.66ba4cbb@kryten>

[-- Attachment #1: Type: text/plain, Size: 598 bytes --]

Hi Anton,

On Sat, 2 Jun 2012 21:34:52 +1000 Anton Blanchard <anton@samba.org> wrote:
>
> commit e57f93cc53b7 (powerpc: get rid of nlink_t uses, switch to
> explicitly-sized type) changed the size of st_nlink on ppc64 from
> a long to a short, resulting in boot failures.
> 
> Signed-off-by: Anton Blanchard <anton@samba.org>

Would this affect my (early user mode) boot problems reported yesterday;

/init: 71: mknod: Permission denied
/init: 88: mknod: Permission denied
/init: 88: mknod: Permission denied

-- 
Cheers,
Stephen Rothwell                    sfr@canb.auug.org.au

[-- Attachment #2: Type: application/pgp-signature, Size: 836 bytes --]

^ permalink raw reply

* Re: [PATCH] powerpc: Fix size of st_nlink on 64bit
From: Anton Blanchard @ 2012-06-03  3:48 UTC (permalink / raw)
  To: Stephen Rothwell; +Cc: michael, linuxppc-dev, paulus, viro
In-Reply-To: <20120603122850.3c5142767e429f34eb8a921e@canb.auug.org.au>


Hi Stephen,

> > commit e57f93cc53b7 (powerpc: get rid of nlink_t uses, switch to
> > explicitly-sized type) changed the size of st_nlink on ppc64 from
> > a long to a short, resulting in boot failures.
> > 
> > Signed-off-by: Anton Blanchard <anton@samba.org>
> 
> Would this affect my (early user mode) boot problems reported
> yesterday;
> 
> /init: 71: mknod: Permission denied
> /init: 88: mknod: Permission denied
> /init: 88: mknod: Permission denied

Very similar to the errors I was seeing so I think the patch will fix
it.

Anton

^ permalink raw reply

* Re: [PATCH v2 2/3] ppc32/kprobe: complete kprobe and migrate exception frame
From: tiejun.chen @ 2012-06-03  5:01 UTC (permalink / raw)
  To: Benjamin Herrenschmidt; +Cc: linuxppc-dev
In-Reply-To: <1336621805.3881.38.camel@pasglop>

On 05/10/2012 11:50 AM, Benjamin Herrenschmidt wrote:
> On Thu, 2011-12-15 at 19:00 +0800, Tiejun Chen wrote:
>> We can't emulate stwu since that may corrupt current exception stack.
>> So we will have to do real store operation in the exception return code.
>>
>> Firstly we'll allocate a trampoline exception frame below the kprobed
>> function stack and copy the current exception frame to the trampoline.
>> Then we can do this real store operation to implement 'stwu', and reroute
>> the trampoline frame to r1 to complete this exception migration.
>>
>> Signed-off-by: Tiejun Chen <tiejun.chen@windriver.com>
>> ---
>>  arch/powerpc/kernel/entry_32.S |   35 +++++++++++++++++++++++++++++++++++
>>  1 files changed, 35 insertions(+), 0 deletions(-)
>>
>> diff --git a/arch/powerpc/kernel/entry_32.S b/arch/powerpc/kernel/entry_32.S
>> index 56212bc..0cdd27d 100644
>> --- a/arch/powerpc/kernel/entry_32.S
>> +++ b/arch/powerpc/kernel/entry_32.S
>> @@ -850,6 +850,41 @@ resume_kernel:
>>  
>>  	/* interrupts are hard-disabled at this point */
>>  restore:
>> +	lwz	r3,_MSR(r1)	/* Returning to user mode? */
>> +	andi.	r0,r3,MSR_PR
>> +	bne	1f	
> 
>  .../...
> 

Sorry for this delay response since I can't take time to do this last week :(

> Wouldn't it be better to use resume_kernel here ?

Agreed :)

> 
> IE. We already have restore_user vs. resume_kernel labels, including
> the PR test. In the !PREEMPT case, resume_kernel is empty but it's
> there, so you can just "populate" it, ie, something like:
> 
> restore_user:
> 	... existing dbcr0 stuff ...
> 	b restore
> 
> resume_kernel: <-- removed the ifdef CONFIG_PREEMPT
> 
> 	... Do the stack store business here...
> 
> #ifdef CONFIG_PREEMPT
> 	... move the preempt code here...
> #endif
> 
> restore:
> 	... existing stuff ...
> 
> Also, the added advantage is that the code to calc
> the thread info pointer and load the TI_FLAG can be
> shared now between your stuff and preempt, ie:
> 
> resume_kernel:
> 	rlwinm	r9,r1,0,0,(31-THREAD_SHIFT)
> 	lwz	r0,TI_FLAGS(r9)
> 	andis.	r0,r0,_TIF_EMULATE_STACK_STORE@h
> 	bne-	emulate_stack_store
> #ifdef CONFIG_PREEMPT
> 	lwz	r8,TI_PREEMPT(r9) <-- note use of r8 instead of r0,
>                                       I -think- r8 can be clobbered
>                                       here but pls dbl check

Its should be safe.

> 	cmpwi	0,r8,0
> 	bne	restore
> 	andi.	r0,r0,_TIF_NEED_RESCHED
> 	etc...

Please check if next, v3, is fine.

>  	
>> +	/* check current_thread_info, _TIF_EMULATE_STACK_STORE */
>> +	rlwinm	r9,r1,0,0,(31-THREAD_SHIFT)
>> +	lwz	r0,TI_FLAGS(r9)
>> +	andis.	r0,r0,_TIF_EMULATE_STACK_STORE@h
>> +	beq+	1f	
>> +
>> +	addi	r9,r1,INT_FRAME_SIZE	/* Get the kprobed function entry */
>> +
>> +	lwz	r3,GPR1(r1)
>> +	subi	r3,r3,INT_FRAME_SIZE	/* dst: Allocate a trampoline exception frame */
>> +	mr	r4,r1			/* src:  current exception frame */
>> +	li	r5,INT_FRAME_SIZE	/* size: INT_FRAME_SIZE */
>> +	mr	r1,r3			/* Reroute the trampoline frame to r1 */
>> +	bl	memcpy			/* Copy from the original to the trampoline */
>> +
>> +	/* Do real store operation to complete stwu */
>> +	lwz	r5,GPR1(r1)
>> +	stw	r9,0(r5)
> 
> Ok, I think I -finally- understand your trick of using r1 +
> INT_FRAME_SIZE as the value to store :-) It makes sense and it's
> actually a nice hack :-)
> 
> I would recommend that in the C code part of the emulation, you
> add some sanity checking to make sure we don't overflow the
> kernel stack etc... it should come in generally handy especially
> if what's your trying to debug with kprobes is a kernel stack
> overflow :-)

Added.

> 
>> +	/* Clear _TIF_EMULATE_STACK_STORE flag */
>> +	rlwinm	r9,r1,0,0,(31-THREAD_SHIFT)
>> +	lis	r11,_TIF_EMULATE_STACK_STORE@h
>> +	addi	r9,r9,TI_FLAGS
>> +0:	lwarx	r8,0,r9
>> +	andc	r8,r8,r11
>> +#ifdef CONFIG_IBM405_ERR77
>> +	dcbt	0,r9
>> +#endif
>> +	stwcx.	r8,0,r9
>> +	bne-	0b
>> +1:
>> +
>>  #ifdef CONFIG_44x
>>  BEGIN_MMU_FTR_SECTION
>>  	b	1f
> 
> BTW. Are you going to do a ppc64 variant of that patch ?

I'd like to go ppc64 ASAP once we did on ppc32 is good enough :)

Tiejun

> 
> Cheers,
> Ben.
> 
> 
> 
> 

^ permalink raw reply

* [v3 PATCH 1/3] powerpc/kprobe: introduce a new thread flag
From: Tiejun Chen @ 2012-06-03  5:07 UTC (permalink / raw)
  To: benh; +Cc: linuxppc-dev

We need to add a new thread flag, TIF_EMULATE_STACK_STORE,
for emulating stack store operation while exiting exception.

Signed-off-by: Tiejun Chen <tiejun.chen@windriver.com>
---
 arch/powerpc/include/asm/thread_info.h |    3 +++
 1 files changed, 3 insertions(+), 0 deletions(-)

diff --git a/arch/powerpc/include/asm/thread_info.h b/arch/powerpc/include/asm/thread_info.h
index bcebc75..45d098c 100644
--- a/arch/powerpc/include/asm/thread_info.h
+++ b/arch/powerpc/include/asm/thread_info.h
@@ -110,6 +110,8 @@ static inline struct thread_info *current_thread_info(void)
 #define TIF_NOERROR		12	/* Force successful syscall return */
 #define TIF_NOTIFY_RESUME	13	/* callback before returning to user */
 #define TIF_SYSCALL_TRACEPOINT	15	/* syscall tracepoint instrumentation */
+#define	TIF_EMULATE_STACK_STORE	17	/* Is an instruction emulation
+						for stack store? */
 
 /* as above, but as bit values */
 #define _TIF_SYSCALL_TRACE	(1<<TIF_SYSCALL_TRACE)
@@ -126,6 +128,7 @@ static inline struct thread_info *current_thread_info(void)
 #define _TIF_NOERROR		(1<<TIF_NOERROR)
 #define _TIF_NOTIFY_RESUME	(1<<TIF_NOTIFY_RESUME)
 #define _TIF_SYSCALL_TRACEPOINT	(1<<TIF_SYSCALL_TRACEPOINT)
+#define	_TIF_EMULATE_STACK_STORE	(1<<TIF_EMULATE_STACK_STORE)
 #define _TIF_SYSCALL_T_OR_A	(_TIF_SYSCALL_TRACE | _TIF_SYSCALL_AUDIT | \
 				 _TIF_SECCOMP | _TIF_SYSCALL_TRACEPOINT)
 
-- 
1.5.6

^ permalink raw reply related

* [v3 PATCH 2/3] ppc32/kprobe: complete kprobe and migrate exception frame
From: Tiejun Chen @ 2012-06-03  5:07 UTC (permalink / raw)
  To: benh; +Cc: linuxppc-dev
In-Reply-To: <1338700063-30670-1-git-send-email-tiejun.chen@windriver.com>

We can't emulate stwu since that may corrupt current exception stack.
So we will have to do real store operation in the exception return code.

Firstly we'll allocate a trampoline exception frame below the kprobed
function stack and copy the current exception frame to the trampoline.
Then we can do this real store operation to implement 'stwu', and reroute
the trampoline frame to r1 to complete this exception migration.

Signed-off-by: Tiejun Chen <tiejun.chen@windriver.com>
---
 arch/powerpc/kernel/entry_32.S |   43 +++++++++++++++++++++++++++++++++------
 1 files changed, 36 insertions(+), 7 deletions(-)

diff --git a/arch/powerpc/kernel/entry_32.S b/arch/powerpc/kernel/entry_32.S
index ba3aeb4..e7eefdf 100644
--- a/arch/powerpc/kernel/entry_32.S
+++ b/arch/powerpc/kernel/entry_32.S
@@ -829,19 +829,50 @@ restore_user:
 	bnel-	load_dbcr0
 #endif
 
-#ifdef CONFIG_PREEMPT
 	b	restore
 
 /* N.B. the only way to get here is from the beq following ret_from_except. */
 resume_kernel:
-	/* check current_thread_info->preempt_count */
+	/* check current_thread_info, _TIF_EMULATE_STACK_STORE */
 	rlwinm	r9,r1,0,0,(31-THREAD_SHIFT)
-	lwz	r0,TI_PREEMPT(r9)
-	cmpwi	0,r0,0		/* if non-zero, just restore regs and return */
-	bne	restore
 	lwz	r0,TI_FLAGS(r9)
+	andis.	r0,r0,_TIF_EMULATE_STACK_STORE@h
+	beq+	1f
+
+	addi	r8,r1,INT_FRAME_SIZE	/* Get the kprobed function entry */
+
+	lwz	r3,GPR1(r1)
+	subi	r3,r3,INT_FRAME_SIZE	/* dst: Allocate a trampoline exception frame */
+	mr	r4,r1			/* src:  current exception frame */
+	li	r5,INT_FRAME_SIZE	/* size: INT_FRAME_SIZE */
+	mr	r1,r3			/* Reroute the trampoline frame to r1 */
+	bl	memcpy			/* Copy from the original to the trampoline */
+
+	/* Do real store operation to complete stwu */
+	lwz	r5,GPR1(r1)
+	stw	r8,0(r5)
+
+	/* Clear _TIF_EMULATE_STACK_STORE flag */
+	rlwinm	r9,r1,0,0,(31-THREAD_SHIFT)
+	lis	r11,_TIF_EMULATE_STACK_STORE@h
+	addi	r5,r9,TI_FLAGS
+0:	lwarx	r8,0,r5
+	andc	r8,r8,r11
+#ifdef CONFIG_IBM405_ERR77
+	dcbt	0,r5
+#endif
+	stwcx.	r8,0,r5
+	bne-	0b
+1:
+
+#ifdef CONFIG_PREEMPT
+	/* check current_thread_info->preempt_count */
+	lwz	r8,TI_PREEMPT(r9)
+	cmpwi	0,r8,0		/* if non-zero, just restore regs and return */
+	bne	restore
 	andi.	r0,r0,_TIF_NEED_RESCHED
 	beq+	restore
+	lwz	r3,_MSR(r1)	
 	andi.	r0,r3,MSR_EE	/* interrupts off? */
 	beq	restore		/* don't schedule if so */
 #ifdef CONFIG_TRACE_IRQFLAGS
@@ -862,8 +893,6 @@ resume_kernel:
 	 */
 	bl	trace_hardirqs_on
 #endif
-#else
-resume_kernel:
 #endif /* CONFIG_PREEMPT */
 
 	/* interrupts are hard-disabled at this point */
-- 
1.5.6

^ permalink raw reply related

* [v3 PATCH 3/3] ppc32/kprobe: don't emulate store when kprobe stwu r1
From: Tiejun Chen @ 2012-06-03  5:07 UTC (permalink / raw)
  To: benh; +Cc: linuxppc-dev
In-Reply-To: <1338700063-30670-1-git-send-email-tiejun.chen@windriver.com>

We don't do the real store operation for kprobing 'stwu Rx,(y)R1'
since this may corrupt the exception frame, now we will do this
operation safely in exception return code after migrate current
exception frame below the kprobed function stack.

So we only update gpr[1] here and trigger a thread flag to mask
this.

Note we should make sure if we trigger kernel stack over flow.

Signed-off-by: Tiejun Chen <tiejun.chen@windriver.com>
---
 arch/powerpc/lib/sstep.c |   37 +++++++++++++++++++++++++++++++++++--
 1 files changed, 35 insertions(+), 2 deletions(-)

diff --git a/arch/powerpc/lib/sstep.c b/arch/powerpc/lib/sstep.c
index 9a52349..a4ce463 100644
--- a/arch/powerpc/lib/sstep.c
+++ b/arch/powerpc/lib/sstep.c
@@ -566,7 +566,7 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
 	unsigned long int ea;
 	unsigned int cr, mb, me, sh;
 	int err;
-	unsigned long old_ra;
+	unsigned long old_ra, val3, r1;
 	long ival;
 
 	opcode = instr >> 26;
@@ -1486,11 +1486,44 @@ int __kprobes emulate_step(struct pt_regs *regs, unsigned int instr)
 		goto ldst_done;
 
 	case 36:	/* stw */
-	case 37:	/* stwu */
 		val = regs->gpr[rd];
 		err = write_mem(val, dform_ea(instr, regs), 4, regs);
 		goto ldst_done;
 
+	case 37:	/* stwu */
+		__asm__ __volatile__("mr %0,1" : "=r" (r1) :);
+
+		val = regs->gpr[rd];
+		val3 = dform_ea(instr, regs);
+		/*
+		 * For PPC32 we always use stwu to change stack point with r1. So
+		 * this emulated store may corrupt the exception frame, now we
+		 * have to provide the exception frame trampoline, which is pushed
+		 * below the kprobed function stack. So we only update gpr[1] but
+		 * don't emulate the real store operation. We will do real store
+		 * operation safely in exception return code by checking this flag.
+		 */
+		if ((ra == 1) && !(regs->msr & MSR_PR) && (val3 >= r1)) {
+			/*
+			 * Check if we will touch kernel sack overflow
+			 */
+			if (r1 - STACK_INT_FRAME_SIZE <= current->thread.ksp_limit) {
+				printk(KERN_CRIT "Can't kprobe this since Kernel stack overflow.\n");
+				err = -EINVAL;
+				break;
+			}
+
+			/*
+			 * Check if we already set since that means we'll
+			 * lose the previous value.
+			 */
+			WARN_ON(test_thread_flag(TIF_EMULATE_STACK_STORE));
+			set_thread_flag(TIF_EMULATE_STACK_STORE);
+			err = 0;
+		} else
+			err = write_mem(val, val3, 4, regs);
+		goto ldst_done;
+
 	case 38:	/* stb */
 	case 39:	/* stbu */
 		val = regs->gpr[rd];
-- 
1.5.6

^ permalink raw reply related


This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox