| OLD | NEW |
| 1 /* | 1 /* |
| 2 * Copyright (C) 2013 Google Inc. All rights reserved. | 2 * Copyright (C) 2013 Google Inc. All rights reserved. |
| 3 * | 3 * |
| 4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
| 5 * modification, are permitted provided that the following conditions are | 5 * modification, are permitted provided that the following conditions are |
| 6 * met: | 6 * met: |
| 7 * | 7 * |
| 8 * * Redistributions of source code must retain the above copyright | 8 * * Redistributions of source code must retain the above copyright |
| 9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
| 10 * * Redistributions in binary form must reproduce the above | 10 * * Redistributions in binary form must reproduce the above |
| (...skipping 165 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 176 static const size_t kGenericMaxBucketedOrder = 15; // Largest bucketed order is
1<<(15-1) (storing 16KB -> almost 32KB)) | 176 static const size_t kGenericMaxBucketedOrder = 15; // Largest bucketed order is
1<<(15-1) (storing 16KB -> almost 32KB)) |
| 177 static const size_t kGenericMinBucketedOrder = 4; // 8 bytes. | 177 static const size_t kGenericMinBucketedOrder = 4; // 8 bytes. |
| 178 static const size_t kGenericNumBucketedOrders = (kGenericMaxBucketedOrder - kGen
ericMinBucketedOrder) + 1; | 178 static const size_t kGenericNumBucketedOrders = (kGenericMaxBucketedOrder - kGen
ericMinBucketedOrder) + 1; |
| 179 static const size_t kGenericNumBucketsPerOrderBits = 3; // Eight buckets per ord
er (for the higher orders), e.g. order 8 is 128, 144, 160, ..., 240 | 179 static const size_t kGenericNumBucketsPerOrderBits = 3; // Eight buckets per ord
er (for the higher orders), e.g. order 8 is 128, 144, 160, ..., 240 |
| 180 static const size_t kGenericNumBucketsPerOrder = 1 << kGenericNumBucketsPerOrder
Bits; | 180 static const size_t kGenericNumBucketsPerOrder = 1 << kGenericNumBucketsPerOrder
Bits; |
| 181 static const size_t kGenericSmallestBucket = 1 << (kGenericMinBucketedOrder - 1)
; | 181 static const size_t kGenericSmallestBucket = 1 << (kGenericMinBucketedOrder - 1)
; |
| 182 static const size_t kGenericMaxBucketSpacing = 1 << ((kGenericMaxBucketedOrder -
1) - kGenericNumBucketsPerOrderBits); | 182 static const size_t kGenericMaxBucketSpacing = 1 << ((kGenericMaxBucketedOrder -
1) - kGenericNumBucketsPerOrderBits); |
| 183 static const size_t kGenericMaxBucketed = (1 << (kGenericMaxBucketedOrder - 1))
+ ((kGenericNumBucketsPerOrder - 1) * kGenericMaxBucketSpacing); | 183 static const size_t kGenericMaxBucketed = (1 << (kGenericMaxBucketedOrder - 1))
+ ((kGenericNumBucketsPerOrder - 1) * kGenericMaxBucketSpacing); |
| 184 static const size_t kBitsPerSizet = sizeof(void*) * CHAR_BIT; | 184 static const size_t kBitsPerSizet = sizeof(void*) * CHAR_BIT; |
| 185 | 185 |
| 186 // Constants for the memory reclaim logic. |
| 187 static const size_t kMaxFreeableSpans = 16; |
| 186 | 188 |
| 187 #ifndef NDEBUG | 189 #ifndef NDEBUG |
| 188 // These two byte values match tcmalloc. | 190 // These two byte values match tcmalloc. |
| 189 static const unsigned char kUninitializedByte = 0xAB; | 191 static const unsigned char kUninitializedByte = 0xAB; |
| 190 static const unsigned char kFreedByte = 0xCD; | 192 static const unsigned char kFreedByte = 0xCD; |
| 191 #if CPU(64BIT) | 193 #if CPU(64BIT) |
| 192 static const uintptr_t kCookieValue = 0xDEADBEEFDEADBEEFul; | 194 static const uintptr_t kCookieValue = 0xDEADBEEFDEADBEEFul; |
| 193 #else | 195 #else |
| 194 static const uintptr_t kCookieValue = 0xDEADBEEFu; | 196 static const uintptr_t kCookieValue = 0xDEADBEEFu; |
| 195 #endif | 197 #endif |
| 196 #endif | 198 #endif |
| 197 | 199 |
| 200 struct PartitionBucket; |
| 198 struct PartitionRootBase; | 201 struct PartitionRootBase; |
| 199 struct PartitionBucket; | |
| 200 | 202 |
| 201 struct PartitionFreelistEntry { | 203 struct PartitionFreelistEntry { |
| 202 PartitionFreelistEntry* next; | 204 PartitionFreelistEntry* next; |
| 203 }; | 205 }; |
| 204 | 206 |
| 205 // Some notes on page states. A page can be in one of three major states: | 207 // Some notes on page states. A page can be in one of three major states: |
| 206 // 1) Active. | 208 // 1) Active. |
| 207 // 2) Full. | 209 // 2) Full. |
| 208 // 3) Free. | 210 // 3) Free. |
| 209 // An active page has available free slots. A full page has no free slots. A | 211 // An active page has available free slots. A full page has no free slots. A |
| (...skipping 12 matching lines...) Expand all Loading... |
| 222 // If it does this, full and free pages encountered will be booted out of the | 224 // If it does this, full and free pages encountered will be booted out of the |
| 223 // active list. If there are no suitable active pages found, a free page (if one | 225 // active list. If there are no suitable active pages found, a free page (if one |
| 224 // exists) will be pulled from the free list on to the active list. | 226 // exists) will be pulled from the free list on to the active list. |
| 225 struct PartitionPage { | 227 struct PartitionPage { |
| 226 PartitionFreelistEntry* freelistHead; | 228 PartitionFreelistEntry* freelistHead; |
| 227 PartitionPage* nextPage; | 229 PartitionPage* nextPage; |
| 228 PartitionBucket* bucket; | 230 PartitionBucket* bucket; |
| 229 int16_t numAllocatedSlots; // Deliberately signed, -1 for free page, -n for
full pages. | 231 int16_t numAllocatedSlots; // Deliberately signed, -1 for free page, -n for
full pages. |
| 230 uint16_t numUnprovisionedSlots; | 232 uint16_t numUnprovisionedSlots; |
| 231 uint16_t pageOffset; | 233 uint16_t pageOffset; |
| 234 uint16_t freeCacheIndex; |
| 232 }; | 235 }; |
| 233 | 236 |
| 234 struct PartitionBucket { | 237 struct PartitionBucket { |
| 235 PartitionPage* activePagesHead; // Accessed most in hot path => goes first. | 238 PartitionPage* activePagesHead; // Accessed most in hot path => goes first. |
| 236 PartitionPage* freePagesHead; | 239 PartitionPage* freePagesHead; |
| 237 uint16_t slotSize; | 240 uint16_t slotSize; |
| 238 uint16_t numSystemPagesPerSlotSpan; | 241 uint16_t numSystemPagesPerSlotSpan; |
| 239 uint32_t numFullPages; | 242 uint32_t numFullPages; |
| 240 }; | 243 }; |
| 241 | 244 |
| (...skipping 10 matching lines...) Expand all Loading... |
| 252 struct WTF_EXPORT PartitionRootBase { | 255 struct WTF_EXPORT PartitionRootBase { |
| 253 size_t totalSizeOfSuperPages; | 256 size_t totalSizeOfSuperPages; |
| 254 unsigned numBuckets; | 257 unsigned numBuckets; |
| 255 unsigned maxAllocation; | 258 unsigned maxAllocation; |
| 256 bool initialized; | 259 bool initialized; |
| 257 char* nextSuperPage; | 260 char* nextSuperPage; |
| 258 char* nextPartitionPage; | 261 char* nextPartitionPage; |
| 259 char* nextPartitionPageEnd; | 262 char* nextPartitionPageEnd; |
| 260 PartitionSuperPageExtentEntry* currentExtent; | 263 PartitionSuperPageExtentEntry* currentExtent; |
| 261 PartitionSuperPageExtentEntry* firstExtent; | 264 PartitionSuperPageExtentEntry* firstExtent; |
| 265 PartitionPage* globalEmptyPageRing[kMaxFreeableSpans]; |
| 266 size_t globalEmptyPageHeadIndex; |
| 267 size_t numGlobalEmptyPageEntries; |
| 262 uintptr_t invertedSelf; | 268 uintptr_t invertedSelf; |
| 263 | 269 |
| 264 static int gInitializedLock; | 270 static int gInitializedLock; |
| 265 static bool gInitialized; | 271 static bool gInitialized; |
| 266 static PartitionPage gSeedPage; | 272 static PartitionPage gSeedPage; |
| 267 static PartitionBucket gPagedBucket; | 273 static PartitionBucket gPagedBucket; |
| 268 }; | 274 }; |
| 269 | 275 |
| 270 // Never instantiate a PartitionRoot directly, instead use PartitionAlloc. | 276 // Never instantiate a PartitionRoot directly, instead use PartitionAlloc. |
| 271 struct PartitionRoot : public PartitionRootBase { | 277 struct PartitionRoot : public PartitionRootBase { |
| (...skipping 370 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 642 using WTF::PartitionRoot; | 648 using WTF::PartitionRoot; |
| 643 using WTF::partitionAllocInit; | 649 using WTF::partitionAllocInit; |
| 644 using WTF::partitionAllocShutdown; | 650 using WTF::partitionAllocShutdown; |
| 645 using WTF::partitionAlloc; | 651 using WTF::partitionAlloc; |
| 646 using WTF::partitionFree; | 652 using WTF::partitionFree; |
| 647 using WTF::partitionAllocGeneric; | 653 using WTF::partitionAllocGeneric; |
| 648 using WTF::partitionFreeGeneric; | 654 using WTF::partitionFreeGeneric; |
| 649 using WTF::partitionReallocGeneric; | 655 using WTF::partitionReallocGeneric; |
| 650 | 656 |
| 651 #endif // WTF_PartitionAlloc_h | 657 #endif // WTF_PartitionAlloc_h |
| OLD | NEW |