summaryrefslogtreecommitdiffstats
path: root/clang/utils/TableGen
diff options
context:
space:
mode:
authorBenjamin Kramer <benny.kra@googlemail.com>2016-02-13 18:11:49 +0000
committerBenjamin Kramer <benny.kra@googlemail.com>2016-02-13 18:11:49 +0000
commit1b5820133f16e12113e759096ad37db0a748b75d (patch)
tree73da2c4e2c7823e5ba0e2258d2384b3e4a1f4114 /clang/utils/TableGen
parentbcdb0f2ede595be12d12c44a68fb9dc6a27e730f (diff)
downloadbcm5719-llvm-1b5820133f16e12113e759096ad37db0a748b75d.tar.gz
bcm5719-llvm-1b5820133f16e12113e759096ad37db0a748b75d.zip
Fix a leak in the generated code for attributes with strings.
Storing std::strings in attributes simply doesn't work, we never call the destructor. Use an array of StringRefs instead of std::strings and copy the data into memory taken from the ASTContext. llvm-svn: 260831
Diffstat (limited to 'clang/utils/TableGen')
-rw-r--r--clang/utils/TableGen/ClangAttrEmitter.cpp21
1 files changed, 17 insertions, 4 deletions
diff --git a/clang/utils/TableGen/ClangAttrEmitter.cpp b/clang/utils/TableGen/ClangAttrEmitter.cpp
index c0574449acc..4a272d6bb79 100644
--- a/clang/utils/TableGen/ClangAttrEmitter.cpp
+++ b/clang/utils/TableGen/ClangAttrEmitter.cpp
@@ -81,7 +81,7 @@ static std::string ReadPCHRecord(StringRef type) {
.Case("TypeSourceInfo *", "GetTypeSourceInfo(F, Record, Idx)")
.Case("Expr *", "ReadExpr(F)")
.Case("IdentifierInfo *", "GetIdentifierInfo(F, Record, Idx)")
- .Case("std::string", "ReadString(Record, Idx)")
+ .Case("StringRef", "ReadString(Record, Idx)")
.Default("Record[Idx++]");
}
@@ -95,7 +95,7 @@ static std::string WritePCHRecord(StringRef type, StringRef name) {
.Case("Expr *", "AddStmt(" + std::string(name) + ");\n")
.Case("IdentifierInfo *",
"AddIdentifierRef(" + std::string(name) + ", Record);\n")
- .Case("std::string", "AddString(" + std::string(name) + ", Record);\n")
+ .Case("StringRef", "AddString(" + std::string(name) + ", Record);\n")
.Default("Record.push_back(" + std::string(name) + ");\n");
}
@@ -528,7 +528,9 @@ namespace {
: Argument(Arg, Attr), Type(T), ArgName(getLowerName().str() + "_"),
ArgSizeName(ArgName + "Size"), RangeName(getLowerName()) {}
- std::string getType() const { return Type; }
+ const std::string &getType() const { return Type; }
+ const std::string &getArgName() const { return ArgName; }
+ const std::string &getArgSizeName() const { return ArgSizeName; }
bool isVariadic() const override { return true; }
void writeAccessors(raw_ostream &OS) const override {
@@ -993,8 +995,19 @@ namespace {
class VariadicStringArgument : public VariadicArgument {
public:
VariadicStringArgument(const Record &Arg, StringRef Attr)
- : VariadicArgument(Arg, Attr, "std::string")
+ : VariadicArgument(Arg, Attr, "StringRef")
{}
+ void writeCtorBody(raw_ostream &OS) const override {
+ OS << " for (size_t I = 0, E = " << getArgSizeName() << "; I != E;\n"
+ " ++I) {\n"
+ " StringRef Ref = " << getUpperName() << "[I];\n"
+ " if (!Ref.empty()) {\n"
+ " char *Mem = new (Ctx, 1) char[Ref.size()];\n"
+ " std::memcpy(Mem, Ref.data(), Ref.size());\n"
+ " " << getArgName() << "[I] = StringRef(Mem, Ref.size());\n"
+ " }\n"
+ " }";
+ }
void writeValueImpl(raw_ostream &OS) const override {
OS << " OS << \"\\\"\" << Val << \"\\\"\";\n";
}
OpenPOWER on IntegriCloud