//===- ConstantProp.cpp - Code to perform Simple Constant Propagation -----===//
//
// 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
//
//===----------------------------------------------------------------------===//
//
// This file implements constant propagation and merging:
//
// Specifically, this:
//   * Converts instructions like "add int 1, 2" into 3
//
// Notice that:
//   * This pass has a habit of making definitions be dead.  It is a good idea
//     to run a DIE pass sometime after running this pass.
//
//===----------------------------------------------------------------------===//

#include "llvm/ADT/SmallPtrSet.h"
#include "llvm/ADT/SmallVector.h"
#include "llvm/ADT/Statistic.h"
#include "llvm/Analysis/ConstantFolding.h"
#include "llvm/Analysis/TargetLibraryInfo.h"
#include "llvm/IR/Constant.h"
#include "llvm/IR/InstIterator.h"
#include "llvm/IR/Instruction.h"
#include "llvm/Pass.h"
#include "llvm/Support/DebugCounter.h"
#include "llvm/Transforms/Scalar.h"
#include "llvm/Transforms/Utils/Local.h"
using namespace llvm;

#define DEBUG_TYPE "constprop"

STATISTIC(NumInstKilled, "Number of instructions killed");
DEBUG_COUNTER(CPCounter, "constprop-transform",
              "Controls which instructions are killed");

namespace {
  struct ConstantPropagation : public FunctionPass {
    static char ID; // Pass identification, replacement for typeid
    ConstantPropagation() : FunctionPass(ID) {
      initializeConstantPropagationPass(*PassRegistry::getPassRegistry());
    }

    bool runOnFunction(Function &F) override;

    void getAnalysisUsage(AnalysisUsage &AU) const override {
      AU.setPreservesCFG();
      AU.addRequired<TargetLibraryInfoWrapperPass>();
    }
  };
}

char ConstantPropagation::ID = 0;
INITIALIZE_PASS_BEGIN(ConstantPropagation, "constprop",
                "Simple constant propagation", false, false)
INITIALIZE_PASS_DEPENDENCY(TargetLibraryInfoWrapperPass)
INITIALIZE_PASS_END(ConstantPropagation, "constprop",
                "Simple constant propagation", false, false)

FunctionPass *llvm::createConstantPropagationPass() {
  return new ConstantPropagation();
}

bool ConstantPropagation::runOnFunction(Function &F) {
  if (skipFunction(F))
    return false;

  // Initialize the worklist to all of the instructions ready to process...
  SmallPtrSet<Instruction *, 16> WorkList;
  // The SmallVector of WorkList ensures that we do iteration at stable order.
  // We use two containers rather than one SetVector, since remove is
  // linear-time, and we don't care enough to remove from Vec.
  SmallVector<Instruction *, 16> WorkListVec;
  for (Instruction &I : instructions(&F)) {
    WorkList.insert(&I);
    WorkListVec.push_back(&I);
  }

  bool Changed = false;
  const DataLayout &DL = F.getParent()->getDataLayout();
  TargetLibraryInfo *TLI =
      &getAnalysis<TargetLibraryInfoWrapperPass>().getTLI(F);

  while (!WorkList.empty()) {
    SmallVector<Instruction*, 16> NewWorkListVec;
    for (auto *I : WorkListVec) {
      WorkList.erase(I); // Remove element from the worklist...

      if (!I->use_empty()) // Don't muck with dead instructions...
        if (Constant *C = ConstantFoldInstruction(I, DL, TLI)) {
          if (!DebugCounter::shouldExecute(CPCounter))
            continue;

          // Add all of the users of this instruction to the worklist, they might
          // be constant propagatable now...
          for (User *U : I->users()) {
            // If user not in the set, then add it to the vector.
            if (WorkList.insert(cast<Instruction>(U)).second)
              NewWorkListVec.push_back(cast<Instruction>(U));
          }

          // Replace all of the uses of a variable with uses of the constant.
          I->replaceAllUsesWith(C);

          if (isInstructionTriviallyDead(I, TLI)) {
            I->eraseFromParent();
            ++NumInstKilled;
          }

          // We made a change to the function...
          Changed = true;
        }
    }
    WorkListVec = std::move(NewWorkListVec);
  }
  return Changed;
}
