Title: [208690] trunk/Source
Revision
208690
Author
mark....@apple.com
Date
2016-11-14 10:04:06 -0800 (Mon, 14 Nov 2016)

Log Message

Add debugging facility to limit the max single allocation size.
https://bugs.webkit.org/show_bug.cgi?id=164681

Reviewed by Keith Miller.

Source/_javascript_Core:

Added JSC option to set FastMalloc's maxSingleAllocationSize for testing purposes.
This option is only available on Debug builds.

* runtime/Options.cpp:
(JSC::Options::isAvailable):
(JSC::recomputeDependentOptions):
* runtime/Options.h:

Source/WTF:

This is useful for simulating memory allocation failures on resource constraint
devices for testing purposes.

This facility is only conditionally compiled in on debug builds.  It does not
have any burden on release builds at all.  When in use, the max single allocation
size limit applies to individual allocations.  For malloc (and similar), the
allocation will crash in FastMalloc if the requested size exceeds the set max
single allocation size.  For tryMalloc (and similar), the allocation returns
nullptr if the requested size exceeds the set max single allocation size.  The
max single allocation size is set to std::numeric_limit<size_t>::max() by default
(i.e. when not set and no limit is in effect).

Also fixed non-bmalloc versions of fastAlignedMalloc() to crash when allocation
fails.

* wtf/FastMalloc.cpp:
(WTF::fastSetMaxSingleAllocationSize):
(WTF::fastAlignedMalloc):
(WTF::tryFastAlignedMalloc):
(WTF::tryFastMalloc):
(WTF::fastMalloc):
(WTF::tryFastCalloc):
(WTF::fastCalloc):
(WTF::fastRealloc):
* wtf/FastMalloc.h:

Modified Paths

Diff

Modified: trunk/Source/_javascript_Core/ChangeLog (208689 => 208690)


--- trunk/Source/_javascript_Core/ChangeLog	2016-11-14 17:59:08 UTC (rev 208689)
+++ trunk/Source/_javascript_Core/ChangeLog	2016-11-14 18:04:06 UTC (rev 208690)
@@ -1,3 +1,18 @@
+2016-11-13  Mark Lam  <mark....@apple.com>
+
+        Add debugging facility to limit the max single allocation size.
+        https://bugs.webkit.org/show_bug.cgi?id=164681
+
+        Reviewed by Keith Miller.
+
+        Added JSC option to set FastMalloc's maxSingleAllocationSize for testing purposes.
+        This option is only available on Debug builds.
+
+        * runtime/Options.cpp:
+        (JSC::Options::isAvailable):
+        (JSC::recomputeDependentOptions):
+        * runtime/Options.h:
+
 2016-11-12  Joseph Pecoraro  <pecor...@apple.com>
 
         Follow-up fix to r208639.

Modified: trunk/Source/_javascript_Core/runtime/Options.cpp (208689 => 208690)


--- trunk/Source/_javascript_Core/runtime/Options.cpp	2016-11-14 17:59:08 UTC (rev 208689)
+++ trunk/Source/_javascript_Core/runtime/Options.cpp	2016-11-14 18:04:06 UTC (rev 208690)
@@ -136,6 +136,10 @@
     if (id == reportLLIntStatsID || id == llintStatsFileID)
         return true;
 #endif
+#if !defined(NDEBUG)
+    if (id == maxSingleAllocationSizeID)
+        return true;
+#endif
     return false;
 }
 
@@ -396,6 +400,12 @@
 #if ENABLE(LLINT_STATS)
     LLInt::Data::loadStats();
 #endif
+#if !defined(NDEBUG)
+    if (Options::maxSingleAllocationSize())
+        fastSetMaxSingleAllocationSize(Options::maxSingleAllocationSize());
+    else
+        fastSetMaxSingleAllocationSize(std::numeric_limits<size_t>::max());
+#endif
 }
 
 void Options::initialize()

Modified: trunk/Source/_javascript_Core/runtime/Options.h (208689 => 208690)


--- trunk/Source/_javascript_Core/runtime/Options.h	2016-11-14 17:59:08 UTC (rev 208689)
+++ trunk/Source/_javascript_Core/runtime/Options.h	2016-11-14 18:04:06 UTC (rev 208690)
@@ -323,6 +323,7 @@
     v(bool, useZombieMode, false, Normal, "debugging option to scribble over dead objects with 0xdeadbeef") \
     v(bool, useImmortalObjects, false, Normal, "debugging option to keep all objects alive forever") \
     v(bool, dumpObjectStatistics, false, Normal, nullptr) \
+    v(unsigned, maxSingleAllocationSize, 0, Configurable, "debugging option to limit individual allocations to a max size (0 = limit not set, N = limit size in bytes)") \
     \
     v(gcLogLevel, logGC, GCLogging::None, Normal, "debugging option to log GC activity (0 = None, 1 = Basic, 2 = Verbose)") \
     v(bool, useGC, true, Normal, nullptr) \

Modified: trunk/Source/WTF/ChangeLog (208689 => 208690)


--- trunk/Source/WTF/ChangeLog	2016-11-14 17:59:08 UTC (rev 208689)
+++ trunk/Source/WTF/ChangeLog	2016-11-14 18:04:06 UTC (rev 208690)
@@ -1,3 +1,36 @@
+2016-11-13  Mark Lam  <mark....@apple.com>
+
+        Add debugging facility to limit the max single allocation size.
+        https://bugs.webkit.org/show_bug.cgi?id=164681
+
+        Reviewed by Keith Miller.
+
+        This is useful for simulating memory allocation failures on resource constraint
+        devices for testing purposes.
+
+        This facility is only conditionally compiled in on debug builds.  It does not
+        have any burden on release builds at all.  When in use, the max single allocation
+        size limit applies to individual allocations.  For malloc (and similar), the
+        allocation will crash in FastMalloc if the requested size exceeds the set max
+        single allocation size.  For tryMalloc (and similar), the allocation returns
+        nullptr if the requested size exceeds the set max single allocation size.  The
+        max single allocation size is set to std::numeric_limit<size_t>::max() by default
+        (i.e. when not set and no limit is in effect).
+
+        Also fixed non-bmalloc versions of fastAlignedMalloc() to crash when allocation
+        fails.
+
+        * wtf/FastMalloc.cpp:
+        (WTF::fastSetMaxSingleAllocationSize):
+        (WTF::fastAlignedMalloc):
+        (WTF::tryFastAlignedMalloc):
+        (WTF::tryFastMalloc):
+        (WTF::fastMalloc):
+        (WTF::tryFastCalloc):
+        (WTF::fastCalloc):
+        (WTF::fastRealloc):
+        * wtf/FastMalloc.h:
+
 2016-11-13  JF Bastien  <jfbast...@apple.com>
 
         Implement WTF::Expected

Modified: trunk/Source/WTF/wtf/FastMalloc.cpp (208689 => 208690)


--- trunk/Source/WTF/wtf/FastMalloc.cpp	2016-11-14 17:59:08 UTC (rev 208689)
+++ trunk/Source/WTF/wtf/FastMalloc.cpp	2016-11-14 18:04:06 UTC (rev 208690)
@@ -46,6 +46,33 @@
 
 namespace WTF {
 
+#if !defined(NDEBUG)
+namespace {
+size_t maxSingleAllocationSize = std::numeric_limits<size_t>::max();
+};
+
+void fastSetMaxSingleAllocationSize(size_t size)
+{
+    maxSingleAllocationSize = size;
+}
+
+#define ASSERT_IS_WITHIN_LIMIT(size) do { \
+        size_t size__ = (size); \
+        ASSERT_WITH_MESSAGE((size__) <= maxSingleAllocationSize, "Requested size (%zu) exceeds max single allocation size set for testing (%zu)", (size__), maxSingleAllocationSize); \
+    } while (false)
+
+#define FAIL_IF_EXCEEDS_LIMIT(size) do { \
+        if (UNLIKELY((size) > maxSingleAllocationSize)) \
+            return nullptr; \
+    } while (false)
+
+#else // !defined(NDEBUG)
+
+#define ASSERT_IS_WITHIN_LIMIT(size)
+#define FAIL_IF_EXCEEDS_LIMIT(size)
+
+#endif // !defined(NDEBUG)
+
 void* fastZeroedMalloc(size_t n) 
 {
     void* result = fastMalloc(n);
@@ -98,11 +125,16 @@
 
 void* fastAlignedMalloc(size_t alignment, size_t size) 
 {
-    return _aligned_malloc(size, alignment);
+    ASSERT_IS_WITHIN_LIMIT(size);
+    void* p = _aligned_malloc(size, alignment);
+    if (UNLIKELY(!p))
+        CRASH();
+    return p;
 }
 
 void* tryFastAlignedMalloc(size_t alignment, size_t size) 
 {
+    FAIL_IF_EXCEEDS_LIMIT(size);
     return _aligned_malloc(size, alignment);
 }
 
@@ -115,13 +147,17 @@
 
 void* fastAlignedMalloc(size_t alignment, size_t size) 
 {
+    ASSERT_IS_WITHIN_LIMIT(size);
     void* p = nullptr;
     posix_memalign(&p, alignment, size);
+    if (UNLIKELY(!p))
+        CRASH();
     return p;
 }
 
 void* tryFastAlignedMalloc(size_t alignment, size_t size) 
 {
+    FAIL_IF_EXCEEDS_LIMIT(size);
     void* p = nullptr;
     posix_memalign(&p, alignment, size);
     return p;
@@ -136,11 +172,13 @@
 
 TryMallocReturnValue tryFastMalloc(size_t n) 
 {
+    FAIL_IF_EXCEEDS_LIMIT(n);
     return malloc(n);
 }
 
 void* fastMalloc(size_t n) 
 {
+    ASSERT_IS_WITHIN_LIMIT(n);
     void* result = malloc(n);
     if (!result)
         CRASH();
@@ -150,11 +188,13 @@
 
 TryMallocReturnValue tryFastCalloc(size_t n_elements, size_t element_size)
 {
+    FAIL_IF_EXCEEDS_LIMIT(n_elements * element_size);
     return calloc(n_elements, element_size);
 }
 
 void* fastCalloc(size_t n_elements, size_t element_size)
 {
+    ASSERT_IS_WITHIN_LIMIT(n_elements * element_size);
     void* result = calloc(n_elements, element_size);
     if (!result)
         CRASH();
@@ -169,6 +209,7 @@
 
 void* fastRealloc(void* p, size_t n)
 {
+    ASSERT_IS_WITHIN_LIMIT(n);
     void* result = realloc(p, n);
     if (!result)
         CRASH();
@@ -211,11 +252,13 @@
 
 void* fastMalloc(size_t size)
 {
+    ASSERT_IS_WITHIN_LIMIT(size);
     return bmalloc::api::malloc(size);
 }
 
 void* fastCalloc(size_t numElements, size_t elementSize)
 {
+    ASSERT_IS_WITHIN_LIMIT(numElements * elementSize);
     Checked<size_t> checkedSize = elementSize;
     checkedSize *= numElements;
     void* result = fastZeroedMalloc(checkedSize.unsafeGet());
@@ -226,6 +269,7 @@
 
 void* fastRealloc(void* object, size_t size)
 {
+    ASSERT_IS_WITHIN_LIMIT(size);
     return bmalloc::api::realloc(object, size);
 }
 
@@ -249,11 +293,13 @@
 
 void* fastAlignedMalloc(size_t alignment, size_t size) 
 {
+    ASSERT_IS_WITHIN_LIMIT(size);
     return bmalloc::api::memalign(alignment, size);
 }
 
 void* tryFastAlignedMalloc(size_t alignment, size_t size) 
 {
+    FAIL_IF_EXCEEDS_LIMIT(size);
     return bmalloc::api::tryMemalign(alignment, size);
 }
 
@@ -264,11 +310,13 @@
 
 TryMallocReturnValue tryFastMalloc(size_t size)
 {
+    FAIL_IF_EXCEEDS_LIMIT(size);
     return bmalloc::api::tryMalloc(size);
 }
     
 TryMallocReturnValue tryFastCalloc(size_t numElements, size_t elementSize)
 {
+    FAIL_IF_EXCEEDS_LIMIT(numElements * elementSize);
     Checked<size_t, RecordOverflow> checkedSize = elementSize;
     checkedSize *= numElements;
     if (checkedSize.hasOverflowed())

Modified: trunk/Source/WTF/wtf/FastMalloc.h (208689 => 208690)


--- trunk/Source/WTF/wtf/FastMalloc.h	2016-11-14 17:59:08 UTC (rev 208689)
+++ trunk/Source/WTF/wtf/FastMalloc.h	2016-11-14 18:04:06 UTC (rev 208690)
@@ -27,6 +27,10 @@
 
 namespace WTF {
 
+#if !defined(NDEBUG)
+void fastSetMaxSingleAllocationSize(size_t);
+#endif
+
 class TryMallocReturnValue {
 public:
     TryMallocReturnValue(void*);
@@ -102,6 +106,10 @@
 
 } // namespace WTF
 
+#if !defined(NDEBUG)
+using WTF::fastSetMaxSingleAllocationSize;
+#endif
+
 using WTF::isFastMallocEnabled;
 using WTF::fastCalloc;
 using WTF::fastFree;
_______________________________________________
webkit-changes mailing list
webkit-changes@lists.webkit.org
https://lists.webkit.org/mailman/listinfo/webkit-changes

Reply via email to