mirror of
https://github.com/torvalds/linux.git
synced 2026-11-06 21:58:01 +01:00
9p: skip over-long directory entry names for legacy 9p2000 too
The legacy 9p2000 and 9p2000.u readdir path, v9fs_dir_readdir(), parses each entry with p9stat_read() and, unlike the 9p2000.L path, never had a 256-byte name limit: a name of any length up to the wire maximum was handed to dir_emit(). getdents64() therefore returned names longer than NAME_MAX that no later syscall can use, and failed with -EIO for names of PATH_MAX bytes or more. Apply the same NAME_MAX check as the previous patch does for v9fs_dir_readdir_dotl(), so both protocol variants behave the same. Note that this is a behaviour change for 9p2000 and 9p2000.u, Name length 256..4095: - before: listed, but unusable (ENAMETOOLONG) - now: entry skipped, fetch continues Name length >=4096: - before: aborts the entire fetch (similar to 9p2000.L side) - now: entry skipped, fetch continues Suggested-by: Christian Schoenebeck <linux_oss@crudebyte.com> Link: https://lore.kernel.org/all/3910569.MHq7AAxBmi@weasel/ Signed-off-by: Haobin Wu <853555@gmail.com> Message-ID: <20260918024851.51229-4-853555@gmail.com> Signed-off-by: Dominique Martinet <asmadeus@codewreck.org>
This commit is contained in:
parent
edd807dc20
commit
55d6732b80
|
|
@ -85,7 +85,6 @@ static struct p9_rdir *v9fs_alloc_rdir_buf(struct file *filp, int buflen)
|
|||
|
||||
static int v9fs_dir_readdir(struct file *file, struct dir_context *ctx)
|
||||
{
|
||||
bool over;
|
||||
struct p9_wstat st;
|
||||
int err = 0;
|
||||
struct p9_fid *fid;
|
||||
|
|
@ -125,6 +124,9 @@ static int v9fs_dir_readdir(struct file *file, struct dir_context *ctx)
|
|||
rdir->offset = ctx->pos;
|
||||
}
|
||||
while (rdir->head < rdir->tail) {
|
||||
bool over = false;
|
||||
size_t namelen;
|
||||
|
||||
err = p9stat_read(fid->clnt, rdir->buf + rdir->head,
|
||||
rdir->tail - rdir->head, &st);
|
||||
if (err <= 0) {
|
||||
|
|
@ -132,8 +134,15 @@ static int v9fs_dir_readdir(struct file *file, struct dir_context *ctx)
|
|||
return -EIO;
|
||||
}
|
||||
|
||||
over = !dir_emit(ctx, st.name, strlen(st.name),
|
||||
QID2INO(&st.qid), dt_type(&st));
|
||||
namelen = strlen(st.name);
|
||||
if (namelen > NAME_MAX) {
|
||||
p9_debug(P9_DEBUG_ERROR,
|
||||
"skip dentry: name length %zu > NAME_MAX\n",
|
||||
namelen);
|
||||
} else {
|
||||
over = !dir_emit(ctx, st.name, namelen,
|
||||
QID2INO(&st.qid), dt_type(&st));
|
||||
}
|
||||
p9stat_free(&st);
|
||||
if (over)
|
||||
return 0;
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user