[libc-commits] [libc] [libc] Implement fcntl when only SYS_fcntl64 is available (PR #97740)
Mikhail R. Gadelha via libc-commits
libc-commits at lists.llvm.org
Thu Jul 4 09:31:43 PDT 2024
https://github.com/mikhailramalho updated https://github.com/llvm/llvm-project/pull/97740
>From d1437a35939438ca535d03ee18345a53d1b913b6 Mon Sep 17 00:00:00 2001
From: "Mikhail R. Gadelha" <mikhail at igalia.com>
Date: Thu, 4 Jul 2024 12:18:44 -0300
Subject: [PATCH] [libc] Implement fcntl when only SYS_fcntl64 is available
This patch tries to implement fcntl with either SYS_fcntl or
SYS_fcntl64, and also changes a test case to call the fcntl function
instead of using the syscall
---
libc/src/__support/OSUtil/linux/fcntl.cpp | 19 ++++++++++++++-----
libc/test/src/sys/mman/linux/CMakeLists.txt | 1 +
libc/test/src/sys/mman/linux/shm_test.cpp | 5 ++---
3 files changed, 17 insertions(+), 8 deletions(-)
diff --git a/libc/src/__support/OSUtil/linux/fcntl.cpp b/libc/src/__support/OSUtil/linux/fcntl.cpp
index 083deb8c33681..b6483bb7534d6 100644
--- a/libc/src/__support/OSUtil/linux/fcntl.cpp
+++ b/libc/src/__support/OSUtil/linux/fcntl.cpp
@@ -22,6 +22,14 @@
namespace LIBC_NAMESPACE::internal {
int fcntl(int fd, int cmd, void *arg) {
+#if SYS_fcntl
+ constexpr auto FCNTL_SYSCALL_ID = SYS_fcntl;
+#elif defined(SYS_fcntl64)
+ constexpr auto FCNTL_SYSCALL_ID = SYS_fcntl64;
+#else
+#error "fcntl and fcntl64 syscalls not available."
+#endif
+
switch (cmd) {
case F_OFD_SETLKW: {
struct flock *flk = reinterpret_cast<struct flock *>(arg);
@@ -33,7 +41,7 @@ int fcntl(int fd, int cmd, void *arg) {
flk64.l_len = flk->l_len;
flk64.l_pid = flk->l_pid;
// create a syscall
- return LIBC_NAMESPACE::syscall_impl<int>(SYS_fcntl, fd, cmd, &flk64);
+ return LIBC_NAMESPACE::syscall_impl<int>(FCNTL_SYSCALL_ID, fd, cmd, &flk64);
}
case F_OFD_GETLK:
case F_OFD_SETLK: {
@@ -46,7 +54,8 @@ int fcntl(int fd, int cmd, void *arg) {
flk64.l_len = flk->l_len;
flk64.l_pid = flk->l_pid;
// create a syscall
- int retVal = LIBC_NAMESPACE::syscall_impl<int>(SYS_fcntl, fd, cmd, &flk64);
+ int retVal =
+ LIBC_NAMESPACE::syscall_impl<int>(FCNTL_SYSCALL_ID, fd, cmd, &flk64);
// On failure, return
if (retVal == -1)
return -1;
@@ -67,8 +76,8 @@ int fcntl(int fd, int cmd, void *arg) {
}
case F_GETOWN: {
struct f_owner_ex fex;
- int ret =
- LIBC_NAMESPACE::syscall_impl<int>(SYS_fcntl, fd, F_GETOWN_EX, &fex);
+ int ret = LIBC_NAMESPACE::syscall_impl<int>(FCNTL_SYSCALL_ID, fd,
+ F_GETOWN_EX, &fex);
if (ret >= 0)
return fex.type == F_OWNER_PGRP ? -fex.pid : fex.pid;
libc_errno = -ret;
@@ -77,7 +86,7 @@ int fcntl(int fd, int cmd, void *arg) {
// The general case
default: {
int retVal = LIBC_NAMESPACE::syscall_impl<int>(
- SYS_fcntl, fd, cmd, reinterpret_cast<void *>(arg));
+ FCNTL_SYSCALL_ID, fd, cmd, reinterpret_cast<void *>(arg));
if (retVal >= 0) {
return retVal;
}
diff --git a/libc/test/src/sys/mman/linux/CMakeLists.txt b/libc/test/src/sys/mman/linux/CMakeLists.txt
index 0762a2d846a8e..b63c76f4306fa 100644
--- a/libc/test/src/sys/mman/linux/CMakeLists.txt
+++ b/libc/test/src/sys/mman/linux/CMakeLists.txt
@@ -138,6 +138,7 @@ add_libc_unittest(
libc.include.sys_mman
libc.include.sys_syscall
libc.src.errno.errno
+ libc.src.fcntl.fcntl
libc.src.sys.mman.shm_open
libc.src.sys.mman.shm_unlink
libc.src.sys.mman.mmap
diff --git a/libc/test/src/sys/mman/linux/shm_test.cpp b/libc/test/src/sys/mman/linux/shm_test.cpp
index 3b1a2aa33b56a..4b8971f670581 100644
--- a/libc/test/src/sys/mman/linux/shm_test.cpp
+++ b/libc/test/src/sys/mman/linux/shm_test.cpp
@@ -7,6 +7,7 @@
//===----------------------------------------------------------------------===//
#include "src/__support/OSUtil/syscall.h"
+#include "src/fcntl/fcntl.h"
#include "src/sys/mman/mmap.h"
#include "src/sys/mman/munmap.h"
#include "src/sys/mman/shm_open.h"
@@ -29,9 +30,7 @@ TEST(LlvmLibcShmTest, Basic) {
returns(GE(0)).with_errno(EQ(0)));
// check that FD_CLOEXEC is set by default.
- // TODO: use fcntl when implemented.
- // https://github.com/llvm/llvm-project/issues/84968
- long flag = LIBC_NAMESPACE::syscall_impl(SYS_fcntl, fd, F_GETFD);
+ long flag = LIBC_NAMESPACE::fcntl(fd, F_GETFD);
ASSERT_GE(static_cast<int>(flag), 0);
EXPECT_NE(static_cast<int>(flag) & FD_CLOEXEC, 0);
More information about the libc-commits
mailing list