| 158 | #if MEGDNN_WITH_BENCHMARK |
| 159 | namespace { |
| 160 | void run_elemwise_benchmark( |
| 161 | const TensorShapeArray& shapes, param::Elemwise::Mode mode, |
| 162 | const char* mode_str, DType type, Handle* handle_bench) { |
| 163 | auto handle_fallback = create_cpu_handle(1); |
| 164 | Benchmarker<Elemwise> benchmarker_bench(handle_bench); |
| 165 | Benchmarker<Elemwise> benchmarker_fallback(handle_fallback.get()); |
| 166 | |
| 167 | float throughput = 0; |
| 168 | SmallVector<TensorLayout> layouts; |
| 169 | std::string src_strs; |
| 170 | for (size_t i = 0; i < shapes.size(); i++) { |
| 171 | layouts.emplace_back(shapes[i], type); |
| 172 | throughput += layouts.back().span().dist_byte(); |
| 173 | src_strs += layouts.back().to_string(); |
| 174 | if (i != shapes.size() - 1) { |
| 175 | src_strs += ","; |
| 176 | } |
| 177 | } |
| 178 | constexpr size_t RUN = 50; |
| 179 | benchmarker_fallback.set_times(RUN).set_display(false); |
| 180 | benchmarker_bench.set_times(RUN).set_display(false); |
| 181 | |
| 182 | benchmarker_fallback.set_param(mode); |
| 183 | benchmarker_bench.set_param(mode); |
| 184 | |
| 185 | TensorLayout dst_layout; |
| 186 | auto opr = handle_bench->create_operator<Elemwise>(); |
| 187 | opr->param() = mode; |
| 188 | opr->deduce_layout(layouts, dst_layout); |
| 189 | |
| 190 | float computations = |
| 191 | dst_layout.total_nr_elems() * (std::max<size_t>(shapes.size(), 2) - 1); |
| 192 | throughput += dst_layout.span().dist_byte(); |
| 193 | computations *= (1e3 / (1024.0 * 1024)); |
| 194 | throughput *= (1e3 / (1024.0 * 1024)); |
| 195 | |
| 196 | layouts.emplace_back(dst_layout); |
| 197 | auto fallback_time = benchmarker_fallback.execl(layouts) / RUN; |
| 198 | auto bench_time = benchmarker_bench.execl(layouts) / RUN; |
| 199 | |
| 200 | float fallback_flops = computations / fallback_time; |
| 201 | float bench_flops = computations / bench_time; |
| 202 | float fallback_thr = throughput / fallback_time; |
| 203 | float bench_thr = throughput / bench_time; |
| 204 | |
| 205 | printf("%s = %s (type: %s, mode: %s) cpu=%fMFLOPS %fMB/s, bench=%fMFLOPS " |
| 206 | "%fMB/s " |
| 207 | "computations: %fx, throughput: %fx\n", |
| 208 | src_strs.c_str(), dst_layout.to_string().c_str(), type.name(), mode_str, |
| 209 | fallback_flops, fallback_thr, bench_flops, bench_thr, |
| 210 | bench_flops / fallback_flops, bench_thr / fallback_thr); |
| 211 | } |
| 212 | } // namespace |
| 213 | |
| 214 | #define INT_RUN(shape, mode) \ |
nothing calls this directly
no test coverage detected