[libc-commits] [libc] [libc] Add support for SYS_fchmodat2 in fchmodat (PR #223997)

Pavel Labath via libc-commits libc-commits at lists.llvm.org
Thu Sep 17 01:00:57 PDT 2026


================
@@ -24,11 +25,25 @@
 namespace LIBC_NAMESPACE_DECL {
 namespace linux_syscalls {
 
-LIBC_INLINE ErrorOr<int> fchmodat(int fd, const char *path, mode_t mode) {
-  int ret = syscall_impl<int>(SYS_fchmodat, fd, path, mode);
-  if (ret < 0)
-    return Error(-ret);
+LIBC_INLINE ErrorOr<int> fchmodat(int fd, const char *path, mode_t mode,
+                                  int flags) {
+#if defined(SYS_fchmodat2)
+  auto ret = syscall_checked<int>(SYS_fchmodat2, fd, path, mode, flags);
+#if defined(SYS_fchmodat)
+  if (!ret && ret.error() == ENOSYS) {
+    if (flags != 0)
+      return Error(ENOTSUP);
+    return syscall_checked<int>(SYS_fchmodat, fd, path, mode);
+  }
+#endif
   return ret;
+#elif defined(SYS_fchmodat)
+  if (flags != 0)
+    return Error(ENOTSUP);
+  return syscall_checked<int>(SYS_fchmodat, fd, path, mode);
+#else
+#error "fchmodat2 and fchmodat syscalls not available."
+#endif
----------------
labath wrote:

Given that the previous version passes, I think we can assume that SYS_fchmodat is always defined and simplify this to something like:

```suggestion
#if defined(SYS_fchmodat2)
  auto ret = syscall_checked<int>(SYS_fchmodat2, fd, path, mode, flags);
  if (ret || ret.error() != ENOSYS)
    return ret;
#endif
  if (flags != 0)
    return Error(ENOTSUP);
  return syscall_checked<int>(SYS_fchmodat, fd, path, mode);
```

https://github.com/llvm/llvm-project/pull/223997


More information about the libc-commits mailing list