================ @@ -0,0 +1,2539 @@ +//===- UncheckedStatusOrAccessModelTestFixture.cpp ------------------------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "UncheckedStatusOrAccessModelTestFixture.h" +#include "MockHeaders.h" +#include "llvm/Support/ErrorHandling.h" + +#include <string> +#include <utility> +#include <vector> + +#include "gtest/gtest.h" + +namespace clang::dataflow::statusor_model { +namespace { + +TEST_P(UncheckedStatusOrAccessModelTest, NoStatusOrMention) { + ExpectDiagnosticsFor(R"cc( + void target() { "nop"; } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Lvalue_CallToValue) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, NonExplicitInitialization) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + STATUSOR_INT target() { + STATUSOR_INT x = Make<STATUSOR_INT>(); + return x.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Lvalue_CallToValue_NewLine) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Rvalue_CallToValue) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + std::move(sor).value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Lvalue_CallToValueOrDie) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + sor.ValueOrDie(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Rvalue_CallToValueOrDie) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + std::move(sor).ValueOrDie(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Lvalue_CallToOperatorStar) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + *sor; // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Lvalue_CallToOperatorStarSeparateLine) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + * // [[unsafe]] + sor; + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Rvalue_CallToOperatorStar) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + *std::move(sor); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Lvalue_CallToOperatorArrow) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + struct Foo { + void foo(); + }; + + void target(absl::StatusOr<Foo> sor) { + sor->foo(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, + UnwrapWithoutCheck_Rvalue_CallToOperatorArrow) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + struct Foo { + void foo(); + }; + + void target(absl::StatusOr<Foo> sor) { + std::move(sor)->foo(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, UnwrapRvalueWithCheck) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (sor.ok()) std::move(sor).value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, ParensInDeclInitExpr) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target() { + auto sor = (Make<STATUSOR_INT>()); + if (sor.ok()) sor.value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, ReferenceInDeclInitExpr) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + struct Foo { + const STATUSOR_INT& GetStatusOrInt() const; + }; + + void target(Foo foo) { + auto sor = foo.GetStatusOrInt(); + if (sor.ok()) sor.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + struct Foo { + STATUSOR_INT& GetStatusOrInt(); + }; + + void target(Foo foo) { + auto sor = foo.GetStatusOrInt(); + if (sor.ok()) sor.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + struct Foo { + STATUSOR_INT&& GetStatusOrInt() &&; + }; + + void target(Foo foo) { + auto sor = std::move(foo).GetStatusOrInt(); + if (sor.ok()) sor.value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (sor.ok()) + sor.value(); + else + sor.value(); // [[unsafe]] + + sor.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target() { + if (auto sor = Make<STATUSOR_INT>(); sor.ok()) + sor.value(); + else + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, JoinSafeSafe) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor, bool b) { + if (sor.ok()) { + if (b) + sor.value(); + else + sor.value(); + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, JoinUnsafeUnsafe) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor, bool b) { + if (b) + sor.value(); // [[unsafe]] + else + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, InversedIfThenElse) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (!sor.ok()) + sor.value(); // [[unsafe]] + else + sor.value(); + + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, DoubleInversedIfThenElse) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (!!sor.ok()) + sor.value(); + else + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, TripleInversedIfThenElse) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (!!!sor.ok()) + sor.value(); // [[unsafe]] + else + sor.value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_LhsAndRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (x.ok() && y.ok()) { + x.value(); + + y.value(); + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_NotLhsAndRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!x.ok() && y.ok()) { + y.value(); + + x.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_LhsAndNotRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (x.ok() && !y.ok()) { + x.value(); + + y.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_NotLhsAndNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!x.ok() && !y.ok()) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_LhsAndRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(x.ok() && y.ok())) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); + + y.value(); + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_NotLhsAndRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(!x.ok() && y.ok())) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + y.value(); + + x.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_LhsAndNotRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(x.ok() && !y.ok())) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_NotLhsAndNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(!x.ok() && !y.ok())) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_LhsOrRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (x.ok() || y.ok()) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_NotLhsOrRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!x.ok() || y.ok()) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_LhsOrNotRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (x.ok() || !y.ok()) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + y.value(); + + x.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_NotLhsOrNotRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!x.ok() || !y.ok()) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); + + y.value(); + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_LhsOrRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(x.ok() || y.ok())) { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_NotLhsOrRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(!x.ok() || y.ok())) { + x.value(); + + y.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_LhsOrNotRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(x.ok() || !y.ok())) { + y.value(); + + x.value(); // [[unsafe]] + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, IfThenElse_Not_NotLhsOrNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!(!x.ok() || !y.ok())) { + x.value(); + + y.value(); + } else { + x.value(); // [[unsafe]] + + y.value(); // [[unsafe]] + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, TerminatingIfThenBranch) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (!sor.ok()) return; + + sor.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (sor.ok()) return; + + sor.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + if (!x.ok() || !y.ok()) return; + + x.value(); + + y.value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, TerminatingIfElseBranch) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (sor.ok()) { + } else { + return; + } + + sor.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + if (!sor.ok()) { + } else { + return; + } + + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, TerminatingIfThenBranchInLoop) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (Make<bool>()) { + if (!sor.ok()) continue; + + sor.value(); + } + + sor.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (Make<bool>()) { + if (!sor.ok()) break; + + sor.value(); + } + + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, TernaryConditionalOperator) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + sor.ok() ? sor.value() : 21; + + sor.ok() ? 21 : sor.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + !sor.ok() ? 21 : sor.value(); + + !sor.ok() ? sor.value() : 21; // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor1, STATUSOR_INT sor2) { + !((__builtin_expect(false || (!(sor1.ok() && sor2.ok())), false))) + ? (void)0 + : (void)1; + do { + sor1.value(); // [[unsafe]] + sor2.value(); // [[unsafe]] + } while (true); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (Make<bool>()) sor.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (sor.ok()) sor.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (!sor.ok()) sor.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (!!sor.ok()) sor.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (!!!sor.ok()) sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_LhsAndRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (x.ok() && y.ok()) { + x.value(); + + y.value(); + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_NotLhsAndRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() && y.ok()) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() && y.ok()) y.value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_LhsAndNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (x.ok() && !y.ok()) x.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (x.ok() && !y.ok()) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_NotLhsAndNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() && !y.ok()) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() && !y.ok()) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_LhsAndRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() && y.ok())) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() && y.ok())) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_NotLhsAndRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(!x.ok() && y.ok())) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(!x.ok() && y.ok())) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_LhsAndNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() && !y.ok())) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() && !y.ok())) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_NotLhsAndNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(!x.ok() && !y.ok())) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(!x.ok() && !y.ok())) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_LhsOrRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (x.ok() || y.ok()) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (x.ok() || y.ok()) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_NotLhsOrRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() || y.ok()) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() || y.ok()) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_LhsOrNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (x.ok() || !y.ok()) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (x.ok() || !y.ok()) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_NotLhsOrNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() || !y.ok()) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!x.ok() || !y.ok()) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_LhsOrRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() || y.ok())) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() || y.ok())) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_NotLhsOrRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(!x.ok() || y.ok())) x.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(!x.ok() || y.ok())) y.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_LhsOrNotRhs) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() || !y.ok())) x.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(x.ok() || !y.ok())) y.value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_Not_NotLhsOrNotRhs) { + ExpectDiagnosticsFor( + R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT x, STATUSOR_INT y) { + while (!(!x.ok() || !y.ok())) { + x.value(); + + y.value(); + } + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_AccessAfterStmt) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (sor.ok()) { + } + + sor.value(); // [[unsafe]] + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (!sor.ok()) { + } + + sor.value(); + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_TerminatingBranch_Return) { + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (!sor.ok()) return; + + sor.value(); + } + )cc"); + ExpectDiagnosticsFor(R"cc( +#include "unchecked_statusor_use_test_defs.h" + + void target(STATUSOR_INT sor) { + while (sor.ok()) return; + + sor.value(); // [[unsafe]] + } + )cc"); +} + +TEST_P(UncheckedStatusOrAccessModelTest, While_TerminatingBranch_Continue) { ---------------- fmayer wrote:
good catch thanks https://github.com/llvm/llvm-project/pull/162932 _______________________________________________ llvm-branch-commits mailing list [email protected] https://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-branch-commits
