c++ - 自动矢量化 : Convincing the compiler that alias check is not necessary

标签 c++ opencv gcc vectorization sse

我正在做一些图像处理,为此我受益于矢量化。 我有一个可以矢量化的函数,但是我无法让编译器相信输入和输出缓冲区没有重叠,因此不需要进行别名检查。 我应该可以使用 __restrict__ 来做到这一点,但是如果缓冲区在作为函数参数到达时未定义为 __restrict__,则无法让编译器相信我是绝对确定 2 个缓冲区永远不会重叠。

这是函数:

__attribute__((optimize("tree-vectorize","tree-vectorizer-verbose=6")))
void threshold(const cv::Mat& inputRoi, cv::Mat& outputRoi, const unsigned char th) {

    const int height = inputRoi.rows;
    const int width = inputRoi.cols;

    for (int j = 0; j < height; j++) {
        const uint8_t* __restrict in = (const uint8_t* __restrict) inputRoi.ptr(j);
        uint8_t* __restrict out = (uint8_t* __restrict) outputRoi.ptr(j);
        for (int i = 0; i < width; i++) {
           out[i] = (in[i] < valueTh) ? 255 : 0;
        }
    }
}

我可以说服编译器不执行别名检查的唯一方法是将内部循环放在一个单独的函数中,其中指针被定义为 __restrict__ 参数。如果我将此内部函数声明为内联函数,则会再次激活别名检查。

这个例子你也可以看到效果,我认为是一致的:http://goo.gl/7HK5p7

(注意:我知道编写相同函数可能有更好的方法,但在这种情况下,我只是想了解如何避免别名检查)

编辑:
问题解决了!! (见 answer below)
使用 gcc 4.9.2,here is the complete example .注意编译器标志 -fopt-info-vec-optimized 的使用代替被取代的 -ftree-vectorizer-verbose=N
因此,对于 gcc,使用 #pragma GCC ivdep 并享受吧! :)

最佳答案

如果您使用的是英特尔编译器,您可以尝试包含以下行:

#pragma ivdep 

以下段落引自英特尔编译器用户手册:

The ivdep pragma instructs the compiler to ignore assumed vector dependencies. To ensure correct code, the compiler treats an assumed dependence as a proven dependence, which prevents vectorization. This pragma overrides that decision. Use this pragma only when you know that the assumed loop dependencies are safe to ignore.

gcc 中,应添加以下行:

#pragma GCC ivdep

在函数内部和要矢量化的循环之前(参见 documentation)。这仅从 gcc 4.9 开始受支持,顺便说一下,使用 __restrict__ 是多余的。

关于c++ - 自动矢量化 : Convincing the compiler that alias check is not necessary,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25934239/

相关文章:

gcc - Visual C++转储预处理器定义

C: 无序浮点比较不会引发 FE_INVALID

c - 为什么我在 Ubuntu 上收到隐式声明函数 'open64'/'openat'/'openat64' 警告?

c++ - 流不按预期工作

c++ - 通过键 vector 从 map 获取 map

opencv 2.4 SIFT编译错误

python - 使用 OpenCV 3.4 加载 CNN tensorflow 模型时出错

c++ - 如何声明 2d std::array

java - 自动为枚举添加类似 Java 枚举的功能

python - 图像中的对象(简单形状)检测