mirror of
https://github.com/RPCSX/llvm.git
synced 2024-11-24 12:19:53 +00:00
Fix memory leak in error paths in YAMLTraits by using unique_ptr
There's some other cleanup that could happen here, but this is at least the mechanical transformation to unique_ptr. Derived from a patch by Anton Yartsev. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@217803 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
parent
3f0ce4fa18
commit
ec182fe2e5
@ -943,16 +943,17 @@ private:
|
||||
};
|
||||
|
||||
class MapHNode : public HNode {
|
||||
virtual void anchor();
|
||||
|
||||
public:
|
||||
MapHNode(Node *n) : HNode(n) { }
|
||||
virtual ~MapHNode();
|
||||
|
||||
static inline bool classof(const HNode *n) {
|
||||
return MappingNode::classof(n->_node);
|
||||
}
|
||||
static inline bool classof(const MapHNode *) { return true; }
|
||||
|
||||
typedef llvm::StringMap<HNode*> NameToNode;
|
||||
typedef llvm::StringMap<std::unique_ptr<HNode>> NameToNode;
|
||||
|
||||
bool isValidKey(StringRef key);
|
||||
|
||||
@ -961,19 +962,20 @@ private:
|
||||
};
|
||||
|
||||
class SequenceHNode : public HNode {
|
||||
virtual void anchor();
|
||||
|
||||
public:
|
||||
SequenceHNode(Node *n) : HNode(n) { }
|
||||
virtual ~SequenceHNode();
|
||||
|
||||
static inline bool classof(const HNode *n) {
|
||||
return SequenceNode::classof(n->_node);
|
||||
}
|
||||
static inline bool classof(const SequenceHNode *) { return true; }
|
||||
|
||||
std::vector<HNode*> Entries;
|
||||
std::vector<std::unique_ptr<HNode>> Entries;
|
||||
};
|
||||
|
||||
Input::HNode *createHNodes(Node *node);
|
||||
std::unique_ptr<Input::HNode> createHNodes(Node *node);
|
||||
void setError(HNode *hnode, const Twine &message);
|
||||
void setError(Node *node, const Twine &message);
|
||||
|
||||
|
@ -63,6 +63,8 @@ std::error_code Input::error() { return EC; }
|
||||
void Input::HNode::anchor() {}
|
||||
void Input::EmptyHNode::anchor() {}
|
||||
void Input::ScalarHNode::anchor() {}
|
||||
void Input::MapHNode::anchor() {}
|
||||
void Input::SequenceHNode::anchor() {}
|
||||
|
||||
bool Input::outputting() {
|
||||
return false;
|
||||
@ -82,7 +84,7 @@ bool Input::setCurrentDocument() {
|
||||
++DocIterator;
|
||||
return setCurrentDocument();
|
||||
}
|
||||
TopNode.reset(this->createHNodes(N));
|
||||
TopNode = this->createHNodes(N);
|
||||
CurrentNode = TopNode.get();
|
||||
return true;
|
||||
}
|
||||
@ -133,7 +135,7 @@ bool Input::preflightKey(const char *Key, bool Required, bool, bool &UseDefault,
|
||||
return false;
|
||||
}
|
||||
MN->ValidKeys.push_back(Key);
|
||||
HNode *Value = MN->Mapping[Key];
|
||||
HNode *Value = MN->Mapping[Key].get();
|
||||
if (!Value) {
|
||||
if (Required)
|
||||
setError(CurrentNode, Twine("missing required key '") + Key + "'");
|
||||
@ -159,7 +161,7 @@ void Input::endMapping() {
|
||||
return;
|
||||
for (const auto &NN : MN->Mapping) {
|
||||
if (!MN->isValidKey(NN.first())) {
|
||||
setError(NN.second, Twine("unknown key '") + NN.first() + "'");
|
||||
setError(NN.second.get(), Twine("unknown key '") + NN.first() + "'");
|
||||
break;
|
||||
}
|
||||
}
|
||||
@ -180,7 +182,7 @@ bool Input::preflightElement(unsigned Index, void *&SaveInfo) {
|
||||
return false;
|
||||
if (SequenceHNode *SQ = dyn_cast<SequenceHNode>(CurrentNode)) {
|
||||
SaveInfo = CurrentNode;
|
||||
CurrentNode = SQ->Entries[Index];
|
||||
CurrentNode = SQ->Entries[Index].get();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
@ -202,7 +204,7 @@ bool Input::preflightFlowElement(unsigned index, void *&SaveInfo) {
|
||||
return false;
|
||||
if (SequenceHNode *SQ = dyn_cast<SequenceHNode>(CurrentNode)) {
|
||||
SaveInfo = CurrentNode;
|
||||
CurrentNode = SQ->Entries[index];
|
||||
CurrentNode = SQ->Entries[index].get();
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
@ -253,8 +255,8 @@ bool Input::bitSetMatch(const char *Str, bool) {
|
||||
return false;
|
||||
if (SequenceHNode *SQ = dyn_cast<SequenceHNode>(CurrentNode)) {
|
||||
unsigned Index = 0;
|
||||
for (HNode *N : SQ->Entries) {
|
||||
if (ScalarHNode *SN = dyn_cast<ScalarHNode>(N)) {
|
||||
for (auto &N : SQ->Entries) {
|
||||
if (ScalarHNode *SN = dyn_cast<ScalarHNode>(N.get())) {
|
||||
if (SN->value().equals(Str)) {
|
||||
BitValuesUsed[Index] = true;
|
||||
return true;
|
||||
@ -277,7 +279,7 @@ void Input::endBitSetScalar() {
|
||||
assert(BitValuesUsed.size() == SQ->Entries.size());
|
||||
for (unsigned i = 0; i < SQ->Entries.size(); ++i) {
|
||||
if (!BitValuesUsed[i]) {
|
||||
setError(SQ->Entries[i], "unknown bit value");
|
||||
setError(SQ->Entries[i].get(), "unknown bit value");
|
||||
return;
|
||||
}
|
||||
}
|
||||
@ -302,7 +304,7 @@ void Input::setError(Node *node, const Twine &message) {
|
||||
EC = make_error_code(errc::invalid_argument);
|
||||
}
|
||||
|
||||
Input::HNode *Input::createHNodes(Node *N) {
|
||||
std::unique_ptr<Input::HNode> Input::createHNodes(Node *N) {
|
||||
SmallString<128> StringStorage;
|
||||
if (ScalarNode *SN = dyn_cast<ScalarNode>(N)) {
|
||||
StringRef KeyStr = SN->getValue(StringStorage);
|
||||
@ -313,18 +315,18 @@ Input::HNode *Input::createHNodes(Node *N) {
|
||||
memcpy(Buf, &StringStorage[0], Len);
|
||||
KeyStr = StringRef(Buf, Len);
|
||||
}
|
||||
return new ScalarHNode(N, KeyStr);
|
||||
return llvm::make_unique<ScalarHNode>(N, KeyStr);
|
||||
} else if (SequenceNode *SQ = dyn_cast<SequenceNode>(N)) {
|
||||
SequenceHNode *SQHNode = new SequenceHNode(N);
|
||||
auto SQHNode = llvm::make_unique<SequenceHNode>(N);
|
||||
for (Node &SN : *SQ) {
|
||||
HNode *Entry = this->createHNodes(&SN);
|
||||
auto Entry = this->createHNodes(&SN);
|
||||
if (EC)
|
||||
break;
|
||||
SQHNode->Entries.push_back(Entry);
|
||||
SQHNode->Entries.push_back(std::move(Entry));
|
||||
}
|
||||
return SQHNode;
|
||||
return std::move(SQHNode);
|
||||
} else if (MappingNode *Map = dyn_cast<MappingNode>(N)) {
|
||||
MapHNode *mapHNode = new MapHNode(N);
|
||||
auto mapHNode = llvm::make_unique<MapHNode>(N);
|
||||
for (KeyValueNode &KVN : *Map) {
|
||||
Node *KeyNode = KVN.getKey();
|
||||
ScalarNode *KeyScalar = dyn_cast<ScalarNode>(KeyNode);
|
||||
@ -341,14 +343,14 @@ Input::HNode *Input::createHNodes(Node *N) {
|
||||
memcpy(Buf, &StringStorage[0], Len);
|
||||
KeyStr = StringRef(Buf, Len);
|
||||
}
|
||||
HNode *ValueHNode = this->createHNodes(KVN.getValue());
|
||||
auto ValueHNode = this->createHNodes(KVN.getValue());
|
||||
if (EC)
|
||||
break;
|
||||
mapHNode->Mapping[KeyStr] = ValueHNode;
|
||||
mapHNode->Mapping[KeyStr] = std::move(ValueHNode);
|
||||
}
|
||||
return mapHNode;
|
||||
return std::move(mapHNode);
|
||||
} else if (isa<NullNode>(N)) {
|
||||
return new EmptyHNode(N);
|
||||
return llvm::make_unique<EmptyHNode>(N);
|
||||
} else {
|
||||
setError(N, "unknown node kind");
|
||||
return nullptr;
|
||||
@ -371,18 +373,6 @@ bool Input::canElideEmptySequence() {
|
||||
return false;
|
||||
}
|
||||
|
||||
Input::MapHNode::~MapHNode() {
|
||||
for (auto &N : Mapping)
|
||||
delete N.second;
|
||||
}
|
||||
|
||||
Input::SequenceHNode::~SequenceHNode() {
|
||||
for (HNode *N : Entries)
|
||||
delete N;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//===----------------------------------------------------------------------===//
|
||||
// Output
|
||||
//===----------------------------------------------------------------------===//
|
||||
|
Loading…
Reference in New Issue
Block a user