the endless quest to plug memory leaks -- episode 378
authorRobin Gareus <robin@gareus.org>
Mon, 25 Jul 2016 15:16:32 +0000 (17:16 +0200)
committerRobin Gareus <robin@gareus.org>
Mon, 25 Jul 2016 15:16:32 +0000 (17:16 +0200)
libs/ardour/ardour/control_protocol_manager.h
libs/ardour/control_protocol_manager.cc
libs/ardour/tempo.cc
libs/canvas/canvas/ruler.h
libs/canvas/ruler.cc
libs/evoral/src/ControlList.cpp
libs/pbd/pthread_utils.cc

index dbbb0c38913003c39e3281bbb8e879e68e6f9d8e..c6ea045ce10d090a6218ac549668552cc06fc4ed 100644 (file)
@@ -36,20 +36,21 @@ class ControlProtocolDescriptor;
 class Session;
 
 class LIBARDOUR_API ControlProtocolInfo {
-public:
-    ControlProtocolDescriptor* descriptor;
-    ControlProtocol* protocol;
-    std::string name;
-    std::string path;
-    bool requested;
-    bool mandatory;
-    bool supports_feedback;
-    XMLNode* state;
-
-    ControlProtocolInfo() : descriptor (0), protocol (0), requested(false),
+       public:
+               ControlProtocolDescriptor* descriptor;
+               ControlProtocol* protocol;
+               std::string name;
+               std::string path;
+               bool requested;
+               bool mandatory;
+               bool supports_feedback;
+               XMLNode* state;
+
+               ControlProtocolInfo() : descriptor (0), protocol (0), requested(false),
                mandatory(false), supports_feedback(false), state (0)
        {}
-    ~ControlProtocolInfo() { delete state; }
+               ~ControlProtocolInfo();
+
 };
 
 class LIBARDOUR_API ControlProtocolManager : public PBD::Stateful, public ARDOUR::SessionHandlePtr
index 2b0a4dce4cd71e5fb8ddb822cdbbbb9d718e35d6..a0a36c17dd2150480e4262d4caea12dd51a8fa14 100644 (file)
@@ -43,6 +43,22 @@ using namespace PBD;
 ControlProtocolManager* ControlProtocolManager::_instance = 0;
 const string ControlProtocolManager::state_node_name = X_("ControlProtocols");
 
+
+ControlProtocolInfo::~ControlProtocolInfo ()
+{
+       if (protocol && descriptor) {
+               descriptor->destroy (descriptor, protocol);
+               protocol = 0;
+       }
+
+       delete state; state = 0;
+
+       if (descriptor) {
+               delete (Glib::Module*) descriptor->module;
+               descriptor = 0;
+       }
+}
+
 ControlProtocolManager::ControlProtocolManager ()
 {
 }
@@ -434,6 +450,7 @@ ControlProtocolManager::set_state (const XMLNode& node, int /*version*/)
                        ControlProtocolInfo* cpi = cpi_by_name (prop->value());
 
                        if (cpi) {
+                               delete cpi->state;
                                cpi->state = new XMLNode (**citer);
 
                                if (active) {
index 793d96c663aed501b318396a70590f920721ea3a..56f88d33d9d6b080ccaab9e837afef4b422c91f6 100644 (file)
@@ -3471,6 +3471,7 @@ TempoMap::set_state (const XMLNode& node, int /*version*/)
                                catch (failed_constructor& err){
                                        error << _("Tempo map: could not set new state, restoring old one.") << endmsg;
                                        _metrics = old_metrics;
+                                       old_metrics.clear();
                                        break;
                                }
 
@@ -3484,6 +3485,7 @@ TempoMap::set_state (const XMLNode& node, int /*version*/)
                                catch (failed_constructor& err) {
                                        error << _("Tempo map: could not set new state, restoring old one.") << endmsg;
                                        _metrics = old_metrics;
+                                       old_metrics.clear();
                                        break;
                                }
                        }
@@ -3535,6 +3537,13 @@ TempoMap::set_state (const XMLNode& node, int /*version*/)
                }
 
                recompute_map (_metrics);
+
+               Metrics::const_iterator d = old_metrics.begin();
+               while (d != old_metrics.end()) {
+                       delete (*d);
+                       ++d;
+               }
+               old_metrics.clear ();
        }
 
        PropertyChanged (PropertyChange ());
index 0a2e43587e99821d92ca83b424ab119f0c34a87a..751ddcc104a6d2d7b9041fb6528b2722021f5cf1 100644 (file)
@@ -60,14 +60,18 @@ public:
        Ruler (Item*, const Metric& m);
        Ruler (Item*, const Metric& m, Rect const&);
 
+       virtual ~Ruler () {
+               delete _font_description;
+       }
+
        void set_range (double lower, double upper);
        void set_font_description (Pango::FontDescription);
        void set_metric (const Metric&);
 
        void render (Rect const & area, Cairo::RefPtr<Cairo::Context>) const;
 
-        void set_divide_colors (Color top, Color bottom);
-        void set_divide_height (double);
+       void set_divide_colors (Color top, Color bottom);
+       void set_divide_height (double);
 private:
        const Metric* _metric;
 
@@ -76,9 +80,9 @@ private:
 
        Coord         _lower;
        Coord         _upper;
-        double        _divide_height;
-        Color         _divider_color_top;
-        Color         _divider_color_bottom;
+       double        _divide_height;
+       Color         _divider_color_top;
+       Color         _divider_color_bottom;
 
        Pango::FontDescription* _font_description;
        mutable std::vector<Mark> marks;
index 74755f6eccced0de6772ee26109b4d24f86a3400..1c11def93a8b95a586cef2aa5c11b44ade1adc0b 100644 (file)
@@ -36,7 +36,8 @@ Ruler::Ruler (Canvas* c, const Metric& m)
        , _metric (&m)
        , _lower (0)
        , _upper (0)
-        , _divide_height (-1.0)
+       , _divide_height (-1.0)
+       , _font_description (0)
        , _need_marks (true)
 {
 }
@@ -46,7 +47,8 @@ Ruler::Ruler (Canvas* c, const Metric& m, Rect const& r)
        , _metric (&m)
        , _lower (0)
        , _upper (0)
-        , _divide_height (-1.0)
+       , _divide_height (-1.0)
+       , _font_description (0)
        , _need_marks (true)
 {
 }
@@ -56,7 +58,8 @@ Ruler::Ruler (Item* parent, const Metric& m)
        , _metric (&m)
        , _lower (0)
        , _upper (0)
-        , _divide_height (-1.0)
+       , _divide_height (-1.0)
+       , _font_description (0)
        , _need_marks (true)
 {
 }
@@ -66,7 +69,8 @@ Ruler::Ruler (Item* parent, const Metric& m, Rect const& r)
        , _metric (&m)
        , _lower (0)
        , _upper (0)
-        , _divide_height (-1.0)
+       , _divide_height (-1.0)
+       , _font_description (0)
        , _need_marks (true)
 {
 }
@@ -85,6 +89,7 @@ void
 Ruler::set_font_description (Pango::FontDescription fd)
 {
        begin_visual_change ();
+       delete _font_description;
        _font_description = new Pango::FontDescription (fd);
        end_visual_change ();
 }
index 2a013f26695e45394ab5026c362837e8908966f6..c665b69a5b2aecf68ff2f38e9c5b8eba1c059402 100644 (file)
@@ -139,6 +139,7 @@ ControlList::~ControlList()
        for (EventList::iterator x = _events.begin(); x != _events.end(); ++x) {
                delete (*x);
        }
+       _events.clear ();
 
        delete _curve;
 }
@@ -178,6 +179,9 @@ ControlList::copy_events (const ControlList& other)
 {
        {
                Glib::Threads::RWLock::WriterLock lm (_lock);
+               for (EventList::iterator x = _events.begin(); x != _events.end(); ++x) {
+                       delete (*x);
+               }
                _events.clear ();
                for (const_iterator i = other.begin(); i != other.end(); ++i) {
                        _events.push_back (new ControlEvent ((*i)->when, (*i)->value));
@@ -216,6 +220,9 @@ ControlList::clear ()
 {
        {
                Glib::Threads::RWLock::WriterLock lm (_lock);
+               for (EventList::iterator x = _events.begin(); x != _events.end(); ++x) {
+                       delete (*x);
+               }
                _events.clear ();
                unlocked_invalidate_insert_iterator ();
                mark_dirty ();
index 7cd25e42b86a23fd6ff1d1332ad6643c31f5282d..5daa60ac424aec37fd6252bd0d2c490f59af04e8 100644 (file)
@@ -146,7 +146,7 @@ pthread_set_name (const char *str)
 {
        /* copy string and delete it when exiting */
 
-       thread_name.set (strdup (str));
+       thread_name.set (strdup (str)); // leaks
 }
 
 const char *