Fixed some of memory leaks and sigsev and bugs
authorBartosz Szatkowski <bulislaw@linux.com>
Fri, 20 Aug 2010 09:37:59 +0000 (11:37 +0200)
committerBartosz Szatkowski <bulislaw@linux.com>
Fri, 20 Aug 2010 09:37:59 +0000 (11:37 +0200)
Mainly fixed sigsev after fetching translation after removing
coresponding dictionary

trunk/src/base/backbone/BookmarkTranslations.h
trunk/src/base/backbone/backbone.cpp
trunk/src/base/backbone/backbone.h
trunk/src/includes/translation.h
trunk/src/plugins/xdxf/src/TranslationXdxf.cpp
trunk/src/plugins/xdxf/src/TranslationXdxf.h
trunk/src/plugins/xdxf/src/xdxfplugin.cpp

index 29ff21e..7f2dd6a 100644 (file)
@@ -59,14 +59,11 @@ public:
     QString toHtml() const {
         if(!_key.size() || !_bookmarks)
             return "";
-        qDebug() << ">toHtml";
 
         QStringList list = _bookmarks->search(_key, _dictionaryInfo);
-        qDebug() << "toHtml" << list.size();
         QString result;
         foreach(QString translation, list)
             result += translation + "\n";
-        qDebug() << "<toHtml";
         return result;
 
     }
index 4708367..e84c4aa 100644 (file)
 #include "backbone.h"
 #include <QDebug>
 
+int Backbone::_searchLimit;
+
+// Sadly QtConcurent mapped dont let me use something like calling method of
+// some class with supplied argument
 QString mappedSearch;
 QList<Translation*> mapSearch(CommonDictInterface *dict) {
     if(dict)
-        return dict->searchWordList(mappedSearch, 15);
+        return dict->searchWordList(mappedSearch, Backbone::_searchLimit);
     return QList<Translation*>();
 }
 
@@ -81,6 +85,7 @@ void Backbone::init() {
            QThreadPool::globalInstance()->maxThreadCount()+1);
 
    _history = new History(5, this);
+   _dictNum = 0;
 }
 
 
@@ -215,7 +220,7 @@ void Backbone::addDictionary(CommonDictInterface *dict, bool active) {
 
 
  void Backbone::addInternalDictionary(CommonDictInterface* dict, bool active) {
-     dict->setHash(_dicts.size()+1);
+     dict->setHash(++_dictNum);
      _dicts[dict] = active;
      connect(dict, SIGNAL(settingsChanged()), this, SLOT(dictUpdated()));
      connect(dict, SIGNAL(notify(Notify::NotifyType,QString)), this,
@@ -224,6 +229,7 @@ void Backbone::addDictionary(CommonDictInterface *dict, bool active) {
 
  void Backbone::removeDictionary(CommonDictInterface *dict) {
      _dicts.remove(dict);
+     delete dict;
      dictUpdated();
 
  }
@@ -400,6 +406,8 @@ void Backbone::loadDicts(QString fileName, bool _default) {
 
         set.endGroup();
         addInternalDictionary(plug->getNew(plugSet), active);
+      //  if(plugSet)
+        //    delete plugSet;
     }
 }
 
@@ -464,8 +472,10 @@ void Backbone::searchHtml(QList<Translation *> translations) {
 
     QList<TranslationPtr> dummy;
     stopped = false;
-    foreach(Translation* tr, translations)
-        dummy.append(TranslationPtr(tr));
+    foreach(Translation* tr, translations) {
+        if(containsDict(tr->dict()) || !tr->dict())
+            dummy.append(TranslationPtr(tr));
+  }
 
    _innerHtmlResult = QtConcurrent::mapped(dummy,
                                             &TranslationPtr::toHtml);
@@ -535,3 +545,14 @@ Settings* Backbone::settings() {
         settings->setValue("search_dictionaries", "false");
     return settings;
 }
+
+
+bool Backbone::containsDict(uint hash) const {
+    QHashIterator<CommonDictInterface*, bool> it(_dicts);
+    if (!hash)
+        return false;
+    while(it.hasNext())
+        if(it.next().key()->hash() == hash)
+            return true;
+    return false;
+}
index 693e322..36d344b 100644 (file)
      * search_limit - int, how many different word may each dictionary returns
      * search_dictionaries - true/false, whether search in dictionaries
      * search_bookmarks - true/false, whether search in bookmarks
+
+    Searching schema:
+        First GUI should ask for list of words matching given pattern
+        then eatch Translation object is capable of finging it own final translation
+
+      List of word:
+        - Gui call search(...)
+        - Backbone call plugins searchWordList(...) in idealThreadCount()+1 threads
+        - Backbone sets  the FutureWatcher to be notifed when plugins are done
+        - Backbone fetch results from Future<..> and formats it for gui then
+           emits ready()
+        - Gui calls result()
+
+      Final translation:
+         - Gui call searchHtml()
+         - Backbone starts for eatch translation object toHtml in separate threads
+         - Backbone sets FutureWatcher to be notified after last toHtml returns
+         - Backbone fetch translation from Future<...> objects and calls
+             htmlReady()
+         - gui calls htmlResult()
+
 */
 class Backbone : public QObject
 {
@@ -83,7 +104,10 @@ class Backbone : public QObject
 
 public:
     /*!\param pluginPath path to plugins (leave blank for default)
-      \param configPath path to folder with configuration files*/
+      \param configPath path to folder with configuration files
+      \param dry dry run is mode without paying attention to configuration etc
+          mainly for testing
+      */
     Backbone(QString pluginPath="", QString configPath="",
              bool dry = 0, QObject *parent = 0);
     ~Backbone();
@@ -107,6 +131,10 @@ public:
     //! \return final translation (after searching for html)
     QStringList htmls();
 
+    /*! maximum number of translation that each plugin may return; it must be
+        public static becouse of QtConcurent::mapped restrictions about
+        what kind of function may be used there see Qt docs */
+    static int _searchLimit;
 
 
 
@@ -135,13 +163,13 @@ public Q_SLOTS:
     void quit();
 
 
-    /*! Fired with given interval during searches -
-        checking if translation is ready
+    /*! Fired by FutureWatcher when list of words is ready (after calling search)
+        fetch Future<...> to final result
       */
     void translationReady();
 
-    /*! Fired with given interval during html searches -
-        checking if html is ready
+    /*! Fired by FutureWatcher when search result is ready, fetch Future to
+        final result
       */
     void htmlTranslationReady();
 
@@ -278,7 +306,7 @@ private:
     QString _pluginPath, _defaultPluginPath;
     QString _configPath;
     QString _defaultConfigPath;
-    int _searchLimit, _defaultSearchLimit;
+    int _defaultSearchLimit;
     int _historyLen, _defaultHistoryLen;
 
     bool dryRun; // mainly for testing - when true then dosent bother configs etc
@@ -303,6 +331,8 @@ private:
 
     CommonDictInterface* plugin(QString type); // search for given type plugin
     QList<CommonDictInterface*> activeDicts();
+    bool containsDict(uint hash) const;
+    int _dictNum;
 
     History* _history;
 
index c32e75d..6076583 100644 (file)
@@ -30,6 +30,7 @@
 
 #include <QString>
 #include <QMetaType>
+class CommonDictInterface;
 
 
 /*! Translation is kind of GoF proxy, it stores key:translation pair and
@@ -53,7 +54,7 @@ class Translation {
     virtual QString toHtml() const = 0;
 
     //! \retrun whether given translation is taken from bookmarks
-    bool isBookmark() const {
+    virtual bool isBookmark() const {
         return _bookmark;
    }
 
@@ -62,6 +63,9 @@ class Translation {
        _bookmark = b;
    }
 
+    //! returns coresponding dict object
+   virtual uint dict() const {return 0;} ;
+
    protected:
        bool _bookmark;
 
index 190e255..ee06a42 100644 (file)
 TranslationXdxf::TranslationXdxf() {
 }
 
-TranslationXdxf::TranslationXdxf(QString _key, QString _dictionaryInfo, XdxfPlugin *xdxfPlugin): _key(_key),_dictionaryInfo(_dictionaryInfo) {
+TranslationXdxf::TranslationXdxf(QString _key, QString _dictionaryInfo,
+         XdxfPlugin *xdxfPlugin): _key(_key),_dictionaryInfo(_dictionaryInfo) {
     this->xdxfPlugin=xdxfPlugin;
+    if(xdxfPlugin)
+        _dictHash = xdxfPlugin->hash();
 }
 
 QString TranslationXdxf::key() const {
@@ -39,11 +42,12 @@ QString TranslationXdxf::dictionaryInfo() const {
 
 QString TranslationXdxf::toHtml() const {
     QString result("");
-//    qDebug()<<xdxfPlugin->search(_key);
-    result+="<dict>" + _dictionaryInfo + "<key>" + _key + "</key>"  +xdxfPlugin->search(_key) + "</dict>";
+    if(!xdxfPlugin)
+        return result;
+    result+="<dict>" + _dictionaryInfo + "<key>" + _key + "</key>"  +
+            xdxfPlugin->search(_key) + "</dict>";
     result.replace("&","&amp;");
 
-//    qDebug()<<result;
     return result;
 }
 
index 81939d1..d85edc0 100644 (file)
@@ -50,10 +50,14 @@ public:
     void setDictionaryInfo(QString);
 
 
+    //! returns coresponding dict object
+    uint dict() const {return _dictHash;}
+
 private:
     QString _key;
     QString _dictionaryInfo;
     XdxfPlugin *xdxfPlugin;
+    int _dictHash;
 
 };
 
index b734e26..9f06587 100644 (file)
@@ -286,6 +286,7 @@ CommonDictInterface* XdxfPlugin::getNew(const Settings *settings) const {
            settings->value("generateCache") == "true") {
             plugin->makeCache("");
         }
+        delete settings;
     }
 
     plugin->getDictionaryInfo();
@@ -329,6 +330,7 @@ void XdxfPlugin::setSettings(Settings *settings) {
     else {
        _settings->setValue("cached", "false");
     }
+    delete settings;
 
     emit settingsChanged();
 }