]> gitweb.hamatoma.de Git - reqt/commitdiff
rebackgui works
authorhama <hama@siduction.net>
Sat, 30 Jan 2016 02:04:06 +0000 (03:04 +0100)
committerhama <hama@siduction.net>
Sat, 30 Jan 2016 02:04:06 +0000 (03:04 +0100)
14 files changed:
appl/rebackgui/BackupEngine.cpp
appl/rebackgui/BackupEngine.hpp
appl/rebackgui/BackupUtils.cpp
appl/rebackgui/mainwindow.cpp
appl/rebackgui/mainwindow.hpp
base/ReFileUtils.cpp
base/ReFileUtils.hpp
base/ReQStringUtils.cpp
base/ReQStringUtils.hpp
base/ReRandomizer.cpp
base/ReStringUtils.cpp
base/rebase.hpp
gui/ReGuiQueue.cpp
gui/ReGuiQueue.hpp

index 3950da99eebf63e84fe021780fded1a01213e6be..025c0a429b92627f99b16b37d597bcd1fd7793cd 100644 (file)
 
 bool BackupEngine::m_shouldStop = false;
 QStringList BackupEngine::m_files;
-qint64 BackupEngine::m_matchedBytes = 0;
+qint64 BackupEngine::m_hotBytes = 0;
+qint64 BackupEngine::m_processedBytes = 0;
+int BackupEngine::m_processedFiles = 0;
 int BackupEngine::m_matchedFiles = 0;
+int BackupEngine::m_hotFiles = 0;
 int BackupEngine::m_totalFiles = 0;
 int BackupEngine::m_totalDirs = 0;
 bool BackupEngine::m_searchReady = false;
@@ -100,16 +103,22 @@ void SearchTask::run()
 {
        qint64 start = QDateTime::currentMSecsSinceEpoch();
        m_searchReady = false;
+       QString targetDir, sourceDir;
        for (int ix = 0; ix < m_sourceDirs.size(); ix++){
-               processOneDirectory(m_sourceDirs.at(ix), m_targetBaseDir, ix);
+               sourceDir = m_sourceDirs.at(ix);
+               targetDir = m_targetDirs.at(ix) + ReFileUtils::nodeOf(sourceDir);
+               processOneDirectory(sourceDir, targetDir, ix);
        }
        m_searchReady = true;
-       m_mainWindow->externalLog(tr("%1 matching file(s) under %2 with %3 in %4 subdirs %5")
-                                                         .arg(m_matchedFiles).arg(m_totalFiles)
-                                                         .arg(ReQStringUtils::readableSize(m_matchedBytes))
-                                                         .arg(m_totalDirs)
-                                                         .arg(ReQStringUtils::readableDuration(
-                                                                          QDateTime::currentMSecsSinceEpoch() - start)));
+       m_mainWindow->externalLog(tr(
+               "Search finished: to copy: %1 with %2 matching: %3 total: %4 "
+               "subdirs: %5 runtime: %6")
+               .arg(m_hotFiles)
+               .arg(ReQStringUtils::readableSize(m_hotBytes))
+               .arg(m_matchedFiles).arg(m_totalFiles)
+                 .arg(m_totalDirs)
+                 .arg(ReQStringUtils::readableDuration(
+                                  QDateTime::currentMSecsSinceEpoch() - start)));
 }
 /**
  * Search the files to backup and write it to a list.
@@ -148,15 +157,21 @@ void SearchTask::processOneDirectory(const QString& source,
                   m_totalFiles++;
                   m_mutex.unlock();
           } else {
-                  bool doCopy = target.isEmpty();
-                  if (! doCopy){
+                  qint64 diff = 0;
+                  bool doCopy = false;
+                  if (target.isEmpty())
+                          doCopy = true;
+                  else {
                           QFileInfo trg(target + it.fileName());
                           if (! trg.exists())
                                   doCopy = true;
                           else {
                                   const QFileInfo src = it.fileInfo();
-                                  doCopy = trg.exists() && (trg.size() != src.size()
-                                          || src.lastModified() > trg.lastModified());
+                                  if (trg.size() != src.size())
+                                          doCopy = true;
+                                  else if ((diff = src.lastModified().toMSecsSinceEpoch()
+                                                  - trg.lastModified().toMSecsSinceEpoch()) > 2000)
+                                          doCopy = true;
                           }
                   }
                   if (doCopy){
@@ -166,10 +181,11 @@ void SearchTask::processOneDirectory(const QString& source,
                   m_mutex.lock();
                   if (doCopy){
                           m_files.append(info);
+                          m_hotFiles++;
+                          m_hotBytes += it.fileInfo().size();
                   }
                   m_totalFiles++;
                   m_matchedFiles++;
-                  m_matchedBytes += it.fileInfo().size();
                   m_mutex.unlock();
           }
        }
@@ -188,9 +204,11 @@ void SearchTask::processOneDirectory(const QString& source,
                           if (target.isEmpty())
                                   subTarget.clear();
                           else{
-                                  subTarget = target + it2.fileName() + OS_2nd_SEPARATOR_STR;
+                                  subTarget = target + it2.fileName();
                                   if (! ReFileUtils::isDirectory(subTarget))
                                           subTarget.clear();
+                                  else
+                                          subTarget += OS_SEPARATOR_STR;
                                   processOneDirectory(it2.filePath(), subTarget, index);
                                   m_mutex.lock();
                                   m_totalDirs++;
@@ -225,28 +243,36 @@ BackupTask::BackupTask(const QString& name,
  * @param relpath      the path relative to the base path, e.g. "abc/"
  * @param node         the node of source and target
  */
-void BackupTask::copyFile(int index, const QString& relPath, const QString& node){
+void BackupTask::copyFile(int index, const QString& relPath,
+               const QString& node){
+       qint64 start = QDateTime::currentMSecsSinceEpoch();
        QString source = m_sourceDirs.at(index) + relPath + node;
-    QString targetDir = m_targetDirs.at(index) + relPath;
-    QString target =  targetDir +  node;
-    ReQStringUtils::chomp(targetDir, OS_SEPARATOR);
-    bool isFile;
-    if (! ReFileUtils::isDirectory(targetDir, &isFile)){
-        if (isFile){
-            if (unlink(I18N::s2b(targetDir).constData()) != 0)
-                error(tr("cannot remove file (for making a directory (%1): %2")
-                      .arg(errno).arg(targetDir));
-        }
-        if (! ReFileUtils::makeDirWithParents(targetDir))
-            error(tr("cannot make directory (%1): %2").arg(errno).arg(targetDir));
-    }
-    QFile src(source);
-    unlink(I18N::s2b(target).constData());
-    if (! src.copy(target)){
-        error(tr("copy failed (%1): %2").arg(errno).arg(source));
-    } else {
-        m_mainWindow->addToFileList(source);
-    }
+       QString targetDir = m_targetDirs.at(index) + relPath;
+       QString target =  targetDir +  node;
+       ReQStringUtils::chomp(targetDir, OS_SEPARATOR);
+       bool isFile;
+       if (! ReFileUtils::isDirectory(targetDir, &isFile)){
+               if (isFile){
+                       if (unlink(I18N::s2b(targetDir).constData()) != 0)
+                               error(tr("cannot remove file (for making a directory (%1): %2")
+                                         .arg(errno).arg(targetDir));
+               }
+               if (! ReFileUtils::makeDirWithParents(targetDir))
+                       error(tr("cannot make directory (%1): %2").arg(errno).arg(targetDir));
+       }
+       QFileInfo info(source);
+       m_mainWindow->addToFileList(source + " " + ReQStringUtils::readableSize(info.size()));
+       m_processedFiles++;
+       m_processedBytes += info.size();
+
+       QString errorMsg = ReFileUtils::copy(source, target, &info, m_buffer);
+       if (! errorMsg.isEmpty()){
+               error(errorMsg);
+               m_mainWindow->expandFileList(errorMsg);
+       } else {
+               m_mainWindow->expandFileList(ReQStringUtils::readableDuration(
+                               QDateTime::currentMSecsSinceEpoch() - start));
+       }
 }
 
 /**
@@ -256,6 +282,7 @@ void BackupTask::run()
 {
        QString relPath, node;
        QString info;
+       qint64 start = QDateTime::currentMSecsSinceEpoch();
        while (true){
                m_mutex.lock();
                if (m_files.size() == 0)
@@ -279,7 +306,19 @@ void BackupTask::run()
                                relPath = info.mid(1, pos - 1);
                        node = info.mid(pos + 1);
                        copyFile(index, relPath, node);
+                       qint64 now = QDateTime::currentMSecsSinceEpoch();
+                       qint64 estimated = (now - start) * m_hotBytes /  max(1LL, m_processedBytes);
+                       m_mainWindow->externalAppend(ReGuiQueueItem::StatusLine, NULL,
+                                       tr("%1 of %2 (%3 of %4) %5 MB/sec Remaining: %6 of %7")
+                                       .arg(m_processedFiles).arg(m_hotFiles)
+                                                                                .arg(ReQStringUtils::readableSize(m_processedBytes))
+                                                                                .arg(ReQStringUtils::readableSize(m_hotBytes))
+                                                                                .arg(m_processedBytes / 1024.0 / 1024 / (now - start) * 1000, 0, 'f', 3)
+                                                                                .arg(ReQStringUtils::readableDuration(estimated - (now - start)))
+                                                                                .arg(ReQStringUtils::readableDuration(estimated)));
                }
        }
-       m_mainWindow->externalTaskFinished("ready");
+       m_mainWindow->externalTaskFinished(tr("backup complete after ")
+                               + ReQStringUtils::readableDuration(
+                                       QDateTime::currentMSecsSinceEpoch() - start));
 }
index 889294aea8bf0881e5ad10e747e4effc999a2147..07f0a1f5d2bb702e20975d3fdafe3e7cdc3d6b47 100644 (file)
@@ -33,7 +33,10 @@ protected:
 public:
    static bool m_shouldStop;
    static QStringList m_files;
-   static qint64 m_matchedBytes;
+   static qint64 m_hotBytes;
+   static int m_processedFiles;
+   static qint64 m_processedBytes;
+   static int m_hotFiles;
    static int m_matchedFiles;
    static int m_totalFiles;
    static int m_totalDirs;
@@ -69,9 +72,11 @@ public:
 public:
        virtual void run();
 protected:
-       void copyFile(int index, const QString& relpath, const QString& node);
+       void copyFile(int index, const QString& relpath,
+                                const QString& node);
 private:
        QString m_lastRelPath;
+       QByteArray m_buffer;
 };
 
 #endif // BACKUPPROCESSOR_HPP
index ee777f693d43aa6a417b7f7c429cfd70089d1e4d..df85b2708ce6b64c065b3b9922d0d7aa180fc00d 100644 (file)
@@ -19,8 +19,8 @@ BackupUtils::BackupUtils()
  */\r
 QString BackupUtils::dateToString(const QDateTime &dateTime)\r
 {\r
-    QString rc = dateTime.toString("yyyy.MM.dd/hh:mm:ss");\r
-    return rc;\r
+       QString rc = dateTime.toString("yyyy.MM.dd/hh:mm:ss");\r
+       return rc;\r
 }\r
 \r
 /**\r
@@ -35,33 +35,39 @@ QString BackupUtils::dateToString(const QDateTime &dateTime)
  */\r
 QString BackupUtils::findTarget(const BackupItem& item, ReLogger* logger)\r
 {\r
-    QString rc;\r
+       QString rc;\r
 #if defined __linux__\r
+       if (item.m_target.startsWith(";/")){\r
+               // the path is an absolute path on a fixed disk:\r
+               rc = item.m_target.mid(1);\r
+       } else {\r
+\r
+       }\r
 #elif defined _WIN32\r
-    QStringList drives = ReFileUtils::findRootDirs();\r
-    QStringList::const_iterator it;\r
-    for (it = drives.cbegin(); it != drives.cend(); ++it){\r
-        QString path = *it;\r
-        ReQStringUtils::ensureLastChar(path, OS_SEPARATOR);\r
-        int pos = item.m_target.indexOf(';');\r
-        if (pos >= 0)\r
-            path += item.m_target.mid(pos + 1);\r
-        else\r
-            path += item.m_target;\r
-        QString markerFile = nameOfTargetDescription(path);\r
-        if (QFileInfo(markerFile).exists()){\r
-            if (rc.isEmpty())\r
-                rc = ReFileUtils::parentOf(markerFile);\r
-            ReConfig config(I18N::s2b(markerFile), true, logger);\r
-            if (! config.asString((item.m_uid + ".created").toLatin1(),\r
-                                  "").isEmpty()){\r
-                rc =  ReFileUtils::parentOf(markerFile);\r
-                break;\r
-            }\r
-        }\r
-    }\r
+       QStringList drives = ReFileUtils::findRootDirs();\r
+       QStringList::const_iterator it;\r
+       for (it = drives.cbegin(); it != drives.cend(); ++it){\r
+               QString path = *it;\r
+               ReQStringUtils::ensureLastChar(path, OS_SEPARATOR);\r
+               int pos = item.m_target.indexOf(';');\r
+               if (pos >= 0)\r
+                       path += item.m_target.mid(pos + 1);\r
+               else\r
+                       path += item.m_target;\r
+               QString markerFile = nameOfTargetDescription(path);\r
+               if (QFileInfo(markerFile).exists()){\r
+                       if (rc.isEmpty())\r
+                               rc = ReFileUtils::parentOf(markerFile);\r
+                       ReConfig config(I18N::s2b(markerFile), true, logger);\r
+                       if (! config.asString((item.m_uid + ".created").toLatin1(),\r
+                                                                 "").isEmpty()){\r
+                               rc =  ReFileUtils::parentOf(markerFile);\r
+                               break;\r
+                       }\r
+               }\r
+       }\r
 #endif\r
-    return rc;\r
+       return rc;\r
 }\r
 \r
 /**\r
@@ -71,10 +77,10 @@ QString BackupUtils::findTarget(const BackupItem& item, ReLogger* logger)
  * @return      the full name of the file\r
  */\r
 QString BackupUtils::nameOfTargetDescription(const QString& path){\r
-    QString fname = path;\r
-    ReQStringUtils::ensureLastChar(fname, OS_SEPARATOR);\r
-    fname += ".rebackgui.target";\r
-    return fname;\r
+       QString fname = path;\r
+       ReQStringUtils::ensureLastChar(fname, OS_SEPARATOR);\r
+       fname += ".rebackgui.target";\r
+       return fname;\r
 }\r
 \r
 /**\r
@@ -88,17 +94,17 @@ QString BackupUtils::nameOfTargetDescription(const QString& path){
  * @return          <code>true</code>: target is already initialized\r
  */\r
 bool BackupUtils::prepareTarget(const QString& path, BackupItem &item,\r
-                                ReLogger* logger)\r
+                                                               ReLogger* logger)\r
 {\r
-    bool rc = false;\r
-    QString fname = nameOfTargetDescription(path);\r
-    ReConfig config(I18N::s2b(fname), false, logger);\r
-    QByteArray key = item.m_uid.toLatin1() + ".created";\r
-    if (config.asString(key.constData(), "").isEmpty()){\r
-        config.put(key, dateToString(QDateTime::currentDateTime()).toLatin1().constData());\r
-        rc = true;\r
-    }\r
-    return rc;\r
+       bool rc = false;\r
+       QString fname = nameOfTargetDescription(path);\r
+       ReConfig config(I18N::s2b(fname), false, logger);\r
+       QByteArray key = item.m_uid.toLatin1() + ".created";\r
+       if (config.asString(key.constData(), "").isEmpty()){\r
+               config.put(key, dateToString(QDateTime::currentDateTime()).toLatin1().constData());\r
+               rc = true;\r
+       }\r
+       return rc;\r
 }\r
 \r
 /**\r
@@ -109,9 +115,9 @@ bool BackupUtils::prepareTarget(const QString& path, BackupItem &item,
  */\r
 QDateTime BackupUtils::stringToDate(const QString &dateTime)\r
 {\r
-    QDateTime rc;\r
-    rc.fromString(dateTime, "yyyy.MM.dd/hh:mm:ss");\r
-    return rc;\r
+       QDateTime rc;\r
+       rc.fromString(dateTime, "yyyy.MM.dd/hh:mm:ss");\r
+       return rc;\r
 }\r
 \r
 \r
index 26b06a9e7a166fb4cd1200f8673df2e1cdda9e30..4a03b99a56291484f056eb79d4a3c9b40aa710ec 100644 (file)
@@ -93,6 +93,17 @@ void MainWindow::addToFileList(const QString info){
        externalAppend(ReGuiQueueItem::ListEnd, ui->listWidgetFile, info);
 }
 
+/**
+ * Appends a string to the current line in the filelist.
+ *
+ * Note: this method is called by a non main thread.
+ *
+ * @param info info to add
+ */
+void MainWindow::expandFileList(const QString info){
+       externalAppend(ReGuiQueueItem::ListAppendToCurrent, ui->listWidgetFile, info);
+}
+
 /**
  * Issues an error message.
  *
@@ -113,19 +124,19 @@ bool MainWindow::error(const QString& message){
  * @return      the relative path
  */
 QString MainWindow::extractTarget(const QString& dir){
-    QString rc;
-    QString target;
+       QString rc;
+       QString target;
 #if defined __linux__
 #elif defined _WIN32
-    rc = dir;
-    if (dir.length() >= 2 && dir.at(1) == ':')
-        rc.remove(0, 2);
-    if (rc.startsWith(OS_SEPARATOR_STR))
-        rc.remove(0, 1);
-    target = ";" + rc;
+       rc = dir;
+       if (dir.length() >= 2 && dir.at(1) == ':')
+               rc.remove(0, 2);
+       if (rc.startsWith(OS_SEPARATOR_STR))
+               rc.remove(0, 1);
+       target = ";" + rc;
 #endif
-    ui->lineEditTarget->setText(target);
-    return rc;
+       ui->lineEditTarget->setText(target);
+       return rc;
 }
 
 /**
@@ -285,11 +296,11 @@ void MainWindow::onSelectTarget(){
                        QFileDialog::ShowDirsOnly);
        if (!dir.isEmpty()){
                dir = ReFileUtils::nativePath(dir);
-        extractTarget(dir);
-        BackupItem& item = m_configuration.items()[m_currentRowConfiguration];
-        if (! BackupUtils::prepareTarget(dir, item, &m_logger))
-            say(LOG_INFO, tr("target initialized with %1")
-                .arg(BackupUtils::nameOfTargetDescription(dir)));
+               extractTarget(dir);
+               BackupItem& item = m_configuration.items()[m_currentRowConfiguration];
+               if (! BackupUtils::prepareTarget(dir, item, &m_logger))
+                       say(LOG_INFO, tr("target initialized with %1")
+                               .arg(BackupUtils::nameOfTargetDescription(dir)));
        }
 }
 /**
@@ -327,25 +338,33 @@ void MainWindow::onStart(){
        if (row < 0){
                say(LOG_ERROR, tr("no backup item selected"));
        } else {
-        const BackupItem& item = m_configuration.items().at(row);
+               const BackupItem& item = m_configuration.items().at(row);
                BackupEngine::m_searchReady = false;
-        QString target = BackupUtils::findTarget(item, &m_logger);
-        if (target.isEmpty()){
-            say(LOG_ERROR, tr("Target not available"));
-        } else {
-            ReQStringUtils::ensureLastChar(target, OS_SEPARATOR);
-            startStop(true);
-            delete m_searchTask;
-            m_searchTask = new SearchTask(item.m_name,
-                                          item.m_filePatterns, item.m_dirPatterns,
-                                          item.m_sources, target, this);
-            m_searchTask->start();
-            delete m_backupTask;
-            m_backupTask = new BackupTask(item.m_name, item.m_sources, target,
-                                          this);
-            m_backupTask->start();
-        }
-    }
+               BackupEngine::m_hotBytes = 0;
+               BackupEngine::m_hotFiles = 0;
+               BackupEngine::m_matchedFiles = 0;
+               BackupEngine::m_totalDirs = 0;
+               BackupEngine::m_totalFiles = 0;
+               BackupEngine::m_processedFiles = 0;
+               BackupEngine::m_processedBytes = 0;
+
+               QString target = BackupUtils::findTarget(item, &m_logger);
+               if (target.isEmpty()){
+                       say(LOG_ERROR, tr("Target not available"));
+               } else {
+                       ReQStringUtils::ensureLastChar(target, OS_SEPARATOR);
+                       startStop(true);
+                       delete m_searchTask;
+                       m_searchTask = new SearchTask(item.m_name,
+                                                                                 item.m_filePatterns, item.m_dirPatterns,
+                                                                                 item.m_sources, target, this);
+                       m_searchTask->start();
+                       delete m_backupTask;
+                       m_backupTask = new BackupTask(item.m_name, item.m_sources, target,
+                                                                                 this);
+                       m_backupTask->start();
+               }
+       }
 }
 /**
  * Stops the backup.
@@ -488,7 +507,7 @@ void MainWindow::updateTableRow(int row, BackupItem& item, QTableWidget* target)
                target->setItem(row, base + 0, new QTableWidgetItem(item.m_name));
                target->setItem(row, base + 1, new QTableWidgetItem(item.m_target));
                target->setItem(row, base + 2, new QTableWidgetItem(! item.m_lastBackup.isValid() ? "" :
-            BackupUtils::dateToString(item.m_lastBackup)));
+                       BackupUtils::dateToString(item.m_lastBackup)));
                target->setItem(row, base + 3, new QTableWidgetItem(item.m_sources.join(" ")));
        }
 }
index 0305348e8f18cedef09e797ce9c070ac2ce91db3..c3c96fcf9fde0d91ebe64b866c93e9d2d3723e1a 100644 (file)
@@ -26,6 +26,7 @@ public:
        void addToFileList(const QString info);
        QString buildTargetDir(const QString& target);
    bool error(const QString& message);
+   void expandFileList(const QString info);
    bool log(const QString& message);
    virtual bool say(ReLoggerLevel level, const QString& message);
    void setStatusMessage(bool error, const QString& message);
@@ -63,7 +64,7 @@ private:
        int m_currentRowBackup;
        QString m_lastSource;
        SearchTask* m_searchTask;
-    BackupTask* m_backupTask;
+       BackupTask* m_backupTask;
 };
 
 #endif // MAINWINDOW_HPP
index e2bae9ef35e81f857f148c4703c9f735703d8d5d..35a69f47ccf669552e62fde088091d9519b80582 100644 (file)
@@ -117,6 +117,76 @@ QString ReFileUtils::cleanPath(const QString& path) {
        return (QString) cleanPath(I18N::s2b(path).constData());
 }
 
+/**
+ * Copies a file with content and metadata (datetime, permissions).
+ *
+ * @param source               full path of the source file
+ * @param target               full path of the target name
+ * @param sourceInfo   NULL or the info about the surce
+ * @param buffer               IN/OUT: used as
+ * @return
+ */
+QString ReFileUtils::copy(const QString& source, const QString& target,
+                                               const QFileInfo* sourceInfo, QByteArray& buffer){
+       QString rc;
+       QByteArray source2 = I18N::s2b(source);
+       QByteArray target2 = I18N::s2b(target);
+       QFileInfo sourceInfo2;
+       if (sourceInfo == NULL){
+               sourceInfo2.setFile(source);
+               sourceInfo = &sourceInfo2;
+       }
+       if (! sourceInfo->exists())
+               rc = QObject::tr("not found: %1").arg(source);
+       else {
+               FILE* fpSource = fopen(source2.constData(), "rb");
+               if (fpSource == NULL){
+                       rc = QObject::tr("cannot open (%1): %2").arg(errno).arg(source);
+               } else {
+                       FILE* fpTarget = fopen(I18N::s2b(target).constData(), "wb");
+                       if (fpTarget == NULL){
+                               rc = QObject::tr("cannot open (%1): %2").arg(errno).arg(target);
+                       } else {
+                               qint64 filesize = sourceInfo->size();
+                               int blockSize = max(buffer.capacity(), 1024*1024);
+                               buffer.resize(blockSize);
+                               int readBytes, writeBytes;
+                               bool again = true;
+                               char* bufferPtr = buffer.data();
+                               qint64 totalBytes = 0;
+                               while(again){
+                                       if ( (readBytes = fread(bufferPtr, 1, blockSize, fpSource)) <= 0)
+                                               again = false;
+                                       if (readBytes > 0){
+                                               totalBytes += readBytes;
+                                               if ( (writeBytes = fwrite(bufferPtr, 1, readBytes, fpTarget))
+                                                        != readBytes){
+                                                       again = false;
+                                                       rc = QObject::tr("cannot write (%1): $2 [%3/%4]").arg(errno)
+                                                                       .arg(target).arg(readBytes).arg(writeBytes);
+                                               }
+                                       }
+                               }
+                               fclose(fpTarget);
+                               if (totalBytes < filesize)
+                                       rc = QObject::tr("file can be read only partitionally: %1 [%2/%3]")
+                                                       .arg(source).arg(totalBytes).arg(filesize);
+                               if (rc.isEmpty()){
+                                       if (! setTimes(target2, sourceInfo->lastModified(),
+                                                                  sourceInfo->lastRead()))
+                                               rc = QObject::tr("cannot set date/time (%1): %2")
+                                                               .arg(errno).arg(target);
+                                       if (! setPermissions(target2, sourceInfo->permissions()))
+                                               rc = QObject::tr("cannot set permissions (%1): %2")
+                                                               .arg(errno).arg(target);
+                               }
+                       }
+                       fclose(fpSource);
+               }
+       }
+       return rc;
+}
+
 /**
  * Delete a directory tree.
  *
@@ -230,7 +300,7 @@ QByteArray ReFileUtils::extensionOf(const char* filename) {
                        ix--;
                }
        }
-    return rc;
+       return rc;
 }
 
 /**
@@ -242,17 +312,17 @@ QByteArray ReFileUtils::extensionOf(const char* filename) {
  */
 QStringList ReFileUtils::findRootDirs()
 {
-    QStringList rc;
+       QStringList rc;
 #if defined __linux__
-    rc.append("/");
+       rc.append("/");
 #elif defined _WIN32
-    QFileInfoList drives = QDir::drives();
-    QFileInfoList::const_iterator it;
-    for (it = drives.cbegin(); it != drives.cend(); ++it){
-        rc.append(it->absolutePath().mid(0, 2));
-    }
+       QFileInfoList drives = QDir::drives();
+       QFileInfoList::const_iterator it;
+       for (it = drives.cbegin(); it != drives.cend(); ++it){
+               rc.append(it->absolutePath().mid(0, 2));
+       }
 #endif
-    return rc;
+       return rc;
 }
 
 /**
@@ -305,10 +375,10 @@ bool ReFileUtils::isDirectory(const QString& path, bool* isFile)
        if (rc){
                if (! info.isDir())
                        rc = false;
-        if (isFile != NULL)
-            *isFile = ! rc;
-    } else if (isFile != NULL)
-        *isFile = false;
+               if (isFile != NULL)
+                       *isFile = ! rc;
+       } else if (isFile != NULL)
+               *isFile = false;
        return rc;
 }
 
@@ -323,10 +393,41 @@ bool ReFileUtils::isRootDir(const char* path)
 #if defined __linux__
        return path[0] == OS_SEPARATOR && path[1] == '\0';
 #elif defined _WIN32
-    return isalpha(path[0]) &&  path[1] == ':' && path[2] == '\\' && path[3] == '\0';
+       return isalpha(path[0]) &&  path[1] == ':' && path[2] == '\\' && path[3] == '\0';
 #endif
 }
 
+/**
+ * Converts QT permissions into linux permissions.
+ *
+ * @param permissions  QT permissions,
+ *                                             e.g. <code>QFile::ReadOwner | QFile::WriteGroup</code>
+ * @return                             the permissions used by linux,
+ *                                             e.G. <code>S_IRUSR | S_IWGRP</code>
+ */
+mode_t ReFileUtils::linuxPermissions(QFile::Permissions permissions){
+       mode_t rc = 0;
+       if (permissions.testFlag(QFile::ReadOwner))
+               rc |= S_IRUSR;
+       if (permissions.testFlag(QFile::ReadGroup))
+               rc |= S_IRGRP;
+       if (permissions.testFlag(QFile::ReadOther))
+               rc |= S_IROTH;
+       if (permissions.testFlag(QFile::WriteOwner))
+               rc |= S_IWUSR;
+       if (permissions.testFlag(QFile::WriteGroup))
+               rc |= S_IWGRP;
+       if (permissions.testFlag(QFile::WriteOther))
+               rc |= S_IWOTH;
+       if (permissions.testFlag(QFile::ExeOwner))
+               rc |= S_IXUSR;
+       if (permissions.testFlag(QFile::ExeGroup))
+               rc |= S_IXGRP;
+       if (permissions.testFlag(QFile::ExeOther))
+               rc |= S_IXOTH;
+       return rc;
+}
+
 /**
  * Creates a directory (if not it does not exist) and logs errors.
  *
@@ -371,39 +472,40 @@ bool ReFileUtils::makeDir(const QString& path, ReLogger* logger) {
  *                                     <code>false</code>: error occurred
  */
 bool ReFileUtils::makeDirWithParents(const char* path, ReLogger* logger) {
-    struct stat info;
-    bool rc = false;
-    if (stat(path, &info) == 0 && S_ISDIR(info.st_mode)){
-        rc = true;
-    } else {
-        QByteArray dir = ReStringUtils::chomp(parentOf(path), OS_SEPARATOR);
-        if (stat(dir.constData(), &info) == 0 && S_ISDIR(info.st_mode))
-            rc = makeDir(path, logger);
-        else {
-            const char* end;
-            const char* start = path;
-            while (rc && (end = strchr(start, OS_SEPARATOR)) != NULL) {
-                if (end == path) {
-                    start++;
-                    dir += OS_SEPARATOR;
-                } else {
-                    dir.append(start, end - start);
-                    start = end + 1;
+       struct stat info;
+       bool rc = false;
+       if (stat(path, &info) == 0 && S_ISDIR(info.st_mode)){
+               rc = true;
+       } else {
+               QByteArray dir = parentOf(path);
+               ReStringUtils::chomp(dir, OS_SEPARATOR);
+               if (stat(dir.constData(), &info) == 0 && S_ISDIR(info.st_mode))
+                       rc = makeDir(path, logger);
+               else {
+                       const char* end;
+                       const char* start = path;
+                       while (rc && (end = strchr(start, OS_SEPARATOR)) != NULL) {
+                               if (end == path) {
+                                       start++;
+                                       dir += OS_SEPARATOR;
+                               } else {
+                                       dir.append(start, end - start);
+                                       start = end + 1;
 #if defined _WIN32
-                    if (dir.length() == 2 && dir.at(1) == ':')
-                        continue;
+                                       if (dir.length() == 2 && dir.at(1) == ':')
+                                               continue;
 #endif
-                    rc = makeDir(dir.constData(), logger);
-                    dir += OS_SEPARATOR;
-                }
-            }
-            if (rc && start[0] != '\0') {
-                dir.append(start);
-                rc = makeDir(dir.constData(), logger);
-            }
-        }
-    }
-    return rc;
+                                       rc = makeDir(dir.constData(), logger);
+                                       dir += OS_SEPARATOR;
+                               }
+                       }
+                       if (rc && start[0] != '\0') {
+                               dir.append(start);
+                               rc = makeDir(dir.constData(), logger);
+                       }
+               }
+       }
+       return rc;
 }
 
 /**
@@ -475,17 +577,17 @@ QByteArray ReFileUtils::nodeOf(const char* filename) {
  *                                     trailing separator
  */
 QString ReFileUtils::parentOf(const QString& filename) {
-    QString rc;
+       QString rc;
 
-    int ix = filename.size() - 1;
-    while (ix >= 0) {
-        if (filename[ix] == '/' || filename[ix] == '\\') {
-            rc = filename.mid(0, ix + 1);
-            break;
-        }
-        ix--;
-    }
-    return rc;
+       int ix = filename.size() - 1;
+       while (ix >= 0) {
+               if (filename[ix] == '/' || filename[ix] == '\\') {
+                       rc = filename.mid(0, ix + 1);
+                       break;
+               }
+               ix--;
+       }
+       return rc;
 }
 
 /**
@@ -498,17 +600,17 @@ QString ReFileUtils::parentOf(const QString& filename) {
  *                                     trailing separator
  */
 QByteArray ReFileUtils::parentOf(const char* filename) {
-    QByteArray rc;
+       QByteArray rc;
 
-    int ix = strlen(filename) - 1;
-    while (ix >= 0) {
-        if (filename[ix] == '/' || filename[ix] == '\\') {
-            rc.append(filename, ix + 1);
-            break;
-        }
-        ix--;
-    }
-    return rc;
+       int ix = strlen(filename) - 1;
+       while (ix >= 0) {
+               if (filename[ix] == '/' || filename[ix] == '\\') {
+                       rc.append(filename, ix + 1);
+                       break;
+               }
+               ix--;
+       }
+       return rc;
 }
 
 /**
@@ -680,6 +782,26 @@ void ReFileUtils::splitUrl(const QString& url, QString* protocol, QString* host,
        }
 }
 
+/**
+ * Sets the permissions.
+ *
+ * @param filename             name of the file to change
+ * @param permissions  the permissions to set.
+ * @param logger               the logger
+ * @return                             <code>true</code>: success
+ */
+bool ReFileUtils::setPermissions(const char* filename,
+               QFile::Permissions permissions, ReLogger* logger) {
+       bool rc = true;
+       if (chmod(filename, linuxPermissions(permissions)) != 0){
+               if (logger != NULL)
+                       logger->logv(LOG_ERROR, LOC_SET_TIMES_1,
+                                                "cannot change permissions (%d): $s", errno, filename);
+               rc = false;
+       }
+       return rc;
+}
+
 /**
  * Sets the filetimes.
  *
@@ -709,16 +831,16 @@ bool ReFileUtils::setTimes(const char* filename, const QDateTime& modified,
                rc = false;
        }
 #else
-    // ANSII-C:
-    struct utimbuf times;
-    times.actime = time_t(accessed.currentMSecsSinceEpoch() / 1000);
-    times.modtime = time_t(modified.currentMSecsSinceEpoch() / 1000);
-    int rc2 = utime(filename, &times);
-    if (rc2 != 0 && logger != NULL){
-        logger->logv(LOG_ERROR, LOC_SET_TIMES_1,
-            "cannot change times (%d): $s", errno, filename);
-        rc = false;
-    }
+       // ANSII-C:
+       struct utimbuf times;
+       times.actime = time_t(accessed.currentMSecsSinceEpoch() / 1000);
+       times.modtime = time_t(modified.currentMSecsSinceEpoch() / 1000);
+       int rc2 = utime(filename, &times);
+       if (rc2 != 0 && logger != NULL){
+               logger->logv(LOG_ERROR, LOC_SET_TIMES_1,
+                       "cannot change times (%d): $s", errno, filename);
+               rc = false;
+       }
 #endif
        return rc;
 }
@@ -737,7 +859,7 @@ int ReFileUtils::seek(FILE* file, int64_t offset, int whence) {
 #if defined __linux__
        rc = fseeko(file, offset, whence);
 #elif defined _WIN32
-    rc = _fseeki64(file, offset, whence);
+       rc = _fseeki64(file, offset, whence);
 #endif
        return rc;
 }
@@ -754,7 +876,7 @@ int64_t ReFileUtils::tell(FILE* file) {
 #if defined __linux__
        rc = ftello(file);
 #elif defined _WIN32
-    rc = _ftelli64(file);
+       rc = _ftelli64(file);
 #endif
        return rc;
 }
index db12853c30d7994c03e00209093732a1b922a975..2aed73313e4d142462c7ea0af9f69d344e6f9cc5 100644 (file)
@@ -32,6 +32,8 @@ public:
                ReLogger* logger = NULL);
        static QByteArray cleanPath(const char* path);
        static QString cleanPath(const QString& path);
+       static QString copy(const QString& source, const QString& target,
+                       const QFileInfo* sourceInfo, QByteArray& buffer);
        static QString extensionOf(const QString& filename);
        static QByteArray extensionOf(const char* filename);
        static QStringList findRootDirs();
@@ -39,6 +41,7 @@ public:
        static bool isAbsolutPath(const char* path);
        static bool isDirectory(const QString& path, bool* isFile = NULL);
        static bool isRootDir(const char* path);
+       static mode_t linuxPermissions(QFile::Permissions permissions);
        /** Returns a path with native separators.
         * QT under windows can operator with 2 separators: '\\' and '/'.
         * '\\' is the native separator.
@@ -79,6 +82,9 @@ public:
        static QString replaceExtension(const QString& path, const QString& ext);
        static QByteArray replaceExtension(const char* path, const char* ext);
        static int seek(FILE* file, int64_t offset, int whence);
+       static bool setPermissions(const char* filename,
+                                                          QFile::Permissions permissions,
+                                                          ReLogger* logger = NULL);
        static bool setTimes(const char* filename, const QDateTime& modified,
                const QDateTime& accessed = m_undefinedTime, ReLogger* logger = NULL);
        static void splitUrl(const QString& url, QString* protocol, QString* host,
index b5fcf726ffb5236359dafd0d18e4a3785ce8ab43..74d2c23435209bf182ab8e108e1b027fffcca2f7 100644 (file)
@@ -505,30 +505,30 @@ void ReQStringUtils::skipExpected(const ReString& text, QChar expected,
 /**
  * Returns a readable string for a duration given by <code>clock_t</code>.
  *
- * @param duration     a duration in msec
+ * @param durationMilliSec     a duration in msec
  *
  * @return     a string describing the duration.
  */
-QString ReQStringUtils::readableDuration(qint64 duration){
+QString ReQStringUtils::readableDuration(qint64 durationMilliSec){
        QString rc;
        char buffer[128];
-       double duration2 = (double) duration / 1000;
+       double duration2 = (double) durationMilliSec / 1000;
        if (duration2 < 60.0){
                rc = QString::number(duration2, 'f', 3) + " sec";
        } else if (duration2 < 3600.0){
                int duration3 = int(duration2);
-        _snprintf(buffer, sizeof buffer, "%d:%02d",
+               _snprintf(buffer, sizeof buffer, "%d:%02d",
                                 duration3 / 60, duration3 % 60);
                rc = buffer;
        } else if (duration2 < 3600.0 * 24){
                int duration3 = int(duration2);
-        _snprintf(buffer, sizeof buffer, "%d:%02d:%02d",
+               _snprintf(buffer, sizeof buffer, "%d:%02d:%02d",
                                 duration3 / 3600, duration3 % 3600 / 60,
                                 duration3 % 60);
                rc = buffer;
        } else {
                int duration3 = int(duration2);
-        _snprintf(buffer, sizeof buffer, "%d:%02d:%02d:%02d",
+               _snprintf(buffer, sizeof buffer, "%d:%02d:%02d:%02d",
                                 int(duration3 / (3600*24)),
                                 int(duration3 % (3600*24) / 3600), int(duration3 % 3600 / 60),
                                 int(duration3 % 60));
index a82853a908d6a80d65f7c8f265bf067b6486173d..bdb9f288db4035556ee3b03fddb1ce3493bce7d0 100644 (file)
@@ -73,7 +73,7 @@ public:
                return path;
 #endif
        }
-       static QString readableDuration(qint64 duration);
+       static QString readableDuration(qint64 durationMilliSec);
        static QString readableSize(int64_t filesize);
        static bool replacePlaceholders(QString& text,
                const QMap<QString, QString>& placeholders, QString* error);
index 92ce55f36ec75a462cc3454be1e4abff5ca412af..a2ad003134d1c3cdac4b26d4074596b5048de8e9 100644 (file)
@@ -10,6 +10,7 @@
  */
 
 #include "base/rebase.hpp"
+#include <QStorageInfo>
 //#define WITH_TRACE
 #include "retrace.hpp"
 enum {
@@ -365,17 +366,24 @@ const QByteArray& ReRandomizer::name() const {
  */
 ReRandomizer::seed_t ReRandomizer::pseudoTrueRandom(){
        clock_t random = clock();
-       time_t random2 = time(NULL);
+       quint64 random2 = QDateTime::currentMSecsSinceEpoch();
+       quint64 random3 = hash(QDir::homePath().toLatin1())
+                       + (hash(QDir::currentPath().toLocal8Bit()) << 15);
+       QStorageInfo storage = QStorageInfo::root();
+       qint64 random4 = storage.bytesAvailable();
+
        static int s_counter = 0;
        void* dummy2 = malloc(1);
        free(dummy2);
-       seed_t rc = (((seed_t) random2) << 31) + (seed_t) random
+       seed_t rc = (((seed_t) random2) << 25) + (seed_t) random
                + ((seed_t) &s_counter << 9)
+               + random3
                + ((-random ^ 0x20111958) ^ (seed_t(dummy2)));
        rc = (rc * m_primes64[int(rc % m_countPrimes)]
                        + (m_primes64[int((rc >> 13) % m_countPrimes)] >> 1))
                        ^ m_primes64[++s_counter % m_countPrimes];
-       rc = (rc << 56) | (uint64_t(rc) >> (64 - 56));
+
+       rc = ((rc << 56) | (quint64(rc) >> (64 - 56))) + random4;
        return rc;
 }
 
@@ -393,7 +401,7 @@ ReRandomizer::seed_t ReRandomizer::nearTrueRandom() {
                rc ^= buffer;
        close(fh);
 #endif
-    return rc;
+       return rc;
 }
 
 /**
@@ -404,16 +412,16 @@ ReRandomizer::seed_t ReRandomizer::nearTrueRandom() {
  */
 QByteArray ReRandomizer::buildUUID(bool readable)
 {
-    QByteArray uuid;
-    uint8_t buffer[2 * sizeof(seed_t)];
-    reinterpret_cast<seed_t*>(buffer)[0] = nearTrueRandom();
-    reinterpret_cast<seed_t*>(buffer)[1] = nearTrueRandom();
-    ReStringUtils::base64Encode(buffer, 12, uuid);
-    if (readable){
-        for (int ix = 12; ix > 0; ix -= 4)
-            uuid.insert(ix, '-');
-    }
-    return uuid;
+       QByteArray uuid;
+       uint8_t buffer[2 * sizeof(seed_t)];
+       reinterpret_cast<seed_t*>(buffer)[0] = nearTrueRandom();
+       reinterpret_cast<seed_t*>(buffer)[1] = nearTrueRandom();
+       ReStringUtils::base64Encode(buffer, 12, uuid);
+       if (readable){
+               for (int ix = 12; ix > 0; ix -= 4)
+                       uuid.insert(ix, '-');
+       }
+       return uuid;
 }
 
 /**
@@ -508,7 +516,7 @@ int64_t ReRandomizer::nextInt64(int64_t maxValue, int64_t minValue) {
                rc = minValue;
        else if (minValue == 0 && maxValue == LLONG_MAX)
                rc = abs((int64_t) seed);
-       else if (uint64_t(maxValue - minValue) < LLONG_MAX)
+       else if (qint64(maxValue - minValue) < LLONG_MAX)
                // no signed int64 overflow:
                rc = minValue + seed % (maxValue - minValue + 1);
        else {
@@ -847,7 +855,7 @@ ReRotateRandomizer::ReRotateRandomizer() :
 
 ReRandomizer::seed_t ReRotateRandomizer::nextSeed64() {
        seed_t rc = ReCongruentialGenerator::nextSeed64();
-       rc = ((rc << 33) | (uint64_t(rc) >> 31));
+       rc = ((rc << 33) | (quint64(rc) >> 31));
        ++m_counter;
        return rc;
 }
@@ -884,7 +892,7 @@ ReRandomizer::seed_t ReMultiCongruentialGenerator::nextSeed64() {
        seed_t rc = m_seeds[m_currentSeed] * m_primes64[ixFactor]
                        + (m_primes64[ixFactor + 1] >> 1);
        m_seeds[m_currentSeed] = rc;
-       rc = (rc << 33) | (uint64_t(rc) >> (64-33));
+       rc = (rc << 33) | (quint64(rc) >> (64-33));
        ++m_counter;
        return rc;
 }
@@ -1079,7 +1087,7 @@ void ReKISSRandomizer::saveSeed(QByteArray& seed) const {
  */
 QByteArray ReKISSRandomizer::state() const{
        char buffer[512];
-    _snprintf(buffer, sizeof buffer,
+       _snprintf(buffer, sizeof buffer,
                         "%2d: f: %016llx i: %016llx: c: %016llx x: %016llx y: %016llx z: %016llx",
                m_counter,
                (long long) m_factor, (long long) m_increment,
index 9e2c8ea6df0931fabeed897d55f18826d725f341..70391252bf3474a5c7f9ceec6127521cfa2d6762 100644 (file)
@@ -28,7 +28,7 @@ const char ReStringUtils::AUTO_SEPARATOR = '\0';
 
 const QByteArray ReStringUtils::m_empty;
 static const char* m_base64Chars =
-             "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
+                        "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
 
 
 /**
@@ -40,25 +40,25 @@ static const char* m_base64Chars =
  * @return              <code>output</code> (for chaining)
  */
 QByteArray& ReStringUtils::base64Decode(const char* input, int inputLength, QByteArray& output) {
-    static uint8_t decoder[256] = {0};
-    if (decoder['A'] == 0){
-        for (int ix = strlen(m_base64Chars) - 1; ix >= 0; ix--)
-            decoder[m_base64Chars[ix]] = ix;
-    }
-    int fillBytes = 0;
-    while(inputLength > 0 && input[inputLength - 1] == '='){
-        fillBytes++;
-        inputLength--;
-    }
-    output.resize((inputLength + 3) * 3 / 4);
-    uint8_t* outCursor = reinterpret_cast<uint8_t*>(output.data());
-    while(inputLength > 4){
-        *outCursor++ = decoder[(input[0] << 2) + ((input[1] & 0x30) >> 4)];
-        *outCursor++ = decoder[((input[1] & 0xf) << 4) + ((input[2] & 0x3c) >> 2)];
-        *outCursor++ = decoder[((input[2] & 0x3) << 6) + input[3]];
-        inputLength -= 4;
-        input += 4;
-    }
+       static uint8_t decoder[256] = {0};
+       if (decoder['A'] == 0){
+               for (int ix = strlen(m_base64Chars) - 1; ix >= 0; ix--)
+                       decoder[(int) m_base64Chars[ix]] = ix;
+       }
+       int fillBytes = 0;
+       while(inputLength > 0 && input[inputLength - 1] == '='){
+               fillBytes++;
+               inputLength--;
+       }
+       output.resize((inputLength + 3) * 3 / 4);
+       uint8_t* outCursor = reinterpret_cast<uint8_t*>(output.data());
+       while(inputLength > 4){
+               *outCursor++ = decoder[(input[0] << 2) + ((input[1] & 0x30) >> 4)];
+               *outCursor++ = decoder[((input[1] & 0xf) << 4) + ((input[2] & 0x3c) >> 2)];
+               *outCursor++ = decoder[((input[2] & 0x3) << 6) + input[3]];
+               inputLength -= 4;
+               input += 4;
+       }
   return output;
 }
 
@@ -74,23 +74,23 @@ QByteArray& ReStringUtils::base64Encode(uint8_t const* input, size_t inputLength
   output.resize(4 * ((inputLength + 2 - ((inputLength + 2) % 3)) / 3));
   uint8_t* outCursor = reinterpret_cast<uint8_t*>(output.data());
   while (inputLength-- > 3) {
-      *outCursor++ = m_base64Chars[(input[0] & 0xfc) >> 2];
-      *outCursor++ = m_base64Chars[((input[0] & 0x03) << 4) + ((input[1] & 0xf0) >> 4)];
-      *outCursor++ = m_base64Chars[((input[1] & 0x0f) << 2) + ((input[2] & 0xc0) >> 6)];
-      *outCursor++ = m_base64Chars[input[2] & 0x3f];
-      input += 3;
-      inputLength -= 3;
-    }
+         *outCursor++ = m_base64Chars[(input[0] & 0xfc) >> 2];
+         *outCursor++ = m_base64Chars[((input[0] & 0x03) << 4) + ((input[1] & 0xf0) >> 4)];
+         *outCursor++ = m_base64Chars[((input[1] & 0x0f) << 2) + ((input[2] & 0xc0) >> 6)];
+         *outCursor++ = m_base64Chars[input[2] & 0x3f];
+         input += 3;
+         inputLength -= 3;
+       }
   if (inputLength > 0){
-    uint8_t buffer[3];
-    memset(buffer, 0, sizeof buffer);
-    memcpy(buffer, input, 3 - inputLength);
-    *outCursor++ = m_base64Chars[(input[0] & 0xfc) >> 2];
-    *outCursor++ = m_base64Chars[((input[0] & 0x03) << 4) + ((input[1] & 0xf0) >> 4)];
-    *outCursor++ = m_base64Chars[((input[1] & 0x0f) << 2) + ((input[2] & 0xc0) >> 6)];
-    *outCursor++ = m_base64Chars[input[2] & 0x3f];
-    for (int ii = inputLength; ii <= 3; ii++)
-        *outCursor++ = '=';
+       uint8_t buffer[3];
+       memset(buffer, 0, sizeof buffer);
+       memcpy(buffer, input, 3 - inputLength);
+       *outCursor++ = m_base64Chars[(input[0] & 0xfc) >> 2];
+       *outCursor++ = m_base64Chars[((input[0] & 0x03) << 4) + ((input[1] & 0xf0) >> 4)];
+       *outCursor++ = m_base64Chars[((input[1] & 0x0f) << 2) + ((input[2] & 0xc0) >> 6)];
+       *outCursor++ = m_base64Chars[input[2] & 0x3f];
+       for (int ii = inputLength; ii <= 3; ii++)
+               *outCursor++ = '=';
   }
   return output;
 }
@@ -105,7 +105,7 @@ QByteArray& ReStringUtils::base64Encode(uint8_t const* input, size_t inputLength
  *                                     at the end of the string
  * @return                     <code>string</code>: for chaining
  */
-QByteArray&ReStringUtils::chomp(QByteArray& string, char cc)
+QByteArray& ReStringUtils::chomp(QByteArray& string, char cc)
 {
        int length;
        if (string.length() > 0 && string.at(length = string.length() - 1) == cc)
index e661449aad654962ce3f2d6dbf744c354b48abd1..2b9a535c2a6b73e21a1eda7b096d8769d4d65ecf 100644 (file)
@@ -77,6 +77,7 @@ typedef short int int16_t;
 #define _mkdir(path) mkdir(path, ALLPERMS)
 #define _rmdir rmdir
 #define _unlink unlink
+#define _snprintf snprintf
 //typedef qint64 uint64_t;
 #else
 #define S_ISDIR(mode) (((mode) & _S_IFDIR) != 0)
index 810eef020095ddb7a0e647e41de399c0b712e049..da230a0ba75a9d530e636fc7a18aa40219a49cae 100644 (file)
@@ -99,6 +99,22 @@ bool ReGuiQueueItem::apply() const
                        list->setCurrentRow(list->count() - 1);
                        break;
                }
+               case ListAppendToCurrent:
+               {
+                       QListWidget* list = reinterpret_cast<QListWidget*>(m_widget);
+                       int count = list->count();
+                       QListWidgetItem* item = list->item(count - 1);
+                       item->setText(item->text() + " " + m_value);
+                       break;
+               }
+               case ListReplaceCurrent:
+               {
+                       QListWidget* list = reinterpret_cast<QListWidget*>(m_widget);
+                       int count = list->count();
+                       QListWidgetItem* item = list->item(count - 1);
+                       item->setText(m_value);
+                       break;
+               }
                default:
                        rc = false;
                        break;
index 0b5775ef60eac9e46cc26e746daecaa4bc6498c7..97dd4c9fea1da93334712e7134ce541f2ee6fb29 100644 (file)
@@ -16,6 +16,7 @@ class ReGuiQueueItem {
 public:
        enum WidgetType {
                Undef, LabelText, NewTableRow, ListEnd, ListAppendToCurrent,
+               ListReplaceCurrent,
                LogMessage, LogError, ReadyMessage, StatusLine,
                UserDefined1, UserDefined2
        };