llvm.org GIT mirror llvm / a75318a
[LVI] Constant-propagate a zero extension of the switch condition value through case edges Summary: (This is a second attempt as https://reviews.llvm.org/D34822 was reverted.) LazyValueInfo currently computes the constant value of the switch condition through case edges, which allows the constant value to be propagated through the case edges. But we have seen a case where a zero-extended value of the switch condition is used past case edges for which the constant propagation doesn't occur. This patch adds a small logic to handle such a case in getEdgeValueLocal(). This is motivated by the Python 2.7 eval loop in PyEval_EvalFrameEx() where the lack of the constant propagation causes longer live ranges and more spill code than necessary. With this patch, we see that the code size of PyEval_EvalFrameEx() decreases by ~5.4% and a performance test improves by ~4.6%. Reviewers: sanjoy Reviewed By: sanjoy Subscribers: llvm-commits Differential Revision: https://reviews.llvm.org/D36247 git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@309986 91177308-0d34-0410-b5e6-96231b3b80d8 Hiroshi Yamauchi 2 years ago
2 changed file(s) with 255 addition(s) and 6 deletion(s). Raw diff Collapse all Expand all
1616 #include "llvm/ADT/STLExtras.h"
1717 #include "llvm/Analysis/AssumptionCache.h"
1818 #include "llvm/Analysis/ConstantFolding.h"
19 #include "llvm/Analysis/InstructionSimplify.h"
1920 #include "llvm/Analysis/TargetLibraryInfo.h"
2021 #include "llvm/Analysis/ValueTracking.h"
2122 #include "llvm/IR/AssemblyAnnotationWriter.h"
145146 assert(isConstantRange() &&
146147 "Cannot get the constant-range of a non-constant-range!");
147148 return Range;
149 }
150
151 Optional asConstantInteger() const {
152 if (isConstant() && isa(Val)) {
153 return Val->getUniqueInteger();
154 } else if (isConstantRange() && Range.isSingleElement()) {
155 return *Range.getSingleElement();
156 }
157 return None;
148158 }
149159
150160 private:
13541364 return getValueFromCondition(Val, Cond, isTrueDest, Visited);
13551365 }
13561366
1367 // Return true if Usr has Op as an operand, otherwise false.
1368 static bool usesOperand(User *Usr, Value *Op) {
1369 return find(Usr->operands(), Op) != Usr->op_end();
1370 }
1371
1372 // Check if Val can be simplified to an integer constant when the value of one
1373 // of its operands Op is an integer constant OpConstVal. If so, return it as an
1374 // lattice value range with a single element or otherwise return an overdefined
1375 // lattice value.
1376 static LVILatticeVal constantFoldUser(Value *Val, Value *Op,
1377 const APInt &OpConstVal,
1378 const DataLayout &DL) {
1379 Constant* OpConst = Constant::getIntegerValue(Op->getType(), OpConstVal);
1380 // Check if Val can be simplified to a constant.
1381 if (auto *CI = dyn_cast(Val)) {
1382 assert(CI->getOperand(0) == Op && "Operand 0 isn't Op");
1383 if (auto *C = dyn_cast_or_null(
1384 SimplifyCastInst(CI->getOpcode(), OpConst,
1385 CI->getDestTy(), DL))) {
1386 return LVILatticeVal::getRange(ConstantRange(C->getUniqueInteger()));
1387 }
1388 } else if (auto *BO = dyn_cast(Val)) {
1389 bool Op0Match = BO->getOperand(0) == Op;
1390 bool Op1Match = BO->getOperand(1) == Op;
1391 assert((Op0Match || Op1Match) &&
1392 "Operand 0 nor Operand 1 isn't a match");
1393 Value *LHS = Op0Match ? OpConst : BO->getOperand(0);
1394 Value *RHS = Op1Match ? OpConst : BO->getOperand(1);
1395 if (auto *C = dyn_cast_or_null(
1396 SimplifyBinOp(BO->getOpcode(), LHS, RHS, DL))) {
1397 return LVILatticeVal::getRange(ConstantRange(C->getUniqueInteger()));
1398 }
1399 }
1400 return LVILatticeVal::getOverdefined();
1401 }
1402
13571403 /// \brief Compute the value of Val on the edge BBFrom -> BBTo. Returns false if
13581404 /// Val is not constrained on the edge. Result is unspecified if return value
13591405 /// is false.
13691415 bool isTrueDest = BI->getSuccessor(0) == BBTo;
13701416 assert(BI->getSuccessor(!isTrueDest) == BBTo &&
13711417 "BBTo isn't a successor of BBFrom");
1418 Value *Condition = BI->getCondition();
13721419
13731420 // If V is the condition of the branch itself, then we know exactly what
13741421 // it is.
1375 if (BI->getCondition() == Val) {
1422 if (Condition == Val) {
13761423 Result = LVILatticeVal::get(ConstantInt::get(
13771424 Type::getInt1Ty(Val->getContext()), isTrueDest));
13781425 return true;
13801427
13811428 // If the condition of the branch is an equality comparison, we may be
13821429 // able to infer the value.
1383 Result = getValueFromCondition(Val, BI->getCondition(), isTrueDest);
1430 Result = getValueFromCondition(Val, Condition, isTrueDest);
1431 if (!Result.isOverdefined())
1432 return true;
1433
1434 if (User *Usr = dyn_cast(Val)) {
1435 assert(Result.isOverdefined() && "Result isn't overdefined");
1436 if (isa(Val->getType())) {
1437 const DataLayout &DL = BBTo->getModule()->getDataLayout();
1438 if (usesOperand(Usr, Condition)) {
1439 // If Val has Condition as an operand and Val can be folded into a
1440 // constant with either Condition == true or Condition == false,
1441 // propagate the constant.
1442 // eg.
1443 // ; %Val is true on the edge to %then.
1444 // %Val = and i1 %Condition, true.
1445 // br %Condition, label %then, label %else
1446 APInt ConditionVal(1, isTrueDest ? 1 : 0);
1447 Result = constantFoldUser(Val, Condition, ConditionVal, DL);
1448 } else {
1449 // If one of Val's operand has an inferred value, we may be able to
1450 // infer the value of Val.
1451 // eg.
1452 // ; %Val is 94 on the edge to %then.
1453 // %Val = add i8 %Op, 1
1454 // %Condition = icmp eq i8 %Op, 93
1455 // br i1 %Condition, label %then, label %else
1456 for (unsigned i = 0; i < Usr->getNumOperands(); ++i) {
1457 Value *Op = Usr->getOperand(i);
1458 LVILatticeVal OpLatticeVal =
1459 getValueFromCondition(Op, Condition, isTrueDest);
1460 if (Optional OpConst = OpLatticeVal.asConstantInteger()) {
1461 Result = constantFoldUser(Val, Op, OpConst.getValue(), DL);
1462 break;
1463 }
1464 }
1465 }
1466 }
1467 }
13841468 if (!Result.isOverdefined())
13851469 return true;
13861470 }
13891473 // If the edge was formed by a switch on the value, then we may know exactly
13901474 // what it is.
13911475 if (SwitchInst *SI = dyn_cast(BBFrom->getTerminator())) {
1392 if (SI->getCondition() != Val)
1476 Value *Condition = SI->getCondition();
1477 if (!isa(Val->getType()))
13931478 return false;
1479 bool ValUsesCondition = false;
1480 if (Condition != Val) {
1481 // Check if Val has Condition as an operand.
1482 if (User *Usr = dyn_cast(Val))
1483 ValUsesCondition = usesOperand(Usr, Condition);
1484 if (!ValUsesCondition)
1485 return false;
1486 }
1487 assert((Condition == Val || ValUsesCondition) &&
1488 "Condition != Val nor Val doesn't use Condition");
13941489
13951490 bool DefaultCase = SI->getDefaultDest() == BBTo;
13961491 unsigned BitWidth = Val->getType()->getIntegerBitWidth();
13971492 ConstantRange EdgesVals(BitWidth, DefaultCase/*isFullSet*/);
13981493
13991494 for (auto Case : SI->cases()) {
1400 ConstantRange EdgeVal(Case.getCaseValue()->getValue());
1495 APInt CaseValue = Case.getCaseValue()->getValue();
1496 ConstantRange EdgeVal(CaseValue);
1497 if (ValUsesCondition) {
1498 const DataLayout &DL = BBTo->getModule()->getDataLayout();
1499 LVILatticeVal EdgeLatticeVal =
1500 constantFoldUser(Val, Condition, CaseValue, DL);
1501 if (EdgeLatticeVal.isOverdefined())
1502 return false;
1503 EdgeVal = EdgeLatticeVal.getConstantRange();
1504 }
14011505 if (DefaultCase) {
14021506 // It is possible that the default destination is the destination of
1403 // some cases. There is no need to perform difference for those cases.
1404 if (Case.getCaseSuccessor() != BBTo)
1507 // some cases. We cannot perform difference for those cases.
1508 // We know Condition != CaseValue in BBTo. In some cases we can use
1509 // this to infer Val == f(Condition) is != f(CaseValue). For now, we
1510 // only do this when f is identity (i.e. Val == Condition), but we
1511 // should be able to do this for any injective f.
1512 if (Case.getCaseSuccessor() != BBTo && Condition == Val)
14051513 EdgesVals = EdgesVals.difference(EdgeVal);
14061514 } else if (Case.getCaseSuccessor() == BBTo)
14071515 EdgesVals = EdgesVals.unionWith(EdgeVal);
461461 else:
462462 ret i1 false
463463 }
464
465 define i32 @test16(i8 %a) {
466 entry:
467 %b = zext i8 %a to i32
468 br label %dispatch
469
470 dispatch:
471 %cmp = icmp eq i8 %a, 93
472 br i1 %cmp, label %target93, label %dispatch
473
474 ; CHECK-LABEL: @test16(
475 ; CHECK: target93:
476 ; CHECK-NEXT: ret i32 93
477 target93:
478 ret i32 %b
479 }
480
481 define i32 @test16_i1(i1 %a) {
482 entry:
483 %b = zext i1 %a to i32
484 br label %dispatch
485
486 dispatch:
487 br i1 %a, label %true, label %dispatch
488
489 ; CHECK-LABEL: @test16_i1(
490 ; CHECK: true:
491 ; CHECK-NEXT: ret i32 1
492 true:
493 ret i32 %b
494 }
495
496 define i8 @test17(i8 %a) {
497 entry:
498 %c = add i8 %a, 3
499 br label %dispatch
500
501 dispatch:
502 %cmp = icmp eq i8 %a, 93
503 br i1 %cmp, label %target93, label %dispatch
504
505 ; CHECK-LABEL: @test17(
506 ; CHECK: target93:
507 ; CHECK-NEXT: ret i8 96
508 target93:
509 ret i8 %c
510 }
511
512 define i8 @test17_2(i8 %a) {
513 entry:
514 %c = add i8 %a, %a
515 br label %dispatch
516
517 dispatch:
518 %cmp = icmp eq i8 %a, 93
519 br i1 %cmp, label %target93, label %dispatch
520
521 ; CHECK-LABEL: @test17_2(
522 ; CHECK: target93:
523 ; CHECK-NEXT: ret i8 -70
524 target93:
525 ret i8 %c
526 }
527
528 define i1 @test17_i1(i1 %a) {
529 entry:
530 %c = and i1 %a, true
531 br label %dispatch
532
533 dispatch:
534 br i1 %a, label %true, label %dispatch
535
536 ; CHECK-LABEL: @test17_i1(
537 ; CHECK: true:
538 ; CHECK-NEXT: ret i1 true
539 true:
540 ret i1 %c
541 }
542
543 define i32 @test18(i8 %a) {
544 entry:
545 %b = zext i8 %a to i32
546 br label %dispatch
547
548 dispatch:
549 switch i8 %a, label %dispatch [
550 i8 93, label %target93
551 i8 -111, label %dispatch
552 ]
553
554 ; CHECK-LABEL: @test18(
555 ; CHECK: target93:
556 ; CHECK-NEXT: ret i32 93
557 target93:
558 ret i32 %b
559 }
560
561 define i8 @test19(i8 %a) {
562 entry:
563 %c = add i8 %a, 3
564 br label %dispatch
565
566 dispatch:
567 switch i8 %a, label %dispatch [
568 i8 93, label %target93
569 i8 -111, label %dispatch
570 ]
571
572 ; CHECK-LABEL: @test19(
573 ; CHECK: target93:
574 ; CHECK-NEXT: ret i8 96
575 target93:
576 ret i8 %c
577 }
578
579 define i1 @test20(i64 %a) {
580 entry:
581 %b = and i64 %a, 7
582 br label %dispatch
583
584 dispatch:
585 switch i64 %a, label %default [
586 i64 0, label %exit2
587 i64 -2147483647, label %exit2
588 ]
589
590 default:
591 %c = icmp eq i64 %b, 0
592 br label %exit
593
594 exit:
595 ; Negative test. Shouldn't be incorrectly optimized to "ret i1 false".
596 ; CHECK-LABEL: @test20(
597 ; CHECK: exit:
598 ; CHECK-NOT: ret i1 false
599 ; CHECK: exit2:
600 ret i1 %c
601
602 exit2:
603 ret i1 false
604 }