003 File Manager
Current Path:
/usr/src/contrib/llvm-project/compiler-rt/lib/sanitizer_common
usr
/
src
/
contrib
/
llvm-project
/
compiler-rt
/
lib
/
sanitizer_common
/
📁
..
📄
sancov_flags.cpp
(1.64 KB)
📄
sancov_flags.h
(1.08 KB)
📄
sancov_flags.inc
(777 B)
📄
sanitizer_addrhashmap.h
(9.19 KB)
📄
sanitizer_allocator.cpp
(8.73 KB)
📄
sanitizer_allocator.h
(2.69 KB)
📄
sanitizer_allocator_bytemap.h
(3.12 KB)
📄
sanitizer_allocator_checks.cpp
(686 B)
📄
sanitizer_allocator_checks.h
(2.67 KB)
📄
sanitizer_allocator_combined.h
(6.29 KB)
📄
sanitizer_allocator_interface.h
(1.83 KB)
📄
sanitizer_allocator_internal.h
(2.03 KB)
📄
sanitizer_allocator_local_cache.h
(8.95 KB)
📄
sanitizer_allocator_primary32.h
(12.64 KB)
📄
sanitizer_allocator_primary64.h
(32.71 KB)
📄
sanitizer_allocator_report.cpp
(4.68 KB)
📄
sanitizer_allocator_report.h
(1.72 KB)
📄
sanitizer_allocator_secondary.h
(10.78 KB)
📄
sanitizer_allocator_size_class_map.h
(10.12 KB)
📄
sanitizer_allocator_stats.h
(2.76 KB)
📄
sanitizer_asm.h
(2.57 KB)
📄
sanitizer_atomic.h
(1.97 KB)
📄
sanitizer_atomic_clang.h
(3.42 KB)
📄
sanitizer_atomic_clang_mips.h
(3.77 KB)
📄
sanitizer_atomic_clang_other.h
(3.02 KB)
📄
sanitizer_atomic_clang_x86.h
(3.77 KB)
📄
sanitizer_atomic_msvc.h
(8.53 KB)
📄
sanitizer_bitvector.h
(9.43 KB)
📄
sanitizer_bvgraph.h
(4.62 KB)
📄
sanitizer_common.cpp
(10.13 KB)
📄
sanitizer_common.h
(30.64 KB)
📄
sanitizer_common_interceptors.inc
(348.66 KB)
📄
sanitizer_common_interceptors_format.inc
(16.84 KB)
📄
sanitizer_common_interceptors_ioctl.inc
(22.13 KB)
📄
sanitizer_common_interceptors_netbsd_compat.inc
(4.07 KB)
📄
sanitizer_common_interceptors_vfork_aarch64.inc.S
(1.23 KB)
📄
sanitizer_common_interceptors_vfork_arm.inc.S
(1.24 KB)
📄
sanitizer_common_interceptors_vfork_i386.inc.S
(1.66 KB)
📄
sanitizer_common_interceptors_vfork_x86_64.inc.S
(1.03 KB)
📄
sanitizer_common_interface.inc
(2.05 KB)
📄
sanitizer_common_interface_posix.inc
(732 B)
📄
sanitizer_common_libcdep.cpp
(5.4 KB)
📄
sanitizer_common_nolibc.cpp
(1.12 KB)
📄
sanitizer_common_syscalls.inc
(85 KB)
📄
sanitizer_coverage_fuchsia.cpp
(10.1 KB)
📄
sanitizer_coverage_interface.inc
(1.73 KB)
📄
sanitizer_coverage_libcdep_new.cpp
(7.39 KB)
📄
sanitizer_coverage_win_dll_thunk.cpp
(1.03 KB)
📄
sanitizer_coverage_win_dynamic_runtime_thunk.cpp
(1.16 KB)
📄
sanitizer_coverage_win_sections.cpp
(3.36 KB)
📄
sanitizer_coverage_win_weak_interception.cpp
(1.17 KB)
📄
sanitizer_dbghelp.h
(1.44 KB)
📄
sanitizer_deadlock_detector.h
(13.28 KB)
📄
sanitizer_deadlock_detector1.cpp
(5.6 KB)
📄
sanitizer_deadlock_detector2.cpp
(10.84 KB)
📄
sanitizer_deadlock_detector_interface.h
(2.66 KB)
📄
sanitizer_errno.cpp
(1.09 KB)
📄
sanitizer_errno.h
(1.3 KB)
📄
sanitizer_errno_codes.h
(1.1 KB)
📄
sanitizer_file.cpp
(6.24 KB)
📄
sanitizer_file.h
(3.67 KB)
📄
sanitizer_flag_parser.cpp
(5.55 KB)
📄
sanitizer_flag_parser.h
(5.71 KB)
📄
sanitizer_flags.cpp
(3.95 KB)
📄
sanitizer_flags.h
(2.13 KB)
📄
sanitizer_flags.inc
(12.73 KB)
📄
sanitizer_freebsd.h
(3.31 KB)
📄
sanitizer_fuchsia.cpp
(16.58 KB)
📄
sanitizer_fuchsia.h
(1.03 KB)
📄
sanitizer_getauxval.h
(1.73 KB)
📄
sanitizer_glibc_version.h
(748 B)
📄
sanitizer_hash.h
(1.04 KB)
📄
sanitizer_interceptors_ioctl_netbsd.inc
(68.81 KB)
📄
sanitizer_interface_internal.h
(5.28 KB)
📄
sanitizer_internal_defs.h
(14.28 KB)
📄
sanitizer_lfstack.h
(2.08 KB)
📄
sanitizer_libc.cpp
(7.21 KB)
📄
sanitizer_libc.h
(3.23 KB)
📄
sanitizer_libignore.cpp
(4.24 KB)
📄
sanitizer_libignore.h
(3.5 KB)
📄
sanitizer_linux.cpp
(71.58 KB)
📄
sanitizer_linux.h
(5.47 KB)
📄
sanitizer_linux_libcdep.cpp
(25.67 KB)
📄
sanitizer_linux_s390.cpp
(6.91 KB)
📄
sanitizer_list.h
(3.81 KB)
📄
sanitizer_local_address_space_view.h
(3.67 KB)
📄
sanitizer_mac.cpp
(38.67 KB)
📄
sanitizer_mac.h
(2.49 KB)
📄
sanitizer_mac_libcdep.cpp
(968 B)
📄
sanitizer_malloc_mac.inc
(13.06 KB)
📄
sanitizer_mutex.h
(5.17 KB)
📄
sanitizer_netbsd.cpp
(9.95 KB)
📄
sanitizer_openbsd.cpp
(3.17 KB)
📄
sanitizer_persistent_allocator.cpp
(687 B)
📄
sanitizer_persistent_allocator.h
(2.31 KB)
📄
sanitizer_placement_new.h
(885 B)
📄
sanitizer_platform.h
(10.11 KB)
📄
sanitizer_platform_interceptors.h
(24.93 KB)
📄
sanitizer_platform_limits_freebsd.cpp
(19.79 KB)
📄
sanitizer_platform_limits_freebsd.h
(18.41 KB)
📄
sanitizer_platform_limits_linux.cpp
(3.32 KB)
📄
sanitizer_platform_limits_netbsd.cpp
(109.73 KB)
📄
sanitizer_platform_limits_netbsd.h
(81.54 KB)
📄
sanitizer_platform_limits_openbsd.cpp
(8.69 KB)
📄
sanitizer_platform_limits_openbsd.h
(8.68 KB)
📄
sanitizer_platform_limits_posix.cpp
(48.89 KB)
📄
sanitizer_platform_limits_posix.h
(40.65 KB)
📄
sanitizer_platform_limits_solaris.cpp
(11.93 KB)
📄
sanitizer_platform_limits_solaris.h
(12.26 KB)
📄
sanitizer_posix.cpp
(11.93 KB)
📄
sanitizer_posix.h
(5.14 KB)
📄
sanitizer_posix_libcdep.cpp
(16.21 KB)
📄
sanitizer_printf.cpp
(12.07 KB)
📄
sanitizer_procmaps.h
(2.93 KB)
📄
sanitizer_procmaps_bsd.cpp
(3.81 KB)
📄
sanitizer_procmaps_common.cpp
(5.27 KB)
📄
sanitizer_procmaps_fuchsia.cpp
(2.51 KB)
📄
sanitizer_procmaps_linux.cpp
(2.9 KB)
📄
sanitizer_procmaps_mac.cpp
(13.7 KB)
📄
sanitizer_procmaps_solaris.cpp
(2.18 KB)
📄
sanitizer_ptrauth.h
(720 B)
📄
sanitizer_quarantine.h
(9.57 KB)
📄
sanitizer_report_decorator.h
(1.89 KB)
📄
sanitizer_ring_buffer.h
(4.7 KB)
📄
sanitizer_rtems.cpp
(7.61 KB)
📄
sanitizer_rtems.h
(772 B)
📄
sanitizer_signal_interceptors.inc
(2.89 KB)
📄
sanitizer_solaris.cpp
(6.6 KB)
📄
sanitizer_stackdepot.cpp
(4.54 KB)
📄
sanitizer_stackdepot.h
(2.13 KB)
📄
sanitizer_stackdepotbase.h
(5.58 KB)
📄
sanitizer_stacktrace.cpp
(4.58 KB)
📄
sanitizer_stacktrace.h
(5.65 KB)
📄
sanitizer_stacktrace_libcdep.cpp
(5.54 KB)
📄
sanitizer_stacktrace_printer.cpp
(9.08 KB)
📄
sanitizer_stacktrace_printer.h
(3.08 KB)
📄
sanitizer_stacktrace_sparc.cpp
(3.05 KB)
📄
sanitizer_stoptheworld.h
(2.34 KB)
📄
sanitizer_stoptheworld_fuchsia.cpp
(1.28 KB)
📄
sanitizer_stoptheworld_linux_libcdep.cpp
(20.8 KB)
📄
sanitizer_stoptheworld_mac.cpp
(5.29 KB)
📄
sanitizer_stoptheworld_netbsd_libcdep.cpp
(11.02 KB)
📄
sanitizer_suppressions.cpp
(5.67 KB)
📄
sanitizer_suppressions.h
(1.69 KB)
📄
sanitizer_symbolizer.cpp
(3.65 KB)
📄
sanitizer_symbolizer.h
(6.62 KB)
📄
sanitizer_symbolizer_fuchsia.h
(1.56 KB)
📄
sanitizer_symbolizer_internal.h
(5.8 KB)
📄
sanitizer_symbolizer_libbacktrace.cpp
(6.1 KB)
📄
sanitizer_symbolizer_libbacktrace.h
(1.49 KB)
📄
sanitizer_symbolizer_libcdep.cpp
(17.45 KB)
📄
sanitizer_symbolizer_mac.cpp
(8.48 KB)
📄
sanitizer_symbolizer_mac.h
(1.37 KB)
📄
sanitizer_symbolizer_markup.cpp
(5.39 KB)
📄
sanitizer_symbolizer_posix_libcdep.cpp
(16.5 KB)
📄
sanitizer_symbolizer_report.cpp
(10.01 KB)
📄
sanitizer_symbolizer_rtems.h
(1.56 KB)
📄
sanitizer_symbolizer_win.cpp
(11.59 KB)
📄
sanitizer_syscall_generic.inc
(1.06 KB)
📄
sanitizer_syscall_linux_aarch64.inc
(4.58 KB)
📄
sanitizer_syscall_linux_arm.inc
(4.58 KB)
📄
sanitizer_syscall_linux_x86_64.inc
(3.07 KB)
📄
sanitizer_syscalls_netbsd.inc
(120.97 KB)
📄
sanitizer_termination.cpp
(2.86 KB)
📄
sanitizer_thread_registry.cpp
(10.31 KB)
📄
sanitizer_thread_registry.h
(5.44 KB)
📄
sanitizer_tls_get_addr.cpp
(5.29 KB)
📄
sanitizer_tls_get_addr.h
(2.21 KB)
📄
sanitizer_type_traits.cpp
(708 B)
📄
sanitizer_type_traits.h
(1.49 KB)
📄
sanitizer_unwind_linux_libcdep.cpp
(6.13 KB)
📄
sanitizer_unwind_win.cpp
(2.41 KB)
📄
sanitizer_vector.h
(2.57 KB)
📄
sanitizer_win.cpp
(33.3 KB)
📄
sanitizer_win.h
(851 B)
📄
sanitizer_win_defs.h
(7.23 KB)
📄
sanitizer_win_dll_thunk.cpp
(3.41 KB)
📄
sanitizer_win_dll_thunk.h
(11.13 KB)
📄
sanitizer_win_dynamic_runtime_thunk.cpp
(1.16 KB)
📄
sanitizer_win_weak_interception.cpp
(3.49 KB)
📄
sanitizer_win_weak_interception.h
(1.64 KB)
📁
symbolizer
📄
weak_symbols.txt
(230 B)
Editing: sanitizer_quarantine.h
//===-- sanitizer_quarantine.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 // //===----------------------------------------------------------------------===// // // Memory quarantine for AddressSanitizer and potentially other tools. // Quarantine caches some specified amount of memory in per-thread caches, // then evicts to global FIFO queue. When the queue reaches specified threshold, // oldest memory is recycled. // //===----------------------------------------------------------------------===// #ifndef SANITIZER_QUARANTINE_H #define SANITIZER_QUARANTINE_H #include "sanitizer_internal_defs.h" #include "sanitizer_mutex.h" #include "sanitizer_list.h" namespace __sanitizer { template<typename Node> class QuarantineCache; struct QuarantineBatch { static const uptr kSize = 1021; QuarantineBatch *next; uptr size; uptr count; void *batch[kSize]; void init(void *ptr, uptr size) { count = 1; batch[0] = ptr; this->size = size + sizeof(QuarantineBatch); // Account for the batch size. } // The total size of quarantined nodes recorded in this batch. uptr quarantined_size() const { return size - sizeof(QuarantineBatch); } void push_back(void *ptr, uptr size) { CHECK_LT(count, kSize); batch[count++] = ptr; this->size += size; } bool can_merge(const QuarantineBatch* const from) const { return count + from->count <= kSize; } void merge(QuarantineBatch* const from) { CHECK_LE(count + from->count, kSize); CHECK_GE(size, sizeof(QuarantineBatch)); for (uptr i = 0; i < from->count; ++i) batch[count + i] = from->batch[i]; count += from->count; size += from->quarantined_size(); from->count = 0; from->size = sizeof(QuarantineBatch); } }; COMPILER_CHECK(sizeof(QuarantineBatch) <= (1 << 13)); // 8Kb. // The callback interface is: // void Callback::Recycle(Node *ptr); // void *cb.Allocate(uptr size); // void cb.Deallocate(void *ptr); template<typename Callback, typename Node> class Quarantine { public: typedef QuarantineCache<Callback> Cache; explicit Quarantine(LinkerInitialized) : cache_(LINKER_INITIALIZED) { } void Init(uptr size, uptr cache_size) { // Thread local quarantine size can be zero only when global quarantine size // is zero (it allows us to perform just one atomic read per Put() call). CHECK((size == 0 && cache_size == 0) || cache_size != 0); atomic_store_relaxed(&max_size_, size); atomic_store_relaxed(&min_size_, size / 10 * 9); // 90% of max size. atomic_store_relaxed(&max_cache_size_, cache_size); cache_mutex_.Init(); recycle_mutex_.Init(); } uptr GetSize() const { return atomic_load_relaxed(&max_size_); } uptr GetCacheSize() const { return atomic_load_relaxed(&max_cache_size_); } void Put(Cache *c, Callback cb, Node *ptr, uptr size) { uptr cache_size = GetCacheSize(); if (cache_size) { c->Enqueue(cb, ptr, size); } else { // GetCacheSize() == 0 only when GetSize() == 0 (see Init). cb.Recycle(ptr); } // Check cache size anyway to accommodate for runtime cache_size change. if (c->Size() > cache_size) Drain(c, cb); } void NOINLINE Drain(Cache *c, Callback cb) { { SpinMutexLock l(&cache_mutex_); cache_.Transfer(c); } if (cache_.Size() > GetSize() && recycle_mutex_.TryLock()) Recycle(atomic_load_relaxed(&min_size_), cb); } void NOINLINE DrainAndRecycle(Cache *c, Callback cb) { { SpinMutexLock l(&cache_mutex_); cache_.Transfer(c); } recycle_mutex_.Lock(); Recycle(0, cb); } void PrintStats() const { // It assumes that the world is stopped, just as the allocator's PrintStats. Printf("Quarantine limits: global: %zdMb; thread local: %zdKb\n", GetSize() >> 20, GetCacheSize() >> 10); cache_.PrintStats(); } private: // Read-only data. char pad0_[kCacheLineSize]; atomic_uintptr_t max_size_; atomic_uintptr_t min_size_; atomic_uintptr_t max_cache_size_; char pad1_[kCacheLineSize]; StaticSpinMutex cache_mutex_; StaticSpinMutex recycle_mutex_; Cache cache_; char pad2_[kCacheLineSize]; void NOINLINE Recycle(uptr min_size, Callback cb) { Cache tmp; { SpinMutexLock l(&cache_mutex_); // Go over the batches and merge partially filled ones to // save some memory, otherwise batches themselves (since the memory used // by them is counted against quarantine limit) can overcome the actual // user's quarantined chunks, which diminishes the purpose of the // quarantine. uptr cache_size = cache_.Size(); uptr overhead_size = cache_.OverheadSize(); CHECK_GE(cache_size, overhead_size); // Do the merge only when overhead exceeds this predefined limit (might // require some tuning). It saves us merge attempt when the batch list // quarantine is unlikely to contain batches suitable for merge. const uptr kOverheadThresholdPercents = 100; if (cache_size > overhead_size && overhead_size * (100 + kOverheadThresholdPercents) > cache_size * kOverheadThresholdPercents) { cache_.MergeBatches(&tmp); } // Extract enough chunks from the quarantine to get below the max // quarantine size and leave some leeway for the newly quarantined chunks. while (cache_.Size() > min_size) { tmp.EnqueueBatch(cache_.DequeueBatch()); } } recycle_mutex_.Unlock(); DoRecycle(&tmp, cb); } void NOINLINE DoRecycle(Cache *c, Callback cb) { while (QuarantineBatch *b = c->DequeueBatch()) { const uptr kPrefetch = 16; CHECK(kPrefetch <= ARRAY_SIZE(b->batch)); for (uptr i = 0; i < kPrefetch; i++) PREFETCH(b->batch[i]); for (uptr i = 0, count = b->count; i < count; i++) { if (i + kPrefetch < count) PREFETCH(b->batch[i + kPrefetch]); cb.Recycle((Node*)b->batch[i]); } cb.Deallocate(b); } } }; // Per-thread cache of memory blocks. template<typename Callback> class QuarantineCache { public: explicit QuarantineCache(LinkerInitialized) { } QuarantineCache() : size_() { list_.clear(); } // Total memory used, including internal accounting. uptr Size() const { return atomic_load_relaxed(&size_); } // Memory used for internal accounting. uptr OverheadSize() const { return list_.size() * sizeof(QuarantineBatch); } void Enqueue(Callback cb, void *ptr, uptr size) { if (list_.empty() || list_.back()->count == QuarantineBatch::kSize) { QuarantineBatch *b = (QuarantineBatch *)cb.Allocate(sizeof(*b)); CHECK(b); b->init(ptr, size); EnqueueBatch(b); } else { list_.back()->push_back(ptr, size); SizeAdd(size); } } void Transfer(QuarantineCache *from_cache) { list_.append_back(&from_cache->list_); SizeAdd(from_cache->Size()); atomic_store_relaxed(&from_cache->size_, 0); } void EnqueueBatch(QuarantineBatch *b) { list_.push_back(b); SizeAdd(b->size); } QuarantineBatch *DequeueBatch() { if (list_.empty()) return nullptr; QuarantineBatch *b = list_.front(); list_.pop_front(); SizeSub(b->size); return b; } void MergeBatches(QuarantineCache *to_deallocate) { uptr extracted_size = 0; QuarantineBatch *current = list_.front(); while (current && current->next) { if (current->can_merge(current->next)) { QuarantineBatch *extracted = current->next; // Move all the chunks into the current batch. current->merge(extracted); CHECK_EQ(extracted->count, 0); CHECK_EQ(extracted->size, sizeof(QuarantineBatch)); // Remove the next batch from the list and account for its size. list_.extract(current, extracted); extracted_size += extracted->size; // Add it to deallocation list. to_deallocate->EnqueueBatch(extracted); } else { current = current->next; } } SizeSub(extracted_size); } void PrintStats() const { uptr batch_count = 0; uptr total_overhead_bytes = 0; uptr total_bytes = 0; uptr total_quarantine_chunks = 0; for (List::ConstIterator it = list_.begin(); it != list_.end(); ++it) { batch_count++; total_bytes += (*it).size; total_overhead_bytes += (*it).size - (*it).quarantined_size(); total_quarantine_chunks += (*it).count; } uptr quarantine_chunks_capacity = batch_count * QuarantineBatch::kSize; int chunks_usage_percent = quarantine_chunks_capacity == 0 ? 0 : total_quarantine_chunks * 100 / quarantine_chunks_capacity; uptr total_quarantined_bytes = total_bytes - total_overhead_bytes; int memory_overhead_percent = total_quarantined_bytes == 0 ? 0 : total_overhead_bytes * 100 / total_quarantined_bytes; Printf("Global quarantine stats: batches: %zd; bytes: %zd (user: %zd); " "chunks: %zd (capacity: %zd); %d%% chunks used; %d%% memory overhead" "\n", batch_count, total_bytes, total_quarantined_bytes, total_quarantine_chunks, quarantine_chunks_capacity, chunks_usage_percent, memory_overhead_percent); } private: typedef IntrusiveList<QuarantineBatch> List; List list_; atomic_uintptr_t size_; void SizeAdd(uptr add) { atomic_store_relaxed(&size_, Size() + add); } void SizeSub(uptr sub) { atomic_store_relaxed(&size_, Size() - sub); } }; } // namespace __sanitizer #endif // SANITIZER_QUARANTINE_H
Upload File
Create Folder