1 /*
2 * Copyright 2019 Google LLC
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 "src/core/SkCpu.h"
9 #include "src/core/SkVM.h"
10 #include "tools/SkVMBuilders.h"
11 #include <chrono>
12 #include <stdio.h>
13 #include <stdlib.h>
14
sk_abort_no_print()15 void sk_abort_no_print() {
16 abort();
17 }
18
SkDebugf(const char * fmt,...)19 void SkDebugf(const char* fmt, ...) {
20 va_list args;
21 va_start(args, fmt);
22 vfprintf(stderr, fmt, args);
23 va_end(args);
24 }
25
plus_one()26 static skvm::Program plus_one() {
27 skvm::Builder b;
28
29 skvm::Arg ptr = b.varying<int>();
30 skvm::I32 v = b.load32(ptr);
31 b.store32(ptr, b.add(v, b.splat(1)));
32
33 return b.done("plus_one");
34 }
35
square()36 static skvm::Program square() {
37 skvm::Builder b;
38
39 skvm::Arg ptr = b.varying<int>();
40 skvm::I32 v = b.load32(ptr);
41 b.store32(ptr, b.mul(v,v));
42
43 return b.done("square");
44 }
45
print(double val,const char * units)46 static void print(double val, const char* units) {
47 const char* scales[] = { "", "K", "M", "G", "T" };
48 const char** scale = scales;
49
50 while (val > 10000.0) {
51 val *= 1/1000.0;
52 scale++;
53 }
54
55 printf("%4d %s%s", (int)val, *scale, units);
56 }
57
58 template <typename Fn>
measure(Fn && fn)59 static double measure(Fn&& fn) {
60 using clock = std::chrono::steady_clock;
61
62 int loops = 0;
63 auto start = clock::now();
64 std::chrono::duration<double> elapsed;
65 do {
66 fn();
67 loops++;
68 elapsed = clock::now() - start;
69 } while (elapsed < std::chrono::milliseconds(100));
70
71 return loops / elapsed.count();
72 }
73
74 template <typename... Args>
time(const char * name,const skvm::Program & program,Args...args)75 static void time(const char* name, const skvm::Program& program, Args... args) {
76 printf("%20s", name);
77
78 for (int N : { 15, 255, 4095 }) {
79 double loops_per_sec = measure([&]{
80 program.eval(N, args...);
81 });
82
83 printf("\t");
84 print(N*loops_per_sec, "px/s");
85 }
86 printf("\n");
87 }
88
main(int argc,char ** argv)89 int main(int argc, char** argv) {
90 #if defined(__x86_64__)
91 SkCpu::CacheRuntimeFeatures();
92 #endif
93
94 int src[4096],
95 dst[4096];
96 time("plus_one", plus_one(), dst);
97 time( "square", square(), dst);
98
99 time("srcover_f32" , SrcoverBuilder_F32 ().done("srcover_f32" ), src, dst);
100 time("srcover_i32" , SrcoverBuilder_I32 ().done("srcover_i32" ), src, dst);
101 time("srcover_i32_naive", SrcoverBuilder_I32_Naive().done("srcover_i32_naive"), src, dst);
102 time("srcover_i32_SWAR" , SrcoverBuilder_I32_SWAR ().done("srcover_i32_SWAR" ), src, dst);
103
104 return 0;
105 }
106