@@ -10889,64 +10889,104 @@ struct AAPotentialValuesFloating : AAPotentialValuesImpl {
10889
10889
10890
10890
// Simplify the operands first.
10891
10891
bool UsedAssumedInformation = false ;
10892
- const auto &SimplifiedLHS = A.getAssumedSimplified (
10893
- IRPosition::value (*LHS, getCallBaseContext ()), *this ,
10894
- UsedAssumedInformation, AA::Intraprocedural);
10895
- if (!SimplifiedLHS.has_value ())
10892
+ SmallVector<AA::ValueAndContext> LHSValues, RHSValues;
10893
+ auto GetSimplifiedValues = [&](Value &V,
10894
+ SmallVector<AA::ValueAndContext> &Values) {
10895
+ if (!A.getAssumedSimplifiedValues (
10896
+ IRPosition::value (V, getCallBaseContext ()), this , Values,
10897
+ AA::Intraprocedural, UsedAssumedInformation)) {
10898
+ Values.clear ();
10899
+ Values.push_back (AA::ValueAndContext{V, II.I .getCtxI ()});
10900
+ }
10901
+ return Values.empty ();
10902
+ };
10903
+ if (GetSimplifiedValues (*LHS, LHSValues))
10896
10904
return true ;
10897
- if (!*SimplifiedLHS)
10898
- return false ;
10899
- LHS = *SimplifiedLHS;
10900
-
10901
- const auto &SimplifiedRHS = A.getAssumedSimplified (
10902
- IRPosition::value (*RHS, getCallBaseContext ()), *this ,
10903
- UsedAssumedInformation, AA::Intraprocedural);
10904
- if (!SimplifiedRHS.has_value ())
10905
+ if (GetSimplifiedValues (*RHS, RHSValues))
10905
10906
return true ;
10906
- if (!*SimplifiedRHS)
10907
- return false ;
10908
- RHS = *SimplifiedRHS;
10909
10907
10910
10908
LLVMContext &Ctx = LHS->getContext ();
10911
- // Handle the trivial case first in which we don't even need to think about
10912
- // null or non-null.
10913
- if (LHS == RHS &&
10914
- (CmpInst::isTrueWhenEqual (Pred) || CmpInst::isFalseWhenEqual (Pred))) {
10915
- Constant *NewV = ConstantInt::get (Type::getInt1Ty (Ctx),
10916
- CmpInst::isTrueWhenEqual (Pred));
10917
- addValue (A, getState (), *NewV, /* CtxI */ nullptr , II.S ,
10918
- getAnchorScope ());
10919
- return true ;
10920
- }
10921
10909
10922
- // From now on we only handle equalities (==, !=).
10923
- if (!CmpInst::isEquality (Pred))
10924
- return false ;
10910
+ InformationCache &InfoCache = A.getInfoCache ();
10911
+ Instruction *CmpI = dyn_cast<Instruction>(&Cmp);
10912
+ Function *F = CmpI ? CmpI->getFunction () : nullptr ;
10913
+ const auto *DT =
10914
+ F ? InfoCache.getAnalysisResultForFunction <DominatorTreeAnalysis>(*F)
10915
+ : nullptr ;
10916
+ const auto *TLI =
10917
+ F ? A.getInfoCache ().getTargetLibraryInfoForFunction (*F) : nullptr ;
10918
+ auto *AC =
10919
+ F ? InfoCache.getAnalysisResultForFunction <AssumptionAnalysis>(*F)
10920
+ : nullptr ;
10925
10921
10926
- bool LHSIsNull = isa<ConstantPointerNull>(LHS);
10927
- bool RHSIsNull = isa<ConstantPointerNull>(RHS);
10928
- if (!LHSIsNull && !RHSIsNull)
10929
- return false ;
10922
+ const DataLayout &DL = A.getDataLayout ();
10923
+ SimplifyQuery Q (DL, TLI, DT, AC, CmpI);
10930
10924
10931
- // Left is the nullptr ==/!= non-nullptr case. We'll use AANonNull on the
10932
- // non-nullptr operand and if we assume it's non-null we can conclude the
10933
- // result of the comparison.
10934
- assert ((LHSIsNull || RHSIsNull) &&
10935
- " Expected nullptr versus non-nullptr comparison at this point" );
10925
+ auto CheckPair = [&](Value &LHSV, Value &RHSV) {
10926
+ if (isa<UndefValue>(LHSV) || isa<UndefValue>(RHSV)) {
10927
+ addValue (A, getState (), *UndefValue::get (Cmp.getType ()),
10928
+ /* CtxI */ nullptr , II.S , getAnchorScope ());
10929
+ return true ;
10930
+ }
10936
10931
10937
- // The index is the operand that we assume is not null.
10938
- unsigned PtrIdx = LHSIsNull;
10939
- bool IsKnownNonNull;
10940
- bool IsAssumedNonNull = AA::hasAssumedIRAttr<Attribute::NonNull>(
10941
- A, this , IRPosition::value (*(PtrIdx ? RHS : LHS)), DepClassTy::REQUIRED,
10942
- IsKnownNonNull);
10943
- if (!IsAssumedNonNull)
10944
- return false ;
10932
+ // Handle the trivial case first in which we don't even need to think
10933
+ // about null or non-null.
10934
+ if (&LHSV == &RHSV &&
10935
+ (CmpInst::isTrueWhenEqual (Pred) || CmpInst::isFalseWhenEqual (Pred))) {
10936
+ Constant *NewV = ConstantInt::get (Type::getInt1Ty (Ctx),
10937
+ CmpInst::isTrueWhenEqual (Pred));
10938
+ addValue (A, getState (), *NewV, /* CtxI */ nullptr , II.S ,
10939
+ getAnchorScope ());
10940
+ return true ;
10941
+ }
10942
+
10943
+ auto *TypedLHS = AA::getWithType (LHSV, *LHS->getType ());
10944
+ auto *TypedRHS = AA::getWithType (RHSV, *RHS->getType ());
10945
+ if (TypedLHS && TypedRHS) {
10946
+ Value *NewV = simplifyCmpInst (Pred, TypedLHS, TypedRHS, Q);
10947
+ if (NewV && NewV != &Cmp) {
10948
+ addValue (A, getState (), *NewV, /* CtxI */ nullptr , II.S ,
10949
+ getAnchorScope ());
10950
+ return true ;
10951
+ }
10952
+ }
10953
+
10954
+ // From now on we only handle equalities (==, !=).
10955
+ if (!CmpInst::isEquality (Pred))
10956
+ return false ;
10945
10957
10946
- // The new value depends on the predicate, true for != and false for ==.
10947
- Constant *NewV =
10948
- ConstantInt::get (Type::getInt1Ty (Ctx), Pred == CmpInst::ICMP_NE);
10949
- addValue (A, getState (), *NewV, /* CtxI */ nullptr , II.S , getAnchorScope ());
10958
+ bool LHSIsNull = isa<ConstantPointerNull>(LHSV);
10959
+ bool RHSIsNull = isa<ConstantPointerNull>(RHSV);
10960
+ if (!LHSIsNull && !RHSIsNull)
10961
+ return false ;
10962
+
10963
+ // Left is the nullptr ==/!= non-nullptr case. We'll use AANonNull on the
10964
+ // non-nullptr operand and if we assume it's non-null we can conclude the
10965
+ // result of the comparison.
10966
+ assert ((LHSIsNull || RHSIsNull) &&
10967
+ " Expected nullptr versus non-nullptr comparison at this point" );
10968
+
10969
+ // The index is the operand that we assume is not null.
10970
+ unsigned PtrIdx = LHSIsNull;
10971
+ bool IsKnownNonNull;
10972
+ bool IsAssumedNonNull = AA::hasAssumedIRAttr<Attribute::NonNull>(
10973
+ A, this , IRPosition::value (*(PtrIdx ? &RHSV : &LHSV)),
10974
+ DepClassTy::REQUIRED, IsKnownNonNull);
10975
+ if (!IsAssumedNonNull)
10976
+ return false ;
10977
+
10978
+ // The new value depends on the predicate, true for != and false for ==.
10979
+ Constant *NewV =
10980
+ ConstantInt::get (Type::getInt1Ty (Ctx), Pred == CmpInst::ICMP_NE);
10981
+ addValue (A, getState (), *NewV, /* CtxI */ nullptr , II.S ,
10982
+ getAnchorScope ());
10983
+ return true ;
10984
+ };
10985
+
10986
+ for (auto &LHSValue : LHSValues)
10987
+ for (auto &RHSValue : RHSValues)
10988
+ if (!CheckPair (*LHSValue.getValue (), *RHSValue.getValue ()))
10989
+ return false ;
10950
10990
return true ;
10951
10991
}
10952
10992
@@ -11161,9 +11201,8 @@ struct AAPotentialValuesFloating : AAPotentialValuesImpl {
11161
11201
SmallVectorImpl<ItemInfo> &Worklist,
11162
11202
SmallMapVector<const Function *, LivenessInfo, 4 > &LivenessAAs) {
11163
11203
if (auto *CI = dyn_cast<CmpInst>(&I))
11164
- if (handleCmp (A, *CI, CI->getOperand (0 ), CI->getOperand (1 ),
11165
- CI->getPredicate (), II, Worklist))
11166
- return true ;
11204
+ return handleCmp (A, *CI, CI->getOperand (0 ), CI->getOperand (1 ),
11205
+ CI->getPredicate (), II, Worklist);
11167
11206
11168
11207
switch (I.getOpcode ()) {
11169
11208
case Instruction::Select:
0 commit comments