diff options
| author | Eugene Leviant <eleviant@accesssoftek.com> | 2018-11-23 10:54:51 +0000 | 
|---|---|---|
| committer | Eugene Leviant <eleviant@accesssoftek.com> | 2018-11-23 10:54:51 +0000 | 
| commit | 009d833a4e1ed1b7371a40ac3463e6e172b90923 (patch) | |
| tree | f6699e776df5d2db074b0f760bbc2d7ed2e0852a /llvm/lib/AsmParser | |
| parent | 7231009b78207b41175a15508f5d4bfd0cc46c9c (diff) | |
| download | bcm5719-llvm-009d833a4e1ed1b7371a40ac3463e6e172b90923.tar.gz bcm5719-llvm-009d833a4e1ed1b7371a40ac3463e6e172b90923.zip  | |
[ThinLTO] Assembly representation of ReadOnly attribute
Differential revision: https://reviews.llvm.org/D54754
llvm-svn: 347489
Diffstat (limited to 'llvm/lib/AsmParser')
| -rw-r--r-- | llvm/lib/AsmParser/LLLexer.cpp | 1 | ||||
| -rw-r--r-- | llvm/lib/AsmParser/LLParser.cpp | 92 | ||||
| -rw-r--r-- | llvm/lib/AsmParser/LLParser.h | 1 | ||||
| -rw-r--r-- | llvm/lib/AsmParser/LLToken.h | 1 | 
4 files changed, 72 insertions, 23 deletions
diff --git a/llvm/lib/AsmParser/LLLexer.cpp b/llvm/lib/AsmParser/LLLexer.cpp index 4f8ce3ddc7b..045214590d8 100644 --- a/llvm/lib/AsmParser/LLLexer.cpp +++ b/llvm/lib/AsmParser/LLLexer.cpp @@ -788,6 +788,7 @@ lltok::Kind LLLexer::LexIdentifier() {    KEYWORD(info);    KEYWORD(byte);    KEYWORD(bit); +  KEYWORD(varFlags);  #undef KEYWORD diff --git a/llvm/lib/AsmParser/LLParser.cpp b/llvm/lib/AsmParser/LLParser.cpp index c945a8ea95e..165d01dc8b4 100644 --- a/llvm/lib/AsmParser/LLParser.cpp +++ b/llvm/lib/AsmParser/LLParser.cpp @@ -7470,8 +7470,14 @@ bool LLParser::ParseArgs(std::vector<uint64_t> &Args) {    return false;  } -static ValueInfo EmptyVI = -    ValueInfo(false, (GlobalValueSummaryMapTy::value_type *)-8); +auto FwdVIRef = (GlobalValueSummaryMapTy::value_type *)-8; + +static void resolveFwdRef(ValueInfo *Fwd, ValueInfo &Resolved) { +  bool ReadOnly = Fwd->isReadOnly(); +  *Fwd = Resolved; +  if (ReadOnly) +    Fwd->setReadOnly(); +}  /// Stores the given Name/GUID and associated summary into the Index.  /// Also updates any forward references to the associated entry ID. @@ -7507,9 +7513,9 @@ void LLParser::AddGlobalValueToIndex(    auto FwdRefVIs = ForwardRefValueInfos.find(ID);    if (FwdRefVIs != ForwardRefValueInfos.end()) {      for (auto VIRef : FwdRefVIs->second) { -      assert(*VIRef.first == EmptyVI && +      assert(VIRef.first->getRef() == FwdVIRef &&               "Forward referenced ValueInfo expected to be empty"); -      *VIRef.first = VI; +      resolveFwdRef(VIRef.first, VI);      }      ForwardRefValueInfos.erase(FwdRefVIs);    } @@ -7699,11 +7705,14 @@ bool LLParser::ParseVariableSummary(std::string Name, GlobalValue::GUID GUID,    GlobalValueSummary::GVFlags GVFlags = GlobalValueSummary::GVFlags(        /*Linkage=*/GlobalValue::ExternalLinkage, /*NotEligibleToImport=*/false,        /*Live=*/false, /*IsLocal=*/false); +  GlobalVarSummary::GVarFlags GVarFlags(/*ReadOnly*/ false);    std::vector<ValueInfo> Refs;    if (ParseToken(lltok::colon, "expected ':' here") ||        ParseToken(lltok::lparen, "expected '(' here") ||        ParseModuleReference(ModulePath) || -      ParseToken(lltok::comma, "expected ',' here") || ParseGVFlags(GVFlags)) +      ParseToken(lltok::comma, "expected ',' here") || ParseGVFlags(GVFlags) || +      ParseToken(lltok::comma, "expected ',' here") || +      ParseGVarFlags(GVarFlags))      return true;    // Parse optional refs field @@ -7715,8 +7724,8 @@ bool LLParser::ParseVariableSummary(std::string Name, GlobalValue::GUID GUID,    if (ParseToken(lltok::rparen, "expected ')' here"))      return true; -  auto GS = llvm::make_unique<GlobalVarSummary>( -      GVFlags, GlobalVarSummary::GVarFlags(), std::move(Refs)); +  auto GS = +      llvm::make_unique<GlobalVarSummary>(GVFlags, GVarFlags, std::move(Refs));    GS->setModulePath(ModulePath); @@ -7761,7 +7770,7 @@ bool LLParser::ParseAliasSummary(std::string Name, GlobalValue::GUID GUID,    AS->setModulePath(ModulePath);    // Record forward reference if the aliasee is not parsed yet. -  if (AliaseeVI == EmptyVI) { +  if (AliaseeVI.getRef() == FwdVIRef) {      auto FwdRef = ForwardRefAliasees.insert(          std::make_pair(GVId, std::vector<std::pair<AliasSummary *, LocTy>>()));      FwdRef.first->second.push_back(std::make_pair(AS.get(), Loc)); @@ -7883,7 +7892,7 @@ bool LLParser::ParseOptionalCalls(std::vector<FunctionSummary::EdgeTy> &Calls) {      // Keep track of the Call array index needing a forward reference.      // We will save the location of the ValueInfo needing an update, but      // can only do so once the std::vector is finalized. -    if (VI == EmptyVI) +    if (VI.getRef() == FwdVIRef)        IdToIndexMap[GVId].push_back(std::make_pair(Calls.size(), Loc));      Calls.push_back(FunctionSummary::EdgeTy{VI, CalleeInfo(Hotness, RelBF)}); @@ -7895,7 +7904,7 @@ bool LLParser::ParseOptionalCalls(std::vector<FunctionSummary::EdgeTy> &Calls) {    // of any forward GV references that need updating later.    for (auto I : IdToIndexMap) {      for (auto P : I.second) { -      assert(Calls[P.first].first == EmptyVI && +      assert(Calls[P.first].first.getRef() == FwdVIRef &&               "Forward referenced ValueInfo expected to be empty");        auto FwdRef = ForwardRefValueInfos.insert(std::make_pair(            I.first, std::vector<std::pair<ValueInfo *, LocTy>>())); @@ -7946,28 +7955,42 @@ bool LLParser::ParseOptionalRefs(std::vector<ValueInfo> &Refs) {        ParseToken(lltok::lparen, "expected '(' in refs"))      return true; -  IdToIndexMapType IdToIndexMap; -  // Parse each ref edge -  do { +  struct ValueContext {      ValueInfo VI; -    LocTy Loc = Lex.getLoc();      unsigned GVId; -    if (ParseGVReference(VI, GVId)) +    LocTy Loc; +  }; +  std::vector<ValueContext> VContexts; +  // Parse each ref edge +  do { +    ValueContext VC; +    VC.Loc = Lex.getLoc(); +    if (ParseGVReference(VC.VI, VC.GVId))        return true; +    VContexts.push_back(VC); +  } while (EatIfPresent(lltok::comma)); +  // Sort value contexts so that ones with readonly ValueInfo are at the end +  // of VContexts vector. This is needed to match immutableRefCount() behavior. +  llvm::sort(VContexts, [](ValueContext &VC1, ValueContext &VC2) { +    return VC1.VI.isReadOnly() < VC2.VI.isReadOnly(); +  }); + +  IdToIndexMapType IdToIndexMap; +  for (auto &VC : VContexts) {      // Keep track of the Refs array index needing a forward reference.      // We will save the location of the ValueInfo needing an update, but      // can only do so once the std::vector is finalized. -    if (VI == EmptyVI) -      IdToIndexMap[GVId].push_back(std::make_pair(Refs.size(), Loc)); -    Refs.push_back(VI); -  } while (EatIfPresent(lltok::comma)); +    if (VC.VI.getRef() == FwdVIRef) +      IdToIndexMap[VC.GVId].push_back(std::make_pair(Refs.size(), VC.Loc)); +    Refs.push_back(VC.VI); +  }    // Now that the Refs vector is finalized, it is safe to save the locations    // of any forward GV references that need updating later.    for (auto I : IdToIndexMap) {      for (auto P : I.second) { -      assert(Refs[P.first] == EmptyVI && +      assert(Refs[P.first].getRef() == FwdVIRef &&               "Forward referenced ValueInfo expected to be empty");        auto FwdRef = ForwardRefValueInfos.insert(std::make_pair(            I.first, std::vector<std::pair<ValueInfo *, LocTy>>())); @@ -8253,6 +8276,27 @@ bool LLParser::ParseGVFlags(GlobalValueSummary::GVFlags &GVFlags) {    return false;  } +/// GVarFlags +///   ::= 'varFlags' ':' '(' 'readonly' ':' Flag ')' +bool LLParser::ParseGVarFlags(GlobalVarSummary::GVarFlags &GVarFlags) { +  assert(Lex.getKind() == lltok::kw_varFlags); +  Lex.Lex(); + +  unsigned Flag; +  if (ParseToken(lltok::colon, "expected ':' here") || +      ParseToken(lltok::lparen, "expected '(' here") || +      ParseToken(lltok::kw_readonly, "expected 'readonly' here") || +      ParseToken(lltok::colon, "expected ':' here")) +    return true; + +  ParseFlag(Flag); +  GVarFlags.ReadOnly = Flag; + +  if (ParseToken(lltok::rparen, "expected ')' here")) +    return true; +  return false; +} +  /// ModuleReference  ///   ::= 'module' ':' UInt  bool LLParser::ParseModuleReference(StringRef &ModulePath) { @@ -8273,18 +8317,20 @@ bool LLParser::ParseModuleReference(StringRef &ModulePath) {  /// GVReference  ///   ::= SummaryID  bool LLParser::ParseGVReference(ValueInfo &VI, unsigned &GVId) { +  bool ReadOnly = EatIfPresent(lltok::kw_readonly);    if (ParseToken(lltok::SummaryID, "expected GV ID"))      return true;    GVId = Lex.getUIntVal(); -    // Check if we already have a VI for this GV    if (GVId < NumberedValueInfos.size()) { -    assert(NumberedValueInfos[GVId] != EmptyVI); +    assert(NumberedValueInfos[GVId].getRef() != FwdVIRef);      VI = NumberedValueInfos[GVId];    } else      // We will create a forward reference to the stored location. -    VI = EmptyVI; +    VI = ValueInfo(false, FwdVIRef); +  if (ReadOnly) +    VI.setReadOnly();    return false;  } diff --git a/llvm/lib/AsmParser/LLParser.h b/llvm/lib/AsmParser/LLParser.h index 6f8962b6d4e..5a0fc297265 100644 --- a/llvm/lib/AsmParser/LLParser.h +++ b/llvm/lib/AsmParser/LLParser.h @@ -352,6 +352,7 @@ namespace llvm {      bool ParseVariableSummary(std::string Name, GlobalValue::GUID, unsigned ID);      bool ParseAliasSummary(std::string Name, GlobalValue::GUID, unsigned ID);      bool ParseGVFlags(GlobalValueSummary::GVFlags &GVFlags); +    bool ParseGVarFlags(GlobalVarSummary::GVarFlags &GVarFlags);      bool ParseOptionalFFlags(FunctionSummary::FFlags &FFlags);      bool ParseOptionalCalls(std::vector<FunctionSummary::EdgeTy> &Calls);      bool ParseHotness(CalleeInfo::HotnessType &Hotness); diff --git a/llvm/lib/AsmParser/LLToken.h b/llvm/lib/AsmParser/LLToken.h index dae1d41fd8c..836d9a06562 100644 --- a/llvm/lib/AsmParser/LLToken.h +++ b/llvm/lib/AsmParser/LLToken.h @@ -418,6 +418,7 @@ enum Kind {    kw_info,    kw_byte,    kw_bit, +  kw_varFlags,    // Unsigned Valued tokens (UIntVal).    GlobalID,   // @42  | 

