libc/lib_remove: fix TOCTOU race condition

Separately checking the state of a file before operating on it may allow
an attacker to modify the file between the two operations.

Reference:
  CWE-367
  4290aed051/sysdeps/posix/remove.c (L29-L41)

Signed-off-by: Mingjie Shen <shen497@purdue.edu>
This commit is contained in:
Mingjie Shen 2023-06-28 23:08:20 -04:00 committed by Xiang Xiao
parent dc69b108b8
commit f5a2741ec2
1 changed files with 10 additions and 17 deletions

View File

@ -51,25 +51,18 @@
int remove(FAR const char *path)
{
struct stat buf;
int ret;
/* First try to unlink since this is
* more frequently the necessary action.
*/
/* Check the kind of object pointed by path */
ret = stat(path, &buf);
if (ret != 0)
if (unlink(path) != 0 /* If it is indeed a directory... */
&& (errno != EPERM /* ...try to remove it. */
|| rmdir(path) != 0))
{
return ret;
/* Cannot remove the object for whatever reason. */
return -1;
}
/* Act according to the kind of object */
if (S_ISDIR(buf.st_mode))
{
return rmdir(path);
}
else
{
return unlink(path);
}
return 0;
}