From 10a8921bbcd9802ad2425e8cee1e5ca70fb0b241 Mon Sep 17 00:00:00 2001 From: Arno Date: Wed, 13 Jun 2018 09:27:59 +0200 Subject: Speed up file copy Hmm, as it turns out QFile does a much better, e.g. faster, job than my open-coded file copy with a progress dialog. I always wondered why it only did 150-170Mbit. I thought that it was just the calculation, but now I have 400 Mbit, and it still stalls at 150 Mbit. QFile::copy maxes out the line, so get rid of the ProgressDialog and show a status message instead. Copy can be canceled by the context menu, but FileCopier will always finish the current file, because I don't want to lock and unlock the CancelMutex during copy. Besides, QFile::copy doesn't admit that :) --- filecopier.cpp | 61 ++++++++++++++-------------------------------------------- 1 file changed, 14 insertions(+), 47 deletions(-) (limited to 'filecopier.cpp') diff --git a/filecopier.cpp b/filecopier.cpp index 1588d6e..6256be1 100644 --- a/filecopier.cpp +++ b/filecopier.cpp @@ -1,6 +1,5 @@ #include #include -#include #include "filecopier.h" @@ -15,11 +14,8 @@ void FileCopier::addJob(const QString &source, const QString &dest){ } void FileCopier::run(){ - int bufsize = 32 * 1024 * 1024; - char *buf = new char[bufsize]; mCancel = false; mCopied = 0; - QElapsedTimer et; while(!mJobs.isEmpty()){ mAddJobMutex.lock(); auto first = mJobs.constBegin(); @@ -27,58 +23,29 @@ void FileCopier::run(){ auto dest = first.value(); mJobs.remove(source); mAddJobMutex.unlock(); + QString msg = QString(tr("Copy: %1 (%2/%3)")).arg(source).arg(QString::number(mCopied + 1)).arg(QString::number(mTotal)); + emit message(msg); QFile sFile(source); - QFile dFile(dest); - bool openSource = sFile.open(QIODevice::ReadOnly); - bool openDest = dFile.open(QIODevice::WriteOnly); - if(!openSource || !openDest){ - emit success(false, source); - goto cleanup; + if(sFile.copy(dest)){ + ++mCopied; + QString msg = QString(tr("Copied file %1/%2").arg(QString::number(mCopied)).arg(QString::number(mTotal))); + emit message(msg); + }else{ + QString msg = QString(tr("Failed to copy %1: %2").arg(source).arg(sFile.errorString())); + emit message(msg); } - emit newFile(source, dest, sFile.size()); - int read = 0; - qint64 total = 0; - qint64 elapsed = 0; - qint64 bytesSinceEl = 0; - et.start(); - while(!sFile.atEnd()){ - read = sFile.read(buf, bufsize); - dFile.write(buf, read); - total += read; - bytesSinceEl += read; - elapsed = et.elapsed(); - if(elapsed > 1000){ - mCancelMutex.lock(); - bool cancel = mCancel; - mCancelMutex.unlock(); - if(cancel){ - dFile.close(); - QFile::remove(dest); - emit success(false, source); - goto cleanup; - } - mCountMutex.lock(); - emit bytesReadIntval(bytesSinceEl, elapsed, mTotal, mCopied); - mCountMutex.unlock(); - elapsed = 0; - bytesSinceEl = 0; - et.restart(); - } - emit bytesRead(total); + QMutexLocker l(&mCancelMutex); + if(mCancel){ + break; } - emit success(true, source); - ++mCopied; - emit bytesReadIntval(bytesSinceEl, elapsed, mTotal, mCopied); - et.restart(); } - - cleanup: - delete buf; + mCancel = false; mTotal = 0; mJobs.clear(); } void FileCopier::cancel(){ QMutexLocker l(&mCancelMutex); + emit message(tr("Canceling copy jobs. Please wait...")); mCancel = true; } -- cgit v1.2.3-70-g09d2