1//===- CanonicalizeAliases.cpp - ThinLTO Support: Canonicalize Aliases ----===// 2// 3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4// See https://llvm.org/LICENSE.txt for license information. 5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6// 7//===----------------------------------------------------------------------===// 8// 9// Currently this file implements partial alias canonicalization, to 10// flatten chains of aliases (also done by GlobalOpt, but not on for 11// O0 compiles). E.g. 12// @a = alias i8, i8 *@b 13// @b = alias i8, i8 *@g 14// 15// will be converted to: 16// @a = alias i8, i8 *@g <-- @a is now an alias to base object @g 17// @b = alias i8, i8 *@g 18// 19// Eventually this file will implement full alias canonicalization, so that 20// all aliasees are private anonymous values. E.g. 21// @a = alias i8, i8 *@g 22// @g = global i8 0 23// 24// will be converted to: 25// @0 = private global 26// @a = alias i8, i8* @0 27// @g = alias i8, i8* @0 28// 29// This simplifies optimization and ThinLTO linking of the original symbols. 30//===----------------------------------------------------------------------===// 31 32#include "llvm/Transforms/Utils/CanonicalizeAliases.h" 33#include "llvm/IR/Constants.h" 34#include "llvm/InitializePasses.h" 35#include "llvm/Pass.h" 36 37using namespace llvm; 38 39namespace { 40 41static Constant *canonicalizeAlias(Constant *C, bool &Changed) { 42 if (auto *GA = dyn_cast<GlobalAlias>(C)) { 43 auto *NewAliasee = canonicalizeAlias(GA->getAliasee(), Changed); 44 if (NewAliasee != GA->getAliasee()) { 45 GA->setAliasee(NewAliasee); 46 Changed = true; 47 } 48 return NewAliasee; 49 } 50 51 auto *CE = dyn_cast<ConstantExpr>(C); 52 if (!CE) 53 return C; 54 55 std::vector<Constant *> Ops; 56 for (Use &U : CE->operands()) 57 Ops.push_back(canonicalizeAlias(cast<Constant>(U), Changed)); 58 return CE->getWithOperands(Ops); 59} 60 61/// Convert aliases to canonical form. 62static bool canonicalizeAliases(Module &M) { 63 bool Changed = false; 64 for (auto &GA : M.aliases()) 65 canonicalizeAlias(&GA, Changed); 66 return Changed; 67} 68} // anonymous namespace 69 70PreservedAnalyses CanonicalizeAliasesPass::run(Module &M, 71 ModuleAnalysisManager &AM) { 72 if (!canonicalizeAliases(M)) 73 return PreservedAnalyses::all(); 74 75 return PreservedAnalyses::none(); 76} 77