Skip to content
Merged
Show file tree
Hide file tree
Changes from 1 commit
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
1 change: 1 addition & 0 deletions libcxx/include/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -535,6 +535,7 @@ set(files
__locale_dir/time.h
__locale_dir/wbuffer_convert.h
__locale_dir/wstring_convert.h
__log_hardening_failure
__math/abs.h
__math/copysign.h
__math/error_functions.h
Expand Down
5 changes: 5 additions & 0 deletions libcxx/include/__configuration/availability.h
Original file line number Diff line number Diff line change
Expand Up @@ -304,6 +304,11 @@
#define _LIBCPP_AVAILABILITY_HAS_VERBOSE_ABORT _LIBCPP_INTRODUCED_IN_LLVM_15
#define _LIBCPP_AVAILABILITY_VERBOSE_ABORT _LIBCPP_INTRODUCED_IN_LLVM_15_ATTRIBUTE

// This controls whether the library provides a function to log hardening failures without terminating the program (for
// the `observe` assertion semantic).
#define _LIBCPP_AVAILABILITY_HAS_LOG_HARDENING_FAILURE _LIBCPP_INTRODUCED_IN_LLVM_21
#define _LIBCPP_AVAILABILITY_LOG_HARDENING_FAILURE _LIBCPP_INTRODUCED_IN_LLVM_21_ATTRIBUTE

// This controls the availability of the C++17 std::pmr library,
// which is implemented in large part in the built library.
//
Expand Down
45 changes: 45 additions & 0 deletions libcxx/include/__log_hardening_failure
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
// -*- 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 _LIBCPP___LOG_HARDENING_FAILURE
#define _LIBCPP___LOG_HARDENING_FAILURE

#include <__config>

#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
# pragma GCC system_header
#endif

_LIBCPP_BEGIN_NAMESPACE_STD

// This function should never be called directly from the code -- it should only be called through the
// `_LIBCPP_LOG_HARDENING_FAILURE` macro.
_LIBCPP_AVAILABILITY_LOG_HARDENING_FAILURE _LIBCPP_OVERRIDABLE_FUNC_VIS void
__libcpp_log_hardening_failure(const char* message) _NOEXCEPT;

// _LIBCPP_LOG_HARDENING_FAILURE(message)
//
// This macro is used to log a hardening failure without terminating the program (as is the case if the `observe`
// assertion semantic is used). Where possible, it logs in a way that indicates a fatal error (which might include
// capturing the stack trace).
#if !defined(_LIBCPP_LOG_HARDENING_FAILURE)

# if !_LIBCPP_AVAILABILITY_HAS_LOG_HARDENING_FAILURE
// The decltype is there to suppress -Wunused warnings in this configuration.
void __use(const char*);
# define _LIBCPP_LOG_HARDENING_FAILURE(message) (decltype(::std::__use(message))())
# else
# define _LIBCPP_LOG_HARDENING_FAILURE(message) ::std::__libcpp_log_hardening_failure(message)
# endif

#endif // !defined(_LIBCPP_LOG_HARDENING_FAILURE)

_LIBCPP_END_NAMESPACE_STD

#endif // _LIBCPP___LOG_HARDENING_FAILURE
1 change: 1 addition & 0 deletions libcxx/src/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@ set(LIBCXX_SOURCES
include/ryu/ryu.h
include/to_chars_floating_point.h
include/from_chars_floating_point.h
log_hardening_failure.cpp
memory.cpp
memory_resource.cpp
new_handler.cpp
Expand Down
49 changes: 49 additions & 0 deletions libcxx/src/log_hardening_failure.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
//===----------------------------------------------------------------------===//
//
// 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 <__config>
#include <__log_hardening_failure>
#include <cstdio>

#ifdef __BIONIC__
# include <syslog.h>
extern "C" void android_set_abort_message(const char* msg);
#endif // __BIONIC__

#if defined(__APPLE__) && __has_include(<os/reason_private.h>)
# include <os/reason_private.h>
#endif

_LIBCPP_BEGIN_NAMESPACE_STD

_LIBCPP_WEAK void __libcpp_log_hardening_failure(const char* message) noexcept {
// On Apple platforms, use the `os_fault_with_payload` OS function that simulates a crash.
#if defined(__APPLE__) && __has_include(<os/reason_private.h>)
os_fault_with_payload(
/*reason_namespace=*/OS_REASON_SECURITY,
/*reason_code=*/0,
/*payload=*/nullptr,
/*payload_size=*/0,
/*reason_string=*/message,
/*reason_flags=*/0);

#elif defined(__BIONIC__)
// Show error in tombstone.
android_set_abort_message(message);

// Show error in logcat.
openlog("libc++", 0, 0);
syslog(LOG_CRIT, "%s", message);
closelog();

#else
fprintf(stderr, "%s", message);
#endif
}

_LIBCPP_END_NAMESPACE_STD
Loading