Skip to content

Commit 1c3d9d2

Browse files
Esteban Padilla Cerdiofacebook-github-bot
authored andcommitted
RegCount max registers calculation
Differential Revision: D59494644
1 parent 3d3babf commit 1c3d9d2

File tree

2 files changed

+132
-0
lines changed

2 files changed

+132
-0
lines changed
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
/*
2+
* Copyright (c) Meta Platforms, Inc. and affiliates.
3+
* All rights reserved.
4+
*
5+
* This source code is licensed under the BSD-style license found in the
6+
* LICENSE file in the root directory of this source tree.
7+
*/
8+
9+
#pragma once
10+
#include <array>
11+
#include <cstdint>
12+
13+
template <typename T>
14+
class AvgStats {
15+
T sum_ = 0;
16+
uint64_t n_ = 0;
17+
18+
public:
19+
typedef T value_t;
20+
21+
void push(T value) {
22+
sum_ += value;
23+
n_ += 1;
24+
}
25+
inline bool has_value() const {
26+
return n_ != 0;
27+
}
28+
operator T() const {
29+
return sum_ / n_;
30+
}
31+
};
32+
33+
template <typename T, size_t NTap>
34+
class NTapAvgStats {
35+
std::array<double, NTap> hist_;
36+
size_t cur_idx_;
37+
bool ready_;
38+
39+
public:
40+
typedef T value_t;
41+
42+
void push(T value) {
43+
hist_[cur_idx_++] = value;
44+
if (cur_idx_ >= NTap) {
45+
cur_idx_ = 0;
46+
ready_ = true;
47+
}
48+
}
49+
inline bool has_value() const {
50+
return ready_;
51+
}
52+
operator T() const {
53+
double out = 0.0;
54+
for (double x : hist_) {
55+
out += x;
56+
}
57+
out /= NTap;
58+
return out;
59+
}
60+
};

backends/vulkan/tools/gpuinfo/src/app.cpp

Lines changed: 72 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,62 @@
1010
#include <executorch/backends/vulkan/runtime/graph/ops/utils/StagingUtils.h>
1111
#include <iostream>
1212

13+
#include "stats.h"
1314
#include "utils.h"
1415

16+
template <uint32_t NTap>
17+
struct DtJumpFinder {
18+
private:
19+
NTapAvgStats<double, NTap> time_avg_;
20+
AvgStats<double> dtime_avg_;
21+
double compensation_;
22+
double threshold_;
23+
24+
public:
25+
// Compensation is a tiny additive to give on delta time so that the algorithm
26+
// works smoothly when a sequence of identical timing is ingested, which is
27+
// pretty common in our tests. Threshold is simply how many times the new
28+
// delta has to be to be recognized as a deviation.
29+
DtJumpFinder(double compensation = 0.01, double threshold = 10)
30+
: time_avg_(),
31+
dtime_avg_(),
32+
compensation_(compensation),
33+
threshold_(threshold) {}
34+
35+
// Returns true if the delta time regarding to the last data point seems
36+
// normal; returns false if it seems the new data point is too much away from
37+
// the historical records.
38+
bool push(double time) {
39+
if (time_avg_.has_value()) {
40+
double dtime = std::abs(time - time_avg_) + (compensation_ * time_avg_);
41+
if (dtime_avg_.has_value()) {
42+
double ddtime = std::abs(dtime - dtime_avg_);
43+
std::cout << dtime << "\t" << dtime_avg_ << "\t" << ddtime << "\t";
44+
if (ddtime > threshold_ * dtime_avg_) {
45+
return true;
46+
}
47+
}
48+
dtime_avg_.push(dtime);
49+
}
50+
time_avg_.push(time);
51+
return false;
52+
}
53+
54+
double dtime_avg() const {
55+
return dtime_avg_;
56+
}
57+
double compensate_time() const {
58+
return compensation_ * time_avg_;
59+
}
60+
};
61+
1562
void reg_count() {
1663
const uint32_t NREG_MIN = 1;
64+
const uint32_t NREG_MAX = 512;
65+
const uint32_t NREG_STEP = 1;
66+
67+
const double COMPENSATE = 0.01;
68+
const double THRESHOLD = 3;
1769

1870
uint32_t NITER;
1971

@@ -43,6 +95,26 @@ void reg_count() {
4395
std::cout << "Calculating NITER..." << std::endl;
4496
ensure_min_niter(1000, NITER, [&]() { return bench(1, 1, NREG_MIN); });
4597
std::cout << "NITER: " << NITER << std::endl;
98+
99+
uint32_t nreg_max;
100+
101+
DtJumpFinder<5> dj(COMPENSATE, THRESHOLD);
102+
uint32_t nreg = NREG_MIN;
103+
for (; nreg <= NREG_MAX; nreg += NREG_STEP) {
104+
double time = bench(1, 1, nreg);
105+
std::cout << "Testing nreg=\t" << nreg << "\tTime=\t" << time << std::endl;
106+
if (dj.push(time)) {
107+
nreg -= NREG_STEP;
108+
nreg_max = nreg;
109+
break;
110+
}
111+
}
112+
if (nreg >= NREG_MAX) {
113+
std::cout << "Unable to conclude a maximal register count" << std::endl;
114+
nreg_max = NREG_STEP;
115+
} else {
116+
std::cout << nreg_max << " available at most" << std::endl;
117+
}
46118
}
47119

48120
int main(int argc, const char** argv) {

0 commit comments

Comments
 (0)