Home | History | Annotate | Download | only in tests
      1 /*
      2  * Copyright 2014 Google, Inc
      3  *
      4  * Use of this source code is governed by a BSD-style license that can be
      5  * found in the LICENSE file.
      6  */
      7 
      8 #include "SkSmallAllocator.h"
      9 #include "SkTypes.h"
     10 #include "Test.h"
     11 
     12 class CountingClass {
     13 public:
     14     CountingClass() {
     15         kCount++;
     16     }
     17 
     18     ~CountingClass() {
     19         kCount--;
     20     }
     21 
     22     static int GetCount() { return kCount; }
     23 
     24 private:
     25     static int kCount;
     26 };
     27 
     28 int CountingClass::kCount;
     29 
     30 template<uint32_t kMaxObjects, size_t kBytes> void test_allocator(skiatest::Reporter* reporter) {
     31     {
     32         SkSmallAllocator<kMaxObjects, kBytes> alloc;
     33         for (uint32_t i = 0; i < kMaxObjects; ++i) {
     34             CountingClass* c = alloc.template createT<CountingClass>();
     35             REPORTER_ASSERT(reporter, c != nullptr);
     36             REPORTER_ASSERT(reporter, CountingClass::GetCount() == static_cast<int>(i+1));
     37         }
     38     }
     39     REPORTER_ASSERT(reporter, CountingClass::GetCount() == 0);
     40 }
     41 
     42 // Tests that ensure that the destructor is called, whether the objects
     43 // were created in fStorage or on the heap.
     44 DEF_TEST(SmallAllocator_destructor, reporter) {
     45     // Four times as many bytes as objects will never require any heap
     46     // allocations (since SkAlign4(sizeof(CountingClass)) == 4 and the allocator
     47     // will stop once it reaches kMaxObjects).
     48     test_allocator<5, 20>(reporter);
     49     test_allocator<10, 40>(reporter);
     50     test_allocator<20, 80>(reporter);
     51 
     52 #ifndef SK_DEBUG
     53     // Allowing less bytes than objects means some will be allocated on the
     54     // heap. Don't run these in debug where we assert.
     55     test_allocator<50, 20>(reporter);
     56     test_allocator<100, 20>(reporter);
     57 #endif
     58 }
     59 
     60 class Dummy {
     61 };
     62 
     63 class DummyContainer {
     64 public:
     65     explicit DummyContainer(Dummy* d)
     66         :fDummy(d)
     67     {}
     68 
     69     Dummy* getDummy() const { return fDummy; }
     70 
     71 private:
     72     Dummy* fDummy;
     73 };
     74 
     75 // Test that using a createT with a constructor taking a pointer as a
     76 // parameter works as expected.
     77 DEF_TEST(SmallAllocator_pointer, reporter) {
     78     SkSmallAllocator<1, 8> alloc;
     79     Dummy d;
     80     DummyContainer* container = alloc.createT<DummyContainer>(&d);
     81     REPORTER_ASSERT(reporter, container != nullptr);
     82     REPORTER_ASSERT(reporter, container->getDummy() == &d);
     83 }
     84