[clang] [clang][dataflow] Fix crash on base-to-derived cast of unmodeled pointer value. (PR #179060)
Artem Dergachev via cfe-commits
cfe-commits at lists.llvm.org
Wed Feb 4 21:09:11 PST 2026
haoNoQ wrote:
> (As usual, `BinaryConditionalOperator` comes to mind as the example of an expression that loads its sub-expressions multiple times. Let me see if I can break it.)
Yeah, for completeness, I guess it may theoretically be a problem in a test such as this one, in the context of `TypeErasedDataflowAnalysisTest.cpp` where there's this little `is_null` analysis:
```
TEST_F(TopTest, CastNeedsAValue) {
std::string Code = R"(
struct Base {};
struct Derived: Base {};
__attribute__((noreturn)) Derived *fail();
Base *unknown();
void target() {
Derived *DPtr = static_cast<Derived *>(unknown()) ?: fail();
// [[p]]
}
)";
runDataflow(
Code,
[](const llvm::StringMap<DataflowAnalysisState<NoopLattice>> &Results,
const AnalysisOutputs &AO) {
AO.ACFG.getCFG().dump(AO.ASTCtx.getLangOpts(), true);
ASSERT_THAT(Results.keys(), UnorderedElementsAre("p"));
const Environment &Env = getEnvironmentAtAnnotation(Results, "p");
Env.dump();
const ValueDecl *DPtrDecl = findValueDecl(AO.ASTCtx, "DPtr");
ASSERT_THAT(DPtrDecl, NotNull());
EXPECT_EQ(Env.getValue(*DPtrDecl)->getProperty("is_null"),
&Env.getBoolLiteralValue(false));
});
}
```
- where we wouldn't notice that `DPtr2` is non-null unless we eagerly assign a value to the static cast expression, because we'll be looking up the value of the operator `?:` from the next CFG block, which would be unconditionally equal to the condition value, which we've already forgot.
But all of this *would* only be a problem if we model the GNU binary form of operator `?:` in the first place. And it's not like we even model null checks. And even then, that's completely ridiculous code.
So, yeah, IIUC I can just skip the value. I'll get back to this tomorrow.
https://github.com/llvm/llvm-project/pull/179060
More information about the cfe-commits
mailing list