diff --git a/infer/tests/codetoanalyze/cpp/quandaryBO/codec.cpp b/infer/tests/codetoanalyze/cpp/quandaryBO/codec.cpp new file mode 100644 index 000000000..0e7bc3181 --- /dev/null +++ b/infer/tests/codetoanalyze/cpp/quandaryBO/codec.cpp @@ -0,0 +1,64 @@ +/* + * Copyright (c) 2018-present, Facebook, Inc. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + */ + +#include +#include +#include + +extern int __infer_taint_source(); + +namespace std { +template +unique_ptr make_unique(size_t n) { + typedef typename remove_extent::type U; + return unique_ptr(new U[n]()); +} +} // namespace std + +namespace Codec_Bad { +uint32_t getP_Bad(uint32_t w) { + auto w4 = w * 4; // BUG: can overflow + auto w4m1 = w4 - 1; // BUG: can underflow (if w = 0) + auto w4m1o15 = w4m1 | 15; // ALWAYS OK + auto w4m1o15p1 = w4m1o15 + 1; // BUG: can overflow + return w4m1o15p1; +} +void foo_Bad_FN() { + int w = __infer_taint_source(); + int h = __infer_taint_source(); + auto p = + getP_Bad(w); // MISSED BUG: downcasting signed int64 -> unsigned int32 + auto s = h * p; // BUG: multiplication can overflow + auto d = std::make_unique(s); // MISSED BUG: casting signed int64 + // -> unsigned int64, +} +} // namespace Codec_Bad + +namespace Codec_Bad2 { +uint64_t getP_Bad(uint64_t w) { + auto w4 = w * 4; // BUG: can overflow + auto w4m1 = w4 - 1; // BUG: can underflow (if w = 0) + auto w4m1o15 = w4m1 | 15; // ALWAYS OK + auto w4m1o15p1 = w4m1o15 + 1; // BUG: can overflow + return w4m1o15p1; +} +uint64_t checkedMultiply_Good_FP(uint64_t a, uint64_t b) { + __uint128_t mul = ((__uint128_t)a) * b; // OK: no overflow + if ((mul >> 64) != 0) { + throw std::runtime_error("Detected overflow in checked multiplcation"); + } + auto result = (uint64_t)mul; // OK: within the bounds + return result; +} +void foo_Bad_FN() { + int w = __infer_taint_source(); + int h = __infer_taint_source(); + auto p = getP_Bad(w); // MISSED BUG: casting signed int64 -> unsigned int64 + auto s = checkedMultiply_Good_FP(h, p); // OK + auto d = std::make_unique(s); // OK +} +} // namespace Codec_Bad2 diff --git a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t1 b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t1 index 25456e245..2f0a5ca00 100644 --- a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t1 +++ b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t1 @@ -1,3 +1,5 @@ +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::foo_Bad_FN, 3, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned64 by call to `Codec_Bad2::getP_Bad` ] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad::foo_Bad_FN, 4, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned32 by call to `Codec_Bad::getP_Bad` ] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, basic_bad, 3, TAINTED_BUFFER_ACCESS, no_bucket, ERROR, [Return from __infer_taint_source,Call to __array_access with tainted index 0,-----------,ArrayDeclaration,Unknown value from: __infer_taint_source,Assignment,ArrayAccess: Offset: [-oo, +oo] Size: 10] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, memory_alloc_bad2, 3, TAINTED_MEMORY_ALLOCATION, no_bucket, ERROR, [Return from __infer_taint_source,Call to __set_array_length with tainted index 1,-----------,Unknown value from: __infer_taint_source,Assignment,Alloc: Length: [-oo, 2147483647]] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, multi_level_bad, 2, TAINTED_BUFFER_ACCESS, no_bucket, ERROR, [Return from __infer_taint_source with tainted data return*,Return from multi_level_source_bad,Call to multi_level_sink_bad with tainted index 0,Call to __array_access with tainted index 0,-----------,Call,Unknown value from: __infer_taint_source,Assignment,Return,Assignment,Call,ArrayDeclaration,Parameter: i,ArrayAccess: Offset: [1, +oo] Size: 10 by call to `multi_level_sink_bad` ] diff --git a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t2 b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t2 index 077739e62..bbdf05057 100644 --- a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t2 +++ b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t2 @@ -1,3 +1,5 @@ +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::foo_Bad_FN, 3, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned64 by call to `Codec_Bad2::getP_Bad` ] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad::foo_Bad_FN, 4, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned32 by call to `Codec_Bad::getP_Bad` ] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, basic_bad, 3, TAINTED_BUFFER_ACCESS, no_bucket, ERROR, [Return from __infer_taint_source,Call to __array_access with tainted index 0,-----------,ArrayDeclaration,Unknown value from: __infer_taint_source,Assignment,ArrayAccess: Offset: [-oo, +oo] Size: 10] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, basic_bad, 3, UNTRUSTED_BUFFER_ACCESS, no_bucket, ERROR, [Return from __infer_taint_source,Call to __array_access with tainted index 0] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, memory_alloc_bad1_FN, 0, UNTRUSTED_VARIABLE_LENGTH_ARRAY, no_bucket, ERROR, [Return from __infer_taint_source,Call to __set_array_length with tainted index 1] diff --git a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t3 b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t3 index 6259d67ef..6e4f6234e 100644 --- a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t3 +++ b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t3 @@ -1,3 +1,5 @@ +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::foo_Bad_FN, 3, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned64 by call to `Codec_Bad2::getP_Bad` ] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad::foo_Bad_FN, 4, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned32 by call to `Codec_Bad::getP_Bad` ] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, basic_bad, 3, BUFFER_OVERRUN_U5, no_bucket, ERROR, [ArrayDeclaration,Unknown value from: __infer_taint_source,Assignment,ArrayAccess: Offset: [-oo, +oo] Size: 10] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, basic_bad, 3, TAINTED_BUFFER_ACCESS, no_bucket, ERROR, [Return from __infer_taint_source,Call to __array_access with tainted index 0,-----------,ArrayDeclaration,Unknown value from: __infer_taint_source,Assignment,ArrayAccess: Offset: [-oo, +oo] Size: 10] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, memory_alloc_bad2, 3, INFERBO_ALLOC_MAY_BE_BIG, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Alloc: Length: [-oo, 2147483647]] diff --git a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t4 b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t4 index 235908eaa..07560e8f7 100644 --- a/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t4 +++ b/infer/tests/codetoanalyze/cpp/quandaryBO/issues.exp-t4 @@ -1,3 +1,11 @@ +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::checkedMultiply_Good_FP, 1, INTEGER_OVERFLOW_L5, no_bucket, ERROR, [Parameter: a,Binop: (a * b):unsigned32] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::checkedMultiply_Good_FP, 2, CONDITION_ALWAYS_FALSE, no_bucket, WARNING, [] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::foo_Bad_FN, 3, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned64 by call to `Codec_Bad2::getP_Bad` ] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::foo_Bad_FN, 3, INTEGER_OVERFLOW_U5, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Binop: ([0, +oo] * 4):unsigned64 by call to `Codec_Bad2::getP_Bad` ] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad2::getP_Bad, 4, INTEGER_OVERFLOW_L5, no_bucket, ERROR, [Parameter: w,Assignment,Assignment,Assignment,Binop: ([-oo, +oo] + 1):unsigned64] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad::foo_Bad_FN, 4, INTEGER_OVERFLOW_L2, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Call,Parameter: w,Assignment,Binop: ([0, +oo] - 1):unsigned32 by call to `Codec_Bad::getP_Bad` ] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad::foo_Bad_FN, 5, INTEGER_OVERFLOW_U5, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Binop: ([-oo, +oo] * [-oo, +oo]):unsigned32] +codetoanalyze/cpp/quandaryBO/codec.cpp, Codec_Bad::getP_Bad, 4, INTEGER_OVERFLOW_L5, no_bucket, ERROR, [Parameter: w,Assignment,Assignment,Assignment,Binop: ([-oo, +oo] + 1):unsigned32] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, basic_bad, 3, BUFFER_OVERRUN_U5, no_bucket, ERROR, [ArrayDeclaration,Unknown value from: __infer_taint_source,Assignment,ArrayAccess: Offset: [-oo, +oo] Size: 10] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, basic_bad, 3, TAINTED_BUFFER_ACCESS, no_bucket, ERROR, [Return from __infer_taint_source,Call to __array_access with tainted index 0,-----------,ArrayDeclaration,Unknown value from: __infer_taint_source,Assignment,ArrayAccess: Offset: [-oo, +oo] Size: 10] codetoanalyze/cpp/quandaryBO/tainted_index.cpp, memory_alloc_bad2, 3, INFERBO_ALLOC_MAY_BE_BIG, no_bucket, ERROR, [Unknown value from: __infer_taint_source,Assignment,Alloc: Length: [-oo, 2147483647]]