[scudo][standalone] Enable secondary cache release on Fuchsia
I had left this as a TODO, but it turns out it wasn't complicated. By specifying `MAP_RESIZABLE`, it allows us to keep the VMO which we can then use for release purposes. `releasePagesToOS` also had to be called the "proper" way, as Fuchsia requires the `Offset` field to be correct. This has no impact on non-Fuchsia platforms. Differential Revision: https://reviews.llvm.org/D86800
This commit is contained in:
		
							parent
							
								
									272742a92d
								
							
						
					
					
						commit
						00d9907a7a
					
				| 
						 | 
					@ -306,7 +306,7 @@ public:
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    void *Block = nullptr;
 | 
					    void *Block = nullptr;
 | 
				
			||||||
    uptr ClassId = 0;
 | 
					    uptr ClassId = 0;
 | 
				
			||||||
    uptr SecondaryBlockEnd;
 | 
					    uptr SecondaryBlockEnd = 0;
 | 
				
			||||||
    if (LIKELY(PrimaryT::canAllocate(NeededSize))) {
 | 
					    if (LIKELY(PrimaryT::canAllocate(NeededSize))) {
 | 
				
			||||||
      ClassId = SizeClassMap::getClassIdBySize(NeededSize);
 | 
					      ClassId = SizeClassMap::getClassIdBySize(NeededSize);
 | 
				
			||||||
      DCHECK_NE(ClassId, 0U);
 | 
					      DCHECK_NE(ClassId, 0U);
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -75,11 +75,6 @@ template <u32 EntriesArraySize = 32U, u32 DefaultMaxEntriesCount = 32U,
 | 
				
			||||||
          s32 MaxReleaseToOsIntervalMs = INT32_MAX>
 | 
					          s32 MaxReleaseToOsIntervalMs = INT32_MAX>
 | 
				
			||||||
class MapAllocatorCache {
 | 
					class MapAllocatorCache {
 | 
				
			||||||
public:
 | 
					public:
 | 
				
			||||||
  // Fuchsia doesn't allow releasing Secondary blocks yet. Note that 0 length
 | 
					 | 
				
			||||||
  // arrays are an extension for some compilers.
 | 
					 | 
				
			||||||
  // FIXME(kostyak): support (partially) the cache on Fuchsia.
 | 
					 | 
				
			||||||
  static_assert(!SCUDO_FUCHSIA || EntriesArraySize == 0U, "");
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
  // Ensure the default maximum specified fits the array.
 | 
					  // Ensure the default maximum specified fits the array.
 | 
				
			||||||
  static_assert(DefaultMaxEntriesCount <= EntriesArraySize, "");
 | 
					  static_assert(DefaultMaxEntriesCount <= EntriesArraySize, "");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -392,9 +387,9 @@ void *MapAllocator<CacheT>::allocate(uptr Size, uptr AlignmentHint,
 | 
				
			||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  const uptr CommitSize = MapEnd - PageSize - CommitBase;
 | 
					  const uptr CommitSize = MapEnd - PageSize - CommitBase;
 | 
				
			||||||
  const uptr Ptr =
 | 
					  const uptr Ptr = reinterpret_cast<uptr>(
 | 
				
			||||||
      reinterpret_cast<uptr>(map(reinterpret_cast<void *>(CommitBase),
 | 
					      map(reinterpret_cast<void *>(CommitBase), CommitSize, "scudo:secondary",
 | 
				
			||||||
                                 CommitSize, "scudo:secondary", 0, &Data));
 | 
					          MAP_RESIZABLE, &Data));
 | 
				
			||||||
  LargeBlock::Header *H = reinterpret_cast<LargeBlock::Header *>(Ptr);
 | 
					  LargeBlock::Header *H = reinterpret_cast<LargeBlock::Header *>(Ptr);
 | 
				
			||||||
  H->MapBase = MapBase;
 | 
					  H->MapBase = MapBase;
 | 
				
			||||||
  H->MapSize = MapEnd - MapBase;
 | 
					  H->MapSize = MapEnd - MapBase;
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -14,6 +14,7 @@
 | 
				
			||||||
#include <condition_variable>
 | 
					#include <condition_variable>
 | 
				
			||||||
#include <memory>
 | 
					#include <memory>
 | 
				
			||||||
#include <mutex>
 | 
					#include <mutex>
 | 
				
			||||||
 | 
					#include <set>
 | 
				
			||||||
#include <thread>
 | 
					#include <thread>
 | 
				
			||||||
#include <vector>
 | 
					#include <vector>
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| 
						 | 
					@ -23,7 +24,8 @@ static bool Ready;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static constexpr scudo::Chunk::Origin Origin = scudo::Chunk::Origin::Malloc;
 | 
					static constexpr scudo::Chunk::Origin Origin = scudo::Chunk::Origin::Malloc;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void disableDebuggerdMaybe() {
 | 
					// Fuchsia complains that the function is not used.
 | 
				
			||||||
 | 
					UNUSED static void disableDebuggerdMaybe() {
 | 
				
			||||||
#if SCUDO_ANDROID
 | 
					#if SCUDO_ANDROID
 | 
				
			||||||
  // Disable the debuggerd signal handler on Android, without this we can end
 | 
					  // Disable the debuggerd signal handler on Android, without this we can end
 | 
				
			||||||
  // up spending a significant amount of time creating tombstones.
 | 
					  // up spending a significant amount of time creating tombstones.
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -56,18 +56,12 @@ template <class SecondaryT> static void testSecondaryBasic(void) {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
TEST(ScudoSecondaryTest, SecondaryBasic) {
 | 
					TEST(ScudoSecondaryTest, SecondaryBasic) {
 | 
				
			||||||
  testSecondaryBasic<scudo::MapAllocator<scudo::MapAllocatorNoCache>>();
 | 
					  testSecondaryBasic<scudo::MapAllocator<scudo::MapAllocatorNoCache>>();
 | 
				
			||||||
#if !SCUDO_FUCHSIA
 | 
					 | 
				
			||||||
  testSecondaryBasic<scudo::MapAllocator<scudo::MapAllocatorCache<>>>();
 | 
					  testSecondaryBasic<scudo::MapAllocator<scudo::MapAllocatorCache<>>>();
 | 
				
			||||||
  testSecondaryBasic<
 | 
					  testSecondaryBasic<
 | 
				
			||||||
      scudo::MapAllocator<scudo::MapAllocatorCache<128U, 64U, 1UL << 20>>>();
 | 
					      scudo::MapAllocator<scudo::MapAllocatorCache<128U, 64U, 1UL << 20>>>();
 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#if SCUDO_FUCHSIA
 | 
					 | 
				
			||||||
using LargeAllocator = scudo::MapAllocator<scudo::MapAllocatorNoCache>;
 | 
					 | 
				
			||||||
#else
 | 
					 | 
				
			||||||
using LargeAllocator = scudo::MapAllocator<scudo::MapAllocatorCache<>>;
 | 
					using LargeAllocator = scudo::MapAllocator<scudo::MapAllocatorCache<>>;
 | 
				
			||||||
#endif
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
// This exercises a variety of combinations of size and alignment for the
 | 
					// This exercises a variety of combinations of size and alignment for the
 | 
				
			||||||
// MapAllocator. The size computation done here mimic the ones done by the
 | 
					// MapAllocator. The size computation done here mimic the ones done by the
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue