This source file includes following definitions.
- is_interleaved
- is_planar
- generate
- schedule
#include "Halide.h"
namespace {
template<typename T>
Halide::Expr is_interleaved(const T &p, int channels = 3) {
return p.dim(0).stride() == channels && p.dim(2).stride() == 1 && p.dim(2).extent() == channels;
}
template<typename T>
Halide::Expr is_planar(const T &p, int channels = 3) {
return p.dim(0).stride() == 1 && p.dim(2).extent() == channels;
}
class Blur2x2 : public Halide::Generator<Blur2x2> {
public:
Input<Buffer<float>> input{ "input", 3 };
Input<int32_t> width{ "width" };
Input<int32_t> height{ "height" };
Output<Buffer<float>> blur{ "blur", 3 };
void generate() {
Func input_clamped = Halide::BoundaryConditions::repeat_edge(
input, 0, width, 0, height);
blur(x, y, c) =
(input_clamped(x - 1, y, c) + input_clamped(x + 1, y, c) +
input_clamped(x, y - 1, c) + input_clamped(x, y + 1, c)) /
4.0f;
}
void schedule() {
input.dim(0).set_stride(Expr());
blur.dim(0).set_stride(Expr());
blur.specialize(is_planar(input) && is_planar(blur))
.vectorize(x, natural_vector_size<float>());
blur.specialize(is_interleaved(input) && is_interleaved(blur))
.reorder(c, x, y)
.vectorize(c);
}
private:
Var x{"x"}, y{"y"}, c{"c"};
};
HALIDE_REGISTER_GENERATOR(Blur2x2, "blur2x2")
}