[cfe-dev] ubsan: problem with detecting UB in shift operation with large RHS

Dmitry Babokin via cfe-dev cfe-dev at lists.llvm.org
Mon Dec 12 14:46:55 PST 2016


Hello,

I'm using ubsan together with creduce to ensure that reduced test doesn't
have UB. And I've noticed that ubsan is not detecting UB in case of large
shift amount, particularly when rhs of shift has larger type that lhs. To
reproduce, rhs also has to have the value that is non-zero, but after
truncation to lhs type the value becomes zero.

Consider the following example.

#include <stdio.h>

// 1 is in 33rd bit.
unsigned long long l = 0x100000000ULL;

int main() {
    // Ubsan doesn't fire
    int res = 123 >> 0x100000000ULL;
    // Ubsan doesn't fire
    res += 123 >> l;
    // Ubsan does fire
    res += 123ULL >> l;
    printf("result = %d\n", res);
    return 0;
}

Changing the constant to the value, which fit 32 bits makes ubsan firing.

I understand where the problem comes from - LLVM IR definition requires
both operands of the shift to be of the same integer type. And ubsan
actually check already truncated value. But it doesn't match C/C++ standard
definition of UB in shift operation.

Is it possible to fix in current infrastructure? Should I file a bug for
this problem?

Note, it's not a theoretical problem, it's very practical one, which pops
up during automatic test reduction relatively frequently for me.

Dmitry.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20161213/3351a331/attachment.html>


More information about the cfe-dev mailing list