ColorPrivBench.cpp 3.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687
  1. /*
  2. * Copyright 2013 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. #include "bench/Benchmark.h"
  8. #include "include/core/SkString.h"
  9. #include "include/private/SkColorData.h"
  10. #include "include/utils/SkRandom.h"
  11. template <bool kFast, bool kScale>
  12. class FourByteInterpBench : public Benchmark {
  13. public:
  14. FourByteInterpBench() {
  15. fName.set("four_byte_interp");
  16. fName.append(kFast ? "_fast" : "_slow");
  17. fName.append(kScale ? "_255" : "_256");
  18. }
  19. bool isSuitableFor(Backend backend) override {
  20. return backend == kNonRendering_Backend;
  21. }
  22. const char* onGetName() override { return fName.c_str(); }
  23. void onDelayedSetup() override {
  24. // A handful of random srcs and dsts.
  25. SkRandom rand;
  26. for (int i = 0; i < kInputs; i++) {
  27. fSrcs[i] = SkPreMultiplyColor(rand.nextU());
  28. fDsts[i] = SkPreMultiplyColor(rand.nextU());
  29. }
  30. // We'll exhaustively test all scales instead of using random numbers.
  31. for (int i = 0; i <= 256; i++) {
  32. fScales[i] = i;
  33. }
  34. if (kScale) fScales[256] = 255; // We'll just do 255 twice if we're limited to [0,255].
  35. }
  36. void onDraw(int loops, SkCanvas*) override {
  37. // We xor results of FourByteInterp into junk to make sure the function runs.
  38. volatile SkPMColor junk = 0;
  39. for (int loop = 0; loop < loops; loop++) {
  40. for (int i = 0; i < kInputs; i++) {
  41. for (size_t j = 0; j <= 256; j++) {
  42. // Note: we really want to load src and dst here and not outside in the i-loop.
  43. // If we put the loads there, a clever compiler will do the not-insignificant
  44. // work in the FourByteInterps that depends only on src and dst outside this
  45. // loop, so we'd only be benchmarking the back half of those functions that also
  46. // depends on scale. Even here, these must be volatile arrays to prevent that
  47. // clever compiler from hoisting the loads out of the loop on its own.
  48. const SkPMColor src = fSrcs[i];
  49. const SkPMColor dst = fDsts[i];
  50. const unsigned scale = fScales[j];
  51. if (kFast && kScale) {
  52. junk ^= SkFastFourByteInterp(src, dst, scale);
  53. } else if (kFast) {
  54. junk ^= SkFastFourByteInterp256(src, dst, scale);
  55. } else if (kScale) {
  56. junk ^= SkFourByteInterp(src, dst, scale);
  57. } else {
  58. junk ^= SkFourByteInterp256(src, dst, scale);
  59. }
  60. }
  61. }
  62. }
  63. }
  64. private:
  65. SkString fName;
  66. static const int kInputs = 10; // Arbitrary.
  67. volatile unsigned fSrcs[kInputs];
  68. volatile unsigned fDsts[kInputs];
  69. unsigned fScales[257]; // We need space for [0, 256].
  70. };
  71. #define COMMA ,
  72. DEF_BENCH(return (new FourByteInterpBench<true COMMA true>);)
  73. DEF_BENCH(return (new FourByteInterpBench<true COMMA false>);)
  74. DEF_BENCH(return (new FourByteInterpBench<false COMMA true>);)
  75. DEF_BENCH(return (new FourByteInterpBench<false COMMA false>);)
  76. #undef COMMA