LinuxPPC-Dev Archive on lore.kernel.org
 help / color / mirror / Atom feed
* Re: please pull powerpc.git 'merge' branch
From: Arnd Bergmann @ 2006-04-30 11:57 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: Olof Johansson, torvalds, Paul Mackerras
In-Reply-To: <200604301342.02043.arnd@arndb.de>

On Sunday 30 April 2006 13:42, Arnd Bergmann wrote:
> The Cell Broadband Engine Architecture in theory is 2.03 and also mandates
> some of the extensions that are optional in there.

Oh, and it also has some extensions that are supposed to be part of later
powerpc architecture releases (CBEA, appendix E):

• Mediated interrupt
• Multiple concurrent large pages
• Add TL (TLB load control) bit to logical-partitioning control register
 (LPCR) for software versus hardware load of TLB
• Change tlbie<l> of large page to always invalidate ERAT
• Hypervisor SPRs no longer readable when HV equals 0

Do we know which ones of these made it into 2.05?

	Arnd <><

^ permalink raw reply

* Re: please pull powerpc.git 'merge' branch
From: Arnd Bergmann @ 2006-04-30 11:42 UTC (permalink / raw)
  To: linuxppc-dev; +Cc: Olof Johansson, torvalds, Paul Mackerras
In-Reply-To: <20060430042059.GO5518@pb15.lixom.net>

On Sunday 30 April 2006 06:20, Olof Johansson wrote:

> We already have SMT, ICACHE_SNOOP and ALTIVEC feature bits, so it probably
> makes sense to stay in the ARCH_2_05 direction. Unfortunately it might
> be tricky to rename the old defines now due to userland exposure.
> 
> I guess Cell breaks all this logic though. Which PPC base version does
> it implement?

The Cell Broadband Engine Architecture in theory is 2.03 and also mandates
some of the extensions that are optional in there.
The relevant sections in the specs are:

| 4.1.1 Optional Features in PowerPC Architecture, Book I (Required for
|       CBEA) 
| The following facilities and instructions are considered optional in
| the PowerPC Architecture, but are required for the PPE by the CBEA
| user mode environment. 
|  • Floating reciprocal estimate single A-form (fres)
|  • Floating reciprocal square-root estimate A-form (frsqte)
|  • Vector/SIMD multimedia extension
| Note: The optional PowerPC floating-point instructions that are
| mandatory in the CBEA are needed for the application space targeted
| by the CBEA. 
|
| 4.1.3 Optional Features in PowerPC Architecture, Book II (Required
|       for CBEA) 
| The following facilities and instructions are considered optional
| in the PowerPC Architecture, but are required in the CBEA.
|  • Data cache block touch X-form (dcbt)
|    This is an optional version of dcbt that permits a program to
|    provide a hint that a sequence of data cache blocks is likely
|    to be needed soon. 
|  Book II describes these facilities and instructions.

I believe the actual implementation is missing one of the mandatory
features of 2.03 that was not in 2.02 though.

	Arnd <><

^ permalink raw reply

* Large Page Support, 2.6 kernel , PPC440
From: moris dong @ 2006-04-30  8:17 UTC (permalink / raw)
  To: linuxppc-dev

Friends,
My PPC440 (32bit) MMU supports multiple page sizes.
For the default 4K pages, my 2.6.11 kernel compiles and boots just fine.
I want to re-build it with large pages, to improve my application 
performance.
I tried modifying PAGE_SHIFT in "page.h" to 13 (8K pages) and re-build my 
kernel.
Compilation worked out fine, but my kernel does NOT boot, nor it prints 
anything to the console.

Has anyone successfully compiled & booted a 2.6 kernel for PPC440 with pages 
larger than 4K ?
What am I doing wrong ?

Thanks a lot.

_________________________________________________________________
Express yourself instantly with MSN Messenger! Download today it's FREE! 
http://messenger.msn.click-url.com/go/onm00200471ave/direct/01/

^ permalink raw reply

* Large Page Support, 2.6 kernel , PPC440
From: moris dong @ 2006-04-30  8:15 UTC (permalink / raw)
  To: linuxppc-embedded

Friends,
My PPC440 (32bit) MMU supports multiple page sizes.
For the default 4K pages, my 2.6.11 kernel compiles and boots just fine.
I want to re-build it with large pages, to improve my application 
performance.
I tried modifying PAGE_SHIFT in "page.h" to 13 (8K pages) and re-build my 
kernel.
Compilation worked out fine, but my kernel does NOT boot, nor it prints 
anything to the console.

Has anyone successfully compiled & booted a 2.6 kernel with pages larger 
than 4K ?
What am I doing wrong ?

Thanks a lot.

_________________________________________________________________
Express yourself instantly with MSN Messenger! Download today it's FREE! 
http://messenger.msn.click-url.com/go/onm00200471ave/direct/01/

^ permalink raw reply

* [PATCH] powerpc: Fix comment in ibm_architecture_vec
From: Olof Johansson @ 2006-04-30  4:53 UTC (permalink / raw)
  To: Paul Mackerras; +Cc: linuxppc-dev
In-Reply-To: <17491.1134.565353.149941@cargo.ozlabs.ibm.com>

On Sat, Apr 29, 2006 at 04:15:10PM +1000, Paul Mackerras wrote:

> Paul Mackerras:
>       powerpc/pseries: Tell firmware our capabilities on new machines

Below is definitely not 2.6.17 material, so for the 2.6.18 queue:

---

Either constant or comment is wrong, I'm guessing it's comment since the
ELF header version uses 64MB.

Signed-off-by: Olof Johansson <olof@lixom.net>


diff --git a/arch/powerpc/kernel/prom_init.c b/arch/powerpc/kernel/prom_init.c
index 078fb55..ef99f26 100644
--- a/arch/powerpc/kernel/prom_init.c
+++ b/arch/powerpc/kernel/prom_init.c
@@ -705,7 +705,7 @@ static unsigned char ibm_architecture_ve
 	W(0xffffffff),			/* virt_base */
 	W(0xffffffff),			/* virt_size */
 	W(0xffffffff),			/* load_base */
-	W(64),				/* 128MB min RMA */
+	W(64),				/* 64MB min RMA */
 	W(0xffffffff),			/* full client load */
 	0,				/* min RMA percentage of total RAM */
 	48,				/* max log_2(hash table size) */

^ permalink raw reply related

* [PATCH] powerpc: rename PPC_FEATURE_POWER.* to PPC_FEATURE_ARCH.*
From: Olof Johansson @ 2006-04-30  4:48 UTC (permalink / raw)
  To: paulus; +Cc: linuxppc-dev
In-Reply-To: <20060430035001.GN5518@pb15.lixom.net>

On Sat, Apr 29, 2006 at 10:50:01PM -0500, Olof Johansson wrote:

> A rename of existing names might make sense for consistency/clarity. But
> that's outside of __KERNEL__ so it would break userspace.

Less talk, more patches. 2.6.18 material.

Btw, looks like glibc duplicates the definitions instead of includes them,
but let's be nice and keep them anyway. Besides, they got the ISA
version to processor mappings wrong in their comments.


---

Rename PPC_FEATURE_POWER.* to be signify the base architecture versions
instead. Keep the old names around since they're defined outside of
__KERNEL__.

If POWER5 is 2.02 (last public version), and POWER6 is 2.05, then POWER5+
should be 2.03 or 2.04. Not sure what fills in the hole, but I took a
guess that 5+ is 2.03.


Signed-off-by: Olof Johansson <olof@lixom.net>

diff --git a/arch/powerpc/kernel/cputable.c b/arch/powerpc/kernel/cputable.c
index 3f7182d..7017d1c 100644
--- a/arch/powerpc/kernel/cputable.c
+++ b/arch/powerpc/kernel/cputable.c
@@ -52,10 +52,10 @@ extern void __setup_cpu_ppc970(unsigned 
 #define COMMON_USER		(PPC_FEATURE_32 | PPC_FEATURE_HAS_FPU | \
 				 PPC_FEATURE_HAS_MMU)
 #define COMMON_USER_PPC64	(COMMON_USER | PPC_FEATURE_64)
-#define COMMON_USER_POWER4	(COMMON_USER_PPC64 | PPC_FEATURE_POWER4)
-#define COMMON_USER_POWER5	(COMMON_USER_PPC64 | PPC_FEATURE_POWER5 |\
+#define COMMON_USER_POWER4	(COMMON_USER_PPC64 | PPC_FEATURE_ARCH_2_00)
+#define COMMON_USER_POWER5	(COMMON_USER_PPC64 | PPC_FEATURE_ARCH_2_02 |\
 				 PPC_FEATURE_SMT | PPC_FEATURE_ICACHE_SNOOP)
-#define COMMON_USER_POWER5_PLUS	(COMMON_USER_PPC64 | PPC_FEATURE_POWER5_PLUS|\
+#define COMMON_USER_POWER5_PLUS	(COMMON_USER_PPC64 | PPC_FEATURE_ARCH_2_03|\
 				 PPC_FEATURE_SMT | PPC_FEATURE_ICACHE_SNOOP)
 #define COMMON_USER_POWER6	(COMMON_USER_PPC64 | PPC_FEATURE_ARCH_2_05 |\
 				 PPC_FEATURE_SMT | PPC_FEATURE_ICACHE_SNOOP)
diff --git a/include/asm-powerpc/cputable.h b/include/asm-powerpc/cputable.h
index 9fcf016..deae3af 100644
--- a/include/asm-powerpc/cputable.h
+++ b/include/asm-powerpc/cputable.h
@@ -15,15 +15,24 @@
 #define PPC_FEATURE_HAS_EFP_SINGLE	0x00400000
 #define PPC_FEATURE_HAS_EFP_DOUBLE	0x00200000
 #define PPC_FEATURE_NO_TB		0x00100000
-#define PPC_FEATURE_POWER4		0x00080000
-#define PPC_FEATURE_POWER5		0x00040000
-#define PPC_FEATURE_POWER5_PLUS		0x00020000
+#define PPC_FEATURE_ARCH_2_00		0x00080000
+#define PPC_FEATURE_ARCH_2_02		0x00040000
+#define PPC_FEATURE_ARCH_2_03		0x00020000
 #define PPC_FEATURE_CELL		0x00010000
 #define PPC_FEATURE_BOOKE		0x00008000
 #define PPC_FEATURE_SMT			0x00004000
 #define PPC_FEATURE_ICACHE_SNOOP	0x00002000
 #define PPC_FEATURE_ARCH_2_05		0x00001000
 
+/*
+ * These are needed for userspace compat, since processor
+ * models used to be used before instead of arch versions
+ */
+
+#define PPC_FEATURE_POWER4	PPC_FEATURE_ARCH_2_00
+#define PPC_FEATURE_POWER5	PPC_FEATURE_ARCH_2_02
+#define PPC_FEATURE_POWER5_PLUS	PPC_FEATURE_ARCH_2_03
+
 #ifdef __KERNEL__
 #ifndef __ASSEMBLY__
 

^ permalink raw reply related

* Re: please pull powerpc.git 'merge' branch
From: Olof Johansson @ 2006-04-30  4:20 UTC (permalink / raw)
  To: Segher Boessenkool; +Cc: Olof Johansson, linuxppc-dev, torvalds, Paul Mackerras
In-Reply-To: <71339D1F-CAF1-4FF0-A1A3-1A74B8984F05@kernel.crashing.org>

On Sun, Apr 30, 2006 at 05:12:57AM +0200, Segher Boessenkool wrote:
> >>Previously we've said implementation instead of specification
> >>("PPC_FEATURE_POWER5_PLUS" etc). That's better than saying base
> >>architecture version, since there are parts of the arch that might or
> >>might not be implemented (i.e. optional features, etc).
> >
> >We now have the AT_PLATFORM string, which we didn't have when we added
> >the POWER5_PLUS etc. features.  That specifies which particular
> >implementation we are on quite precisely.  We don't want to have a bit
> >for every single implementation or we'll run out of bits.
> >
> >The ARCH_2_05 bit means all the non-optional bits of the 2.05
> >architecture.  If there are optional features in the architecture, we
> >have separate bits for them.  For example, we don't have separate
> >bits for POWER4 and for 970; instead we have a HAS_ALTIVEC bit, and
> >for 970 we set both POWER4 and HAS_ALTIVEC.  So the POWER4 bit is
> >really a "2.00 architecture version" bit.
> 
> Except that the 970 at least is actually version 2.01.

Are there any userspace-visible differences between 2.00 and 2.01?

> Sounds
> like names are better than bare numbers -- you showed yourself that
> numbers like this are confusing, but you also say that a cpu name
> really means an arch version (which isn't so bad -- there generally
> is only one "main" CPU per arch version anyway, and people generally
> know what is compatible to what).

It's actually about an even tradeoff between the two. We run the risk
of running out of bits eventually no matter what, and as long as it's
blindingly clear and well stated that it does not imply any optional
features, then it doesn't matter. This puts the burden on userspace
developers to know which features are optional, not just what works on
their POWER6 lab machine, etc.

> So please rename ARCH_2_05 to the name of the first CPU that implements
> architecture 2.05?

We already have SMT, ICACHE_SNOOP and ALTIVEC feature bits, so it probably
makes sense to stay in the ARCH_2_05 direction. Unfortunately it might
be tricky to rename the old defines now due to userland exposure.

I guess Cell breaks all this logic though. Which PPC base version does
it implement?


-Olof

^ permalink raw reply

* Re: please pull powerpc.git 'merge' branch
From: Olof Johansson @ 2006-04-30  3:50 UTC (permalink / raw)
  To: Paul Mackerras; +Cc: Olof Johansson, linuxppc-dev, torvalds
In-Reply-To: <17491.64254.653743.367039@cargo.ozlabs.ibm.com>

On Sun, Apr 30, 2006 at 09:47:10AM +1000, Paul Mackerras wrote:
> Olof Johansson writes:
> 
> > Previously we've said implementation instead of specification
> > ("PPC_FEATURE_POWER5_PLUS" etc). That's better than saying base
> > architecture version, since there are parts of the arch that might or
> > might not be implemented (i.e. optional features, etc).
> 
> We now have the AT_PLATFORM string, which we didn't have when we added
> the POWER5_PLUS etc. features.  That specifies which particular
> implementation we are on quite precisely.  We don't want to have a bit
> for every single implementation or we'll run out of bits.
> 
> The ARCH_2_05 bit means all the non-optional bits of the 2.05
> architecture.  If there are optional features in the architecture, we
> have separate bits for them.  For example, we don't have separate
> bits for POWER4 and for 970; instead we have a HAS_ALTIVEC bit, and
> for 970 we set both POWER4 and HAS_ALTIVEC.  So the POWER4 bit is
> really a "2.00 architecture version" bit.

Ok, I guess that's more or less how it's been used, since there's only
been one implementation per architecture version in the past (970 series
being the main exception). The only one left out from the table seems
to be 2.01 (POWER4+), not sure if it had any userspace-visible changes
in the first place.

A rename of existing names might make sense for consistency/clarity. But
that's outside of __KERNEL__ so it would break userspace.

> > Don't you want to fall back to the ELF method if the prom call fails
> > (ret != 0)? Right you close and return.
> 
> If the ibm,client-architecture-support method exists but
> returns an error, call_prom_ret returns zero but puts a non-zero value
> in ret.

Right, that's quite obvious from the implementation.

> In that case we don't want to try the elf-header method.

That was my question, if it made sense to fall back to it. And that's a
"no". Thanks. :-)


-Olof

^ permalink raw reply

* Re: please pull powerpc.git 'merge' branch
From: Segher Boessenkool @ 2006-04-30  3:12 UTC (permalink / raw)
  To: Paul Mackerras; +Cc: Olof Johansson, linuxppc-dev, torvalds
In-Reply-To: <17491.64254.653743.367039@cargo.ozlabs.ibm.com>

>> Previously we've said implementation instead of specification
>> ("PPC_FEATURE_POWER5_PLUS" etc). That's better than saying base
>> architecture version, since there are parts of the arch that might or
>> might not be implemented (i.e. optional features, etc).
>
> We now have the AT_PLATFORM string, which we didn't have when we added
> the POWER5_PLUS etc. features.  That specifies which particular
> implementation we are on quite precisely.  We don't want to have a bit
> for every single implementation or we'll run out of bits.
>
> The ARCH_2_05 bit means all the non-optional bits of the 2.05
> architecture.  If there are optional features in the architecture, we
> have separate bits for them.  For example, we don't have separate
> bits for POWER4 and for 970; instead we have a HAS_ALTIVEC bit, and
> for 970 we set both POWER4 and HAS_ALTIVEC.  So the POWER4 bit is
> really a "2.00 architecture version" bit.

Except that the 970 at least is actually version 2.01.  Sounds
like names are better than bare numbers -- you showed yourself that
numbers like this are confusing, but you also say that a cpu name
really means an arch version (which isn't so bad -- there generally
is only one "main" CPU per arch version anyway, and people generally
know what is compatible to what).

So please rename ARCH_2_05 to the name of the first CPU that implements
architecture 2.05?


Segher

^ permalink raw reply

* [PATCH] powerpc: Make rtas console _much_ faster
From: Michael Ellerman @ 2006-04-30  3:07 UTC (permalink / raw)
  To: Paul Mackerras; +Cc: linuxppc-dev, linux-kernel, Arnd Bergmann, cbe-oss-dev
In-Reply-To: <200604291000.52541.arnd@arndb.de>

Currently the hvc_rtas driver is painfully slow to use. Our "benchmark" is
ls -R /etc, which spits out about 27866 characters. The theoretical maximum
speed would be about 2.2 seconds, the current code takes ~50 seconds.

The core of the problem is that sometimes when the tty layer asks us to push
characters the firmware isn't able to handle some or all of them, and so
returns an error. The current code sees this and just returns to the tty code
with the buffer half sent.

The khvcd thread will eventually wake up and try to push more characters, which
will usually work because by then the firmware's had time to make room. But
the khvcd thread only wakes up every 10 milliseconds, which isn't fast enough.

So change the khvcd thread logic so that if there's an incomplete write we
yield() and then immediately try writing again. Doing so makes POLL_QUICK and
POLL_WRITE synonymous, so remove POLL_QUICK.

With this patch our "benchmark" takes ~2.8 seconds.

Signed-off-by: Michael Ellerman <michael@ellerman.id.au>
---

 drivers/char/hvc_console.c |    4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

Index: cell/drivers/char/hvc_console.c
===================================================================
--- cell.orig/drivers/char/hvc_console.c
+++ cell/drivers/char/hvc_console.c
@@ -553,7 +553,6 @@ static int hvc_chars_in_buffer(struct tt
 
 #define HVC_POLL_READ	0x00000001
 #define HVC_POLL_WRITE	0x00000002
-#define HVC_POLL_QUICK	0x00000004
 
 static int hvc_poll(struct hvc_struct *hp)
 {
@@ -568,6 +567,7 @@ static int hvc_poll(struct hvc_struct *h
 	/* Push pending writes */
 	if (hp->n_outbuf > 0)
 		hvc_push(hp);
+
 	/* Reschedule us if still some write pending */
 	if (hp->n_outbuf > 0)
 		poll_mask |= HVC_POLL_WRITE;
@@ -680,7 +680,7 @@ int khvcd(void *unused)
 			poll_mask |= HVC_POLL_READ;
 		if (hvc_kicked)
 			continue;
-		if (poll_mask & HVC_POLL_QUICK) {
+		if (poll_mask & HVC_POLL_WRITE) {
 			yield();
 			continue;
 		}

^ permalink raw reply

* Re: [PATCH 11/13] cell: split out board specific files
From: Segher Boessenkool @ 2006-04-30  2:52 UTC (permalink / raw)
  To: Arnd Bergmann
  Cc: linuxppc-dev, paulus, Arnd Bergmann, linux-kernel, cbe-oss-dev
In-Reply-To: <20060429233922.167124000@localhost.localdomain>

> Split the Cell BE support into generic and platform
> dependant parts.
>
> Creates a new config variable CONFIG_PPC_IBM_CELL_BLADE.
> The existing CONFIG_PPC_CELL is now used to denote the
> generic Cell processor support.  Also renames spu_priv1.c
> to spu_priv1_mmio.c.

>  config CELL_IIC
> -	depends on PPC_CELL
> +	depends on PPC_IBM_CELL_BLADE
>  	bool
>  	default y

Erm no...  Make this

	depends on PPC_CELL && !SOME_HYPERVISOR_THING

to reflect the _real_ dependency please?  Similar in a few other
places perhaps.


Segher

^ permalink raw reply

* Re: please pull powerpc.git 'merge' branch
From: Paul Mackerras @ 2006-04-29 23:47 UTC (permalink / raw)
  To: Olof Johansson; +Cc: linuxppc-dev, torvalds
In-Reply-To: <20060429151936.GM5518@pb15.lixom.net>

Olof Johansson writes:

> Previously we've said implementation instead of specification
> ("PPC_FEATURE_POWER5_PLUS" etc). That's better than saying base
> architecture version, since there are parts of the arch that might or
> might not be implemented (i.e. optional features, etc).

We now have the AT_PLATFORM string, which we didn't have when we added
the POWER5_PLUS etc. features.  That specifies which particular
implementation we are on quite precisely.  We don't want to have a bit
for every single implementation or we'll run out of bits.

The ARCH_2_05 bit means all the non-optional bits of the 2.05
architecture.  If there are optional features in the architecture, we
have separate bits for them.  For example, we don't have separate
bits for POWER4 and for 970; instead we have a HAS_ALTIVEC bit, and
for 970 we set both POWER4 and HAS_ALTIVEC.  So the POWER4 bit is
really a "2.00 architecture version" bit.

> Don't you want to fall back to the ELF method if the prom call fails
> (ret != 0)? Right you close and return.

There are two return values here - the return from call-method, and
the return from ibm,client-architecture-support.  If the latter does
not exist, call-method returns non-zero, which gets returned from
call_prom_ret, and we close the root node and try the elf-header
method.  If the ibm,client-architecture-support method exists but
returns an error, call_prom_ret returns zero but puts a non-zero value
in ret.  In that case we don't want to try the elf-header method.

So I claim that the code is correct as it is. :)

Paul.

^ permalink raw reply

* [PATCH 10/13] cell: correctly detect systemsim host
From: Arnd Bergmann @ 2006-04-29 23:42 UTC (permalink / raw)
  To: paulus
  Cc: Arnd Bergmann, linuxppc-dev, Christian Krafft, cbe-oss-dev,
	linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

From: Christian Krafft <krafft@de.ibm.com>
Systemsim uses a different compatible property in the device tree.

Signed-off-by: Christian Krafft <krafft@de.ibm.com>
Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/platforms/cell/setup.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/setup.c	2006-04-29 
22:53:51.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/setup.c	2006-04-29 
22:54:32.000000000 +0200
@@ -201,10 +201,13 @@
 	 * more appropriate detection logic
 	 */
 	unsigned long root = of_get_flat_dt_root();
-	if (!of_flat_dt_is_compatible(root, "IBM,CPBW-1.0"))
-		return 0;
+	if (of_flat_dt_is_compatible(root, "IBM,CPBW-1.0"))
+		return 1;
 
-	return 1;
+	if (of_flat_dt_is_compatible(root, "IBM,CPBW-SystemSim"))
+		return 1;
+
+	return 0;
 }
 
 /*

--

^ permalink raw reply

* [PATCH 13/13] cell: set SPU interrupt affinity in spu_priv1 code
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

 From: Geoff Levand <geoffrey.levand@am.sony.com>

This changes the hypervisor abstraction of setting cpu affinity to a
higher level to avoid platform dependent interrupt controller
routines.  I replaced spu_priv1_ops:spu_int_route_set() with a
new routine spu_priv1_ops:spu_cpu_affinity_set().

As a by-product, this change eliminated what looked like an
existing bug in the set affinity code where spu_int_route_set()
mistakenly called int_stat_get().

Signed-off-by: Geoff Levand <geoffrey.levand@am.sony.com>
Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/platforms/cell/spu_base.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spu_base.c	2006-04-29 22:54:59.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spu_base.c	2006-04-29 22:57:08.000000000 +0200
@@ -522,14 +522,6 @@
 	return ret;
 }
 
-void spu_irq_setaffinity(struct spu *spu, int cpu)
-{
-	u64 target = iic_get_target_id(cpu);
-	u64 route = target << 48 | target << 32 | target << 16;
-	spu_int_route_set(spu, route);
-}
-EXPORT_SYMBOL_GPL(spu_irq_setaffinity);
-
 static void __iomem * __init map_spe_prop(struct device_node *n,
 						 const char *name)
 {
Index: linus-2.6/arch/powerpc/platforms/cell/spu_priv1_mmio.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spu_priv1_mmio.c	2006-04-29 22:54:59.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spu_priv1_mmio.c	2006-04-29 22:56:37.000000000 +0200
@@ -24,6 +24,8 @@
 #include <asm/spu.h>
 #include <asm/spu_priv1.h>
 
+#include "interrupt.h"
+
 static void int_mask_and(struct spu *spu, int class, u64 mask)
 {
 	u64 old_mask;
@@ -60,8 +62,10 @@
 	return in_be64(&spu->priv1->int_stat_RW[class]);
 }
 
-static void int_route_set(struct spu *spu, u64 route)
+static void cpu_affinity_set(struct spu *spu, int cpu)
 {
+	u64 target = iic_get_target_id(cpu);
+	u64 route = target << 48 | target << 32 | target << 16;
 	out_be64(&spu->priv1->int_route_RW, route);
 }
 
@@ -138,7 +142,7 @@
 	.int_mask_get = int_mask_get,
 	.int_stat_clear = int_stat_clear,
 	.int_stat_get = int_stat_get,
-	.int_route_set = int_route_set,
+	.cpu_affinity_set = cpu_affinity_set,
 	.mfc_dar_get = mfc_dar_get,
 	.mfc_dsisr_get = mfc_dsisr_get,
 	.mfc_dsisr_set = mfc_dsisr_set,
Index: linus-2.6/arch/powerpc/platforms/cell/spufs/sched.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spufs/sched.c	2006-04-29 22:53:50.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spufs/sched.c	2006-04-29 22:56:37.000000000 +0200
@@ -43,6 +43,7 @@
 #include <asm/mmu_context.h>
 #include <asm/spu.h>
 #include <asm/spu_csa.h>
+#include <asm/spu_priv1.h>
 #include "spufs.h"
 
 #define SPU_MIN_TIMESLICE 	(100 * HZ / 1000)
@@ -363,7 +364,7 @@
 	 * We're likely to wait for interrupts on the same
 	 * CPU that we are now on, so send them here.
 	 */
-	spu_irq_setaffinity(spu, raw_smp_processor_id());
+	spu_cpu_affinity_set(spu, raw_smp_processor_id());
 	put_active_spu(spu);
 	return 0;
 }
Index: linus-2.6/include/asm-powerpc/spu_priv1.h
===================================================================
--- linus-2.6.orig/include/asm-powerpc/spu_priv1.h	2006-04-29 22:54:59.000000000 +0200
+++ linus-2.6/include/asm-powerpc/spu_priv1.h	2006-04-29 22:56:37.000000000 +0200
@@ -33,7 +33,7 @@
 	u64 (*int_mask_get) (struct spu *spu, int class);
 	void (*int_stat_clear) (struct spu *spu, int class, u64 stat);
 	u64 (*int_stat_get) (struct spu *spu, int class);
-	void (*int_route_set) (struct spu *spu, u64 route);
+	void (*cpu_affinity_set) (struct spu *spu, int cpu);
 	u64 (*mfc_dar_get) (struct spu *spu);
 	u64 (*mfc_dsisr_get) (struct spu *spu);
 	void (*mfc_dsisr_set) (struct spu *spu, u64 dsisr);
@@ -89,9 +89,9 @@
 }
 
 static inline void
-spu_int_route_set (struct spu *spu, u64 route)
+spu_cpu_affinity_set (struct spu *spu, int cpu)
 {
-	spu_priv1_ops->int_stat_get(spu, route);
+	spu_priv1_ops->cpu_affinity_set(spu, cpu);
 }
 
 static inline u64

--

^ permalink raw reply

* [PATCH 12/13] cell: abstract priviledge-1 SPU registers for hypervisors
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

 From: Geoff Levand <geoffrey.levand@am.sony.com>

To support multi-platform binaries the spu hypervisor accessor
routines must have runtime binding.

I removed the existing statically linked routines in spu.h
and spu_priv1_mmio.c and created new accessor routines in spu_priv1.h
that operate indirectly through an ops struct spu_priv1_ops.
spu_priv1_mmio.c contains the instance of the accessor routines
for running on raw hardware.

Signed-off-by: Geoff Levand <geoffrey.levand@am.sony.com>
Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/platforms/cell/setup.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/setup.c	2006-04-29 23:12:15.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/setup.c	2006-04-29 23:13:06.000000000 +0200
@@ -46,6 +46,7 @@
 #include <asm/cputable.h>
 #include <asm/ppc-pci.h>
 #include <asm/irq.h>
+#include <asm/spu_priv1.h>
 
 #include "interrupt.h"
 #include "iommu.h"
@@ -149,6 +150,9 @@
 {
 	ppc_md.init_IRQ       = iic_init_IRQ;
 	ppc_md.get_irq        = iic_get_irq;
+#ifdef CONFIG_SPU_BASE
+	spu_priv1_ops         = &spu_priv1_mmio_ops;
+#endif
 
 #ifdef CONFIG_SMP
 	smp_init_cell();
Index: linus-2.6/arch/powerpc/platforms/cell/spu_base.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spu_base.c	2006-04-29 23:12:16.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spu_base.c	2006-04-29 23:13:06.000000000 +0200
@@ -34,10 +34,15 @@
 #include <asm/prom.h>
 #include <linux/mutex.h>
 #include <asm/spu.h>
+#include <asm/spu_priv1.h>
 #include <asm/mmu_context.h>
 
 #include "interrupt.h"
 
+const struct spu_priv1_ops *spu_priv1_ops;
+
+EXPORT_SYMBOL_GPL(spu_priv1_ops);
+
 static int __spu_trap_invalid_dma(struct spu *spu)
 {
 	pr_debug("%s\n", __FUNCTION__);
Index: linus-2.6/arch/powerpc/platforms/cell/spu_priv1_mmio.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spu_priv1_mmio.c	2006-04-29 23:12:55.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spu_priv1_mmio.c	2006-04-29 23:13:06.000000000 +0200
@@ -1,133 +1,155 @@
 /*
- * access to SPU privileged registers
+ * spu hypervisor abstraction for direct hardware access.
+ *
+ *  (C) Copyright IBM Deutschland Entwicklung GmbH 2005
+ *  Copyright 2006 Sony Corp.
+ *
+ *  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; version 2 of the License.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, write to the Free Software
+ *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
  */
+
 #include <linux/module.h>
 
 #include <asm/io.h>
 #include <asm/spu.h>
+#include <asm/spu_priv1.h>
 
-void spu_int_mask_and(struct spu *spu, int class, u64 mask)
+static void int_mask_and(struct spu *spu, int class, u64 mask)
 {
 	u64 old_mask;
 
 	old_mask = in_be64(&spu->priv1->int_mask_RW[class]);
 	out_be64(&spu->priv1->int_mask_RW[class], old_mask & mask);
 }
-EXPORT_SYMBOL_GPL(spu_int_mask_and);
 
-void spu_int_mask_or(struct spu *spu, int class, u64 mask)
+static void int_mask_or(struct spu *spu, int class, u64 mask)
 {
 	u64 old_mask;
 
 	old_mask = in_be64(&spu->priv1->int_mask_RW[class]);
 	out_be64(&spu->priv1->int_mask_RW[class], old_mask | mask);
 }
-EXPORT_SYMBOL_GPL(spu_int_mask_or);
 
-void spu_int_mask_set(struct spu *spu, int class, u64 mask)
+static void int_mask_set(struct spu *spu, int class, u64 mask)
 {
 	out_be64(&spu->priv1->int_mask_RW[class], mask);
 }
-EXPORT_SYMBOL_GPL(spu_int_mask_set);
 
-u64 spu_int_mask_get(struct spu *spu, int class)
+static u64 int_mask_get(struct spu *spu, int class)
 {
 	return in_be64(&spu->priv1->int_mask_RW[class]);
 }
-EXPORT_SYMBOL_GPL(spu_int_mask_get);
 
-void spu_int_stat_clear(struct spu *spu, int class, u64 stat)
+static void int_stat_clear(struct spu *spu, int class, u64 stat)
 {
 	out_be64(&spu->priv1->int_stat_RW[class], stat);
 }
-EXPORT_SYMBOL_GPL(spu_int_stat_clear);
 
-u64 spu_int_stat_get(struct spu *spu, int class)
+static u64 int_stat_get(struct spu *spu, int class)
 {
 	return in_be64(&spu->priv1->int_stat_RW[class]);
 }
-EXPORT_SYMBOL_GPL(spu_int_stat_get);
 
-void spu_int_route_set(struct spu *spu, u64 route)
+static void int_route_set(struct spu *spu, u64 route)
 {
 	out_be64(&spu->priv1->int_route_RW, route);
 }
-EXPORT_SYMBOL_GPL(spu_int_route_set);
 
-u64 spu_mfc_dar_get(struct spu *spu)
+static u64 mfc_dar_get(struct spu *spu)
 {
 	return in_be64(&spu->priv1->mfc_dar_RW);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_dar_get);
 
-u64 spu_mfc_dsisr_get(struct spu *spu)
+static u64 mfc_dsisr_get(struct spu *spu)
 {
 	return in_be64(&spu->priv1->mfc_dsisr_RW);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_dsisr_get);
 
-void spu_mfc_dsisr_set(struct spu *spu, u64 dsisr)
+static void mfc_dsisr_set(struct spu *spu, u64 dsisr)
 {
 	out_be64(&spu->priv1->mfc_dsisr_RW, dsisr);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_dsisr_set);
 
-void spu_mfc_sdr_set(struct spu *spu, u64 sdr)
+static void mfc_sdr_set(struct spu *spu, u64 sdr)
 {
 	out_be64(&spu->priv1->mfc_sdr_RW, sdr);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_sdr_set);
 
-void spu_mfc_sr1_set(struct spu *spu, u64 sr1)
+static void mfc_sr1_set(struct spu *spu, u64 sr1)
 {
 	out_be64(&spu->priv1->mfc_sr1_RW, sr1);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_sr1_set);
 
-u64 spu_mfc_sr1_get(struct spu *spu)
+static u64 mfc_sr1_get(struct spu *spu)
 {
 	return in_be64(&spu->priv1->mfc_sr1_RW);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_sr1_get);
 
-void spu_mfc_tclass_id_set(struct spu *spu, u64 tclass_id)
+static void mfc_tclass_id_set(struct spu *spu, u64 tclass_id)
 {
 	out_be64(&spu->priv1->mfc_tclass_id_RW, tclass_id);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_tclass_id_set);
 
-u64 spu_mfc_tclass_id_get(struct spu *spu)
+static u64 mfc_tclass_id_get(struct spu *spu)
 {
 	return in_be64(&spu->priv1->mfc_tclass_id_RW);
 }
-EXPORT_SYMBOL_GPL(spu_mfc_tclass_id_get);
 
-void spu_tlb_invalidate(struct spu *spu)
+static void tlb_invalidate(struct spu *spu)
 {
 	out_be64(&spu->priv1->tlb_invalidate_entry_W, 0ul);
 }
-EXPORT_SYMBOL_GPL(spu_tlb_invalidate);
 
-void spu_resource_allocation_groupID_set(struct spu *spu, u64 id)
+static void resource_allocation_groupID_set(struct spu *spu, u64 id)
 {
 	out_be64(&spu->priv1->resource_allocation_groupID_RW, id);
 }
-EXPORT_SYMBOL_GPL(spu_resource_allocation_groupID_set);
 
-u64 spu_resource_allocation_groupID_get(struct spu *spu)
+static u64 resource_allocation_groupID_get(struct spu *spu)
 {
 	return in_be64(&spu->priv1->resource_allocation_groupID_RW);
 }
-EXPORT_SYMBOL_GPL(spu_resource_allocation_groupID_get);
 
-void spu_resource_allocation_enable_set(struct spu *spu, u64 enable)
+static void resource_allocation_enable_set(struct spu *spu, u64 enable)
 {
 	out_be64(&spu->priv1->resource_allocation_enable_RW, enable);
 }
-EXPORT_SYMBOL_GPL(spu_resource_allocation_enable_set);
 
-u64 spu_resource_allocation_enable_get(struct spu *spu)
+static u64 resource_allocation_enable_get(struct spu *spu)
 {
 	return in_be64(&spu->priv1->resource_allocation_enable_RW);
 }
-EXPORT_SYMBOL_GPL(spu_resource_allocation_enable_get);
+
+const struct spu_priv1_ops spu_priv1_mmio_ops =
+{
+	.int_mask_and = int_mask_and,
+	.int_mask_or = int_mask_or,
+	.int_mask_set = int_mask_set,
+	.int_mask_get = int_mask_get,
+	.int_stat_clear = int_stat_clear,
+	.int_stat_get = int_stat_get,
+	.int_route_set = int_route_set,
+	.mfc_dar_get = mfc_dar_get,
+	.mfc_dsisr_get = mfc_dsisr_get,
+	.mfc_dsisr_set = mfc_dsisr_set,
+	.mfc_sdr_set = mfc_sdr_set,
+	.mfc_sr1_set = mfc_sr1_set,
+	.mfc_sr1_get = mfc_sr1_get,
+	.mfc_tclass_id_set = mfc_tclass_id_set,
+	.mfc_tclass_id_get = mfc_tclass_id_get,
+	.tlb_invalidate = tlb_invalidate,
+	.resource_allocation_groupID_set = resource_allocation_groupID_set,
+	.resource_allocation_groupID_get = resource_allocation_groupID_get,
+	.resource_allocation_enable_set = resource_allocation_enable_set,
+	.resource_allocation_enable_get = resource_allocation_enable_get,
+};
Index: linus-2.6/arch/powerpc/platforms/cell/spufs/hw_ops.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spufs/hw_ops.c	2006-04-29 23:12:15.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spufs/hw_ops.c	2006-04-29 23:13:06.000000000 +0200
@@ -32,6 +32,7 @@
 
 #include <asm/io.h>
 #include <asm/spu.h>
+#include <asm/spu_priv1.h>
 #include <asm/spu_csa.h>
 #include <asm/mmu_context.h>
 #include "spufs.h"
Index: linus-2.6/arch/powerpc/platforms/cell/spufs/switch.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spufs/switch.c	2006-04-29 23:12:15.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spufs/switch.c	2006-04-29 23:13:06.000000000 +0200
@@ -46,6 +46,7 @@
 
 #include <asm/io.h>
 #include <asm/spu.h>
+#include <asm/spu_priv1.h>
 #include <asm/spu_csa.h>
 #include <asm/mmu_context.h>
 
Index: linus-2.6/include/asm-powerpc/spu.h
===================================================================
--- linus-2.6.orig/include/asm-powerpc/spu.h	2006-04-29 23:12:16.000000000 +0200
+++ linus-2.6/include/asm-powerpc/spu.h	2006-04-29 23:13:06.000000000 +0200
@@ -181,29 +181,6 @@
 #endif /* MODULE */
 
 
-/* access to priv1 registers */
-void spu_int_mask_and(struct spu *spu, int class, u64 mask);
-void spu_int_mask_or(struct spu *spu, int class, u64 mask);
-void spu_int_mask_set(struct spu *spu, int class, u64 mask);
-u64 spu_int_mask_get(struct spu *spu, int class);
-void spu_int_stat_clear(struct spu *spu, int class, u64 stat);
-u64 spu_int_stat_get(struct spu *spu, int class);
-void spu_int_route_set(struct spu *spu, u64 route);
-u64 spu_mfc_dar_get(struct spu *spu);
-u64 spu_mfc_dsisr_get(struct spu *spu);
-void spu_mfc_dsisr_set(struct spu *spu, u64 dsisr);
-void spu_mfc_sdr_set(struct spu *spu, u64 sdr);
-void spu_mfc_sr1_set(struct spu *spu, u64 sr1);
-u64 spu_mfc_sr1_get(struct spu *spu);
-void spu_mfc_tclass_id_set(struct spu *spu, u64 tclass_id);
-u64 spu_mfc_tclass_id_get(struct spu *spu);
-void spu_tlb_invalidate(struct spu *spu);
-void spu_resource_allocation_groupID_set(struct spu *spu, u64 id);
-u64 spu_resource_allocation_groupID_get(struct spu *spu);
-void spu_resource_allocation_enable_set(struct spu *spu, u64 enable);
-u64 spu_resource_allocation_enable_get(struct spu *spu);
-
-
 /*
  * This defines the Local Store, Problem Area and Privlege Area of an SPU.
  */
Index: linus-2.6/include/asm-powerpc/spu_priv1.h
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ linus-2.6/include/asm-powerpc/spu_priv1.h	2006-04-29 23:13:06.000000000 +0200
@@ -0,0 +1,189 @@
+/*
+ * Defines an spu hypervisor abstraction layer.
+ *
+ *  Copyright 2006 Sony Corp.
+ *
+ *  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; version 2 of the License.
+ *
+ *  This program is distributed in the hope that it will be useful,
+ *  but WITHOUT ANY WARRANTY; without even the implied warranty of
+ *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ *  GNU General Public License for more details.
+ *
+ *  You should have received a copy of the GNU General Public License
+ *  along with this program; if not, write to the Free Software
+ *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
+ */
+
+#if !defined(_SPU_PRIV1_H)
+#define _SPU_PRIV1_H
+#if defined(__KERNEL__)
+
+struct spu;
+
+/* access to priv1 registers */
+
+struct spu_priv1_ops
+{
+	void (*int_mask_and) (struct spu *spu, int class, u64 mask);
+	void (*int_mask_or) (struct spu *spu, int class, u64 mask);
+	void (*int_mask_set) (struct spu *spu, int class, u64 mask);
+	u64 (*int_mask_get) (struct spu *spu, int class);
+	void (*int_stat_clear) (struct spu *spu, int class, u64 stat);
+	u64 (*int_stat_get) (struct spu *spu, int class);
+	void (*int_route_set) (struct spu *spu, u64 route);
+	u64 (*mfc_dar_get) (struct spu *spu);
+	u64 (*mfc_dsisr_get) (struct spu *spu);
+	void (*mfc_dsisr_set) (struct spu *spu, u64 dsisr);
+	void (*mfc_sdr_set) (struct spu *spu, u64 sdr);
+	void (*mfc_sr1_set) (struct spu *spu, u64 sr1);
+	u64 (*mfc_sr1_get) (struct spu *spu);
+	void (*mfc_tclass_id_set) (struct spu *spu, u64 tclass_id);
+	u64 (*mfc_tclass_id_get) (struct spu *spu);
+	void (*smm_pgsz_set) (struct spu *spu, u64 pgsz);
+	void (*tlb_invalidate) (struct spu *spu);
+	void (*resource_allocation_groupID_set) (struct spu *spu, u64 id);
+	u64 (*resource_allocation_groupID_get) (struct spu *spu);
+	void (*resource_allocation_enable_set) (struct spu *spu, u64 enable);
+	u64 (*resource_allocation_enable_get) (struct spu *spu);
+};
+
+extern const struct spu_priv1_ops* spu_priv1_ops;
+
+static inline void
+spu_int_mask_and (struct spu *spu, int class, u64 mask)
+{
+	spu_priv1_ops->int_mask_and(spu, class, mask);
+}
+
+static inline void
+spu_int_mask_or (struct spu *spu, int class, u64 mask)
+{
+	spu_priv1_ops->int_mask_or(spu, class, mask);
+}
+
+static inline void
+spu_int_mask_set (struct spu *spu, int class, u64 mask)
+{
+	spu_priv1_ops->int_mask_set(spu, class, mask);
+}
+
+static inline u64
+spu_int_mask_get (struct spu *spu, int class)
+{
+	return spu_priv1_ops->int_mask_get(spu, class);
+}
+
+static inline void
+spu_int_stat_clear (struct spu *spu, int class, u64 stat)
+{
+	spu_priv1_ops->int_stat_clear(spu, class, stat);
+}
+
+static inline u64
+spu_int_stat_get (struct spu *spu, int class)
+{
+	return spu_priv1_ops->int_stat_get (spu, class);
+}
+
+static inline void
+spu_int_route_set (struct spu *spu, u64 route)
+{
+	spu_priv1_ops->int_stat_get(spu, route);
+}
+
+static inline u64
+spu_mfc_dar_get (struct spu *spu)
+{
+	return spu_priv1_ops->mfc_dar_get(spu);
+}
+
+static inline u64
+spu_mfc_dsisr_get (struct spu *spu)
+{
+	return spu_priv1_ops->mfc_dsisr_get(spu);
+}
+
+static inline void
+spu_mfc_dsisr_set (struct spu *spu, u64 dsisr)
+{
+	spu_priv1_ops->mfc_dsisr_set(spu, dsisr);
+}
+
+static inline void
+spu_mfc_sdr_set (struct spu *spu, u64 sdr)
+{
+	spu_priv1_ops->mfc_sdr_set(spu, sdr);
+}
+
+static inline void
+spu_mfc_sr1_set (struct spu *spu, u64 sr1)
+{
+	spu_priv1_ops->mfc_sr1_set(spu, sr1);
+}
+
+static inline u64
+spu_mfc_sr1_get (struct spu *spu)
+{
+	return spu_priv1_ops->mfc_sr1_get(spu);
+}
+
+static inline void
+spu_mfc_tclass_id_set (struct spu *spu, u64 tclass_id)
+{
+	spu_priv1_ops->mfc_tclass_id_set(spu, tclass_id);
+}
+
+static inline u64
+spu_mfc_tclass_id_get (struct spu *spu)
+{
+	return spu_priv1_ops->mfc_tclass_id_get(spu);
+}
+
+static inline void
+spu_smm_pgsz_set (struct spu *spu, u64 pgsz)
+{
+	spu_priv1_ops->smm_pgsz_set(spu, pgsz);
+}
+
+static inline void
+spu_tlb_invalidate (struct spu *spu)
+{
+	spu_priv1_ops->tlb_invalidate(spu);
+}
+
+static inline void
+spu_resource_allocation_groupID_set (struct spu *spu, u64 id)
+{
+	spu_priv1_ops->resource_allocation_groupID_set(spu, id);
+}
+
+static inline u64
+spu_resource_allocation_groupID_get (struct spu *spu)
+{
+	return spu_priv1_ops->resource_allocation_groupID_get(spu);
+}
+
+static inline void
+spu_resource_allocation_enable_set (struct spu *spu, u64 enable)
+{
+	spu_priv1_ops->resource_allocation_enable_set(spu, enable);
+}
+
+static inline u64
+spu_resource_allocation_enable_get (struct spu *spu)
+{
+	return spu_priv1_ops->resource_allocation_enable_get(spu);
+}
+
+/* The declarations folowing are put here for convenience
+ * and only intended to be used by the platform setup code
+ * for initializing spu_priv1_ops.
+ */
+
+extern const struct spu_priv1_ops spu_priv1_mmio_ops;
+
+#endif /* __KERNEL__ */
+#endif

--

^ permalink raw reply

* [PATCH 11/13] cell: split out board specific files
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

 From: Geoff Levand <geoffrey.levand@am.sony.com>

Split the Cell BE support into generic and platform
dependant parts.

Creates a new config variable CONFIG_PPC_IBM_CELL_BLADE.
The existing CONFIG_PPC_CELL is now used to denote the
generic Cell processor support.  Also renames spu_priv1.c
to spu_priv1_mmio.c.

Signed-off-by: Geoff Levand <geoffrey.levand@am.sony.com>
Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/Kconfig
===================================================================
--- linus-2.6.orig/arch/powerpc/Kconfig	2006-04-29 22:53:50.000000000 +0200
+++ linus-2.6/arch/powerpc/Kconfig	2006-04-29 22:54:42.000000000 +0200
@@ -391,11 +391,17 @@
 	  For more informations, refer to <http://www.970eval.com>
 
 config PPC_CELL
-	bool "  Cell Broadband Processor Architecture"
+	bool
+	default n
+
+config PPC_IBM_CELL_BLADE
+	bool "  IBM Cell Blade"
 	depends on PPC_MULTIPLATFORM && PPC64
+	select PPC_CELL
 	select PPC_RTAS
 	select MMIO_NVRAM
 	select PPC_UDBG_16550
+	select SPUFS_PRIV1_MMIO
 
 config XICS
 	depends on PPC_PSERIES
@@ -440,7 +446,7 @@
 	default y
 
 config CELL_IIC
-	depends on PPC_CELL
+	depends on PPC_IBM_CELL_BLADE
 	bool
 	default y
 
Index: linus-2.6/arch/powerpc/configs/cell_defconfig
===================================================================
--- linus-2.6.orig/arch/powerpc/configs/cell_defconfig	2006-04-29 22:53:50.000000000 +0200
+++ linus-2.6/arch/powerpc/configs/cell_defconfig	2006-04-29 22:54:42.000000000 +0200
@@ -116,6 +116,7 @@
 # CONFIG_PPC_PMAC is not set
 # CONFIG_PPC_MAPLE is not set
 CONFIG_PPC_CELL=y
+CONFIG_PPC_IBM_CELL_BLADE=y
 # CONFIG_U3_DART is not set
 CONFIG_PPC_RTAS=y
 # CONFIG_RTAS_ERROR_LOGGING is not set
@@ -132,6 +133,8 @@
 # Cell Broadband Engine options
 #
 CONFIG_SPU_FS=m
+CONFIG_SPU_BASE=y
+CONFIG_SPUFS_PRIV1_MMIO=y
 CONFIG_SPUFS_MMAP=y
 
 #
Index: linus-2.6/arch/powerpc/platforms/cell/Kconfig
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/Kconfig	2006-04-29 22:53:51.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/Kconfig	2006-04-29 22:54:42.000000000 +0200
@@ -5,11 +5,20 @@
 	tristate "SPU file system"
 	default m
 	depends on PPC_CELL
+	select SPU_BASE
 	help
 	  The SPU file system is used to access Synergistic Processing
 	  Units on machines implementing the Broadband Processor
 	  Architecture.
 
+config SPU_BASE
+	bool
+	default n
+
+config SPUFS_PRIV1_MMIO
+	bool
+	default n
+
 config SPUFS_MMAP
 	bool
 	depends on SPU_FS && SPARSEMEM && !PPC_64K_PAGES
Index: linus-2.6/arch/powerpc/platforms/cell/Makefile
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/Makefile	2006-04-29 22:54:25.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/Makefile	2006-04-29 22:54:42.000000000 +0200
@@ -1,14 +1,13 @@
-obj-y			+= interrupt.o iommu.o setup.o spider-pic.o
-obj-y			+= pervasive.o
-
-obj-$(CONFIG_SMP)	+= smp.o
+obj-$(CONFIG_PPC_IBM_CELL_BLADE)	+= interrupt.o iommu.o setup.o \
+					   spider-pic.o pervasive.o
+ifeq ($(CONFIG_SMP),y)
+obj-$(CONFIG_PPC_IBM_CELL_BLADE)	+= smp.o
+endif
 
 # needed only when building loadable spufs.ko
-spufs-modular-$(CONFIG_SPU_FS) += spu_syscalls.o
-obj-y			+= $(spufs-modular-m)
-
-# always needed in kernel
-spufs-builtin-$(CONFIG_SPU_FS) += spu_callbacks.o spu_base.o spu_priv1.o
-obj-y			+= $(spufs-builtin-y) $(spufs-builtin-m)
+spufs-modular-$(CONFIG_SPU_FS)		+= spu_syscalls.o
 
-obj-$(CONFIG_SPU_FS)	+= spufs/
+obj-$(CONFIG_SPU_BASE)			+= spu_callbacks.o spu_base.o \
+					   $(spufs-modular-m)
+obj-$(CONFIG_SPUFS_PRIV1_MMIO)		+= spu_priv1_mmio.o
+obj-$(CONFIG_SPU_FS)			+= spufs/
Index: linus-2.6/arch/powerpc/platforms/cell/spu_priv1.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spu_priv1.c	2006-04-29 22:53:50.000000000 +0200
+++ /dev/null	1970-01-01 00:00:00.000000000 +0000
@@ -1,133 +0,0 @@
-/*
- * access to SPU privileged registers
- */
-#include <linux/module.h>
-
-#include <asm/io.h>
-#include <asm/spu.h>
-
-void spu_int_mask_and(struct spu *spu, int class, u64 mask)
-{
-	u64 old_mask;
-
-	old_mask = in_be64(&spu->priv1->int_mask_RW[class]);
-	out_be64(&spu->priv1->int_mask_RW[class], old_mask & mask);
-}
-EXPORT_SYMBOL_GPL(spu_int_mask_and);
-
-void spu_int_mask_or(struct spu *spu, int class, u64 mask)
-{
-	u64 old_mask;
-
-	old_mask = in_be64(&spu->priv1->int_mask_RW[class]);
-	out_be64(&spu->priv1->int_mask_RW[class], old_mask | mask);
-}
-EXPORT_SYMBOL_GPL(spu_int_mask_or);
-
-void spu_int_mask_set(struct spu *spu, int class, u64 mask)
-{
-	out_be64(&spu->priv1->int_mask_RW[class], mask);
-}
-EXPORT_SYMBOL_GPL(spu_int_mask_set);
-
-u64 spu_int_mask_get(struct spu *spu, int class)
-{
-	return in_be64(&spu->priv1->int_mask_RW[class]);
-}
-EXPORT_SYMBOL_GPL(spu_int_mask_get);
-
-void spu_int_stat_clear(struct spu *spu, int class, u64 stat)
-{
-	out_be64(&spu->priv1->int_stat_RW[class], stat);
-}
-EXPORT_SYMBOL_GPL(spu_int_stat_clear);
-
-u64 spu_int_stat_get(struct spu *spu, int class)
-{
-	return in_be64(&spu->priv1->int_stat_RW[class]);
-}
-EXPORT_SYMBOL_GPL(spu_int_stat_get);
-
-void spu_int_route_set(struct spu *spu, u64 route)
-{
-	out_be64(&spu->priv1->int_route_RW, route);
-}
-EXPORT_SYMBOL_GPL(spu_int_route_set);
-
-u64 spu_mfc_dar_get(struct spu *spu)
-{
-	return in_be64(&spu->priv1->mfc_dar_RW);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_dar_get);
-
-u64 spu_mfc_dsisr_get(struct spu *spu)
-{
-	return in_be64(&spu->priv1->mfc_dsisr_RW);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_dsisr_get);
-
-void spu_mfc_dsisr_set(struct spu *spu, u64 dsisr)
-{
-	out_be64(&spu->priv1->mfc_dsisr_RW, dsisr);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_dsisr_set);
-
-void spu_mfc_sdr_set(struct spu *spu, u64 sdr)
-{
-	out_be64(&spu->priv1->mfc_sdr_RW, sdr);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_sdr_set);
-
-void spu_mfc_sr1_set(struct spu *spu, u64 sr1)
-{
-	out_be64(&spu->priv1->mfc_sr1_RW, sr1);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_sr1_set);
-
-u64 spu_mfc_sr1_get(struct spu *spu)
-{
-	return in_be64(&spu->priv1->mfc_sr1_RW);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_sr1_get);
-
-void spu_mfc_tclass_id_set(struct spu *spu, u64 tclass_id)
-{
-	out_be64(&spu->priv1->mfc_tclass_id_RW, tclass_id);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_tclass_id_set);
-
-u64 spu_mfc_tclass_id_get(struct spu *spu)
-{
-	return in_be64(&spu->priv1->mfc_tclass_id_RW);
-}
-EXPORT_SYMBOL_GPL(spu_mfc_tclass_id_get);
-
-void spu_tlb_invalidate(struct spu *spu)
-{
-	out_be64(&spu->priv1->tlb_invalidate_entry_W, 0ul);
-}
-EXPORT_SYMBOL_GPL(spu_tlb_invalidate);
-
-void spu_resource_allocation_groupID_set(struct spu *spu, u64 id)
-{
-	out_be64(&spu->priv1->resource_allocation_groupID_RW, id);
-}
-EXPORT_SYMBOL_GPL(spu_resource_allocation_groupID_set);
-
-u64 spu_resource_allocation_groupID_get(struct spu *spu)
-{
-	return in_be64(&spu->priv1->resource_allocation_groupID_RW);
-}
-EXPORT_SYMBOL_GPL(spu_resource_allocation_groupID_get);
-
-void spu_resource_allocation_enable_set(struct spu *spu, u64 enable)
-{
-	out_be64(&spu->priv1->resource_allocation_enable_RW, enable);
-}
-EXPORT_SYMBOL_GPL(spu_resource_allocation_enable_set);
-
-u64 spu_resource_allocation_enable_get(struct spu *spu)
-{
-	return in_be64(&spu->priv1->resource_allocation_enable_RW);
-}
-EXPORT_SYMBOL_GPL(spu_resource_allocation_enable_get);
Index: linus-2.6/arch/powerpc/platforms/cell/spu_priv1_mmio.c
===================================================================
--- /dev/null	1970-01-01 00:00:00.000000000 +0000
+++ linus-2.6/arch/powerpc/platforms/cell/spu_priv1_mmio.c	2006-04-29 22:54:42.000000000 +0200
@@ -0,0 +1,133 @@
+/*
+ * access to SPU privileged registers
+ */
+#include <linux/module.h>
+
+#include <asm/io.h>
+#include <asm/spu.h>
+
+void spu_int_mask_and(struct spu *spu, int class, u64 mask)
+{
+	u64 old_mask;
+
+	old_mask = in_be64(&spu->priv1->int_mask_RW[class]);
+	out_be64(&spu->priv1->int_mask_RW[class], old_mask & mask);
+}
+EXPORT_SYMBOL_GPL(spu_int_mask_and);
+
+void spu_int_mask_or(struct spu *spu, int class, u64 mask)
+{
+	u64 old_mask;
+
+	old_mask = in_be64(&spu->priv1->int_mask_RW[class]);
+	out_be64(&spu->priv1->int_mask_RW[class], old_mask | mask);
+}
+EXPORT_SYMBOL_GPL(spu_int_mask_or);
+
+void spu_int_mask_set(struct spu *spu, int class, u64 mask)
+{
+	out_be64(&spu->priv1->int_mask_RW[class], mask);
+}
+EXPORT_SYMBOL_GPL(spu_int_mask_set);
+
+u64 spu_int_mask_get(struct spu *spu, int class)
+{
+	return in_be64(&spu->priv1->int_mask_RW[class]);
+}
+EXPORT_SYMBOL_GPL(spu_int_mask_get);
+
+void spu_int_stat_clear(struct spu *spu, int class, u64 stat)
+{
+	out_be64(&spu->priv1->int_stat_RW[class], stat);
+}
+EXPORT_SYMBOL_GPL(spu_int_stat_clear);
+
+u64 spu_int_stat_get(struct spu *spu, int class)
+{
+	return in_be64(&spu->priv1->int_stat_RW[class]);
+}
+EXPORT_SYMBOL_GPL(spu_int_stat_get);
+
+void spu_int_route_set(struct spu *spu, u64 route)
+{
+	out_be64(&spu->priv1->int_route_RW, route);
+}
+EXPORT_SYMBOL_GPL(spu_int_route_set);
+
+u64 spu_mfc_dar_get(struct spu *spu)
+{
+	return in_be64(&spu->priv1->mfc_dar_RW);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_dar_get);
+
+u64 spu_mfc_dsisr_get(struct spu *spu)
+{
+	return in_be64(&spu->priv1->mfc_dsisr_RW);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_dsisr_get);
+
+void spu_mfc_dsisr_set(struct spu *spu, u64 dsisr)
+{
+	out_be64(&spu->priv1->mfc_dsisr_RW, dsisr);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_dsisr_set);
+
+void spu_mfc_sdr_set(struct spu *spu, u64 sdr)
+{
+	out_be64(&spu->priv1->mfc_sdr_RW, sdr);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_sdr_set);
+
+void spu_mfc_sr1_set(struct spu *spu, u64 sr1)
+{
+	out_be64(&spu->priv1->mfc_sr1_RW, sr1);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_sr1_set);
+
+u64 spu_mfc_sr1_get(struct spu *spu)
+{
+	return in_be64(&spu->priv1->mfc_sr1_RW);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_sr1_get);
+
+void spu_mfc_tclass_id_set(struct spu *spu, u64 tclass_id)
+{
+	out_be64(&spu->priv1->mfc_tclass_id_RW, tclass_id);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_tclass_id_set);
+
+u64 spu_mfc_tclass_id_get(struct spu *spu)
+{
+	return in_be64(&spu->priv1->mfc_tclass_id_RW);
+}
+EXPORT_SYMBOL_GPL(spu_mfc_tclass_id_get);
+
+void spu_tlb_invalidate(struct spu *spu)
+{
+	out_be64(&spu->priv1->tlb_invalidate_entry_W, 0ul);
+}
+EXPORT_SYMBOL_GPL(spu_tlb_invalidate);
+
+void spu_resource_allocation_groupID_set(struct spu *spu, u64 id)
+{
+	out_be64(&spu->priv1->resource_allocation_groupID_RW, id);
+}
+EXPORT_SYMBOL_GPL(spu_resource_allocation_groupID_set);
+
+u64 spu_resource_allocation_groupID_get(struct spu *spu)
+{
+	return in_be64(&spu->priv1->resource_allocation_groupID_RW);
+}
+EXPORT_SYMBOL_GPL(spu_resource_allocation_groupID_get);
+
+void spu_resource_allocation_enable_set(struct spu *spu, u64 enable)
+{
+	out_be64(&spu->priv1->resource_allocation_enable_RW, enable);
+}
+EXPORT_SYMBOL_GPL(spu_resource_allocation_enable_set);
+
+u64 spu_resource_allocation_enable_get(struct spu *spu)
+{
+	return in_be64(&spu->priv1->resource_allocation_enable_RW);
+}
+EXPORT_SYMBOL_GPL(spu_resource_allocation_enable_get);
Index: linus-2.6/drivers/net/Kconfig
===================================================================
--- linus-2.6.orig/drivers/net/Kconfig	2006-04-29 22:53:50.000000000 +0200
+++ linus-2.6/drivers/net/Kconfig	2006-04-29 22:54:42.000000000 +0200
@@ -2171,7 +2171,7 @@
 
 config SPIDER_NET
 	tristate "Spider Gigabit Ethernet driver"
-	depends on PCI && PPC_CELL
+	depends on PCI && PPC_IBM_CELL_BLADE
 	select FW_LOADER
 	help
 	  This driver supports the Gigabit Ethernet chips present on the

--

^ permalink raw reply

* [PATCH 09/13] spufs: add a phys-id attribute to each SPU context
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

For performance analysis, it is often interesting to know
which physical SPE a thread is currently running on, and,
more importantly, if it is running at all.

This patch adds a simple attribute to each SPU directory
with that information.
The attribute is read-only and called 'phys-id'. It contains
an ascii string with the number of the physical SPU (e.g.
"0x5"), or alternatively the string "0xffffffff" (32 bit -1)
when it is not running at all at the time that the file
is read.

Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/platforms/cell/spufs/file.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spufs/file.c	2006-04-29 22:53:41.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spufs/file.c	2006-04-29 22:53:44.000000000 +0200
@@ -1328,6 +1328,22 @@
 DEFINE_SIMPLE_ATTRIBUTE(spufs_srr0_ops, spufs_srr0_get, spufs_srr0_set,
 			"%llx\n")
 
+static u64 spufs_id_get(void *data)
+{
+	struct spu_context *ctx = data;
+	u64 num;
+
+	spu_acquire(ctx);
+	if (ctx->state == SPU_STATE_RUNNABLE)
+		num = ctx->spu->number;
+	else
+		num = (unsigned int)-1;
+	spu_release(ctx);
+
+	return num;
+}
+DEFINE_SIMPLE_ATTRIBUTE(spufs_id_ops, spufs_id_get, 0, "0x%llx\n")
+
 struct tree_descr spufs_dir_contents[] = {
 	{ "mem",  &spufs_mem_fops,  0666, },
 	{ "regs", &spufs_regs_fops,  0666, },
@@ -1351,5 +1367,6 @@
 	{ "spu_tag_mask", &spufs_spu_tag_mask_ops, 0666, },
 	{ "event_mask", &spufs_event_mask_ops, 0666, },
 	{ "srr0", &spufs_srr0_ops, 0666, },
+	{ "phys-id", &spufs_id_ops, 0666, },
 	{},
 };

--

^ permalink raw reply

* [PATCH 08/13] spufs: set up correct SLB entries for 64k pages
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

spufs currently knows only 4k pages and 16M hugetlb
pages. Make it use the regular methods for deciding on
the SLB bits.

Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/platforms/cell/spu_base.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spu_base.c	2006-04-29 22:53:40.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spu_base.c	2006-04-29 22:53:43.000000000 +0200
@@ -71,7 +71,7 @@
 {
 	struct spu_priv2 __iomem *priv2 = spu->priv2;
 	struct mm_struct *mm = spu->mm;
-	u64 esid, vsid;
+	u64 esid, vsid, llp;
 
 	pr_debug("%s\n", __FUNCTION__);
 
@@ -91,9 +91,14 @@
 	}
 
 	esid = (ea & ESID_MASK) | SLB_ESID_V;
-	vsid = (get_vsid(mm->context.id, ea) << SLB_VSID_SHIFT) | SLB_VSID_USER;
+#ifdef CONFIG_HUGETLB_PAGE
 	if (in_hugepage_area(mm->context, ea))
-		vsid |= SLB_VSID_L;
+		llp = mmu_psize_defs[mmu_huge_psize].sllp;
+	else
+#endif
+		llp = mmu_psize_defs[mmu_virtual_psize].sllp;
+	vsid = (get_vsid(mm->context.id, ea) << SLB_VSID_SHIFT) |
+			SLB_VSID_USER | llp;
 
 	out_be64(&priv2->slb_index_W, spu->slb_replace);
 	out_be64(&priv2->slb_vsid_RW, vsid);
Index: linus-2.6/arch/powerpc/platforms/cell/spufs/switch.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spufs/switch.c	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spufs/switch.c	2006-04-29 22:53:43.000000000 +0200
@@ -718,13 +718,15 @@
 
 static inline void get_kernel_slb(u64 ea, u64 slb[2])
 {
-	slb[0] = (get_kernel_vsid(ea) << SLB_VSID_SHIFT) | SLB_VSID_KERNEL;
-	slb[1] = (ea & ESID_MASK) | SLB_ESID_V;
+	u64 llp;
 
-	/* Large pages are used for kernel text/data, but not vmalloc.  */
-	if (cpu_has_feature(CPU_FTR_16M_PAGE)
-	    && REGION_ID(ea) == KERNEL_REGION_ID)
-		slb[0] |= SLB_VSID_L;
+	if (REGION_ID(ea) == KERNEL_REGION_ID)
+		llp = mmu_psize_defs[mmu_linear_psize].sllp;
+	else
+		llp = mmu_psize_defs[mmu_virtual_psize].sllp;
+	slb[0] = (get_kernel_vsid(ea) << SLB_VSID_SHIFT) |
+		SLB_VSID_KERNEL | llp;
+	slb[1] = (ea & ESID_MASK) | SLB_ESID_V;
 }
 
 static inline void load_mfc_slb(struct spu *spu, u64 slb[2], int slbe)

--

^ permalink raw reply

* [PATCH 07/13] powerpc: export symbols for page size selection
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

We need access to some symbols in powerpc memory management
from spufs in order to create proper SLB entries.

Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/mm/hash_utils_64.c
===================================================================
--- linus-2.6.orig/arch/powerpc/mm/hash_utils_64.c	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/arch/powerpc/mm/hash_utils_64.c	2006-04-29 22:53:43.000000000 +0200
@@ -85,16 +85,26 @@
 #endif /* CONFIG_U3_DART */
 
 static unsigned long _SDR1;
-struct mmu_psize_def mmu_psize_defs[MMU_PAGE_COUNT];
 
 hpte_t *htab_address;
 unsigned long htab_size_bytes;
 unsigned long htab_hash_mask;
+
+struct mmu_psize_def mmu_psize_defs[MMU_PAGE_COUNT];
+EXPORT_SYMBOL_GPL(mmu_psize_defs);
+
 int mmu_linear_psize = MMU_PAGE_4K;
+EXPORT_SYMBOL_GPL(mmu_linear_psize);
+
 int mmu_virtual_psize = MMU_PAGE_4K;
+EXPORT_SYMBOL_GPL(mmu_virtual_psize);
+
 #ifdef CONFIG_HUGETLB_PAGE
 int mmu_huge_psize = MMU_PAGE_16M;
+EXPORT_SYMBOL_GPL(mmu_huge_psize);
+
 unsigned int HPAGE_SHIFT;
+EXPORT_SYMBOL_GPL(HPAGE_SHIFT);
 #endif
 
 /* There are definitions of page sizes arrays to be used when none

--

^ permalink raw reply

* [PATCH 06/13] powerpc: fix 64k pages on non-hypervisor
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

 From: Benjamin Herrenschmidt <benh@kernel.crashing.org>

The page size encoding passed to tlbie is incorrect for
new-style large pages. This fixes it.

Signed-off-by: Benjamin Herrenschmidt <benh@kernel.crashing.org>
Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/mm/hash_native_64.c
===================================================================
--- linus-2.6.orig/arch/powerpc/mm/hash_native_64.c	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/arch/powerpc/mm/hash_native_64.c	2006-04-29 22:53:42.000000000 +0200
@@ -52,7 +52,7 @@
 	default:
 		penc = mmu_psize_defs[psize].penc;
 		va &= ~((1ul << mmu_psize_defs[psize].shift) - 1);
-		va |= (0x7f >> (8 - penc)) << 12;
+		va |= penc << 12;
 		asm volatile("tlbie %0,1" : : "r" (va) : "memory");
 		break;
 	}
@@ -74,7 +74,7 @@
 	default:
 		penc = mmu_psize_defs[psize].penc;
 		va &= ~((1ul << mmu_psize_defs[psize].shift) - 1);
-		va |= (0x7f >> (8 - penc)) << 12;
+		va |= penc << 12;
 		asm volatile(".long 0x7c000224 | (%0 << 11) | (1 << 21)"
 			     : : "r"(va) : "memory");
 		break;

--

^ permalink raw reply

* [PATCH 05/13] cell: enable CPU_FTR_CI_LARGE_PAGE
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

Reflect the fact that the Cell Broadband Engine supports 64k
pages by adding the bit to the CPU features.

Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/include/asm-powerpc/cputable.h
===================================================================
--- linus-2.6.orig/include/asm-powerpc/cputable.h	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/include/asm-powerpc/cputable.h	2006-04-29 22:53:42.000000000 +0200
@@ -329,7 +329,7 @@
 #define CPU_FTRS_CELL	(CPU_FTR_SPLIT_ID_CACHE | CPU_FTR_USE_TB | \
 	    CPU_FTR_HPTE_TABLE | CPU_FTR_PPCAS_ARCH_V2 | \
 	    CPU_FTR_ALTIVEC_COMP | CPU_FTR_MMCRA | CPU_FTR_SMT | \
-	    CPU_FTR_CTRL | CPU_FTR_PAUSE_ZERO)
+	    CPU_FTR_CTRL | CPU_FTR_PAUSE_ZERO | CPU_FTR_CI_LARGE_PAGE)
 #define CPU_FTRS_COMPATIBLE	(CPU_FTR_SPLIT_ID_CACHE | CPU_FTR_USE_TB | \
 	    CPU_FTR_HPTE_TABLE | CPU_FTR_PPCAS_ARCH_V2)
 #endif

--

^ permalink raw reply

* [PATCH 04/13] cell: remove broken __setup_cpu_be function
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

 From: Geoff Levand <geoffrey.levand@am.sony.com>

This patch removes the incorrect Cell processor setup routine
__setup_cpu_be.  This routine improperly accesses the hypervisor
page size configuration at SPR HID6.  The correct behavior is for
firmware, or if needed, platform setup code, to set the correct
page size.

Signed-off-by: Geoff Levand <geoffrey.levand@am.sony.com>
Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---
Index: linus-2.6/arch/powerpc/kernel/cpu_setup_power4.S
===================================================================
--- linus-2.6.orig/arch/powerpc/kernel/cpu_setup_power4.S	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/arch/powerpc/kernel/cpu_setup_power4.S	2006-04-29 22:53:42.000000000 +0200
@@ -76,20 +76,6 @@
 _GLOBAL(__setup_cpu_power4)
 	blr
 
-_GLOBAL(__setup_cpu_be)
-        /* Set large page sizes LP=0: 16MB, LP=1: 64KB */
-        addi    r3, 0,  0
-        ori     r3, r3, HID6_LB
-        sldi    r3, r3, 32
-        nor     r3, r3, r3
-        mfspr   r4, SPRN_HID6
-        and     r4, r4, r3
-        addi    r3, 0, 0x02000
-        sldi    r3, r3, 32
-        or      r4, r4, r3
-        mtspr   SPRN_HID6, r4
-	blr
-
 _GLOBAL(__setup_cpu_ppc970)
 	mfspr	r0,SPRN_HID0
 	li	r11,5			/* clear DOZE and SLEEP */
Index: linus-2.6/arch/powerpc/kernel/cputable.c
===================================================================
--- linus-2.6.orig/arch/powerpc/kernel/cputable.c	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/arch/powerpc/kernel/cputable.c	2006-04-29 22:53:42.000000000 +0200
@@ -33,7 +33,6 @@
 #ifdef CONFIG_PPC64
 extern void __setup_cpu_power3(unsigned long offset, struct cpu_spec* spec);
 extern void __setup_cpu_power4(unsigned long offset, struct cpu_spec* spec);
-extern void __setup_cpu_be(unsigned long offset, struct cpu_spec* spec);
 #else
 extern void __setup_cpu_603(unsigned long offset, struct cpu_spec* spec);
 extern void __setup_cpu_604(unsigned long offset, struct cpu_spec* spec);
@@ -289,7 +288,7 @@
 			PPC_FEATURE_SMT,
 		.icache_bsize		= 128,
 		.dcache_bsize		= 128,
-		.cpu_setup		= __setup_cpu_be,
+		.cpu_setup		= __setup_cpu_power4,
 		.platform		= "ppc-cell-be",
 	},
 	{	/* default match */

--

^ permalink raw reply

* [PATCH 03/13] cell: fix interrupt priority handling
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

Checking the priority field to test for irq validity is
completely bogus and breaks with future external interrupt
controllers.

Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---

Index: linus-2.6/arch/powerpc/platforms/cell/interrupt.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/interrupt.c	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/interrupt.c	2006-04-29 22:53:41.000000000 +0200
@@ -136,8 +136,7 @@
 		 * One of these units can be connected
 		 * to an external interrupt controller.
 		 */
-		if (pending.prio > 0x3f ||
-		    pending.class != 2)
+		if (pending.class != 2)
 			break;
 		irq = IIC_EXT_OFFSET
 			+ spider_get_irq(node)

--

^ permalink raw reply

* [PATCH 02/13] spufs: restore mapping of mssync register
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

A recent change to the way that the mfc file gets mapped made it
impossible to map the SPE Multi-Source Synchronization register
into user space, but that may be needed by some applications.

This restores the missing functionality.

Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>

Index: linus-2.6/arch/powerpc/platforms/cell/spufs/file.c
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/spufs/file.c	2006-04-29 22:47:55.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/spufs/file.c	2006-04-29 22:53:41.000000000 +0200
@@ -825,6 +825,55 @@
 					spufs_signal2_type_set, "%llu");
 
 #ifdef CONFIG_SPUFS_MMAP
+static struct page *spufs_mss_mmap_nopage(struct vm_area_struct *vma,
+					   unsigned long address, int *type)
+{
+	return spufs_ps_nopage(vma, address, type, 0x0000);
+}
+
+static struct vm_operations_struct spufs_mss_mmap_vmops = {
+	.nopage = spufs_mss_mmap_nopage,
+};
+
+/*
+ * mmap support for problem state MFC DMA area [0x0000 - 0x0fff].
+ * Mapping this area requires that the application have CAP_SYS_RAWIO,
+ * as these registers require special care when read/writing.
+ */
+static int spufs_mss_mmap(struct file *file, struct vm_area_struct *vma)
+{
+	if (!(vma->vm_flags & VM_SHARED))
+		return -EINVAL;
+
+	if (!capable(CAP_SYS_RAWIO))
+		return -EPERM;
+
+	vma->vm_flags |= VM_RESERVED;
+	vma->vm_page_prot = __pgprot(pgprot_val(vma->vm_page_prot)
+				     | _PAGE_NO_CACHE);
+
+	vma->vm_ops = &spufs_mss_mmap_vmops;
+	return 0;
+}
+#endif
+
+static int spufs_mss_open(struct inode *inode, struct file *file)
+{
+	struct spufs_inode_info *i = SPUFS_I(inode);
+
+	file->private_data = i->i_ctx;
+	return nonseekable_open(inode, file);
+}
+
+static struct file_operations spufs_mss_fops = {
+	.open	 = spufs_mss_open,
+#ifdef CONFIG_SPUFS_MMAP
+	.mmap	 = spufs_mss_mmap,
+#endif
+};
+
+
+#ifdef CONFIG_SPUFS_MMAP
 static struct page *spufs_mfc_mmap_nopage(struct vm_area_struct *vma,
 					   unsigned long address, int *type)
 {
@@ -1292,6 +1341,7 @@
 	{ "signal2", &spufs_signal2_fops, 0666, },
 	{ "signal1_type", &spufs_signal1_type, 0666, },
 	{ "signal2_type", &spufs_signal2_type, 0666, },
+	{ "mss", &spufs_mss_fops, 0666, },
 	{ "mfc", &spufs_mfc_fops, 0666, },
 	{ "cntl", &spufs_cntl_fops,  0666, },
 	{ "npc", &spufs_npc_ops, 0666, },

--

^ permalink raw reply

* [PATCH 01/13] cell: always build spu base into the kernel
From: Arnd Bergmann @ 2006-04-29 23:28 UTC (permalink / raw)
  To: paulus; +Cc: Arnd Bergmann, linuxppc-dev, cbe-oss-dev, linux-kernel
In-Reply-To: <20060429232812.825714000@localhost.localdomain>

The spu_base module is rather deeply intermixed with the
core kernel, so it makes sense to have that built-in.
This will let us extend the base in the future without
having to export more core symbols just for it.

Signed-off-by: Arnd Bergmann <arnd.bergmann@de.ibm.com>
---

Index: linus-2.6/arch/powerpc/platforms/cell/Makefile
===================================================================
--- linus-2.6.orig/arch/powerpc/platforms/cell/Makefile	2006-04-29 22:47:56.000000000 +0200
+++ linus-2.6/arch/powerpc/platforms/cell/Makefile	2006-04-29 22:53:41.000000000 +0200
@@ -2,15 +2,13 @@
 obj-y			+= pervasive.o
 
 obj-$(CONFIG_SMP)	+= smp.o
-obj-$(CONFIG_SPU_FS)	+= spu-base.o spufs/
-
-spu-base-y		+= spu_base.o spu_priv1.o
 
 # needed only when building loadable spufs.ko
 spufs-modular-$(CONFIG_SPU_FS) += spu_syscalls.o
 obj-y			+= $(spufs-modular-m)
 
 # always needed in kernel
-spufs-builtin-$(CONFIG_SPU_FS) += spu_callbacks.o
+spufs-builtin-$(CONFIG_SPU_FS) += spu_callbacks.o spu_base.o spu_priv1.o
 obj-y			+= $(spufs-builtin-y) $(spufs-builtin-m)
 
+obj-$(CONFIG_SPU_FS)	+= spufs/

--

^ permalink raw reply


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