15#define DEBUG_TYPE "dataflow"
23 auto DstDecl = DstType->getAsCXXRecordDecl();
25 bool compatibleTypes =
27 (SrcDecl && DstDecl && SrcDecl->isDerivedFrom(DstDecl));
28 (void)compatibleTypes;
31 if (!compatibleTypes) {
32 llvm::dbgs() <<
"Source type " << Src.
getType() <<
"\n";
33 llvm::dbgs() <<
"Destination type " << Dst.
getType() <<
"\n";
36 assert(compatibleTypes);
38 for (
auto [Field, DstFieldLoc] : Dst.
children()) {
41 assert(Field->getType()->isReferenceType() ||
42 (SrcFieldLoc !=
nullptr && DstFieldLoc !=
nullptr));
44 if (Field->getType()->isRecordType()) {
45 copyRecord(cast<RecordStorageLocation>(*SrcFieldLoc),
46 cast<RecordStorageLocation>(*DstFieldLoc),
Env);
47 }
else if (Field->getType()->isReferenceType()) {
50 if (
Value *Val =
Env.getValue(*SrcFieldLoc))
51 Env.setValue(*DstFieldLoc, *Val);
53 Env.clearValue(*DstFieldLoc);
58 if (SynthFieldLoc->getType()->isRecordType()) {
59 copyRecord(*cast<RecordStorageLocation>(SynthFieldLoc),
62 if (
Value *Val =
Env.getValue(*SynthFieldLoc))
69 RecordValue *SrcVal = cast_or_null<RecordValue>(
Env.getValue(Src));
70 RecordValue *DstVal = cast_or_null<RecordValue>(
Env.getValue(Dst));
73 Env.setValue(Dst, *DstVal);
75 if (SrcVal ==
nullptr)
91 llvm::dbgs() <<
"Loc1 type " << Loc1.getType() <<
"\n";
92 llvm::dbgs() <<
"Loc2 type " << Loc2.getType() <<
"\n";
98 for (
auto [Field, FieldLoc1] : Loc1.
children()) {
101 assert(Field->getType()->isReferenceType() ||
102 (FieldLoc1 !=
nullptr && FieldLoc2 !=
nullptr));
104 if (Field->getType()->isRecordType()) {
105 if (!
recordsEqual(cast<RecordStorageLocation>(*FieldLoc1), Env1,
106 cast<RecordStorageLocation>(*FieldLoc2), Env2))
108 }
else if (Field->getType()->isReferenceType()) {
109 if (FieldLoc1 != FieldLoc2)
117 if (SynthFieldLoc1->getType()->isRecordType()) {
119 *cast<RecordStorageLocation>(SynthFieldLoc1), Env1,
122 }
else if (Env1.
getValue(*SynthFieldLoc1) !=
128 llvm::StringMap<Value *> Props1, Props2;
131 for (
const auto &[Name,
Value] : Val1->properties())
132 Props1[Name] =
Value;
134 for (
const auto &[Name,
Value] : Val2->properties())
135 Props2[Name] =
Value;
137 if (Props1.size() != Props2.size())
140 for (
const auto &[Name,
Value] : Props1) {
141 auto It = Props2.find(Name);
142 if (It == Props2.end())
144 if (
Value != It->second)
QualType getCanonicalType() const
QualType getUnqualifiedType() const
Retrieve the unqualified variant of the given type, removing as little sugar as possible.
CXXRecordDecl * getAsCXXRecordDecl() const
Retrieves the CXXRecordDecl that this type refers to, either because the type is a RecordType or beca...
Holds the state of the program (store and heap) at a given program point.
Value * getValue(const StorageLocation &Loc) const
Returns the value assigned to Loc in the environment or null if Loc isn't assigned a value in the env...
A storage location for a record (struct, class, or union).
llvm::iterator_range< SyntheticFieldMap::const_iterator > synthetic_fields() const
StorageLocation * getChild(const ValueDecl &D) const
Returns the child storage location for D.
void setChild(const ValueDecl &D, StorageLocation *Loc)
Changes the child storage location for a field D of reference type.
StorageLocation & getSyntheticField(llvm::StringRef Name) const
Returns the storage location for the synthetic field Name.
llvm::iterator_range< FieldToLoc::const_iterator > children() const
Models a value of struct or class type.
Base class for elements of the local variable store and of the heap.
Base class for all values computed by abstract interpretation.
void setProperty(llvm::StringRef Name, Value &Val)
Assigns Val as the value of the synthetic property with the given Name.
llvm::iterator_range< llvm::StringMap< Value * >::const_iterator > properties() const
bool recordsEqual(const RecordStorageLocation &Loc1, const Environment &Env1, const RecordStorageLocation &Loc2, const Environment &Env2)
Returns whether the records Loc1 and Loc2 are equal.
void copyRecord(RecordStorageLocation &Src, RecordStorageLocation &Dst, Environment &Env)
Copies a record (struct, class, or union) from Src to Dst.