From c86a027e88bbd5cbfb5fa603cf82bd185ef42b62 Mon Sep 17 00:00:00 2001 From: Jonathan G Rennison Date: Wed, 8 Feb 2017 21:46:32 +0000 Subject: [PATCH] Linkgraph: Use an arena allocator for path objects. Fixes leaks when job is aborted early. --- src/linkgraph/flowmapper.cpp | 7 ++----- src/linkgraph/linkgraphjob.h | 3 +++ src/linkgraph/mcf.cpp | 9 ++++++--- 3 files changed, 11 insertions(+), 8 deletions(-) diff --git a/src/linkgraph/flowmapper.cpp b/src/linkgraph/flowmapper.cpp index 04e8fd776f..e0fe90219e 100644 --- a/src/linkgraph/flowmapper.cpp +++ b/src/linkgraph/flowmapper.cpp @@ -60,10 +60,7 @@ void FlowMapper::Run(LinkGraphJob &job) const } } /* Clear paths. */ - PathList &paths = node.Paths(); - for (PathList::iterator i = paths.begin(); i != paths.end(); ++i) { - delete *i; - } - paths.clear(); + node.Paths().clear(); } + job.path_allocator.ResetArena(); } diff --git a/src/linkgraph/linkgraphjob.h b/src/linkgraph/linkgraphjob.h index 146ddc7117..cdab1ba99f 100644 --- a/src/linkgraph/linkgraphjob.h +++ b/src/linkgraph/linkgraphjob.h @@ -13,6 +13,7 @@ #define LINKGRAPHJOB_H #include "../thread/thread.h" +#include "../core/dyn_arena_alloc.hpp" #include "linkgraph.h" #include #include @@ -77,6 +78,8 @@ protected: public: + DynUniformArenaAllocator path_allocator; ///< Arena allocator used for paths + bool IsJobAborted() const; /** diff --git a/src/linkgraph/mcf.cpp b/src/linkgraph/mcf.cpp index 547f6ed5f0..7dcd7bf01c 100644 --- a/src/linkgraph/mcf.cpp +++ b/src/linkgraph/mcf.cpp @@ -378,8 +378,11 @@ void MultiCommodityFlow::Dijkstra(NodeID source_node, PathVector &paths) Tedge_iterator iter(this->job); uint size = this->job.Size(); paths.resize(size, NULL); + + this->job.path_allocator.SetParameters(sizeof(AnnosWrapper), (8192 - 32) / sizeof(AnnosWrapper)); + for (NodeID node = 0; node < size; ++node) { - AnnosWrapper *anno = new AnnosWrapper(node, node == source_node); + AnnosWrapper *anno = new (this->job.path_allocator.Allocate()) AnnosWrapper(node, node == source_node); anno->UpdateAnnotation(); anno->self_iter = annos.insert(AnnoSetItem(anno)).first; paths[node] = anno; @@ -431,12 +434,12 @@ void MultiCommodityFlow::CleanupPaths(NodeID source_id, PathVector &paths) path->Detach(); if (path->GetNumChildren() == 0) { paths[path->GetNode()] = NULL; - delete path; + this->job.path_allocator.Free(path); } path = parent; } } - delete source; + this->job.path_allocator.Free(source); paths.clear(); }