diff options
Diffstat (limited to 'contrib/llvm-project/compiler-rt/lib/dfsan')
18 files changed, 9562 insertions, 0 deletions
diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.cpp b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.cpp new file mode 100644 index 000000000000..302e3c3032ac --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.cpp @@ -0,0 +1,1303 @@ +//===-- dfsan.cpp ---------------------------------------------------------===// +// +// 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// DataFlowSanitizer runtime. This file defines the public interface to +// DataFlowSanitizer as well as the definition of certain runtime functions +// called automatically by the compiler (specifically the instrumentation pass +// in llvm/lib/Transforms/Instrumentation/DataFlowSanitizer.cpp). +// +// The public interface is defined in include/sanitizer/dfsan_interface.h whose +// functions are prefixed dfsan_ while the compiler interface functions are +// prefixed __dfsan_. +//===----------------------------------------------------------------------===// + +#include "dfsan/dfsan.h" + +#include "dfsan/dfsan_chained_origin_depot.h" +#include "dfsan/dfsan_flags.h" +#include "dfsan/dfsan_origin.h" +#include "dfsan/dfsan_thread.h" +#include "sanitizer_common/sanitizer_atomic.h" +#include "sanitizer_common/sanitizer_common.h" +#include "sanitizer_common/sanitizer_file.h" +#include "sanitizer_common/sanitizer_flag_parser.h" +#include "sanitizer_common/sanitizer_flags.h" +#include "sanitizer_common/sanitizer_internal_defs.h" +#include "sanitizer_common/sanitizer_libc.h" +#include "sanitizer_common/sanitizer_report_decorator.h" +#include "sanitizer_common/sanitizer_stacktrace.h" +#if SANITIZER_LINUX +# include <sys/personality.h> +#endif + +using namespace __dfsan; + +Flags __dfsan::flags_data; + +// The size of TLS variables. These constants must be kept in sync with the ones +// in DataFlowSanitizer.cpp. +static const int kDFsanArgTlsSize = 800; +static const int kDFsanRetvalTlsSize = 800; +static const int kDFsanArgOriginTlsSize = 800; + +SANITIZER_INTERFACE_ATTRIBUTE THREADLOCAL u64 + __dfsan_retval_tls[kDFsanRetvalTlsSize / sizeof(u64)]; +SANITIZER_INTERFACE_ATTRIBUTE THREADLOCAL u32 __dfsan_retval_origin_tls; +SANITIZER_INTERFACE_ATTRIBUTE THREADLOCAL u64 + __dfsan_arg_tls[kDFsanArgTlsSize / sizeof(u64)]; +SANITIZER_INTERFACE_ATTRIBUTE THREADLOCAL u32 + __dfsan_arg_origin_tls[kDFsanArgOriginTlsSize / sizeof(u32)]; + +// Instrumented code may set this value in terms of -dfsan-track-origins. +// * undefined or 0: do not track origins. +// * 1: track origins at memory store operations. +// * 2: track origins at memory load and store operations. +// TODO: track callsites. +extern "C" SANITIZER_WEAK_ATTRIBUTE const int __dfsan_track_origins; + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE int dfsan_get_track_origins() { + return &__dfsan_track_origins ? __dfsan_track_origins : 0; +} + +// On Linux/x86_64, memory is laid out as follows: +// +// +--------------------+ 0x800000000000 (top of memory) +// | application 3 | +// +--------------------+ 0x700000000000 +// | invalid | +// +--------------------+ 0x610000000000 +// | origin 1 | +// +--------------------+ 0x600000000000 +// | application 2 | +// +--------------------+ 0x510000000000 +// | shadow 1 | +// +--------------------+ 0x500000000000 +// | invalid | +// +--------------------+ 0x400000000000 +// | origin 3 | +// +--------------------+ 0x300000000000 +// | shadow 3 | +// +--------------------+ 0x200000000000 +// | origin 2 | +// +--------------------+ 0x110000000000 +// | invalid | +// +--------------------+ 0x100000000000 +// | shadow 2 | +// +--------------------+ 0x010000000000 +// | application 1 | +// +--------------------+ 0x000000000000 +// +// MEM_TO_SHADOW(mem) = mem ^ 0x500000000000 +// SHADOW_TO_ORIGIN(shadow) = shadow + 0x100000000000 + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE +dfsan_label __dfsan_union_load(const dfsan_label *ls, uptr n) { + dfsan_label label = ls[0]; + for (uptr i = 1; i != n; ++i) + label |= ls[i]; + return label; +} + +// Return the union of all the n labels from addr at the high 32 bit, and the +// origin of the first taint byte at the low 32 bit. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE u64 +__dfsan_load_label_and_origin(const void *addr, uptr n) { + dfsan_label label = 0; + u64 ret = 0; + uptr p = (uptr)addr; + dfsan_label *s = shadow_for((void *)p); + for (uptr i = 0; i < n; ++i) { + dfsan_label l = s[i]; + if (!l) + continue; + label |= l; + if (!ret) + ret = *(dfsan_origin *)origin_for((void *)(p + i)); + } + return ret | (u64)label << 32; +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE +void __dfsan_unimplemented(char *fname) { + if (flags().warn_unimplemented) + Report("WARNING: DataFlowSanitizer: call to uninstrumented function %s\n", + fname); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void __dfsan_wrapper_extern_weak_null( + const void *addr, char *fname) { + if (!addr) + Report( + "ERROR: DataFlowSanitizer: dfsan generated wrapper calling null " + "extern_weak function %s\nIf this only happens with dfsan, the " + "dfsan instrumentation pass may be accidentally optimizing out a " + "null check\n", + fname); +} + +// Use '-mllvm -dfsan-debug-nonzero-labels' and break on this function +// to try to figure out where labels are being introduced in a nominally +// label-free program. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void __dfsan_nonzero_label() { + if (flags().warn_nonzero_labels) + Report("WARNING: DataFlowSanitizer: saw nonzero label\n"); +} + +// Indirect call to an uninstrumented vararg function. We don't have a way of +// handling these at the moment. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void +__dfsan_vararg_wrapper(const char *fname) { + Report("FATAL: DataFlowSanitizer: unsupported indirect call to vararg " + "function %s\n", fname); + Die(); +} + +// Resolves the union of two labels. +SANITIZER_INTERFACE_ATTRIBUTE dfsan_label +dfsan_union(dfsan_label l1, dfsan_label l2) { + return l1 | l2; +} + +static const uptr kOriginAlign = sizeof(dfsan_origin); +static const uptr kOriginAlignMask = ~(kOriginAlign - 1UL); + +static uptr OriginAlignUp(uptr u) { + return (u + kOriginAlign - 1) & kOriginAlignMask; +} + +static uptr OriginAlignDown(uptr u) { return u & kOriginAlignMask; } + +// Return the origin of the first taint byte in the size bytes from the address +// addr. +static dfsan_origin GetOriginIfTainted(uptr addr, uptr size) { + for (uptr i = 0; i < size; ++i, ++addr) { + dfsan_label *s = shadow_for((void *)addr); + + if (*s) { + // Validate address region. + CHECK(MEM_IS_SHADOW(s)); + return *(dfsan_origin *)origin_for((void *)addr); + } + } + return 0; +} + +// For platforms which support slow unwinder only, we need to restrict the store +// context size to 1, basically only storing the current pc, because the slow +// unwinder which is based on libunwind is not async signal safe and causes +// random freezes in forking applications as well as in signal handlers. +// DFSan supports only Linux. So we do not restrict the store context size. +#define GET_STORE_STACK_TRACE_PC_BP(pc, bp) \ + BufferedStackTrace stack; \ + stack.Unwind(pc, bp, nullptr, true, flags().store_context_size); + +#define PRINT_CALLER_STACK_TRACE \ + { \ + GET_CALLER_PC_BP; \ + GET_STORE_STACK_TRACE_PC_BP(pc, bp) \ + stack.Print(); \ + } + +// Return a chain with the previous ID id and the current stack. +// from_init = true if this is the first chain of an origin tracking path. +static u32 ChainOrigin(u32 id, StackTrace *stack, bool from_init = false) { + // StackDepot is not async signal safe. Do not create new chains in a signal + // handler. + DFsanThread *t = GetCurrentThread(); + if (t && t->InSignalHandler()) + return id; + + // As an optimization the origin of an application byte is updated only when + // its shadow is non-zero. Because we are only interested in the origins of + // taint labels, it does not matter what origin a zero label has. This reduces + // memory write cost. MSan does similar optimization. The following invariant + // may not hold because of some bugs. We check the invariant to help debug. + if (!from_init && id == 0 && flags().check_origin_invariant) { + Printf(" DFSan found invalid origin invariant\n"); + PRINT_CALLER_STACK_TRACE + } + + Origin o = Origin::FromRawId(id); + stack->tag = StackTrace::TAG_UNKNOWN; + Origin chained = Origin::CreateChainedOrigin(o, stack); + return chained.raw_id(); +} + +static void ChainAndWriteOriginIfTainted(uptr src, uptr size, uptr dst, + StackTrace *stack) { + dfsan_origin o = GetOriginIfTainted(src, size); + if (o) { + o = ChainOrigin(o, stack); + *(dfsan_origin *)origin_for((void *)dst) = o; + } +} + +// Copy the origins of the size bytes from src to dst. The source and target +// memory ranges cannot be overlapped. This is used by memcpy. stack records the +// stack trace of the memcpy. When dst and src are not 4-byte aligned properly, +// origins at the unaligned address boundaries may be overwritten because four +// contiguous bytes share the same origin. +static void CopyOrigin(const void *dst, const void *src, uptr size, + StackTrace *stack) { + uptr d = (uptr)dst; + uptr beg = OriginAlignDown(d); + // Copy left unaligned origin if that memory is tainted. + if (beg < d) { + ChainAndWriteOriginIfTainted((uptr)src, beg + kOriginAlign - d, beg, stack); + beg += kOriginAlign; + } + + uptr end = OriginAlignDown(d + size); + // If both ends fall into the same 4-byte slot, we are done. + if (end < beg) + return; + + // Copy right unaligned origin if that memory is tainted. + if (end < d + size) + ChainAndWriteOriginIfTainted((uptr)src + (end - d), (d + size) - end, end, + stack); + + if (beg >= end) + return; + + // Align src up. + uptr src_a = OriginAlignUp((uptr)src); + dfsan_origin *src_o = origin_for((void *)src_a); + u32 *src_s = (u32 *)shadow_for((void *)src_a); + dfsan_origin *src_end = origin_for((void *)(src_a + (end - beg))); + dfsan_origin *dst_o = origin_for((void *)beg); + dfsan_origin last_src_o = 0; + dfsan_origin last_dst_o = 0; + for (; src_o < src_end; ++src_o, ++src_s, ++dst_o) { + if (!*src_s) + continue; + if (*src_o != last_src_o) { + last_src_o = *src_o; + last_dst_o = ChainOrigin(last_src_o, stack); + } + *dst_o = last_dst_o; + } +} + +// Copy the origins of the size bytes from src to dst. The source and target +// memory ranges may be overlapped. So the copy is done in a reverse order. +// This is used by memmove. stack records the stack trace of the memmove. +static void ReverseCopyOrigin(const void *dst, const void *src, uptr size, + StackTrace *stack) { + uptr d = (uptr)dst; + uptr end = OriginAlignDown(d + size); + + // Copy right unaligned origin if that memory is tainted. + if (end < d + size) + ChainAndWriteOriginIfTainted((uptr)src + (end - d), (d + size) - end, end, + stack); + + uptr beg = OriginAlignDown(d); + + if (beg + kOriginAlign < end) { + // Align src up. + uptr src_a = OriginAlignUp((uptr)src); + void *src_end = (void *)(src_a + end - beg - kOriginAlign); + dfsan_origin *src_end_o = origin_for(src_end); + u32 *src_end_s = (u32 *)shadow_for(src_end); + dfsan_origin *src_begin_o = origin_for((void *)src_a); + dfsan_origin *dst = origin_for((void *)(end - kOriginAlign)); + dfsan_origin last_src_o = 0; + dfsan_origin last_dst_o = 0; + for (; src_end_o >= src_begin_o; --src_end_o, --src_end_s, --dst) { + if (!*src_end_s) + continue; + if (*src_end_o != last_src_o) { + last_src_o = *src_end_o; + last_dst_o = ChainOrigin(last_src_o, stack); + } + *dst = last_dst_o; + } + } + + // Copy left unaligned origin if that memory is tainted. + if (beg < d) + ChainAndWriteOriginIfTainted((uptr)src, beg + kOriginAlign - d, beg, stack); +} + +// Copy or move the origins of the len bytes from src to dst. The source and +// target memory ranges may or may not be overlapped. This is used by memory +// transfer operations. stack records the stack trace of the memory transfer +// operation. +static void MoveOrigin(const void *dst, const void *src, uptr size, + StackTrace *stack) { + // Validate address regions. + if (!MEM_IS_SHADOW(shadow_for(dst)) || + !MEM_IS_SHADOW(shadow_for((void *)((uptr)dst + size))) || + !MEM_IS_SHADOW(shadow_for(src)) || + !MEM_IS_SHADOW(shadow_for((void *)((uptr)src + size)))) { + CHECK(false); + return; + } + // If destination origin range overlaps with source origin range, move + // origins by copying origins in a reverse order; otherwise, copy origins in + // a normal order. The orders of origin transfer are consistent with the + // orders of how memcpy and memmove transfer user data. + uptr src_aligned_beg = OriginAlignDown((uptr)src); + uptr src_aligned_end = OriginAlignDown((uptr)src + size); + uptr dst_aligned_beg = OriginAlignDown((uptr)dst); + if (dst_aligned_beg < src_aligned_end && dst_aligned_beg >= src_aligned_beg) + return ReverseCopyOrigin(dst, src, size, stack); + return CopyOrigin(dst, src, size, stack); +} + +// Set the size bytes from the addres dst to be the origin value. +static void SetOrigin(const void *dst, uptr size, u32 origin) { + if (size == 0) + return; + + // Origin mapping is 4 bytes per 4 bytes of application memory. + // Here we extend the range such that its left and right bounds are both + // 4 byte aligned. + uptr x = unaligned_origin_for((uptr)dst); + uptr beg = OriginAlignDown(x); + uptr end = OriginAlignUp(x + size); // align up. + u64 origin64 = ((u64)origin << 32) | origin; + // This is like memset, but the value is 32-bit. We unroll by 2 to write + // 64 bits at once. May want to unroll further to get 128-bit stores. + if (beg & 7ULL) { + if (*(u32 *)beg != origin) + *(u32 *)beg = origin; + beg += 4; + } + for (uptr addr = beg; addr < (end & ~7UL); addr += 8) { + if (*(u64 *)addr == origin64) + continue; + *(u64 *)addr = origin64; + } + if (end & 7ULL) + if (*(u32 *)(end - kOriginAlign) != origin) + *(u32 *)(end - kOriginAlign) = origin; +} + +#define RET_CHAIN_ORIGIN(id) \ + GET_CALLER_PC_BP; \ + GET_STORE_STACK_TRACE_PC_BP(pc, bp); \ + return ChainOrigin(id, &stack); + +// Return a new origin chain with the previous ID id and the current stack +// trace. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_origin +__dfsan_chain_origin(dfsan_origin id) { + RET_CHAIN_ORIGIN(id) +} + +// Return a new origin chain with the previous ID id and the current stack +// trace if the label is tainted. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_origin +__dfsan_chain_origin_if_tainted(dfsan_label label, dfsan_origin id) { + if (!label) + return id; + RET_CHAIN_ORIGIN(id) +} + +// Copy or move the origins of the len bytes from src to dst. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void __dfsan_mem_origin_transfer( + const void *dst, const void *src, uptr len) { + if (src == dst) + return; + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + MoveOrigin(dst, src, len, &stack); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void dfsan_mem_origin_transfer( + const void *dst, const void *src, uptr len) { + __dfsan_mem_origin_transfer(dst, src, len); +} + +static void CopyShadow(void *dst, const void *src, uptr len) { + internal_memcpy((void *)__dfsan::shadow_for(dst), + (const void *)__dfsan::shadow_for(src), + len * sizeof(dfsan_label)); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void dfsan_mem_shadow_transfer( + void *dst, const void *src, uptr len) { + CopyShadow(dst, src, len); +} + +// Copy shadow and origins of the len bytes from src to dst. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void +__dfsan_mem_shadow_origin_transfer(void *dst, const void *src, uptr size) { + if (src == dst) + return; + CopyShadow(dst, src, size); + if (dfsan_get_track_origins()) { + // Duplicating code instead of calling __dfsan_mem_origin_transfer + // so that the getting the caller stack frame works correctly. + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + MoveOrigin(dst, src, size, &stack); + } +} + +// Copy shadow and origins as per __atomic_compare_exchange. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void +__dfsan_mem_shadow_origin_conditional_exchange(u8 condition, void *target, + void *expected, + const void *desired, uptr size) { + void *dst; + const void *src; + // condition is result of native call to __atomic_compare_exchange + if (condition) { + // Copy desired into target + dst = target; + src = desired; + } else { + // Copy target into expected + dst = expected; + src = target; + } + if (src == dst) + return; + CopyShadow(dst, src, size); + if (dfsan_get_track_origins()) { + // Duplicating code instead of calling __dfsan_mem_origin_transfer + // so that the getting the caller stack frame works correctly. + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + MoveOrigin(dst, src, size, &stack); + } +} + +namespace __dfsan { + +bool dfsan_inited = false; +bool dfsan_init_is_running = false; + +void dfsan_copy_memory(void *dst, const void *src, uptr size) { + internal_memcpy(dst, src, size); + dfsan_mem_shadow_transfer(dst, src, size); + if (dfsan_get_track_origins()) + dfsan_mem_origin_transfer(dst, src, size); +} + +// Releases the pages within the origin address range. +static void ReleaseOrigins(void *addr, uptr size) { + const uptr beg_origin_addr = (uptr)__dfsan::origin_for(addr); + const void *end_addr = (void *)((uptr)addr + size); + const uptr end_origin_addr = (uptr)__dfsan::origin_for(end_addr); + + if (end_origin_addr - beg_origin_addr < + common_flags()->clear_shadow_mmap_threshold) + return; + + const uptr page_size = GetPageSizeCached(); + const uptr beg_aligned = RoundUpTo(beg_origin_addr, page_size); + const uptr end_aligned = RoundDownTo(end_origin_addr, page_size); + + if (!MmapFixedSuperNoReserve(beg_aligned, end_aligned - beg_aligned)) + Die(); +} + +static void WriteZeroShadowInRange(uptr beg, uptr end) { + // Don't write the label if it is already the value we need it to be. + // In a program where most addresses are not labeled, it is common that + // a page of shadow memory is entirely zeroed. The Linux copy-on-write + // implementation will share all of the zeroed pages, making a copy of a + // page when any value is written. The un-sharing will happen even if + // the value written does not change the value in memory. Avoiding the + // write when both |label| and |*labelp| are zero dramatically reduces + // the amount of real memory used by large programs. + if (!mem_is_zero((const char *)beg, end - beg)) + internal_memset((void *)beg, 0, end - beg); +} + +// Releases the pages within the shadow address range, and sets +// the shadow addresses not on the pages to be 0. +static void ReleaseOrClearShadows(void *addr, uptr size) { + const uptr beg_shadow_addr = (uptr)__dfsan::shadow_for(addr); + const void *end_addr = (void *)((uptr)addr + size); + const uptr end_shadow_addr = (uptr)__dfsan::shadow_for(end_addr); + + if (end_shadow_addr - beg_shadow_addr < + common_flags()->clear_shadow_mmap_threshold) { + WriteZeroShadowInRange(beg_shadow_addr, end_shadow_addr); + return; + } + + const uptr page_size = GetPageSizeCached(); + const uptr beg_aligned = RoundUpTo(beg_shadow_addr, page_size); + const uptr end_aligned = RoundDownTo(end_shadow_addr, page_size); + + if (beg_aligned >= end_aligned) { + WriteZeroShadowInRange(beg_shadow_addr, end_shadow_addr); + } else { + if (beg_aligned != beg_shadow_addr) + WriteZeroShadowInRange(beg_shadow_addr, beg_aligned); + if (end_aligned != end_shadow_addr) + WriteZeroShadowInRange(end_aligned, end_shadow_addr); + if (!MmapFixedSuperNoReserve(beg_aligned, end_aligned - beg_aligned)) + Die(); + } +} + +void SetShadow(dfsan_label label, void *addr, uptr size, dfsan_origin origin) { + if (0 != label) { + const uptr beg_shadow_addr = (uptr)__dfsan::shadow_for(addr); + internal_memset((void *)beg_shadow_addr, label, size); + if (dfsan_get_track_origins()) + SetOrigin(addr, size, origin); + return; + } + + if (dfsan_get_track_origins()) + ReleaseOrigins(addr, size); + + ReleaseOrClearShadows(addr, size); +} + +} // namespace __dfsan + +// If the label s is tainted, set the size bytes from the address p to be a new +// origin chain with the previous ID o and the current stack trace. This is +// used by instrumentation to reduce code size when too much code is inserted. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void __dfsan_maybe_store_origin( + dfsan_label s, void *p, uptr size, dfsan_origin o) { + if (UNLIKELY(s)) { + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + SetOrigin(p, size, ChainOrigin(o, &stack)); + } +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void __dfsan_set_label( + dfsan_label label, dfsan_origin origin, void *addr, uptr size) { + __dfsan::SetShadow(label, addr, size, origin); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void dfsan_set_label(dfsan_label label, void *addr, uptr size) { + dfsan_origin init_origin = 0; + if (label && dfsan_get_track_origins()) { + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + init_origin = ChainOrigin(0, &stack, true); + } + __dfsan::SetShadow(label, addr, size, init_origin); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void dfsan_add_label(dfsan_label label, void *addr, uptr size) { + if (0 == label) + return; + + if (dfsan_get_track_origins()) { + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + dfsan_origin init_origin = ChainOrigin(0, &stack, true); + SetOrigin(addr, size, init_origin); + } + + for (dfsan_label *labelp = shadow_for(addr); size != 0; --size, ++labelp) + *labelp |= label; +} + +// Unlike the other dfsan interface functions the behavior of this function +// depends on the label of one of its arguments. Hence it is implemented as a +// custom function. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_label +__dfsw_dfsan_get_label(long data, dfsan_label data_label, + dfsan_label *ret_label) { + *ret_label = 0; + return data_label; +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_label __dfso_dfsan_get_label( + long data, dfsan_label data_label, dfsan_label *ret_label, + dfsan_origin data_origin, dfsan_origin *ret_origin) { + *ret_label = 0; + *ret_origin = 0; + return data_label; +} + +// This function is used if dfsan_get_origin is called when origin tracking is +// off. +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_origin __dfsw_dfsan_get_origin( + long data, dfsan_label data_label, dfsan_label *ret_label) { + *ret_label = 0; + return 0; +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_origin __dfso_dfsan_get_origin( + long data, dfsan_label data_label, dfsan_label *ret_label, + dfsan_origin data_origin, dfsan_origin *ret_origin) { + *ret_label = 0; + *ret_origin = 0; + return data_origin; +} + +SANITIZER_INTERFACE_ATTRIBUTE dfsan_label +dfsan_read_label(const void *addr, uptr size) { + if (size == 0) + return 0; + return __dfsan_union_load(shadow_for(addr), size); +} + +SANITIZER_INTERFACE_ATTRIBUTE dfsan_origin +dfsan_read_origin_of_first_taint(const void *addr, uptr size) { + return GetOriginIfTainted((uptr)addr, size); +} + +SANITIZER_INTERFACE_ATTRIBUTE void dfsan_set_label_origin(dfsan_label label, + dfsan_origin origin, + void *addr, + uptr size) { + __dfsan_set_label(label, origin, addr, size); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE int +dfsan_has_label(dfsan_label label, dfsan_label elem) { + return (label & elem) == elem; +} + +namespace __dfsan { + +typedef void (*dfsan_conditional_callback_t)(dfsan_label label, + dfsan_origin origin); +static dfsan_conditional_callback_t conditional_callback = nullptr; +static dfsan_label labels_in_signal_conditional = 0; + +static void ConditionalCallback(dfsan_label label, dfsan_origin origin) { + // Programs have many branches. For efficiency the conditional sink callback + // handler needs to ignore as many as possible as early as possible. + if (label == 0) { + return; + } + if (conditional_callback == nullptr) { + return; + } + + // This initial ConditionalCallback handler needs to be in here in dfsan + // runtime (rather than being an entirely user implemented hook) so that it + // has access to dfsan thread information. + DFsanThread *t = GetCurrentThread(); + // A callback operation which does useful work (like record the flow) will + // likely be too long executed in a signal handler. + if (t && t->InSignalHandler()) { + // Record set of labels used in signal handler for completeness. + labels_in_signal_conditional |= label; + return; + } + + conditional_callback(label, origin); +} + +} // namespace __dfsan + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void +__dfsan_conditional_callback_origin(dfsan_label label, dfsan_origin origin) { + __dfsan::ConditionalCallback(label, origin); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void __dfsan_conditional_callback( + dfsan_label label) { + __dfsan::ConditionalCallback(label, 0); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void dfsan_set_conditional_callback( + __dfsan::dfsan_conditional_callback_t callback) { + __dfsan::conditional_callback = callback; +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_label +dfsan_get_labels_in_signal_conditional() { + return __dfsan::labels_in_signal_conditional; +} + +namespace __dfsan { + +typedef void (*dfsan_reaches_function_callback_t)(dfsan_label label, + dfsan_origin origin, + const char *file, + unsigned int line, + const char *function); +static dfsan_reaches_function_callback_t reaches_function_callback = nullptr; +static dfsan_label labels_in_signal_reaches_function = 0; + +static void ReachesFunctionCallback(dfsan_label label, dfsan_origin origin, + const char *file, unsigned int line, + const char *function) { + if (label == 0) { + return; + } + if (reaches_function_callback == nullptr) { + return; + } + + // This initial ReachesFunctionCallback handler needs to be in here in dfsan + // runtime (rather than being an entirely user implemented hook) so that it + // has access to dfsan thread information. + DFsanThread *t = GetCurrentThread(); + // A callback operation which does useful work (like record the flow) will + // likely be too long executed in a signal handler. + if (t && t->InSignalHandler()) { + // Record set of labels used in signal handler for completeness. + labels_in_signal_reaches_function |= label; + return; + } + + reaches_function_callback(label, origin, file, line, function); +} + +} // namespace __dfsan + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void +__dfsan_reaches_function_callback_origin(dfsan_label label, dfsan_origin origin, + const char *file, unsigned int line, + const char *function) { + __dfsan::ReachesFunctionCallback(label, origin, file, line, function); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void +__dfsan_reaches_function_callback(dfsan_label label, const char *file, + unsigned int line, const char *function) { + __dfsan::ReachesFunctionCallback(label, 0, file, line, function); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void +dfsan_set_reaches_function_callback( + __dfsan::dfsan_reaches_function_callback_t callback) { + __dfsan::reaches_function_callback = callback; +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_label +dfsan_get_labels_in_signal_reaches_function() { + return __dfsan::labels_in_signal_reaches_function; +} + +class Decorator : public __sanitizer::SanitizerCommonDecorator { + public: + Decorator() : SanitizerCommonDecorator() {} + const char *Origin() const { return Magenta(); } +}; + +namespace { + +void PrintNoOriginTrackingWarning() { + Decorator d; + Printf( + " %sDFSan: origin tracking is not enabled. Did you specify the " + "-dfsan-track-origins=1 option?%s\n", + d.Warning(), d.Default()); +} + +void PrintNoTaintWarning(const void *address) { + Decorator d; + Printf(" %sDFSan: no tainted value at %x%s\n", d.Warning(), address, + d.Default()); +} + +void PrintInvalidOriginWarning(dfsan_label label, const void *address) { + Decorator d; + Printf( + " %sTaint value 0x%x (at %p) has invalid origin tracking. This can " + "be a DFSan bug.%s\n", + d.Warning(), label, address, d.Default()); +} + +void PrintInvalidOriginIdWarning(dfsan_origin origin) { + Decorator d; + Printf( + " %sOrigin Id %d has invalid origin tracking. This can " + "be a DFSan bug.%s\n", + d.Warning(), origin, d.Default()); +} + +bool PrintOriginTraceFramesToStr(Origin o, InternalScopedString *out) { + Decorator d; + bool found = false; + + while (o.isChainedOrigin()) { + StackTrace stack; + dfsan_origin origin_id = o.raw_id(); + o = o.getNextChainedOrigin(&stack); + if (o.isChainedOrigin()) + out->AppendF( + " %sOrigin value: 0x%x, Taint value was stored to memory at%s\n", + d.Origin(), origin_id, d.Default()); + else + out->AppendF(" %sOrigin value: 0x%x, Taint value was created at%s\n", + d.Origin(), origin_id, d.Default()); + + // Includes a trailing newline, so no need to add it again. + stack.PrintTo(out); + found = true; + } + + return found; +} + +bool PrintOriginTraceToStr(const void *addr, const char *description, + InternalScopedString *out) { + CHECK(out); + CHECK(dfsan_get_track_origins()); + Decorator d; + + const dfsan_label label = *__dfsan::shadow_for(addr); + CHECK(label); + + const dfsan_origin origin = *__dfsan::origin_for(addr); + + out->AppendF(" %sTaint value 0x%x (at %p) origin tracking (%s)%s\n", + d.Origin(), label, addr, description ? description : "", + d.Default()); + + Origin o = Origin::FromRawId(origin); + return PrintOriginTraceFramesToStr(o, out); +} + +} // namespace + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void dfsan_print_origin_trace( + const void *addr, const char *description) { + if (!dfsan_get_track_origins()) { + PrintNoOriginTrackingWarning(); + return; + } + + const dfsan_label label = *__dfsan::shadow_for(addr); + if (!label) { + PrintNoTaintWarning(addr); + return; + } + + InternalScopedString trace; + bool success = PrintOriginTraceToStr(addr, description, &trace); + + if (trace.length()) + Printf("%s", trace.data()); + + if (!success) + PrintInvalidOriginWarning(label, addr); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE uptr +dfsan_sprint_origin_trace(const void *addr, const char *description, + char *out_buf, uptr out_buf_size) { + CHECK(out_buf); + + if (!dfsan_get_track_origins()) { + PrintNoOriginTrackingWarning(); + return 0; + } + + const dfsan_label label = *__dfsan::shadow_for(addr); + if (!label) { + PrintNoTaintWarning(addr); + return 0; + } + + InternalScopedString trace; + bool success = PrintOriginTraceToStr(addr, description, &trace); + + if (!success) { + PrintInvalidOriginWarning(label, addr); + return 0; + } + + if (out_buf_size) { + internal_strncpy(out_buf, trace.data(), out_buf_size - 1); + out_buf[out_buf_size - 1] = '\0'; + } + + return trace.length(); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void dfsan_print_origin_id_trace( + dfsan_origin origin) { + if (!dfsan_get_track_origins()) { + PrintNoOriginTrackingWarning(); + return; + } + Origin o = Origin::FromRawId(origin); + + InternalScopedString trace; + bool success = PrintOriginTraceFramesToStr(o, &trace); + + if (trace.length()) + Printf("%s", trace.data()); + + if (!success) + PrintInvalidOriginIdWarning(origin); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE uptr dfsan_sprint_origin_id_trace( + dfsan_origin origin, char *out_buf, uptr out_buf_size) { + CHECK(out_buf); + + if (!dfsan_get_track_origins()) { + PrintNoOriginTrackingWarning(); + return 0; + } + Origin o = Origin::FromRawId(origin); + + InternalScopedString trace; + bool success = PrintOriginTraceFramesToStr(o, &trace); + + if (!success) { + PrintInvalidOriginIdWarning(origin); + return 0; + } + + if (out_buf_size) { + internal_strncpy(out_buf, trace.data(), out_buf_size - 1); + out_buf[out_buf_size - 1] = '\0'; + } + + return trace.length(); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE dfsan_origin +dfsan_get_init_origin(const void *addr) { + if (!dfsan_get_track_origins()) + return 0; + + const dfsan_label label = *__dfsan::shadow_for(addr); + if (!label) + return 0; + + const dfsan_origin origin = *__dfsan::origin_for(addr); + + Origin o = Origin::FromRawId(origin); + dfsan_origin origin_id = o.raw_id(); + while (o.isChainedOrigin()) { + StackTrace stack; + origin_id = o.raw_id(); + o = o.getNextChainedOrigin(&stack); + } + return origin_id; +} + +void __sanitizer::BufferedStackTrace::UnwindImpl(uptr pc, uptr bp, + void *context, + bool request_fast, + u32 max_depth) { + using namespace __dfsan; + DFsanThread *t = GetCurrentThread(); + if (!t || !StackTrace::WillUseFastUnwind(request_fast)) { + return Unwind(max_depth, pc, bp, context, 0, 0, false); + } + Unwind(max_depth, pc, bp, nullptr, t->stack_top(), t->stack_bottom(), true); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE void __sanitizer_print_stack_trace() { + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + stack.Print(); +} + +extern "C" SANITIZER_INTERFACE_ATTRIBUTE uptr +dfsan_sprint_stack_trace(char *out_buf, uptr out_buf_size) { + CHECK(out_buf); + GET_CALLER_PC_BP; + GET_STORE_STACK_TRACE_PC_BP(pc, bp); + return stack.PrintTo(out_buf, out_buf_size); +} + +void Flags::SetDefaults() { +#define DFSAN_FLAG(Type, Name, DefaultValue, Description) Name = DefaultValue; +#include "dfsan_flags.inc" +#undef DFSAN_FLAG +} + +static void RegisterDfsanFlags(FlagParser *parser, Flags *f) { +#define DFSAN_FLAG(Type, Name, DefaultValue, Description) \ + RegisterFlag(parser, #Name, Description, &f->Name); +#include "dfsan_flags.inc" +#undef DFSAN_FLAG +} + +static void InitializeFlags() { + SetCommonFlagsDefaults(); + { + CommonFlags cf; + cf.CopyFrom(*common_flags()); + cf.intercept_tls_get_addr = true; + OverrideCommonFlags(cf); + } + flags().SetDefaults(); + + FlagParser parser; + RegisterCommonFlags(&parser); + RegisterDfsanFlags(&parser, &flags()); + parser.ParseStringFromEnv("DFSAN_OPTIONS"); + InitializeCommonFlags(); + if (Verbosity()) ReportUnrecognizedFlags(); + if (common_flags()->help) parser.PrintFlagDescriptions(); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void dfsan_clear_arg_tls(uptr offset, uptr size) { + internal_memset((void *)((uptr)__dfsan_arg_tls + offset), 0, size); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void dfsan_clear_thread_local_state() { + internal_memset(__dfsan_arg_tls, 0, sizeof(__dfsan_arg_tls)); + internal_memset(__dfsan_retval_tls, 0, sizeof(__dfsan_retval_tls)); + + if (dfsan_get_track_origins()) { + internal_memset(__dfsan_arg_origin_tls, 0, sizeof(__dfsan_arg_origin_tls)); + internal_memset(&__dfsan_retval_origin_tls, 0, + sizeof(__dfsan_retval_origin_tls)); + } +} + +SANITIZER_INTERFACE_ATTRIBUTE +void dfsan_set_arg_tls(uptr offset, dfsan_label label) { + // 2x to match ShadowTLSAlignment. + // ShadowTLSAlignment should probably be changed. + // TODO: Consider reducing ShadowTLSAlignment to 1. + // Aligning to 2 bytes is probably a remnant of fast16 mode. + ((dfsan_label *)__dfsan_arg_tls)[offset * 2] = label; +} + +SANITIZER_INTERFACE_ATTRIBUTE +void dfsan_set_arg_origin_tls(uptr offset, dfsan_origin o) { + __dfsan_arg_origin_tls[offset] = o; +} + +extern "C" void dfsan_flush() { + const uptr maxVirtualAddress = GetMaxUserVirtualAddress(); + for (unsigned i = 0; i < kMemoryLayoutSize; ++i) { + uptr start = kMemoryLayout[i].start; + uptr end = kMemoryLayout[i].end; + uptr size = end - start; + MappingDesc::Type type = kMemoryLayout[i].type; + + if (type != MappingDesc::SHADOW && type != MappingDesc::ORIGIN) + continue; + + // Check if the segment should be mapped based on platform constraints. + if (start >= maxVirtualAddress) + continue; + + if (!MmapFixedSuperNoReserve(start, size, kMemoryLayout[i].name)) { + Printf("FATAL: DataFlowSanitizer: failed to clear memory region\n"); + Die(); + } + } + __dfsan::labels_in_signal_conditional = 0; + __dfsan::labels_in_signal_reaches_function = 0; +} + +// TODO: CheckMemoryLayoutSanity is based on msan. +// Consider refactoring these into a shared implementation. +static void CheckMemoryLayoutSanity() { + uptr prev_end = 0; + for (unsigned i = 0; i < kMemoryLayoutSize; ++i) { + uptr start = kMemoryLayout[i].start; + uptr end = kMemoryLayout[i].end; + MappingDesc::Type type = kMemoryLayout[i].type; + CHECK_LT(start, end); + CHECK_EQ(prev_end, start); + CHECK(addr_is_type(start, type)); + CHECK(addr_is_type((start + end) / 2, type)); + CHECK(addr_is_type(end - 1, type)); + if (type == MappingDesc::APP) { + uptr addr = start; + CHECK(MEM_IS_SHADOW(MEM_TO_SHADOW(addr))); + CHECK(MEM_IS_ORIGIN(MEM_TO_ORIGIN(addr))); + CHECK_EQ(MEM_TO_ORIGIN(addr), SHADOW_TO_ORIGIN(MEM_TO_SHADOW(addr))); + + addr = (start + end) / 2; + CHECK(MEM_IS_SHADOW(MEM_TO_SHADOW(addr))); + CHECK(MEM_IS_ORIGIN(MEM_TO_ORIGIN(addr))); + CHECK_EQ(MEM_TO_ORIGIN(addr), SHADOW_TO_ORIGIN(MEM_TO_SHADOW(addr))); + + addr = end - 1; + CHECK(MEM_IS_SHADOW(MEM_TO_SHADOW(addr))); + CHECK(MEM_IS_ORIGIN(MEM_TO_ORIGIN(addr))); + CHECK_EQ(MEM_TO_ORIGIN(addr), SHADOW_TO_ORIGIN(MEM_TO_SHADOW(addr))); + } + prev_end = end; + } +} + +// TODO: CheckMemoryRangeAvailability is based on msan. +// Consider refactoring these into a shared implementation. +static bool CheckMemoryRangeAvailability(uptr beg, uptr size, bool verbose) { + if (size > 0) { + uptr end = beg + size - 1; + if (!MemoryRangeIsAvailable(beg, end)) { + if (verbose) + Printf("FATAL: Memory range %p - %p is not available.\n", beg, end); + return false; + } + } + return true; +} + +// TODO: ProtectMemoryRange is based on msan. +// Consider refactoring these into a shared implementation. +static bool ProtectMemoryRange(uptr beg, uptr size, const char *name) { + if (size > 0) { + void *addr = MmapFixedNoAccess(beg, size, name); + if (beg == 0 && addr) { + // Depending on the kernel configuration, we may not be able to protect + // the page at address zero. + uptr gap = 16 * GetPageSizeCached(); + beg += gap; + size -= gap; + addr = MmapFixedNoAccess(beg, size, name); + } + if ((uptr)addr != beg) { + uptr end = beg + size - 1; + Printf("FATAL: Cannot protect memory range %p - %p (%s).\n", beg, end, + name); + return false; + } + } + return true; +} + +// TODO: InitShadow is based on msan. +// Consider refactoring these into a shared implementation. +bool InitShadow(bool init_origins, bool dry_run) { + // Let user know mapping parameters first. + VPrintf(1, "dfsan_init %p\n", (void *)&__dfsan::dfsan_init); + for (unsigned i = 0; i < kMemoryLayoutSize; ++i) + VPrintf(1, "%s: %zx - %zx\n", kMemoryLayout[i].name, kMemoryLayout[i].start, + kMemoryLayout[i].end - 1); + + CheckMemoryLayoutSanity(); + + if (!MEM_IS_APP(&__dfsan::dfsan_init)) { + if (!dry_run) + Printf("FATAL: Code %p is out of application range. Non-PIE build?\n", + (uptr)&__dfsan::dfsan_init); + return false; + } + + const uptr maxVirtualAddress = GetMaxUserVirtualAddress(); + + for (unsigned i = 0; i < kMemoryLayoutSize; ++i) { + uptr start = kMemoryLayout[i].start; + uptr end = kMemoryLayout[i].end; + uptr size = end - start; + MappingDesc::Type type = kMemoryLayout[i].type; + + // Check if the segment should be mapped based on platform constraints. + if (start >= maxVirtualAddress) + continue; + + bool map = type == MappingDesc::SHADOW || + (init_origins && type == MappingDesc::ORIGIN); + bool protect = type == MappingDesc::INVALID || + (!init_origins && type == MappingDesc::ORIGIN); + CHECK(!(map && protect)); + if (!map && !protect) { + CHECK(type == MappingDesc::APP || type == MappingDesc::ALLOCATOR); + + if (dry_run && type == MappingDesc::ALLOCATOR && + !CheckMemoryRangeAvailability(start, size, !dry_run)) + return false; + } + if (map) { + if (dry_run && !CheckMemoryRangeAvailability(start, size, !dry_run)) + return false; + if (!dry_run && + !MmapFixedSuperNoReserve(start, size, kMemoryLayout[i].name)) + return false; + if (!dry_run && common_flags()->use_madv_dontdump) + DontDumpShadowMemory(start, size); + } + if (protect) { + if (dry_run && !CheckMemoryRangeAvailability(start, size, !dry_run)) + return false; + if (!dry_run && !ProtectMemoryRange(start, size, kMemoryLayout[i].name)) + return false; + } + } + + return true; +} + +bool InitShadowWithReExec(bool init_origins) { + // Start with dry run: check layout is ok, but don't print warnings because + // warning messages will cause tests to fail (even if we successfully re-exec + // after the warning). + bool success = InitShadow(init_origins, true); + if (!success) { +#if SANITIZER_LINUX + // Perhaps ASLR entropy is too high. If ASLR is enabled, re-exec without it. + int old_personality = personality(0xffffffff); + bool aslr_on = + (old_personality != -1) && ((old_personality & ADDR_NO_RANDOMIZE) == 0); + + if (aslr_on) { + VReport(1, + "WARNING: DataflowSanitizer: memory layout is incompatible, " + "possibly due to high-entropy ASLR.\n" + "Re-execing with fixed virtual address space.\n" + "N.B. reducing ASLR entropy is preferable.\n"); + CHECK_NE(personality(old_personality | ADDR_NO_RANDOMIZE), -1); + ReExec(); + } +#endif + } + + // The earlier dry run didn't actually map or protect anything. Run again in + // non-dry run mode. + return success && InitShadow(init_origins, false); +} + +static void DFsanInit(int argc, char **argv, char **envp) { + CHECK(!dfsan_init_is_running); + if (dfsan_inited) + return; + dfsan_init_is_running = true; + SanitizerToolName = "DataflowSanitizer"; + + AvoidCVE_2016_2143(); + + InitializeFlags(); + + CheckASLR(); + + if (!InitShadowWithReExec(dfsan_get_track_origins())) { + Printf("FATAL: DataflowSanitizer can not mmap the shadow memory.\n"); + DumpProcessMap(); + Die(); + } + + initialize_interceptors(); + + // Set up threads + DFsanTSDInit(DFsanTSDDtor); + + dfsan_allocator_init(); + + DFsanThread *main_thread = DFsanThread::Create(nullptr, nullptr); + SetCurrentThread(main_thread); + main_thread->Init(); + + dfsan_init_is_running = false; + dfsan_inited = true; +} + +namespace __dfsan { + +void dfsan_init() { DFsanInit(0, nullptr, nullptr); } + +} // namespace __dfsan + +#if SANITIZER_CAN_USE_PREINIT_ARRAY +__attribute__((section(".preinit_array"), + used)) static void (*dfsan_init_ptr)(int, char **, + char **) = DFsanInit; +#endif diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.h b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.h new file mode 100644 index 000000000000..29938a08de54 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.h @@ -0,0 +1,112 @@ +//===-- dfsan.h -------------------------------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// Private DFSan header. +//===----------------------------------------------------------------------===// + +#ifndef DFSAN_H +#define DFSAN_H + +#include "sanitizer_common/sanitizer_internal_defs.h" + +#include "dfsan_platform.h" + +using __sanitizer::u32; +using __sanitizer::u8; +using __sanitizer::uptr; + +// Copy declarations from public sanitizer/dfsan_interface.h header here. +typedef u8 dfsan_label; +typedef u32 dfsan_origin; + +extern "C" { +void dfsan_add_label(dfsan_label label, void *addr, uptr size); +void dfsan_set_label(dfsan_label label, void *addr, uptr size); +dfsan_label dfsan_read_label(const void *addr, uptr size); +dfsan_label dfsan_union(dfsan_label l1, dfsan_label l2); +// Zero out [offset, offset+size) from __dfsan_arg_tls. +void dfsan_clear_arg_tls(uptr offset, uptr size); +// Zero out the TLS storage. +void dfsan_clear_thread_local_state(); + +// Set DFSan label and origin TLS of argument for a call. +// Note that offset may not correspond with argument number. +// Some arguments (aggregate/array) will use several offsets. +void dfsan_set_arg_tls(uptr offset, dfsan_label label); +void dfsan_set_arg_origin_tls(uptr offset, dfsan_origin o); + +// Return the origin associated with the first taint byte in the size bytes +// from the address addr. +dfsan_origin dfsan_read_origin_of_first_taint(const void *addr, uptr size); + +// Set the data within [addr, addr+size) with label and origin. +void dfsan_set_label_origin(dfsan_label label, dfsan_origin origin, void *addr, + uptr size); + +// Copy or move the origins of the len bytes from src to dst. +void dfsan_mem_origin_transfer(const void *dst, const void *src, uptr len); + +// Copy shadow bytes from src to dst. +// Note this preserves distinct taint labels at specific offsets. +void dfsan_mem_shadow_transfer(void *dst, const void *src, uptr len); +} // extern "C" + +template <typename T> +void dfsan_set_label(dfsan_label label, T &data) { + dfsan_set_label(label, (void *)&data, sizeof(T)); +} + +namespace __dfsan { + +extern bool dfsan_inited; +extern bool dfsan_init_is_running; + +void initialize_interceptors(); + +inline dfsan_label *shadow_for(void *ptr) { + return (dfsan_label *)MEM_TO_SHADOW(ptr); +} + +inline const dfsan_label *shadow_for(const void *ptr) { + return shadow_for(const_cast<void *>(ptr)); +} + +inline uptr unaligned_origin_for(uptr ptr) { return MEM_TO_ORIGIN(ptr); } + +inline dfsan_origin *origin_for(void *ptr) { + auto aligned_addr = unaligned_origin_for(reinterpret_cast<uptr>(ptr)) & + ~(sizeof(dfsan_origin) - 1); + return reinterpret_cast<dfsan_origin *>(aligned_addr); +} + +inline const dfsan_origin *origin_for(const void *ptr) { + return origin_for(const_cast<void *>(ptr)); +} + +void dfsan_copy_memory(void *dst, const void *src, uptr size); + +void dfsan_allocator_init(); +void dfsan_deallocate(void *ptr); + +void *dfsan_malloc(uptr size); +void *dfsan_calloc(uptr nmemb, uptr size); +void *dfsan_realloc(void *ptr, uptr size); +void *dfsan_reallocarray(void *ptr, uptr nmemb, uptr size); +void *dfsan_valloc(uptr size); +void *dfsan_pvalloc(uptr size); +void *dfsan_aligned_alloc(uptr alignment, uptr size); +void *dfsan_memalign(uptr alignment, uptr size); +int dfsan_posix_memalign(void **memptr, uptr alignment, uptr size); + +void dfsan_init(); + +} // namespace __dfsan + +#endif // DFSAN_H diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.syms.extra b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.syms.extra new file mode 100644 index 000000000000..e34766c3ba1c --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan.syms.extra @@ -0,0 +1,4 @@ +dfsan_* +__dfsan_* +__dfsw_* +__dfso_* diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_allocator.cpp b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_allocator.cpp new file mode 100644 index 000000000000..682df8c6e034 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_allocator.cpp @@ -0,0 +1,333 @@ +//===-- dfsan_allocator.cpp -------------------------- --------------------===// +// +// 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataflowSanitizer. +// +// DataflowSanitizer allocator. +//===----------------------------------------------------------------------===// + +#include "dfsan_allocator.h" + +#include "dfsan.h" +#include "dfsan_flags.h" +#include "dfsan_thread.h" +#include "sanitizer_common/sanitizer_allocator.h" +#include "sanitizer_common/sanitizer_allocator_checks.h" +#include "sanitizer_common/sanitizer_allocator_interface.h" +#include "sanitizer_common/sanitizer_allocator_report.h" +#include "sanitizer_common/sanitizer_errno.h" + +namespace __dfsan { + +struct Metadata { + uptr requested_size; +}; + +struct DFsanMapUnmapCallback { + void OnMap(uptr p, uptr size) const { dfsan_set_label(0, (void *)p, size); } + void OnMapSecondary(uptr p, uptr size, uptr user_begin, + uptr user_size) const { + OnMap(p, size); + } + void OnUnmap(uptr p, uptr size) const { dfsan_set_label(0, (void *)p, size); } +}; + +// Note: to ensure that the allocator is compatible with the application memory +// layout (especially with high-entropy ASLR), kSpaceBeg and kSpaceSize must be +// duplicated as MappingDesc::ALLOCATOR in dfsan_platform.h. +#if defined(__aarch64__) +const uptr kAllocatorSpace = 0xE00000000000ULL; +#else +const uptr kAllocatorSpace = 0x700000000000ULL; +#endif +const uptr kMaxAllowedMallocSize = 1ULL << 40; + +struct AP64 { // Allocator64 parameters. Deliberately using a short name. + static const uptr kSpaceBeg = kAllocatorSpace; + static const uptr kSpaceSize = 0x40000000000; // 4T. + static const uptr kMetadataSize = sizeof(Metadata); + typedef DefaultSizeClassMap SizeClassMap; + typedef DFsanMapUnmapCallback MapUnmapCallback; + static const uptr kFlags = 0; + using AddressSpaceView = LocalAddressSpaceView; +}; + +typedef SizeClassAllocator64<AP64> PrimaryAllocator; + +typedef CombinedAllocator<PrimaryAllocator> Allocator; +typedef Allocator::AllocatorCache AllocatorCache; + +static Allocator allocator; +static AllocatorCache fallback_allocator_cache; +static StaticSpinMutex fallback_mutex; + +static uptr max_malloc_size; + +void dfsan_allocator_init() { + SetAllocatorMayReturnNull(common_flags()->allocator_may_return_null); + allocator.Init(common_flags()->allocator_release_to_os_interval_ms); + if (common_flags()->max_allocation_size_mb) + max_malloc_size = Min(common_flags()->max_allocation_size_mb << 20, + kMaxAllowedMallocSize); + else + max_malloc_size = kMaxAllowedMallocSize; +} + +AllocatorCache *GetAllocatorCache(DFsanThreadLocalMallocStorage *ms) { + CHECK(ms); + CHECK_LE(sizeof(AllocatorCache), sizeof(ms->allocator_cache)); + return reinterpret_cast<AllocatorCache *>(ms->allocator_cache); +} + +void DFsanThreadLocalMallocStorage::CommitBack() { + allocator.SwallowCache(GetAllocatorCache(this)); +} + +static void *DFsanAllocate(uptr size, uptr alignment, bool zeroise) { + if (size > max_malloc_size) { + if (AllocatorMayReturnNull()) { + Report("WARNING: DataflowSanitizer failed to allocate 0x%zx bytes\n", + size); + return nullptr; + } + BufferedStackTrace stack; + ReportAllocationSizeTooBig(size, max_malloc_size, &stack); + } + if (UNLIKELY(IsRssLimitExceeded())) { + if (AllocatorMayReturnNull()) + return nullptr; + BufferedStackTrace stack; + ReportRssLimitExceeded(&stack); + } + DFsanThread *t = GetCurrentThread(); + void *allocated; + if (t) { + AllocatorCache *cache = GetAllocatorCache(&t->malloc_storage()); + allocated = allocator.Allocate(cache, size, alignment); + } else { + SpinMutexLock l(&fallback_mutex); + AllocatorCache *cache = &fallback_allocator_cache; + allocated = allocator.Allocate(cache, size, alignment); + } + if (UNLIKELY(!allocated)) { + SetAllocatorOutOfMemory(); + if (AllocatorMayReturnNull()) + return nullptr; + BufferedStackTrace stack; + ReportOutOfMemory(size, &stack); + } + Metadata *meta = + reinterpret_cast<Metadata *>(allocator.GetMetaData(allocated)); + meta->requested_size = size; + if (zeroise) { + internal_memset(allocated, 0, size); + dfsan_set_label(0, allocated, size); + } else if (flags().zero_in_malloc) { + dfsan_set_label(0, allocated, size); + } + return allocated; +} + +void dfsan_deallocate(void *p) { + CHECK(p); + Metadata *meta = reinterpret_cast<Metadata *>(allocator.GetMetaData(p)); + uptr size = meta->requested_size; + meta->requested_size = 0; + if (flags().zero_in_free) + dfsan_set_label(0, p, size); + DFsanThread *t = GetCurrentThread(); + if (t) { + AllocatorCache *cache = GetAllocatorCache(&t->malloc_storage()); + allocator.Deallocate(cache, p); + } else { + SpinMutexLock l(&fallback_mutex); + AllocatorCache *cache = &fallback_allocator_cache; + allocator.Deallocate(cache, p); + } +} + +void *DFsanReallocate(void *old_p, uptr new_size, uptr alignment) { + Metadata *meta = reinterpret_cast<Metadata *>(allocator.GetMetaData(old_p)); + uptr old_size = meta->requested_size; + uptr actually_allocated_size = allocator.GetActuallyAllocatedSize(old_p); + if (new_size <= actually_allocated_size) { + // We are not reallocating here. + meta->requested_size = new_size; + if (new_size > old_size && flags().zero_in_malloc) + dfsan_set_label(0, (char *)old_p + old_size, new_size - old_size); + return old_p; + } + uptr memcpy_size = Min(new_size, old_size); + void *new_p = DFsanAllocate(new_size, alignment, false /*zeroise*/); + if (new_p) { + dfsan_copy_memory(new_p, old_p, memcpy_size); + dfsan_deallocate(old_p); + } + return new_p; +} + +void *DFsanCalloc(uptr nmemb, uptr size) { + if (UNLIKELY(CheckForCallocOverflow(size, nmemb))) { + if (AllocatorMayReturnNull()) + return nullptr; + BufferedStackTrace stack; + ReportCallocOverflow(nmemb, size, &stack); + } + return DFsanAllocate(nmemb * size, sizeof(u64), true /*zeroise*/); +} + +static const void *AllocationBegin(const void *p) { + if (!p) + return nullptr; + void *beg = allocator.GetBlockBegin(p); + if (!beg) + return nullptr; + Metadata *b = (Metadata *)allocator.GetMetaData(beg); + if (!b) + return nullptr; + if (b->requested_size == 0) + return nullptr; + return (const void *)beg; +} + +static uptr AllocationSize(const void *p) { + if (!p) + return 0; + const void *beg = allocator.GetBlockBegin(p); + if (beg != p) + return 0; + Metadata *b = (Metadata *)allocator.GetMetaData(p); + return b->requested_size; +} + +static uptr AllocationSizeFast(const void *p) { + return reinterpret_cast<Metadata *>(allocator.GetMetaData(p))->requested_size; +} + +void *dfsan_malloc(uptr size) { + return SetErrnoOnNull(DFsanAllocate(size, sizeof(u64), false /*zeroise*/)); +} + +void *dfsan_calloc(uptr nmemb, uptr size) { + return SetErrnoOnNull(DFsanCalloc(nmemb, size)); +} + +void *dfsan_realloc(void *ptr, uptr size) { + if (!ptr) + return SetErrnoOnNull(DFsanAllocate(size, sizeof(u64), false /*zeroise*/)); + if (size == 0) { + dfsan_deallocate(ptr); + return nullptr; + } + return SetErrnoOnNull(DFsanReallocate(ptr, size, sizeof(u64))); +} + +void *dfsan_reallocarray(void *ptr, uptr nmemb, uptr size) { + if (UNLIKELY(CheckForCallocOverflow(size, nmemb))) { + errno = errno_ENOMEM; + if (AllocatorMayReturnNull()) + return nullptr; + BufferedStackTrace stack; + ReportReallocArrayOverflow(nmemb, size, &stack); + } + return dfsan_realloc(ptr, nmemb * size); +} + +void *dfsan_valloc(uptr size) { + return SetErrnoOnNull( + DFsanAllocate(size, GetPageSizeCached(), false /*zeroise*/)); +} + +void *dfsan_pvalloc(uptr size) { + uptr PageSize = GetPageSizeCached(); + if (UNLIKELY(CheckForPvallocOverflow(size, PageSize))) { + errno = errno_ENOMEM; + if (AllocatorMayReturnNull()) + return nullptr; + BufferedStackTrace stack; + ReportPvallocOverflow(size, &stack); + } + // pvalloc(0) should allocate one page. + size = size ? RoundUpTo(size, PageSize) : PageSize; + return SetErrnoOnNull(DFsanAllocate(size, PageSize, false /*zeroise*/)); +} + +void *dfsan_aligned_alloc(uptr alignment, uptr size) { + if (UNLIKELY(!CheckAlignedAllocAlignmentAndSize(alignment, size))) { + errno = errno_EINVAL; + if (AllocatorMayReturnNull()) + return nullptr; + BufferedStackTrace stack; + ReportInvalidAlignedAllocAlignment(size, alignment, &stack); + } + return SetErrnoOnNull(DFsanAllocate(size, alignment, false /*zeroise*/)); +} + +void *dfsan_memalign(uptr alignment, uptr size) { + if (UNLIKELY(!IsPowerOfTwo(alignment))) { + errno = errno_EINVAL; + if (AllocatorMayReturnNull()) + return nullptr; + BufferedStackTrace stack; + ReportInvalidAllocationAlignment(alignment, &stack); + } + return SetErrnoOnNull(DFsanAllocate(size, alignment, false /*zeroise*/)); +} + +int dfsan_posix_memalign(void **memptr, uptr alignment, uptr size) { + if (UNLIKELY(!CheckPosixMemalignAlignment(alignment))) { + if (AllocatorMayReturnNull()) + return errno_EINVAL; + BufferedStackTrace stack; + ReportInvalidPosixMemalignAlignment(alignment, &stack); + } + void *ptr = DFsanAllocate(size, alignment, false /*zeroise*/); + if (UNLIKELY(!ptr)) + // OOM error is already taken care of by DFsanAllocate. + return errno_ENOMEM; + CHECK(IsAligned((uptr)ptr, alignment)); + *memptr = ptr; + return 0; +} + +} // namespace __dfsan + +using namespace __dfsan; + +uptr __sanitizer_get_current_allocated_bytes() { + uptr stats[AllocatorStatCount]; + allocator.GetStats(stats); + return stats[AllocatorStatAllocated]; +} + +uptr __sanitizer_get_heap_size() { + uptr stats[AllocatorStatCount]; + allocator.GetStats(stats); + return stats[AllocatorStatMapped]; +} + +uptr __sanitizer_get_free_bytes() { return 1; } + +uptr __sanitizer_get_unmapped_bytes() { return 1; } + +uptr __sanitizer_get_estimated_allocated_size(uptr size) { return size; } + +int __sanitizer_get_ownership(const void *p) { return AllocationSize(p) != 0; } + +const void *__sanitizer_get_allocated_begin(const void *p) { + return AllocationBegin(p); +} + +uptr __sanitizer_get_allocated_size(const void *p) { return AllocationSize(p); } + +uptr __sanitizer_get_allocated_size_fast(const void *p) { + DCHECK_EQ(p, __sanitizer_get_allocated_begin(p)); + uptr ret = AllocationSizeFast(p); + DCHECK_EQ(ret, __sanitizer_get_allocated_size(p)); + return ret; +} diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_allocator.h b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_allocator.h new file mode 100644 index 000000000000..6ff24fc57a85 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_allocator.h @@ -0,0 +1,30 @@ +//===-- dfsan_allocator.h ---------------------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataflowSanitizer. +// +//===----------------------------------------------------------------------===// + +#ifndef DFSAN_ALLOCATOR_H +#define DFSAN_ALLOCATOR_H + +#include "sanitizer_common/sanitizer_common.h" + +namespace __dfsan { + +struct DFsanThreadLocalMallocStorage { + alignas(8) uptr allocator_cache[96 * (512 * 8 + 16)]; // Opaque. + void CommitBack(); + + private: + // These objects are allocated via mmap() and are zero-initialized. + DFsanThreadLocalMallocStorage() {} +}; + +} // namespace __dfsan +#endif // DFSAN_ALLOCATOR_H diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_chained_origin_depot.cpp b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_chained_origin_depot.cpp new file mode 100644 index 000000000000..f95194d19f03 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_chained_origin_depot.cpp @@ -0,0 +1,28 @@ +//===-- dfsan_chained_origin_depot.cpp ------------------------------------===// +// +// 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// A storage for chained origins. +//===----------------------------------------------------------------------===// + +#include "dfsan_chained_origin_depot.h" + +namespace __dfsan { + +static ChainedOriginDepot chainedOriginDepot; + +ChainedOriginDepot* GetChainedOriginDepot() { return &chainedOriginDepot; } + +void ChainedOriginDepotLockBeforeFork() { chainedOriginDepot.LockBeforeFork(); } + +void ChainedOriginDepotUnlockAfterFork(bool fork_child) { + chainedOriginDepot.UnlockAfterFork(fork_child); +} + +} // namespace __dfsan diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_chained_origin_depot.h b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_chained_origin_depot.h new file mode 100644 index 000000000000..83b9e29e1b71 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_chained_origin_depot.h @@ -0,0 +1,29 @@ +//===-- dfsan_chained_origin_depot.h ----------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// A storage for chained origins. +//===----------------------------------------------------------------------===// + +#ifndef DFSAN_CHAINED_ORIGIN_DEPOT_H +#define DFSAN_CHAINED_ORIGIN_DEPOT_H + +#include "sanitizer_common/sanitizer_chained_origin_depot.h" +#include "sanitizer_common/sanitizer_common.h" + +namespace __dfsan { + +ChainedOriginDepot* GetChainedOriginDepot(); + +void ChainedOriginDepotLockBeforeFork(); +void ChainedOriginDepotUnlockAfterFork(bool fork_child); + +} // namespace __dfsan + +#endif // DFSAN_CHAINED_ORIGIN_DEPOT_H diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_custom.cpp b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_custom.cpp new file mode 100644 index 000000000000..050f5232c040 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_custom.cpp @@ -0,0 +1,2905 @@ +//===-- dfsan_custom.cpp --------------------------------------------------===// +// +// 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// This file defines the custom functions listed in done_abilist.txt. +//===----------------------------------------------------------------------===// + +#include <arpa/inet.h> +#include <assert.h> +#include <ctype.h> +#include <dlfcn.h> +#include <link.h> +#include <poll.h> +#include <pthread.h> +#include <pwd.h> +#include <sched.h> +#include <signal.h> +#include <stdarg.h> +#include <stdint.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <sys/epoll.h> +#include <sys/resource.h> +#include <sys/select.h> +#include <sys/socket.h> +#include <sys/stat.h> +#include <sys/time.h> +#include <sys/types.h> +#include <time.h> +#include <unistd.h> + +#include "dfsan/dfsan.h" +#include "dfsan/dfsan_chained_origin_depot.h" +#include "dfsan/dfsan_flags.h" +#include "dfsan/dfsan_thread.h" +#include "sanitizer_common/sanitizer_common.h" +#include "sanitizer_common/sanitizer_internal_defs.h" +#include "sanitizer_common/sanitizer_linux.h" +#include "sanitizer_common/sanitizer_stackdepot.h" + +using namespace __dfsan; + +#define CALL_WEAK_INTERCEPTOR_HOOK(f, ...) \ + do { \ + if (f) \ + f(__VA_ARGS__); \ + } while (false) +#define DECLARE_WEAK_INTERCEPTOR_HOOK(f, ...) \ +SANITIZER_INTERFACE_ATTRIBUTE SANITIZER_WEAK_ATTRIBUTE void f(__VA_ARGS__); + +#define WRAPPER_ALIAS(fun, real) \ + SANITIZER_INTERFACE_ATTRIBUTE void __dfsw_##fun() ALIAS(__dfsw_##real); \ + SANITIZER_INTERFACE_ATTRIBUTE void __dfso_##fun() ALIAS(__dfso_##real); + +// Async-safe, non-reentrant spin lock. +class SignalSpinLocker { + public: + SignalSpinLocker() { + sigset_t all_set; + sigfillset(&all_set); + pthread_sigmask(SIG_SETMASK, &all_set, &saved_thread_mask_); + sigactions_mu.Lock(); + } + ~SignalSpinLocker() { + sigactions_mu.Unlock(); + pthread_sigmask(SIG_SETMASK, &saved_thread_mask_, nullptr); + } + + private: + static StaticSpinMutex sigactions_mu; + sigset_t saved_thread_mask_; + + SignalSpinLocker(const SignalSpinLocker &) = delete; + SignalSpinLocker &operator=(const SignalSpinLocker &) = delete; +}; + +StaticSpinMutex SignalSpinLocker::sigactions_mu; + +extern "C" { +SANITIZER_INTERFACE_ATTRIBUTE int +__dfsw_stat(const char *path, struct stat *buf, dfsan_label path_label, + dfsan_label buf_label, dfsan_label *ret_label) { + int ret = stat(path, buf); + if (ret == 0) + dfsan_set_label(0, buf, sizeof(struct stat)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_stat( + const char *path, struct stat *buf, dfsan_label path_label, + dfsan_label buf_label, dfsan_label *ret_label, dfsan_origin path_origin, + dfsan_origin buf_origin, dfsan_origin *ret_origin) { + int ret = __dfsw_stat(path, buf, path_label, buf_label, ret_label); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_fstat(int fd, struct stat *buf, + dfsan_label fd_label, + dfsan_label buf_label, + dfsan_label *ret_label) { + int ret = fstat(fd, buf); + if (ret == 0) + dfsan_set_label(0, buf, sizeof(struct stat)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_fstat( + int fd, struct stat *buf, dfsan_label fd_label, dfsan_label buf_label, + dfsan_label *ret_label, dfsan_origin fd_origin, dfsan_origin buf_origin, + dfsan_origin *ret_origin) { + int ret = __dfsw_fstat(fd, buf, fd_label, buf_label, ret_label); + return ret; +} + +static char *dfsan_strchr_with_label(const char *s, int c, size_t *bytes_read, + dfsan_label s_label, dfsan_label c_label, + dfsan_label *ret_label) { + char *match_pos = nullptr; + for (size_t i = 0;; ++i) { + if (s[i] == c || s[i] == 0) { + // If s[i] is the \0 at the end of the string, and \0 is not the + // character we are searching for, then return null. + *bytes_read = i + 1; + match_pos = s[i] == 0 && c != 0 ? nullptr : const_cast<char *>(s + i); + break; + } + } + if (flags().strict_data_dependencies) + *ret_label = s_label; + else + *ret_label = dfsan_union(dfsan_read_label(s, *bytes_read), + dfsan_union(s_label, c_label)); + return match_pos; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfsw_strchr(const char *s, int c, + dfsan_label s_label, + dfsan_label c_label, + dfsan_label *ret_label) { + size_t bytes_read; + return dfsan_strchr_with_label(s, c, &bytes_read, s_label, c_label, + ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strchr( + const char *s, int c, dfsan_label s_label, dfsan_label c_label, + dfsan_label *ret_label, dfsan_origin s_origin, dfsan_origin c_origin, + dfsan_origin *ret_origin) { + size_t bytes_read; + char *r = + dfsan_strchr_with_label(s, c, &bytes_read, s_label, c_label, ret_label); + if (flags().strict_data_dependencies) { + *ret_origin = s_origin; + } else if (*ret_label) { + dfsan_origin o = dfsan_read_origin_of_first_taint(s, bytes_read); + *ret_origin = o ? o : (s_label ? s_origin : c_origin); + } + return r; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfsw_strpbrk(const char *s, + const char *accept, + dfsan_label s_label, + dfsan_label accept_label, + dfsan_label *ret_label) { + const char *ret = strpbrk(s, accept); + if (flags().strict_data_dependencies) { + *ret_label = ret ? s_label : 0; + } else { + size_t s_bytes_read = (ret ? ret - s : strlen(s)) + 1; + *ret_label = + dfsan_union(dfsan_read_label(s, s_bytes_read), + dfsan_union(dfsan_read_label(accept, strlen(accept) + 1), + dfsan_union(s_label, accept_label))); + } + return const_cast<char *>(ret); +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strpbrk( + const char *s, const char *accept, dfsan_label s_label, + dfsan_label accept_label, dfsan_label *ret_label, dfsan_origin s_origin, + dfsan_origin accept_origin, dfsan_origin *ret_origin) { + const char *ret = __dfsw_strpbrk(s, accept, s_label, accept_label, ret_label); + if (flags().strict_data_dependencies) { + if (ret) + *ret_origin = s_origin; + } else { + if (*ret_label) { + size_t s_bytes_read = (ret ? ret - s : strlen(s)) + 1; + dfsan_origin o = dfsan_read_origin_of_first_taint(s, s_bytes_read); + if (o) { + *ret_origin = o; + } else { + o = dfsan_read_origin_of_first_taint(accept, strlen(accept) + 1); + *ret_origin = o ? o : (s_label ? s_origin : accept_origin); + } + } + } + return const_cast<char *>(ret); +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfsw_strsep(char **s, const char *delim, + dfsan_label s_label, + dfsan_label delim_label, + dfsan_label *ret_label) { + dfsan_label base_label = dfsan_read_label(s, sizeof(*s)); + char *base = *s; + char *res = strsep(s, delim); + if (res != *s) { + char *token_start = res; + int token_length = strlen(res); + // the delimiter byte has been set to NULL + dfsan_set_label(0, token_start + token_length, 1); + } + + if (flags().strict_data_dependencies) { + *ret_label = res ? base_label : 0; + } else { + size_t s_bytes_read = (res ? strlen(res) : strlen(base)) + 1; + *ret_label = dfsan_union( + dfsan_union(base_label, dfsan_read_label(base, sizeof(s_bytes_read))), + dfsan_union(dfsan_read_label(delim, strlen(delim) + 1), + dfsan_union(s_label, delim_label))); + } + + return res; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strsep( + char **s, const char *delim, dfsan_label s_label, dfsan_label delim_label, + dfsan_label *ret_label, dfsan_origin s_origin, dfsan_origin delim_origin, + dfsan_origin *ret_origin) { + dfsan_origin base_origin = dfsan_read_origin_of_first_taint(s, sizeof(*s)); + char *res = __dfsw_strsep(s, delim, s_label, delim_label, ret_label); + if (flags().strict_data_dependencies) { + if (res) + *ret_origin = base_origin; + } else { + if (*ret_label) { + if (base_origin) { + *ret_origin = base_origin; + } else { + dfsan_origin o = + dfsan_read_origin_of_first_taint(delim, strlen(delim) + 1); + *ret_origin = o ? o : (s_label ? s_origin : delim_origin); + } + } + } + + return res; +} + +static int dfsan_memcmp_bcmp(const void *s1, const void *s2, size_t n, + size_t *bytes_read) { + const char *cs1 = (const char *) s1, *cs2 = (const char *) s2; + for (size_t i = 0; i != n; ++i) { + if (cs1[i] != cs2[i]) { + *bytes_read = i + 1; + return cs1[i] - cs2[i]; + } + } + *bytes_read = n; + return 0; +} + +static dfsan_label dfsan_get_memcmp_label(const void *s1, const void *s2, + size_t pos) { + if (flags().strict_data_dependencies) + return 0; + return dfsan_union(dfsan_read_label(s1, pos), dfsan_read_label(s2, pos)); +} + +static void dfsan_get_memcmp_origin(const void *s1, const void *s2, size_t pos, + dfsan_label *ret_label, + dfsan_origin *ret_origin) { + *ret_label = dfsan_get_memcmp_label(s1, s2, pos); + if (*ret_label == 0) + return; + dfsan_origin o = dfsan_read_origin_of_first_taint(s1, pos); + *ret_origin = o ? o : dfsan_read_origin_of_first_taint(s2, pos); +} + +static int dfsan_memcmp_bcmp_label(const void *s1, const void *s2, size_t n, + dfsan_label *ret_label) { + size_t bytes_read; + int r = dfsan_memcmp_bcmp(s1, s2, n, &bytes_read); + *ret_label = dfsan_get_memcmp_label(s1, s2, bytes_read); + return r; +} + +static int dfsan_memcmp_bcmp_origin(const void *s1, const void *s2, size_t n, + dfsan_label *ret_label, + dfsan_origin *ret_origin) { + size_t bytes_read; + int r = dfsan_memcmp_bcmp(s1, s2, n, &bytes_read); + dfsan_get_memcmp_origin(s1, s2, bytes_read, ret_label, ret_origin); + return r; +} + +DECLARE_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_memcmp, uptr caller_pc, + const void *s1, const void *s2, size_t n, + dfsan_label s1_label, dfsan_label s2_label, + dfsan_label n_label) + +DECLARE_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_origin_memcmp, uptr caller_pc, + const void *s1, const void *s2, size_t n, + dfsan_label s1_label, dfsan_label s2_label, + dfsan_label n_label, dfsan_origin s1_origin, + dfsan_origin s2_origin, dfsan_origin n_origin) + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_memcmp(const void *s1, const void *s2, + size_t n, dfsan_label s1_label, + dfsan_label s2_label, + dfsan_label n_label, + dfsan_label *ret_label) { + CALL_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_memcmp, GET_CALLER_PC(), s1, s2, n, + s1_label, s2_label, n_label); + return dfsan_memcmp_bcmp_label(s1, s2, n, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_memcmp( + const void *s1, const void *s2, size_t n, dfsan_label s1_label, + dfsan_label s2_label, dfsan_label n_label, dfsan_label *ret_label, + dfsan_origin s1_origin, dfsan_origin s2_origin, dfsan_origin n_origin, + dfsan_origin *ret_origin) { + CALL_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_origin_memcmp, GET_CALLER_PC(), s1, + s2, n, s1_label, s2_label, n_label, s1_origin, + s2_origin, n_origin); + return dfsan_memcmp_bcmp_origin(s1, s2, n, ret_label, ret_origin); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_bcmp(const void *s1, const void *s2, + size_t n, dfsan_label s1_label, + dfsan_label s2_label, + dfsan_label n_label, + dfsan_label *ret_label) { + return dfsan_memcmp_bcmp_label(s1, s2, n, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_bcmp( + const void *s1, const void *s2, size_t n, dfsan_label s1_label, + dfsan_label s2_label, dfsan_label n_label, dfsan_label *ret_label, + dfsan_origin s1_origin, dfsan_origin s2_origin, dfsan_origin n_origin, + dfsan_origin *ret_origin) { + return dfsan_memcmp_bcmp_origin(s1, s2, n, ret_label, ret_origin); +} + +// When n == 0, compare strings without byte limit. +// When n > 0, compare the first (at most) n bytes of s1 and s2. +static int dfsan_strncmp(const char *s1, const char *s2, size_t n, + size_t *bytes_read) { + for (size_t i = 0;; ++i) { + if (s1[i] != s2[i] || s1[i] == 0 || s2[i] == 0 || (n > 0 && i == n - 1)) { + *bytes_read = i + 1; + return s1[i] - s2[i]; + } + } +} + +DECLARE_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_strcmp, uptr caller_pc, + const char *s1, const char *s2, + dfsan_label s1_label, dfsan_label s2_label) + +DECLARE_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_origin_strcmp, uptr caller_pc, + const char *s1, const char *s2, + dfsan_label s1_label, dfsan_label s2_label, + dfsan_origin s1_origin, dfsan_origin s2_origin) + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_strcmp(const char *s1, const char *s2, + dfsan_label s1_label, + dfsan_label s2_label, + dfsan_label *ret_label) { + CALL_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_strcmp, GET_CALLER_PC(), s1, s2, + s1_label, s2_label); + size_t bytes_read; + int r = dfsan_strncmp(s1, s2, 0, &bytes_read); + *ret_label = dfsan_get_memcmp_label(s1, s2, bytes_read); + return r; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_strcmp( + const char *s1, const char *s2, dfsan_label s1_label, dfsan_label s2_label, + dfsan_label *ret_label, dfsan_origin s1_origin, dfsan_origin s2_origin, + dfsan_origin *ret_origin) { + CALL_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_origin_strcmp, GET_CALLER_PC(), s1, + s2, s1_label, s2_label, s1_origin, s2_origin); + size_t bytes_read; + int r = dfsan_strncmp(s1, s2, 0, &bytes_read); + dfsan_get_memcmp_origin(s1, s2, bytes_read, ret_label, ret_origin); + return r; +} + +// When n == 0, compare strings without byte limit. +// When n > 0, compare the first (at most) n bytes of s1 and s2. +static int dfsan_strncasecmp(const char *s1, const char *s2, size_t n, + size_t *bytes_read) { + for (size_t i = 0;; ++i) { + char s1_lower = tolower(s1[i]); + char s2_lower = tolower(s2[i]); + + if (s1_lower != s2_lower || s1[i] == 0 || s2[i] == 0 || + (n > 0 && i == n - 1)) { + *bytes_read = i + 1; + return s1_lower - s2_lower; + } + } +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_strcasecmp(const char *s1, + const char *s2, + dfsan_label s1_label, + dfsan_label s2_label, + dfsan_label *ret_label) { + size_t bytes_read; + int r = dfsan_strncasecmp(s1, s2, 0, &bytes_read); + *ret_label = dfsan_get_memcmp_label(s1, s2, bytes_read); + return r; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_strcasecmp( + const char *s1, const char *s2, dfsan_label s1_label, dfsan_label s2_label, + dfsan_label *ret_label, dfsan_origin s1_origin, dfsan_origin s2_origin, + dfsan_origin *ret_origin) { + size_t bytes_read; + int r = dfsan_strncasecmp(s1, s2, 0, &bytes_read); + dfsan_get_memcmp_origin(s1, s2, bytes_read, ret_label, ret_origin); + return r; +} + +DECLARE_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_strncmp, uptr caller_pc, + const char *s1, const char *s2, size_t n, + dfsan_label s1_label, dfsan_label s2_label, + dfsan_label n_label) + +DECLARE_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_origin_strncmp, uptr caller_pc, + const char *s1, const char *s2, size_t n, + dfsan_label s1_label, dfsan_label s2_label, + dfsan_label n_label, dfsan_origin s1_origin, + dfsan_origin s2_origin, dfsan_origin n_origin) + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_strncmp(const char *s1, const char *s2, + size_t n, dfsan_label s1_label, + dfsan_label s2_label, + dfsan_label n_label, + dfsan_label *ret_label) { + if (n == 0) { + *ret_label = 0; + return 0; + } + + CALL_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_strncmp, GET_CALLER_PC(), s1, s2, + n, s1_label, s2_label, n_label); + + size_t bytes_read; + int r = dfsan_strncmp(s1, s2, n, &bytes_read); + *ret_label = dfsan_get_memcmp_label(s1, s2, bytes_read); + return r; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_strncmp( + const char *s1, const char *s2, size_t n, dfsan_label s1_label, + dfsan_label s2_label, dfsan_label n_label, dfsan_label *ret_label, + dfsan_origin s1_origin, dfsan_origin s2_origin, dfsan_origin n_origin, + dfsan_origin *ret_origin) { + if (n == 0) { + *ret_label = 0; + return 0; + } + + CALL_WEAK_INTERCEPTOR_HOOK(dfsan_weak_hook_origin_strncmp, GET_CALLER_PC(), + s1, s2, n, s1_label, s2_label, n_label, s1_origin, + s2_origin, n_origin); + + size_t bytes_read; + int r = dfsan_strncmp(s1, s2, n, &bytes_read); + dfsan_get_memcmp_origin(s1, s2, bytes_read, ret_label, ret_origin); + return r; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_strncasecmp( + const char *s1, const char *s2, size_t n, dfsan_label s1_label, + dfsan_label s2_label, dfsan_label n_label, dfsan_label *ret_label) { + if (n == 0) { + *ret_label = 0; + return 0; + } + + size_t bytes_read; + int r = dfsan_strncasecmp(s1, s2, n, &bytes_read); + *ret_label = dfsan_get_memcmp_label(s1, s2, bytes_read); + return r; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_strncasecmp( + const char *s1, const char *s2, size_t n, dfsan_label s1_label, + dfsan_label s2_label, dfsan_label n_label, dfsan_label *ret_label, + dfsan_origin s1_origin, dfsan_origin s2_origin, dfsan_origin n_origin, + dfsan_origin *ret_origin) { + if (n == 0) { + *ret_label = 0; + return 0; + } + + size_t bytes_read; + int r = dfsan_strncasecmp(s1, s2, n, &bytes_read); + dfsan_get_memcmp_origin(s1, s2, bytes_read, ret_label, ret_origin); + return r; +} + + +SANITIZER_INTERFACE_ATTRIBUTE size_t +__dfsw_strlen(const char *s, dfsan_label s_label, dfsan_label *ret_label) { + size_t ret = strlen(s); + if (flags().strict_data_dependencies) { + *ret_label = 0; + } else { + *ret_label = dfsan_read_label(s, ret + 1); + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE size_t __dfso_strlen(const char *s, + dfsan_label s_label, + dfsan_label *ret_label, + dfsan_origin s_origin, + dfsan_origin *ret_origin) { + size_t ret = __dfsw_strlen(s, s_label, ret_label); + if (!flags().strict_data_dependencies) + *ret_origin = dfsan_read_origin_of_first_taint(s, ret + 1); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE size_t __dfsw_strnlen(const char *s, + size_t maxlen, + dfsan_label s_label, + dfsan_label maxlen_label, + dfsan_label *ret_label) { + size_t ret = strnlen(s, maxlen); + if (flags().strict_data_dependencies) { + *ret_label = 0; + } else { + size_t full_len = strlen(s); + size_t covered_len = maxlen > (full_len + 1) ? (full_len + 1) : maxlen; + *ret_label = dfsan_union(maxlen_label, dfsan_read_label(s, covered_len)); + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE size_t __dfso_strnlen( + const char *s, size_t maxlen, dfsan_label s_label, dfsan_label maxlen_label, + dfsan_label *ret_label, dfsan_origin s_origin, dfsan_origin maxlen_origin, + dfsan_origin *ret_origin) { + size_t ret = __dfsw_strnlen(s, maxlen, s_label, maxlen_label, ret_label); + if (!flags().strict_data_dependencies) { + size_t full_len = strlen(s); + size_t covered_len = maxlen > (full_len + 1) ? (full_len + 1) : maxlen; + dfsan_origin o = dfsan_read_origin_of_first_taint(s, covered_len); + *ret_origin = o ? o : maxlen_origin; + } + return ret; +} + +static void *dfsan_memmove(void *dest, const void *src, size_t n) { + dfsan_label *sdest = shadow_for(dest); + const dfsan_label *ssrc = shadow_for(src); + internal_memmove((void *)sdest, (const void *)ssrc, n * sizeof(dfsan_label)); + return internal_memmove(dest, src, n); +} + +static void *dfsan_memmove_with_origin(void *dest, const void *src, size_t n) { + dfsan_mem_origin_transfer(dest, src, n); + return dfsan_memmove(dest, src, n); +} + +static void *dfsan_memcpy(void *dest, const void *src, size_t n) { + dfsan_mem_shadow_transfer(dest, src, n); + return internal_memcpy(dest, src, n); +} + +static void *dfsan_memcpy_with_origin(void *dest, const void *src, size_t n) { + dfsan_mem_origin_transfer(dest, src, n); + return dfsan_memcpy(dest, src, n); +} + +static void dfsan_memset(void *s, int c, dfsan_label c_label, size_t n) { + internal_memset(s, c, n); + dfsan_set_label(c_label, s, n); +} + +static void dfsan_memset_with_origin(void *s, int c, dfsan_label c_label, + dfsan_origin c_origin, size_t n) { + internal_memset(s, c, n); + dfsan_set_label_origin(c_label, c_origin, s, n); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void *__dfsw_memcpy(void *dest, const void *src, size_t n, + dfsan_label dest_label, dfsan_label src_label, + dfsan_label n_label, dfsan_label *ret_label) { + *ret_label = dest_label; + return dfsan_memcpy(dest, src, n); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void *__dfso_memcpy(void *dest, const void *src, size_t n, + dfsan_label dest_label, dfsan_label src_label, + dfsan_label n_label, dfsan_label *ret_label, + dfsan_origin dest_origin, dfsan_origin src_origin, + dfsan_origin n_origin, dfsan_origin *ret_origin) { + *ret_label = dest_label; + *ret_origin = dest_origin; + return dfsan_memcpy_with_origin(dest, src, n); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void *__dfsw_memmove(void *dest, const void *src, size_t n, + dfsan_label dest_label, dfsan_label src_label, + dfsan_label n_label, dfsan_label *ret_label) { + *ret_label = dest_label; + return dfsan_memmove(dest, src, n); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void *__dfso_memmove(void *dest, const void *src, size_t n, + dfsan_label dest_label, dfsan_label src_label, + dfsan_label n_label, dfsan_label *ret_label, + dfsan_origin dest_origin, dfsan_origin src_origin, + dfsan_origin n_origin, dfsan_origin *ret_origin) { + *ret_label = dest_label; + *ret_origin = dest_origin; + return dfsan_memmove_with_origin(dest, src, n); +} + +SANITIZER_INTERFACE_ATTRIBUTE +void *__dfsw_memset(void *s, int c, size_t n, + dfsan_label s_label, dfsan_label c_label, + dfsan_label n_label, dfsan_label *ret_label) { + dfsan_memset(s, c, c_label, n); + *ret_label = s_label; + return s; +} + +SANITIZER_INTERFACE_ATTRIBUTE +void *__dfso_memset(void *s, int c, size_t n, dfsan_label s_label, + dfsan_label c_label, dfsan_label n_label, + dfsan_label *ret_label, dfsan_origin s_origin, + dfsan_origin c_origin, dfsan_origin n_origin, + dfsan_origin *ret_origin) { + dfsan_memset_with_origin(s, c, c_label, c_origin, n); + *ret_label = s_label; + *ret_origin = s_origin; + return s; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfsw_strcat(char *dest, const char *src, + dfsan_label dest_label, + dfsan_label src_label, + dfsan_label *ret_label) { + size_t dest_len = strlen(dest); + char *ret = strcat(dest, src); + dfsan_mem_shadow_transfer(dest + dest_len, src, strlen(src)); + *ret_label = dest_label; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strcat( + char *dest, const char *src, dfsan_label dest_label, dfsan_label src_label, + dfsan_label *ret_label, dfsan_origin dest_origin, dfsan_origin src_origin, + dfsan_origin *ret_origin) { + size_t dest_len = strlen(dest); + char *ret = strcat(dest, src); + size_t src_len = strlen(src); + dfsan_mem_origin_transfer(dest + dest_len, src, src_len); + dfsan_mem_shadow_transfer(dest + dest_len, src, src_len); + *ret_label = dest_label; + *ret_origin = dest_origin; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfsw_strncat( + char *dest, const char *src, size_t num, dfsan_label dest_label, + dfsan_label src_label, dfsan_label num_label, dfsan_label *ret_label) { + size_t src_len = strlen(src); + src_len = src_len < num ? src_len : num; + size_t dest_len = strlen(dest); + + char *ret = strncat(dest, src, num); + dfsan_mem_shadow_transfer(dest + dest_len, src, src_len); + *ret_label = dest_label; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strncat( + char *dest, const char *src, size_t num, dfsan_label dest_label, + dfsan_label src_label, dfsan_label num_label, dfsan_label *ret_label, + dfsan_origin dest_origin, dfsan_origin src_origin, dfsan_origin num_origin, + dfsan_origin *ret_origin) { + size_t src_len = strlen(src); + src_len = src_len < num ? src_len : num; + size_t dest_len = strlen(dest); + + char *ret = strncat(dest, src, num); + + dfsan_mem_origin_transfer(dest + dest_len, src, src_len); + dfsan_mem_shadow_transfer(dest + dest_len, src, src_len); + *ret_label = dest_label; + *ret_origin = dest_origin; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char * +__dfsw_strdup(const char *s, dfsan_label s_label, dfsan_label *ret_label) { + size_t len = strlen(s); + void *p = malloc(len+1); + dfsan_memcpy(p, s, len+1); + *ret_label = 0; + return static_cast<char *>(p); +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strdup(const char *s, + dfsan_label s_label, + dfsan_label *ret_label, + dfsan_origin s_origin, + dfsan_origin *ret_origin) { + size_t len = strlen(s); + void *p = malloc(len + 1); + dfsan_memcpy_with_origin(p, s, len + 1); + *ret_label = 0; + return static_cast<char *>(p); +} + +SANITIZER_INTERFACE_ATTRIBUTE char * +__dfsw_strncpy(char *s1, const char *s2, size_t n, dfsan_label s1_label, + dfsan_label s2_label, dfsan_label n_label, + dfsan_label *ret_label) { + size_t len = strlen(s2); + if (len < n) { + dfsan_memcpy(s1, s2, len+1); + dfsan_memset(s1+len+1, 0, 0, n-len-1); + } else { + dfsan_memcpy(s1, s2, n); + } + + *ret_label = s1_label; + return s1; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strncpy( + char *s1, const char *s2, size_t n, dfsan_label s1_label, + dfsan_label s2_label, dfsan_label n_label, dfsan_label *ret_label, + dfsan_origin s1_origin, dfsan_origin s2_origin, dfsan_origin n_origin, + dfsan_origin *ret_origin) { + size_t len = strlen(s2); + if (len < n) { + dfsan_memcpy_with_origin(s1, s2, len + 1); + dfsan_memset_with_origin(s1 + len + 1, 0, 0, 0, n - len - 1); + } else { + dfsan_memcpy_with_origin(s1, s2, n); + } + + *ret_label = s1_label; + *ret_origin = s1_origin; + return s1; +} + +SANITIZER_INTERFACE_ATTRIBUTE ssize_t +__dfsw_pread(int fd, void *buf, size_t count, off_t offset, + dfsan_label fd_label, dfsan_label buf_label, + dfsan_label count_label, dfsan_label offset_label, + dfsan_label *ret_label) { + ssize_t ret = pread(fd, buf, count, offset); + if (ret > 0) + dfsan_set_label(0, buf, ret); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE ssize_t __dfso_pread( + int fd, void *buf, size_t count, off_t offset, dfsan_label fd_label, + dfsan_label buf_label, dfsan_label count_label, dfsan_label offset_label, + dfsan_label *ret_label, dfsan_origin fd_origin, dfsan_origin buf_origin, + dfsan_origin count_origin, dfsan_label offset_origin, + dfsan_origin *ret_origin) { + return __dfsw_pread(fd, buf, count, offset, fd_label, buf_label, count_label, + offset_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE ssize_t +__dfsw_read(int fd, void *buf, size_t count, + dfsan_label fd_label, dfsan_label buf_label, + dfsan_label count_label, + dfsan_label *ret_label) { + ssize_t ret = read(fd, buf, count); + if (ret > 0) + dfsan_set_label(0, buf, ret); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE ssize_t __dfso_read( + int fd, void *buf, size_t count, dfsan_label fd_label, + dfsan_label buf_label, dfsan_label count_label, dfsan_label *ret_label, + dfsan_origin fd_origin, dfsan_origin buf_origin, dfsan_origin count_origin, + dfsan_origin *ret_origin) { + return __dfsw_read(fd, buf, count, fd_label, buf_label, count_label, + ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_clock_gettime(clockid_t clk_id, + struct timespec *tp, + dfsan_label clk_id_label, + dfsan_label tp_label, + dfsan_label *ret_label) { + int ret = clock_gettime(clk_id, tp); + if (ret == 0) + dfsan_set_label(0, tp, sizeof(struct timespec)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_clock_gettime( + clockid_t clk_id, struct timespec *tp, dfsan_label clk_id_label, + dfsan_label tp_label, dfsan_label *ret_label, dfsan_origin clk_id_origin, + dfsan_origin tp_origin, dfsan_origin *ret_origin) { + return __dfsw_clock_gettime(clk_id, tp, clk_id_label, tp_label, ret_label); +} + +static void dfsan_set_zero_label(const void *ptr, uptr size) { + dfsan_set_label(0, const_cast<void *>(ptr), size); +} + +// dlopen() ultimately calls mmap() down inside the loader, which generally +// doesn't participate in dynamic symbol resolution. Therefore we won't +// intercept its calls to mmap, and we have to hook it here. +SANITIZER_INTERFACE_ATTRIBUTE void * +__dfsw_dlopen(const char *filename, int flag, dfsan_label filename_label, + dfsan_label flag_label, dfsan_label *ret_label) { + void *handle = dlopen(filename, flag); + link_map *map = GET_LINK_MAP_BY_DLOPEN_HANDLE(handle); + if (filename && map) + ForEachMappedRegion(map, dfsan_set_zero_label); + *ret_label = 0; + return handle; +} + +SANITIZER_INTERFACE_ATTRIBUTE void *__dfso_dlopen( + const char *filename, int flag, dfsan_label filename_label, + dfsan_label flag_label, dfsan_label *ret_label, + dfsan_origin filename_origin, dfsan_origin flag_origin, + dfsan_origin *ret_origin) { + return __dfsw_dlopen(filename, flag, filename_label, flag_label, ret_label); +} + +static void *DFsanThreadStartFunc(void *arg) { + DFsanThread *t = (DFsanThread *)arg; + SetCurrentThread(t); + t->Init(); + SetSigProcMask(&t->starting_sigset_, nullptr); + return t->ThreadStart(); +} + +static int dfsan_pthread_create(pthread_t *thread, const pthread_attr_t *attr, + void *start_routine, void *arg, + dfsan_label *ret_label, + bool track_origins = false) { + pthread_attr_t myattr; + if (!attr) { + pthread_attr_init(&myattr); + attr = &myattr; + } + + // Ensure that the thread stack is large enough to hold all TLS data. + AdjustStackSize((void *)(const_cast<pthread_attr_t *>(attr))); + + DFsanThread *t = + DFsanThread::Create((thread_callback_t)start_routine, arg, track_origins); + ScopedBlockSignals block(&t->starting_sigset_); + int res = pthread_create(thread, attr, DFsanThreadStartFunc, t); + + if (attr == &myattr) + pthread_attr_destroy(&myattr); + *ret_label = 0; + return res; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_pthread_create( + pthread_t *thread, const pthread_attr_t *attr, void *start_routine, + void *arg, dfsan_label thread_label, dfsan_label attr_label, + dfsan_label start_routine_label, dfsan_label arg_label, + dfsan_label *ret_label) { + return dfsan_pthread_create(thread, attr, start_routine, arg, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_pthread_create( + pthread_t *thread, const pthread_attr_t *attr, void *start_routine, + void *arg, dfsan_label thread_label, dfsan_label attr_label, + dfsan_label start_routine_label, dfsan_label arg_label, + dfsan_label *ret_label, dfsan_origin thread_origin, + dfsan_origin attr_origin, dfsan_origin start_routine_origin, + dfsan_origin arg_origin, dfsan_origin *ret_origin) { + return dfsan_pthread_create(thread, attr, start_routine, arg, ret_label, + true); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_pthread_join(pthread_t thread, + void **retval, + dfsan_label thread_label, + dfsan_label retval_label, + dfsan_label *ret_label) { + int ret = pthread_join(thread, retval); + if (ret == 0 && retval) + dfsan_set_label(0, retval, sizeof(*retval)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_pthread_join( + pthread_t thread, void **retval, dfsan_label thread_label, + dfsan_label retval_label, dfsan_label *ret_label, + dfsan_origin thread_origin, dfsan_origin retval_origin, + dfsan_origin *ret_origin) { + return __dfsw_pthread_join(thread, retval, thread_label, retval_label, + ret_label); +} + +struct dl_iterate_phdr_info { + int (*callback)(struct dl_phdr_info *info, size_t size, void *data); + void *data; +}; + +int dl_iterate_phdr_cb(struct dl_phdr_info *info, size_t size, void *data) { + dl_iterate_phdr_info *dipi = (dl_iterate_phdr_info *)data; + dfsan_set_label(0, *info); + dfsan_set_label(0, const_cast<char *>(info->dlpi_name), + strlen(info->dlpi_name) + 1); + dfsan_set_label( + 0, const_cast<char *>(reinterpret_cast<const char *>(info->dlpi_phdr)), + sizeof(*info->dlpi_phdr) * info->dlpi_phnum); + + dfsan_clear_thread_local_state(); + return dipi->callback(info, size, dipi->data); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_dl_iterate_phdr( + int (*callback)(struct dl_phdr_info *info, size_t size, void *data), + void *data, dfsan_label callback_label, dfsan_label data_label, + dfsan_label *ret_label) { + dl_iterate_phdr_info dipi = {callback, data}; + *ret_label = 0; + return dl_iterate_phdr(dl_iterate_phdr_cb, &dipi); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_dl_iterate_phdr( + int (*callback)(struct dl_phdr_info *info, size_t size, void *data), + void *data, dfsan_label callback_label, dfsan_label data_label, + dfsan_label *ret_label, dfsan_origin callback_origin, + dfsan_origin data_origin, dfsan_origin *ret_origin) { + dl_iterate_phdr_info dipi = {callback, data}; + *ret_label = 0; + return dl_iterate_phdr(dl_iterate_phdr_cb, &dipi); +} + +// This function is only available for glibc 2.27 or newer. Mark it weak so +// linking succeeds with older glibcs. +SANITIZER_WEAK_ATTRIBUTE void _dl_get_tls_static_info(size_t *sizep, + size_t *alignp); + +SANITIZER_INTERFACE_ATTRIBUTE void __dfsw__dl_get_tls_static_info( + size_t *sizep, size_t *alignp, dfsan_label sizep_label, + dfsan_label alignp_label) { + assert(_dl_get_tls_static_info); + _dl_get_tls_static_info(sizep, alignp); + dfsan_set_label(0, sizep, sizeof(*sizep)); + dfsan_set_label(0, alignp, sizeof(*alignp)); +} + +SANITIZER_INTERFACE_ATTRIBUTE void __dfso__dl_get_tls_static_info( + size_t *sizep, size_t *alignp, dfsan_label sizep_label, + dfsan_label alignp_label, dfsan_origin sizep_origin, + dfsan_origin alignp_origin) { + __dfsw__dl_get_tls_static_info(sizep, alignp, sizep_label, alignp_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfsw_ctime_r(const time_t *timep, char *buf, dfsan_label timep_label, + dfsan_label buf_label, dfsan_label *ret_label) { + char *ret = ctime_r(timep, buf); + if (ret) { + dfsan_set_label(dfsan_read_label(timep, sizeof(time_t)), buf, + strlen(buf) + 1); + *ret_label = buf_label; + } else { + *ret_label = 0; + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfso_ctime_r(const time_t *timep, char *buf, dfsan_label timep_label, + dfsan_label buf_label, dfsan_label *ret_label, + dfsan_origin timep_origin, dfsan_origin buf_origin, + dfsan_origin *ret_origin) { + char *ret = ctime_r(timep, buf); + if (ret) { + dfsan_set_label_origin( + dfsan_read_label(timep, sizeof(time_t)), + dfsan_read_origin_of_first_taint(timep, sizeof(time_t)), buf, + strlen(buf) + 1); + *ret_label = buf_label; + *ret_origin = buf_origin; + } else { + *ret_label = 0; + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfsw_fgets(char *s, int size, FILE *stream, dfsan_label s_label, + dfsan_label size_label, dfsan_label stream_label, + dfsan_label *ret_label) { + char *ret = fgets(s, size, stream); + if (ret) { + dfsan_set_label(0, ret, strlen(ret) + 1); + *ret_label = s_label; + } else { + *ret_label = 0; + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfso_fgets(char *s, int size, FILE *stream, dfsan_label s_label, + dfsan_label size_label, dfsan_label stream_label, + dfsan_label *ret_label, dfsan_origin s_origin, + dfsan_origin size_origin, dfsan_origin stream_origin, + dfsan_origin *ret_origin) { + char *ret = __dfsw_fgets(s, size, stream, s_label, size_label, stream_label, + ret_label); + if (ret) + *ret_origin = s_origin; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfsw_getcwd(char *buf, size_t size, dfsan_label buf_label, + dfsan_label size_label, dfsan_label *ret_label) { + char *ret = getcwd(buf, size); + if (ret) { + dfsan_set_label(0, ret, strlen(ret) + 1); + *ret_label = buf_label; + } else { + *ret_label = 0; + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfso_getcwd(char *buf, size_t size, dfsan_label buf_label, + dfsan_label size_label, dfsan_label *ret_label, + dfsan_origin buf_origin, dfsan_origin size_origin, + dfsan_origin *ret_origin) { + char *ret = __dfsw_getcwd(buf, size, buf_label, size_label, ret_label); + if (ret) + *ret_origin = buf_origin; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfsw_get_current_dir_name(dfsan_label *ret_label) { + char *ret = get_current_dir_name(); + if (ret) + dfsan_set_label(0, ret, strlen(ret) + 1); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfso_get_current_dir_name(dfsan_label *ret_label, + dfsan_origin *ret_origin) { + return __dfsw_get_current_dir_name(ret_label); +} + +// This function is only available for glibc 2.25 or newer. Mark it weak so +// linking succeeds with older glibcs. +SANITIZER_WEAK_ATTRIBUTE int getentropy(void *buffer, size_t length); + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_getentropy(void *buffer, size_t length, + dfsan_label buffer_label, + dfsan_label length_label, + dfsan_label *ret_label) { + int ret = getentropy(buffer, length); + if (ret == 0) { + dfsan_set_label(0, buffer, length); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_getentropy(void *buffer, size_t length, + dfsan_label buffer_label, + dfsan_label length_label, + dfsan_label *ret_label, + dfsan_origin buffer_origin, + dfsan_origin length_origin, + dfsan_origin *ret_origin) { + return __dfsw_getentropy(buffer, length, buffer_label, length_label, + ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_gethostname(char *name, size_t len, dfsan_label name_label, + dfsan_label len_label, dfsan_label *ret_label) { + int ret = gethostname(name, len); + if (ret == 0) { + dfsan_set_label(0, name, strlen(name) + 1); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_gethostname(char *name, size_t len, dfsan_label name_label, + dfsan_label len_label, dfsan_label *ret_label, + dfsan_origin name_origin, dfsan_origin len_origin, + dfsan_label *ret_origin) { + return __dfsw_gethostname(name, len, name_label, len_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_getrlimit(int resource, struct rlimit *rlim, + dfsan_label resource_label, dfsan_label rlim_label, + dfsan_label *ret_label) { + int ret = getrlimit(resource, rlim); + if (ret == 0) { + dfsan_set_label(0, rlim, sizeof(struct rlimit)); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_getrlimit(int resource, struct rlimit *rlim, + dfsan_label resource_label, dfsan_label rlim_label, + dfsan_label *ret_label, dfsan_origin resource_origin, + dfsan_origin rlim_origin, dfsan_origin *ret_origin) { + return __dfsw_getrlimit(resource, rlim, resource_label, rlim_label, + ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_getrusage(int who, struct rusage *usage, dfsan_label who_label, + dfsan_label usage_label, dfsan_label *ret_label) { + int ret = getrusage(who, usage); + if (ret == 0) { + dfsan_set_label(0, usage, sizeof(struct rusage)); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_getrusage(int who, struct rusage *usage, dfsan_label who_label, + dfsan_label usage_label, dfsan_label *ret_label, + dfsan_origin who_origin, dfsan_origin usage_origin, + dfsan_label *ret_origin) { + return __dfsw_getrusage(who, usage, who_label, usage_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfsw_strcpy(char *dest, const char *src, dfsan_label dst_label, + dfsan_label src_label, dfsan_label *ret_label) { + char *ret = strcpy(dest, src); + if (ret) { + dfsan_mem_shadow_transfer(dest, src, strlen(src) + 1); + } + *ret_label = dst_label; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +char *__dfso_strcpy(char *dest, const char *src, dfsan_label dst_label, + dfsan_label src_label, dfsan_label *ret_label, + dfsan_origin dst_origin, dfsan_origin src_origin, + dfsan_origin *ret_origin) { + char *ret = strcpy(dest, src); + if (ret) { + size_t str_len = strlen(src) + 1; + dfsan_mem_origin_transfer(dest, src, str_len); + dfsan_mem_shadow_transfer(dest, src, str_len); + } + *ret_label = dst_label; + *ret_origin = dst_origin; + return ret; +} +} + +template <typename Fn> +static ALWAYS_INLINE auto dfsan_strtol_impl( + Fn real, const char *nptr, char **endptr, int base, + char **tmp_endptr) -> decltype(real(nullptr, nullptr, 0)) { + assert(tmp_endptr); + auto ret = real(nptr, tmp_endptr, base); + if (endptr) + *endptr = *tmp_endptr; + return ret; +} + +extern "C" { +static void dfsan_strtolong_label(const char *nptr, const char *tmp_endptr, + dfsan_label base_label, + dfsan_label *ret_label) { + if (tmp_endptr > nptr) { + // If *tmp_endptr is '\0' include its label as well. + *ret_label = dfsan_union( + base_label, + dfsan_read_label(nptr, tmp_endptr - nptr + (*tmp_endptr ? 0 : 1))); + } else { + *ret_label = 0; + } +} + +static void dfsan_strtolong_origin(const char *nptr, const char *tmp_endptr, + dfsan_label base_label, + dfsan_label *ret_label, + dfsan_origin base_origin, + dfsan_origin *ret_origin) { + if (tmp_endptr > nptr) { + // When multiple inputs are tainted, we propagate one of its origins. + // Because checking if base_label is tainted does not need additional + // computation, we prefer to propagating base_origin. + *ret_origin = base_label + ? base_origin + : dfsan_read_origin_of_first_taint( + nptr, tmp_endptr - nptr + (*tmp_endptr ? 0 : 1)); + } +} + +static double dfsan_strtod(const char *nptr, char **endptr, char **tmp_endptr) { + assert(tmp_endptr); + double ret = strtod(nptr, tmp_endptr); + if (endptr) + *endptr = *tmp_endptr; + return ret; +} + +static void dfsan_strtod_label(const char *nptr, const char *tmp_endptr, + dfsan_label *ret_label) { + if (tmp_endptr > nptr) { + // If *tmp_endptr is '\0' include its label as well. + *ret_label = dfsan_read_label( + nptr, + tmp_endptr - nptr + (*tmp_endptr ? 0 : 1)); + } else { + *ret_label = 0; + } +} + +SANITIZER_INTERFACE_ATTRIBUTE +double __dfsw_strtod(const char *nptr, char **endptr, dfsan_label nptr_label, + dfsan_label endptr_label, dfsan_label *ret_label) { + char *tmp_endptr; + double ret = dfsan_strtod(nptr, endptr, &tmp_endptr); + dfsan_strtod_label(nptr, tmp_endptr, ret_label); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +double __dfso_strtod(const char *nptr, char **endptr, dfsan_label nptr_label, + dfsan_label endptr_label, dfsan_label *ret_label, + dfsan_origin nptr_origin, dfsan_origin endptr_origin, + dfsan_origin *ret_origin) { + char *tmp_endptr; + double ret = dfsan_strtod(nptr, endptr, &tmp_endptr); + dfsan_strtod_label(nptr, tmp_endptr, ret_label); + if (tmp_endptr > nptr) { + // If *tmp_endptr is '\0' include its label as well. + *ret_origin = dfsan_read_origin_of_first_taint( + nptr, tmp_endptr - nptr + (*tmp_endptr ? 0 : 1)); + } else { + *ret_origin = 0; + } + return ret; +} + +WRAPPER_ALIAS(__isoc23_strtod, strtod) + +#define WRAPPER_STRTO(ret_type, fun) \ + SANITIZER_INTERFACE_ATTRIBUTE ret_type __dfsw_##fun( \ + const char *nptr, char **endptr, int base, dfsan_label nptr_label, \ + dfsan_label endptr_label, dfsan_label base_label, \ + dfsan_label *ret_label) { \ + char *tmp_endptr; \ + auto ret = dfsan_strtol_impl(fun, nptr, endptr, base, &tmp_endptr); \ + dfsan_strtolong_label(nptr, tmp_endptr, base_label, ret_label); \ + return ret; \ + } \ + SANITIZER_INTERFACE_ATTRIBUTE ret_type __dfso_##fun( \ + const char *nptr, char **endptr, int base, dfsan_label nptr_label, \ + dfsan_label endptr_label, dfsan_label base_label, \ + dfsan_label *ret_label, dfsan_origin nptr_origin, \ + dfsan_origin endptr_origin, dfsan_origin base_origin, \ + dfsan_origin *ret_origin) { \ + char *tmp_endptr; \ + auto ret = dfsan_strtol_impl(fun, nptr, endptr, base, &tmp_endptr); \ + dfsan_strtolong_label(nptr, tmp_endptr, base_label, ret_label); \ + dfsan_strtolong_origin(nptr, tmp_endptr, base_label, ret_label, \ + base_origin, ret_origin); \ + return ret; \ + } + +WRAPPER_STRTO(long, strtol) +WRAPPER_STRTO(long long, strtoll) +WRAPPER_STRTO(unsigned long, strtoul) +WRAPPER_STRTO(unsigned long long, strtoull) +WRAPPER_ALIAS(__isoc23_strtol, strtol) +WRAPPER_ALIAS(__isoc23_strtoll, strtoll) +WRAPPER_ALIAS(__isoc23_strtoul, strtoul) +WRAPPER_ALIAS(__isoc23_strtoull, strtoull) + +SANITIZER_INTERFACE_ATTRIBUTE +time_t __dfsw_time(time_t *t, dfsan_label t_label, dfsan_label *ret_label) { + time_t ret = time(t); + if (ret != (time_t) -1 && t) { + dfsan_set_label(0, t, sizeof(time_t)); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +time_t __dfso_time(time_t *t, dfsan_label t_label, dfsan_label *ret_label, + dfsan_origin t_origin, dfsan_origin *ret_origin) { + return __dfsw_time(t, t_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_inet_pton(int af, const char *src, void *dst, dfsan_label af_label, + dfsan_label src_label, dfsan_label dst_label, + dfsan_label *ret_label) { + int ret = inet_pton(af, src, dst); + if (ret == 1) { + dfsan_set_label(dfsan_read_label(src, strlen(src) + 1), dst, + af == AF_INET ? sizeof(struct in_addr) : sizeof(in6_addr)); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_inet_pton(int af, const char *src, void *dst, dfsan_label af_label, + dfsan_label src_label, dfsan_label dst_label, + dfsan_label *ret_label, dfsan_origin af_origin, + dfsan_origin src_origin, dfsan_origin dst_origin, + dfsan_origin *ret_origin) { + int ret = inet_pton(af, src, dst); + if (ret == 1) { + int src_len = strlen(src) + 1; + dfsan_set_label_origin( + dfsan_read_label(src, src_len), + dfsan_read_origin_of_first_taint(src, src_len), dst, + af == AF_INET ? sizeof(struct in_addr) : sizeof(in6_addr)); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +struct tm *__dfsw_localtime_r(const time_t *timep, struct tm *result, + dfsan_label timep_label, dfsan_label result_label, + dfsan_label *ret_label) { + struct tm *ret = localtime_r(timep, result); + if (ret) { + dfsan_set_label(dfsan_read_label(timep, sizeof(time_t)), result, + sizeof(struct tm)); + *ret_label = result_label; + } else { + *ret_label = 0; + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +struct tm *__dfso_localtime_r(const time_t *timep, struct tm *result, + dfsan_label timep_label, dfsan_label result_label, + dfsan_label *ret_label, dfsan_origin timep_origin, + dfsan_origin result_origin, + dfsan_origin *ret_origin) { + struct tm *ret = localtime_r(timep, result); + if (ret) { + dfsan_set_label_origin( + dfsan_read_label(timep, sizeof(time_t)), + dfsan_read_origin_of_first_taint(timep, sizeof(time_t)), result, + sizeof(struct tm)); + *ret_label = result_label; + *ret_origin = result_origin; + } else { + *ret_label = 0; + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_getpwuid_r(id_t uid, struct passwd *pwd, + char *buf, size_t buflen, struct passwd **result, + dfsan_label uid_label, dfsan_label pwd_label, + dfsan_label buf_label, dfsan_label buflen_label, + dfsan_label result_label, dfsan_label *ret_label) { + // Store the data in pwd, the strings referenced from pwd in buf, and the + // address of pwd in *result. On failure, NULL is stored in *result. + int ret = getpwuid_r(uid, pwd, buf, buflen, result); + if (ret == 0) { + dfsan_set_label(0, pwd, sizeof(struct passwd)); + dfsan_set_label(0, buf, strlen(buf) + 1); + } + *ret_label = 0; + dfsan_set_label(0, result, sizeof(struct passwd*)); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_getpwuid_r(id_t uid, struct passwd *pwd, char *buf, size_t buflen, + struct passwd **result, dfsan_label uid_label, + dfsan_label pwd_label, dfsan_label buf_label, + dfsan_label buflen_label, dfsan_label result_label, + dfsan_label *ret_label, dfsan_origin uid_origin, + dfsan_origin pwd_origin, dfsan_origin buf_origin, + dfsan_origin buflen_origin, dfsan_origin result_origin, + dfsan_origin *ret_origin) { + return __dfsw_getpwuid_r(uid, pwd, buf, buflen, result, uid_label, pwd_label, + buf_label, buflen_label, result_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_epoll_wait(int epfd, struct epoll_event *events, int maxevents, + int timeout, dfsan_label epfd_label, + dfsan_label events_label, dfsan_label maxevents_label, + dfsan_label timeout_label, dfsan_label *ret_label) { + int ret = epoll_wait(epfd, events, maxevents, timeout); + if (ret > 0) + dfsan_set_label(0, events, ret * sizeof(*events)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_epoll_wait(int epfd, struct epoll_event *events, int maxevents, + int timeout, dfsan_label epfd_label, + dfsan_label events_label, dfsan_label maxevents_label, + dfsan_label timeout_label, dfsan_label *ret_label, + dfsan_origin epfd_origin, dfsan_origin events_origin, + dfsan_origin maxevents_origin, + dfsan_origin timeout_origin, dfsan_origin *ret_origin) { + return __dfsw_epoll_wait(epfd, events, maxevents, timeout, epfd_label, + events_label, maxevents_label, timeout_label, + ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_poll(struct pollfd *fds, nfds_t nfds, int timeout, + dfsan_label dfs_label, dfsan_label nfds_label, + dfsan_label timeout_label, dfsan_label *ret_label) { + int ret = poll(fds, nfds, timeout); + if (ret >= 0) { + for (; nfds > 0; --nfds) { + dfsan_set_label(0, &fds[nfds - 1].revents, sizeof(fds[nfds - 1].revents)); + } + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_poll(struct pollfd *fds, nfds_t nfds, int timeout, + dfsan_label dfs_label, dfsan_label nfds_label, + dfsan_label timeout_label, dfsan_label *ret_label, + dfsan_origin dfs_origin, dfsan_origin nfds_origin, + dfsan_origin timeout_origin, dfsan_origin *ret_origin) { + return __dfsw_poll(fds, nfds, timeout, dfs_label, nfds_label, timeout_label, + ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_select(int nfds, fd_set *readfds, fd_set *writefds, + fd_set *exceptfds, struct timeval *timeout, + dfsan_label nfds_label, dfsan_label readfds_label, + dfsan_label writefds_label, dfsan_label exceptfds_label, + dfsan_label timeout_label, dfsan_label *ret_label) { + int ret = select(nfds, readfds, writefds, exceptfds, timeout); + // Clear everything (also on error) since their content is either set or + // undefined. + if (readfds) { + dfsan_set_label(0, readfds, sizeof(fd_set)); + } + if (writefds) { + dfsan_set_label(0, writefds, sizeof(fd_set)); + } + if (exceptfds) { + dfsan_set_label(0, exceptfds, sizeof(fd_set)); + } + dfsan_set_label(0, timeout, sizeof(struct timeval)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_select(int nfds, fd_set *readfds, fd_set *writefds, + fd_set *exceptfds, struct timeval *timeout, + dfsan_label nfds_label, dfsan_label readfds_label, + dfsan_label writefds_label, dfsan_label exceptfds_label, + dfsan_label timeout_label, dfsan_label *ret_label, + dfsan_origin nfds_origin, dfsan_origin readfds_origin, + dfsan_origin writefds_origin, dfsan_origin exceptfds_origin, + dfsan_origin timeout_origin, dfsan_origin *ret_origin) { + return __dfsw_select(nfds, readfds, writefds, exceptfds, timeout, nfds_label, + readfds_label, writefds_label, exceptfds_label, + timeout_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_sched_getaffinity(pid_t pid, size_t cpusetsize, cpu_set_t *mask, + dfsan_label pid_label, + dfsan_label cpusetsize_label, + dfsan_label mask_label, dfsan_label *ret_label) { + int ret = sched_getaffinity(pid, cpusetsize, mask); + if (ret == 0) { + dfsan_set_label(0, mask, cpusetsize); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_sched_getaffinity(pid_t pid, size_t cpusetsize, cpu_set_t *mask, + dfsan_label pid_label, + dfsan_label cpusetsize_label, + dfsan_label mask_label, dfsan_label *ret_label, + dfsan_origin pid_origin, + dfsan_origin cpusetsize_origin, + dfsan_origin mask_origin, + dfsan_origin *ret_origin) { + return __dfsw_sched_getaffinity(pid, cpusetsize, mask, pid_label, + cpusetsize_label, mask_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_sigemptyset(sigset_t *set, dfsan_label set_label, + dfsan_label *ret_label) { + int ret = sigemptyset(set); + dfsan_set_label(0, set, sizeof(sigset_t)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_sigemptyset(sigset_t *set, dfsan_label set_label, + dfsan_label *ret_label, dfsan_origin set_origin, + dfsan_origin *ret_origin) { + return __dfsw_sigemptyset(set, set_label, ret_label); +} + +class SignalHandlerScope { + public: + SignalHandlerScope() { + if (DFsanThread *t = GetCurrentThread()) + t->EnterSignalHandler(); + } + ~SignalHandlerScope() { + if (DFsanThread *t = GetCurrentThread()) + t->LeaveSignalHandler(); + } +}; + +// Clear DFSan runtime TLS state at the end of a scope. +// +// Implementation must be async-signal-safe and use small data size, because +// instances of this class may live on the signal handler stack. +// +// DFSan uses TLS to pass metadata of arguments and return values. When an +// instrumented function accesses the TLS, if a signal callback happens, and the +// callback calls other instrumented functions with updating the same TLS, the +// TLS is in an inconsistent state after the callback ends. This may cause +// either under-tainting or over-tainting. +// +// The current implementation simply resets TLS at restore. This prevents from +// over-tainting. Although under-tainting may still happen, a taint flow can be +// found eventually if we run a DFSan-instrumented program multiple times. The +// alternative option is saving the entire TLS. However the TLS storage takes +// 2k bytes, and signal calls could be nested. So it does not seem worth. +class ScopedClearThreadLocalState { + public: + ScopedClearThreadLocalState() {} + ~ScopedClearThreadLocalState() { dfsan_clear_thread_local_state(); } +}; + +// SignalSpinLocker::sigactions_mu guarantees atomicity of sigaction() calls. +const int kMaxSignals = 1024; +static atomic_uintptr_t sigactions[kMaxSignals]; + +static void SignalHandler(int signo) { + SignalHandlerScope signal_handler_scope; + ScopedClearThreadLocalState scoped_clear_tls; + + // Clear shadows for all inputs provided by system. + dfsan_clear_arg_tls(0, sizeof(dfsan_label)); + + typedef void (*signal_cb)(int x); + signal_cb cb = + (signal_cb)atomic_load(&sigactions[signo], memory_order_relaxed); + cb(signo); +} + +static void SignalAction(int signo, siginfo_t *si, void *uc) { + SignalHandlerScope signal_handler_scope; + ScopedClearThreadLocalState scoped_clear_tls; + + // Clear shadows for all inputs provided by system. Similar to SignalHandler. + dfsan_clear_arg_tls(0, 3 * sizeof(dfsan_label)); + dfsan_set_label(0, si, sizeof(*si)); + dfsan_set_label(0, uc, sizeof(ucontext_t)); + + typedef void (*sigaction_cb)(int, siginfo_t *, void *); + sigaction_cb cb = + (sigaction_cb)atomic_load(&sigactions[signo], memory_order_relaxed); + cb(signo, si, uc); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_sigaction(int signum, const struct sigaction *act, + struct sigaction *oldact, dfsan_label signum_label, + dfsan_label act_label, dfsan_label oldact_label, + dfsan_label *ret_label) { + CHECK_LT(signum, kMaxSignals); + SignalSpinLocker lock; + uptr old_cb = atomic_load(&sigactions[signum], memory_order_relaxed); + struct sigaction new_act; + struct sigaction *pnew_act = act ? &new_act : nullptr; + if (act) { + internal_memcpy(pnew_act, act, sizeof(struct sigaction)); + if (pnew_act->sa_flags & SA_SIGINFO) { + uptr cb = (uptr)(pnew_act->sa_sigaction); + if (cb != (uptr)SIG_IGN && cb != (uptr)SIG_DFL) { + atomic_store(&sigactions[signum], cb, memory_order_relaxed); + pnew_act->sa_sigaction = SignalAction; + } + } else { + uptr cb = (uptr)(pnew_act->sa_handler); + if (cb != (uptr)SIG_IGN && cb != (uptr)SIG_DFL) { + atomic_store(&sigactions[signum], cb, memory_order_relaxed); + pnew_act->sa_handler = SignalHandler; + } + } + } + + int ret = sigaction(signum, pnew_act, oldact); + + if (ret == 0 && oldact) { + if (oldact->sa_flags & SA_SIGINFO) { + if (oldact->sa_sigaction == SignalAction) + oldact->sa_sigaction = (decltype(oldact->sa_sigaction))old_cb; + } else { + if (oldact->sa_handler == SignalHandler) + oldact->sa_handler = (decltype(oldact->sa_handler))old_cb; + } + } + + if (oldact) { + dfsan_set_label(0, oldact, sizeof(struct sigaction)); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_sigaction(int signum, const struct sigaction *act, + struct sigaction *oldact, dfsan_label signum_label, + dfsan_label act_label, dfsan_label oldact_label, + dfsan_label *ret_label, dfsan_origin signum_origin, + dfsan_origin act_origin, dfsan_origin oldact_origin, + dfsan_origin *ret_origin) { + return __dfsw_sigaction(signum, act, oldact, signum_label, act_label, + oldact_label, ret_label); +} + +static sighandler_t dfsan_signal(int signum, sighandler_t handler, + dfsan_label *ret_label) { + CHECK_LT(signum, kMaxSignals); + SignalSpinLocker lock; + uptr old_cb = atomic_load(&sigactions[signum], memory_order_relaxed); + if (handler != SIG_IGN && handler != SIG_DFL) { + atomic_store(&sigactions[signum], (uptr)handler, memory_order_relaxed); + handler = &SignalHandler; + } + + sighandler_t ret = signal(signum, handler); + + if (ret == SignalHandler) + ret = (sighandler_t)old_cb; + + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +sighandler_t __dfsw_signal(int signum, sighandler_t handler, + dfsan_label signum_label, dfsan_label handler_label, + dfsan_label *ret_label) { + return dfsan_signal(signum, handler, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +sighandler_t __dfso_signal(int signum, sighandler_t handler, + dfsan_label signum_label, dfsan_label handler_label, + dfsan_label *ret_label, dfsan_origin signum_origin, + dfsan_origin handler_origin, + dfsan_origin *ret_origin) { + return dfsan_signal(signum, handler, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_sigaltstack(const stack_t *ss, stack_t *old_ss, dfsan_label ss_label, + dfsan_label old_ss_label, dfsan_label *ret_label) { + int ret = sigaltstack(ss, old_ss); + if (ret != -1 && old_ss) + dfsan_set_label(0, old_ss, sizeof(*old_ss)); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_sigaltstack(const stack_t *ss, stack_t *old_ss, dfsan_label ss_label, + dfsan_label old_ss_label, dfsan_label *ret_label, + dfsan_origin ss_origin, dfsan_origin old_ss_origin, + dfsan_origin *ret_origin) { + return __dfsw_sigaltstack(ss, old_ss, ss_label, old_ss_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_gettimeofday(struct timeval *tv, struct timezone *tz, + dfsan_label tv_label, dfsan_label tz_label, + dfsan_label *ret_label) { + int ret = gettimeofday(tv, tz); + if (tv) { + dfsan_set_label(0, tv, sizeof(struct timeval)); + } + if (tz) { + dfsan_set_label(0, tz, sizeof(struct timezone)); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_gettimeofday(struct timeval *tv, struct timezone *tz, + dfsan_label tv_label, dfsan_label tz_label, + dfsan_label *ret_label, dfsan_origin tv_origin, + dfsan_origin tz_origin, dfsan_origin *ret_origin) { + return __dfsw_gettimeofday(tv, tz, tv_label, tz_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE void *__dfsw_memchr(void *s, int c, size_t n, + dfsan_label s_label, + dfsan_label c_label, + dfsan_label n_label, + dfsan_label *ret_label) { + void *ret = memchr(s, c, n); + if (flags().strict_data_dependencies) { + *ret_label = ret ? s_label : 0; + } else { + size_t len = + ret ? reinterpret_cast<char *>(ret) - reinterpret_cast<char *>(s) + 1 + : n; + *ret_label = + dfsan_union(dfsan_read_label(s, len), dfsan_union(s_label, c_label)); + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE void *__dfso_memchr( + void *s, int c, size_t n, dfsan_label s_label, dfsan_label c_label, + dfsan_label n_label, dfsan_label *ret_label, dfsan_origin s_origin, + dfsan_origin c_origin, dfsan_origin n_origin, dfsan_origin *ret_origin) { + void *ret = __dfsw_memchr(s, c, n, s_label, c_label, n_label, ret_label); + if (flags().strict_data_dependencies) { + if (ret) + *ret_origin = s_origin; + } else { + size_t len = + ret ? reinterpret_cast<char *>(ret) - reinterpret_cast<char *>(s) + 1 + : n; + dfsan_origin o = dfsan_read_origin_of_first_taint(s, len); + *ret_origin = o ? o : (s_label ? s_origin : c_origin); + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfsw_strrchr(char *s, int c, + dfsan_label s_label, + dfsan_label c_label, + dfsan_label *ret_label) { + char *ret = strrchr(s, c); + if (flags().strict_data_dependencies) { + *ret_label = ret ? s_label : 0; + } else { + *ret_label = + dfsan_union(dfsan_read_label(s, strlen(s) + 1), + dfsan_union(s_label, c_label)); + } + + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strrchr( + char *s, int c, dfsan_label s_label, dfsan_label c_label, + dfsan_label *ret_label, dfsan_origin s_origin, dfsan_origin c_origin, + dfsan_origin *ret_origin) { + char *ret = __dfsw_strrchr(s, c, s_label, c_label, ret_label); + if (flags().strict_data_dependencies) { + if (ret) + *ret_origin = s_origin; + } else { + size_t s_len = strlen(s) + 1; + dfsan_origin o = dfsan_read_origin_of_first_taint(s, s_len); + *ret_origin = o ? o : (s_label ? s_origin : c_origin); + } + + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfsw_strstr(char *haystack, char *needle, + dfsan_label haystack_label, + dfsan_label needle_label, + dfsan_label *ret_label) { + char *ret = strstr(haystack, needle); + if (flags().strict_data_dependencies) { + *ret_label = ret ? haystack_label : 0; + } else { + size_t len = ret ? ret + strlen(needle) - haystack : strlen(haystack) + 1; + *ret_label = + dfsan_union(dfsan_read_label(haystack, len), + dfsan_union(dfsan_read_label(needle, strlen(needle) + 1), + dfsan_union(haystack_label, needle_label))); + } + + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE char *__dfso_strstr(char *haystack, char *needle, + dfsan_label haystack_label, + dfsan_label needle_label, + dfsan_label *ret_label, + dfsan_origin haystack_origin, + dfsan_origin needle_origin, + dfsan_origin *ret_origin) { + char *ret = + __dfsw_strstr(haystack, needle, haystack_label, needle_label, ret_label); + if (flags().strict_data_dependencies) { + if (ret) + *ret_origin = haystack_origin; + } else { + size_t needle_len = strlen(needle); + size_t len = ret ? ret + needle_len - haystack : strlen(haystack) + 1; + dfsan_origin o = dfsan_read_origin_of_first_taint(haystack, len); + if (o) { + *ret_origin = o; + } else { + o = dfsan_read_origin_of_first_taint(needle, needle_len + 1); + *ret_origin = o ? o : (haystack_label ? haystack_origin : needle_origin); + } + } + + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_nanosleep(const struct timespec *req, + struct timespec *rem, + dfsan_label req_label, + dfsan_label rem_label, + dfsan_label *ret_label) { + int ret = nanosleep(req, rem); + *ret_label = 0; + if (ret == -1) { + // Interrupted by a signal, rem is filled with the remaining time. + dfsan_set_label(0, rem, sizeof(struct timespec)); + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_nanosleep( + const struct timespec *req, struct timespec *rem, dfsan_label req_label, + dfsan_label rem_label, dfsan_label *ret_label, dfsan_origin req_origin, + dfsan_origin rem_origin, dfsan_origin *ret_origin) { + return __dfsw_nanosleep(req, rem, req_label, rem_label, ret_label); +} + +static void clear_msghdr_labels(size_t bytes_written, struct msghdr *msg, + int flags) { + dfsan_set_label(0, msg, sizeof(*msg)); + dfsan_set_label(0, msg->msg_name, msg->msg_namelen); + dfsan_set_label(0, msg->msg_control, msg->msg_controllen); + for (size_t i = 0; i < msg->msg_iovlen; ++i) { + struct iovec *iov = &msg->msg_iov[i]; + size_t iov_written = iov->iov_len; + + // When MSG_TRUNC is not set, we want to avoid setting 0 label on bytes that + // may not have changed, using bytes_written to bound the 0 label write. + // When MSG_TRUNC flag is set, bytes_written may be larger than the buffer, + // and should not be used as a bound. + if (!(MSG_TRUNC & flags)) { + if (bytes_written < iov->iov_len) { + iov_written = bytes_written; + } + bytes_written -= iov_written; + } + + dfsan_set_label(0, iov->iov_base, iov_written); + } +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_recvmmsg( + int sockfd, struct mmsghdr *msgvec, unsigned int vlen, int flags, + struct timespec *timeout, dfsan_label sockfd_label, + dfsan_label msgvec_label, dfsan_label vlen_label, dfsan_label flags_label, + dfsan_label timeout_label, dfsan_label *ret_label) { + int ret = recvmmsg(sockfd, msgvec, vlen, flags, timeout); + for (int i = 0; i < ret; ++i) { + dfsan_set_label(0, &msgvec[i].msg_len, sizeof(msgvec[i].msg_len)); + clear_msghdr_labels(msgvec[i].msg_len, &msgvec[i].msg_hdr, flags); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_recvmmsg( + int sockfd, struct mmsghdr *msgvec, unsigned int vlen, int flags, + struct timespec *timeout, dfsan_label sockfd_label, + dfsan_label msgvec_label, dfsan_label vlen_label, dfsan_label flags_label, + dfsan_label timeout_label, dfsan_label *ret_label, + dfsan_origin sockfd_origin, dfsan_origin msgvec_origin, + dfsan_origin vlen_origin, dfsan_origin flags_origin, + dfsan_origin timeout_origin, dfsan_origin *ret_origin) { + return __dfsw_recvmmsg(sockfd, msgvec, vlen, flags, timeout, sockfd_label, + msgvec_label, vlen_label, flags_label, timeout_label, + ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE ssize_t __dfsw_recvmsg( + int sockfd, struct msghdr *msg, int flags, dfsan_label sockfd_label, + dfsan_label msg_label, dfsan_label flags_label, dfsan_label *ret_label) { + ssize_t ret = recvmsg(sockfd, msg, flags); + if (ret >= 0) + clear_msghdr_labels(ret, msg, flags); + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE ssize_t __dfso_recvmsg( + int sockfd, struct msghdr *msg, int flags, dfsan_label sockfd_label, + dfsan_label msg_label, dfsan_label flags_label, dfsan_label *ret_label, + dfsan_origin sockfd_origin, dfsan_origin msg_origin, + dfsan_origin flags_origin, dfsan_origin *ret_origin) { + return __dfsw_recvmsg(sockfd, msg, flags, sockfd_label, msg_label, + flags_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int +__dfsw_socketpair(int domain, int type, int protocol, int sv[2], + dfsan_label domain_label, dfsan_label type_label, + dfsan_label protocol_label, dfsan_label sv_label, + dfsan_label *ret_label) { + int ret = socketpair(domain, type, protocol, sv); + *ret_label = 0; + if (ret == 0) { + dfsan_set_label(0, sv, sizeof(*sv) * 2); + } + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_socketpair( + int domain, int type, int protocol, int sv[2], dfsan_label domain_label, + dfsan_label type_label, dfsan_label protocol_label, dfsan_label sv_label, + dfsan_label *ret_label, dfsan_origin domain_origin, + dfsan_origin type_origin, dfsan_origin protocol_origin, + dfsan_origin sv_origin, dfsan_origin *ret_origin) { + return __dfsw_socketpair(domain, type, protocol, sv, domain_label, type_label, + protocol_label, sv_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_getsockopt( + int sockfd, int level, int optname, void *optval, socklen_t *optlen, + dfsan_label sockfd_label, dfsan_label level_label, + dfsan_label optname_label, dfsan_label optval_label, + dfsan_label optlen_label, dfsan_label *ret_label) { + int ret = getsockopt(sockfd, level, optname, optval, optlen); + if (ret != -1 && optval && optlen) { + dfsan_set_label(0, optlen, sizeof(*optlen)); + dfsan_set_label(0, optval, *optlen); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_getsockopt( + int sockfd, int level, int optname, void *optval, socklen_t *optlen, + dfsan_label sockfd_label, dfsan_label level_label, + dfsan_label optname_label, dfsan_label optval_label, + dfsan_label optlen_label, dfsan_label *ret_label, + dfsan_origin sockfd_origin, dfsan_origin level_origin, + dfsan_origin optname_origin, dfsan_origin optval_origin, + dfsan_origin optlen_origin, dfsan_origin *ret_origin) { + return __dfsw_getsockopt(sockfd, level, optname, optval, optlen, sockfd_label, + level_label, optname_label, optval_label, + optlen_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_getsockname( + int sockfd, struct sockaddr *addr, socklen_t *addrlen, + dfsan_label sockfd_label, dfsan_label addr_label, dfsan_label addrlen_label, + dfsan_label *ret_label) { + socklen_t origlen = addrlen ? *addrlen : 0; + int ret = getsockname(sockfd, addr, addrlen); + if (ret != -1 && addr && addrlen) { + socklen_t written_bytes = origlen < *addrlen ? origlen : *addrlen; + dfsan_set_label(0, addrlen, sizeof(*addrlen)); + dfsan_set_label(0, addr, written_bytes); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_getsockname( + int sockfd, struct sockaddr *addr, socklen_t *addrlen, + dfsan_label sockfd_label, dfsan_label addr_label, dfsan_label addrlen_label, + dfsan_label *ret_label, dfsan_origin sockfd_origin, + dfsan_origin addr_origin, dfsan_origin addrlen_origin, + dfsan_origin *ret_origin) { + return __dfsw_getsockname(sockfd, addr, addrlen, sockfd_label, addr_label, + addrlen_label, ret_label); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfsw_getpeername( + int sockfd, struct sockaddr *addr, socklen_t *addrlen, + dfsan_label sockfd_label, dfsan_label addr_label, dfsan_label addrlen_label, + dfsan_label *ret_label) { + socklen_t origlen = addrlen ? *addrlen : 0; + int ret = getpeername(sockfd, addr, addrlen); + if (ret != -1 && addr && addrlen) { + socklen_t written_bytes = origlen < *addrlen ? origlen : *addrlen; + dfsan_set_label(0, addrlen, sizeof(*addrlen)); + dfsan_set_label(0, addr, written_bytes); + } + *ret_label = 0; + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_getpeername( + int sockfd, struct sockaddr *addr, socklen_t *addrlen, + dfsan_label sockfd_label, dfsan_label addr_label, dfsan_label addrlen_label, + dfsan_label *ret_label, dfsan_origin sockfd_origin, + dfsan_origin addr_origin, dfsan_origin addrlen_origin, + dfsan_origin *ret_origin) { + return __dfsw_getpeername(sockfd, addr, addrlen, sockfd_label, addr_label, + addrlen_label, ret_label); +} + +// Type of the function passed to dfsan_set_write_callback. +typedef void (*write_dfsan_callback_t)(int fd, const void *buf, ssize_t count); + +// Calls to dfsan_set_write_callback() set the values in this struct. +// Calls to the custom version of write() read (and invoke) them. +static struct { + write_dfsan_callback_t write_callback = nullptr; +} write_callback_info; + +SANITIZER_INTERFACE_ATTRIBUTE void __dfsw_dfsan_set_write_callback( + write_dfsan_callback_t write_callback, dfsan_label write_callback_label, + dfsan_label *ret_label) { + write_callback_info.write_callback = write_callback; +} + +SANITIZER_INTERFACE_ATTRIBUTE void __dfso_dfsan_set_write_callback( + write_dfsan_callback_t write_callback, dfsan_label write_callback_label, + dfsan_label *ret_label, dfsan_origin write_callback_origin, + dfsan_origin *ret_origin) { + write_callback_info.write_callback = write_callback; +} + +static inline void setup_tls_args_for_write_callback( + dfsan_label fd_label, dfsan_label buf_label, dfsan_label count_label, + bool origins, dfsan_origin fd_origin, dfsan_origin buf_origin, + dfsan_origin count_origin) { + // The callback code will expect argument shadow labels in the args TLS, + // and origin labels in the origin args TLS. + // Previously this was done by a trampoline, but we want to remove this: + // https://github.com/llvm/llvm-project/issues/54172 + // + // Instead, this code is manually setting up the args TLS data. + // + // The offsets used need to correspond with the instrumentation code, + // see llvm/lib/Transforms/Instrumentation/DataFlowSanitizer.cpp + // DFSanFunction::getShadowForTLSArgument. + // https://github.com/llvm/llvm-project/blob/0acc9e4b5edd8b39ff3d4c6d0e17f02007671c4e/llvm/lib/Transforms/Instrumentation/DataFlowSanitizer.cpp#L1684 + // https://github.com/llvm/llvm-project/blob/0acc9e4b5edd8b39ff3d4c6d0e17f02007671c4e/llvm/lib/Transforms/Instrumentation/DataFlowSanitizer.cpp#L125 + // + // Here the arguments are all primitives, but it can be more complex + // to compute offsets for array/aggregate type arguments. + // + // TODO(browneee): Consider a builtin to improve maintainabliity. + // With a builtin, we would provide the argument labels via builtin, + // and the builtin would reuse parts of the instrumentation code to ensure + // that this code and the instrumentation can never be out of sync. + // Note: Currently DFSan instrumentation does not run on this code, so + // the builtin may need to be handled outside DFSan instrumentation. + dfsan_set_arg_tls(0, fd_label); + dfsan_set_arg_tls(1, buf_label); + dfsan_set_arg_tls(2, count_label); + if (origins) { + dfsan_set_arg_origin_tls(0, fd_origin); + dfsan_set_arg_origin_tls(1, buf_origin); + dfsan_set_arg_origin_tls(2, count_origin); + } +} + +SANITIZER_INTERFACE_ATTRIBUTE int +__dfsw_write(int fd, const void *buf, size_t count, + dfsan_label fd_label, dfsan_label buf_label, + dfsan_label count_label, dfsan_label *ret_label) { + if (write_callback_info.write_callback) { + setup_tls_args_for_write_callback(fd_label, buf_label, count_label, false, + 0, 0, 0); + write_callback_info.write_callback(fd, buf, count); + } + + *ret_label = 0; + return write(fd, buf, count); +} + +SANITIZER_INTERFACE_ATTRIBUTE int __dfso_write( + int fd, const void *buf, size_t count, dfsan_label fd_label, + dfsan_label buf_label, dfsan_label count_label, dfsan_label *ret_label, + dfsan_origin fd_origin, dfsan_origin buf_origin, dfsan_origin count_origin, + dfsan_origin *ret_origin) { + if (write_callback_info.write_callback) { + setup_tls_args_for_write_callback(fd_label, buf_label, count_label, true, + fd_origin, buf_origin, count_origin); + write_callback_info.write_callback(fd, buf, count); + } + + *ret_label = 0; + return write(fd, buf, count); +} +} // namespace __dfsan + +// Type used to extract a dfsan_label with va_arg() +typedef int dfsan_label_va; + +// Formats a chunk either a constant string or a single format directive (e.g., +// '%.3f'). +struct Formatter { + Formatter(char *str_, const char *fmt_, size_t size_) + : str(str_), + str_off(0), + size(size_), + fmt_start(fmt_), + fmt_cur(fmt_), + width(-1), + num_scanned(-1), + skip(false) {} + + int format() { + char *tmp_fmt = build_format_string(); + int retval = + snprintf(str + str_off, str_off < size ? size - str_off : 0, tmp_fmt, + 0 /* used only to avoid warnings */); + free(tmp_fmt); + return retval; + } + + template <typename T> int format(T arg) { + char *tmp_fmt = build_format_string(); + int retval; + if (width >= 0) { + retval = snprintf(str + str_off, str_off < size ? size - str_off : 0, + tmp_fmt, width, arg); + } else { + retval = snprintf(str + str_off, str_off < size ? size - str_off : 0, + tmp_fmt, arg); + } + free(tmp_fmt); + return retval; + } + + char *build_format_string() { + size_t fmt_size = fmt_cur - fmt_start + 1; + char *new_fmt = (char *)malloc(fmt_size + 1); + assert(new_fmt); + internal_memcpy(new_fmt, fmt_start, fmt_size); + new_fmt[fmt_size] = '\0'; + return new_fmt; + } + + char *str_cur() { return str + str_off; } + + size_t num_written_bytes(int retval) { + if (retval < 0) { + return 0; + } + + size_t num_avail = str_off < size ? size - str_off : 0; + if (num_avail == 0) { + return 0; + } + + size_t num_written = retval; + // A return value of {v,}snprintf of size or more means that the output was + // truncated. + if (num_written >= num_avail) { + num_written -= num_avail; + } + + return num_written; + } + + char *str; + size_t str_off; + size_t size; + const char *fmt_start; + const char *fmt_cur; + int width; + int num_scanned; + bool skip; +}; + +// Formats the input and propagates the input labels to the output. The output +// is stored in 'str'. 'size' bounds the number of output bytes. 'format' and +// 'ap' are the format string and the list of arguments for formatting. Returns +// the return value vsnprintf would return. +// +// The function tokenizes the format string in chunks representing either a +// constant string or a single format directive (e.g., '%.3f') and formats each +// chunk independently into the output string. This approach allows to figure +// out which bytes of the output string depends on which argument and thus to +// propagate labels more precisely. +// +// WARNING: This implementation does not support conversion specifiers with +// positional arguments. +static int format_buffer(char *str, size_t size, const char *fmt, + dfsan_label *va_labels, dfsan_label *ret_label, + dfsan_origin *va_origins, dfsan_origin *ret_origin, + va_list ap) { + Formatter formatter(str, fmt, size); + + while (*formatter.fmt_cur) { + formatter.fmt_start = formatter.fmt_cur; + formatter.width = -1; + int retval = 0; + + if (*formatter.fmt_cur != '%') { + // Ordinary character. Consume all the characters until a '%' or the end + // of the string. + for (; *(formatter.fmt_cur + 1) && *(formatter.fmt_cur + 1) != '%'; + ++formatter.fmt_cur) {} + retval = formatter.format(); + dfsan_set_label(0, formatter.str_cur(), + formatter.num_written_bytes(retval)); + } else { + // Conversion directive. Consume all the characters until a conversion + // specifier or the end of the string. + bool end_fmt = false; + for (; *formatter.fmt_cur && !end_fmt; ) { + switch (*++formatter.fmt_cur) { + case 'd': + case 'i': + case 'o': + case 'u': + case 'x': + case 'X': + switch (*(formatter.fmt_cur - 1)) { + case 'h': + // Also covers the 'hh' case (since the size of the arg is still + // an int). + retval = formatter.format(va_arg(ap, int)); + break; + case 'l': + if (formatter.fmt_cur - formatter.fmt_start >= 2 && + *(formatter.fmt_cur - 2) == 'l') { + retval = formatter.format(va_arg(ap, long long int)); + } else { + retval = formatter.format(va_arg(ap, long int)); + } + break; + case 'q': + retval = formatter.format(va_arg(ap, long long int)); + break; + case 'j': + retval = formatter.format(va_arg(ap, intmax_t)); + break; + case 'z': + case 't': + retval = formatter.format(va_arg(ap, size_t)); + break; + default: + retval = formatter.format(va_arg(ap, int)); + } + if (va_origins == nullptr) + dfsan_set_label(*va_labels++, formatter.str_cur(), + formatter.num_written_bytes(retval)); + else + dfsan_set_label_origin(*va_labels++, *va_origins++, + formatter.str_cur(), + formatter.num_written_bytes(retval)); + end_fmt = true; + break; + + case 'a': + case 'A': + case 'e': + case 'E': + case 'f': + case 'F': + case 'g': + case 'G': + if (*(formatter.fmt_cur - 1) == 'L') { + retval = formatter.format(va_arg(ap, long double)); + } else { + retval = formatter.format(va_arg(ap, double)); + } + if (va_origins == nullptr) + dfsan_set_label(*va_labels++, formatter.str_cur(), + formatter.num_written_bytes(retval)); + else + dfsan_set_label_origin(*va_labels++, *va_origins++, + formatter.str_cur(), + formatter.num_written_bytes(retval)); + end_fmt = true; + break; + + case 'c': + retval = formatter.format(va_arg(ap, int)); + if (va_origins == nullptr) + dfsan_set_label(*va_labels++, formatter.str_cur(), + formatter.num_written_bytes(retval)); + else + dfsan_set_label_origin(*va_labels++, *va_origins++, + formatter.str_cur(), + formatter.num_written_bytes(retval)); + end_fmt = true; + break; + + case 's': { + char *arg = va_arg(ap, char *); + retval = formatter.format(arg); + if (va_origins) { + va_origins++; + dfsan_mem_origin_transfer(formatter.str_cur(), arg, + formatter.num_written_bytes(retval)); + } + va_labels++; + dfsan_mem_shadow_transfer(formatter.str_cur(), arg, + formatter.num_written_bytes(retval)); + end_fmt = true; + break; + } + + case 'p': + retval = formatter.format(va_arg(ap, void *)); + if (va_origins == nullptr) + dfsan_set_label(*va_labels++, formatter.str_cur(), + formatter.num_written_bytes(retval)); + else + dfsan_set_label_origin(*va_labels++, *va_origins++, + formatter.str_cur(), + formatter.num_written_bytes(retval)); + end_fmt = true; + break; + + case 'n': { + int *ptr = va_arg(ap, int *); + *ptr = (int)formatter.str_off; + va_labels++; + if (va_origins) + va_origins++; + dfsan_set_label(0, ptr, sizeof(ptr)); + end_fmt = true; + break; + } + + case '%': + retval = formatter.format(); + dfsan_set_label(0, formatter.str_cur(), + formatter.num_written_bytes(retval)); + end_fmt = true; + break; + + case '*': + formatter.width = va_arg(ap, int); + va_labels++; + if (va_origins) + va_origins++; + break; + + default: + break; + } + } + } + + if (retval < 0) { + return retval; + } + + formatter.fmt_cur++; + formatter.str_off += retval; + } + + *ret_label = 0; + if (ret_origin) + *ret_origin = 0; + + // Number of bytes written in total. + return formatter.str_off; +} + +// Scans a chunk either a constant string or a single format directive (e.g., +// '%.3f'). +struct Scanner { + Scanner(char *str_, const char *fmt_, size_t size_) + : str(str_), + str_off(0), + size(size_), + fmt_start(fmt_), + fmt_cur(fmt_), + width(-1), + num_scanned(0), + skip(false) {} + + // Consumes a chunk of ordinary characters. + // Returns number of matching ordinary characters. + // Returns -1 if the match failed. + // In format strings, a space will match multiple spaces. + int check_match_ordinary() { + char *tmp_fmt = build_format_string_with_n(); + int read_count = -1; + sscanf(str + str_off, tmp_fmt, &read_count); + free(tmp_fmt); + if (read_count > 0) { + str_off += read_count; + } + return read_count; + } + + int scan() { + char *tmp_fmt = build_format_string_with_n(); + int read_count = 0; + int retval = sscanf(str + str_off, tmp_fmt, &read_count); + free(tmp_fmt); + if (retval > 0) { + num_scanned += retval; + } + return read_count; + } + + template <typename T> + int scan(T arg) { + char *tmp_fmt = build_format_string_with_n(); + int read_count = 0; + int retval = sscanf(str + str_off, tmp_fmt, arg, &read_count); + free(tmp_fmt); + if (retval > 0) { + num_scanned += retval; + } + return read_count; + } + + // Adds %n onto current format string to measure length. + char *build_format_string_with_n() { + size_t fmt_size = fmt_cur - fmt_start + 1; + // +2 for %n, +1 for \0 + char *new_fmt = (char *)malloc(fmt_size + 2 + 1); + assert(new_fmt); + internal_memcpy(new_fmt, fmt_start, fmt_size); + new_fmt[fmt_size] = '%'; + new_fmt[fmt_size + 1] = 'n'; + new_fmt[fmt_size + 2] = '\0'; + return new_fmt; + } + + char *str_cur() { return str + str_off; } + + size_t num_written_bytes(int retval) { + if (retval < 0) { + return 0; + } + + size_t num_avail = str_off < size ? size - str_off : 0; + if (num_avail == 0) { + return 0; + } + + size_t num_written = retval; + // A return value of {v,}snprintf of size or more means that the output was + // truncated. + if (num_written >= num_avail) { + num_written -= num_avail; + } + + return num_written; + } + + char *str; + size_t str_off; + size_t size; + const char *fmt_start; + const char *fmt_cur; + int width; + int num_scanned; + bool skip; +}; + +// This function is an inverse of format_buffer: we take the input buffer, +// scan it in search for format strings and store the results in the varargs. +// The labels are propagated from the input buffer to the varargs. +static int scan_buffer(char *str, size_t size, const char *fmt, + dfsan_label *va_labels, dfsan_label *ret_label, + dfsan_origin *str_origin, dfsan_origin *ret_origin, + va_list ap) { + Scanner scanner(str, fmt, size); + while (*scanner.fmt_cur) { + scanner.fmt_start = scanner.fmt_cur; + scanner.width = -1; + scanner.skip = false; + int read_count = 0; + void *dst_ptr = 0; + size_t write_size = 0; + if (*scanner.fmt_cur != '%') { + // Ordinary character and spaces. + // Consume all the characters until a '%' or the end of the string. + for (; *(scanner.fmt_cur + 1) && *(scanner.fmt_cur + 1) != '%'; + ++scanner.fmt_cur) { + } + if (scanner.check_match_ordinary() < 0) { + // The ordinary characters did not match. + break; + } + } else { + // Conversion directive. Consume all the characters until a conversion + // specifier or the end of the string. + bool end_fmt = false; + for (; *scanner.fmt_cur && !end_fmt;) { + switch (*++scanner.fmt_cur) { + case 'd': + case 'i': + case 'o': + case 'u': + case 'x': + case 'X': + if (scanner.skip) { + read_count = scanner.scan(); + } else { + switch (*(scanner.fmt_cur - 1)) { + case 'h': + // Also covers the 'hh' case (since the size of the arg is + // still an int). + dst_ptr = va_arg(ap, int *); + read_count = scanner.scan((int *)dst_ptr); + write_size = sizeof(int); + break; + case 'l': + if (scanner.fmt_cur - scanner.fmt_start >= 2 && + *(scanner.fmt_cur - 2) == 'l') { + dst_ptr = va_arg(ap, long long int *); + read_count = scanner.scan((long long int *)dst_ptr); + write_size = sizeof(long long int); + } else { + dst_ptr = va_arg(ap, long int *); + read_count = scanner.scan((long int *)dst_ptr); + write_size = sizeof(long int); + } + break; + case 'q': + dst_ptr = va_arg(ap, long long int *); + read_count = scanner.scan((long long int *)dst_ptr); + write_size = sizeof(long long int); + break; + case 'j': + dst_ptr = va_arg(ap, intmax_t *); + read_count = scanner.scan((intmax_t *)dst_ptr); + write_size = sizeof(intmax_t); + break; + case 'z': + case 't': + dst_ptr = va_arg(ap, size_t *); + read_count = scanner.scan((size_t *)dst_ptr); + write_size = sizeof(size_t); + break; + default: + dst_ptr = va_arg(ap, int *); + read_count = scanner.scan((int *)dst_ptr); + write_size = sizeof(int); + } + // get the label associated with the string at the corresponding + // place + dfsan_label l = dfsan_read_label( + scanner.str_cur(), scanner.num_written_bytes(read_count)); + dfsan_set_label(l, dst_ptr, write_size); + if (str_origin != nullptr) { + dfsan_set_label(l, dst_ptr, write_size); + size_t scan_count = scanner.num_written_bytes(read_count); + size_t size = scan_count > write_size ? write_size : scan_count; + dfsan_mem_origin_transfer(dst_ptr, scanner.str_cur(), size); + } + } + end_fmt = true; + + break; + + case 'a': + case 'A': + case 'e': + case 'E': + case 'f': + case 'F': + case 'g': + case 'G': + if (scanner.skip) { + read_count = scanner.scan(); + } else { + if (*(scanner.fmt_cur - 1) == 'L') { + dst_ptr = va_arg(ap, long double *); + read_count = scanner.scan((long double *)dst_ptr); + write_size = sizeof(long double); + } else if (*(scanner.fmt_cur - 1) == 'l') { + dst_ptr = va_arg(ap, double *); + read_count = scanner.scan((double *)dst_ptr); + write_size = sizeof(double); + } else { + dst_ptr = va_arg(ap, float *); + read_count = scanner.scan((float *)dst_ptr); + write_size = sizeof(float); + } + dfsan_label l = dfsan_read_label( + scanner.str_cur(), scanner.num_written_bytes(read_count)); + dfsan_set_label(l, dst_ptr, write_size); + if (str_origin != nullptr) { + dfsan_set_label(l, dst_ptr, write_size); + size_t scan_count = scanner.num_written_bytes(read_count); + size_t size = scan_count > write_size ? write_size : scan_count; + dfsan_mem_origin_transfer(dst_ptr, scanner.str_cur(), size); + } + } + end_fmt = true; + break; + + case 'c': + if (scanner.skip) { + read_count = scanner.scan(); + } else { + dst_ptr = va_arg(ap, char *); + read_count = scanner.scan((char *)dst_ptr); + write_size = sizeof(char); + dfsan_label l = dfsan_read_label( + scanner.str_cur(), scanner.num_written_bytes(read_count)); + dfsan_set_label(l, dst_ptr, write_size); + if (str_origin != nullptr) { + size_t scan_count = scanner.num_written_bytes(read_count); + size_t size = scan_count > write_size ? write_size : scan_count; + dfsan_mem_origin_transfer(dst_ptr, scanner.str_cur(), size); + } + } + end_fmt = true; + break; + + case 's': { + if (scanner.skip) { + read_count = scanner.scan(); + } else { + dst_ptr = va_arg(ap, char *); + read_count = scanner.scan((char *)dst_ptr); + if (1 == read_count) { + // special case: we have parsed a single string and we need to + // update read_count with the string size + read_count = strlen((char *)dst_ptr); + } + if (str_origin) + dfsan_mem_origin_transfer( + dst_ptr, scanner.str_cur(), + scanner.num_written_bytes(read_count)); + va_labels++; + dfsan_mem_shadow_transfer(dst_ptr, scanner.str_cur(), + scanner.num_written_bytes(read_count)); + } + end_fmt = true; + break; + } + + case 'p': + if (scanner.skip) { + read_count = scanner.scan(); + } else { + dst_ptr = va_arg(ap, void *); + read_count = + scanner.scan((int *)dst_ptr); // note: changing void* to int* + // since we need to call sizeof + write_size = sizeof(int); + + dfsan_label l = dfsan_read_label( + scanner.str_cur(), scanner.num_written_bytes(read_count)); + dfsan_set_label(l, dst_ptr, write_size); + if (str_origin != nullptr) { + dfsan_set_label(l, dst_ptr, write_size); + size_t scan_count = scanner.num_written_bytes(read_count); + size_t size = scan_count > write_size ? write_size : scan_count; + dfsan_mem_origin_transfer(dst_ptr, scanner.str_cur(), size); + } + } + end_fmt = true; + break; + + case 'n': { + if (!scanner.skip) { + int *ptr = va_arg(ap, int *); + *ptr = (int)scanner.str_off; + *va_labels++ = 0; + dfsan_set_label(0, ptr, sizeof(*ptr)); + if (str_origin != nullptr) + *str_origin++ = 0; + } + end_fmt = true; + break; + } + + case '%': + read_count = scanner.scan(); + end_fmt = true; + break; + + case '*': + scanner.skip = true; + break; + + default: + break; + } + } + } + + if (read_count < 0) { + // There was an error. + return read_count; + } + + scanner.fmt_cur++; + scanner.str_off += read_count; + } + + (void)va_labels; // Silence unused-but-set-parameter warning + *ret_label = 0; + if (ret_origin) + *ret_origin = 0; + + // Number of items scanned in total. + return scanner.num_scanned; +} + +extern "C" { +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_sprintf(char *str, const char *format, dfsan_label str_label, + dfsan_label format_label, dfsan_label *va_labels, + dfsan_label *ret_label, ...) { + va_list ap; + va_start(ap, ret_label); + + int ret = format_buffer(str, INT32_MAX, format, va_labels, ret_label, nullptr, + nullptr, ap); + va_end(ap); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_sprintf(char *str, const char *format, dfsan_label str_label, + dfsan_label format_label, dfsan_label *va_labels, + dfsan_label *ret_label, dfsan_origin str_origin, + dfsan_origin format_origin, dfsan_origin *va_origins, + dfsan_origin *ret_origin, ...) { + va_list ap; + va_start(ap, ret_origin); + int ret = format_buffer(str, INT32_MAX, format, va_labels, ret_label, + va_origins, ret_origin, ap); + va_end(ap); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_snprintf(char *str, size_t size, const char *format, + dfsan_label str_label, dfsan_label size_label, + dfsan_label format_label, dfsan_label *va_labels, + dfsan_label *ret_label, ...) { + va_list ap; + va_start(ap, ret_label); + int ret = format_buffer(str, size, format, va_labels, ret_label, nullptr, + nullptr, ap); + va_end(ap); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_snprintf(char *str, size_t size, const char *format, + dfsan_label str_label, dfsan_label size_label, + dfsan_label format_label, dfsan_label *va_labels, + dfsan_label *ret_label, dfsan_origin str_origin, + dfsan_origin size_origin, dfsan_origin format_origin, + dfsan_origin *va_origins, dfsan_origin *ret_origin, ...) { + va_list ap; + va_start(ap, ret_origin); + int ret = format_buffer(str, size, format, va_labels, ret_label, va_origins, + ret_origin, ap); + va_end(ap); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfsw_sscanf(char *str, const char *format, dfsan_label str_label, + dfsan_label format_label, dfsan_label *va_labels, + dfsan_label *ret_label, ...) { + va_list ap; + va_start(ap, ret_label); + int ret = scan_buffer(str, ~0ul, format, va_labels, ret_label, nullptr, + nullptr, ap); + va_end(ap); + return ret; +} + +SANITIZER_INTERFACE_ATTRIBUTE +int __dfso_sscanf(char *str, const char *format, dfsan_label str_label, + dfsan_label format_label, dfsan_label *va_labels, + dfsan_label *ret_label, dfsan_origin str_origin, + dfsan_origin format_origin, dfsan_origin *va_origins, + dfsan_origin *ret_origin, ...) { + va_list ap; + va_start(ap, ret_origin); + int ret = scan_buffer(str, ~0ul, format, va_labels, ret_label, &str_origin, + ret_origin, ap); + va_end(ap); + return ret; +} + +WRAPPER_ALIAS(__isoc99_sscanf, sscanf) +WRAPPER_ALIAS(__isoc23_sscanf, sscanf) + +static void BeforeFork() { + StackDepotLockBeforeFork(); + ChainedOriginDepotLockBeforeFork(); +} + +static void AfterFork(bool fork_child) { + ChainedOriginDepotUnlockAfterFork(fork_child); + StackDepotUnlockAfterFork(fork_child); +} + +SANITIZER_INTERFACE_ATTRIBUTE +pid_t __dfsw_fork(dfsan_label *ret_label) { + pid_t pid = fork(); + *ret_label = 0; + return pid; +} + +SANITIZER_INTERFACE_ATTRIBUTE +pid_t __dfso_fork(dfsan_label *ret_label, dfsan_origin *ret_origin) { + BeforeFork(); + pid_t pid = __dfsw_fork(ret_label); + AfterFork(/* fork_child= */ pid == 0); + return pid; +} + +// Default empty implementations (weak). Users should redefine them. +SANITIZER_INTERFACE_WEAK_DEF(void, __sanitizer_cov_trace_pc_guard, u32 *) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __sanitizer_cov_trace_pc_guard_init, u32 *, + u32 *) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __sanitizer_cov_pcs_init, const uptr *beg, + const uptr *end) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __sanitizer_cov_trace_pc_indir, void) {} + +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_cmp, void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_cmp1, void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_cmp2, void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_cmp4, void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_cmp8, void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_const_cmp1, + void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_const_cmp2, + void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_const_cmp4, + void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_const_cmp8, + void) {} +SANITIZER_INTERFACE_WEAK_DEF(void, __dfsw___sanitizer_cov_trace_switch, void) {} +} // extern "C" diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_flags.h b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_flags.h new file mode 100644 index 000000000000..ec7edf6112a9 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_flags.h @@ -0,0 +1,32 @@ +//===-- dfsan_flags.h -------------------------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// DFSan flags. +//===----------------------------------------------------------------------===// + +#ifndef DFSAN_FLAGS_H +#define DFSAN_FLAGS_H + +namespace __dfsan { + +struct Flags { +#define DFSAN_FLAG(Type, Name, DefaultValue, Description) Type Name; +#include "dfsan_flags.inc" +#undef DFSAN_FLAG + + void SetDefaults(); +}; + +extern Flags flags_data; +inline Flags &flags() { return flags_data; } + +} // namespace __dfsan + +#endif // DFSAN_FLAGS_H diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_flags.inc b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_flags.inc new file mode 100644 index 000000000000..67fda0eee490 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_flags.inc @@ -0,0 +1,43 @@ +//===-- dfsan_flags.inc -----------------------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// DFSan runtime flags. +// +//===----------------------------------------------------------------------===// +#ifndef DFSAN_FLAG +# error "Define DFSAN_FLAG prior to including this file!" +#endif + +// DFSAN_FLAG(Type, Name, DefaultValue, Description) +// See COMMON_FLAG in sanitizer_flags.inc for more details. + +DFSAN_FLAG(bool, warn_unimplemented, false, + "Whether to warn on unimplemented functions.") +DFSAN_FLAG(bool, warn_nonzero_labels, false, + "Whether to warn on unimplemented functions.") +DFSAN_FLAG( + bool, strict_data_dependencies, true, + "Whether to propagate labels only when there is an obvious data dependency" + "(e.g., when comparing strings, ignore the fact that the output of the" + "comparison might be data-dependent on the content of the strings). This" + "applies only to the custom functions defined in 'custom.c'.") +DFSAN_FLAG( + int, origin_history_size, Origin::kMaxDepth, + "The limit of origin chain length. Non-positive values mean unlimited.") +DFSAN_FLAG( + int, origin_history_per_stack_limit, 20000, + "The limit of origin node's references count. " + "Non-positive values mean unlimited.") +DFSAN_FLAG(int, store_context_size, 20, + "The depth limit of origin tracking stack traces.") +DFSAN_FLAG(bool, check_origin_invariant, false, + "Whether to check if the origin invariant holds.") +DFSAN_FLAG(bool, zero_in_malloc, true, + "Whether to zero shadow space of new allocated memory.") +DFSAN_FLAG(bool, zero_in_free, true, + "Whether to zero shadow space of deallocated memory.") diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_interceptors.cpp b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_interceptors.cpp new file mode 100644 index 000000000000..d8fb9ea86618 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_interceptors.cpp @@ -0,0 +1,220 @@ +//===-- dfsan_interceptors.cpp --------------------------------------------===// +// +// 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// Interceptors for standard library functions. +//===----------------------------------------------------------------------===// + +#include <sys/syscall.h> +#include <unistd.h> + +#include "dfsan/dfsan.h" +#include "dfsan/dfsan_thread.h" +#include "interception/interception.h" +#include "sanitizer_common/sanitizer_allocator_dlsym.h" +#include "sanitizer_common/sanitizer_allocator_interface.h" +#include "sanitizer_common/sanitizer_common.h" +#include "sanitizer_common/sanitizer_errno.h" +#include "sanitizer_common/sanitizer_platform_limits_posix.h" +#include "sanitizer_common/sanitizer_posix.h" +#include "sanitizer_common/sanitizer_tls_get_addr.h" + +using namespace __sanitizer; + +static bool interceptors_initialized; + +struct DlsymAlloc : public DlSymAllocator<DlsymAlloc> { + static bool UseImpl() { return !__dfsan::dfsan_inited; } +}; + +INTERCEPTOR(void *, reallocarray, void *ptr, SIZE_T nmemb, SIZE_T size) { + return __dfsan::dfsan_reallocarray(ptr, nmemb, size); +} + +INTERCEPTOR(void *, __libc_memalign, SIZE_T alignment, SIZE_T size) { + void *ptr = __dfsan::dfsan_memalign(alignment, size); + if (ptr) + DTLS_on_libc_memalign(ptr, size); + return ptr; +} + +INTERCEPTOR(void *, aligned_alloc, SIZE_T alignment, SIZE_T size) { + return __dfsan::dfsan_aligned_alloc(alignment, size); +} + +INTERCEPTOR(void *, calloc, SIZE_T nmemb, SIZE_T size) { + if (DlsymAlloc::Use()) + return DlsymAlloc::Callocate(nmemb, size); + return __dfsan::dfsan_calloc(nmemb, size); +} + +INTERCEPTOR(void *, realloc, void *ptr, SIZE_T size) { + if (DlsymAlloc::Use() || DlsymAlloc::PointerIsMine(ptr)) + return DlsymAlloc::Realloc(ptr, size); + return __dfsan::dfsan_realloc(ptr, size); +} + +INTERCEPTOR(void *, malloc, SIZE_T size) { + if (DlsymAlloc::Use()) + return DlsymAlloc::Allocate(size); + return __dfsan::dfsan_malloc(size); +} + +INTERCEPTOR(void, free, void *ptr) { + if (!ptr) + return; + if (DlsymAlloc::PointerIsMine(ptr)) + return DlsymAlloc::Free(ptr); + return __dfsan::dfsan_deallocate(ptr); +} + +INTERCEPTOR(void, cfree, void *ptr) { + if (!ptr) + return; + if (DlsymAlloc::PointerIsMine(ptr)) + return DlsymAlloc::Free(ptr); + return __dfsan::dfsan_deallocate(ptr); +} + +INTERCEPTOR(int, posix_memalign, void **memptr, SIZE_T alignment, SIZE_T size) { + CHECK_NE(memptr, 0); + int res = __dfsan::dfsan_posix_memalign(memptr, alignment, size); + if (!res) + dfsan_set_label(0, memptr, sizeof(*memptr)); + return res; +} + +INTERCEPTOR(void *, memalign, SIZE_T alignment, SIZE_T size) { + return __dfsan::dfsan_memalign(alignment, size); +} + +INTERCEPTOR(void *, valloc, SIZE_T size) { return __dfsan::dfsan_valloc(size); } + +INTERCEPTOR(void *, pvalloc, SIZE_T size) { + return __dfsan::dfsan_pvalloc(size); +} + +INTERCEPTOR(void, mallinfo, __sanitizer_struct_mallinfo *sret) { + internal_memset(sret, 0, sizeof(*sret)); + dfsan_set_label(0, sret, sizeof(*sret)); +} + +INTERCEPTOR(int, mallopt, int cmd, int value) { return 0; } + +INTERCEPTOR(void, malloc_stats, void) { + // FIXME: implement, but don't call REAL(malloc_stats)! +} + +INTERCEPTOR(uptr, malloc_usable_size, void *ptr) { + return __sanitizer_get_allocated_size(ptr); +} + +#define ENSURE_DFSAN_INITED() \ + do { \ + CHECK(!__dfsan::dfsan_init_is_running); \ + if (!__dfsan::dfsan_inited) { \ + __dfsan::dfsan_init(); \ + } \ + } while (0) + +#define COMMON_INTERCEPTOR_ENTER(func, ...) \ + if (__dfsan::dfsan_init_is_running) \ + return REAL(func)(__VA_ARGS__); \ + ENSURE_DFSAN_INITED(); \ + dfsan_set_label(0, __errno_location(), sizeof(int)); + +INTERCEPTOR(void *, mmap, void *addr, SIZE_T length, int prot, int flags, + int fd, OFF_T offset) { + if (common_flags()->detect_write_exec) + ReportMmapWriteExec(prot, flags); + if (!__dfsan::dfsan_inited) + return (void *)internal_mmap(addr, length, prot, flags, fd, offset); + COMMON_INTERCEPTOR_ENTER(mmap, addr, length, prot, flags, fd, offset); + void *res = REAL(mmap)(addr, length, prot, flags, fd, offset); + if (res != (void *)-1) { + dfsan_set_label(0, res, RoundUpTo(length, GetPageSizeCached())); + } + return res; +} + +INTERCEPTOR(void *, mmap64, void *addr, SIZE_T length, int prot, int flags, + int fd, OFF64_T offset) { + if (common_flags()->detect_write_exec) + ReportMmapWriteExec(prot, flags); + if (!__dfsan::dfsan_inited) + return (void *)internal_mmap(addr, length, prot, flags, fd, offset); + COMMON_INTERCEPTOR_ENTER(mmap64, addr, length, prot, flags, fd, offset); + void *res = REAL(mmap64)(addr, length, prot, flags, fd, offset); + if (res != (void *)-1) { + dfsan_set_label(0, res, RoundUpTo(length, GetPageSizeCached())); + } + return res; +} + +INTERCEPTOR(int, munmap, void *addr, SIZE_T length) { + if (!__dfsan::dfsan_inited) + return internal_munmap(addr, length); + COMMON_INTERCEPTOR_ENTER(munmap, addr, length); + int res = REAL(munmap)(addr, length); + if (res != -1) + dfsan_set_label(0, addr, RoundUpTo(length, GetPageSizeCached())); + return res; +} + +#define COMMON_INTERCEPTOR_GET_TLS_RANGE(begin, end) \ + if (__dfsan::DFsanThread *t = __dfsan::GetCurrentThread()) { \ + *begin = t->tls_begin(); \ + *end = t->tls_end(); \ + } else { \ + *begin = *end = 0; \ + } +#define COMMON_INTERCEPTOR_INITIALIZE_RANGE(ptr, size) \ + dfsan_set_label(0, ptr, size) + +INTERCEPTOR(void *, __tls_get_addr, void *arg) { + COMMON_INTERCEPTOR_ENTER(__tls_get_addr, arg); + void *res = REAL(__tls_get_addr)(arg); + uptr tls_begin, tls_end; + COMMON_INTERCEPTOR_GET_TLS_RANGE(&tls_begin, &tls_end); + DTLS::DTV *dtv = DTLS_on_tls_get_addr(arg, res, tls_begin, tls_end); + if (dtv) { + // New DTLS block has been allocated. + COMMON_INTERCEPTOR_INITIALIZE_RANGE((void *)dtv->beg, dtv->size); + } + return res; +} + +namespace __dfsan { +void initialize_interceptors() { + CHECK(!interceptors_initialized); + + INTERCEPT_FUNCTION(aligned_alloc); + INTERCEPT_FUNCTION(calloc); + INTERCEPT_FUNCTION(cfree); + INTERCEPT_FUNCTION(free); + INTERCEPT_FUNCTION(mallinfo); + INTERCEPT_FUNCTION(malloc); + INTERCEPT_FUNCTION(malloc_stats); + INTERCEPT_FUNCTION(malloc_usable_size); + INTERCEPT_FUNCTION(mallopt); + INTERCEPT_FUNCTION(memalign); + INTERCEPT_FUNCTION(mmap); + INTERCEPT_FUNCTION(mmap64); + INTERCEPT_FUNCTION(munmap); + INTERCEPT_FUNCTION(posix_memalign); + INTERCEPT_FUNCTION(pvalloc); + INTERCEPT_FUNCTION(realloc); + INTERCEPT_FUNCTION(reallocarray); + INTERCEPT_FUNCTION(valloc); + INTERCEPT_FUNCTION(__tls_get_addr); + INTERCEPT_FUNCTION(__libc_memalign); + + interceptors_initialized = true; +} +} // namespace __dfsan diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_new_delete.cpp b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_new_delete.cpp new file mode 100644 index 000000000000..7ac906e81077 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_new_delete.cpp @@ -0,0 +1,124 @@ +//===-- dfsan_new_delete.cpp ----------------------------------------------===// +// +// 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataflowSanitizer. +// +// Interceptors for operators new and delete. +//===----------------------------------------------------------------------===// + +#include <stddef.h> + +#include "dfsan.h" +#include "interception/interception.h" +#include "sanitizer_common/sanitizer_allocator.h" +#include "sanitizer_common/sanitizer_allocator_report.h" + +using namespace __dfsan; + +// Fake std::nothrow_t and std::align_val_t to avoid including <new>. +namespace std { +struct nothrow_t {}; +enum class align_val_t : size_t {}; +} // namespace std + +// TODO(alekseys): throw std::bad_alloc instead of dying on OOM. +#define OPERATOR_NEW_BODY(nothrow) \ + void *res = dfsan_malloc(size); \ + if (!nothrow && UNLIKELY(!res)) { \ + BufferedStackTrace stack; \ + ReportOutOfMemory(size, &stack); \ + } \ + return res +#define OPERATOR_NEW_BODY_ALIGN(nothrow) \ + void *res = dfsan_memalign((uptr)align, size); \ + if (!nothrow && UNLIKELY(!res)) { \ + BufferedStackTrace stack; \ + ReportOutOfMemory(size, &stack); \ + } \ + return res; + +INTERCEPTOR_ATTRIBUTE +void *operator new(size_t size) { OPERATOR_NEW_BODY(false /*nothrow*/); } +INTERCEPTOR_ATTRIBUTE +void *operator new[](size_t size) { OPERATOR_NEW_BODY(false /*nothrow*/); } +INTERCEPTOR_ATTRIBUTE +void *operator new(size_t size, std::nothrow_t const &) { + OPERATOR_NEW_BODY(true /*nothrow*/); +} +INTERCEPTOR_ATTRIBUTE +void *operator new[](size_t size, std::nothrow_t const &) { + OPERATOR_NEW_BODY(true /*nothrow*/); +} +INTERCEPTOR_ATTRIBUTE +void *operator new(size_t size, std::align_val_t align) { + OPERATOR_NEW_BODY_ALIGN(false /*nothrow*/); +} +INTERCEPTOR_ATTRIBUTE +void *operator new[](size_t size, std::align_val_t align) { + OPERATOR_NEW_BODY_ALIGN(false /*nothrow*/); +} +INTERCEPTOR_ATTRIBUTE +void *operator new(size_t size, std::align_val_t align, + std::nothrow_t const &) { + OPERATOR_NEW_BODY_ALIGN(true /*nothrow*/); +} +INTERCEPTOR_ATTRIBUTE +void *operator new[](size_t size, std::align_val_t align, + std::nothrow_t const &) { + OPERATOR_NEW_BODY_ALIGN(true /*nothrow*/); +} + +#define OPERATOR_DELETE_BODY \ + if (ptr) \ + dfsan_deallocate(ptr) + +INTERCEPTOR_ATTRIBUTE +void operator delete(void *ptr)NOEXCEPT { OPERATOR_DELETE_BODY; } +INTERCEPTOR_ATTRIBUTE +void operator delete[](void *ptr) NOEXCEPT { OPERATOR_DELETE_BODY; } +INTERCEPTOR_ATTRIBUTE +void operator delete(void *ptr, std::nothrow_t const &) { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete[](void *ptr, std::nothrow_t const &) { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete(void *ptr, size_t size)NOEXCEPT { OPERATOR_DELETE_BODY; } +INTERCEPTOR_ATTRIBUTE +void operator delete[](void *ptr, size_t size) NOEXCEPT { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete(void *ptr, std::align_val_t align)NOEXCEPT { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete[](void *ptr, std::align_val_t align) NOEXCEPT { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete(void *ptr, std::align_val_t align, + std::nothrow_t const &) { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete[](void *ptr, std::align_val_t align, + std::nothrow_t const &) { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete(void *ptr, size_t size, std::align_val_t align)NOEXCEPT { + OPERATOR_DELETE_BODY; +} +INTERCEPTOR_ATTRIBUTE +void operator delete[](void *ptr, size_t size, + std::align_val_t align) NOEXCEPT { + OPERATOR_DELETE_BODY; +} diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_origin.h b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_origin.h new file mode 100644 index 000000000000..89fd7f99599f --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_origin.h @@ -0,0 +1,127 @@ +//===-- dfsan_origin.h ----------------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// Origin id utils. +//===----------------------------------------------------------------------===// + +#ifndef DFSAN_ORIGIN_H +#define DFSAN_ORIGIN_H + +#include "dfsan_chained_origin_depot.h" +#include "dfsan_flags.h" +#include "sanitizer_common/sanitizer_stackdepot.h" + +namespace __dfsan { + +// Origin handling. +// +// Origin is a 32-bit identifier that is attached to any taint value in the +// program and describes how this memory came to be tainted. +// +// Chained origin id is like: +// zzzz xxxx xxxx xxxx +// +// Chained origin id describes an event of storing a taint value to +// memory. The xxx part is a value of ChainedOriginDepot, which is a mapping of +// (stack_id, prev_id) -> id, where +// * stack_id describes the event. +// StackDepot keeps a mapping between those and corresponding stack traces. +// * prev_id is another origin id that describes the earlier part of the +// taint value history. 0 prev_id indicates the start of a chain. +// Following a chain of prev_id provides the full recorded history of a taint +// value. +// +// This, effectively, defines a forest where nodes are points in value history +// marked with origin ids, and edges are events that are marked with stack_id. +// +// The "zzzz" bits of chained origin id are used to store the length of the +// origin chain. + +class Origin { + public: + static bool isValidId(u32 id) { return id != 0; } + + u32 raw_id() const { return raw_id_; } + + bool isChainedOrigin() const { return Origin::isValidId(raw_id_); } + + u32 getChainedId() const { + CHECK(Origin::isValidId(raw_id_)); + return raw_id_ & kChainedIdMask; + } + + // Returns the next origin in the chain and the current stack trace. + // + // It scans a partition of StackDepot linearly, and is used only by origin + // tracking report. + Origin getNextChainedOrigin(StackTrace *stack) const { + CHECK(Origin::isValidId(raw_id_)); + u32 prev_id; + u32 stack_id = GetChainedOriginDepot()->Get(getChainedId(), &prev_id); + if (stack) + *stack = StackDepotGet(stack_id); + return Origin(prev_id); + } + + static Origin CreateChainedOrigin(Origin prev, StackTrace *stack) { + int depth = prev.isChainedOrigin() ? prev.depth() : -1; + // depth is the length of the chain minus 1. + // origin_history_size of 0 means unlimited depth. + if (flags().origin_history_size > 0) { + ++depth; + if (depth >= flags().origin_history_size || depth > kMaxDepth) + return prev; + } + + StackDepotHandle h = StackDepotPut_WithHandle(*stack); + if (!h.valid()) + return prev; + + if (flags().origin_history_per_stack_limit > 0) { + int use_count = h.use_count(); + if (use_count > flags().origin_history_per_stack_limit) + return prev; + } + + u32 chained_id; + bool inserted = + GetChainedOriginDepot()->Put(h.id(), prev.raw_id(), &chained_id); + CHECK((chained_id & kChainedIdMask) == chained_id); + + if (inserted && flags().origin_history_per_stack_limit > 0) + h.inc_use_count_unsafe(); + + return Origin((depth << kDepthShift) | chained_id); + } + + static Origin FromRawId(u32 id) { return Origin(id); } + + private: + static const int kDepthBits = 4; + static const int kDepthShift = 32 - kDepthBits; + + static const u32 kChainedIdMask = ((u32)-1) >> kDepthBits; + + u32 raw_id_; + + explicit Origin(u32 raw_id) : raw_id_(raw_id) {} + + int depth() const { + CHECK(isChainedOrigin()); + return (raw_id_ >> kDepthShift) & ((1 << kDepthBits) - 1); + } + + public: + static const int kMaxDepth = (1 << kDepthBits) - 1; +}; + +} // namespace __dfsan + +#endif // DFSAN_ORIGIN_H diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_platform.h b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_platform.h new file mode 100644 index 000000000000..01f0de47d960 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_platform.h @@ -0,0 +1,127 @@ +//===-- dfsan_platform.h ----------------------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +// Platform specific information for DFSan. +//===----------------------------------------------------------------------===// + +#ifndef DFSAN_PLATFORM_H +#define DFSAN_PLATFORM_H + +#include "sanitizer_common/sanitizer_common.h" +#include "sanitizer_common/sanitizer_platform.h" + +namespace __dfsan { + +using __sanitizer::uptr; + +// TODO: The memory mapping code to setup a 1:1 shadow is based on msan. +// Consider refactoring these into a shared implementation. + +struct MappingDesc { + uptr start; + uptr end; + enum Type { + INVALID = 1, + ALLOCATOR = 2, + APP = 4, + SHADOW = 8, + ORIGIN = 16, + } type; + const char *name; +}; + +// Note: MappingDesc::ALLOCATOR entries are only used to check for memory +// layout compatibility. The actual allocation settings are in +// dfsan_allocator.cpp, which need to be kept in sync. +#if SANITIZER_LINUX && SANITIZER_WORDSIZE == 64 + +# if defined(__aarch64__) +// The mapping assumes 48-bit VMA. AArch64 maps: +// - 0x0000000000000-0x0100000000000: 39/42/48-bits program own segments +// - 0x0a00000000000-0x0b00000000000: 48-bits PIE program segments +// Ideally, this would extend to 0x0c00000000000 (2^45 bytes - the +// maximum ASLR region for 48-bit VMA) but it is too hard to fit in +// the larger app/shadow/origin regions. +// - 0x0e00000000000-0x1000000000000: 48-bits libraries segments +const MappingDesc kMemoryLayout[] = { + {0X0000000000000, 0X0100000000000, MappingDesc::APP, "app-10-13"}, + {0X0100000000000, 0X0200000000000, MappingDesc::SHADOW, "shadow-14"}, + {0X0200000000000, 0X0300000000000, MappingDesc::INVALID, "invalid"}, + {0X0300000000000, 0X0400000000000, MappingDesc::ORIGIN, "origin-14"}, + {0X0400000000000, 0X0600000000000, MappingDesc::SHADOW, "shadow-15"}, + {0X0600000000000, 0X0800000000000, MappingDesc::ORIGIN, "origin-15"}, + {0X0800000000000, 0X0A00000000000, MappingDesc::INVALID, "invalid"}, + {0X0A00000000000, 0X0B00000000000, MappingDesc::APP, "app-14"}, + {0X0B00000000000, 0X0C00000000000, MappingDesc::SHADOW, "shadow-10-13"}, + {0X0C00000000000, 0X0D00000000000, MappingDesc::INVALID, "invalid"}, + {0X0D00000000000, 0X0E00000000000, MappingDesc::ORIGIN, "origin-10-13"}, + {0X0E00000000000, 0X0E40000000000, MappingDesc::ALLOCATOR, "allocator"}, + {0X0E40000000000, 0X1000000000000, MappingDesc::APP, "app-15"}, +}; +# define MEM_TO_SHADOW(mem) ((uptr)mem ^ 0xB00000000000ULL) +# define SHADOW_TO_ORIGIN(shadow) (((uptr)(shadow)) + 0x200000000000ULL) + +# else +// All of the following configurations are supported. +// ASLR disabled: main executable and DSOs at 0x555550000000 +// PIE and ASLR: main executable and DSOs at 0x7f0000000000 +// non-PIE: main executable below 0x100000000, DSOs at 0x7f0000000000 +// Heap at 0x700000000000. +const MappingDesc kMemoryLayout[] = { + {0x000000000000ULL, 0x010000000000ULL, MappingDesc::APP, "app-1"}, + {0x010000000000ULL, 0x100000000000ULL, MappingDesc::SHADOW, "shadow-2"}, + {0x100000000000ULL, 0x110000000000ULL, MappingDesc::INVALID, "invalid"}, + {0x110000000000ULL, 0x200000000000ULL, MappingDesc::ORIGIN, "origin-2"}, + {0x200000000000ULL, 0x300000000000ULL, MappingDesc::SHADOW, "shadow-3"}, + {0x300000000000ULL, 0x400000000000ULL, MappingDesc::ORIGIN, "origin-3"}, + {0x400000000000ULL, 0x500000000000ULL, MappingDesc::INVALID, "invalid"}, + {0x500000000000ULL, 0x510000000000ULL, MappingDesc::SHADOW, "shadow-1"}, + {0x510000000000ULL, 0x600000000000ULL, MappingDesc::APP, "app-2"}, + {0x600000000000ULL, 0x610000000000ULL, MappingDesc::ORIGIN, "origin-1"}, + {0x610000000000ULL, 0x700000000000ULL, MappingDesc::INVALID, "invalid"}, + {0x700000000000ULL, 0x740000000000ULL, MappingDesc::ALLOCATOR, "allocator"}, + {0x740000000000ULL, 0x800000000000ULL, MappingDesc::APP, "app-3"}}; +# define MEM_TO_SHADOW(mem) (((uptr)(mem)) ^ 0x500000000000ULL) +# define SHADOW_TO_ORIGIN(mem) (((uptr)(mem)) + 0x100000000000ULL) +# endif + +#else +# error "Unsupported platform" +#endif + +const uptr kMemoryLayoutSize = sizeof(kMemoryLayout) / sizeof(kMemoryLayout[0]); + +#define MEM_TO_ORIGIN(mem) (SHADOW_TO_ORIGIN(MEM_TO_SHADOW((mem)))) + +#ifndef __clang__ +__attribute__((optimize("unroll-loops"))) +#endif +inline bool +addr_is_type(uptr addr, int mapping_types) { +// It is critical for performance that this loop is unrolled (because then it is +// simplified into just a few constant comparisons). +#ifdef __clang__ +# pragma unroll +#endif + for (unsigned i = 0; i < kMemoryLayoutSize; ++i) + if ((kMemoryLayout[i].type & mapping_types) && + addr >= kMemoryLayout[i].start && addr < kMemoryLayout[i].end) + return true; + return false; +} + +#define MEM_IS_APP(mem) \ + (addr_is_type((uptr)(mem), MappingDesc::APP | MappingDesc::ALLOCATOR)) +#define MEM_IS_SHADOW(mem) addr_is_type((uptr)(mem), MappingDesc::SHADOW) +#define MEM_IS_ORIGIN(mem) addr_is_type((uptr)(mem), MappingDesc::ORIGIN) + +} // namespace __dfsan + +#endif diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_thread.cpp b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_thread.cpp new file mode 100644 index 000000000000..e64f0f818fb8 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_thread.cpp @@ -0,0 +1,134 @@ +#include "dfsan_thread.h" + +#include <pthread.h> + +#include "dfsan.h" +#include "sanitizer_common/sanitizer_tls_get_addr.h" + +namespace __dfsan { + +DFsanThread *DFsanThread::Create(thread_callback_t start_routine, void *arg, + bool track_origins) { + uptr PageSize = GetPageSizeCached(); + uptr size = RoundUpTo(sizeof(DFsanThread), PageSize); + DFsanThread *thread = (DFsanThread *)MmapOrDie(size, __func__); + thread->start_routine_ = start_routine; + thread->arg_ = arg; + thread->track_origins_ = track_origins; + thread->destructor_iterations_ = GetPthreadDestructorIterations(); + + return thread; +} + +void DFsanThread::SetThreadStackAndTls() { + uptr tls_size = 0; + uptr stack_size = 0; + GetThreadStackAndTls(IsMainThread(), &stack_.bottom, &stack_size, &tls_begin_, + &tls_size); + stack_.top = stack_.bottom + stack_size; + tls_end_ = tls_begin_ + tls_size; + + int local; + CHECK(AddrIsInStack((uptr)&local)); +} + +void DFsanThread::ClearShadowForThreadStackAndTLS() { + dfsan_set_label(0, (void *)stack_.bottom, stack_.top - stack_.bottom); + if (tls_begin_ != tls_end_) + dfsan_set_label(0, (void *)tls_begin_, tls_end_ - tls_begin_); + DTLS *dtls = DTLS_Get(); + CHECK_NE(dtls, 0); + ForEachDVT(dtls, [](const DTLS::DTV &dtv, int id) { + dfsan_set_label(0, (void *)(dtv.beg), dtv.size); + }); +} + +void DFsanThread::Init() { + SetThreadStackAndTls(); + ClearShadowForThreadStackAndTLS(); +} + +void DFsanThread::TSDDtor(void *tsd) { + DFsanThread *t = (DFsanThread *)tsd; + t->Destroy(); +} + +void DFsanThread::Destroy() { + malloc_storage().CommitBack(); + // We also clear the shadow on thread destruction because + // some code may still be executing in later TSD destructors + // and we don't want it to have any poisoned stack. + ClearShadowForThreadStackAndTLS(); + uptr size = RoundUpTo(sizeof(DFsanThread), GetPageSizeCached()); + UnmapOrDie(this, size); + DTLS_Destroy(); +} + +thread_return_t DFsanThread::ThreadStart() { + if (!start_routine_) { + // start_routine_ == 0 if we're on the main thread or on one of the + // OS X libdispatch worker threads. But nobody is supposed to call + // ThreadStart() for the worker threads. + return 0; + } + + // The only argument is void* arg. + // + // We have never supported propagating the pointer arg as tainted, + // __dfsw_pthread_create/__dfso_pthread_create ignore the taint label. + // Note that the bytes pointed-to (probably the much more common case) + // can still have taint labels attached to them. + dfsan_clear_thread_local_state(); + + return start_routine_(arg_); +} + +DFsanThread::StackBounds DFsanThread::GetStackBounds() const { + return {stack_.bottom, stack_.top}; +} + +uptr DFsanThread::stack_top() { return GetStackBounds().top; } + +uptr DFsanThread::stack_bottom() { return GetStackBounds().bottom; } + +bool DFsanThread::AddrIsInStack(uptr addr) { + const auto bounds = GetStackBounds(); + return addr >= bounds.bottom && addr < bounds.top; +} + +static pthread_key_t tsd_key; +static bool tsd_key_inited = false; + +void DFsanTSDInit(void (*destructor)(void *tsd)) { + CHECK(!tsd_key_inited); + tsd_key_inited = true; + CHECK_EQ(0, pthread_key_create(&tsd_key, destructor)); +} + +static THREADLOCAL DFsanThread *dfsan_current_thread; + +DFsanThread *GetCurrentThread() { return dfsan_current_thread; } + +void SetCurrentThread(DFsanThread *t) { + // Make sure we do not reset the current DFsanThread. + CHECK_EQ(0, dfsan_current_thread); + dfsan_current_thread = t; + // Make sure that DFsanTSDDtor gets called at the end. + CHECK(tsd_key_inited); + pthread_setspecific(tsd_key, t); +} + +void DFsanTSDDtor(void *tsd) { + DFsanThread *t = (DFsanThread *)tsd; + if (t->destructor_iterations_ > 1) { + t->destructor_iterations_--; + CHECK_EQ(0, pthread_setspecific(tsd_key, tsd)); + return; + } + dfsan_current_thread = nullptr; + // Make sure that signal handler can not see a stale current thread pointer. + atomic_signal_fence(memory_order_seq_cst); + DFsanThread::TSDDtor(tsd); +} + +} // namespace __dfsan diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_thread.h b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_thread.h new file mode 100644 index 000000000000..ebc25499e269 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/dfsan_thread.h @@ -0,0 +1,82 @@ +//===-- dfsan_thread.h ------------------------------------------*- 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 +// +//===----------------------------------------------------------------------===// +// +// This file is a part of DataFlowSanitizer. +// +//===----------------------------------------------------------------------===// + +#ifndef DFSAN_THREAD_H +#define DFSAN_THREAD_H + +#include "dfsan_allocator.h" +#include "sanitizer_common/sanitizer_common.h" +#include "sanitizer_common/sanitizer_posix.h" + +namespace __dfsan { + +class DFsanThread { + public: + // NOTE: There is no DFsanThread constructor. It is allocated + // via mmap() and *must* be valid in zero-initialized state. + + static DFsanThread *Create(thread_callback_t start_routine, void *arg, + bool track_origins = false); + static void TSDDtor(void *tsd); + void Destroy(); + + void Init(); // Should be called from the thread itself. + thread_return_t ThreadStart(); + + uptr stack_top(); + uptr stack_bottom(); + uptr tls_begin() { return tls_begin_; } + uptr tls_end() { return tls_end_; } + bool IsMainThread() { return start_routine_ == nullptr; } + + bool InSignalHandler() { return in_signal_handler_; } + void EnterSignalHandler() { in_signal_handler_++; } + void LeaveSignalHandler() { in_signal_handler_--; } + + DFsanThreadLocalMallocStorage &malloc_storage() { return malloc_storage_; } + + int destructor_iterations_; + __sanitizer_sigset_t starting_sigset_; + + private: + void SetThreadStackAndTls(); + void ClearShadowForThreadStackAndTLS(); + struct StackBounds { + uptr bottom; + uptr top; + }; + StackBounds GetStackBounds() const; + + bool AddrIsInStack(uptr addr); + + thread_callback_t start_routine_; + void *arg_; + bool track_origins_; + + StackBounds stack_; + + uptr tls_begin_; + uptr tls_end_; + + unsigned in_signal_handler_; + + DFsanThreadLocalMallocStorage malloc_storage_; +}; + +DFsanThread *GetCurrentThread(); +void SetCurrentThread(DFsanThread *t); +void DFsanTSDInit(void (*destructor)(void *tsd)); +void DFsanTSDDtor(void *tsd); + +} // namespace __dfsan + +#endif // DFSAN_THREAD_H diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/done_abilist.txt b/contrib/llvm-project/compiler-rt/lib/dfsan/done_abilist.txt new file mode 100644 index 000000000000..86a42ee1b4dc --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/done_abilist.txt @@ -0,0 +1,490 @@ +fun:main=uninstrumented +fun:main=discard + +############################################################################### +# DFSan interface functions +############################################################################### +fun:dfsan_union=uninstrumented +fun:dfsan_union=discard +fun:dfsan_create_label=uninstrumented +fun:dfsan_create_label=discard +fun:dfsan_set_label=uninstrumented +fun:dfsan_set_label=discard +fun:dfsan_add_label=uninstrumented +fun:dfsan_add_label=discard +fun:dfsan_get_label=uninstrumented +fun:dfsan_get_label=custom +fun:dfsan_read_label=uninstrumented +fun:dfsan_read_label=discard +fun:dfsan_get_label_count=uninstrumented +fun:dfsan_get_label_count=discard +fun:dfsan_get_label_info=uninstrumented +fun:dfsan_get_label_info=discard +fun:dfsan_has_label=uninstrumented +fun:dfsan_has_label=discard +fun:dfsan_has_label_with_desc=uninstrumented +fun:dfsan_has_label_with_desc=discard +fun:dfsan_set_write_callback=uninstrumented +fun:dfsan_set_write_callback=custom +fun:dfsan_flush=uninstrumented +fun:dfsan_flush=discard +fun:dfsan_print_origin_trace=uninstrumented +fun:dfsan_print_origin_trace=discard +fun:dfsan_print_origin_id_trace=uninstrumented +fun:dfsan_print_origin_id_trace=discard +fun:dfsan_sprint_origin_trace=uninstrumented +fun:dfsan_sprint_origin_trace=discard +fun:dfsan_sprint_origin_id_trace=uninstrumented +fun:dfsan_sprint_origin_id_trace=discard +fun:dfsan_sprint_stack_trace=uninstrumented +fun:dfsan_sprint_stack_trace=discard +fun:dfsan_get_origin=uninstrumented +fun:dfsan_get_origin=custom +fun:dfsan_read_origin_of_first_taint=uninstrumented +fun:dfsan_read_origin_of_first_taint=discard +fun:dfsan_get_init_origin=uninstrumented +fun:dfsan_get_init_origin=discard +fun:dfsan_get_track_origins=uninstrumented +fun:dfsan_get_track_origins=discard +fun:dfsan_set_conditional_callback=uninstrumented +fun:dfsan_set_conditional_callback=discard +fun:dfsan_get_labels_in_signal_conditional=uninstrumented +fun:dfsan_get_labels_in_signal_conditional=discard +fun:dfsan_set_reaches_function_callback=uninstrumented +fun:dfsan_set_reaches_function_callback=discard +fun:dfsan_get_labels_in_signal_reaches_function=uninstrumented +fun:dfsan_get_labels_in_signal_reaches_function=discard +fun:dfsan_reaches_function_callback=uninstrumented +fun:dfsan_reaches_function_callback=discard + +############################################################################### +# glibc +############################################################################### +# Functions of memory allocators +fun:__libc_memalign=discard +fun:aligned_alloc=discard +fun:calloc=discard +fun:cfree=discard +fun:mallinfo=discard +fun:malloc=discard +fun:free=discard +fun:malloc_stats=discard +fun:malloc_usable_size=discard +fun:mallopt=discard +fun:memalign=discard +fun:posix_memalign=discard +fun:pvalloc=discard +fun:realloc=discard +fun:reallocarray=discard +fun:valloc=discard + +# Functions that return a value that depends on the input, but the output might +# not be necessarily data-dependent on the input. +fun:isalpha=functional +fun:isdigit=functional +fun:isprint=functional +fun:isxdigit=functional +fun:isalnum=functional +fun:ispunct=functional +fun:isspace=functional +fun:tolower=functional +fun:_tolower=functional +fun:toupper=functional + +# Functions that return a value that is data-dependent on the input. +fun:__isinf=functional +fun:__isinff=functional +fun:__signbit=functional +fun:__signbitf=functional +fun:__signbitl=functional +fun:btowc=functional +fun:exp=functional +fun:exp2=functional +fun:expf=functional +fun:expl=functional +fun:fabs=functional +fun:finite=functional +fun:finitef=functional +fun:finitel=functional +fun:floor=functional +fun:fmod=functional +fun:isinf=functional +fun:isinff=functional +fun:isinfl=functional +fun:isnan=functional +fun:isnanf=functional +fun:isnanl=functional +fun:log=functional +fun:log1p=functional +fun:log1pf=functional +fun:log1pl=functional +fun:log2=functional +fun:log2f=functional +fun:log2l=functional +fun:modf=functional +fun:nextafter=functional +fun:nextafterf=functional +fun:nextafterl=functional +fun:nexttoward=functional +fun:nexttowardf=functional +fun:nexttowardl=functional +fun:pow=functional +fun:powf=functional +fun:powl=functional +fun:round=functional +fun:sqrt=functional +fun:sqrtf=functional +fun:sqrtl=functional +fun:wctob=functional + +# Functions that produce an output that does not depend on the input (shadow is +# zeroed automatically). +fun:__assert_fail=discard +fun:__cmsg_nxthdr=discard +fun:__ctype_b_loc=discard +fun:__cxa_atexit=discard +fun:__errno_location=discard +fun:__newlocale=discard +fun:__sbrk=discard +fun:__sigsetjmp=discard +fun:__uselocale=discard +fun:__wctype_l=discard +fun:access=discard +fun:alarm=discard +fun:atexit=discard +fun:bind=discard +fun:chdir=discard +fun:close=discard +fun:closedir=discard +fun:connect=discard +fun:creat=discard +fun:dladdr=discard +fun:dlclose=discard +fun:epoll_create=discard +fun:epoll_create1=discard +fun:epoll_ctl=discard +fun:fclose=discard +fun:feof=discard +fun:ferror=discard +fun:fflush=discard +fun:fileno=discard +fun:fopen=discard +fun:fprintf=discard +fun:fputc=discard +fun:fputc=discard +fun:fputs=discard +fun:fputs=discard +fun:fseek=discard +fun:ftell=discard +fun:fwrite=discard +fun:getenv=discard +fun:getuid=discard +fun:geteuid=discard +fun:getpagesize=discard +fun:getpid=discard +fun:kill=discard +fun:listen=discard +fun:lseek=discard +fun:mkdir=discard +fun:mmap=discard +fun:munmap=discard +fun:open=discard +fun:openat=discard +fun:pipe=discard +fun:posix_fadvise=discard +fun:prctl=discard +fun:printf=discard +fun:pthread_sigmask=discard +fun:putc=discard +fun:putchar=discard +fun:puts=discard +fun:rand=discard +fun:random=discard +fun:remove=discard +fun:sched_getcpu=discard +fun:sched_get_priority_max=discard +fun:sched_setaffinity=discard +fun:sched_yield=discard +fun:sem_destroy=discard +fun:sem_init=discard +fun:sem_post=discard +fun:sem_wait=discard +fun:send=discard +fun:sendmsg=discard +fun:sendto=discard +fun:setsockopt=discard +fun:shutdown=discard +fun:sleep=discard +fun:socket=discard +fun:strerror=discard +fun:strspn=discard +fun:strcspn=discard +fun:symlink=discard +fun:syscall=discard +fun:unlink=discard +fun:uselocale=discard +fun:vfprintf=discard + +# Functions that produce output does not depend on the input (need to zero the +# shadow manually). +fun:_dl_get_tls_static_info=custom +fun:clock_gettime=custom +fun:dlopen=custom +fun:epoll_wait=custom +fun:fgets=custom +fun:fstat=custom +fun:getcwd=custom +fun:get_current_dir_name=custom +fun:getentropy=custom +fun:gethostname=custom +fun:getpeername=custom +fun:getrlimit=custom +fun:getrusage=custom +fun:getsockname=custom +fun:getsockopt=custom +fun:nanosleep=custom +fun:pread=custom +fun:read=custom +fun:recvmmsg=custom +fun:recvmsg=custom +fun:sigaltstack=custom +fun:socketpair=custom +fun:stat=custom +fun:time=custom + +# Functions that produce an output that depend on the input (propagate the +# shadow manually). +fun:ctime_r=custom +fun:inet_pton=custom +fun:localtime_r=custom +fun:memcpy=custom +fun:memmove=custom +fun:memset=custom +fun:strcpy=custom +fun:strdup=custom +fun:strncpy=custom +fun:strtod=custom +fun:strtol=custom +fun:strtoll=custom +fun:strtoul=custom +fun:strtoull=custom +fun:strcat=custom +fun:strncat=custom +fun:__isoc23_strtod=custom +fun:__isoc23_strtol=custom +fun:__isoc23_strtoll=custom +fun:__isoc23_strtoul=custom +fun:__isoc23_strtoull=custom + +# Functions that produce an output that is computed from the input, but is not +# necessarily data dependent. +fun:bcmp=custom +fun:memchr=custom +fun:memcmp=custom +fun:strcasecmp=custom +fun:strchr=custom +fun:strcmp=custom +fun:strlen=custom +fun:strnlen=custom +fun:strncasecmp=custom +fun:strncmp=custom +fun:strpbrk=custom +fun:strrchr=custom +fun:strstr=custom +fun:strsep=custom + +# Functions which take action based on global state, such as running a callback +# set by a separate function. +fun:write=custom + +# Functions that take a callback (wrap the callback manually). +fun:dl_iterate_phdr=custom + +fun:getpwuid_r=custom +fun:poll=custom +fun:sched_getaffinity=custom +fun:select=custom +fun:sigemptyset=custom +fun:sigaction=custom +fun:signal=custom +fun:gettimeofday=custom + +# sprintf-like +fun:sprintf=custom +fun:snprintf=custom + +# scanf-like +fun:sscanf=custom +fun:__isoc99_sscanf=custom +fun:__isoc23_sscanf=custom + +# TODO: custom +fun:asprintf=discard +fun:qsort=discard + +# fork +fun:fork=custom + +############################################################################### +# pthread +############################################################################### +fun:__pthread_register_cancel=discard +fun:__pthread_unregister_cancel=discard +fun:pthread_attr_destroy=discard +fun:pthread_attr_getaffinity_np=discard +fun:pthread_attr_getdetachstate=discard +fun:pthread_attr_getguardsize=discard +fun:pthread_attr_getinheritsched=discard +fun:pthread_attr_getschedparam=discard +fun:pthread_attr_getschedpolicy=discard +fun:pthread_attr_getscope=discard +fun:pthread_attr_getstack=discard +fun:pthread_attr_getstackaddr=disacrd +fun:pthread_attr_getstacksize=discard +fun:pthread_attr_init=discard +fun:pthread_attr_setaffinity_np=discard +fun:pthread_attr_setdetachstate=discard +fun:pthread_attr_setguardsize=discard +fun:pthread_attr_setinheritsched=discard +fun:pthread_attr_setschedparam=discard +fun:pthread_attr_setschedpolicy=discard +fun:pthread_attr_setscope=discard +fun:pthread_attr_setstack=discard +fun:pthread_attr_setstackaddr=discard +fun:pthread_attr_setstacksize=discard +fun:pthread_equal=discard +fun:pthread_getschedparam=discard +fun:pthread_getspecific=discard +fun:pthread_key_create=discard +fun:pthread_key_delete=discard +fun:pthread_mutex_destroy=discard +fun:pthread_mutex_init=discard +fun:pthread_mutex_lock=discard +fun:pthread_mutex_trylock=discard +fun:pthread_mutex_unlock=discard +fun:pthread_mutexattr_destroy=discard +fun:pthread_mutexattr_init=discard +fun:pthread_mutexattr_settype=discard +fun:pthread_rwlock_destroy=discard +fun:pthread_rwlock_init=discard +fun:pthread_rwlock_rdlock=discard +fun:pthread_rwlock_timedrdlock=discard +fun:pthread_rwlock_timedwrlock=discard +fun:pthread_rwlock_tryrdlock=discard +fun:pthread_rwlock_trywrlock=discard +fun:pthread_rwlock_wrlock=discard +fun:pthread_rwlock_unlock=discard +fun:pthread_setschedparam=discard +fun:pthread_setname_np=discard +fun:pthread_once=discard +fun:pthread_self=discard +fun:pthread_setspecific=discard + +# Functions that take a callback (wrap the callback manually). +fun:pthread_create=custom + +# Functions that produce output does not depend on the input (need to zero the +# shadow manually). +fun:pthread_join=custom + +############################################################################### +# libffi/libgo +############################################################################### +# Functions that are written in asm or are called from asm. +fun:ffi_call_unix64=uninstrumented +fun:ffi_call_unix64=discard +fun:ffi_closure_unix64_inner=uninstrumented +fun:ffi_closure_unix64_inner=discard +fun:ffi_closure_unix64=uninstrumented +fun:ffi_closure_unix64=discard +fun:__go_get_closure=uninstrumented +fun:__go_get_closure=discard +fun:__go_makefunc_can_recover=uninstrumented +fun:__go_makefunc_can_recover=discard +fun:__go_makefunc_returning=uninstrumented +fun:__go_makefunc_returning=discard +fun:reflect.MakeFuncStubGo=uninstrumented +fun:reflect.MakeFuncStubGo=discard +fun:reflect.makeFuncStub=uninstrumented +fun:reflect.makeFuncStub=discard + + +############################################################################### +# lib/Fuzzer +############################################################################### +# Replaces __sanitizer_cov_trace_cmp with __dfsw___sanitizer_cov_trace_cmp +fun:__sanitizer_cov_trace_cmp1=custom +fun:__sanitizer_cov_trace_cmp1=uninstrumented +fun:__sanitizer_cov_trace_cmp2=custom +fun:__sanitizer_cov_trace_cmp2=uninstrumented +fun:__sanitizer_cov_trace_cmp4=custom +fun:__sanitizer_cov_trace_cmp4=uninstrumented +fun:__sanitizer_cov_trace_cmp8=custom +fun:__sanitizer_cov_trace_cmp8=uninstrumented +fun:__sanitizer_cov_trace_const_cmp1=custom +fun:__sanitizer_cov_trace_const_cmp1=uninstrumented +fun:__sanitizer_cov_trace_const_cmp2=custom +fun:__sanitizer_cov_trace_const_cmp2=uninstrumented +fun:__sanitizer_cov_trace_const_cmp4=custom +fun:__sanitizer_cov_trace_const_cmp4=uninstrumented +fun:__sanitizer_cov_trace_const_cmp8=custom +fun:__sanitizer_cov_trace_const_cmp8=uninstrumented +# Similar for __sanitizer_cov_trace_switch +fun:__sanitizer_cov_trace_switch=custom +fun:__sanitizer_cov_trace_switch=uninstrumented + +# Ignores all other __sanitizer callbacks. +fun:__sanitizer_cov=uninstrumented +fun:__sanitizer_cov=discard +fun:__sanitizer_cov_module_init=uninstrumented +fun:__sanitizer_cov_module_init=discard +fun:__sanitizer_cov_with_check=uninstrumented +fun:__sanitizer_cov_with_check=discard +fun:__sanitizer_set_death_callback=uninstrumented +fun:__sanitizer_set_death_callback=discard +fun:__sanitizer_update_counter_bitset_and_clear_counters=uninstrumented +fun:__sanitizer_update_counter_bitset_and_clear_counters=discard +fun:__sanitizer_cov_trace_pc*=uninstrumented +fun:__sanitizer_cov_trace_pc*=discard +fun:__sanitizer_cov_pcs_init=uninstrumented +fun:__sanitizer_cov_pcs_init=discard + +fun:__sanitizer_get_current_allocated_bytes=uninstrumented +fun:__sanitizer_get_current_allocated_bytes=discard +fun:__sanitizer_get_heap_size=uninstrumented +fun:__sanitizer_get_heap_size=discard +fun:__sanitizer_get_free_bytes=uninstrumented +fun:__sanitizer_get_free_bytes=discard +fun:__sanitizer_get_unmapped_bytes=uninstrumented +fun:__sanitizer_get_unmapped_bytes=discard +fun:__sanitizer_get_estimated_allocated_size=uninstrumented +fun:__sanitizer_get_estimated_allocated_size=discard +fun:__sanitizer_get_ownership=uninstrumented +fun:__sanitizer_get_ownership=discard +fun:__sanitizer_get_allocated_begin=uninstrumented +fun:__sanitizer_get_allocated_begin=discard +fun:__sanitizer_get_allocated_size=uninstrumented +fun:__sanitizer_get_allocated_size=discard +fun:__sanitizer_get_allocated_size_fast=uninstrumented +fun:__sanitizer_get_allocated_size_fast=discard +fun:__sanitizer_print_stack_trace=uninstrumented +fun:__sanitizer_print_stack_trace=discard + +fun:TcmallocSlab_Internal_PushBatch_FixedShift=uninstrumented +fun:TcmallocSlab_Internal_PushBatch_FixedShift=discard +fun:TcmallocSlab_Internal_PushBatch_FixedShift_VCPU=uninstrumented +fun:TcmallocSlab_Internal_PushBatch_FixedShift_VCPU=discard +fun:TcmallocSlab_Internal_PerCpuCmpxchg64=uninstrumented +fun:TcmallocSlab_Internal_PerCpuCmpxchg64=discard +fun:TcmallocSlab_Internal_PerCpuCmpxchg64_VCPU=uninstrumented +fun:TcmallocSlab_Internal_PerCpuCmpxchg64_VCPU=discard +fun:TcmallocSlab_Internal_PopBatch_FixedShift=uninstrumented +fun:TcmallocSlab_Internal_PopBatch_FixedShift=discard +fun:TcmallocSlab_Internal_PopBatch_FixedShift_VCPU=uninstrumented +fun:TcmallocSlab_Internal_PopBatch_FixedShift_VCPU=discard + +# Ignores the dfsan wrappers. +fun:__dfsw_*=uninstrumented +fun:__dfsw_*=discard +fun:__dfso_*=uninstrumented +fun:__dfso_*=discard diff --git a/contrib/llvm-project/compiler-rt/lib/dfsan/libc_ubuntu1404_abilist.txt b/contrib/llvm-project/compiler-rt/lib/dfsan/libc_ubuntu1404_abilist.txt new file mode 100644 index 000000000000..9ffa56a23818 --- /dev/null +++ b/contrib/llvm-project/compiler-rt/lib/dfsan/libc_ubuntu1404_abilist.txt @@ -0,0 +1,3439 @@ +fun:__isoc23_sscanf=uninstrumented +fun:__isoc23_strtol=uninstrumented +fun:__isoc23_strtoll=uninstrumented +fun:__isoc23_strtoul=uninstrumented +fun:__isoc23_strtoull=uninstrumented +fun:_Exit=uninstrumented +fun:_IO_adjust_column=uninstrumented +fun:_IO_adjust_wcolumn=uninstrumented +fun:_IO_default_doallocate=uninstrumented +fun:_IO_default_finish=uninstrumented +fun:_IO_default_pbackfail=uninstrumented +fun:_IO_default_uflow=uninstrumented +fun:_IO_default_xsgetn=uninstrumented +fun:_IO_default_xsputn=uninstrumented +fun:_IO_do_write=uninstrumented +fun:_IO_doallocbuf=uninstrumented +fun:_IO_fclose=uninstrumented +fun:_IO_fdopen=uninstrumented +fun:_IO_feof=uninstrumented +fun:_IO_ferror=uninstrumented +fun:_IO_fflush=uninstrumented +fun:_IO_fgetpos=uninstrumented +fun:_IO_fgetpos64=uninstrumented +fun:_IO_fgets=uninstrumented +fun:_IO_file_attach=uninstrumented +fun:_IO_file_close=uninstrumented +fun:_IO_file_close_it=uninstrumented +fun:_IO_file_doallocate=uninstrumented +fun:_IO_file_finish=uninstrumented +fun:_IO_file_fopen=uninstrumented +fun:_IO_file_init=uninstrumented +fun:_IO_file_open=uninstrumented +fun:_IO_file_overflow=uninstrumented +fun:_IO_file_read=uninstrumented +fun:_IO_file_seek=uninstrumented +fun:_IO_file_seekoff=uninstrumented +fun:_IO_file_setbuf=uninstrumented +fun:_IO_file_stat=uninstrumented +fun:_IO_file_sync=uninstrumented +fun:_IO_file_underflow=uninstrumented +fun:_IO_file_write=uninstrumented +fun:_IO_file_xsputn=uninstrumented +fun:_IO_flockfile=uninstrumented +fun:_IO_flush_all=uninstrumented +fun:_IO_flush_all_linebuffered=uninstrumented +fun:_IO_fopen=uninstrumented +fun:_IO_fprintf=uninstrumented +fun:_IO_fputs=uninstrumented +fun:_IO_fread=uninstrumented +fun:_IO_free_backup_area=uninstrumented +fun:_IO_free_wbackup_area=uninstrumented +fun:_IO_fsetpos=uninstrumented +fun:_IO_fsetpos64=uninstrumented +fun:_IO_ftell=uninstrumented +fun:_IO_ftrylockfile=uninstrumented +fun:_IO_funlockfile=uninstrumented +fun:_IO_fwrite=uninstrumented +fun:_IO_getc=uninstrumented +fun:_IO_getline=uninstrumented +fun:_IO_getline_info=uninstrumented +fun:_IO_gets=uninstrumented +fun:_IO_init=uninstrumented +fun:_IO_init_marker=uninstrumented +fun:_IO_init_wmarker=uninstrumented +fun:_IO_iter_begin=uninstrumented +fun:_IO_iter_end=uninstrumented +fun:_IO_iter_file=uninstrumented +fun:_IO_iter_next=uninstrumented +fun:_IO_least_wmarker=uninstrumented +fun:_IO_link_in=uninstrumented +fun:_IO_list_lock=uninstrumented +fun:_IO_list_resetlock=uninstrumented +fun:_IO_list_unlock=uninstrumented +fun:_IO_marker_delta=uninstrumented +fun:_IO_marker_difference=uninstrumented +fun:_IO_padn=uninstrumented +fun:_IO_peekc_locked=uninstrumented +fun:_IO_popen=uninstrumented +fun:_IO_printf=uninstrumented +fun:_IO_proc_close=uninstrumented +fun:_IO_proc_open=uninstrumented +fun:_IO_putc=uninstrumented +fun:_IO_puts=uninstrumented +fun:_IO_remove_marker=uninstrumented +fun:_IO_seekmark=uninstrumented +fun:_IO_seekoff=uninstrumented +fun:_IO_seekpos=uninstrumented +fun:_IO_seekwmark=uninstrumented +fun:_IO_setb=uninstrumented +fun:_IO_setbuffer=uninstrumented +fun:_IO_setvbuf=uninstrumented +fun:_IO_sgetn=uninstrumented +fun:_IO_sprintf=uninstrumented +fun:_IO_sputbackc=uninstrumented +fun:_IO_sputbackwc=uninstrumented +fun:_IO_sscanf=uninstrumented +fun:_IO_str_init_readonly=uninstrumented +fun:_IO_str_init_static=uninstrumented +fun:_IO_str_overflow=uninstrumented +fun:_IO_str_pbackfail=uninstrumented +fun:_IO_str_seekoff=uninstrumented +fun:_IO_str_underflow=uninstrumented +fun:_IO_sungetc=uninstrumented +fun:_IO_sungetwc=uninstrumented +fun:_IO_switch_to_get_mode=uninstrumented +fun:_IO_switch_to_main_wget_area=uninstrumented +fun:_IO_switch_to_wbackup_area=uninstrumented +fun:_IO_switch_to_wget_mode=uninstrumented +fun:_IO_un_link=uninstrumented +fun:_IO_ungetc=uninstrumented +fun:_IO_unsave_markers=uninstrumented +fun:_IO_unsave_wmarkers=uninstrumented +fun:_IO_vfprintf=uninstrumented +fun:_IO_vfscanf=uninstrumented +fun:_IO_vsprintf=uninstrumented +fun:_IO_wdefault_doallocate=uninstrumented +fun:_IO_wdefault_finish=uninstrumented +fun:_IO_wdefault_pbackfail=uninstrumented +fun:_IO_wdefault_uflow=uninstrumented +fun:_IO_wdefault_xsgetn=uninstrumented +fun:_IO_wdefault_xsputn=uninstrumented +fun:_IO_wdo_write=uninstrumented +fun:_IO_wdoallocbuf=uninstrumented +fun:_IO_wfile_overflow=uninstrumented +fun:_IO_wfile_seekoff=uninstrumented +fun:_IO_wfile_sync=uninstrumented +fun:_IO_wfile_underflow=uninstrumented +fun:_IO_wfile_xsputn=uninstrumented +fun:_IO_wmarker_delta=uninstrumented +fun:_IO_wsetb=uninstrumented +fun:_Unwind_Backtrace=uninstrumented +fun:_Unwind_DeleteException=uninstrumented +fun:_Unwind_FindEnclosingFunction=uninstrumented +fun:_Unwind_Find_FDE=uninstrumented +fun:_Unwind_ForcedUnwind=uninstrumented +fun:_Unwind_GetCFA=uninstrumented +fun:_Unwind_GetDataRelBase=uninstrumented +fun:_Unwind_GetGR=uninstrumented +fun:_Unwind_GetIP=uninstrumented +fun:_Unwind_GetIPInfo=uninstrumented +fun:_Unwind_GetLanguageSpecificData=uninstrumented +fun:_Unwind_GetRegionStart=uninstrumented +fun:_Unwind_GetTextRelBase=uninstrumented +fun:_Unwind_RaiseException=uninstrumented +fun:_Unwind_Resume=uninstrumented +fun:_Unwind_Resume_or_Rethrow=uninstrumented +fun:_Unwind_SetGR=uninstrumented +fun:_Unwind_SetIP=uninstrumented +fun:__absvdi2=uninstrumented +fun:__absvsi2=uninstrumented +fun:__absvti2=uninstrumented +fun:__acos_finite=uninstrumented +fun:__acosf_finite=uninstrumented +fun:__acosh_finite=uninstrumented +fun:__acoshf_finite=uninstrumented +fun:__acoshl_finite=uninstrumented +fun:__acosl_finite=uninstrumented +fun:__addtf3=uninstrumented +fun:__addvdi3=uninstrumented +fun:__addvsi3=uninstrumented +fun:__addvti3=uninstrumented +fun:__adjtimex=uninstrumented +fun:__arch_prctl=uninstrumented +fun:__argz_count=uninstrumented +fun:__argz_next=uninstrumented +fun:__argz_stringify=uninstrumented +fun:__ashlti3=uninstrumented +fun:__ashrti3=uninstrumented +fun:__asin_finite=uninstrumented +fun:__asinf_finite=uninstrumented +fun:__asinl_finite=uninstrumented +fun:__asprintf=uninstrumented +fun:__asprintf_chk=uninstrumented +fun:__assert=uninstrumented +fun:__assert_fail=uninstrumented +fun:__assert_perror_fail=uninstrumented +fun:__atan2_finite=uninstrumented +fun:__atan2f_finite=uninstrumented +fun:__atan2l_finite=uninstrumented +fun:__atanh_finite=uninstrumented +fun:__atanhf_finite=uninstrumented +fun:__atanhl_finite=uninstrumented +fun:__b64_ntop=uninstrumented +fun:__b64_pton=uninstrumented +fun:__backtrace=uninstrumented +fun:__backtrace_symbols=uninstrumented +fun:__backtrace_symbols_fd=uninstrumented +fun:__bid128_abs=uninstrumented +fun:__bid128_add=uninstrumented +fun:__bid128_class=uninstrumented +fun:__bid128_copy=uninstrumented +fun:__bid128_copySign=uninstrumented +fun:__bid128_div=uninstrumented +fun:__bid128_fma=uninstrumented +fun:__bid128_from_int32=uninstrumented +fun:__bid128_from_int64=uninstrumented +fun:__bid128_from_uint32=uninstrumented +fun:__bid128_from_uint64=uninstrumented +fun:__bid128_isCanonical=uninstrumented +fun:__bid128_isFinite=uninstrumented +fun:__bid128_isInf=uninstrumented +fun:__bid128_isNaN=uninstrumented +fun:__bid128_isNormal=uninstrumented +fun:__bid128_isSignaling=uninstrumented +fun:__bid128_isSigned=uninstrumented +fun:__bid128_isSubnormal=uninstrumented +fun:__bid128_isZero=uninstrumented +fun:__bid128_mul=uninstrumented +fun:__bid128_negate=uninstrumented +fun:__bid128_quiet_equal=uninstrumented +fun:__bid128_quiet_greater=uninstrumented +fun:__bid128_quiet_greater_equal=uninstrumented +fun:__bid128_quiet_greater_unordered=uninstrumented +fun:__bid128_quiet_less=uninstrumented +fun:__bid128_quiet_less_equal=uninstrumented +fun:__bid128_quiet_less_unordered=uninstrumented +fun:__bid128_quiet_not_equal=uninstrumented +fun:__bid128_quiet_not_greater=uninstrumented +fun:__bid128_quiet_not_less=uninstrumented +fun:__bid128_quiet_ordered=uninstrumented +fun:__bid128_quiet_unordered=uninstrumented +fun:__bid128_radix=uninstrumented +fun:__bid128_sameQuantum=uninstrumented +fun:__bid128_signaling_greater=uninstrumented +fun:__bid128_signaling_greater_equal=uninstrumented +fun:__bid128_signaling_greater_unordered=uninstrumented +fun:__bid128_signaling_less=uninstrumented +fun:__bid128_signaling_less_equal=uninstrumented +fun:__bid128_signaling_less_unordered=uninstrumented +fun:__bid128_signaling_not_greater=uninstrumented +fun:__bid128_signaling_not_less=uninstrumented +fun:__bid128_sub=uninstrumented +fun:__bid128_to_bid32=uninstrumented +fun:__bid128_to_bid64=uninstrumented +fun:__bid128_to_binary128=uninstrumented +fun:__bid128_to_binary32=uninstrumented +fun:__bid128_to_binary64=uninstrumented +fun:__bid128_to_binary80=uninstrumented +fun:__bid128_to_int32_ceil=uninstrumented +fun:__bid128_to_int32_floor=uninstrumented +fun:__bid128_to_int32_int=uninstrumented +fun:__bid128_to_int32_rnint=uninstrumented +fun:__bid128_to_int32_rninta=uninstrumented +fun:__bid128_to_int32_xceil=uninstrumented +fun:__bid128_to_int32_xfloor=uninstrumented +fun:__bid128_to_int32_xint=uninstrumented +fun:__bid128_to_int32_xrnint=uninstrumented +fun:__bid128_to_int32_xrninta=uninstrumented +fun:__bid128_to_int64_ceil=uninstrumented +fun:__bid128_to_int64_floor=uninstrumented +fun:__bid128_to_int64_int=uninstrumented +fun:__bid128_to_int64_rnint=uninstrumented +fun:__bid128_to_int64_rninta=uninstrumented +fun:__bid128_to_int64_xceil=uninstrumented +fun:__bid128_to_int64_xfloor=uninstrumented +fun:__bid128_to_int64_xint=uninstrumented +fun:__bid128_to_int64_xrnint=uninstrumented +fun:__bid128_to_int64_xrninta=uninstrumented +fun:__bid128_to_uint32_ceil=uninstrumented +fun:__bid128_to_uint32_floor=uninstrumented +fun:__bid128_to_uint32_int=uninstrumented +fun:__bid128_to_uint32_rnint=uninstrumented +fun:__bid128_to_uint32_rninta=uninstrumented +fun:__bid128_to_uint32_xceil=uninstrumented +fun:__bid128_to_uint32_xfloor=uninstrumented +fun:__bid128_to_uint32_xint=uninstrumented +fun:__bid128_to_uint32_xrnint=uninstrumented +fun:__bid128_to_uint32_xrninta=uninstrumented +fun:__bid128_to_uint64_ceil=uninstrumented +fun:__bid128_to_uint64_floor=uninstrumented +fun:__bid128_to_uint64_int=uninstrumented +fun:__bid128_to_uint64_rnint=uninstrumented +fun:__bid128_to_uint64_rninta=uninstrumented +fun:__bid128_to_uint64_xceil=uninstrumented +fun:__bid128_to_uint64_xfloor=uninstrumented +fun:__bid128_to_uint64_xint=uninstrumented +fun:__bid128_to_uint64_xrnint=uninstrumented +fun:__bid128_to_uint64_xrninta=uninstrumented +fun:__bid128_totalOrder=uninstrumented +fun:__bid128_totalOrderMag=uninstrumented +fun:__bid128dd_add=uninstrumented +fun:__bid128dd_div=uninstrumented +fun:__bid128dd_mul=uninstrumented +fun:__bid128dd_sub=uninstrumented +fun:__bid128ddd_fma=uninstrumented +fun:__bid128ddq_fma=uninstrumented +fun:__bid128dq_add=uninstrumented +fun:__bid128dq_div=uninstrumented +fun:__bid128dq_mul=uninstrumented +fun:__bid128dq_sub=uninstrumented +fun:__bid128dqd_fma=uninstrumented +fun:__bid128dqq_fma=uninstrumented +fun:__bid128qd_add=uninstrumented +fun:__bid128qd_div=uninstrumented +fun:__bid128qd_mul=uninstrumented +fun:__bid128qd_sub=uninstrumented +fun:__bid128qdd_fma=uninstrumented +fun:__bid128qdq_fma=uninstrumented +fun:__bid128qqd_fma=uninstrumented +fun:__bid32_to_bid128=uninstrumented +fun:__bid32_to_bid64=uninstrumented +fun:__bid32_to_binary128=uninstrumented +fun:__bid32_to_binary32=uninstrumented +fun:__bid32_to_binary64=uninstrumented +fun:__bid32_to_binary80=uninstrumented +fun:__bid64_abs=uninstrumented +fun:__bid64_add=uninstrumented +fun:__bid64_class=uninstrumented +fun:__bid64_copy=uninstrumented +fun:__bid64_copySign=uninstrumented +fun:__bid64_div=uninstrumented +fun:__bid64_from_int32=uninstrumented +fun:__bid64_from_int64=uninstrumented +fun:__bid64_from_uint32=uninstrumented +fun:__bid64_from_uint64=uninstrumented +fun:__bid64_isCanonical=uninstrumented +fun:__bid64_isFinite=uninstrumented +fun:__bid64_isInf=uninstrumented +fun:__bid64_isNaN=uninstrumented +fun:__bid64_isNormal=uninstrumented +fun:__bid64_isSignaling=uninstrumented +fun:__bid64_isSigned=uninstrumented +fun:__bid64_isSubnormal=uninstrumented +fun:__bid64_isZero=uninstrumented +fun:__bid64_mul=uninstrumented +fun:__bid64_negate=uninstrumented +fun:__bid64_quiet_equal=uninstrumented +fun:__bid64_quiet_greater=uninstrumented +fun:__bid64_quiet_greater_equal=uninstrumented +fun:__bid64_quiet_greater_unordered=uninstrumented +fun:__bid64_quiet_less=uninstrumented +fun:__bid64_quiet_less_equal=uninstrumented +fun:__bid64_quiet_less_unordered=uninstrumented +fun:__bid64_quiet_not_equal=uninstrumented +fun:__bid64_quiet_not_greater=uninstrumented +fun:__bid64_quiet_not_less=uninstrumented +fun:__bid64_quiet_ordered=uninstrumented +fun:__bid64_quiet_unordered=uninstrumented +fun:__bid64_radix=uninstrumented +fun:__bid64_sameQuantum=uninstrumented +fun:__bid64_signaling_greater=uninstrumented +fun:__bid64_signaling_greater_equal=uninstrumented +fun:__bid64_signaling_greater_unordered=uninstrumented +fun:__bid64_signaling_less=uninstrumented +fun:__bid64_signaling_less_equal=uninstrumented +fun:__bid64_signaling_less_unordered=uninstrumented +fun:__bid64_signaling_not_greater=uninstrumented +fun:__bid64_signaling_not_less=uninstrumented +fun:__bid64_sub=uninstrumented +fun:__bid64_to_bid128=uninstrumented +fun:__bid64_to_bid32=uninstrumented +fun:__bid64_to_binary128=uninstrumented +fun:__bid64_to_binary32=uninstrumented +fun:__bid64_to_binary64=uninstrumented +fun:__bid64_to_binary80=uninstrumented +fun:__bid64_to_int32_ceil=uninstrumented +fun:__bid64_to_int32_floor=uninstrumented +fun:__bid64_to_int32_int=uninstrumented +fun:__bid64_to_int32_rnint=uninstrumented +fun:__bid64_to_int32_rninta=uninstrumented +fun:__bid64_to_int32_xceil=uninstrumented +fun:__bid64_to_int32_xfloor=uninstrumented +fun:__bid64_to_int32_xint=uninstrumented +fun:__bid64_to_int32_xrnint=uninstrumented +fun:__bid64_to_int32_xrninta=uninstrumented +fun:__bid64_to_int64_ceil=uninstrumented +fun:__bid64_to_int64_floor=uninstrumented +fun:__bid64_to_int64_int=uninstrumented +fun:__bid64_to_int64_rnint=uninstrumented +fun:__bid64_to_int64_rninta=uninstrumented +fun:__bid64_to_int64_xceil=uninstrumented +fun:__bid64_to_int64_xfloor=uninstrumented +fun:__bid64_to_int64_xint=uninstrumented +fun:__bid64_to_int64_xrnint=uninstrumented +fun:__bid64_to_int64_xrninta=uninstrumented +fun:__bid64_to_uint32_ceil=uninstrumented +fun:__bid64_to_uint32_floor=uninstrumented +fun:__bid64_to_uint32_int=uninstrumented +fun:__bid64_to_uint32_rnint=uninstrumented +fun:__bid64_to_uint32_rninta=uninstrumented +fun:__bid64_to_uint32_xceil=uninstrumented +fun:__bid64_to_uint32_xfloor=uninstrumented +fun:__bid64_to_uint32_xint=uninstrumented +fun:__bid64_to_uint32_xrnint=uninstrumented +fun:__bid64_to_uint32_xrninta=uninstrumented +fun:__bid64_to_uint64_ceil=uninstrumented +fun:__bid64_to_uint64_floor=uninstrumented +fun:__bid64_to_uint64_int=uninstrumented +fun:__bid64_to_uint64_rnint=uninstrumented +fun:__bid64_to_uint64_rninta=uninstrumented +fun:__bid64_to_uint64_xceil=uninstrumented +fun:__bid64_to_uint64_xfloor=uninstrumented +fun:__bid64_to_uint64_xint=uninstrumented +fun:__bid64_to_uint64_xrnint=uninstrumented +fun:__bid64_to_uint64_xrninta=uninstrumented +fun:__bid64_totalOrder=uninstrumented +fun:__bid64_totalOrderMag=uninstrumented +fun:__bid64ddq_fma=uninstrumented +fun:__bid64dq_add=uninstrumented +fun:__bid64dq_div=uninstrumented +fun:__bid64dq_mul=uninstrumented +fun:__bid64dq_sub=uninstrumented +fun:__bid64dqd_fma=uninstrumented +fun:__bid64dqq_fma=uninstrumented +fun:__bid64qd_add=uninstrumented +fun:__bid64qd_div=uninstrumented +fun:__bid64qd_mul=uninstrumented +fun:__bid64qd_sub=uninstrumented +fun:__bid64qdd_fma=uninstrumented +fun:__bid64qdq_fma=uninstrumented +fun:__bid64qq_add=uninstrumented +fun:__bid64qq_div=uninstrumented +fun:__bid64qq_mul=uninstrumented +fun:__bid64qq_sub=uninstrumented +fun:__bid64qqd_fma=uninstrumented +fun:__bid64qqq_fma=uninstrumented +fun:__bid_adddd3=uninstrumented +fun:__bid_addsd3=uninstrumented +fun:__bid_addtd3=uninstrumented +fun:__bid_divdd3=uninstrumented +fun:__bid_divsd3=uninstrumented +fun:__bid_divtd3=uninstrumented +fun:__bid_eqdd2=uninstrumented +fun:__bid_eqsd2=uninstrumented +fun:__bid_eqtd2=uninstrumented +fun:__bid_extendddtd2=uninstrumented +fun:__bid_extendddtf=uninstrumented +fun:__bid_extendddxf=uninstrumented +fun:__bid_extenddfdd=uninstrumented +fun:__bid_extenddftd=uninstrumented +fun:__bid_extendsddd2=uninstrumented +fun:__bid_extendsddf=uninstrumented +fun:__bid_extendsdtd2=uninstrumented +fun:__bid_extendsdtf=uninstrumented +fun:__bid_extendsdxf=uninstrumented +fun:__bid_extendsfdd=uninstrumented +fun:__bid_extendsfsd=uninstrumented +fun:__bid_extendsftd=uninstrumented +fun:__bid_extendtftd=uninstrumented +fun:__bid_extendxftd=uninstrumented +fun:__bid_fixdddi=uninstrumented +fun:__bid_fixddsi=uninstrumented +fun:__bid_fixsddi=uninstrumented +fun:__bid_fixsdsi=uninstrumented +fun:__bid_fixtddi=uninstrumented +fun:__bid_fixtdsi=uninstrumented +fun:__bid_fixunsdddi=uninstrumented +fun:__bid_fixunsddsi=uninstrumented +fun:__bid_fixunssddi=uninstrumented +fun:__bid_fixunssdsi=uninstrumented +fun:__bid_fixunstddi=uninstrumented +fun:__bid_fixunstdsi=uninstrumented +fun:__bid_floatdidd=uninstrumented +fun:__bid_floatdisd=uninstrumented +fun:__bid_floatditd=uninstrumented +fun:__bid_floatsidd=uninstrumented +fun:__bid_floatsisd=uninstrumented +fun:__bid_floatsitd=uninstrumented +fun:__bid_floatunsdidd=uninstrumented +fun:__bid_floatunsdisd=uninstrumented +fun:__bid_floatunsditd=uninstrumented +fun:__bid_floatunssidd=uninstrumented +fun:__bid_floatunssisd=uninstrumented +fun:__bid_floatunssitd=uninstrumented +fun:__bid_gedd2=uninstrumented +fun:__bid_gesd2=uninstrumented +fun:__bid_getd2=uninstrumented +fun:__bid_gtdd2=uninstrumented +fun:__bid_gtsd2=uninstrumented +fun:__bid_gttd2=uninstrumented +fun:__bid_ledd2=uninstrumented +fun:__bid_lesd2=uninstrumented +fun:__bid_letd2=uninstrumented +fun:__bid_ltdd2=uninstrumented +fun:__bid_ltsd2=uninstrumented +fun:__bid_lttd2=uninstrumented +fun:__bid_muldd3=uninstrumented +fun:__bid_mulsd3=uninstrumented +fun:__bid_multd3=uninstrumented +fun:__bid_nedd2=uninstrumented +fun:__bid_nesd2=uninstrumented +fun:__bid_netd2=uninstrumented +fun:__bid_round128_19_38=uninstrumented +fun:__bid_round192_39_57=uninstrumented +fun:__bid_round256_58_76=uninstrumented +fun:__bid_round64_2_18=uninstrumented +fun:__bid_subdd3=uninstrumented +fun:__bid_subsd3=uninstrumented +fun:__bid_subtd3=uninstrumented +fun:__bid_truncdddf=uninstrumented +fun:__bid_truncddsd2=uninstrumented +fun:__bid_truncddsf=uninstrumented +fun:__bid_truncdfsd=uninstrumented +fun:__bid_truncsdsf=uninstrumented +fun:__bid_trunctddd2=uninstrumented +fun:__bid_trunctddf=uninstrumented +fun:__bid_trunctdsd2=uninstrumented +fun:__bid_trunctdsf=uninstrumented +fun:__bid_trunctdtf=uninstrumented +fun:__bid_trunctdxf=uninstrumented +fun:__bid_trunctfdd=uninstrumented +fun:__bid_trunctfsd=uninstrumented +fun:__bid_truncxfdd=uninstrumented +fun:__bid_truncxfsd=uninstrumented +fun:__bid_unorddd2=uninstrumented +fun:__bid_unordsd2=uninstrumented +fun:__bid_unordtd2=uninstrumented +fun:__binary128_to_bid128=uninstrumented +fun:__binary128_to_bid32=uninstrumented +fun:__binary128_to_bid64=uninstrumented +fun:__binary32_to_bid128=uninstrumented +fun:__binary32_to_bid32=uninstrumented +fun:__binary32_to_bid64=uninstrumented +fun:__binary64_to_bid128=uninstrumented +fun:__binary64_to_bid32=uninstrumented +fun:__binary64_to_bid64=uninstrumented +fun:__binary80_to_bid128=uninstrumented +fun:__binary80_to_bid32=uninstrumented +fun:__binary80_to_bid64=uninstrumented +fun:__bsd_getpgrp=uninstrumented +fun:__bswapdi2=uninstrumented +fun:__bswapsi2=uninstrumented +fun:__bzero=uninstrumented +fun:__call_tls_dtors=uninstrumented +fun:__chk_fail=uninstrumented +fun:__clear_cache=uninstrumented +fun:__clock_getcpuclockid=uninstrumented +fun:__clock_getres=uninstrumented +fun:__clock_gettime=uninstrumented +fun:__clock_nanosleep=uninstrumented +fun:__clock_settime=uninstrumented +fun:__clog10=uninstrumented +fun:__clog10f=uninstrumented +fun:__clog10l=uninstrumented +fun:__clone=uninstrumented +fun:__close=uninstrumented +fun:__clrsbdi2=uninstrumented +fun:__clrsbti2=uninstrumented +fun:__clzdi2=uninstrumented +fun:__clzti2=uninstrumented +fun:__cmpti2=uninstrumented +fun:__cmsg_nxthdr=uninstrumented +fun:__confstr_chk=uninstrumented +fun:__connect=uninstrumented +fun:__cosh_finite=uninstrumented +fun:__coshf_finite=uninstrumented +fun:__coshl_finite=uninstrumented +fun:__cpu_indicator_init=uninstrumented +fun:__create_ib_request=uninstrumented +fun:__ctype_b_loc=uninstrumented +fun:__ctype_get_mb_cur_max=uninstrumented +fun:__ctype_init=uninstrumented +fun:__ctype_tolower_loc=uninstrumented +fun:__ctype_toupper_loc=uninstrumented +fun:__ctzdi2=uninstrumented +fun:__ctzti2=uninstrumented +fun:__cxa_at_quick_exit=uninstrumented +fun:__cxa_atexit=uninstrumented +fun:__cxa_finalize=uninstrumented +fun:__cxa_thread_atexit_impl=uninstrumented +fun:__cyg_profile_func_enter=uninstrumented +fun:__cyg_profile_func_exit=uninstrumented +fun:__dcgettext=uninstrumented +fun:__default_morecore=uninstrumented +fun:__deregister_frame=uninstrumented +fun:__deregister_frame_info=uninstrumented +fun:__deregister_frame_info_bases=uninstrumented +fun:__dfp_clear_except=uninstrumented +fun:__dfp_get_round=uninstrumented +fun:__dfp_raise_except=uninstrumented +fun:__dfp_set_round=uninstrumented +fun:__dfp_test_except=uninstrumented +fun:__dgettext=uninstrumented +fun:__divdc3=uninstrumented +fun:__divsc3=uninstrumented +fun:__divtc3=uninstrumented +fun:__divtf3=uninstrumented +fun:__divti3=uninstrumented +fun:__divxc3=uninstrumented +fun:__dn_comp=uninstrumented +fun:__dn_count_labels=uninstrumented +fun:__dn_expand=uninstrumented +fun:__dn_skipname=uninstrumented +fun:__do_niscall3=uninstrumented +fun:__dprintf_chk=uninstrumented +fun:__dup2=uninstrumented +fun:__duplocale=uninstrumented +fun:__emutls_get_address=uninstrumented +fun:__emutls_register_common=uninstrumented +fun:__enable_execute_stack=uninstrumented +fun:__endmntent=uninstrumented +fun:__eprintf=uninstrumented +fun:__eqtf2=uninstrumented +fun:__errno_location=uninstrumented +fun:__exp10_finite=uninstrumented +fun:__exp10f_finite=uninstrumented +fun:__exp10l_finite=uninstrumented +fun:__exp2_finite=uninstrumented +fun:__exp2f_finite=uninstrumented +fun:__exp2l_finite=uninstrumented +fun:__exp_finite=uninstrumented +fun:__expf_finite=uninstrumented +fun:__expl_finite=uninstrumented +fun:__extenddftf2=uninstrumented +fun:__extendsftf2=uninstrumented +fun:__extendxftf2=uninstrumented +fun:__fbufsize=uninstrumented +fun:__fcntl=uninstrumented +fun:__fdelt_chk=uninstrumented +fun:__fdelt_warn=uninstrumented +fun:__fentry__=uninstrumented +fun:__ffs=uninstrumented +fun:__ffsdi2=uninstrumented +fun:__ffsti2=uninstrumented +fun:__fgets_chk=uninstrumented +fun:__fgets_unlocked_chk=uninstrumented +fun:__fgetws_chk=uninstrumented +fun:__fgetws_unlocked_chk=uninstrumented +fun:__finite=uninstrumented +fun:__finitef=uninstrumented +fun:__finitel=uninstrumented +fun:__fixdfti=uninstrumented +fun:__fixsfti=uninstrumented +fun:__fixtfdi=uninstrumented +fun:__fixtfsi=uninstrumented +fun:__fixtfti=uninstrumented +fun:__fixunsdfdi=uninstrumented +fun:__fixunsdfti=uninstrumented +fun:__fixunssfdi=uninstrumented +fun:__fixunssfti=uninstrumented +fun:__fixunstfdi=uninstrumented +fun:__fixunstfsi=uninstrumented +fun:__fixunstfti=uninstrumented +fun:__fixunsxfdi=uninstrumented +fun:__fixunsxfti=uninstrumented +fun:__fixxfti=uninstrumented +fun:__flbf=uninstrumented +fun:__floatditf=uninstrumented +fun:__floatsitf=uninstrumented +fun:__floattidf=uninstrumented +fun:__floattisf=uninstrumented +fun:__floattitf=uninstrumented +fun:__floattixf=uninstrumented +fun:__floatunditf=uninstrumented +fun:__floatunsitf=uninstrumented +fun:__floatuntidf=uninstrumented +fun:__floatuntisf=uninstrumented +fun:__floatuntitf=uninstrumented +fun:__floatuntixf=uninstrumented +fun:__fmod_finite=uninstrumented +fun:__fmodf_finite=uninstrumented +fun:__fmodl_finite=uninstrumented +fun:__follow_path=uninstrumented +fun:__fork=uninstrumented +fun:__fortify_fail=uninstrumented +fun:__fp_nquery=uninstrumented +fun:__fp_query=uninstrumented +fun:__fp_resstat=uninstrumented +fun:__fpclassify=uninstrumented +fun:__fpclassifyf=uninstrumented +fun:__fpclassifyl=uninstrumented +fun:__fpending=uninstrumented +fun:__fprintf_chk=uninstrumented +fun:__fpurge=uninstrumented +fun:__fread_chk=uninstrumented +fun:__fread_unlocked_chk=uninstrumented +fun:__freadable=uninstrumented +fun:__freading=uninstrumented +fun:__free_fdresult=uninstrumented +fun:__freelocale=uninstrumented +fun:__fsetlocking=uninstrumented +fun:__fstat=uninstrumented +fun:__fwprintf_chk=uninstrumented +fun:__fwritable=uninstrumented +fun:__fwriting=uninstrumented +fun:__fxstat=uninstrumented +fun:__fxstat64=uninstrumented +fun:__fxstatat=uninstrumented +fun:__fxstatat64=uninstrumented +fun:__gai_sigqueue=uninstrumented +fun:__gamma_r_finite=uninstrumented +fun:__gammaf_r_finite=uninstrumented +fun:__gammal_r_finite=uninstrumented +fun:__gcc_bcmp=uninstrumented +fun:__gcc_personality_v0=uninstrumented +fun:__gconv_get_alias_db=uninstrumented +fun:__gconv_get_cache=uninstrumented +fun:__gconv_get_modules_db=uninstrumented +fun:__generic_findstack=uninstrumented +fun:__generic_morestack=uninstrumented +fun:__generic_morestack_set_initial_sp=uninstrumented +fun:__generic_releasestack=uninstrumented +fun:__get_cpu_features=uninstrumented +fun:__getauxval=uninstrumented +fun:__getcwd_chk=uninstrumented +fun:__getdelim=uninstrumented +fun:__getdomainname_chk=uninstrumented +fun:__getf2=uninstrumented +fun:__getgroups_chk=uninstrumented +fun:__gethostname_chk=uninstrumented +fun:__getlogin_r_chk=uninstrumented +fun:__getmntent_r=uninstrumented +fun:__getpagesize=uninstrumented +fun:__getpgid=uninstrumented +fun:__getpid=uninstrumented +fun:__gets_chk=uninstrumented +fun:__gettimeofday=uninstrumented +fun:__getwd_chk=uninstrumented +fun:__gmtime_r=uninstrumented +fun:__gttf2=uninstrumented +fun:__h_errno_location=uninstrumented +fun:__hostalias=uninstrumented +fun:__hypot_finite=uninstrumented +fun:__hypotf_finite=uninstrumented +fun:__hypotl_finite=uninstrumented +fun:__internal_endnetgrent=uninstrumented +fun:__internal_getnetgrent_r=uninstrumented +fun:__internal_setnetgrent=uninstrumented +fun:__isalnum_l=uninstrumented +fun:__isalpha_l=uninstrumented +fun:__isascii_l=uninstrumented +fun:__isblank_l=uninstrumented +fun:__iscntrl_l=uninstrumented +fun:__isctype=uninstrumented +fun:__isdigit_l=uninstrumented +fun:__isgraph_l=uninstrumented +fun:__isinf=uninstrumented +fun:__isinff=uninstrumented +fun:__isinfl=uninstrumented +fun:__islower_l=uninstrumented +fun:__isnan=uninstrumented +fun:__isnanf=uninstrumented +fun:__isnanl=uninstrumented +fun:__isoc99_fscanf=uninstrumented +fun:__isoc99_fwscanf=uninstrumented +fun:__isoc99_scanf=uninstrumented +fun:__isoc99_sscanf=uninstrumented +fun:__isoc99_swscanf=uninstrumented +fun:__isoc99_vfscanf=uninstrumented +fun:__isoc99_vfwscanf=uninstrumented +fun:__isoc99_vscanf=uninstrumented +fun:__isoc99_vsscanf=uninstrumented +fun:__isoc99_vswscanf=uninstrumented +fun:__isoc99_vwscanf=uninstrumented +fun:__isoc99_wscanf=uninstrumented +fun:__isprint_l=uninstrumented +fun:__ispunct_l=uninstrumented +fun:__issignaling=uninstrumented +fun:__issignalingf=uninstrumented +fun:__issignalingl=uninstrumented +fun:__isspace_l=uninstrumented +fun:__isupper_l=uninstrumented +fun:__iswalnum_l=uninstrumented +fun:__iswalpha_l=uninstrumented +fun:__iswblank_l=uninstrumented +fun:__iswcntrl_l=uninstrumented +fun:__iswctype=uninstrumented +fun:__iswctype_l=uninstrumented +fun:__iswdigit_l=uninstrumented +fun:__iswgraph_l=uninstrumented +fun:__iswlower_l=uninstrumented +fun:__iswprint_l=uninstrumented +fun:__iswpunct_l=uninstrumented +fun:__iswspace_l=uninstrumented +fun:__iswupper_l=uninstrumented +fun:__iswxdigit_l=uninstrumented +fun:__isxdigit_l=uninstrumented +fun:__ivaliduser=uninstrumented +fun:__j0_finite=uninstrumented +fun:__j0f_finite=uninstrumented +fun:__j0l_finite=uninstrumented +fun:__j1_finite=uninstrumented +fun:__j1f_finite=uninstrumented +fun:__j1l_finite=uninstrumented +fun:__jn_finite=uninstrumented +fun:__jnf_finite=uninstrumented +fun:__jnl_finite=uninstrumented +fun:__letf2=uninstrumented +fun:__lgamma_r_finite=uninstrumented +fun:__lgammaf_r_finite=uninstrumented +fun:__lgammal_r_finite=uninstrumented +fun:__libc_alloca_cutoff=uninstrumented +fun:__libc_allocate_rtsig=uninstrumented +fun:__libc_allocate_rtsig_private=uninstrumented +fun:__libc_calloc=uninstrumented +fun:__libc_clntudp_bufcreate=uninstrumented +fun:__libc_csu_fini=uninstrumented +fun:__libc_csu_init=uninstrumented +fun:__libc_current_sigrtmax=uninstrumented +fun:__libc_current_sigrtmax_private=uninstrumented +fun:__libc_current_sigrtmin=uninstrumented +fun:__libc_current_sigrtmin_private=uninstrumented +fun:__libc_dl_error_tsd=uninstrumented +fun:__libc_dlclose=uninstrumented +fun:__libc_dlopen_mode=uninstrumented +fun:__libc_dlsym=uninstrumented +fun:__libc_fatal=uninstrumented +fun:__libc_fork=uninstrumented +fun:__libc_free=uninstrumented +fun:__libc_freeres=uninstrumented +fun:__libc_ifunc_impl_list=uninstrumented +fun:__libc_init_first=uninstrumented +fun:__libc_longjmp=uninstrumented +fun:__libc_mallinfo=uninstrumented +fun:__libc_malloc=uninstrumented +fun:__libc_mallopt=uninstrumented +fun:__libc_memalign=uninstrumented +fun:__libc_pthread_init=uninstrumented +fun:__libc_pvalloc=uninstrumented +fun:__libc_pwrite=uninstrumented +fun:__libc_realloc=uninstrumented +fun:__libc_res_nquery=uninstrumented +fun:__libc_res_nsearch=uninstrumented +fun:__libc_rpc_getport=uninstrumented +fun:__libc_sa_len=uninstrumented +fun:__libc_secure_getenv=uninstrumented +fun:__libc_siglongjmp=uninstrumented +fun:__libc_start_main=uninstrumented +fun:__libc_system=uninstrumented +fun:__libc_thread_freeres=uninstrumented +fun:__libc_valloc=uninstrumented +fun:__loc_aton=uninstrumented +fun:__loc_ntoa=uninstrumented +fun:__log10_finite=uninstrumented +fun:__log10f_finite=uninstrumented +fun:__log10l_finite=uninstrumented +fun:__log2_finite=uninstrumented +fun:__log2f_finite=uninstrumented +fun:__log2l_finite=uninstrumented +fun:__log_finite=uninstrumented +fun:__logf_finite=uninstrumented +fun:__logl_finite=uninstrumented +fun:__longjmp_chk=uninstrumented +fun:__lseek=uninstrumented +fun:__lshrti3=uninstrumented +fun:__lstat=uninstrumented +fun:__lttf2=uninstrumented +fun:__lxstat=uninstrumented +fun:__lxstat64=uninstrumented +fun:__madvise=uninstrumented +fun:__mbrlen=uninstrumented +fun:__mbrtowc=uninstrumented +fun:__mbsnrtowcs_chk=uninstrumented +fun:__mbsrtowcs_chk=uninstrumented +fun:__mbstowcs_chk=uninstrumented +fun:__memcpy_chk=uninstrumented +fun:__memmove_chk=uninstrumented +fun:__mempcpy=uninstrumented +fun:__mempcpy_chk=uninstrumented +fun:__mempcpy_small=uninstrumented +fun:__memset_chk=uninstrumented +fun:__mknod=uninstrumented +fun:__mktemp=uninstrumented +fun:__modti3=uninstrumented +fun:__monstartup=uninstrumented +fun:__morestack=uninstrumented +fun:__morestack_allocate_stack_space=uninstrumented +fun:__morestack_block_signals=uninstrumented +fun:__morestack_fail=uninstrumented +fun:__morestack_get_guard=uninstrumented +fun:__morestack_large_model=uninstrumented +fun:__morestack_load_mmap=uninstrumented +fun:__morestack_make_guard=uninstrumented +fun:__morestack_non_split=uninstrumented +fun:__morestack_release_segments=uninstrumented +fun:__morestack_set_guard=uninstrumented +fun:__morestack_unblock_signals=uninstrumented +fun:__mq_open_2=uninstrumented +fun:__muldc3=uninstrumented +fun:__mulsc3=uninstrumented +fun:__multc3=uninstrumented +fun:__multf3=uninstrumented +fun:__multi3=uninstrumented +fun:__mulvdi3=uninstrumented +fun:__mulvsi3=uninstrumented +fun:__mulvti3=uninstrumented +fun:__mulxc3=uninstrumented +fun:__nanosleep=uninstrumented +fun:__negtf2=uninstrumented +fun:__negti2=uninstrumented +fun:__negvdi2=uninstrumented +fun:__negvsi2=uninstrumented +fun:__negvti2=uninstrumented +fun:__netf2=uninstrumented +fun:__newlocale=uninstrumented +fun:__nis_default_access=uninstrumented +fun:__nis_default_group=uninstrumented +fun:__nis_default_owner=uninstrumented +fun:__nis_default_ttl=uninstrumented +fun:__nis_finddirectory=uninstrumented +fun:__nis_hash=uninstrumented +fun:__nisbind_connect=uninstrumented +fun:__nisbind_create=uninstrumented +fun:__nisbind_destroy=uninstrumented +fun:__nisbind_next=uninstrumented +fun:__nl_langinfo_l=uninstrumented +fun:__ns_get16=uninstrumented +fun:__ns_get32=uninstrumented +fun:__ns_name_ntop=uninstrumented +fun:__ns_name_unpack=uninstrumented +fun:__nss_configure_lookup=uninstrumented +fun:__nss_database_lookup=uninstrumented +fun:__nss_disable_nscd=uninstrumented +fun:__nss_group_lookup=uninstrumented +fun:__nss_group_lookup2=uninstrumented +fun:__nss_hostname_digits_dots=uninstrumented +fun:__nss_hosts_lookup=uninstrumented +fun:__nss_hosts_lookup2=uninstrumented +fun:__nss_lookup=uninstrumented +fun:__nss_lookup_function=uninstrumented +fun:__nss_next=uninstrumented +fun:__nss_next2=uninstrumented +fun:__nss_passwd_lookup=uninstrumented +fun:__nss_passwd_lookup2=uninstrumented +fun:__nss_services_lookup2=uninstrumented +fun:__obstack_printf_chk=uninstrumented +fun:__obstack_vprintf_chk=uninstrumented +fun:__open=uninstrumented +fun:__open64=uninstrumented +fun:__open64_2=uninstrumented +fun:__open_2=uninstrumented +fun:__open_catalog=uninstrumented +fun:__openat64_2=uninstrumented +fun:__openat_2=uninstrumented +fun:__overflow=uninstrumented +fun:__p_cdname=uninstrumented +fun:__p_cdnname=uninstrumented +fun:__p_class=uninstrumented +fun:__p_fqname=uninstrumented +fun:__p_fqnname=uninstrumented +fun:__p_option=uninstrumented +fun:__p_query=uninstrumented +fun:__p_rcode=uninstrumented +fun:__p_secstodate=uninstrumented +fun:__p_time=uninstrumented +fun:__p_type=uninstrumented +fun:__paritydi2=uninstrumented +fun:__parityti2=uninstrumented +fun:__pipe=uninstrumented +fun:__poll=uninstrumented +fun:__poll_chk=uninstrumented +fun:__popcountdi2=uninstrumented +fun:__popcountti2=uninstrumented +fun:__posix_getopt=uninstrumented +fun:__pow_finite=uninstrumented +fun:__powf_finite=uninstrumented +fun:__powidf2=uninstrumented +fun:__powisf2=uninstrumented +fun:__powitf2=uninstrumented +fun:__powixf2=uninstrumented +fun:__powl_finite=uninstrumented +fun:__ppoll_chk=uninstrumented +fun:__pread64=uninstrumented +fun:__pread64_chk=uninstrumented +fun:__pread_chk=uninstrumented +fun:__prepare_niscall=uninstrumented +fun:__printf_chk=uninstrumented +fun:__printf_fp=uninstrumented +fun:__profile_frequency=uninstrumented +fun:__pthread_atfork=uninstrumented +fun:__pthread_cleanup_routine=uninstrumented +fun:__pthread_clock_gettime=uninstrumented +fun:__pthread_clock_settime=uninstrumented +fun:__pthread_get_minstack=uninstrumented +fun:__pthread_getspecific=uninstrumented +fun:__pthread_initialize_minimal=uninstrumented +fun:__pthread_key_create=uninstrumented +fun:__pthread_mutex_destroy=uninstrumented +fun:__pthread_mutex_init=uninstrumented +fun:__pthread_mutex_lock=uninstrumented +fun:__pthread_mutex_trylock=uninstrumented +fun:__pthread_mutex_unlock=uninstrumented +fun:__pthread_mutexattr_destroy=uninstrumented +fun:__pthread_mutexattr_init=uninstrumented +fun:__pthread_mutexattr_settype=uninstrumented +fun:__pthread_once=uninstrumented +fun:__pthread_register_cancel=uninstrumented +fun:__pthread_register_cancel_defer=uninstrumented +fun:__pthread_rwlock_destroy=uninstrumented +fun:__pthread_rwlock_init=uninstrumented +fun:__pthread_rwlock_rdlock=uninstrumented +fun:__pthread_rwlock_tryrdlock=uninstrumented +fun:__pthread_rwlock_trywrlock=uninstrumented +fun:__pthread_rwlock_unlock=uninstrumented +fun:__pthread_rwlock_wrlock=uninstrumented +fun:__pthread_setspecific=uninstrumented +fun:__pthread_unregister_cancel=uninstrumented +fun:__pthread_unregister_cancel_restore=uninstrumented +fun:__pthread_unwind=uninstrumented +fun:__pthread_unwind_next=uninstrumented +fun:__ptsname_r_chk=uninstrumented +fun:__putlong=uninstrumented +fun:__putshort=uninstrumented +fun:__pwrite64=uninstrumented +fun:__rawmemchr=uninstrumented +fun:__read=uninstrumented +fun:__read_chk=uninstrumented +fun:__readlink_chk=uninstrumented +fun:__readlinkat_chk=uninstrumented +fun:__realpath_chk=uninstrumented +fun:__recv_chk=uninstrumented +fun:__recvfrom_chk=uninstrumented +fun:__register_atfork=uninstrumented +fun:__register_frame=uninstrumented +fun:__register_frame_info=uninstrumented +fun:__register_frame_info_bases=uninstrumented +fun:__register_frame_info_table=uninstrumented +fun:__register_frame_info_table_bases=uninstrumented +fun:__register_frame_table=uninstrumented +fun:__remainder_finite=uninstrumented +fun:__remainderf_finite=uninstrumented +fun:__remainderl_finite=uninstrumented +fun:__res_close=uninstrumented +fun:__res_dnok=uninstrumented +fun:__res_hnok=uninstrumented +fun:__res_hostalias=uninstrumented +fun:__res_iclose=uninstrumented +fun:__res_init=uninstrumented +fun:__res_isourserver=uninstrumented +fun:__res_mailok=uninstrumented +fun:__res_maybe_init=uninstrumented +fun:__res_mkquery=uninstrumented +fun:__res_nameinquery=uninstrumented +fun:__res_nclose=uninstrumented +fun:__res_ninit=uninstrumented +fun:__res_nmkquery=uninstrumented +fun:__res_nquery=uninstrumented +fun:__res_nquerydomain=uninstrumented +fun:__res_nsearch=uninstrumented +fun:__res_nsend=uninstrumented +fun:__res_ownok=uninstrumented +fun:__res_queriesmatch=uninstrumented +fun:__res_query=uninstrumented +fun:__res_querydomain=uninstrumented +fun:__res_randomid=uninstrumented +fun:__res_search=uninstrumented +fun:__res_send=uninstrumented +fun:__res_state=uninstrumented +fun:__rpc_thread_createerr=uninstrumented +fun:__rpc_thread_svc_fdset=uninstrumented +fun:__rpc_thread_svc_max_pollfd=uninstrumented +fun:__rpc_thread_svc_pollfd=uninstrumented +fun:__sbrk=uninstrumented +fun:__scalb_finite=uninstrumented +fun:__scalbf_finite=uninstrumented +fun:__scalbl_finite=uninstrumented +fun:__sched_cpualloc=uninstrumented +fun:__sched_cpucount=uninstrumented +fun:__sched_cpufree=uninstrumented +fun:__sched_get_priority_max=uninstrumented +fun:__sched_get_priority_min=uninstrumented +fun:__sched_getparam=uninstrumented +fun:__sched_getscheduler=uninstrumented +fun:__sched_setscheduler=uninstrumented +fun:__sched_yield=uninstrumented +fun:__secure_getenv=uninstrumented +fun:__select=uninstrumented +fun:__send=uninstrumented +fun:__sendmmsg=uninstrumented +fun:__setmntent=uninstrumented +fun:__setpgid=uninstrumented +fun:__sfp_handle_exceptions=uninstrumented +fun:__sigaction=uninstrumented +fun:__sigaddset=uninstrumented +fun:__sigdelset=uninstrumented +fun:__sigismember=uninstrumented +fun:__signbit=uninstrumented +fun:__signbitf=uninstrumented +fun:__signbitl=uninstrumented +fun:__sigpause=uninstrumented +fun:__sigsetjmp=uninstrumented +fun:__sigsuspend=uninstrumented +fun:__sinh_finite=uninstrumented +fun:__sinhf_finite=uninstrumented +fun:__sinhl_finite=uninstrumented +fun:__snprintf_chk=uninstrumented +fun:__splitstack_block_signals=uninstrumented +fun:__splitstack_block_signals_context=uninstrumented +fun:__splitstack_find=uninstrumented +fun:__splitstack_find_context=uninstrumented +fun:__splitstack_getcontext=uninstrumented +fun:__splitstack_makecontext=uninstrumented +fun:__splitstack_releasecontext=uninstrumented +fun:__splitstack_resetcontext=uninstrumented +fun:__splitstack_setcontext=uninstrumented +fun:__sprintf_chk=uninstrumented +fun:__sqrt_finite=uninstrumented +fun:__sqrtf_finite=uninstrumented +fun:__sqrtl_finite=uninstrumented +fun:__stack_chk_fail=uninstrumented +fun:__stack_chk_fail_local=uninstrumented +fun:__stack_split_initialize=uninstrumented +fun:__stat=uninstrumented +fun:__statfs=uninstrumented +fun:__stpcpy=uninstrumented +fun:__stpcpy_chk=uninstrumented +fun:__stpcpy_small=uninstrumented +fun:__stpncpy=uninstrumented +fun:__stpncpy_chk=uninstrumented +fun:__strcasecmp=uninstrumented +fun:__strcasecmp_l=uninstrumented +fun:__strcasestr=uninstrumented +fun:__strcat_chk=uninstrumented +fun:__strcoll_l=uninstrumented +fun:__strcpy_chk=uninstrumented +fun:__strcpy_small=uninstrumented +fun:__strcspn_c1=uninstrumented +fun:__strcspn_c2=uninstrumented +fun:__strcspn_c3=uninstrumented +fun:__strdup=uninstrumented +fun:__strerror_r=uninstrumented +fun:__strfmon_l=uninstrumented +fun:__strftime_l=uninstrumented +fun:__strncasecmp_l=uninstrumented +fun:__strncat_chk=uninstrumented +fun:__strncpy_chk=uninstrumented +fun:__strndup=uninstrumented +fun:__strpbrk_c2=uninstrumented +fun:__strpbrk_c3=uninstrumented +fun:__strsep_1c=uninstrumented +fun:__strsep_2c=uninstrumented +fun:__strsep_3c=uninstrumented +fun:__strsep_g=uninstrumented +fun:__strspn_c1=uninstrumented +fun:__strspn_c2=uninstrumented +fun:__strspn_c3=uninstrumented +fun:__strtod_internal=uninstrumented +fun:__strtod_l=uninstrumented +fun:__strtof_internal=uninstrumented +fun:__strtof_l=uninstrumented +fun:__strtok_r=uninstrumented +fun:__strtok_r_1c=uninstrumented +fun:__strtol_internal=uninstrumented +fun:__strtol_l=uninstrumented +fun:__strtold_internal=uninstrumented +fun:__strtold_l=uninstrumented +fun:__strtoll_internal=uninstrumented +fun:__strtoll_l=uninstrumented +fun:__strtoul_internal=uninstrumented +fun:__strtoul_l=uninstrumented +fun:__strtoull_internal=uninstrumented +fun:__strtoull_l=uninstrumented +fun:__strverscmp=uninstrumented +fun:__strxfrm_l=uninstrumented +fun:__subtf3=uninstrumented +fun:__subvdi3=uninstrumented +fun:__subvsi3=uninstrumented +fun:__subvti3=uninstrumented +fun:__swprintf_chk=uninstrumented +fun:__sym_ntop=uninstrumented +fun:__sym_ntos=uninstrumented +fun:__sym_ston=uninstrumented +fun:__sysconf=uninstrumented +fun:__sysctl=uninstrumented +fun:__syslog_chk=uninstrumented +fun:__sysv_signal=uninstrumented +fun:__tls_get_addr=uninstrumented +fun:__toascii_l=uninstrumented +fun:__tolower_l=uninstrumented +fun:__toupper_l=uninstrumented +fun:__towctrans=uninstrumented +fun:__towctrans_l=uninstrumented +fun:__towlower_l=uninstrumented +fun:__towupper_l=uninstrumented +fun:__trunctfdf2=uninstrumented +fun:__trunctfsf2=uninstrumented +fun:__trunctfxf2=uninstrumented +fun:__ttyname_r_chk=uninstrumented +fun:__ucmpti2=uninstrumented +fun:__udiv_w_sdiv=uninstrumented +fun:__udivmodti4=uninstrumented +fun:__udivti3=uninstrumented +fun:__uflow=uninstrumented +fun:__umodti3=uninstrumented +fun:__underflow=uninstrumented +fun:__unordtf2=uninstrumented +fun:__uselocale=uninstrumented +fun:__vasprintf_chk=uninstrumented +fun:__vdprintf_chk=uninstrumented +fun:__vfork=uninstrumented +fun:__vfprintf_chk=uninstrumented +fun:__vfscanf=uninstrumented +fun:__vfwprintf_chk=uninstrumented +fun:__vprintf_chk=uninstrumented +fun:__vsnprintf=uninstrumented +fun:__vsnprintf_chk=uninstrumented +fun:__vsprintf_chk=uninstrumented +fun:__vsscanf=uninstrumented +fun:__vswprintf_chk=uninstrumented +fun:__vsyslog_chk=uninstrumented +fun:__vwprintf_chk=uninstrumented +fun:__wait=uninstrumented +fun:__waitpid=uninstrumented +fun:__warn_memset_zero_len=uninstrumented +fun:__wcpcpy_chk=uninstrumented +fun:__wcpncpy_chk=uninstrumented +fun:__wcrtomb_chk=uninstrumented +fun:__wcscasecmp_l=uninstrumented +fun:__wcscat_chk=uninstrumented +fun:__wcscoll_l=uninstrumented +fun:__wcscpy_chk=uninstrumented +fun:__wcsftime_l=uninstrumented +fun:__wcsncasecmp_l=uninstrumented +fun:__wcsncat_chk=uninstrumented +fun:__wcsncpy_chk=uninstrumented +fun:__wcsnrtombs_chk=uninstrumented +fun:__wcsrtombs_chk=uninstrumented +fun:__wcstod_internal=uninstrumented +fun:__wcstod_l=uninstrumented +fun:__wcstof_internal=uninstrumented +fun:__wcstof_l=uninstrumented +fun:__wcstol_internal=uninstrumented +fun:__wcstol_l=uninstrumented +fun:__wcstold_internal=uninstrumented +fun:__wcstold_l=uninstrumented +fun:__wcstoll_internal=uninstrumented +fun:__wcstoll_l=uninstrumented +fun:__wcstombs_chk=uninstrumented +fun:__wcstoul_internal=uninstrumented +fun:__wcstoul_l=uninstrumented +fun:__wcstoull_internal=uninstrumented +fun:__wcstoull_l=uninstrumented +fun:__wcsxfrm_l=uninstrumented +fun:__wctomb_chk=uninstrumented +fun:__wctrans_l=uninstrumented +fun:__wctype_l=uninstrumented +fun:__wmemcpy_chk=uninstrumented +fun:__wmemmove_chk=uninstrumented +fun:__wmempcpy_chk=uninstrumented +fun:__wmemset_chk=uninstrumented +fun:__woverflow=uninstrumented +fun:__wprintf_chk=uninstrumented +fun:__wrap_pthread_create=uninstrumented +fun:__write=uninstrumented +fun:__wuflow=uninstrumented +fun:__wunderflow=uninstrumented +fun:__xmknod=uninstrumented +fun:__xmknodat=uninstrumented +fun:__xpg_basename=uninstrumented +fun:__xpg_sigpause=uninstrumented +fun:__xpg_strerror_r=uninstrumented +fun:__xstat=uninstrumented +fun:__xstat64=uninstrumented +fun:__y0_finite=uninstrumented +fun:__y0f_finite=uninstrumented +fun:__y0l_finite=uninstrumented +fun:__y1_finite=uninstrumented +fun:__y1f_finite=uninstrumented +fun:__y1l_finite=uninstrumented +fun:__yn_finite=uninstrumented +fun:__ynf_finite=uninstrumented +fun:__ynl_finite=uninstrumented +fun:__yp_check=uninstrumented +fun:_authenticate=uninstrumented +fun:_dl_addr=uninstrumented +fun:_dl_allocate_tls=uninstrumented +fun:_dl_allocate_tls_init=uninstrumented +fun:_dl_deallocate_tls=uninstrumented +fun:_dl_debug_state=uninstrumented +fun:_dl_find_dso_for_object=uninstrumented +fun:_dl_get_tls_static_info=uninstrumented +fun:_dl_make_stack_executable=uninstrumented +fun:_dl_mcount=uninstrumented +fun:_dl_mcount_wrapper=uninstrumented +fun:_dl_mcount_wrapper_check=uninstrumented +fun:_dl_rtld_di_serinfo=uninstrumented +fun:_dl_sym=uninstrumented +fun:_dl_tls_setup=uninstrumented +fun:_dl_vsym=uninstrumented +fun:_exit=uninstrumented +fun:_flushlbf=uninstrumented +fun:_gethtbyaddr=uninstrumented +fun:_gethtbyname=uninstrumented +fun:_gethtbyname2=uninstrumented +fun:_gethtent=uninstrumented +fun:_getlong=uninstrumented +fun:_getshort=uninstrumented +fun:_longjmp=uninstrumented +fun:_mcleanup=uninstrumented +fun:_mcount=uninstrumented +fun:_nsl_default_nss=uninstrumented +fun:_nss_files_parse_grent=uninstrumented +fun:_nss_files_parse_pwent=uninstrumented +fun:_nss_files_parse_sgent=uninstrumented +fun:_nss_files_parse_spent=uninstrumented +fun:_obstack_allocated_p=uninstrumented +fun:_obstack_begin=uninstrumented +fun:_obstack_begin_1=uninstrumented +fun:_obstack_free=uninstrumented +fun:_obstack_memory_used=uninstrumented +fun:_obstack_newchunk=uninstrumented +fun:_pthread_cleanup_pop=uninstrumented +fun:_pthread_cleanup_pop_restore=uninstrumented +fun:_pthread_cleanup_push=uninstrumented +fun:_pthread_cleanup_push_defer=uninstrumented +fun:_rpc_dtablesize=uninstrumented +fun:_seterr_reply=uninstrumented +fun:_sethtent=uninstrumented +fun:_setjmp=uninstrumented +fun:_tolower=uninstrumented +fun:_toupper=uninstrumented +fun:_xdr_ib_request=uninstrumented +fun:_xdr_nis_result=uninstrumented +fun:a64l=uninstrumented +fun:abort=uninstrumented +fun:abs=uninstrumented +fun:accept=uninstrumented +fun:accept4=uninstrumented +fun:access=uninstrumented +fun:acct=uninstrumented +fun:acos=uninstrumented +fun:acosf=uninstrumented +fun:acosh=uninstrumented +fun:acoshf=uninstrumented +fun:acoshl=uninstrumented +fun:acosl=uninstrumented +fun:addmntent=uninstrumented +fun:addseverity=uninstrumented +fun:adjtime=uninstrumented +fun:adjtimex=uninstrumented +fun:advance=uninstrumented +fun:aio_cancel=uninstrumented +fun:aio_cancel64=uninstrumented +fun:aio_error=uninstrumented +fun:aio_error64=uninstrumented +fun:aio_fsync=uninstrumented +fun:aio_fsync64=uninstrumented +fun:aio_init=uninstrumented +fun:aio_read=uninstrumented +fun:aio_read64=uninstrumented +fun:aio_return=uninstrumented +fun:aio_return64=uninstrumented +fun:aio_suspend=uninstrumented +fun:aio_suspend64=uninstrumented +fun:aio_write=uninstrumented +fun:aio_write64=uninstrumented +fun:alarm=uninstrumented +fun:aligned_alloc=uninstrumented +fun:alphasort=uninstrumented +fun:alphasort64=uninstrumented +fun:arch_prctl=uninstrumented +fun:argp_error=uninstrumented +fun:argp_failure=uninstrumented +fun:argp_help=uninstrumented +fun:argp_parse=uninstrumented +fun:argp_state_help=uninstrumented +fun:argp_usage=uninstrumented +fun:argz_add=uninstrumented +fun:argz_add_sep=uninstrumented +fun:argz_append=uninstrumented +fun:argz_count=uninstrumented +fun:argz_create=uninstrumented +fun:argz_create_sep=uninstrumented +fun:argz_delete=uninstrumented +fun:argz_extract=uninstrumented +fun:argz_insert=uninstrumented +fun:argz_next=uninstrumented +fun:argz_replace=uninstrumented +fun:argz_stringify=uninstrumented +fun:asctime=uninstrumented +fun:asctime_r=uninstrumented +fun:asin=uninstrumented +fun:asinf=uninstrumented +fun:asinh=uninstrumented +fun:asinhf=uninstrumented +fun:asinhl=uninstrumented +fun:asinl=uninstrumented +fun:asprintf=uninstrumented +fun:at_quick_exit=uninstrumented +fun:atan=uninstrumented +fun:atan2=uninstrumented +fun:atan2f=uninstrumented +fun:atan2l=uninstrumented +fun:atanf=uninstrumented +fun:atanh=uninstrumented +fun:atanhf=uninstrumented +fun:atanhl=uninstrumented +fun:atanl=uninstrumented +fun:atexit=uninstrumented +fun:atof=uninstrumented +fun:atoi=uninstrumented +fun:atol=uninstrumented +fun:atoll=uninstrumented +fun:authdes_create=uninstrumented +fun:authdes_getucred=uninstrumented +fun:authdes_pk_create=uninstrumented +fun:authnone_create=uninstrumented +fun:authunix_create=uninstrumented +fun:authunix_create_default=uninstrumented +fun:backtrace=uninstrumented +fun:backtrace_symbols=uninstrumented +fun:backtrace_symbols_fd=uninstrumented +fun:basename=uninstrumented +fun:bcmp=uninstrumented +fun:bcopy=uninstrumented +fun:bdflush=uninstrumented +fun:bind=uninstrumented +fun:bind_textdomain_codeset=uninstrumented +fun:bindresvport=uninstrumented +fun:bindtextdomain=uninstrumented +fun:brk=uninstrumented +fun:bsd_signal=uninstrumented +fun:bsearch=uninstrumented +fun:btowc=uninstrumented +fun:bzero=uninstrumented +fun:c16rtomb=uninstrumented +fun:c32rtomb=uninstrumented +fun:cabs=uninstrumented +fun:cabsf=uninstrumented +fun:cabsl=uninstrumented +fun:cacos=uninstrumented +fun:cacosf=uninstrumented +fun:cacosh=uninstrumented +fun:cacoshf=uninstrumented +fun:cacoshl=uninstrumented +fun:cacosl=uninstrumented +fun:calloc=uninstrumented +fun:callrpc=uninstrumented +fun:canonicalize_file_name=uninstrumented +fun:capget=uninstrumented +fun:capset=uninstrumented +fun:carg=uninstrumented +fun:cargf=uninstrumented +fun:cargl=uninstrumented +fun:casin=uninstrumented +fun:casinf=uninstrumented +fun:casinh=uninstrumented +fun:casinhf=uninstrumented +fun:casinhl=uninstrumented +fun:casinl=uninstrumented +fun:catan=uninstrumented +fun:catanf=uninstrumented +fun:catanh=uninstrumented +fun:catanhf=uninstrumented +fun:catanhl=uninstrumented +fun:catanl=uninstrumented +fun:catclose=uninstrumented +fun:catgets=uninstrumented +fun:catopen=uninstrumented +fun:cbc_crypt=uninstrumented +fun:cbrt=uninstrumented +fun:cbrtf=uninstrumented +fun:cbrtl=uninstrumented +fun:ccos=uninstrumented +fun:ccosf=uninstrumented +fun:ccosh=uninstrumented +fun:ccoshf=uninstrumented +fun:ccoshl=uninstrumented +fun:ccosl=uninstrumented +fun:ceil=uninstrumented +fun:ceilf=uninstrumented +fun:ceill=uninstrumented +fun:cexp=uninstrumented +fun:cexpf=uninstrumented +fun:cexpl=uninstrumented +fun:cfgetispeed=uninstrumented +fun:cfgetospeed=uninstrumented +fun:cfmakeraw=uninstrumented +fun:cfree=uninstrumented +fun:cfsetispeed=uninstrumented +fun:cfsetospeed=uninstrumented +fun:cfsetspeed=uninstrumented +fun:chdir=uninstrumented +fun:chflags=uninstrumented +fun:chmod=uninstrumented +fun:chown=uninstrumented +fun:chroot=uninstrumented +fun:cimag=uninstrumented +fun:cimagf=uninstrumented +fun:cimagl=uninstrumented +fun:clearenv=uninstrumented +fun:clearerr=uninstrumented +fun:clearerr_unlocked=uninstrumented +fun:clnt_broadcast=uninstrumented +fun:clnt_create=uninstrumented +fun:clnt_pcreateerror=uninstrumented +fun:clnt_perrno=uninstrumented +fun:clnt_perror=uninstrumented +fun:clnt_spcreateerror=uninstrumented +fun:clnt_sperrno=uninstrumented +fun:clnt_sperror=uninstrumented +fun:clntraw_create=uninstrumented +fun:clnttcp_create=uninstrumented +fun:clntudp_bufcreate=uninstrumented +fun:clntudp_create=uninstrumented +fun:clntunix_create=uninstrumented +fun:clock=uninstrumented +fun:clock_adjtime=uninstrumented +fun:clock_getcpuclockid=uninstrumented +fun:clock_getres=uninstrumented +fun:clock_gettime=uninstrumented +fun:clock_nanosleep=uninstrumented +fun:clock_settime=uninstrumented +fun:clog=uninstrumented +fun:clog10=uninstrumented +fun:clog10f=uninstrumented +fun:clog10l=uninstrumented +fun:clogf=uninstrumented +fun:clogl=uninstrumented +fun:clone=uninstrumented +fun:close=uninstrumented +fun:closedir=uninstrumented +fun:closelog=uninstrumented +fun:confstr=uninstrumented +fun:conj=uninstrumented +fun:conjf=uninstrumented +fun:conjl=uninstrumented +fun:connect=uninstrumented +fun:copysign=uninstrumented +fun:copysignf=uninstrumented +fun:copysignl=uninstrumented +fun:cos=uninstrumented +fun:cosf=uninstrumented +fun:cosh=uninstrumented +fun:coshf=uninstrumented +fun:coshl=uninstrumented +fun:cosl=uninstrumented +fun:cpow=uninstrumented +fun:cpowf=uninstrumented +fun:cpowl=uninstrumented +fun:cproj=uninstrumented +fun:cprojf=uninstrumented +fun:cprojl=uninstrumented +fun:creal=uninstrumented +fun:crealf=uninstrumented +fun:creall=uninstrumented +fun:creat=uninstrumented +fun:creat64=uninstrumented +fun:create_module=uninstrumented +fun:crypt=uninstrumented +fun:crypt_r=uninstrumented +fun:csin=uninstrumented +fun:csinf=uninstrumented +fun:csinh=uninstrumented +fun:csinhf=uninstrumented +fun:csinhl=uninstrumented +fun:csinl=uninstrumented +fun:csqrt=uninstrumented +fun:csqrtf=uninstrumented +fun:csqrtl=uninstrumented +fun:ctan=uninstrumented +fun:ctanf=uninstrumented +fun:ctanh=uninstrumented +fun:ctanhf=uninstrumented +fun:ctanhl=uninstrumented +fun:ctanl=uninstrumented +fun:ctermid=uninstrumented +fun:ctime=uninstrumented +fun:ctime_r=uninstrumented +fun:cuserid=uninstrumented +fun:daemon=uninstrumented +fun:dcgettext=uninstrumented +fun:dcngettext=uninstrumented +fun:delete_module=uninstrumented +fun:des_setparity=uninstrumented +fun:dgettext=uninstrumented +fun:difftime=uninstrumented +fun:dirfd=uninstrumented +fun:dirname=uninstrumented +fun:div=uninstrumented +fun:dl_iterate_phdr=uninstrumented +fun:dladdr=uninstrumented +fun:dladdr1=uninstrumented +fun:dlclose=uninstrumented +fun:dlerror=uninstrumented +fun:dlinfo=uninstrumented +fun:dlmopen=uninstrumented +fun:dlopen=uninstrumented +fun:dlsym=uninstrumented +fun:dlvsym=uninstrumented +fun:dngettext=uninstrumented +fun:dprintf=uninstrumented +fun:drand48=uninstrumented +fun:drand48_r=uninstrumented +fun:drem=uninstrumented +fun:dremf=uninstrumented +fun:dreml=uninstrumented +fun:dup=uninstrumented +fun:dup2=uninstrumented +fun:dup3=uninstrumented +fun:duplocale=uninstrumented +fun:dysize=uninstrumented +fun:eaccess=uninstrumented +fun:ecb_crypt=uninstrumented +fun:ecvt=uninstrumented +fun:ecvt_r=uninstrumented +fun:encrypt=uninstrumented +fun:encrypt_r=uninstrumented +fun:endaliasent=uninstrumented +fun:endfsent=uninstrumented +fun:endgrent=uninstrumented +fun:endhostent=uninstrumented +fun:endmntent=uninstrumented +fun:endnetent=uninstrumented +fun:endnetgrent=uninstrumented +fun:endprotoent=uninstrumented +fun:endpwent=uninstrumented +fun:endrpcent=uninstrumented +fun:endservent=uninstrumented +fun:endsgent=uninstrumented +fun:endspent=uninstrumented +fun:endttyent=uninstrumented +fun:endusershell=uninstrumented +fun:endutent=uninstrumented +fun:endutxent=uninstrumented +fun:envz_add=uninstrumented +fun:envz_entry=uninstrumented +fun:envz_get=uninstrumented +fun:envz_merge=uninstrumented +fun:envz_remove=uninstrumented +fun:envz_strip=uninstrumented +fun:epoll_create=uninstrumented +fun:epoll_create1=uninstrumented +fun:epoll_ctl=uninstrumented +fun:epoll_pwait=uninstrumented +fun:epoll_wait=uninstrumented +fun:erand48=uninstrumented +fun:erand48_r=uninstrumented +fun:erf=uninstrumented +fun:erfc=uninstrumented +fun:erfcf=uninstrumented +fun:erfcl=uninstrumented +fun:erff=uninstrumented +fun:erfl=uninstrumented +fun:err=uninstrumented +fun:error=uninstrumented +fun:error_at_line=uninstrumented +fun:errx=uninstrumented +fun:ether_aton=uninstrumented +fun:ether_aton_r=uninstrumented +fun:ether_hostton=uninstrumented +fun:ether_line=uninstrumented +fun:ether_ntoa=uninstrumented +fun:ether_ntoa_r=uninstrumented +fun:ether_ntohost=uninstrumented +fun:euidaccess=uninstrumented +fun:eventfd=uninstrumented +fun:eventfd_read=uninstrumented +fun:eventfd_write=uninstrumented +fun:execl=uninstrumented +fun:execle=uninstrumented +fun:execlp=uninstrumented +fun:execv=uninstrumented +fun:execve=uninstrumented +fun:execvp=uninstrumented +fun:execvpe=uninstrumented +fun:exit=uninstrumented +fun:exp=uninstrumented +fun:exp10=uninstrumented +fun:exp10f=uninstrumented +fun:exp10l=uninstrumented +fun:exp2=uninstrumented +fun:exp2f=uninstrumented +fun:exp2l=uninstrumented +fun:expf=uninstrumented +fun:expl=uninstrumented +fun:expm1=uninstrumented +fun:expm1f=uninstrumented +fun:expm1l=uninstrumented +fun:fabs=uninstrumented +fun:fabsf=uninstrumented +fun:fabsl=uninstrumented +fun:faccessat=uninstrumented +fun:fallocate=uninstrumented +fun:fallocate64=uninstrumented +fun:fanotify_init=uninstrumented +fun:fanotify_mark=uninstrumented +fun:fattach=uninstrumented +fun:fchdir=uninstrumented +fun:fchflags=uninstrumented +fun:fchmod=uninstrumented +fun:fchmodat=uninstrumented +fun:fchown=uninstrumented +fun:fchownat=uninstrumented +fun:fclose=uninstrumented +fun:fcloseall=uninstrumented +fun:fcntl=uninstrumented +fun:fcrypt=uninstrumented +fun:fcvt=uninstrumented +fun:fcvt_r=uninstrumented +fun:fdatasync=uninstrumented +fun:fdetach=uninstrumented +fun:fdim=uninstrumented +fun:fdimf=uninstrumented +fun:fdiml=uninstrumented +fun:fdopen=uninstrumented +fun:fdopendir=uninstrumented +fun:feclearexcept=uninstrumented +fun:fedisableexcept=uninstrumented +fun:feenableexcept=uninstrumented +fun:fegetenv=uninstrumented +fun:fegetexcept=uninstrumented +fun:fegetexceptflag=uninstrumented +fun:fegetround=uninstrumented +fun:feholdexcept=uninstrumented +fun:feof=uninstrumented +fun:feof_unlocked=uninstrumented +fun:feraiseexcept=uninstrumented +fun:ferror=uninstrumented +fun:ferror_unlocked=uninstrumented +fun:fesetenv=uninstrumented +fun:fesetexceptflag=uninstrumented +fun:fesetround=uninstrumented +fun:fetestexcept=uninstrumented +fun:feupdateenv=uninstrumented +fun:fexecve=uninstrumented +fun:fflush=uninstrumented +fun:fflush_unlocked=uninstrumented +fun:ffs=uninstrumented +fun:ffsl=uninstrumented +fun:ffsll=uninstrumented +fun:fgetc=uninstrumented +fun:fgetc_unlocked=uninstrumented +fun:fgetgrent=uninstrumented +fun:fgetgrent_r=uninstrumented +fun:fgetpos=uninstrumented +fun:fgetpos64=uninstrumented +fun:fgetpwent=uninstrumented +fun:fgetpwent_r=uninstrumented +fun:fgets=uninstrumented +fun:fgets_unlocked=uninstrumented +fun:fgetsgent=uninstrumented +fun:fgetsgent_r=uninstrumented +fun:fgetspent=uninstrumented +fun:fgetspent_r=uninstrumented +fun:fgetwc=uninstrumented +fun:fgetwc_unlocked=uninstrumented +fun:fgetws=uninstrumented +fun:fgetws_unlocked=uninstrumented +fun:fgetxattr=uninstrumented +fun:fileno=uninstrumented +fun:fileno_unlocked=uninstrumented +fun:finite=uninstrumented +fun:finitef=uninstrumented +fun:finitel=uninstrumented +fun:flistxattr=uninstrumented +fun:flock=uninstrumented +fun:flockfile=uninstrumented +fun:floor=uninstrumented +fun:floorf=uninstrumented +fun:floorl=uninstrumented +fun:fma=uninstrumented +fun:fmaf=uninstrumented +fun:fmal=uninstrumented +fun:fmax=uninstrumented +fun:fmaxf=uninstrumented +fun:fmaxl=uninstrumented +fun:fmemopen=uninstrumented +fun:fmin=uninstrumented +fun:fminf=uninstrumented +fun:fminl=uninstrumented +fun:fmod=uninstrumented +fun:fmodf=uninstrumented +fun:fmodl=uninstrumented +fun:fmtmsg=uninstrumented +fun:fnmatch=uninstrumented +fun:fopen=uninstrumented +fun:fopen64=uninstrumented +fun:fopencookie=uninstrumented +fun:fork=uninstrumented +fun:forkpty=uninstrumented +fun:fpathconf=uninstrumented +fun:fprintf=uninstrumented +fun:fputc=uninstrumented +fun:fputc_unlocked=uninstrumented +fun:fputs=uninstrumented +fun:fputs_unlocked=uninstrumented +fun:fputwc=uninstrumented +fun:fputwc_unlocked=uninstrumented +fun:fputws=uninstrumented +fun:fputws_unlocked=uninstrumented +fun:fread=uninstrumented +fun:fread_unlocked=uninstrumented +fun:free=uninstrumented +fun:freeaddrinfo=uninstrumented +fun:freeifaddrs=uninstrumented +fun:freelocale=uninstrumented +fun:fremovexattr=uninstrumented +fun:freopen=uninstrumented +fun:freopen64=uninstrumented +fun:frexp=uninstrumented +fun:frexpf=uninstrumented +fun:frexpl=uninstrumented +fun:fscanf=uninstrumented +fun:fseek=uninstrumented +fun:fseeko=uninstrumented +fun:fseeko64=uninstrumented +fun:fsetpos=uninstrumented +fun:fsetpos64=uninstrumented +fun:fsetxattr=uninstrumented +fun:fstat=uninstrumented +fun:fstat64=uninstrumented +fun:fstatat=uninstrumented +fun:fstatat64=uninstrumented +fun:fstatfs=uninstrumented +fun:fstatfs64=uninstrumented +fun:fstatvfs=uninstrumented +fun:fstatvfs64=uninstrumented +fun:fsync=uninstrumented +fun:ftell=uninstrumented +fun:ftello=uninstrumented +fun:ftello64=uninstrumented +fun:ftime=uninstrumented +fun:ftok=uninstrumented +fun:ftruncate=uninstrumented +fun:ftruncate64=uninstrumented +fun:ftrylockfile=uninstrumented +fun:fts_children=uninstrumented +fun:fts_close=uninstrumented +fun:fts_open=uninstrumented +fun:fts_read=uninstrumented +fun:fts_set=uninstrumented +fun:ftw=uninstrumented +fun:ftw64=uninstrumented +fun:funlockfile=uninstrumented +fun:futimens=uninstrumented +fun:futimes=uninstrumented +fun:futimesat=uninstrumented +fun:fwide=uninstrumented +fun:fwprintf=uninstrumented +fun:fwrite=uninstrumented +fun:fwrite_unlocked=uninstrumented +fun:fwscanf=uninstrumented +fun:gai_cancel=uninstrumented +fun:gai_error=uninstrumented +fun:gai_strerror=uninstrumented +fun:gai_suspend=uninstrumented +fun:gamma=uninstrumented +fun:gammaf=uninstrumented +fun:gammal=uninstrumented +fun:gcvt=uninstrumented +fun:get_avphys_pages=uninstrumented +fun:get_current_dir_name=uninstrumented +fun:get_kernel_syms=uninstrumented +fun:get_myaddress=uninstrumented +fun:get_nprocs=uninstrumented +fun:get_nprocs_conf=uninstrumented +fun:get_phys_pages=uninstrumented +fun:getaddrinfo=uninstrumented +fun:getaddrinfo_a=uninstrumented +fun:getaliasbyname=uninstrumented +fun:getaliasbyname_r=uninstrumented +fun:getaliasent=uninstrumented +fun:getaliasent_r=uninstrumented +fun:getauxval=uninstrumented +fun:getc=uninstrumented +fun:getc_unlocked=uninstrumented +fun:getchar=uninstrumented +fun:getchar_unlocked=uninstrumented +fun:getcontext=uninstrumented +fun:getcwd=uninstrumented +fun:getdate=uninstrumented +fun:getdate_r=uninstrumented +fun:getdelim=uninstrumented +fun:getdirentries=uninstrumented +fun:getdirentries64=uninstrumented +fun:getdomainname=uninstrumented +fun:getdtablesize=uninstrumented +fun:getegid=uninstrumented +fun:getentropy=uninstrumented +fun:getenv=uninstrumented +fun:geteuid=uninstrumented +fun:getfsent=uninstrumented +fun:getfsfile=uninstrumented +fun:getfsspec=uninstrumented +fun:getgid=uninstrumented +fun:getgrent=uninstrumented +fun:getgrent_r=uninstrumented +fun:getgrgid=uninstrumented +fun:getgrgid_r=uninstrumented +fun:getgrnam=uninstrumented +fun:getgrnam_r=uninstrumented +fun:getgrouplist=uninstrumented +fun:getgroups=uninstrumented +fun:gethostbyaddr=uninstrumented +fun:gethostbyaddr_r=uninstrumented +fun:gethostbyname=uninstrumented +fun:gethostbyname2=uninstrumented +fun:gethostbyname2_r=uninstrumented +fun:gethostbyname_r=uninstrumented +fun:gethostent=uninstrumented +fun:gethostent_r=uninstrumented +fun:gethostid=uninstrumented +fun:gethostname=uninstrumented +fun:getifaddrs=uninstrumented +fun:getipv4sourcefilter=uninstrumented +fun:getitimer=uninstrumented +fun:getline=uninstrumented +fun:getloadavg=uninstrumented +fun:getlogin=uninstrumented +fun:getlogin_r=uninstrumented +fun:getmntent=uninstrumented +fun:getmntent_r=uninstrumented +fun:getmsg=uninstrumented +fun:getnameinfo=uninstrumented +fun:getnetbyaddr=uninstrumented +fun:getnetbyaddr_r=uninstrumented +fun:getnetbyname=uninstrumented +fun:getnetbyname_r=uninstrumented +fun:getnetent=uninstrumented +fun:getnetent_r=uninstrumented +fun:getnetgrent=uninstrumented +fun:getnetgrent_r=uninstrumented +fun:getnetname=uninstrumented +fun:getopt=uninstrumented +fun:getopt_long=uninstrumented +fun:getopt_long_only=uninstrumented +fun:getpagesize=uninstrumented +fun:getpass=uninstrumented +fun:getpeername=uninstrumented +fun:getpgid=uninstrumented +fun:getpgrp=uninstrumented +fun:getpid=uninstrumented +fun:getpmsg=uninstrumented +fun:getppid=uninstrumented +fun:getpriority=uninstrumented +fun:getprotobyname=uninstrumented +fun:getprotobyname_r=uninstrumented +fun:getprotobynumber=uninstrumented +fun:getprotobynumber_r=uninstrumented +fun:getprotoent=uninstrumented +fun:getprotoent_r=uninstrumented +fun:getpt=uninstrumented +fun:getpublickey=uninstrumented +fun:getpw=uninstrumented +fun:getpwent=uninstrumented +fun:getpwent_r=uninstrumented +fun:getpwnam=uninstrumented +fun:getpwnam_r=uninstrumented +fun:getpwuid=uninstrumented +fun:getpwuid_r=uninstrumented +fun:getresgid=uninstrumented +fun:getresuid=uninstrumented +fun:getrlimit=uninstrumented +fun:getrlimit64=uninstrumented +fun:getrpcbyname=uninstrumented +fun:getrpcbyname_r=uninstrumented +fun:getrpcbynumber=uninstrumented +fun:getrpcbynumber_r=uninstrumented +fun:getrpcent=uninstrumented +fun:getrpcent_r=uninstrumented +fun:getrpcport=uninstrumented +fun:getrusage=uninstrumented +fun:gets=uninstrumented +fun:getsecretkey=uninstrumented +fun:getservbyname=uninstrumented +fun:getservbyname_r=uninstrumented +fun:getservbyport=uninstrumented +fun:getservbyport_r=uninstrumented +fun:getservent=uninstrumented +fun:getservent_r=uninstrumented +fun:getsgent=uninstrumented +fun:getsgent_r=uninstrumented +fun:getsgnam=uninstrumented +fun:getsgnam_r=uninstrumented +fun:getsid=uninstrumented +fun:getsockname=uninstrumented +fun:getsockopt=uninstrumented +fun:getsourcefilter=uninstrumented +fun:getspent=uninstrumented +fun:getspent_r=uninstrumented +fun:getspnam=uninstrumented +fun:getspnam_r=uninstrumented +fun:getsubopt=uninstrumented +fun:gettext=uninstrumented +fun:gettimeofday=uninstrumented +fun:getttyent=uninstrumented +fun:getttynam=uninstrumented +fun:getuid=uninstrumented +fun:getusershell=uninstrumented +fun:getutent=uninstrumented +fun:getutent_r=uninstrumented +fun:getutid=uninstrumented +fun:getutid_r=uninstrumented +fun:getutline=uninstrumented +fun:getutline_r=uninstrumented +fun:getutmp=uninstrumented +fun:getutmpx=uninstrumented +fun:getutxent=uninstrumented +fun:getutxid=uninstrumented +fun:getutxline=uninstrumented +fun:getw=uninstrumented +fun:getwc=uninstrumented +fun:getwc_unlocked=uninstrumented +fun:getwchar=uninstrumented +fun:getwchar_unlocked=uninstrumented +fun:getwd=uninstrumented +fun:getxattr=uninstrumented +fun:glob=uninstrumented +fun:glob64=uninstrumented +fun:glob_pattern_p=uninstrumented +fun:globfree=uninstrumented +fun:globfree64=uninstrumented +fun:gmtime=uninstrumented +fun:gmtime_r=uninstrumented +fun:gnu_dev_major=uninstrumented +fun:gnu_dev_makedev=uninstrumented +fun:gnu_dev_minor=uninstrumented +fun:gnu_get_libc_release=uninstrumented +fun:gnu_get_libc_version=uninstrumented +fun:grantpt=uninstrumented +fun:group_member=uninstrumented +fun:gsignal=uninstrumented +fun:gtty=uninstrumented +fun:hasmntopt=uninstrumented +fun:hcreate=uninstrumented +fun:hcreate_r=uninstrumented +fun:hdestroy=uninstrumented +fun:hdestroy_r=uninstrumented +fun:herror=uninstrumented +fun:host2netname=uninstrumented +fun:hsearch=uninstrumented +fun:hsearch_r=uninstrumented +fun:hstrerror=uninstrumented +fun:htonl=uninstrumented +fun:htons=uninstrumented +fun:hypot=uninstrumented +fun:hypotf=uninstrumented +fun:hypotl=uninstrumented +fun:iconv=uninstrumented +fun:iconv_close=uninstrumented +fun:iconv_open=uninstrumented +fun:idna_to_ascii_lz=uninstrumented +fun:idna_to_unicode_lzlz=uninstrumented +fun:if_freenameindex=uninstrumented +fun:if_indextoname=uninstrumented +fun:if_nameindex=uninstrumented +fun:if_nametoindex=uninstrumented +fun:ilogb=uninstrumented +fun:ilogbf=uninstrumented +fun:ilogbl=uninstrumented +fun:imaxabs=uninstrumented +fun:imaxdiv=uninstrumented +fun:index=uninstrumented +fun:inet6_opt_append=uninstrumented +fun:inet6_opt_find=uninstrumented +fun:inet6_opt_finish=uninstrumented +fun:inet6_opt_get_val=uninstrumented +fun:inet6_opt_init=uninstrumented +fun:inet6_opt_next=uninstrumented +fun:inet6_opt_set_val=uninstrumented +fun:inet6_option_alloc=uninstrumented +fun:inet6_option_append=uninstrumented +fun:inet6_option_find=uninstrumented +fun:inet6_option_init=uninstrumented +fun:inet6_option_next=uninstrumented +fun:inet6_option_space=uninstrumented +fun:inet6_rth_add=uninstrumented +fun:inet6_rth_getaddr=uninstrumented +fun:inet6_rth_init=uninstrumented +fun:inet6_rth_reverse=uninstrumented +fun:inet6_rth_segments=uninstrumented +fun:inet6_rth_space=uninstrumented +fun:inet_addr=uninstrumented +fun:inet_aton=uninstrumented +fun:inet_lnaof=uninstrumented +fun:inet_makeaddr=uninstrumented +fun:inet_net_ntop=uninstrumented +fun:inet_net_pton=uninstrumented +fun:inet_neta=uninstrumented +fun:inet_netof=uninstrumented +fun:inet_network=uninstrumented +fun:inet_nsap_addr=uninstrumented +fun:inet_nsap_ntoa=uninstrumented +fun:inet_ntoa=uninstrumented +fun:inet_ntop=uninstrumented +fun:inet_pton=uninstrumented +fun:init_module=uninstrumented +fun:initgroups=uninstrumented +fun:initstate=uninstrumented +fun:initstate_r=uninstrumented +fun:innetgr=uninstrumented +fun:inotify_add_watch=uninstrumented +fun:inotify_init=uninstrumented +fun:inotify_init1=uninstrumented +fun:inotify_rm_watch=uninstrumented +fun:insque=uninstrumented +fun:ioctl=uninstrumented +fun:ioperm=uninstrumented +fun:iopl=uninstrumented +fun:iruserok=uninstrumented +fun:iruserok_af=uninstrumented +fun:isalnum=uninstrumented +fun:isalnum_l=uninstrumented +fun:isalpha=uninstrumented +fun:isalpha_l=uninstrumented +fun:isascii=uninstrumented +fun:isastream=uninstrumented +fun:isatty=uninstrumented +fun:isblank=uninstrumented +fun:isblank_l=uninstrumented +fun:iscntrl=uninstrumented +fun:iscntrl_l=uninstrumented +fun:isctype=uninstrumented +fun:isdigit=uninstrumented +fun:isdigit_l=uninstrumented +fun:isfdtype=uninstrumented +fun:isgraph=uninstrumented +fun:isgraph_l=uninstrumented +fun:isinf=uninstrumented +fun:isinfd128=uninstrumented +fun:isinfd32=uninstrumented +fun:isinfd64=uninstrumented +fun:isinff=uninstrumented +fun:isinfl=uninstrumented +fun:islower=uninstrumented +fun:islower_l=uninstrumented +fun:isnan=uninstrumented +fun:isnanf=uninstrumented +fun:isnanl=uninstrumented +fun:isprint=uninstrumented +fun:isprint_l=uninstrumented +fun:ispunct=uninstrumented +fun:ispunct_l=uninstrumented +fun:isspace=uninstrumented +fun:isspace_l=uninstrumented +fun:isupper=uninstrumented +fun:isupper_l=uninstrumented +fun:iswalnum=uninstrumented +fun:iswalnum_l=uninstrumented +fun:iswalpha=uninstrumented +fun:iswalpha_l=uninstrumented +fun:iswblank=uninstrumented +fun:iswblank_l=uninstrumented +fun:iswcntrl=uninstrumented +fun:iswcntrl_l=uninstrumented +fun:iswctype=uninstrumented +fun:iswctype_l=uninstrumented +fun:iswdigit=uninstrumented +fun:iswdigit_l=uninstrumented +fun:iswgraph=uninstrumented +fun:iswgraph_l=uninstrumented +fun:iswlower=uninstrumented +fun:iswlower_l=uninstrumented +fun:iswprint=uninstrumented +fun:iswprint_l=uninstrumented +fun:iswpunct=uninstrumented +fun:iswpunct_l=uninstrumented +fun:iswspace=uninstrumented +fun:iswspace_l=uninstrumented +fun:iswupper=uninstrumented +fun:iswupper_l=uninstrumented +fun:iswxdigit=uninstrumented +fun:iswxdigit_l=uninstrumented +fun:isxdigit=uninstrumented +fun:isxdigit_l=uninstrumented +fun:j0=uninstrumented +fun:j0f=uninstrumented +fun:j0l=uninstrumented +fun:j1=uninstrumented +fun:j1f=uninstrumented +fun:j1l=uninstrumented +fun:jn=uninstrumented +fun:jnf=uninstrumented +fun:jnl=uninstrumented +fun:jrand48=uninstrumented +fun:jrand48_r=uninstrumented +fun:key_decryptsession=uninstrumented +fun:key_decryptsession_pk=uninstrumented +fun:key_encryptsession=uninstrumented +fun:key_encryptsession_pk=uninstrumented +fun:key_gendes=uninstrumented +fun:key_get_conv=uninstrumented +fun:key_secretkey_is_set=uninstrumented +fun:key_setnet=uninstrumented +fun:key_setsecret=uninstrumented +fun:kill=uninstrumented +fun:killpg=uninstrumented +fun:klogctl=uninstrumented +fun:l64a=uninstrumented +fun:labs=uninstrumented +fun:lchmod=uninstrumented +fun:lchown=uninstrumented +fun:lckpwdf=uninstrumented +fun:lcong48=uninstrumented +fun:lcong48_r=uninstrumented +fun:ldexp=uninstrumented +fun:ldexpf=uninstrumented +fun:ldexpl=uninstrumented +fun:ldiv=uninstrumented +fun:lfind=uninstrumented +fun:lgamma=uninstrumented +fun:lgamma_r=uninstrumented +fun:lgammaf=uninstrumented +fun:lgammaf_r=uninstrumented +fun:lgammal=uninstrumented +fun:lgammal_r=uninstrumented +fun:lgetxattr=uninstrumented +fun:link=uninstrumented +fun:linkat=uninstrumented +fun:lio_listio=uninstrumented +fun:lio_listio64=uninstrumented +fun:listen=uninstrumented +fun:listxattr=uninstrumented +fun:llabs=uninstrumented +fun:lldiv=uninstrumented +fun:llistxattr=uninstrumented +fun:llrint=uninstrumented +fun:llrintf=uninstrumented +fun:llrintl=uninstrumented +fun:llround=uninstrumented +fun:llroundf=uninstrumented +fun:llroundl=uninstrumented +fun:llseek=uninstrumented +fun:localeconv=uninstrumented +fun:localtime=uninstrumented +fun:localtime_r=uninstrumented +fun:lockf=uninstrumented +fun:lockf64=uninstrumented +fun:log=uninstrumented +fun:log10=uninstrumented +fun:log10f=uninstrumented +fun:log10l=uninstrumented +fun:log1p=uninstrumented +fun:log1pf=uninstrumented +fun:log1pl=uninstrumented +fun:log2=uninstrumented +fun:log2f=uninstrumented +fun:log2l=uninstrumented +fun:logb=uninstrumented +fun:logbf=uninstrumented +fun:logbl=uninstrumented +fun:logf=uninstrumented +fun:login=uninstrumented +fun:login_tty=uninstrumented +fun:logl=uninstrumented +fun:logout=uninstrumented +fun:logwtmp=uninstrumented +fun:longjmp=uninstrumented +fun:lrand48=uninstrumented +fun:lrand48_r=uninstrumented +fun:lremovexattr=uninstrumented +fun:lrint=uninstrumented +fun:lrintf=uninstrumented +fun:lrintl=uninstrumented +fun:lround=uninstrumented +fun:lroundf=uninstrumented +fun:lroundl=uninstrumented +fun:lsearch=uninstrumented +fun:lseek=uninstrumented +fun:lseek64=uninstrumented +fun:lsetxattr=uninstrumented +fun:lstat=uninstrumented +fun:lstat64=uninstrumented +fun:lutimes=uninstrumented +fun:madvise=uninstrumented +fun:makecontext=uninstrumented +fun:mallinfo=uninstrumented +fun:malloc=uninstrumented +fun:malloc_get_state=uninstrumented +fun:malloc_info=uninstrumented +fun:malloc_set_state=uninstrumented +fun:malloc_stats=uninstrumented +fun:malloc_trim=uninstrumented +fun:malloc_usable_size=uninstrumented +fun:mallopt=uninstrumented +fun:matherr=uninstrumented +fun:mblen=uninstrumented +fun:mbrlen=uninstrumented +fun:mbrtoc16=uninstrumented +fun:mbrtoc32=uninstrumented +fun:mbrtowc=uninstrumented +fun:mbsinit=uninstrumented +fun:mbsnrtowcs=uninstrumented +fun:mbsrtowcs=uninstrumented +fun:mbstowcs=uninstrumented +fun:mbtowc=uninstrumented +fun:mcheck=uninstrumented +fun:mcheck_check_all=uninstrumented +fun:mcheck_pedantic=uninstrumented +fun:mcount=uninstrumented +fun:memalign=uninstrumented +fun:memccpy=uninstrumented +fun:memchr=uninstrumented +fun:memcmp=uninstrumented +fun:memcpy=uninstrumented +fun:memfrob=uninstrumented +fun:memmem=uninstrumented +fun:memmove=uninstrumented +fun:mempcpy=uninstrumented +fun:memrchr=uninstrumented +fun:memset=uninstrumented +fun:mincore=uninstrumented +fun:mkdir=uninstrumented +fun:mkdirat=uninstrumented +fun:mkdtemp=uninstrumented +fun:mkfifo=uninstrumented +fun:mkfifoat=uninstrumented +fun:mknod=uninstrumented +fun:mknodat=uninstrumented +fun:mkostemp=uninstrumented +fun:mkostemp64=uninstrumented +fun:mkostemps=uninstrumented +fun:mkostemps64=uninstrumented +fun:mkstemp=uninstrumented +fun:mkstemp64=uninstrumented +fun:mkstemps=uninstrumented +fun:mkstemps64=uninstrumented +fun:mktemp=uninstrumented +fun:mktime=uninstrumented +fun:mlock=uninstrumented +fun:mlockall=uninstrumented +fun:mmap=uninstrumented +fun:mmap64=uninstrumented +fun:modf=uninstrumented +fun:modff=uninstrumented +fun:modfl=uninstrumented +fun:modify_ldt=uninstrumented +fun:moncontrol=uninstrumented +fun:monstartup=uninstrumented +fun:mount=uninstrumented +fun:mprobe=uninstrumented +fun:mprotect=uninstrumented +fun:mq_close=uninstrumented +fun:mq_getattr=uninstrumented +fun:mq_notify=uninstrumented +fun:mq_open=uninstrumented +fun:mq_receive=uninstrumented +fun:mq_send=uninstrumented +fun:mq_setattr=uninstrumented +fun:mq_timedreceive=uninstrumented +fun:mq_timedsend=uninstrumented +fun:mq_unlink=uninstrumented +fun:mrand48=uninstrumented +fun:mrand48_r=uninstrumented +fun:mremap=uninstrumented +fun:msgctl=uninstrumented +fun:msgget=uninstrumented +fun:msgrcv=uninstrumented +fun:msgsnd=uninstrumented +fun:msync=uninstrumented +fun:mtrace=uninstrumented +fun:munlock=uninstrumented +fun:munlockall=uninstrumented +fun:munmap=uninstrumented +fun:muntrace=uninstrumented +fun:name_to_handle_at=uninstrumented +fun:nan=uninstrumented +fun:nanf=uninstrumented +fun:nanl=uninstrumented +fun:nanosleep=uninstrumented +fun:nearbyint=uninstrumented +fun:nearbyintf=uninstrumented +fun:nearbyintl=uninstrumented +fun:netname2host=uninstrumented +fun:netname2user=uninstrumented +fun:newlocale=uninstrumented +fun:nextafter=uninstrumented +fun:nextafterf=uninstrumented +fun:nextafterl=uninstrumented +fun:nexttoward=uninstrumented +fun:nexttowardf=uninstrumented +fun:nexttowardl=uninstrumented +fun:nfsservctl=uninstrumented +fun:nftw=uninstrumented +fun:nftw64=uninstrumented +fun:ngettext=uninstrumented +fun:nice=uninstrumented +fun:nis_add=uninstrumented +fun:nis_add_entry=uninstrumented +fun:nis_addmember=uninstrumented +fun:nis_checkpoint=uninstrumented +fun:nis_clone_directory=uninstrumented +fun:nis_clone_object=uninstrumented +fun:nis_clone_result=uninstrumented +fun:nis_creategroup=uninstrumented +fun:nis_destroy_object=uninstrumented +fun:nis_destroygroup=uninstrumented +fun:nis_dir_cmp=uninstrumented +fun:nis_domain_of=uninstrumented +fun:nis_domain_of_r=uninstrumented +fun:nis_first_entry=uninstrumented +fun:nis_free_directory=uninstrumented +fun:nis_free_object=uninstrumented +fun:nis_free_request=uninstrumented +fun:nis_freenames=uninstrumented +fun:nis_freeresult=uninstrumented +fun:nis_freeservlist=uninstrumented +fun:nis_freetags=uninstrumented +fun:nis_getnames=uninstrumented +fun:nis_getservlist=uninstrumented +fun:nis_ismember=uninstrumented +fun:nis_leaf_of=uninstrumented +fun:nis_leaf_of_r=uninstrumented +fun:nis_lerror=uninstrumented +fun:nis_list=uninstrumented +fun:nis_local_directory=uninstrumented +fun:nis_local_group=uninstrumented +fun:nis_local_host=uninstrumented +fun:nis_local_principal=uninstrumented +fun:nis_lookup=uninstrumented +fun:nis_mkdir=uninstrumented +fun:nis_modify=uninstrumented +fun:nis_modify_entry=uninstrumented +fun:nis_name_of=uninstrumented +fun:nis_name_of_r=uninstrumented +fun:nis_next_entry=uninstrumented +fun:nis_perror=uninstrumented +fun:nis_ping=uninstrumented +fun:nis_print_directory=uninstrumented +fun:nis_print_entry=uninstrumented +fun:nis_print_group=uninstrumented +fun:nis_print_group_entry=uninstrumented +fun:nis_print_link=uninstrumented +fun:nis_print_object=uninstrumented +fun:nis_print_result=uninstrumented +fun:nis_print_rights=uninstrumented +fun:nis_print_table=uninstrumented +fun:nis_read_obj=uninstrumented +fun:nis_remove=uninstrumented +fun:nis_remove_entry=uninstrumented +fun:nis_removemember=uninstrumented +fun:nis_rmdir=uninstrumented +fun:nis_servstate=uninstrumented +fun:nis_sperrno=uninstrumented +fun:nis_sperror=uninstrumented +fun:nis_sperror_r=uninstrumented +fun:nis_stats=uninstrumented +fun:nis_verifygroup=uninstrumented +fun:nis_write_obj=uninstrumented +fun:nl_langinfo=uninstrumented +fun:nl_langinfo_l=uninstrumented +fun:nrand48=uninstrumented +fun:nrand48_r=uninstrumented +fun:ns_datetosecs=uninstrumented +fun:ns_format_ttl=uninstrumented +fun:ns_get16=uninstrumented +fun:ns_get32=uninstrumented +fun:ns_initparse=uninstrumented +fun:ns_makecanon=uninstrumented +fun:ns_msg_getflag=uninstrumented +fun:ns_name_compress=uninstrumented +fun:ns_name_ntol=uninstrumented +fun:ns_name_ntop=uninstrumented +fun:ns_name_pack=uninstrumented +fun:ns_name_pton=uninstrumented +fun:ns_name_rollback=uninstrumented +fun:ns_name_skip=uninstrumented +fun:ns_name_uncompress=uninstrumented +fun:ns_name_unpack=uninstrumented +fun:ns_parse_ttl=uninstrumented +fun:ns_parserr=uninstrumented +fun:ns_put16=uninstrumented +fun:ns_put32=uninstrumented +fun:ns_samedomain=uninstrumented +fun:ns_samename=uninstrumented +fun:ns_skiprr=uninstrumented +fun:ns_sprintrr=uninstrumented +fun:ns_sprintrrf=uninstrumented +fun:ns_subdomain=uninstrumented +fun:ntohl=uninstrumented +fun:ntohs=uninstrumented +fun:ntp_adjtime=uninstrumented +fun:ntp_gettime=uninstrumented +fun:ntp_gettimex=uninstrumented +fun:obstack_free=uninstrumented +fun:obstack_printf=uninstrumented +fun:obstack_vprintf=uninstrumented +fun:on_exit=uninstrumented +fun:open=uninstrumented +fun:open64=uninstrumented +fun:open_by_handle_at=uninstrumented +fun:open_memstream=uninstrumented +fun:open_wmemstream=uninstrumented +fun:openat=uninstrumented +fun:openat64=uninstrumented +fun:opendir=uninstrumented +fun:openlog=uninstrumented +fun:openpty=uninstrumented +fun:parse_printf_format=uninstrumented +fun:passwd2des=uninstrumented +fun:pathconf=uninstrumented +fun:pause=uninstrumented +fun:pclose=uninstrumented +fun:perror=uninstrumented +fun:personality=uninstrumented +fun:pipe=uninstrumented +fun:pipe2=uninstrumented +fun:pivot_root=uninstrumented +fun:pmap_getmaps=uninstrumented +fun:pmap_getport=uninstrumented +fun:pmap_rmtcall=uninstrumented +fun:pmap_set=uninstrumented +fun:pmap_unset=uninstrumented +fun:poll=uninstrumented +fun:popen=uninstrumented +fun:posix_fadvise=uninstrumented +fun:posix_fadvise64=uninstrumented +fun:posix_fallocate=uninstrumented +fun:posix_fallocate64=uninstrumented +fun:posix_madvise=uninstrumented +fun:posix_memalign=uninstrumented +fun:posix_openpt=uninstrumented +fun:posix_spawn=uninstrumented +fun:posix_spawn_file_actions_addclose=uninstrumented +fun:posix_spawn_file_actions_adddup2=uninstrumented +fun:posix_spawn_file_actions_addopen=uninstrumented +fun:posix_spawn_file_actions_destroy=uninstrumented +fun:posix_spawn_file_actions_init=uninstrumented +fun:posix_spawnattr_destroy=uninstrumented +fun:posix_spawnattr_getflags=uninstrumented +fun:posix_spawnattr_getpgroup=uninstrumented +fun:posix_spawnattr_getschedparam=uninstrumented +fun:posix_spawnattr_getschedpolicy=uninstrumented +fun:posix_spawnattr_getsigdefault=uninstrumented +fun:posix_spawnattr_getsigmask=uninstrumented +fun:posix_spawnattr_init=uninstrumented +fun:posix_spawnattr_setflags=uninstrumented +fun:posix_spawnattr_setpgroup=uninstrumented +fun:posix_spawnattr_setschedparam=uninstrumented +fun:posix_spawnattr_setschedpolicy=uninstrumented +fun:posix_spawnattr_setsigdefault=uninstrumented +fun:posix_spawnattr_setsigmask=uninstrumented +fun:posix_spawnp=uninstrumented +fun:pow=uninstrumented +fun:pow10=uninstrumented +fun:pow10f=uninstrumented +fun:pow10l=uninstrumented +fun:powf=uninstrumented +fun:powl=uninstrumented +fun:ppoll=uninstrumented +fun:prctl=uninstrumented +fun:pread=uninstrumented +fun:pread64=uninstrumented +fun:preadv=uninstrumented +fun:preadv64=uninstrumented +fun:printf=uninstrumented +fun:printf_size=uninstrumented +fun:printf_size_info=uninstrumented +fun:prlimit=uninstrumented +fun:prlimit64=uninstrumented +fun:process_vm_readv=uninstrumented +fun:process_vm_writev=uninstrumented +fun:profil=uninstrumented +fun:pselect=uninstrumented +fun:psiginfo=uninstrumented +fun:psignal=uninstrumented +fun:pthread_atfork=uninstrumented +fun:pthread_attr_destroy=uninstrumented +fun:pthread_attr_getaffinity_np=uninstrumented +fun:pthread_attr_getdetachstate=uninstrumented +fun:pthread_attr_getguardsize=uninstrumented +fun:pthread_attr_getinheritsched=uninstrumented +fun:pthread_attr_getschedparam=uninstrumented +fun:pthread_attr_getschedpolicy=uninstrumented +fun:pthread_attr_getscope=uninstrumented +fun:pthread_attr_getstack=uninstrumented +fun:pthread_attr_getstackaddr=uninstrumented +fun:pthread_attr_getstacksize=uninstrumented +fun:pthread_attr_init=uninstrumented +fun:pthread_attr_setaffinity_np=uninstrumented +fun:pthread_attr_setdetachstate=uninstrumented +fun:pthread_attr_setguardsize=uninstrumented +fun:pthread_attr_setinheritsched=uninstrumented +fun:pthread_attr_setschedparam=uninstrumented +fun:pthread_attr_setschedpolicy=uninstrumented +fun:pthread_attr_setscope=uninstrumented +fun:pthread_attr_setstack=uninstrumented +fun:pthread_attr_setstackaddr=uninstrumented +fun:pthread_attr_setstacksize=uninstrumented +fun:pthread_barrier_destroy=uninstrumented +fun:pthread_barrier_init=uninstrumented +fun:pthread_barrier_wait=uninstrumented +fun:pthread_barrierattr_destroy=uninstrumented +fun:pthread_barrierattr_getpshared=uninstrumented +fun:pthread_barrierattr_init=uninstrumented +fun:pthread_barrierattr_setpshared=uninstrumented +fun:pthread_cancel=uninstrumented +fun:pthread_cond_broadcast=uninstrumented +fun:pthread_cond_destroy=uninstrumented +fun:pthread_cond_init=uninstrumented +fun:pthread_cond_signal=uninstrumented +fun:pthread_cond_timedwait=uninstrumented +fun:pthread_cond_wait=uninstrumented +fun:pthread_condattr_destroy=uninstrumented +fun:pthread_condattr_getclock=uninstrumented +fun:pthread_condattr_getpshared=uninstrumented +fun:pthread_condattr_init=uninstrumented +fun:pthread_condattr_setclock=uninstrumented +fun:pthread_condattr_setpshared=uninstrumented +fun:pthread_create=uninstrumented +fun:pthread_detach=uninstrumented +fun:pthread_equal=uninstrumented +fun:pthread_exit=uninstrumented +fun:pthread_getaffinity_np=uninstrumented +fun:pthread_getattr_default_np=uninstrumented +fun:pthread_getattr_np=uninstrumented +fun:pthread_getconcurrency=uninstrumented +fun:pthread_getcpuclockid=uninstrumented +fun:pthread_getname_np=uninstrumented +fun:pthread_getschedparam=uninstrumented +fun:pthread_getspecific=uninstrumented +fun:pthread_join=uninstrumented +fun:pthread_key_create=uninstrumented +fun:pthread_key_delete=uninstrumented +fun:pthread_kill=uninstrumented +fun:pthread_kill_other_threads_np=uninstrumented +fun:pthread_mutex_consistent=uninstrumented +fun:pthread_mutex_consistent_np=uninstrumented +fun:pthread_mutex_destroy=uninstrumented +fun:pthread_mutex_getprioceiling=uninstrumented +fun:pthread_mutex_init=uninstrumented +fun:pthread_mutex_lock=uninstrumented +fun:pthread_mutex_setprioceiling=uninstrumented +fun:pthread_mutex_timedlock=uninstrumented +fun:pthread_mutex_trylock=uninstrumented +fun:pthread_mutex_unlock=uninstrumented +fun:pthread_mutexattr_destroy=uninstrumented +fun:pthread_mutexattr_getkind_np=uninstrumented +fun:pthread_mutexattr_getprioceiling=uninstrumented +fun:pthread_mutexattr_getprotocol=uninstrumented +fun:pthread_mutexattr_getpshared=uninstrumented +fun:pthread_mutexattr_getrobust=uninstrumented +fun:pthread_mutexattr_getrobust_np=uninstrumented +fun:pthread_mutexattr_gettype=uninstrumented +fun:pthread_mutexattr_init=uninstrumented +fun:pthread_mutexattr_setkind_np=uninstrumented +fun:pthread_mutexattr_setprioceiling=uninstrumented +fun:pthread_mutexattr_setprotocol=uninstrumented +fun:pthread_mutexattr_setpshared=uninstrumented +fun:pthread_mutexattr_setrobust=uninstrumented +fun:pthread_mutexattr_setrobust_np=uninstrumented +fun:pthread_mutexattr_settype=uninstrumented +fun:pthread_once=uninstrumented +fun:pthread_rwlock_destroy=uninstrumented +fun:pthread_rwlock_init=uninstrumented +fun:pthread_rwlock_rdlock=uninstrumented +fun:pthread_rwlock_timedrdlock=uninstrumented +fun:pthread_rwlock_timedwrlock=uninstrumented +fun:pthread_rwlock_tryrdlock=uninstrumented +fun:pthread_rwlock_trywrlock=uninstrumented +fun:pthread_rwlock_unlock=uninstrumented +fun:pthread_rwlock_wrlock=uninstrumented +fun:pthread_rwlockattr_destroy=uninstrumented +fun:pthread_rwlockattr_getkind_np=uninstrumented +fun:pthread_rwlockattr_getpshared=uninstrumented +fun:pthread_rwlockattr_init=uninstrumented +fun:pthread_rwlockattr_setkind_np=uninstrumented +fun:pthread_rwlockattr_setpshared=uninstrumented +fun:pthread_self=uninstrumented +fun:pthread_setaffinity_np=uninstrumented +fun:pthread_setattr_default_np=uninstrumented +fun:pthread_setcancelstate=uninstrumented +fun:pthread_setcanceltype=uninstrumented +fun:pthread_setconcurrency=uninstrumented +fun:pthread_setname_np=uninstrumented +fun:pthread_setschedparam=uninstrumented +fun:pthread_setschedprio=uninstrumented +fun:pthread_setspecific=uninstrumented +fun:pthread_sigmask=uninstrumented +fun:pthread_sigqueue=uninstrumented +fun:pthread_spin_destroy=uninstrumented +fun:pthread_spin_init=uninstrumented +fun:pthread_spin_lock=uninstrumented +fun:pthread_spin_trylock=uninstrumented +fun:pthread_spin_unlock=uninstrumented +fun:pthread_testcancel=uninstrumented +fun:pthread_timedjoin_np=uninstrumented +fun:pthread_tryjoin_np=uninstrumented +fun:pthread_yield=uninstrumented +fun:ptrace=uninstrumented +fun:ptsname=uninstrumented +fun:ptsname_r=uninstrumented +fun:putc=uninstrumented +fun:putc_unlocked=uninstrumented +fun:putchar=uninstrumented +fun:putchar_unlocked=uninstrumented +fun:putenv=uninstrumented +fun:putgrent=uninstrumented +fun:putmsg=uninstrumented +fun:putpmsg=uninstrumented +fun:putpwent=uninstrumented +fun:puts=uninstrumented +fun:putsgent=uninstrumented +fun:putspent=uninstrumented +fun:pututline=uninstrumented +fun:pututxline=uninstrumented +fun:putw=uninstrumented +fun:putwc=uninstrumented +fun:putwc_unlocked=uninstrumented +fun:putwchar=uninstrumented +fun:putwchar_unlocked=uninstrumented +fun:pvalloc=uninstrumented +fun:pwrite=uninstrumented +fun:pwrite64=uninstrumented +fun:pwritev=uninstrumented +fun:pwritev64=uninstrumented +fun:qecvt=uninstrumented +fun:qecvt_r=uninstrumented +fun:qfcvt=uninstrumented +fun:qfcvt_r=uninstrumented +fun:qgcvt=uninstrumented +fun:qsort=uninstrumented +fun:qsort_r=uninstrumented +fun:query_module=uninstrumented +fun:quick_exit=uninstrumented +fun:quotactl=uninstrumented +fun:raise=uninstrumented +fun:rand=uninstrumented +fun:rand_r=uninstrumented +fun:random=uninstrumented +fun:random_r=uninstrumented +fun:rawmemchr=uninstrumented +fun:rcmd=uninstrumented +fun:rcmd_af=uninstrumented +fun:re_comp=uninstrumented +fun:re_compile_fastmap=uninstrumented +fun:re_compile_pattern=uninstrumented +fun:re_exec=uninstrumented +fun:re_match=uninstrumented +fun:re_match_2=uninstrumented +fun:re_search=uninstrumented +fun:re_search_2=uninstrumented +fun:re_set_registers=uninstrumented +fun:re_set_syntax=uninstrumented +fun:read=uninstrumented +fun:readColdStartFile=uninstrumented +fun:readahead=uninstrumented +fun:readdir=uninstrumented +fun:readdir64=uninstrumented +fun:readdir64_r=uninstrumented +fun:readdir_r=uninstrumented +fun:readlink=uninstrumented +fun:readlinkat=uninstrumented +fun:readv=uninstrumented +fun:realloc=uninstrumented +fun:realpath=uninstrumented +fun:reboot=uninstrumented +fun:recv=uninstrumented +fun:recvfrom=uninstrumented +fun:recvmmsg=uninstrumented +fun:recvmsg=uninstrumented +fun:regcomp=uninstrumented +fun:regerror=uninstrumented +fun:regexec=uninstrumented +fun:regfree=uninstrumented +fun:register_printf_function=uninstrumented +fun:register_printf_modifier=uninstrumented +fun:register_printf_specifier=uninstrumented +fun:register_printf_type=uninstrumented +fun:registerrpc=uninstrumented +fun:remainder=uninstrumented +fun:remainderf=uninstrumented +fun:remainderl=uninstrumented +fun:remap_file_pages=uninstrumented +fun:remove=uninstrumented +fun:removexattr=uninstrumented +fun:remque=uninstrumented +fun:remquo=uninstrumented +fun:remquof=uninstrumented +fun:remquol=uninstrumented +fun:rename=uninstrumented +fun:renameat=uninstrumented +fun:res_gethostbyaddr=uninstrumented +fun:res_gethostbyname=uninstrumented +fun:res_gethostbyname2=uninstrumented +fun:res_send_setqhook=uninstrumented +fun:res_send_setrhook=uninstrumented +fun:revoke=uninstrumented +fun:rewind=uninstrumented +fun:rewinddir=uninstrumented +fun:rexec=uninstrumented +fun:rexec_af=uninstrumented +fun:rindex=uninstrumented +fun:rint=uninstrumented +fun:rintf=uninstrumented +fun:rintl=uninstrumented +fun:rmdir=uninstrumented +fun:round=uninstrumented +fun:roundf=uninstrumented +fun:roundl=uninstrumented +fun:rpmatch=uninstrumented +fun:rresvport=uninstrumented +fun:rresvport_af=uninstrumented +fun:rtime=uninstrumented +fun:ruserok=uninstrumented +fun:ruserok_af=uninstrumented +fun:ruserpass=uninstrumented +fun:sbrk=uninstrumented +fun:scalb=uninstrumented +fun:scalbf=uninstrumented +fun:scalbl=uninstrumented +fun:scalbln=uninstrumented +fun:scalblnf=uninstrumented +fun:scalblnl=uninstrumented +fun:scalbn=uninstrumented +fun:scalbnf=uninstrumented +fun:scalbnl=uninstrumented +fun:scandir=uninstrumented +fun:scandir64=uninstrumented +fun:scandirat=uninstrumented +fun:scandirat64=uninstrumented +fun:scanf=uninstrumented +fun:sched_get_priority_max=uninstrumented +fun:sched_get_priority_min=uninstrumented +fun:sched_getaffinity=uninstrumented +fun:sched_getcpu=uninstrumented +fun:sched_getparam=uninstrumented +fun:sched_getscheduler=uninstrumented +fun:sched_rr_get_interval=uninstrumented +fun:sched_setaffinity=uninstrumented +fun:sched_setparam=uninstrumented +fun:sched_setscheduler=uninstrumented +fun:sched_yield=uninstrumented +fun:secure_getenv=uninstrumented +fun:seed48=uninstrumented +fun:seed48_r=uninstrumented +fun:seekdir=uninstrumented +fun:select=uninstrumented +fun:sem_close=uninstrumented +fun:sem_destroy=uninstrumented +fun:sem_getvalue=uninstrumented +fun:sem_init=uninstrumented +fun:sem_open=uninstrumented +fun:sem_post=uninstrumented +fun:sem_timedwait=uninstrumented +fun:sem_trywait=uninstrumented +fun:sem_unlink=uninstrumented +fun:sem_wait=uninstrumented +fun:semctl=uninstrumented +fun:semget=uninstrumented +fun:semop=uninstrumented +fun:semtimedop=uninstrumented +fun:send=uninstrumented +fun:sendfile=uninstrumented +fun:sendfile64=uninstrumented +fun:sendmmsg=uninstrumented +fun:sendmsg=uninstrumented +fun:sendto=uninstrumented +fun:setaliasent=uninstrumented +fun:setbuf=uninstrumented +fun:setbuffer=uninstrumented +fun:setcontext=uninstrumented +fun:setdomainname=uninstrumented +fun:setegid=uninstrumented +fun:setenv=uninstrumented +fun:seteuid=uninstrumented +fun:setfsent=uninstrumented +fun:setfsgid=uninstrumented +fun:setfsuid=uninstrumented +fun:setgid=uninstrumented +fun:setgrent=uninstrumented +fun:setgroups=uninstrumented +fun:sethostent=uninstrumented +fun:sethostid=uninstrumented +fun:sethostname=uninstrumented +fun:setipv4sourcefilter=uninstrumented +fun:setitimer=uninstrumented +fun:setjmp=uninstrumented +fun:setkey=uninstrumented +fun:setkey_r=uninstrumented +fun:setlinebuf=uninstrumented +fun:setlocale=uninstrumented +fun:setlogin=uninstrumented +fun:setlogmask=uninstrumented +fun:setmntent=uninstrumented +fun:setnetent=uninstrumented +fun:setnetgrent=uninstrumented +fun:setns=uninstrumented +fun:setpgid=uninstrumented +fun:setpgrp=uninstrumented +fun:setpriority=uninstrumented +fun:setprotoent=uninstrumented +fun:setpwent=uninstrumented +fun:setregid=uninstrumented +fun:setresgid=uninstrumented +fun:setresuid=uninstrumented +fun:setreuid=uninstrumented +fun:setrlimit=uninstrumented +fun:setrlimit64=uninstrumented +fun:setrpcent=uninstrumented +fun:setservent=uninstrumented +fun:setsgent=uninstrumented +fun:setsid=uninstrumented +fun:setsockopt=uninstrumented +fun:setsourcefilter=uninstrumented +fun:setspent=uninstrumented +fun:setstate=uninstrumented +fun:setstate_r=uninstrumented +fun:settimeofday=uninstrumented +fun:setttyent=uninstrumented +fun:setuid=uninstrumented +fun:setusershell=uninstrumented +fun:setutent=uninstrumented +fun:setutxent=uninstrumented +fun:setvbuf=uninstrumented +fun:setxattr=uninstrumented +fun:sgetsgent=uninstrumented +fun:sgetsgent_r=uninstrumented +fun:sgetspent=uninstrumented +fun:sgetspent_r=uninstrumented +fun:shm_open=uninstrumented +fun:shm_unlink=uninstrumented +fun:shmat=uninstrumented +fun:shmctl=uninstrumented +fun:shmdt=uninstrumented +fun:shmget=uninstrumented +fun:shutdown=uninstrumented +fun:sigaction=uninstrumented +fun:sigaddset=uninstrumented +fun:sigaltstack=uninstrumented +fun:sigandset=uninstrumented +fun:sigblock=uninstrumented +fun:sigdelset=uninstrumented +fun:sigemptyset=uninstrumented +fun:sigfillset=uninstrumented +fun:siggetmask=uninstrumented +fun:sighold=uninstrumented +fun:sigignore=uninstrumented +fun:siginterrupt=uninstrumented +fun:sigisemptyset=uninstrumented +fun:sigismember=uninstrumented +fun:siglongjmp=uninstrumented +fun:signal=uninstrumented +fun:signalfd=uninstrumented +fun:significand=uninstrumented +fun:significandf=uninstrumented +fun:significandl=uninstrumented +fun:sigorset=uninstrumented +fun:sigpause=uninstrumented +fun:sigpending=uninstrumented +fun:sigprocmask=uninstrumented +fun:sigqueue=uninstrumented +fun:sigrelse=uninstrumented +fun:sigreturn=uninstrumented +fun:sigset=uninstrumented +fun:sigsetmask=uninstrumented +fun:sigstack=uninstrumented +fun:sigsuspend=uninstrumented +fun:sigtimedwait=uninstrumented +fun:sigvec=uninstrumented +fun:sigwait=uninstrumented +fun:sigwaitinfo=uninstrumented +fun:sin=uninstrumented +fun:sincos=uninstrumented +fun:sincosf=uninstrumented +fun:sincosl=uninstrumented +fun:sinf=uninstrumented +fun:sinh=uninstrumented +fun:sinhf=uninstrumented +fun:sinhl=uninstrumented +fun:sinl=uninstrumented +fun:sleep=uninstrumented +fun:snprintf=uninstrumented +fun:sockatmark=uninstrumented +fun:socket=uninstrumented +fun:socketpair=uninstrumented +fun:splice=uninstrumented +fun:sprintf=uninstrumented +fun:sprofil=uninstrumented +fun:sqrt=uninstrumented +fun:sqrtf=uninstrumented +fun:sqrtl=uninstrumented +fun:srand=uninstrumented +fun:srand48=uninstrumented +fun:srand48_r=uninstrumented +fun:srandom=uninstrumented +fun:srandom_r=uninstrumented +fun:sscanf=uninstrumented +fun:ssignal=uninstrumented +fun:sstk=uninstrumented +fun:stat=uninstrumented +fun:stat64=uninstrumented +fun:statfs=uninstrumented +fun:statfs64=uninstrumented +fun:statvfs=uninstrumented +fun:statvfs64=uninstrumented +fun:step=uninstrumented +fun:stime=uninstrumented +fun:stpcpy=uninstrumented +fun:stpncpy=uninstrumented +fun:strcasecmp=uninstrumented +fun:strcasecmp_l=uninstrumented +fun:strcasestr=uninstrumented +fun:strcat=uninstrumented +fun:strchr=uninstrumented +fun:strchrnul=uninstrumented +fun:strcmp=uninstrumented +fun:strcoll=uninstrumented +fun:strcoll_l=uninstrumented +fun:strcpy=uninstrumented +fun:strcspn=uninstrumented +fun:strdup=uninstrumented +fun:strerror=uninstrumented +fun:strerror_l=uninstrumented +fun:strerror_r=uninstrumented +fun:strfmon=uninstrumented +fun:strfmon_l=uninstrumented +fun:strfry=uninstrumented +fun:strftime=uninstrumented +fun:strftime_l=uninstrumented +fun:strlen=uninstrumented +fun:strncasecmp=uninstrumented +fun:strncasecmp_l=uninstrumented +fun:strncat=uninstrumented +fun:strncmp=uninstrumented +fun:strncpy=uninstrumented +fun:strndup=uninstrumented +fun:strnlen=uninstrumented +fun:strpbrk=uninstrumented +fun:strptime=uninstrumented +fun:strptime_l=uninstrumented +fun:strrchr=uninstrumented +fun:strsep=uninstrumented +fun:strsignal=uninstrumented +fun:strspn=uninstrumented +fun:strstr=uninstrumented +fun:strtod=uninstrumented +fun:strtod_l=uninstrumented +fun:strtof=uninstrumented +fun:strtof_l=uninstrumented +fun:strtoimax=uninstrumented +fun:strtok=uninstrumented +fun:strtok_r=uninstrumented +fun:strtol=uninstrumented +fun:strtol_l=uninstrumented +fun:strtold=uninstrumented +fun:strtold_l=uninstrumented +fun:strtoll=uninstrumented +fun:strtoll_l=uninstrumented +fun:strtoq=uninstrumented +fun:strtoul=uninstrumented +fun:strtoul_l=uninstrumented +fun:strtoull=uninstrumented +fun:strtoull_l=uninstrumented +fun:strtoumax=uninstrumented +fun:strtouq=uninstrumented +fun:strverscmp=uninstrumented +fun:strxfrm=uninstrumented +fun:strxfrm_l=uninstrumented +fun:stty=uninstrumented +fun:svc_exit=uninstrumented +fun:svc_getreq=uninstrumented +fun:svc_getreq_common=uninstrumented +fun:svc_getreq_poll=uninstrumented +fun:svc_getreqset=uninstrumented +fun:svc_register=uninstrumented +fun:svc_run=uninstrumented +fun:svc_sendreply=uninstrumented +fun:svc_unregister=uninstrumented +fun:svcerr_auth=uninstrumented +fun:svcerr_decode=uninstrumented +fun:svcerr_noproc=uninstrumented +fun:svcerr_noprog=uninstrumented +fun:svcerr_progvers=uninstrumented +fun:svcerr_systemerr=uninstrumented +fun:svcerr_weakauth=uninstrumented +fun:svcfd_create=uninstrumented +fun:svcraw_create=uninstrumented +fun:svctcp_create=uninstrumented +fun:svcudp_bufcreate=uninstrumented +fun:svcudp_create=uninstrumented +fun:svcudp_enablecache=uninstrumented +fun:svcunix_create=uninstrumented +fun:svcunixfd_create=uninstrumented +fun:swab=uninstrumented +fun:swapcontext=uninstrumented +fun:swapoff=uninstrumented +fun:swapon=uninstrumented +fun:swprintf=uninstrumented +fun:swscanf=uninstrumented +fun:symlink=uninstrumented +fun:symlinkat=uninstrumented +fun:sync=uninstrumented +fun:sync_file_range=uninstrumented +fun:syncfs=uninstrumented +fun:syscall=uninstrumented +fun:sysconf=uninstrumented +fun:sysctl=uninstrumented +fun:sysinfo=uninstrumented +fun:syslog=uninstrumented +fun:system=uninstrumented +fun:sysv_signal=uninstrumented +fun:tan=uninstrumented +fun:tanf=uninstrumented +fun:tanh=uninstrumented +fun:tanhf=uninstrumented +fun:tanhl=uninstrumented +fun:tanl=uninstrumented +fun:tcdrain=uninstrumented +fun:tcflow=uninstrumented +fun:tcflush=uninstrumented +fun:tcgetattr=uninstrumented +fun:tcgetpgrp=uninstrumented +fun:tcgetsid=uninstrumented +fun:tcsendbreak=uninstrumented +fun:tcsetattr=uninstrumented +fun:tcsetpgrp=uninstrumented +fun:td_init=uninstrumented +fun:td_log=uninstrumented +fun:td_symbol_list=uninstrumented +fun:td_ta_clear_event=uninstrumented +fun:td_ta_delete=uninstrumented +fun:td_ta_enable_stats=uninstrumented +fun:td_ta_event_addr=uninstrumented +fun:td_ta_event_getmsg=uninstrumented +fun:td_ta_get_nthreads=uninstrumented +fun:td_ta_get_ph=uninstrumented +fun:td_ta_get_stats=uninstrumented +fun:td_ta_map_id2thr=uninstrumented +fun:td_ta_map_lwp2thr=uninstrumented +fun:td_ta_new=uninstrumented +fun:td_ta_reset_stats=uninstrumented +fun:td_ta_set_event=uninstrumented +fun:td_ta_setconcurrency=uninstrumented +fun:td_ta_thr_iter=uninstrumented +fun:td_ta_tsd_iter=uninstrumented +fun:td_thr_clear_event=uninstrumented +fun:td_thr_dbresume=uninstrumented +fun:td_thr_dbsuspend=uninstrumented +fun:td_thr_event_enable=uninstrumented +fun:td_thr_event_getmsg=uninstrumented +fun:td_thr_get_info=uninstrumented +fun:td_thr_getfpregs=uninstrumented +fun:td_thr_getgregs=uninstrumented +fun:td_thr_getxregs=uninstrumented +fun:td_thr_getxregsize=uninstrumented +fun:td_thr_set_event=uninstrumented +fun:td_thr_setfpregs=uninstrumented +fun:td_thr_setgregs=uninstrumented +fun:td_thr_setprio=uninstrumented +fun:td_thr_setsigpending=uninstrumented +fun:td_thr_setxregs=uninstrumented +fun:td_thr_sigsetmask=uninstrumented +fun:td_thr_tls_get_addr=uninstrumented +fun:td_thr_tlsbase=uninstrumented +fun:td_thr_tsd=uninstrumented +fun:td_thr_validate=uninstrumented +fun:tdelete=uninstrumented +fun:tdestroy=uninstrumented +fun:tee=uninstrumented +fun:telldir=uninstrumented +fun:tempnam=uninstrumented +fun:textdomain=uninstrumented +fun:tfind=uninstrumented +fun:tgamma=uninstrumented +fun:tgammaf=uninstrumented +fun:tgammal=uninstrumented +fun:time=uninstrumented +fun:timegm=uninstrumented +fun:timelocal=uninstrumented +fun:timer_create=uninstrumented +fun:timer_delete=uninstrumented +fun:timer_getoverrun=uninstrumented +fun:timer_gettime=uninstrumented +fun:timer_settime=uninstrumented +fun:timerfd_create=uninstrumented +fun:timerfd_gettime=uninstrumented +fun:timerfd_settime=uninstrumented +fun:times=uninstrumented +fun:timespec_get=uninstrumented +fun:tmpfile=uninstrumented +fun:tmpfile64=uninstrumented +fun:tmpnam=uninstrumented +fun:tmpnam_r=uninstrumented +fun:toascii=uninstrumented +fun:tolower=uninstrumented +fun:tolower_l=uninstrumented +fun:toupper=uninstrumented +fun:toupper_l=uninstrumented +fun:towctrans=uninstrumented +fun:towctrans_l=uninstrumented +fun:towlower=uninstrumented +fun:towlower_l=uninstrumented +fun:towupper=uninstrumented +fun:towupper_l=uninstrumented +fun:tr_break=uninstrumented +fun:trunc=uninstrumented +fun:truncate=uninstrumented +fun:truncate64=uninstrumented +fun:truncf=uninstrumented +fun:truncl=uninstrumented +fun:tsearch=uninstrumented +fun:ttyname=uninstrumented +fun:ttyname_r=uninstrumented +fun:ttyslot=uninstrumented +fun:twalk=uninstrumented +fun:tzset=uninstrumented +fun:ualarm=uninstrumented +fun:ulckpwdf=uninstrumented +fun:ulimit=uninstrumented +fun:umask=uninstrumented +fun:umount=uninstrumented +fun:umount2=uninstrumented +fun:uname=uninstrumented +fun:ungetc=uninstrumented +fun:ungetwc=uninstrumented +fun:unlink=uninstrumented +fun:unlinkat=uninstrumented +fun:unlockpt=uninstrumented +fun:unsetenv=uninstrumented +fun:unshare=uninstrumented +fun:updwtmp=uninstrumented +fun:updwtmpx=uninstrumented +fun:uselib=uninstrumented +fun:uselocale=uninstrumented +fun:user2netname=uninstrumented +fun:usleep=uninstrumented +fun:ustat=uninstrumented +fun:utime=uninstrumented +fun:utimensat=uninstrumented +fun:utimes=uninstrumented +fun:utmpname=uninstrumented +fun:utmpxname=uninstrumented +fun:valloc=uninstrumented +fun:vasprintf=uninstrumented +fun:vdprintf=uninstrumented +fun:verr=uninstrumented +fun:verrx=uninstrumented +fun:versionsort=uninstrumented +fun:versionsort64=uninstrumented +fun:vfork=uninstrumented +fun:vfprintf=uninstrumented +fun:vfscanf=uninstrumented +fun:vfwprintf=uninstrumented +fun:vfwscanf=uninstrumented +fun:vhangup=uninstrumented +fun:vlimit=uninstrumented +fun:vmsplice=uninstrumented +fun:vprintf=uninstrumented +fun:vscanf=uninstrumented +fun:vsnprintf=uninstrumented +fun:vsprintf=uninstrumented +fun:vsscanf=uninstrumented +fun:vswprintf=uninstrumented +fun:vswscanf=uninstrumented +fun:vsyslog=uninstrumented +fun:vtimes=uninstrumented +fun:vwarn=uninstrumented +fun:vwarnx=uninstrumented +fun:vwprintf=uninstrumented +fun:vwscanf=uninstrumented +fun:wait=uninstrumented +fun:wait3=uninstrumented +fun:wait4=uninstrumented +fun:waitid=uninstrumented +fun:waitpid=uninstrumented +fun:warn=uninstrumented +fun:warnx=uninstrumented +fun:wcpcpy=uninstrumented +fun:wcpncpy=uninstrumented +fun:wcrtomb=uninstrumented +fun:wcscasecmp=uninstrumented +fun:wcscasecmp_l=uninstrumented +fun:wcscat=uninstrumented +fun:wcschr=uninstrumented +fun:wcschrnul=uninstrumented +fun:wcscmp=uninstrumented +fun:wcscoll=uninstrumented +fun:wcscoll_l=uninstrumented +fun:wcscpy=uninstrumented +fun:wcscspn=uninstrumented +fun:wcsdup=uninstrumented +fun:wcsftime=uninstrumented +fun:wcsftime_l=uninstrumented +fun:wcslen=uninstrumented +fun:wcsncasecmp=uninstrumented +fun:wcsncasecmp_l=uninstrumented +fun:wcsncat=uninstrumented +fun:wcsncmp=uninstrumented +fun:wcsncpy=uninstrumented +fun:wcsnlen=uninstrumented +fun:wcsnrtombs=uninstrumented +fun:wcspbrk=uninstrumented +fun:wcsrchr=uninstrumented +fun:wcsrtombs=uninstrumented +fun:wcsspn=uninstrumented +fun:wcsstr=uninstrumented +fun:wcstod=uninstrumented +fun:wcstod_l=uninstrumented +fun:wcstof=uninstrumented +fun:wcstof_l=uninstrumented +fun:wcstoimax=uninstrumented +fun:wcstok=uninstrumented +fun:wcstol=uninstrumented +fun:wcstol_l=uninstrumented +fun:wcstold=uninstrumented +fun:wcstold_l=uninstrumented +fun:wcstoll=uninstrumented +fun:wcstoll_l=uninstrumented +fun:wcstombs=uninstrumented +fun:wcstoq=uninstrumented +fun:wcstoul=uninstrumented +fun:wcstoul_l=uninstrumented +fun:wcstoull=uninstrumented +fun:wcstoull_l=uninstrumented +fun:wcstoumax=uninstrumented +fun:wcstouq=uninstrumented +fun:wcswcs=uninstrumented +fun:wcswidth=uninstrumented +fun:wcsxfrm=uninstrumented +fun:wcsxfrm_l=uninstrumented +fun:wctob=uninstrumented +fun:wctomb=uninstrumented +fun:wctrans=uninstrumented +fun:wctrans_l=uninstrumented +fun:wctype=uninstrumented +fun:wctype_l=uninstrumented +fun:wcwidth=uninstrumented +fun:wmemchr=uninstrumented +fun:wmemcmp=uninstrumented +fun:wmemcpy=uninstrumented +fun:wmemmove=uninstrumented +fun:wmempcpy=uninstrumented +fun:wmemset=uninstrumented +fun:wordexp=uninstrumented +fun:wordfree=uninstrumented +fun:wprintf=uninstrumented +fun:write=uninstrumented +fun:writeColdStartFile=uninstrumented +fun:writev=uninstrumented +fun:wscanf=uninstrumented +fun:xdecrypt=uninstrumented +fun:xdr_accepted_reply=uninstrumented +fun:xdr_array=uninstrumented +fun:xdr_authdes_cred=uninstrumented +fun:xdr_authdes_verf=uninstrumented +fun:xdr_authunix_parms=uninstrumented +fun:xdr_bool=uninstrumented +fun:xdr_bytes=uninstrumented +fun:xdr_callhdr=uninstrumented +fun:xdr_callmsg=uninstrumented +fun:xdr_cback_data=uninstrumented +fun:xdr_char=uninstrumented +fun:xdr_cryptkeyarg=uninstrumented +fun:xdr_cryptkeyarg2=uninstrumented +fun:xdr_cryptkeyres=uninstrumented +fun:xdr_des_block=uninstrumented +fun:xdr_domainname=uninstrumented +fun:xdr_double=uninstrumented +fun:xdr_enum=uninstrumented +fun:xdr_float=uninstrumented +fun:xdr_free=uninstrumented +fun:xdr_getcredres=uninstrumented +fun:xdr_hyper=uninstrumented +fun:xdr_int=uninstrumented +fun:xdr_int16_t=uninstrumented +fun:xdr_int32_t=uninstrumented +fun:xdr_int64_t=uninstrumented +fun:xdr_int8_t=uninstrumented +fun:xdr_key_netstarg=uninstrumented +fun:xdr_key_netstres=uninstrumented +fun:xdr_keybuf=uninstrumented +fun:xdr_keydat=uninstrumented +fun:xdr_keystatus=uninstrumented +fun:xdr_long=uninstrumented +fun:xdr_longlong_t=uninstrumented +fun:xdr_mapname=uninstrumented +fun:xdr_netnamestr=uninstrumented +fun:xdr_netobj=uninstrumented +fun:xdr_obj_p=uninstrumented +fun:xdr_opaque=uninstrumented +fun:xdr_opaque_auth=uninstrumented +fun:xdr_peername=uninstrumented +fun:xdr_pmap=uninstrumented +fun:xdr_pmaplist=uninstrumented +fun:xdr_pointer=uninstrumented +fun:xdr_quad_t=uninstrumented +fun:xdr_reference=uninstrumented +fun:xdr_rejected_reply=uninstrumented +fun:xdr_replymsg=uninstrumented +fun:xdr_rmtcall_args=uninstrumented +fun:xdr_rmtcallres=uninstrumented +fun:xdr_short=uninstrumented +fun:xdr_sizeof=uninstrumented +fun:xdr_string=uninstrumented +fun:xdr_u_char=uninstrumented +fun:xdr_u_hyper=uninstrumented +fun:xdr_u_int=uninstrumented +fun:xdr_u_long=uninstrumented +fun:xdr_u_longlong_t=uninstrumented +fun:xdr_u_quad_t=uninstrumented +fun:xdr_u_short=uninstrumented +fun:xdr_uint16_t=uninstrumented +fun:xdr_uint32_t=uninstrumented +fun:xdr_uint64_t=uninstrumented +fun:xdr_uint8_t=uninstrumented +fun:xdr_union=uninstrumented +fun:xdr_unixcred=uninstrumented +fun:xdr_valdat=uninstrumented +fun:xdr_vector=uninstrumented +fun:xdr_void=uninstrumented +fun:xdr_wrapstring=uninstrumented +fun:xdr_yp_buf=uninstrumented +fun:xdr_ypall=uninstrumented +fun:xdr_ypbind_binding=uninstrumented +fun:xdr_ypbind_resp=uninstrumented +fun:xdr_ypbind_resptype=uninstrumented +fun:xdr_ypbind_setdom=uninstrumented +fun:xdr_ypdelete_args=uninstrumented +fun:xdr_ypmap_parms=uninstrumented +fun:xdr_ypmaplist=uninstrumented +fun:xdr_yppush_status=uninstrumented +fun:xdr_yppushresp_xfr=uninstrumented +fun:xdr_ypreq_key=uninstrumented +fun:xdr_ypreq_nokey=uninstrumented +fun:xdr_ypreq_xfr=uninstrumented +fun:xdr_ypresp_all=uninstrumented +fun:xdr_ypresp_key_val=uninstrumented +fun:xdr_ypresp_maplist=uninstrumented +fun:xdr_ypresp_master=uninstrumented +fun:xdr_ypresp_order=uninstrumented +fun:xdr_ypresp_val=uninstrumented +fun:xdr_ypresp_xfr=uninstrumented +fun:xdr_ypstat=uninstrumented +fun:xdr_ypupdate_args=uninstrumented +fun:xdr_ypxfrstat=uninstrumented +fun:xdrmem_create=uninstrumented +fun:xdrrec_create=uninstrumented +fun:xdrrec_endofrecord=uninstrumented +fun:xdrrec_eof=uninstrumented +fun:xdrrec_skiprecord=uninstrumented +fun:xdrstdio_create=uninstrumented +fun:xencrypt=uninstrumented +fun:xprt_register=uninstrumented +fun:xprt_unregister=uninstrumented +fun:y0=uninstrumented +fun:y0f=uninstrumented +fun:y0l=uninstrumented +fun:y1=uninstrumented +fun:y1f=uninstrumented +fun:y1l=uninstrumented +fun:yn=uninstrumented +fun:ynf=uninstrumented +fun:ynl=uninstrumented +fun:yp_all=uninstrumented +fun:yp_bind=uninstrumented +fun:yp_first=uninstrumented +fun:yp_get_default_domain=uninstrumented +fun:yp_maplist=uninstrumented +fun:yp_master=uninstrumented +fun:yp_match=uninstrumented +fun:yp_next=uninstrumented +fun:yp_order=uninstrumented +fun:yp_unbind=uninstrumented +fun:yp_update=uninstrumented +fun:ypbinderr_string=uninstrumented +fun:yperr_string=uninstrumented +fun:ypprot_err=uninstrumented |
