* [PATCH 1/6] powerpc/spufs: fix spu_context leak in coredump
2026-08-02 15:51 [PATCH 0/6] powerpc/spufs: assorted fixes Junrui Luo via B4 Relay
@ 2026-08-02 15:51 ` Junrui Luo via B4 Relay
2026-08-03 9:05 ` Arnd Bergmann
2026-08-02 15:51 ` [PATCH 2/6] powerpc/spufs: don't leak kernel stack via spu_run Junrui Luo via B4 Relay
` (5 subsequent siblings)
6 siblings, 1 reply; 16+ messages in thread
From: Junrui Luo via B4 Relay @ 2026-08-02 15:51 UTC (permalink / raw)
To: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy (CS GROUP), Paul Mackerras, Arnd Bergmann,
Al Viro
Cc: linuxppc-dev, linux-kernel, Junrui Luo, Yuhao Jiang, stable
From: Junrui Luo <moonafterrain@outlook.com>
coredump_next_context() returns a spu_context with a reference taken by
get_spu_context(), which the caller must drop.
spufs_coredump_extra_notes_size() does so on all of its exits, but
spufs_coredump_extra_notes_write() never calls put_spu_context(), so
every context dumped through elf_coredump_extra_notes_write() leaks a
reference, including on the success path.
Fix by dropping the reference on each of the three exits of the loop,
mirroring ..._size().
Fixes: 38b407be172d ("powerpc/spufs: Rework fcheck() usage")
Reported-by: Yuhao Jiang <danisjiang@gmail.com>
Cc: stable@vger.kernel.org
Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
---
arch/powerpc/platforms/cell/spufs/coredump.c | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/arch/powerpc/platforms/cell/spufs/coredump.c b/arch/powerpc/platforms/cell/spufs/coredump.c
index 301ee7d8b7df..f5964c9ebb3e 100644
--- a/arch/powerpc/platforms/cell/spufs/coredump.c
+++ b/arch/powerpc/platforms/cell/spufs/coredump.c
@@ -162,13 +162,16 @@ int spufs_coredump_extra_notes_write(struct coredump_params *cprm)
fd = 0;
while ((ctx = coredump_next_context(&fd)) != NULL) {
rc = spu_acquire_saved(ctx);
- if (rc)
+ if (rc) {
+ put_spu_context(ctx);
return rc;
+ }
for (j = 0; spufs_coredump_read[j].name != NULL; j++) {
rc = spufs_arch_write_note(ctx, j, cprm, fd);
if (rc) {
spu_release_saved(ctx);
+ put_spu_context(ctx);
return rc;
}
}
@@ -177,6 +180,7 @@ int spufs_coredump_extra_notes_write(struct coredump_params *cprm)
/* start searching the next fd next time */
fd++;
+ put_spu_context(ctx);
}
return 0;
--
2.51.2
^ permalink raw reply related [flat|nested] 16+ messages in thread* Re: [PATCH 1/6] powerpc/spufs: fix spu_context leak in coredump
2026-08-02 15:51 ` [PATCH 1/6] powerpc/spufs: fix spu_context leak in coredump Junrui Luo via B4 Relay
@ 2026-08-03 9:05 ` Arnd Bergmann
0 siblings, 0 replies; 16+ messages in thread
From: Arnd Bergmann @ 2026-08-03 9:05 UTC (permalink / raw)
To: moonafterrain, Madhavan Srinivasan, Michael Ellerman,
Nicholas Piggin, Christophe Leroy, Paul Mackerras, Alexander Viro
Cc: linuxppc-dev, linux-kernel, Yuhao Jiang, stable
On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
> From: Junrui Luo <moonafterrain@outlook.com>
>
> coredump_next_context() returns a spu_context with a reference taken by
> get_spu_context(), which the caller must drop.
> spufs_coredump_extra_notes_size() does so on all of its exits, but
> spufs_coredump_extra_notes_write() never calls put_spu_context(), so
> every context dumped through elf_coredump_extra_notes_write() leaks a
> reference, including on the success path.
>
> Fix by dropping the reference on each of the three exits of the loop,
> mirroring ..._size().
>
> Fixes: 38b407be172d ("powerpc/spufs: Rework fcheck() usage")
> Reported-by: Yuhao Jiang <danisjiang@gmail.com>
> Cc: stable@vger.kernel.org
> Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
Reviewed-by: Arnd Bergmann <arnd@arndb.de>
^ permalink raw reply [flat|nested] 16+ messages in thread
* [PATCH 2/6] powerpc/spufs: don't leak kernel stack via spu_run
2026-08-02 15:51 [PATCH 0/6] powerpc/spufs: assorted fixes Junrui Luo via B4 Relay
2026-08-02 15:51 ` [PATCH 1/6] powerpc/spufs: fix spu_context leak in coredump Junrui Luo via B4 Relay
@ 2026-08-02 15:51 ` Junrui Luo via B4 Relay
2026-08-03 9:09 ` Arnd Bergmann
2026-08-02 15:51 ` [PATCH 3/6] powerpc/spufs: bound NPC against local store size Junrui Luo via B4 Relay
` (4 subsequent siblings)
6 siblings, 1 reply; 16+ messages in thread
From: Junrui Luo via B4 Relay @ 2026-08-02 15:51 UTC (permalink / raw)
To: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy (CS GROUP), Paul Mackerras, Arnd Bergmann,
Al Viro
Cc: linuxppc-dev, linux-kernel, Junrui Luo, Yuhao Jiang, stable
From: Junrui Luo <moonafterrain@outlook.com>
do_spu_run() hands the address of an uninitialized local to
spufs_run_spu() and then copies it out unconditionally:
u32 npc, status;
...
ret = spufs_run_spu(i->i_ctx, &npc, &status);
...
if (ustatus && put_user(status, ustatus))
ret = -EFAULT;
spufs_run_spu() writes through that pointer at exactly one place, the
"out:" label, and two of its exits never reach it: the interruptible
acquisition of ctx->run_mutex returns -ERESTARTSYS directly, and a
failed spu_acquire() jumps to "out_unlock", which sits just after the
assignment.
Initialize status to 0, which is what userspace would have observed had
the assignment been reached anyway: spufs_run_spu() resets
ctx->event_return to 0 on entry, and 0 is the "no events pending" value
for this word.
Fixes: 67207b9664a8 ("[PATCH] spufs: The SPU file system, base")
Reported-by: Yuhao Jiang <danisjiang@gmail.com>
Cc: stable@vger.kernel.org
Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
---
arch/powerpc/platforms/cell/spufs/syscalls.c | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/arch/powerpc/platforms/cell/spufs/syscalls.c b/arch/powerpc/platforms/cell/spufs/syscalls.c
index ea4ba1b6ce6a..549fcfbbc140 100644
--- a/arch/powerpc/platforms/cell/spufs/syscalls.c
+++ b/arch/powerpc/platforms/cell/spufs/syscalls.c
@@ -37,7 +37,7 @@ static long do_spu_run(struct file *filp,
{
long ret;
struct spufs_inode_info *i;
- u32 npc, status;
+ u32 npc, status = 0;
ret = -EFAULT;
if (get_user(npc, unpc))
--
2.51.2
^ permalink raw reply related [flat|nested] 16+ messages in thread* Re: [PATCH 2/6] powerpc/spufs: don't leak kernel stack via spu_run
2026-08-02 15:51 ` [PATCH 2/6] powerpc/spufs: don't leak kernel stack via spu_run Junrui Luo via B4 Relay
@ 2026-08-03 9:09 ` Arnd Bergmann
0 siblings, 0 replies; 16+ messages in thread
From: Arnd Bergmann @ 2026-08-03 9:09 UTC (permalink / raw)
To: moonafterrain, Madhavan Srinivasan, Michael Ellerman,
Nicholas Piggin, Christophe Leroy, Paul Mackerras, Alexander Viro
Cc: linuxppc-dev, linux-kernel, Yuhao Jiang, stable
On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
>
> Initialize status to 0, which is what userspace would have observed had
> the assignment been reached anyway: spufs_run_spu() resets
> ctx->event_return to 0 on entry, and 0 is the "no events pending" value
> for this word.
>
> Fixes: 67207b9664a8 ("[PATCH] spufs: The SPU file system, base")
> Reported-by: Yuhao Jiang <danisjiang@gmail.com>
> Cc: stable@vger.kernel.org
> Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
Reviewed-by: Arnd Bergmann <arnd@arndb.de>
> @@ -37,7 +37,7 @@ static long do_spu_run(struct file *filp,
> {
> long ret;
> struct spufs_inode_info *i;
> - u32 npc, status;
> + u32 npc, status = 0;
>
> ret = -EFAULT;
> if (get_user(npc, unpc))
I think I would prefer skipping the broken put_user() in case
of an error, but your version also works.
Arnd
^ permalink raw reply [flat|nested] 16+ messages in thread
* [PATCH 3/6] powerpc/spufs: bound NPC against local store size
2026-08-02 15:51 [PATCH 0/6] powerpc/spufs: assorted fixes Junrui Luo via B4 Relay
2026-08-02 15:51 ` [PATCH 1/6] powerpc/spufs: fix spu_context leak in coredump Junrui Luo via B4 Relay
2026-08-02 15:51 ` [PATCH 2/6] powerpc/spufs: don't leak kernel stack via spu_run Junrui Luo via B4 Relay
@ 2026-08-02 15:51 ` Junrui Luo via B4 Relay
2026-08-03 9:14 ` Arnd Bergmann
2026-08-02 15:51 ` [PATCH 4/6] powerpc/spufs: check permissions in spufs_setattr() Junrui Luo via B4 Relay
` (3 subsequent siblings)
6 siblings, 1 reply; 16+ messages in thread
From: Junrui Luo via B4 Relay @ 2026-08-02 15:51 UTC (permalink / raw)
To: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy (CS GROUP), Paul Mackerras, Arnd Bergmann,
Al Viro
Cc: linuxppc-dev, linux-kernel, Junrui Luo, Yuhao Jiang, stable
From: Junrui Luo <moonafterrain@outlook.com>
spu_process_callback() masks the low bits of the NPC register and uses
the result as an offset into the SPU local store: `ls_pointer = in_be32(ls
+ npc)`. The following guard validates ls_pointer against LS_SIZE, but npc
itself is never bounds-checked.
Fix by rejecting npc greater than LS_SIZE - sizeof(ls_pointer) before the
read, mirroring the adjacent ls_pointer guard and returning the same
-EFAULT.
Fixes: 2dd14934c913 ("[PATCH] spufs: allow SPU code to do syscalls")
Reported-by: Yuhao Jiang <danisjiang@gmail.com>
Cc: stable@vger.kernel.org
Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
---
arch/powerpc/platforms/cell/spufs/run.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/arch/powerpc/platforms/cell/spufs/run.c b/arch/powerpc/platforms/cell/spufs/run.c
index ce52b87496d2..87497316d128 100644
--- a/arch/powerpc/platforms/cell/spufs/run.c
+++ b/arch/powerpc/platforms/cell/spufs/run.c
@@ -317,6 +317,8 @@ static int spu_process_callback(struct spu_context *ctx)
/* get syscall block from local store */
npc = ctx->ops->npc_read(ctx) & ~3;
ls = (void __iomem *)ctx->ops->get_ls(ctx);
+ if (npc > (LS_SIZE - sizeof(ls_pointer)))
+ return -EFAULT;
ls_pointer = in_be32(ls + npc);
if (ls_pointer > (LS_SIZE - sizeof(s)))
return -EFAULT;
--
2.51.2
^ permalink raw reply related [flat|nested] 16+ messages in thread* Re: [PATCH 3/6] powerpc/spufs: bound NPC against local store size
2026-08-02 15:51 ` [PATCH 3/6] powerpc/spufs: bound NPC against local store size Junrui Luo via B4 Relay
@ 2026-08-03 9:14 ` Arnd Bergmann
2026-08-04 6:30 ` Junrui Luo
0 siblings, 1 reply; 16+ messages in thread
From: Arnd Bergmann @ 2026-08-03 9:14 UTC (permalink / raw)
To: moonafterrain, Madhavan Srinivasan, Michael Ellerman,
Nicholas Piggin, Christophe Leroy, Paul Mackerras, Alexander Viro
Cc: linuxppc-dev, linux-kernel, Yuhao Jiang, stable
On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
> From: Junrui Luo <moonafterrain@outlook.com>
>
> spu_process_callback() masks the low bits of the NPC register and uses
> the result as an offset into the SPU local store: `ls_pointer = in_be32(ls
> + npc)`. The following guard validates ls_pointer against LS_SIZE, but npc
> itself is never bounds-checked.
>
> Fix by rejecting npc greater than LS_SIZE - sizeof(ls_pointer) before the
> read, mirroring the adjacent ls_pointer guard and returning the same
> -EFAULT.
This one seems wrong: npc is a hardware register value that can't
go out of range, unlike the ls_pointer value. I don't think there
is any use for the check.
Arnd
^ permalink raw reply [flat|nested] 16+ messages in thread* Re: [PATCH 3/6] powerpc/spufs: bound NPC against local store size
2026-08-03 9:14 ` Arnd Bergmann
@ 2026-08-04 6:30 ` Junrui Luo
0 siblings, 0 replies; 16+ messages in thread
From: Junrui Luo @ 2026-08-04 6:30 UTC (permalink / raw)
To: Arnd Bergmann
Cc: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy, Paul Mackerras, Alexander Viro,
linuxppc-dev@lists.ozlabs.org, linux-kernel@vger.kernel.org,
Yuhao Jiang, stable@vger.kernel.org
On Mon, Aug 03, 2026 at 11:14:03AM +0200, Arnd Bergmann wrote:
> On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
> > From: Junrui Luo <moonafterrain@outlook.com>
> >
> > spu_process_callback() masks the low bits of the NPC register and uses
> > the result as an offset into the SPU local store: `ls_pointer = in_be32(ls
> > + npc)`. The following guard validates ls_pointer against LS_SIZE, but npc
> > itself is never bounds-checked.
> >
> > Fix by rejecting npc greater than LS_SIZE - sizeof(ls_pointer) before the
> > read, mirroring the adjacent ls_pointer guard and returning the same
> > -EFAULT.
>
> This one seems wrong: npc is a hardware register value that can't
> go out of range, unlike the ls_pointer value. I don't think there
> is any use for the check.
>
> Arnd
Thanks for the review. I didn't establish that it can actually go
out of range. Please drop this one.
Thanks,
Junrui Luo
^ permalink raw reply [flat|nested] 16+ messages in thread
* [PATCH 4/6] powerpc/spufs: check permissions in spufs_setattr()
2026-08-02 15:51 [PATCH 0/6] powerpc/spufs: assorted fixes Junrui Luo via B4 Relay
` (2 preceding siblings ...)
2026-08-02 15:51 ` [PATCH 3/6] powerpc/spufs: bound NPC against local store size Junrui Luo via B4 Relay
@ 2026-08-02 15:51 ` Junrui Luo via B4 Relay
2026-08-03 9:16 ` Arnd Bergmann
2026-08-02 15:51 ` [PATCH 5/6] powerpc/spufs: fix deadlock on gang creation failure Junrui Luo via B4 Relay
` (2 subsequent siblings)
6 siblings, 1 reply; 16+ messages in thread
From: Junrui Luo via B4 Relay @ 2026-08-02 15:51 UTC (permalink / raw)
To: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy (CS GROUP), Paul Mackerras, Arnd Bergmann,
Al Viro
Cc: linuxppc-dev, linux-kernel, Junrui Luo, Yuhao Jiang, stable
From: Junrui Luo <moonafterrain@outlook.com>
spufs_setattr() applies the caller's attributes with setattr_copy() but
never calls setattr_prepare(). notify_change() leaves that to the
filesystem: it runs only may_setattr(), while inode_owner_or_capable()
and the CAP_CHOWN test live inside setattr_prepare(). setattr_copy()
performs no checking of its own.
The handler is installed for every regular spufs file, so mode and
ownership of another user's context files can be changed without the
usual authorization.
Call setattr_prepare() before setattr_copy(). The existing ATTR_SIZE
test stays ahead of it so that resizing a spufs file keeps returning
-EINVAL. &nop_mnt_idmap matches the adjacent setattr_copy() call.
Fixes: 67207b9664a8 ("[PATCH] spufs: The SPU file system, base")
Reported-by: Yuhao Jiang <danisjiang@gmail.com>
Cc: stable@vger.kernel.org
Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
---
arch/powerpc/platforms/cell/spufs/inode.c | 4 ++++
1 file changed, 4 insertions(+)
diff --git a/arch/powerpc/platforms/cell/spufs/inode.c b/arch/powerpc/platforms/cell/spufs/inode.c
index 2b54afb31529..c2b15c30f7c0 100644
--- a/arch/powerpc/platforms/cell/spufs/inode.c
+++ b/arch/powerpc/platforms/cell/spufs/inode.c
@@ -96,10 +96,14 @@ spufs_setattr(struct mnt_idmap *idmap, struct dentry *dentry,
struct iattr *attr)
{
struct inode *inode = d_inode(dentry);
+ int ret;
if ((attr->ia_valid & ATTR_SIZE) &&
(attr->ia_size != inode->i_size))
return -EINVAL;
+ ret = setattr_prepare(&nop_mnt_idmap, dentry, attr);
+ if (ret)
+ return ret;
setattr_copy(&nop_mnt_idmap, inode, attr);
mark_inode_dirty(inode);
return 0;
--
2.51.2
^ permalink raw reply related [flat|nested] 16+ messages in thread* Re: [PATCH 4/6] powerpc/spufs: check permissions in spufs_setattr()
2026-08-02 15:51 ` [PATCH 4/6] powerpc/spufs: check permissions in spufs_setattr() Junrui Luo via B4 Relay
@ 2026-08-03 9:16 ` Arnd Bergmann
0 siblings, 0 replies; 16+ messages in thread
From: Arnd Bergmann @ 2026-08-03 9:16 UTC (permalink / raw)
To: moonafterrain, Madhavan Srinivasan, Michael Ellerman,
Nicholas Piggin, Christophe Leroy, Paul Mackerras, Alexander Viro
Cc: linuxppc-dev, linux-kernel, Yuhao Jiang, stable
On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
> From: Junrui Luo <moonafterrain@outlook.com>
>
> spufs_setattr() applies the caller's attributes with setattr_copy() but
> never calls setattr_prepare(). notify_change() leaves that to the
> filesystem: it runs only may_setattr(), while inode_owner_or_capable()
> and the CAP_CHOWN test live inside setattr_prepare(). setattr_copy()
> performs no checking of its own.
>
> The handler is installed for every regular spufs file, so mode and
> ownership of another user's context files can be changed without the
> usual authorization.
>
> Call setattr_prepare() before setattr_copy(). The existing ATTR_SIZE
> test stays ahead of it so that resizing a spufs file keeps returning
> -EINVAL. &nop_mnt_idmap matches the adjacent setattr_copy() call.
>
> Fixes: 67207b9664a8 ("[PATCH] spufs: The SPU file system, base")
> Reported-by: Yuhao Jiang <danisjiang@gmail.com>
> Cc: stable@vger.kernel.org
> Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
Reviewed-by: Arnd Bergmann <arnd@arndb.de>
^ permalink raw reply [flat|nested] 16+ messages in thread
* [PATCH 5/6] powerpc/spufs: fix deadlock on gang creation failure
2026-08-02 15:51 [PATCH 0/6] powerpc/spufs: assorted fixes Junrui Luo via B4 Relay
` (3 preceding siblings ...)
2026-08-02 15:51 ` [PATCH 4/6] powerpc/spufs: check permissions in spufs_setattr() Junrui Luo via B4 Relay
@ 2026-08-02 15:51 ` Junrui Luo via B4 Relay
2026-08-02 15:51 ` [PATCH 6/6] powerpc/spufs: don't hold state_mutex during user access Junrui Luo via B4 Relay
2026-08-03 9:28 ` [PATCH 0/6] powerpc/spufs: assorted fixes Arnd Bergmann
6 siblings, 0 replies; 16+ messages in thread
From: Junrui Luo via B4 Relay @ 2026-08-02 15:51 UTC (permalink / raw)
To: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy (CS GROUP), Paul Mackerras, Arnd Bergmann,
Al Viro
Cc: linuxppc-dev, linux-kernel, Junrui Luo, Yuhao Jiang, stable
From: Junrui Luo <moonafterrain@outlook.com>
do_spu_create() enters spufs with the parent directory's i_rwsem held
for write, taken as I_MUTEX_PARENT by start_creating_user_path() and
dropped only by end_creating_path(). When spufs_gang_open() fails inside
that window, spufs_create_gang() cleans up by calling unuse_gang().
The gang was just created, so gang->alive drops to 0 and unuse_gang()
proceeds to simple_recursive_removal(), which takes the parent inode's
i_rwsem as I_MUTEX_CHILD. This leads to the task blocking on an rwsem it
already holds, leaving the spufs directory write-locked. The other two
callers of unuse_gang() do not hold the parent lock: spufs_gang_close()
runs from ->release, and spufs_dir_close() drops the parent lock first.
Tell unuse_gang() which context it is called from, and use
locked_recursive_removal() when the parent is already held. This matches
spufs_rmdir(), which spufs_create_context() already uses for the same
cleanup under the same lock.
Fixes: c134deabf478 ("spufs: fix gang directory lifetimes")
Reported-by: Yuhao Jiang <danisjiang@gmail.com>
Cc: stable@vger.kernel.org
Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
---
arch/powerpc/platforms/cell/spufs/inode.c | 17 +++++++++++------
1 file changed, 11 insertions(+), 6 deletions(-)
diff --git a/arch/powerpc/platforms/cell/spufs/inode.c b/arch/powerpc/platforms/cell/spufs/inode.c
index c2b15c30f7c0..998512409552 100644
--- a/arch/powerpc/platforms/cell/spufs/inode.c
+++ b/arch/powerpc/platforms/cell/spufs/inode.c
@@ -175,7 +175,8 @@ static int spufs_fill_dir(struct dentry *dir,
return 0;
}
-static void unuse_gang(struct dentry *dir)
+/* @parent_locked: caller holds dir->d_parent's i_rwsem as I_MUTEX_PARENT */
+static void unuse_gang(struct dentry *dir, bool parent_locked)
{
struct inode *inode = dir->d_inode;
struct spu_gang *gang = SPUFS_I(inode)->i_gang;
@@ -187,8 +188,12 @@ static void unuse_gang(struct dentry *dir)
dead = !--gang->alive;
inode_unlock(inode);
- if (dead)
- simple_recursive_removal(dir, NULL);
+ if (dead) {
+ if (parent_locked)
+ locked_recursive_removal(dir, NULL);
+ else
+ simple_recursive_removal(dir, NULL);
+ }
}
}
@@ -204,7 +209,7 @@ static int spufs_dir_close(struct inode *inode, struct file *file)
spufs_rmdir(parent, dir);
inode_unlock(parent);
- unuse_gang(dir->d_parent);
+ unuse_gang(dir->d_parent, false);
return dcache_dir_close(inode, file);
}
@@ -483,7 +488,7 @@ spufs_mkgang(struct inode *dir, struct dentry *dentry, umode_t mode)
static int spufs_gang_close(struct inode *inode, struct file *file)
{
- unuse_gang(file->f_path.dentry);
+ unuse_gang(file->f_path.dentry, false);
return dcache_dir_close(inode, file);
}
@@ -520,7 +525,7 @@ static int spufs_create_gang(struct inode *inode,
if (!ret) {
ret = spufs_gang_open(&path);
if (ret < 0)
- unuse_gang(dentry);
+ unuse_gang(dentry, true);
}
return ret;
}
--
2.51.2
^ permalink raw reply related [flat|nested] 16+ messages in thread* [PATCH 6/6] powerpc/spufs: don't hold state_mutex during user access
2026-08-02 15:51 [PATCH 0/6] powerpc/spufs: assorted fixes Junrui Luo via B4 Relay
` (4 preceding siblings ...)
2026-08-02 15:51 ` [PATCH 5/6] powerpc/spufs: fix deadlock on gang creation failure Junrui Luo via B4 Relay
@ 2026-08-02 15:51 ` Junrui Luo via B4 Relay
2026-08-03 9:26 ` Arnd Bergmann
2026-08-03 9:28 ` [PATCH 0/6] powerpc/spufs: assorted fixes Arnd Bergmann
6 siblings, 1 reply; 16+ messages in thread
From: Junrui Luo via B4 Relay @ 2026-08-02 15:51 UTC (permalink / raw)
To: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy (CS GROUP), Paul Mackerras, Arnd Bergmann,
Al Viro
Cc: linuxppc-dev, linux-kernel, Junrui Luo, Yuhao Jiang
From: Junrui Luo <moonafterrain@outlook.com>
spufs_mbox_read(), spufs_ibox_read() and spufs_wbox_write() take the
context state_mutex with spu_acquire() and only drop it once their
transfer loop has finished, so every put_user()/get_user() in those
loops runs with the mutex held. The faulting address comes from
userspace, so the fault can be made to take arbitrarily long via
userfaultfd region or a FUSE-backed mapping.
Drop the mutex around the user accesses: acquire it per mailbox element,
just long enough for the ctx->ops mailbox operation, and release it
before touching the user buffer.
spufs_switch_log_read() has the same problem but its loop needs the lock
for more than just the copy.
Fixes: cdcc89bb1c6e ("[POWERPC] spufs: make mailbox functions handle multiple elements")
Reported-by: Yuhao Jiang <danisjiang@gmail.com>
Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
---
arch/powerpc/platforms/cell/spufs/file.c | 52 ++++++++++++++++++--------------
1 file changed, 29 insertions(+), 23 deletions(-)
diff --git a/arch/powerpc/platforms/cell/spufs/file.c b/arch/powerpc/platforms/cell/spufs/file.c
index de7494748fec..c8c3b6e8affb 100644
--- a/arch/powerpc/platforms/cell/spufs/file.c
+++ b/arch/powerpc/platforms/cell/spufs/file.c
@@ -602,13 +602,17 @@ static ssize_t spufs_mbox_read(struct file *file, char __user *buf,
if (len < 4)
return -EINVAL;
- count = spu_acquire(ctx);
- if (count)
- return count;
-
for (count = 0; (count + 4) <= len; count += 4, udata++) {
int ret;
+
+ ret = spu_acquire(ctx);
+ if (ret) {
+ if (!count)
+ count = ret;
+ break;
+ }
ret = ctx->ops->mbox_read(ctx, &mbox_data);
+ spu_release(ctx);
if (ret == 0)
break;
@@ -624,7 +628,6 @@ static ssize_t spufs_mbox_read(struct file *file, char __user *buf,
break;
}
}
- spu_release(ctx);
if (!count)
count = -EAGAIN;
@@ -705,29 +708,34 @@ static ssize_t spufs_ibox_read(struct file *file, char __user *buf,
count = spu_acquire(ctx);
if (count)
- goto out;
+ return count;
/* wait only for the first element */
- count = 0;
if (file->f_flags & O_NONBLOCK) {
if (!spu_ibox_read(ctx, &ibox_data)) {
- count = -EAGAIN;
- goto out_unlock;
+ spu_release(ctx);
+ return -EAGAIN;
}
} else {
count = spufs_wait(ctx->ibox_wq, spu_ibox_read(ctx, &ibox_data));
if (count)
- goto out;
+ return count;
}
+ spu_release(ctx);
/* if we can't write at all, return -EFAULT */
count = put_user(ibox_data, udata);
if (count)
- goto out_unlock;
+ return count;
for (count = 4, udata++; (count + 4) <= len; count += 4, udata++) {
int ret;
+
+ ret = spu_acquire(ctx);
+ if (ret)
+ break;
ret = ctx->ops->ibox_read(ctx, &ibox_data);
+ spu_release(ctx);
if (ret == 0)
break;
/*
@@ -740,9 +748,6 @@ static ssize_t spufs_ibox_read(struct file *file, char __user *buf,
break;
}
-out_unlock:
- spu_release(ctx);
-out:
return count;
}
@@ -839,40 +844,41 @@ static ssize_t spufs_wbox_write(struct file *file, const char __user *buf,
count = spu_acquire(ctx);
if (count)
- goto out;
+ return count;
/*
* make sure we can at least write one element, by waiting
* in case of !O_NONBLOCK
*/
- count = 0;
if (file->f_flags & O_NONBLOCK) {
if (!spu_wbox_write(ctx, wbox_data)) {
- count = -EAGAIN;
- goto out_unlock;
+ spu_release(ctx);
+ return -EAGAIN;
}
} else {
count = spufs_wait(ctx->wbox_wq, spu_wbox_write(ctx, wbox_data));
if (count)
- goto out;
+ return count;
}
-
+ spu_release(ctx);
/* write as much as possible */
for (count = 4, udata++; (count + 4) <= len; count += 4, udata++) {
int ret;
+
ret = get_user(wbox_data, udata);
if (ret)
break;
+ ret = spu_acquire(ctx);
+ if (ret)
+ break;
ret = spu_wbox_write(ctx, wbox_data);
+ spu_release(ctx);
if (ret == 0)
break;
}
-out_unlock:
- spu_release(ctx);
-out:
return count;
}
--
2.51.2
^ permalink raw reply related [flat|nested] 16+ messages in thread* Re: [PATCH 6/6] powerpc/spufs: don't hold state_mutex during user access
2026-08-02 15:51 ` [PATCH 6/6] powerpc/spufs: don't hold state_mutex during user access Junrui Luo via B4 Relay
@ 2026-08-03 9:26 ` Arnd Bergmann
0 siblings, 0 replies; 16+ messages in thread
From: Arnd Bergmann @ 2026-08-03 9:26 UTC (permalink / raw)
To: moonafterrain, Madhavan Srinivasan, Michael Ellerman,
Nicholas Piggin, Christophe Leroy, Paul Mackerras, Alexander Viro
Cc: linuxppc-dev, linux-kernel, Yuhao Jiang
On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
> From: Junrui Luo <moonafterrain@outlook.com>
>
> spufs_mbox_read(), spufs_ibox_read() and spufs_wbox_write() take the
> context state_mutex with spu_acquire() and only drop it once their
> transfer loop has finished, so every put_user()/get_user() in those
> loops runs with the mutex held. The faulting address comes from
> userspace, so the fault can be made to take arbitrarily long via
> userfaultfd region or a FUSE-backed mapping.
>
> Drop the mutex around the user accesses: acquire it per mailbox element,
> just long enough for the ctx->ops mailbox operation, and release it
> before touching the user buffer.
>
> spufs_switch_log_read() has the same problem but its loop needs the lock
> for more than just the copy.
>
> Fixes: cdcc89bb1c6e ("[POWERPC] spufs: make mailbox functions handle
> multiple elements")
> Reported-by: Yuhao Jiang <danisjiang@gmail.com>
> Signed-off-by: Junrui Luo <moonafterrain@outlook.com>
I'm not sure if anything relies on the accesses to be atomic,
but it does seem unlikely, given that you typically only
have a single CPU thread interacting with an spu context.
It clearly fixes a bug, so
Reviewed-by: Arnd Bergmann <arnd@arndb.de>
Arnd
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH 0/6] powerpc/spufs: assorted fixes
2026-08-02 15:51 [PATCH 0/6] powerpc/spufs: assorted fixes Junrui Luo via B4 Relay
` (5 preceding siblings ...)
2026-08-02 15:51 ` [PATCH 6/6] powerpc/spufs: don't hold state_mutex during user access Junrui Luo via B4 Relay
@ 2026-08-03 9:28 ` Arnd Bergmann
2026-08-03 9:59 ` Junrui Luo
6 siblings, 1 reply; 16+ messages in thread
From: Arnd Bergmann @ 2026-08-03 9:28 UTC (permalink / raw)
To: moonafterrain, Madhavan Srinivasan, Michael Ellerman,
Nicholas Piggin, Christophe Leroy, Paul Mackerras, Alexander Viro
Cc: linuxppc-dev, linux-kernel, Yuhao Jiang, stable
On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
>
> Patches 1-5 are tagged for stable. 6/6 is deliberately not: it changes the
> atomicity of multi-element mailbox transfers rather than just adding a
> check, so it seems better to let it soak in mainline first.
>
> Build-tested only. I have no Cell or PS3 hardware, so none of this has
> been exercised at runtime.
These are all reasonable fixes as far as I can tell, but I'm missing
information about why you care about spufs. If you used some atomated
tooling, please add some reference to what you used.
Arnd
^ permalink raw reply [flat|nested] 16+ messages in thread* Re: [PATCH 0/6] powerpc/spufs: assorted fixes
2026-08-03 9:28 ` [PATCH 0/6] powerpc/spufs: assorted fixes Arnd Bergmann
@ 2026-08-03 9:59 ` Junrui Luo
2026-08-03 10:18 ` Arnd Bergmann
0 siblings, 1 reply; 16+ messages in thread
From: Junrui Luo @ 2026-08-03 9:59 UTC (permalink / raw)
To: Arnd Bergmann
Cc: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy, Paul Mackerras, Alexander Viro,
linuxppc-dev@lists.ozlabs.org, linux-kernel@vger.kernel.org,
Yuhao Jiang, stable@vger.kernel.org
On Mon, Aug 03, 2026 at 11:28:46AM +0200, Arnd Bergmann wrote:
> On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
> >
> > Patches 1-5 are tagged for stable. 6/6 is deliberately not: it changes the
> > atomicity of multi-element mailbox transfers rather than just adding a
> > check, so it seems better to let it soak in mainline first.
> >
> > Build-tested only. I have no Cell or PS3 hardware, so none of this has
> > been exercised at runtime.
>
> These are all reasonable fixes as far as I can tell, but I'm missing
> information about why you care about spufs. If you used some atomated
> tooling, please add some reference to what you used.
>
> Arnd
Hi Arnd,
We're working on a paper on LLM-assisted vulnerability research. spufs
was just picked at random as one of the modules to look at. The tooling
is an agent we developed ourselves. Should we add an Assisted-by tag in
v2?
Thanks,
Junrui Luo
^ permalink raw reply [flat|nested] 16+ messages in thread
* Re: [PATCH 0/6] powerpc/spufs: assorted fixes
2026-08-03 9:59 ` Junrui Luo
@ 2026-08-03 10:18 ` Arnd Bergmann
0 siblings, 0 replies; 16+ messages in thread
From: Arnd Bergmann @ 2026-08-03 10:18 UTC (permalink / raw)
To: Junrui Luo
Cc: Madhavan Srinivasan, Michael Ellerman, Nicholas Piggin,
Christophe Leroy, Paul Mackerras, Alexander Viro,
linuxppc-dev@lists.ozlabs.org, linux-kernel@vger.kernel.org,
Yuhao Jiang, stable@vger.kernel.org
On Mon, Aug 3, 2026, at 11:59, Junrui Luo wrote:
> On Mon, Aug 03, 2026 at 11:28:46AM +0200, Arnd Bergmann wrote:
>> On Sun, Aug 2, 2026, at 17:51, Junrui Luo via B4 Relay wrote:
>> >
>> > Patches 1-5 are tagged for stable. 6/6 is deliberately not: it changes the
>> > atomicity of multi-element mailbox transfers rather than just adding a
>> > check, so it seems better to let it soak in mainline first.
>> >
>> > Build-tested only. I have no Cell or PS3 hardware, so none of this has
>> > been exercised at runtime.
>>
>> These are all reasonable fixes as far as I can tell, but I'm missing
>> information about why you care about spufs. If you used some atomated
>> tooling, please add some reference to what you used.
>
> We're working on a paper on LLM-assisted vulnerability research. spufs
> was just picked at random as one of the modules to look at. The tooling
> is an agent we developed ourselves. Should we add an Assisted-by tag in
> v2?
Yes, I think that would help.
Arnd
^ permalink raw reply [flat|nested] 16+ messages in thread