Home | History | Annotate | Download | only in bench
      1 /*
      2  * Copyright 2012 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 "SkTypes.h"
      9 
     10 // This tests a Gr class
     11 #if SK_SUPPORT_GPU
     12 
     13 #include "Benchmark.h"
     14 #include "GrMemoryPool.h"
     15 #include "SkRandom.h"
     16 #include "SkTDArray.h"
     17 #include "SkTemplates.h"
     18 
     19 // change this to 0 to compare GrMemoryPool to default new / delete
     20 #define OVERRIDE_NEW    1
     21 
     22 struct A {
     23     int gStuff[10];
     24 #if OVERRIDE_NEW
     25     void* operator new (size_t size) { return gBenchPool.allocate(size); }
     26     void operator delete (void* mem) { if (mem) { return gBenchPool.release(mem); } }
     27 #endif
     28     static GrMemoryPool gBenchPool;
     29 };
     30 GrMemoryPool A::gBenchPool(10 * (1 << 10), 10 * (1 << 10));
     31 
     32 /**
     33  * This benchmark creates and deletes objects in stack order
     34  */
     35 class GrMemoryPoolBenchStack : public Benchmark {
     36 public:
     37     bool isSuitableFor(Backend backend) override {
     38         return backend == kNonRendering_Backend;
     39     }
     40 
     41 protected:
     42     const char* onGetName() override {
     43         return "grmemorypool_stack";
     44     }
     45 
     46     void onDraw(int loops, SkCanvas*) override {
     47         SkRandom r;
     48         enum {
     49             kMaxObjects = 4 * (1 << 10),
     50         };
     51         A* objects[kMaxObjects];
     52 
     53         // We delete if a random number [-1, 1] is < the thresh. Otherwise,
     54         // we allocate. We start allocate-biased and ping-pong to delete-biased
     55         SkScalar delThresh = -SK_ScalarHalf;
     56         const int kSwitchThreshPeriod = loops / (2 * kMaxObjects);
     57         int s = 0;
     58 
     59         int count = 0;
     60         for (int i = 0; i < loops; i++, ++s) {
     61             if (kSwitchThreshPeriod == s) {
     62                 delThresh = -delThresh;
     63                 s = 0;
     64             }
     65             SkScalar del = r.nextSScalar1();
     66             if (count &&
     67                 (kMaxObjects == count || del < delThresh)) {
     68                 delete objects[count-1];
     69                 --count;
     70             } else {
     71                 objects[count] = new A;
     72                 ++count;
     73             }
     74         }
     75         for (int i = 0; i < count; ++i) {
     76             delete objects[i];
     77         }
     78     }
     79 
     80 private:
     81     typedef Benchmark INHERITED;
     82 };
     83 
     84 struct B {
     85     int gStuff[10];
     86 #if OVERRIDE_NEW
     87     void* operator new (size_t size) { return gBenchPool.allocate(size); }
     88     void operator delete (void* mem) { if (mem) { return gBenchPool.release(mem); } }
     89 #endif
     90     static GrMemoryPool gBenchPool;
     91 };
     92 GrMemoryPool B::gBenchPool(10 * (1 << 10), 10 * (1 << 10));
     93 
     94 /**
     95  * This benchmark creates objects and deletes them in random order
     96  */
     97 class GrMemoryPoolBenchRandom : public Benchmark {
     98 public:
     99     bool isSuitableFor(Backend backend) override {
    100         return backend == kNonRendering_Backend;
    101     }
    102 
    103 protected:
    104     const char* onGetName() override {
    105         return "grmemorypool_random";
    106     }
    107 
    108     void onDraw(int loops, SkCanvas*) override {
    109         SkRandom r;
    110         enum {
    111             kMaxObjects = 4 * (1 << 10),
    112         };
    113         std::unique_ptr<B> objects[kMaxObjects];
    114 
    115         for (int i = 0; i < loops; i++) {
    116             uint32_t idx = r.nextRangeU(0, kMaxObjects-1);
    117             if (nullptr == objects[idx].get()) {
    118                 objects[idx].reset(new B);
    119             } else {
    120                 objects[idx].reset();
    121             }
    122         }
    123     }
    124 
    125 private:
    126     typedef Benchmark INHERITED;
    127 };
    128 
    129 struct C {
    130     int gStuff[10];
    131 #if OVERRIDE_NEW
    132     void* operator new (size_t size) { return gBenchPool.allocate(size); }
    133     void operator delete (void* mem) { if (mem) { return gBenchPool.release(mem); } }
    134 #endif
    135     static GrMemoryPool gBenchPool;
    136 };
    137 GrMemoryPool C::gBenchPool(10 * (1 << 10), 10 * (1 << 10));
    138 
    139 /**
    140  * This benchmark creates objects and deletes them in queue order
    141  */
    142 class GrMemoryPoolBenchQueue : public Benchmark {
    143     enum {
    144         M = 4 * (1 << 10),
    145     };
    146 public:
    147     bool isSuitableFor(Backend backend) override {
    148         return backend == kNonRendering_Backend;
    149     }
    150 
    151 protected:
    152     const char* onGetName() override {
    153         return "grmemorypool_queue";
    154     }
    155 
    156     void onDraw(int loops, SkCanvas*) override {
    157         SkRandom r;
    158         C* objects[M];
    159         for (int i = 0; i < loops; i++) {
    160             uint32_t count = r.nextRangeU(0, M-1);
    161             for (uint32_t i = 0; i < count; i++) {
    162                 objects[i] = new C;
    163             }
    164             for (uint32_t i = 0; i < count; i++) {
    165                 delete objects[i];
    166             }
    167         }
    168     }
    169 
    170 private:
    171     typedef Benchmark INHERITED;
    172 };
    173 
    174 ///////////////////////////////////////////////////////////////////////////////
    175 
    176 DEF_BENCH( return new GrMemoryPoolBenchStack(); )
    177 DEF_BENCH( return new GrMemoryPoolBenchRandom(); )
    178 DEF_BENCH( return new GrMemoryPoolBenchQueue(); )
    179 
    180 #endif
    181