This is an automated email from the ASF dual-hosted git repository.

GUIDINGLI pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/nuttx.git


The following commit(s) were added to refs/heads/master by this push:
     new 20752312eaa fs/inode: bound fdlist_extend() against the requested row
20752312eaa is described below

commit 20752312eaac24994487891207c81fa22c02f7b5
Author: AlmAck <[email protected]>
AuthorDate: Sat Aug 29 19:02:15 2026 +0200

    fs/inode: bound fdlist_extend() against the requested row
    
    fdlist_extend() grows a task group's descriptor table to 'row' rows of
    CONFIG_NFILE_DESCRIPTORS_PER_BLOCK entries each, and guards the growth
    against OPEN_MAX:
    
      if (CONFIG_NFILE_DESCRIPTORS_PER_BLOCK * (orig_rows + 1) > OPEN_MAX)
    
    The check sizes the table at orig_rows + 1, which assumes the caller
    only ever grows by a single block.  The function then allocates 'row'
    rows, so the two agree only for growth by one.
    
    Callers do skip ahead.  fdlist_dup3() asks for
    fd2 / CONFIG_NFILE_DESCRIPTORS_PER_BLOCK + 1, fdlist_dupfile() for the
    row holding minfd, and fdlist_copy() for the row holding a parent
    descriptor it is duplicating.  Any of those can request a row well past
    orig_rows + 1.
    
    Such a request passes the check and the function then allocates and
    installs a table with more than OPEN_MAX descriptors.  With the defaults
    (8 per block, OPEN_MAX 256) a process holding one row that calls
    dup2(fd, 400) ends up with 51 rows, or 408 descriptor slots, against a
    256 limit.
    
    Check the row actually being requested.  For single-block growth
    row == orig_rows + 1 and the comparison is unchanged.
    
    Signed-off-by: AlmAck <[email protected]>
---
 fs/inode/fs_files.c | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/fs/inode/fs_files.c b/fs/inode/fs_files.c
index b039051bb73..6407f0eb9bd 100644
--- a/fs/inode/fs_files.c
+++ b/fs/inode/fs_files.c
@@ -104,7 +104,7 @@ static int fdlist_extend(FAR struct fdlist *list, size_t 
row)
       return 0;
     }
 
-  if (CONFIG_NFILE_DESCRIPTORS_PER_BLOCK * (orig_rows + 1) > OPEN_MAX)
+  if (CONFIG_NFILE_DESCRIPTORS_PER_BLOCK * row > OPEN_MAX)
     {
       fdlist_dump(list);
       return -EMFILE;

Reply via email to