diff --git a/test/tools/llvm-rc/Inputs/tag-stringtable-basic.rc b/test/tools/llvm-rc/Inputs/tag-stringtable-basic.rc index afda2f3af63..7c929bb4a32 100644 Binary files a/test/tools/llvm-rc/Inputs/tag-stringtable-basic.rc and b/test/tools/llvm-rc/Inputs/tag-stringtable-basic.rc differ diff --git a/tools/llvm-rc/ResourceFileWriter.cpp b/tools/llvm-rc/ResourceFileWriter.cpp index d8d40141248..09b078c94cd 100644 --- a/tools/llvm-rc/ResourceFileWriter.cpp +++ b/tools/llvm-rc/ResourceFileWriter.cpp @@ -1246,7 +1246,8 @@ Error ResourceFileWriter::visitStringTableBundle(const RCResource *Res) { } Error ResourceFileWriter::insertStringIntoBundle( - StringTableInfo::Bundle &Bundle, uint16_t StringID, StringRef String) { + StringTableInfo::Bundle &Bundle, uint16_t StringID, + const std::vector &String) { uint16_t StringLoc = StringID & 15; if (Bundle.Data[StringLoc]) return createError("Multiple STRINGTABLE strings located under ID " + @@ -1261,13 +1262,15 @@ Error ResourceFileWriter::writeStringTableBundleBody(const RCResource *Base) { // The string format is a tiny bit different here. We // first output the size of the string, and then the string itself // (which is not null-terminated). - bool IsLongString; SmallVector Data; - RETURN_IF_ERROR(processString(Res->Bundle.Data[ID].getValueOr(StringRef()), - NullHandlingMethod::CutAtDoubleNull, - IsLongString, Data, Params.CodePage)); - if (AppendNull && Res->Bundle.Data[ID]) - Data.push_back('\0'); + if (Res->Bundle.Data[ID]) { + bool IsLongString; + for (StringRef S : *Res->Bundle.Data[ID]) + RETURN_IF_ERROR(processString(S, NullHandlingMethod::CutAtDoubleNull, + IsLongString, Data, Params.CodePage)); + if (AppendNull) + Data.push_back('\0'); + } RETURN_IF_ERROR( checkNumberFits(Data.size(), "STRINGTABLE string size")); writeInt(Data.size()); diff --git a/tools/llvm-rc/ResourceFileWriter.h b/tools/llvm-rc/ResourceFileWriter.h index 673830601e8..d545a7a9cab 100644 --- a/tools/llvm-rc/ResourceFileWriter.h +++ b/tools/llvm-rc/ResourceFileWriter.h @@ -103,7 +103,7 @@ public: using BundleKey = std::pair; // Each bundle is in fact an array of 16 strings. struct Bundle { - std::array, 16> Data; + std::array>, 16> Data; ObjectInfo DeclTimeInfo; uint16_t MemoryFlags; Bundle(const ObjectInfo &Info, uint16_t Flags) @@ -157,7 +157,8 @@ private: Error visitStringTableBundle(const RCResource *); Error writeStringTableBundleBody(const RCResource *); Error insertStringIntoBundle(StringTableInfo::Bundle &Bundle, - uint16_t StringID, StringRef String); + uint16_t StringID, + const std::vector &String); // User defined resource Error writeUserDefinedBody(const RCResource *); diff --git a/tools/llvm-rc/ResourceScriptParser.cpp b/tools/llvm-rc/ResourceScriptParser.cpp index 36b305645fb..2155985c61b 100644 --- a/tools/llvm-rc/ResourceScriptParser.cpp +++ b/tools/llvm-rc/ResourceScriptParser.cpp @@ -698,8 +698,14 @@ RCParser::ParseType RCParser::parseStringTableResource() { // between, however we strictly adhere to the single statement definition. ASSIGN_OR_RETURN(IDResult, readInt()); consumeOptionalType(Kind::Comma); + + std::vector Strings; ASSIGN_OR_RETURN(StrResult, readString()); - Table->addString(*IDResult, *StrResult); + Strings.push_back(*StrResult); + while (isNextTokenKind(Kind::String)) + Strings.push_back(read().value()); + + Table->addStrings(*IDResult, std::move(Strings)); } return std::move(Table); diff --git a/tools/llvm-rc/ResourceScriptStmt.cpp b/tools/llvm-rc/ResourceScriptStmt.cpp index a0d4adbe641..ef8c3454188 100644 --- a/tools/llvm-rc/ResourceScriptStmt.cpp +++ b/tools/llvm-rc/ResourceScriptStmt.cpp @@ -118,8 +118,12 @@ raw_ostream &MenuResource::log(raw_ostream &OS) const { raw_ostream &StringTableResource::log(raw_ostream &OS) const { OS << "StringTable:\n"; OptStatements->log(OS); - for (const auto &String : Table) - OS << " " << String.first << " => " << String.second << "\n"; + for (const auto &String : Table) { + OS << " " << String.first << " =>"; + for (const auto &S : String.second) + OS << " " << S; + OS << "\n"; + } return OS; } diff --git a/tools/llvm-rc/ResourceScriptStmt.h b/tools/llvm-rc/ResourceScriptStmt.h index b772732e78e..27fbea3ae8c 100644 --- a/tools/llvm-rc/ResourceScriptStmt.h +++ b/tools/llvm-rc/ResourceScriptStmt.h @@ -583,12 +583,12 @@ public: // Ref: msdn.microsoft.com/en-us/library/windows/desktop/aa381050(v=vs.85).aspx class StringTableResource : public OptStatementsRCResource { public: - std::vector> Table; + std::vector>> Table; StringTableResource(OptionalStmtList &&List, uint16_t Flags) : OptStatementsRCResource(std::move(List), Flags) {} - void addString(uint32_t ID, StringRef String) { - Table.emplace_back(ID, String); + void addStrings(uint32_t ID, std::vector &&Strings) { + Table.emplace_back(ID, Strings); } raw_ostream &log(raw_ostream &) const override; Twine getResourceTypeName() const override { return "STRINGTABLE"; }