Skip to content
Merged
Show file tree
Hide file tree
Changes from 4 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions libc/config/linux/x86_64/entrypoints.txt
Original file line number Diff line number Diff line change
Expand Up @@ -1049,6 +1049,8 @@ if(LLVM_LIBC_FULL_BUILD)
# setjmp.h entrypoints
libc.src.setjmp.longjmp
libc.src.setjmp.setjmp
libc.src.setjmp.siglongjmp
libc.src.setjmp.sigsetjmp

# stdio.h entrypoints
libc.src.stdio.clearerr
Expand Down
9 changes: 9 additions & 0 deletions libc/hdr/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -223,5 +223,14 @@ add_proxy_header_library(
libc.include.wchar
)

# offsetof is a macro inside compiler resource header stddef.h
add_proxy_header_library(
offsetof_macros
HDRS
offsetof_macros.h
FULL_BUILD_DEPENDS
libc.include.llvm-libc-macros.offsetof_macro
)

add_subdirectory(types)
add_subdirectory(func)
23 changes: 23 additions & 0 deletions libc/hdr/offsetof_macros.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
//===-- Definition of macros for offsetof ---------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_LIBC_HDR_OFFSETOF_MACROS_H
#define LLVM_LIBC_HDR_OFFSETOF_MACROS_H

#ifdef LIBC_FULL_BUILD

#include "include/llvm-libc-macros/offsetof-macro.h"

#else // Overlay mode

#define __need_offsetof
#include <stddef.h>

#endif // LLVM_LIBC_FULL_BUILD

#endif // LLVM_LIBC_HDR_OFFSETOF_MACROS_H
2 changes: 1 addition & 1 deletion libc/include/llvm-libc-types/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,6 @@ add_header(gid_t HDR gid_t.h)
add_header(uid_t HDR uid_t.h)
add_header(imaxdiv_t HDR imaxdiv_t.h)
add_header(ino_t HDR ino_t.h)
add_header(jmp_buf HDR jmp_buf.h)
add_header(mbstate_t HDR mbstate_t.h)
add_header(mode_t HDR mode_t.h)
add_header(mtx_t HDR mtx_t.h DEPENDS .__futex_word .__mutex_type)
Expand Down Expand Up @@ -83,6 +82,7 @@ add_header(union_sigval HDR union_sigval.h)
add_header(siginfo_t HDR siginfo_t.h DEPENDS .union_sigval .pid_t .uid_t .clock_t)
add_header(sig_atomic_t HDR sig_atomic_t.h)
add_header(sigset_t HDR sigset_t.h DEPENDS libc.include.llvm-libc-macros.signal_macros)
add_header(jmp_buf HDR jmp_buf.h DEPENDS .sigset_t)
add_header(struct_sigaction HDR struct_sigaction.h DEPENDS .sigset_t .siginfo_t)
add_header(struct_timespec HDR struct_timespec.h DEPENDS .time_t)
add_header(
Expand Down
24 changes: 24 additions & 0 deletions libc/include/llvm-libc-types/jmp_buf.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,16 @@
#ifndef LLVM_LIBC_TYPES_JMP_BUF_H
#define LLVM_LIBC_TYPES_JMP_BUF_H

// TODO: implement sigjmp_buf related functions for other architectures
// Issue: https://github.com/llvm/llvm-project/issues/136358
#if defined(__linux__) && (defined(__i386__) || defined(__x86_64__))
#define __LIBC_HAS_SIGJMP_BUF
#endif

#if defined(__LIBC_HAS_SIGJMP_BUF)
#include "sigset_t.h"
#endif

typedef struct {
#ifdef __x86_64__
__UINT64_TYPE__ rbx;
Expand Down Expand Up @@ -50,8 +60,22 @@ typedef struct {
#else
#error "__jmp_buf not available for your target architecture."
#endif
#if defined(__LIBC_HAS_SIGJMP_BUF)
// return address
void *sig_retaddr;
// extra register buffer to avoid indefinite stack growth in sigsetjmp
void *sig_extra;
// signal masks
sigset_t sigmask;
#endif
} __jmp_buf;

typedef __jmp_buf jmp_buf[1];

#if defined(__LIBC_HAS_SIGJMP_BUF)
typedef __jmp_buf sigjmp_buf[1];
#endif

#undef __LIBC_HAS_SIGJMP_BUF

#endif // LLVM_LIBC_TYPES_JMP_BUF_H
16 changes: 16 additions & 0 deletions libc/include/setjmp.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -21,3 +21,19 @@ functions:
- _Returns_twice
arguments:
- type: jmp_buf
- name: sigsetjmp
standards:
- POSIX
return_type: int
attributes:
- _Returns_twice
arguments:
- type: sigjmp_buf
- type: int
- name: siglongjmp
standards:
- POSIX
return_type: _Noreturn void
arguments:
- type: sigjmp_buf
- type: int
29 changes: 29 additions & 0 deletions libc/src/setjmp/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,13 @@
if(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/${LIBC_TARGET_OS})
add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/${LIBC_TARGET_OS})
add_object_library(
sigsetjmp_epilogue
ALIAS
DEPENDS
.${LIBC_TARGET_OS}.sigsetjmp_epilogue
)
endif()

if(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/${LIBC_TARGET_ARCHITECTURE})
add_subdirectory(${CMAKE_CURRENT_SOURCE_DIR}/${LIBC_TARGET_ARCHITECTURE})
endif()
Expand All @@ -15,3 +25,22 @@ add_entrypoint_object(
DEPENDS
.${LIBC_TARGET_ARCHITECTURE}.longjmp
)

if (TARGET libc.src.setjmp.sigsetjmp_epilogue)
add_entrypoint_object(
siglongjmp
SRCS
siglongjmp.cpp
HDRS
siglongjmp.h
DEPENDS
.longjmp
)

add_entrypoint_object(
sigsetjmp
ALIAS
DEPENDS
.${LIBC_TARGET_ARCHITECTURE}.sigsetjmp
)
endif()
12 changes: 12 additions & 0 deletions libc/src/setjmp/linux/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
add_object_library(
sigsetjmp_epilogue
HDRS
../sigsetjmp_epilogue.h
SRCS
sigsetjmp_epilogue.cpp
DEPENDS
libc.src.__support.common
libc.src.__support.OSUtil.osutil
libc.hdr.types.jmp_buf
libc.hdr.types.sigset_t
)
25 changes: 25 additions & 0 deletions libc/src/setjmp/linux/sigsetjmp_epilogue.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
//===-- Implementation of sigsetjmp_epilogue ------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "src/setjmp/sigsetjmp_epilogue.h"
#include "src/__support/OSUtil/syscall.h"
#include "src/__support/common.h"
#include <sys/syscall.h> // For syscall numbers.

namespace LIBC_NAMESPACE_DECL {
[[gnu::returns_twice]] int sigsetjmp_epilogue(jmp_buf buffer, int retval) {
// If set is NULL, then the signal mask is unchanged (i.e., how is
// ignored), but the current value of the signal mask is nevertheless
// returned in oldset (if it is not NULL).
syscall_impl<long>(SYS_rt_sigprocmask, SIG_SETMASK,
/* set= */ retval ? &buffer->sigmask : nullptr,
/* old_set= */ retval ? nullptr : &buffer->sigmask,
sizeof(sigset_t));
return retval;
}
} // namespace LIBC_NAMESPACE_DECL
3 changes: 2 additions & 1 deletion libc/src/setjmp/setjmp_impl.h
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,8 @@ namespace LIBC_NAMESPACE_DECL {
#ifdef LIBC_COMPILER_IS_GCC
[[gnu::nothrow]]
#endif
__attribute__((returns_twice)) int setjmp(jmp_buf buf);
[[gnu::returns_twice]] int
setjmp(jmp_buf buf);

} // namespace LIBC_NAMESPACE_DECL

Expand Down
23 changes: 23 additions & 0 deletions libc/src/setjmp/siglongjmp.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
//===-- Implementation of siglongjmp --------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "src/setjmp/siglongjmp.h"
#include "src/__support/common.h"
#include "src/setjmp/longjmp.h"

namespace LIBC_NAMESPACE_DECL {

// siglongjmp is the same as longjmp. The additional recovery work is done in
// the epilogue of the sigsetjmp function.
// TODO: move this inside the TU of longjmp and making it an alias after
// sigsetjmp is implemented for all architectures.
LLVM_LIBC_FUNCTION(void, siglongjmp, (jmp_buf buf, int val)) {
return LIBC_NAMESPACE::longjmp(buf, val);
}

} // namespace LIBC_NAMESPACE_DECL
25 changes: 25 additions & 0 deletions libc/src/setjmp/siglongjmp.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
//===-- Implementation header for siglongjmp --------------------*- C++ -*-===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_LIBC_SRC_SETJMP_SIGLONGJMP_H
#define LLVM_LIBC_SRC_SETJMP_SIGLONGJMP_H

#include "hdr/types/jmp_buf.h"
#include "src/__support/macros/config.h"
#include "src/__support/macros/properties/compiler.h"

namespace LIBC_NAMESPACE_DECL {

#ifdef LIBC_COMPILER_IS_GCC
[[gnu::nothrow]]
#endif
void siglongjmp(jmp_buf buf, int val);

} // namespace LIBC_NAMESPACE_DECL

#endif // LLVM_LIBC_SRC_SETJMP_SIGLONGJMP_H
26 changes: 26 additions & 0 deletions libc/src/setjmp/sigsetjmp.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
//===-- Implementation header for sigsetjmp ---------------------*- C++ -*-===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_LIBC_SRC_SETJMP_SIGSETJMP_H
#define LLVM_LIBC_SRC_SETJMP_SIGSETJMP_H

#include "hdr/types/jmp_buf.h"
#include "src/__support/macros/config.h"
#include "src/__support/macros/properties/compiler.h"

namespace LIBC_NAMESPACE_DECL {

#ifdef LIBC_COMPILER_IS_GCC
[[gnu::nothrow]]
#endif
[[gnu::returns_twice]] int
sigsetjmp(sigjmp_buf buf, int savesigs);

} // namespace LIBC_NAMESPACE_DECL

#endif // LLVM_LIBC_SRC_SETJMP_SIGSETJMP_H
19 changes: 19 additions & 0 deletions libc/src/setjmp/sigsetjmp_epilogue.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
//===-- Implementation header for sigsetjmp epilogue ------------*- C++ -*-===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#ifndef LLVM_LIBC_SRC_SETJMP_SIGSETJMP_EPILOGUE_H
#define LLVM_LIBC_SRC_SETJMP_SIGSETJMP_EPILOGUE_H

#include "hdr/types/jmp_buf.h"
#include "src/__support/common.h"

namespace LIBC_NAMESPACE_DECL {
[[gnu::returns_twice]] int sigsetjmp_epilogue(jmp_buf buffer, int retval);
} // namespace LIBC_NAMESPACE_DECL

#endif // LLVM_LIBC_SRC_SETJMP_SIGSETJMP_EPILOGUE_H
21 changes: 16 additions & 5 deletions libc/src/setjmp/x86_64/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,24 @@ add_entrypoint_object(
HDRS
../setjmp_impl.h
DEPENDS
libc.hdr.offsetof_macros
libc.hdr.types.jmp_buf
COMPILE_OPTIONS
${libc_opt_high_flag}
)
if (TARGET libc.src.setjmp.sigsetjmp_epilogue)
add_entrypoint_object(
sigsetjmp
SRCS
sigsetjmp.cpp
HDRS
../sigsetjmp.h
DEPENDS
libc.hdr.types.jmp_buf
libc.hdr.types.sigset_t
libc.hdr.offsetof_macros
libc.src.setjmp.sigsetjmp_epilogue
libc.src.setjmp.setjmp
)
endif()

add_entrypoint_object(
longjmp
Expand All @@ -18,7 +32,4 @@ add_entrypoint_object(
../longjmp.h
DEPENDS
libc.hdr.types.jmp_buf
COMPILE_OPTIONS
${libc_opt_high_flag}
-fomit-frame-pointer
)
2 changes: 1 addition & 1 deletion libc/src/setjmp/x86_64/setjmp.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@
//
//===----------------------------------------------------------------------===//

#include "include/llvm-libc-macros/offsetof-macro.h"
#include "hdr/offsetof_macros.h"
#include "src/__support/common.h"
#include "src/__support/macros/config.h"
#include "src/setjmp/setjmp_impl.h"
Expand Down
Loading
Loading