Index: src/PNaClTranslator.cpp |
diff --git a/src/PNaClTranslator.cpp b/src/PNaClTranslator.cpp |
index bde906ab8bee81be43aecfe6bb1f611ace8b6628..7271d944bca77db937d79753421fc1b8904d9953 100644 |
--- a/src/PNaClTranslator.cpp |
+++ b/src/PNaClTranslator.cpp |
@@ -732,21 +732,27 @@ void GlobalsParser::ProcessRecord() { |
installGlobalVar(); |
} |
-// Parses a valuesymtab block in the bitcode file. |
+/// Base class for parsing a valuesymtab block in the bitcode file. |
class ValuesymtabParser : public BlockParserBaseClass { |
- typedef SmallString<128> StringType; |
+ ValuesymtabParser(const ValuesymtabParser &) LLVM_DELETED_FUNCTION; |
+ void operator=(const ValuesymtabParser &) LLVM_DELETED_FUNCTION; |
public: |
- ValuesymtabParser(unsigned BlockID, BlockParserBaseClass *EnclosingParser, |
- bool AllowBbEntries) |
- : BlockParserBaseClass(BlockID, EnclosingParser), |
- AllowBbEntries(AllowBbEntries) {} |
+ ValuesymtabParser(unsigned BlockID, BlockParserBaseClass *EnclosingParser) |
+ : BlockParserBaseClass(BlockID, EnclosingParser) {} |
virtual ~ValuesymtabParser() LLVM_OVERRIDE {} |
+protected: |
+ typedef SmallString<128> StringType; |
+ |
+ // Associates Name with the value defined by the given Index. |
+ virtual void setValueName(uint64_t Index, StringType &Name) = 0; |
+ |
+ // Associates Name with the value defined by the given Index; |
+ virtual void setBbName(uint64_t Index, StringType &Name) = 0; |
+ |
private: |
- // True if entries to name basic blocks allowed. |
- bool AllowBbEntries; |
virtual void ProcessRecord() LLVM_OVERRIDE; |
@@ -767,25 +773,16 @@ void ValuesymtabParser::ProcessRecord() { |
if (!isValidRecordSizeAtLeast(2, "Valuesymtab value entry")) |
return; |
ConvertToString(ConvertedName); |
- Value *V = Context->getGlobalValueByID(Values[0]); |
- if (V == NULL) { |
- std::string Buffer; |
- raw_string_ostream StrBuf(Buffer); |
- StrBuf << "Invalid global address ID in valuesymtab: " << Values[0]; |
- Error(StrBuf.str()); |
- return; |
- } |
- V->setName(StringRef(ConvertedName.data(), ConvertedName.size())); |
+ setValueName(Values[0], ConvertedName); |
return; |
} |
case naclbitc::VST_CODE_BBENTRY: { |
// VST_BBENTRY: [BbId, namechar x N] |
- // For now, since we aren't processing function blocks, don't handle. |
- if (AllowBbEntries) { |
- Error("Valuesymtab bb entry not implemented"); |
+ if (!isValidRecordSizeAtLeast(2, "Valuesymtab basic block entry")) |
return; |
- } |
- break; |
+ ConvertToString(ConvertedName); |
+ setBbName(Values[0], ConvertedName); |
+ return; |
} |
default: |
break; |
@@ -795,10 +792,13 @@ void ValuesymtabParser::ProcessRecord() { |
return; |
} |
+class FunctionValuesymtabParser; |
+ |
/// Parses function blocks in the bitcode file. |
class FunctionParser : public BlockParserBaseClass { |
FunctionParser(const FunctionParser &) LLVM_DELETED_FUNCTION; |
FunctionParser &operator=(const FunctionParser &) LLVM_DELETED_FUNCTION; |
+ friend class FunctionValuesymtabParser; |
public: |
FunctionParser(unsigned BlockID, BlockParserBaseClass *EnclosingParser) |
@@ -812,6 +812,7 @@ public: |
Func->setReturnType(Context->convertToIceType(LLVMFunc->getReturnType())); |
Func->setInternal(LLVMFunc->hasInternalLinkage()); |
CurrentNode = InstallNextBasicBlock(); |
+ Func->setEntryNode(CurrentNode); |
for (Function::const_arg_iterator ArgI = LLVMFunc->arg_begin(), |
ArgE = LLVMFunc->arg_end(); |
ArgI != ArgE; ++ArgI) { |
@@ -1222,6 +1223,7 @@ void FunctionParser::ExitBlock() { |
Node->appendInst(Ice::InstUnreachable::create(Func)); |
} |
} |
+ Func->computePredecessors(); |
// Note: Once any errors have been found, we turn off all |
// translation of all remaining functions. This allows use to see |
// multiple errors, without adding extra checks to the translator |
@@ -1667,15 +1669,80 @@ void ConstantsParser::ProcessRecord() { |
} |
} |
+// Parses valuesymtab blocks appearing in a function block. |
+class FunctionValuesymtabParser : public ValuesymtabParser { |
+ FunctionValuesymtabParser(const FunctionValuesymtabParser &) |
+ LLVM_DELETED_FUNCTION; |
+ void operator=(const FunctionValuesymtabParser &) LLVM_DELETED_FUNCTION; |
+ |
+public: |
+ FunctionValuesymtabParser(unsigned BlockID, FunctionParser *EnclosingParser) |
+ : ValuesymtabParser(BlockID, EnclosingParser) {} |
+ |
+private: |
+ // Returns the enclosing function parser. |
+ FunctionParser *getFunctionParser() const { |
+ return reinterpret_cast<FunctionParser *>(GetEnclosingParser()); |
+ } |
+ |
+ virtual void setValueName(uint64_t Index, StringType &Name) LLVM_OVERRIDE; |
+ virtual void setBbName(uint64_t Index, StringType &Name) LLVM_OVERRIDE; |
+ |
+ // Reports that the assignment of Name to the value associated with |
+ // index is not possible, for the given Context. |
+ void reportUnableToAssign(const char *Context, uint64_t Index, |
+ StringType &Name) { |
+ std::string Buffer; |
+ raw_string_ostream StrBuf(Buffer); |
+ StrBuf << "Function-local " << Context << " name '" << Name |
+ << "' can't be associated with index " << Index; |
+ Error(StrBuf.str()); |
+ } |
+}; |
+ |
+void FunctionValuesymtabParser::setValueName(uint64_t Index, StringType &Name) { |
+ // Note: We check when Index is too small, so that we can error recover |
+ // (FP->getOperand will create fatal error). |
+ if (Index < getFunctionParser()->CachedNumGlobalValueIDs) { |
+ reportUnableToAssign("instruction", Index, Name); |
+ // TODO(kschimpf) Remove error recovery once implementation complete. |
+ return; |
+ } |
+ Ice::Operand *Op = getFunctionParser()->getOperand(Index); |
+ if (Ice::Variable *V = dyn_cast<Ice::Variable>(Op)) { |
+ std::string Nm(Name.data(), Name.size()); |
+ V->setName(Nm); |
+ } else { |
+ reportUnableToAssign("variable", Index, Name); |
+ } |
+} |
+ |
+void FunctionValuesymtabParser::setBbName(uint64_t Index, StringType &Name) { |
+ if (Index >= getFunctionParser()->Func->getNumNodes()) { |
+ reportUnableToAssign("block", Index, Name); |
+ return; |
+ } |
+ std::string Nm(Name.data(), Name.size()); |
+ getFunctionParser()->Func->getNodes()[Index]->setName(Nm); |
+} |
+ |
bool FunctionParser::ParseBlock(unsigned BlockID) { |
switch (BlockID) { |
case naclbitc::CONSTANTS_BLOCK_ID: { |
ConstantsParser Parser(BlockID, this); |
return Parser.ParseThisBlock(); |
} |
+ case naclbitc::VALUE_SYMTAB_BLOCK_ID: { |
+ if (PNaClAllowLocalSymbolTables) { |
+ FunctionValuesymtabParser Parser(BlockID, this); |
+ return Parser.ParseThisBlock(); |
+ } |
+ break; |
+ } |
default: |
- return BlockParserBaseClass::ParseBlock(BlockID); |
+ break; |
} |
+ return BlockParserBaseClass::ParseBlock(BlockID); |
} |
/// Parses the module block in the bitcode file. |
@@ -1692,6 +1759,42 @@ protected: |
virtual void ProcessRecord() LLVM_OVERRIDE; |
}; |
+class ModuleValuesymtabParser : public ValuesymtabParser { |
+ ModuleValuesymtabParser(const ModuleValuesymtabParser &) |
+ LLVM_DELETED_FUNCTION; |
+ void operator=(const ModuleValuesymtabParser &) LLVM_DELETED_FUNCTION; |
+ |
+public: |
+ ModuleValuesymtabParser(unsigned BlockID, ModuleParser *MP) |
+ : ValuesymtabParser(BlockID, MP) {} |
+ |
+ virtual ~ModuleValuesymtabParser() LLVM_OVERRIDE {} |
+ |
+private: |
+ virtual void setValueName(uint64_t Index, StringType &Name) LLVM_OVERRIDE; |
+ virtual void setBbName(uint64_t Index, StringType &Name) LLVM_OVERRIDE; |
+}; |
+ |
+void ModuleValuesymtabParser::setValueName(uint64_t Index, StringType &Name) { |
+ Value *V = Context->getGlobalValueByID(Index); |
+ if (V == NULL) { |
+ std::string Buffer; |
+ raw_string_ostream StrBuf(Buffer); |
+ StrBuf << "Invalid global address ID in valuesymtab: " << Index; |
+ Error(StrBuf.str()); |
+ return; |
+ } |
+ V->setName(StringRef(Name.data(), Name.size())); |
+} |
+ |
+void ModuleValuesymtabParser::setBbName(uint64_t Index, StringType &Name) { |
+ std::string Buffer; |
+ raw_string_ostream StrBuf(Buffer); |
+ StrBuf << "Can't define basic block name at global level: '" << Name |
+ << "' -> " << Index; |
+ Error(StrBuf.str()); |
+} |
+ |
bool ModuleParser::ParseBlock(unsigned BlockID) LLVM_OVERRIDE { |
switch (BlockID) { |
case naclbitc::BLOCKINFO_BLOCK_ID: |
@@ -1705,7 +1808,7 @@ bool ModuleParser::ParseBlock(unsigned BlockID) LLVM_OVERRIDE { |
return Parser.ParseThisBlock(); |
} |
case naclbitc::VALUE_SYMTAB_BLOCK_ID: { |
- ValuesymtabParser Parser(BlockID, this, false); |
+ ModuleValuesymtabParser Parser(BlockID, this); |
return Parser.ParseThisBlock(); |
} |
case naclbitc::FUNCTION_BLOCK_ID: { |